#ifdef WIN32
#define CORE_PRIVATE
#include "httpd.h"
#include "http_config.h"
#include "http_core.h"
#include "http_protocol.h"
#include "http_request.h"
#include "http_log.h"
#include "util_script.h"
#include <stdlib.h>
#include <HttpExt.h>
#define RELAX_HEADER_RULE
#if !defined(HSE_REQ_SEND_RESPONSE_HEADER_EX) \
|| !defined(HSE_REQ_MAP_URL_TO_PATH_EX)
#pragma message("WARNING: This build of Apache is missing the recent changes")
#pragma message("in the Microsoft Win32 Platform SDK; some mod_isapi features")
#pragma message("will be disabled. To obtain the latest Platform SDK files,")
#pragma message("please refer to:")
#endif
module isapi_module;
static
DWORD
ReadAheadBuffer = 49152;
static
int
LogNotSupported = -1;
static
int
AppendLogToErrors = 0;
static
int
AppendLogToQuery = 0;
typedef
struct
{
LPEXTENSION_CONTROL_BLOCK ecb;
request_rec *r;
int
status;
} isapi_cid;
BOOL
WINAPI GetServerVariable (HCONN hConn,
LPSTR
lpszVariableName,
LPVOID
lpvBuffer,
LPDWORD
lpdwSizeofBuffer);
BOOL
WINAPI WriteClient (HCONN ConnID,
LPVOID
Buffer,
LPDWORD
lpwdwBytes,
DWORD
dwReserved);
BOOL
WINAPI ReadClient (HCONN ConnID,
LPVOID
lpvBuffer,
LPDWORD
lpdwSize);
BOOL
WINAPI ServerSupportFunction (HCONN hConn,
DWORD
dwHSERequest,
LPVOID
lpvBuffer,
LPDWORD
lpdwSize,
LPDWORD
lpdwDataType);
#pragma optimize("y",off)
int
isapi_handler (request_rec *r) {
LPEXTENSION_CONTROL_BLOCK ecb =
ap_pcalloc(r->pool,
sizeof
(
struct
_EXTENSION_CONTROL_BLOCK));
HSE_VERSION_INFO *pVer = ap_pcalloc(r->pool,
sizeof
(HSE_VERSION_INFO));
HINSTANCE
isapi_handle;
BOOL
(*isapi_version)(HSE_VERSION_INFO *);
DWORD
(*isapi_entry)(LPEXTENSION_CONTROL_BLOCK);
BOOL
(*isapi_term)(
DWORD
);
isapi_cid *cid = ap_pcalloc(r->pool,
sizeof
(isapi_cid));
table *e = r->subprocess_env;
DWORD
read;
char
*p;
int
retval;
int
res;
if
(!(ap_allow_options(r) & OPT_EXECCGI))
return
FORBIDDEN;
if
(r->finfo.st_mode == 0)
return
NOT_FOUND;
if
(S_ISDIR(r->finfo.st_mode))
return
FORBIDDEN;
if
(!(isapi_handle = ap_os_dso_load(r->filename))) {
ap_log_rerror(APLOG_MARK, APLOG_ALERT, r,
"ISAPI Could not load DLL: %s"
, r->filename);
return
SERVER_ERROR;
}
if
(!(isapi_version =
(
void
*)(ap_os_dso_sym(isapi_handle,
"GetExtensionVersion"
)))) {
ap_log_rerror(APLOG_MARK, APLOG_ALERT, r,
"DLL could not load GetExtensionVersion(): %s"
,
r->filename);
ap_os_dso_unload(isapi_handle);
return
SERVER_ERROR;
}
if
(!(isapi_entry =
(
void
*)(ap_os_dso_sym(isapi_handle,
"HttpExtensionProc"
)))) {
ap_log_rerror(APLOG_MARK, APLOG_ALERT, r,
"DLL could not load HttpExtensionProc(): %s"
,
r->filename);
ap_os_dso_unload(isapi_handle);
return
SERVER_ERROR;
}
isapi_term = (
void
*)(ap_os_dso_sym(isapi_handle,
"TerminateExtension"
));
if
(!(*isapi_version)(pVer)) {
ap_log_rerror(APLOG_MARK, APLOG_ALERT, r,
"ISAPI GetExtensionVersion() failed: %s"
, r->filename);
ap_os_dso_unload(isapi_handle);
return
SERVER_ERROR;
}
ap_add_common_vars(r);
ap_add_cgi_vars(r);
ap_table_setn(r->subprocess_env,
"UNMAPPED_REMOTE_USER"
,
"REMOTE_USER"
);
ap_table_setn(r->subprocess_env,
"SERVER_PORT_SECURE"
,
"0"
);
ap_table_setn(r->subprocess_env,
"URL"
, r->uri);
ecb->ConnID = (HCONN)cid;
cid->ecb = ecb;
cid->r = r;
cid->status = 0;
ecb->cbSize =
sizeof
(
struct
_EXTENSION_CONTROL_BLOCK);
ecb->dwVersion = MAKELONG(0, 2);
ecb->dwHttpStatusCode = 0;
strcpy
(ecb->lpszLogData,
""
);
ecb->lpszMethod = ap_pstrdup(r->pool, r->method);
ecb->lpszQueryString = ap_pstrdup(r->pool, ap_table_get(e,
"QUERY_STRING"
));
ecb->lpszPathInfo = ap_pstrdup(r->pool, ap_table_get(e,
"PATH_INFO"
));
ecb->lpszPathTranslated = ap_pstrdup(r->pool, ap_table_get(e,
"PATH_TRANSLATED"
));
ecb->lpszContentType = ap_pstrdup(r->pool, ap_table_get(e,
"CONTENT_TYPE"
));
if
((retval = ap_setup_client_block(r, REQUEST_CHUNKED_ERROR))) {
if
(isapi_term) (*isapi_term)( 2
);
ap_os_dso_unload(isapi_handle);
return
retval;
}
if
(ap_should_client_block(r)) {
if
(r->remaining) {
ecb->cbTotalBytes = r->remaining;
if
(ecb->cbTotalBytes > ReadAheadBuffer)
ecb->cbAvailable = ReadAheadBuffer;
else
ecb->cbAvailable = ecb->cbTotalBytes;
}
else
{
ecb->cbTotalBytes = 0xffffffff;
ecb->cbAvailable = ReadAheadBuffer;
}
ecb->lpbData = ap_pcalloc(r->pool, ecb->cbAvailable + 1);
p = ecb->lpbData;
read = 0;
while
(read < ecb->cbAvailable &&
((res = ap_get_client_block(r, ecb->lpbData + read,
ecb->cbAvailable - read)) > 0)) {
read += res;
}
if
(res < 0) {
if
(isapi_term) (*isapi_term)(HSE_TERM_MUST_UNLOAD);
ap_os_dso_unload(isapi_handle);
return
SERVER_ERROR;
}
if
(res == 0)
ecb->cbAvailable = ecb->cbTotalBytes = read;
else
ecb->cbAvailable = read;
ecb->lpbData[read] =
'\0'
;
}
else
{
ecb->cbTotalBytes = 0;
ecb->cbAvailable = 0;
ecb->lpbData = NULL;
}
ecb->GetServerVariable = &GetServerVariable;
ecb->WriteClient = &WriteClient;
ecb->ReadClient = &ReadClient;
ecb->ServerSupportFunction = &ServerSupportFunction;
retval = (*isapi_entry)(ecb);
if
(ecb->dwHttpStatusCode)
r->status = ecb->dwHttpStatusCode;
if
(ecb->lpszLogData &&
strcmp
(ecb->lpszLogData,
""
))
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, r,
"ISAPI: %s: %s"
, ecb->lpszLogData, r->filename);
if
(r->remaining > 0) {
char
argsbuffer[HUGE_STRING_LEN];
while
(ap_get_client_block(r, argsbuffer, HUGE_STRING_LEN) > 0);
}
if
(isapi_term) (*isapi_term)(HSE_TERM_MUST_UNLOAD);
ap_os_dso_unload(isapi_handle);
switch
(retval) {
case
0:
case
HSE_STATUS_SUCCESS:
case
HSE_STATUS_SUCCESS_AND_KEEP_CONN:
if
(cid->status)
return
cid->status;
return
OK;
case
HSE_STATUS_PENDING:
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI asynchronous I/O not supported: %s"
,
r->filename);
case
HSE_STATUS_ERROR:
default
:
return
SERVER_ERROR;
}
}
#pragma optimize("",on)
BOOL
WINAPI GetServerVariable (HCONN hConn,
LPSTR
lpszVariableName,
LPVOID
lpvBuffer,
LPDWORD
lpdwSizeofBuffer) {
request_rec *r = ((isapi_cid *)hConn)->r;
const
char
*result;
DWORD
len;
if
(!
strcmp
(lpszVariableName,
"ALL_HTTP"
)) {
char
**env = (
char
**) ap_table_elts(r->subprocess_env)->elts;
int
nelts = 2 * ap_table_elts(r->subprocess_env)->nelts;
int
i;
for
(len = 0, i = 0; i < nelts; i += 2)
if
(!
strncmp
(env[i],
"HTTP_"
, 5))
len +=
strlen
(env[i]) +
strlen
(env[i + 1]) + 2;
if
(*lpdwSizeofBuffer < len + 1) {
*lpdwSizeofBuffer = len + 1;
SetLastError(ERROR_INSUFFICIENT_BUFFER);
return
FALSE;
}
for
(i = 0; i < nelts; i += 2)
if
(!
strncmp
(env[i],
"HTTP_"
, 5)) {
strcpy
(lpvBuffer, env[i]);
((
char
*)lpvBuffer) +=
strlen
(env[i]);
*(((
char
*)lpvBuffer)++) =
':'
;
strcpy
(lpvBuffer, env[i + 1]);
((
char
*)lpvBuffer) +=
strlen
(env[i + 1]);
*(((
char
*)lpvBuffer)++) =
'\n'
;
}
*(((
char
*)lpvBuffer)++) =
'\0'
;
*lpdwSizeofBuffer = len;
return
TRUE;
}
if
(!
strcmp
(lpszVariableName,
"ALL_RAW"
)) {
char
**raw = (
char
**) ap_table_elts(r->headers_in)->elts;
int
nelts = 2 * ap_table_elts(r->headers_in)->nelts;
int
i;
for
(len = 0, i = 0; i < nelts; i += 2)
len +=
strlen
(raw[i]) +
strlen
(raw[i + 1]) + 2;
if
(*lpdwSizeofBuffer < len + 1) {
*lpdwSizeofBuffer = len + 1;
SetLastError(ERROR_INSUFFICIENT_BUFFER);
return
FALSE;
}
for
(i = 0; i < nelts; i += 2) {
strcpy
(lpvBuffer, raw[i]);
((
char
*)lpvBuffer) +=
strlen
(raw[i]);
*(((
char
*)lpvBuffer)++) =
':'
;
*(((
char
*)lpvBuffer)++) =
' '
;
strcpy
(lpvBuffer, raw[i + 1]);
((
char
*)lpvBuffer) +=
strlen
(raw[i + 1]);
*(((
char
*)lpvBuffer)++) =
'\n'
;
i += 2;
}
*(((
char
*)lpvBuffer)++) =
'\0'
;
*lpdwSizeofBuffer = len;
return
TRUE;
}
result = ap_table_get(r->subprocess_env, lpszVariableName);
if
(result) {
len =
strlen
(result);
if
(*lpdwSizeofBuffer < len + 1) {
*lpdwSizeofBuffer = len + 1;
SetLastError(ERROR_INSUFFICIENT_BUFFER);
return
FALSE;
}
strcpy
(lpvBuffer, result);
*lpdwSizeofBuffer = len;
return
TRUE;
}
SetLastError(ERROR_INVALID_INDEX);
return
FALSE;
}
BOOL
WINAPI WriteClient (HCONN ConnID,
LPVOID
Buffer,
LPDWORD
lpwdwBytes,
DWORD
dwReserved) {
request_rec *r = ((isapi_cid *)ConnID)->r;
if
(dwReserved && dwReserved != HSE_IO_SYNC) {
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI asynchronous I/O not supported: %s"
,
r->filename);
SetLastError(ERROR_INVALID_PARAMETER);
return
FALSE;
}
if
((*lpwdwBytes = ap_rwrite(Buffer, *lpwdwBytes, r)) <= 0) {
if
(!GetLastError())
SetLastError(ERROR);
return
FALSE;
}
return
TRUE;
}
BOOL
WINAPI ReadClient (HCONN ConnID,
LPVOID
lpvBuffer,
LPDWORD
lpdwSize) {
request_rec *r = ((isapi_cid *)ConnID)->r;
DWORD
read = 0;
int
res;
if
(r->remaining < (
long
) *lpdwSize)
*lpdwSize = r->remaining;
while
(read < *lpdwSize &&
((res = ap_get_client_block(r, (
char
*)lpvBuffer + read,
*lpdwSize - read)) > 0)) {
if
(res < 0) {
*lpdwSize = 0;
if
(!GetLastError())
SetLastError(ERROR);
return
FALSE;
}
read += res;
}
*lpdwSize = read;
return
TRUE;
}
static
BOOL
SendResponseHeaderEx(isapi_cid *cid,
const
char
*stat,
const
char
*head,
DWORD
statlen,
DWORD
headlen)
{
int
termarg;
char
*termch;
if
(!stat || statlen == 0 || !*stat) {
stat =
"Status: 200 OK"
;
}
else
{
char
*newstat;
newstat = ap_palloc(cid->r->pool, statlen + 9);
strcpy
(newstat,
"Status: "
);
ap_cpystrn(newstat + 8, stat, statlen + 1);
stat = newstat;
}
if
(!head || headlen == 0 || !*head) {
head =
"\r\n"
;
}
else
{
if
(head[headlen]) {
head = ap_pstrndup(cid->r->pool, head, headlen);
}
}
cid->status = ap_scan_script_header_err_strs(cid->r, NULL, &termch,
&termarg, stat, head, NULL);
cid->ecb->dwHttpStatusCode = cid->r->status;
ap_send_http_header(cid->r);
if
(termch && (termarg == 1)) {
if
(headlen == -1 && *termch)
ap_rputs(termch, cid->r);
else
if
(headlen > (
size_t
) (termch - head))
ap_rwrite(termch, headlen - (termch - head), cid->r);
}
if
(cid->status == HTTP_INTERNAL_SERVER_ERROR)
return
FALSE;
return
TRUE;
}
BOOL
WINAPI ServerSupportFunction (HCONN hConn,
DWORD
dwHSERequest,
LPVOID
lpvBuffer,
LPDWORD
lpdwSize,
LPDWORD
lpdwDataType) {
isapi_cid *cid = (isapi_cid *)hConn;
request_rec *r = cid->r;
request_rec *subreq;
switch
(dwHSERequest) {
case
1:
ap_table_set(r->headers_out,
"Location"
, lpvBuffer);
cid->status = cid->r->status
= cid->ecb->dwHttpStatusCode = HTTP_MOVED_TEMPORARILY;
return
TRUE;
case
2:
if
(r->remaining > 0) {
char
argsbuffer[HUGE_STRING_LEN];
while
(ap_get_client_block(r, argsbuffer, HUGE_STRING_LEN) > 0);
}
r->method = ap_pstrdup(r->pool,
"GET"
);
r->method_number = M_GET;
ap_table_unset(r->headers_in,
"Content-Length"
);
(
char
*)lpvBuffer = ap_pstrdup(r->pool, (
char
*)lpvBuffer);
ap_internal_redirect((
char
*)lpvBuffer, r);
return
TRUE;
case
3:
{
DWORD
statlen = 0, headlen = 0;
if
(lpvBuffer)
statlen =
strlen
((
char
*) lpvBuffer);
if
(lpdwDataType)
headlen =
strlen
((
char
*) lpdwDataType);
return
SendResponseHeaderEx(cid, (
char
*) lpvBuffer, (
char
*) lpdwDataType,
statlen, headlen);
}
case
4:
return
TRUE;
case
1001:
{
char
*file = (
char
*)lpvBuffer;
DWORD
len;
subreq = ap_sub_req_lookup_uri(ap_pstrndup(r->pool, file, *lpdwSize), r);
len = ap_cpystrn(file, subreq->filename, *lpdwSize) - file;
if
(S_ISDIR (subreq->finfo.st_mode)) {
if
(len < *lpdwSize - 1) {
file[len++] =
'\\'
;
file[len] =
'\0'
;
}
}
*lpdwSize = len;
return
TRUE;
}
case
1002:
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI ServerSupportFunction HSE_REQ_GET_SSPI_INFO "
"is not supported: %s"
, r->filename);
SetLastError(ERROR_INVALID_PARAMETER);
return
FALSE;
case
1003:
ap_table_set(r->notes,
"isapi-parameter"
, (
char
*) lpvBuffer);
if
(AppendLogToQuery) {
if
(r->args)
r->args = ap_pstrcat(r->pool, r->args, (
char
*) lpvBuffer, NULL);
else
r->args = ap_pstrdup(r->pool, (
char
*) lpvBuffer);
}
if
(AppendLogToErrors)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_INFO, r,
"ISAPI %s: %s"
, cid->r->filename,
(
char
*) lpvBuffer);
return
TRUE;
case
1005:
case
1006:
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI asynchronous I/O not supported: %s"
,
r->filename);
SetLastError(ERROR_INVALID_PARAMETER);
return
FALSE;
case
1007:
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI ServerSupportFunction "
"HSE_REQ_REFRESH_ISAPI_ACL "
"is not supported: %s"
, r->filename);
SetLastError(ERROR_INVALID_PARAMETER);
return
FALSE;
case
1008:
*((
LPBOOL
) lpvBuffer) = (r->connection->keepalive == 1);
return
TRUE;
case
1010:
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI asynchronous I/O not supported: %s"
,
r->filename);
SetLastError(ERROR_INVALID_PARAMETER);
return
FALSE;
case
1011:
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI ServerSupportFunction "
"HSE_REQ_GET_IMPERSONATION_TOKEN "
"is not supported: %s"
, r->filename);
SetLastError(ERROR_INVALID_PARAMETER);
return
FALSE;
#ifdef HSE_REQ_MAP_URL_TO_PATH_EX
case
1012:
{
LPHSE_URL_MAPEX_INFO info = (LPHSE_URL_MAPEX_INFO) lpdwDataType;
char
* test_uri = ap_pstrndup(r->pool, (
char
*)lpvBuffer, *lpdwSize);
subreq = ap_sub_req_lookup_uri(test_uri, r);
info->cchMatchingURL =
strlen
(test_uri);
info->cchMatchingPath = ap_cpystrn(info->lpszPath, subreq->filename,
MAX_PATH) - info->lpszPath;
if
(subreq->path_info && *subreq->path_info) {
ap_cpystrn(info->lpszPath + info->cchMatchingPath,
subreq->path_info, MAX_PATH - info->cchMatchingPath);
info->cchMatchingURL -=
strlen
(subreq->path_info);
if
(S_ISDIR(subreq->finfo.st_mode)
&& info->cchMatchingPath < MAX_PATH - 1) {
++info->cchMatchingPath;
++info->cchMatchingURL;
}
}
else
if
(S_ISDIR(subreq->finfo.st_mode)
&& info->cchMatchingPath < MAX_PATH - 1) {
info->lpszPath[info->cchMatchingPath++] =
'/'
;
info->lpszPath[info->cchMatchingPath] =
'\0'
;
}
if
(!subreq->finfo.st_mode) {
while
(info->cchMatchingPath && info->cchMatchingURL) {
if
(info->lpszPath[info->cchMatchingPath - 1] ==
'/'
)
break
;
--info->cchMatchingPath;
--info->cchMatchingURL;
}
}
for
(test_uri = info->lpszPath; *test_uri; ++test_uri)
if
(*test_uri ==
'/'
)
*test_uri =
'\\'
;
info->dwFlags = (subreq->finfo.st_mode & _S_IREAD ? 0x001 : 0)
| (subreq->finfo.st_mode & _S_IWRITE ? 0x002 : 0)
| (subreq->finfo.st_mode & _S_IEXEC ? 0x204 : 0);
return
TRUE;
}
#endif
case
1014:
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI ServerSupportFunction HSE_REQ_ABORTIVE_CLOSE"
" is not supported: %s"
, r->filename);
SetLastError(ERROR_INVALID_PARAMETER);
return
FALSE;
case
1015:
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI ServerSupportFunction "
"HSE_REQ_GET_CERT_INFO_EX "
"is not supported: %s"
, r->filename);
SetLastError(ERROR_INVALID_PARAMETER);
return
FALSE;
#ifdef HSE_REQ_SEND_RESPONSE_HEADER_EX
case
1016:
{
LPHSE_SEND_HEADER_EX_INFO shi
= (LPHSE_SEND_HEADER_EX_INFO) lpvBuffer;
return
SendResponseHeaderEx(cid, shi->pszStatus, shi->pszHeader,
shi->cchStatus, shi->cchHeader);
}
#endif
case
1017:
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI ServerSupportFunction "
"HSE_REQ_CLOSE_CONNECTION "
"is not supported: %s"
, r->filename);
SetLastError(ERROR_INVALID_PARAMETER);
return
FALSE;
case
1018:
*((
LPBOOL
) lpvBuffer) = (r->connection->aborted == 0);
return
TRUE;
case
1020:
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI ServerSupportFunction "
"HSE_REQ_EXTENSION_TRIGGER "
"is not supported: %s"
, r->filename);
SetLastError(ERROR_INVALID_PARAMETER);
return
FALSE;
default
:
if
(LogNotSupported)
ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, r,
"ISAPI ServerSupportFunction (%d) not supported: "
"%s"
, dwHSERequest, r->filename);
SetLastError(ERROR_INVALID_PARAMETER);
return
FALSE;
}
}
static
const
char
*isapi_cmd_readaheadbuffer(cmd_parms *cmd,
void
*config,
char
*arg)
{
long
val;
const
char
*err = ap_check_cmd_context(cmd, GLOBAL_ONLY);
if
(err != NULL) {
return
err;
}
if
(((val =
strtol
(arg, (
char
**) &err, 10)) <= 0) || *err)
return
"ISAPIReadAheadBuffer must be a legitimate value."
;
ReadAheadBuffer = val;
return
NULL;
}
static
const
char
*isapi_cmd_lognotsupported(cmd_parms *cmd,
void
*config,
char
*arg)
{
const
char
*err = ap_check_cmd_context(cmd, GLOBAL_ONLY);
if
(err != NULL) {
return
err;
}
if
(strcasecmp(arg,
"on"
) == 0) {
LogNotSupported = -1;
}
else
if
(strcasecmp(arg,
"off"
) == 0) {
LogNotSupported = 0;
}
else
{
return
"ISAPILogNotSupported must be on or off"
;
}
return
NULL;
}
static
const
char
*isapi_cmd_appendlogtoerrors(cmd_parms *cmd,
void
*config,
char
*arg)
{
const
char
*err = ap_check_cmd_context(cmd, GLOBAL_ONLY);
if
(err != NULL) {
return
err;
}
if
(strcasecmp(arg,
"on"
) == 0) {
AppendLogToErrors = -1;
}
else
if
(strcasecmp(arg,
"off"
) == 0) {
AppendLogToErrors = 0;
}
else
{
return
"ISAPIAppendLogToErrors must be on or off"
;
}
return
NULL;
}
static
const
char
*isapi_cmd_appendlogtoquery(cmd_parms *cmd,
void
*config,
char
*arg)
{
const
char
*err = ap_check_cmd_context(cmd, GLOBAL_ONLY);
if
(err != NULL) {
return
err;
}
if
(strcasecmp(arg,
"on"
) == 0) {
AppendLogToQuery = -1;
}
else
if
(strcasecmp(arg,
"off"
) == 0) {
AppendLogToQuery = 0;
}
else
{
return
"ISAPIAppendLogToQuery must be on or off"
;
}
return
NULL;
}
static
const
command_rec isapi_cmds[] = {
{
"ISAPIReadAheadBuffer"
, isapi_cmd_readaheadbuffer, NULL, RSRC_CONF, TAKE1,
"Maximum bytes to initially pass to the ISAPI handler"
},
{
"ISAPILogNotSupported"
, isapi_cmd_lognotsupported, NULL, RSRC_CONF, TAKE1,
"Log requests not supported by the ISAPI server"
},
{
"ISAPIAppendLogToErrors"
, isapi_cmd_appendlogtoerrors, NULL, RSRC_CONF, TAKE1,
"Send all Append Log requests to the error log"
},
{
"ISAPIAppendLogToQuery"
, isapi_cmd_appendlogtoquery, NULL, RSRC_CONF, TAKE1,
"Append Log requests are concatinated to the query args"
},
{ NULL }
};
handler_rec isapi_handlers[] = {
{
"isapi-isa"
, isapi_handler },
{ NULL}
};
module isapi_module = {
STANDARD_MODULE_STUFF,
NULL,
NULL,
NULL,
NULL,
NULL,
isapi_cmds,
isapi_handlers,
NULL,
NULL,
NULL,
NULL,
NULL,
NULL,
NULL
};
#endif /* WIN32 */