⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 shorthand_isapi.cpp

📁 Shorthand是一个强大的脚本语言
💻 CPP
📖 第 1 页 / 共 3 页
字号:
///////////////////////////////////////////////////////////////////////////////
// $Header: /shorthand/src/shorthand_isapi.cpp 1     2/08/03 6:40a Arm $
//-----------------------------------------------------------------------------
// Project: ShortHand interpreter
// Author: Andrei Remenchuk <andrei@remenchuk.com>
//-----------------------------------------------------------------------------
// shorthand_isapi.cpp: implementations of ISAPI Module mod_shorthand
///////////////////////////////////////////////////////////////////////////////
#include <windows.h>
#include <process.h>

#include <httpext.h>
#include <httpfilt.h>
#include <httpext.h>

#include "version.h"
#include "shorthand.h"
#include "array.h"
#include "nodes.h"
#include "http.h"
#include "utils.h"
#include "module.h"
#include "version.h"
#include "regexx.h"
#undef putenv

#define PHP_ENABLE_SEH

#define MAX_STATUS_LENGTH sizeof("xxxx LONGEST STATUS DESCRIPTION")
#define ISAPI_SERVER_VAR_BUF_SIZE 1024
#define ISAPI_POST_DATA_BUF 1024

int isapi_shorthand_main(LPEXTENSION_CONTROL_BLOCK ecb, int display_source_mode);

/**
 * HTTPStream implementation that is responsible for handling
 * HTTP i/o tasks for ShortHand core.
 */
class ISAPIHttpStream : public HttpStream
{
protected:

    LPEXTENSION_CONTROL_BLOCK m_ecb;
    int m_chunk_number;
    
    map<string*> m_in_cookies; // inbound cookies
    CHttpCookieJar m_out_cookies;
    map<string*> m_out_headers; // outbound headers

    string m_content_type;

    bool m_headers_sent;
    bool m_did_client_block;
    bool m_have_input;
    bool m_cookies_grabbed;
    int  m_response_code;
    string m_response_message;

    DWORD m_input_offset;

public:
    ISAPIHttpStream(LPEXTENSION_CONTROL_BLOCK ecb)
    {
        m_ecb = ecb;
        m_headers_sent = false;
        m_did_client_block = false;
        m_have_input = false;
        m_response_code = 200;
        m_response_message = "OK";
        m_cookies_grabbed = false;
        m_content_type = "text/html";
        m_input_offset = 0;
    }

    bool http_headers_sent() { return m_headers_sent; }
    int http_read(void* buffer, int buffer_size);

    int code() const { return m_response_code; }
    int http_add_header(const char* name, const char* value);
    int http_send_headers();
    int http_write_chunk(const void* chunk_data, unsigned int chunk_length);
    void grab_cookies();
    const char* http_get_cookie(const char* name);
    int http_set_cookie(const CHttpCookie* cookie);

    // overrides HTTP response code (with optional status line message)
    // most servers will allow to change code, but few allow to change message
    void http_set_response_code(int code, const char* msg);
    int http_finalize();


};



static bool bFilterLoaded = false;
static bool bTerminateThreadsOnError = false;

static char *isapi_special_server_variable_names[] = 
{
	"ALL_HTTP",
	"HTTPS",
	"SCRIPT_NAME",
	NULL
};

#define NUM_SPECIAL_VARS        (sizeof(isapi_special_server_variable_names)/sizeof(char *))
#define SPECIAL_VAR_ALL_HTTP    0
#define SPECIAL_VAR_HTTPS       1
#define SPECIAL_VAR_PHP_SELF    2

static char *isapi_server_variable_names[] = 
{
	"AUTH_PASSWORD",
	"AUTH_TYPE",
	"AUTH_USER",
	"CONTENT_LENGTH",
	"CONTENT_TYPE",
        "HTTP_ACCEPT",
        "HTTP_ACCEPT_LANGUAGE",
        "HTTP_COOKIE",
        "HTTP_USER_AGENT",
        "HTTP_HOST",
        "HTTP_REFERER",
	"PATH_INFO",
	"PATH_TRANSLATED",
	"QUERY_STRING",
	"REMOTE_ADDR",
	"REMOTE_HOST",
	"REMOTE_PORT",
	"REMOTE_USER",
	"REQUEST_METHOD",
        "REQUEST_URI",
	"SCRIPT_NAME",
	"SERVER_ADMIN",
	"SERVER_NAME",
	"SERVER_PORT",
	"SERVER_PROTOCOL",
	"SERVER_SOFTWARE",
	"REQUEST_URI",
	"URL",
	NULL
};


static char *isapi_secure_server_variable_names[] = {
	"CERT_COOKIE",
	"CERT_FLAGS",
	"CERT_ISSUER",
	"CERT_KEYSIZE",
	"CERT_SECRETKEYSIZE",
	"CERT_SERIALNUMBER",
	"CERT_SERVER_ISSUER",
	"CERT_SERVER_SUBJECT",
	"CERT_SUBJECT",
	"HTTPS_KEYSIZE",
	"HTTPS_SECRETKEYSIZE",
	"HTTPS_SERVER_ISSUER",
	"HTTPS_SERVER_SUBJECT",
	"SERVER_PORT_SECURE",
	NULL
};


/*
static void php_info_isapi(ZEND_MODULE_INFO_FUNC_ARGS)
{
	char **p;
	char variable_buf[ISAPI_SERVER_VAR_BUF_SIZE];
	DWORD variable_len;
	char **all_variables[] = {
		isapi_server_variable_names,
		isapi_special_server_variable_names,
		isapi_secure_server_variable_names,
		NULL
	};
	char ***server_variable_names;
	LPEXTENSION_CONTROL_BLOCK lpECB;

	lpECB = (LPEXTENSION_CONTROL_BLOCK) SG(server_context);

	php_info_print_table_start();
	php_info_print_table_header(2, "Server Variable", "Value");
	server_variable_names = all_variables;
	while (*server_variable_names) {
		p = *server_variable_names;
		while (*p) {
			variable_len = ISAPI_SERVER_VAR_BUF_SIZE;
			if (lpECB->GetServerVariable(lpECB->ConnID, *p, variable_buf, &variable_len)
				&& variable_buf[0]) {
				php_info_print_table_row(2, *p, variable_buf);
			} else if (GetLastError() == ERROR_INSUFFICIENT_BUFFER) {
				char *tmp_variable_buf;

				tmp_variable_buf = (char *) emalloc(variable_len);
				if (lpECB->GetServerVariable(lpECB->ConnID, *p, tmp_variable_buf, &variable_len)
					&& variable_buf[0]) {
					php_info_print_table_row(2, *p, tmp_variable_buf);
				}
				efree(tmp_variable_buf);
			}
			p++;
		}
		server_variable_names++;
	}
	php_info_print_table_end();
}


static zend_module_entry php_isapi_module = {
    STANDARD_MODULE_HEADER,
	"ISAPI",
	NULL,
	NULL,
	NULL,
	NULL,
	NULL,
	php_info_isapi,
    NULL,
	STANDARD_MODULE_PROPERTIES
};
*/

static int isapi_write_client(LPEXTENSION_CONTROL_BLOCK ecb, const char *str, int str_length = -1)
{
    if (str_length == -1) str_length = strlen(str);
    DWORD num_bytes = str_length;
    
    if (ecb->WriteClient(ecb->ConnID, (char *) str, &num_bytes, HSE_IO_SYNC ) == FALSE) 
    {
	    //php_handle_aborted_connection();
    }
    return num_bytes;
}

/*
static int sapi_isapi_header_handler(sapi_header_struct *sapi_header, sapi_headers_struct *sapi_headers TSRMLS_DC)
{
	return SAPI_HEADER_ADD;
}


static void accumulate_header_length(sapi_header_struct *sapi_header, uint *total_length TSRMLS_DC)
{
	*total_length += sapi_header->header_len+2;
}
*/

/*
static void concat_header(sapi_header_struct *sapi_header, char **combined_headers_ptr TSRMLS_DC)
{
	memcpy(*combined_headers_ptr, sapi_header->header, sapi_header->header_len);
	*combined_headers_ptr += sapi_header->header_len;
	**combined_headers_ptr = '\r';
	(*combined_headers_ptr)++;
	**combined_headers_ptr = '\n';
	(*combined_headers_ptr)++;
}
*/

/*
static int sapi_isapi_send_headers(sapi_headers_struct *sapi_headers TSRMLS_DC)
{
	uint total_length = 2;		// account for the trailing \r\n 
	char *combined_headers, *combined_headers_ptr;
	LPEXTENSION_CONTROL_BLOCK lpECB = (LPEXTENSION_CONTROL_BLOCK) SG(server_context);
	HSE_SEND_HEADER_EX_INFO header_info;
	char status_buf[MAX_STATUS_LENGTH];
	sapi_header_struct default_content_type;

	// Obtain headers length 
	if (SG(sapi_headers).send_default_content_type) {
		sapi_get_default_content_type_header(&default_content_type TSRMLS_CC);
		accumulate_header_length(&default_content_type, (void *) &total_length TSRMLS_CC);
	}
	zend_llist_apply_with_argument(&SG(sapi_headers).headers, (llist_apply_with_arg_func_t) accumulate_header_length, (void *) &total_length TSRMLS_CC);

	// Generate headers 
	combined_headers = (char *) emalloc(total_length+1);
	combined_headers_ptr = combined_headers;
	if (SG(sapi_headers).send_default_content_type) {
		concat_header(&default_content_type, (void *) &combined_headers_ptr TSRMLS_CC);
		sapi_free_header(&default_content_type); // we no longer need it 
	}
	zend_llist_apply_with_argument(&SG(sapi_headers).headers, (llist_apply_with_arg_func_t) concat_header, (void *) &combined_headers_ptr TSRMLS_CC);
	*combined_headers_ptr++ = '\r';
	*combined_headers_ptr++ = '\n';
	*combined_headers_ptr = 0;

	switch (SG(sapi_headers).http_response_code) {
		case 200:
			header_info.pszStatus = "200 OK";
			break;
		case 302:
			header_info.pszStatus = "302 Moved Temporarily";
			break;
		case 401:
			header_info.pszStatus = "401 Authorization Required";
			break;
		default:
			snprintf(status_buf, MAX_STATUS_LENGTH, "%d Undescribed", SG(sapi_headers).http_response_code);
			header_info.pszStatus = status_buf;
			break;
	}
	header_info.cchStatus = strlen(header_info.pszStatus);
	header_info.pszHeader = combined_headers;
	header_info.cchHeader = total_length;
	header_info.fKeepConn = FALSE;
	lpECB->dwHttpStatusCode = SG(sapi_headers).http_response_code;

	lpECB->ServerSupportFunction(lpECB->ConnID, HSE_REQ_SEND_RESPONSE_HEADER_EX, &header_info, NULL, NULL);

	efree(combined_headers);
	return SAPI_HEADER_SENT_SUCCESSFULLY;
}
*/

/*
static int php_isapi_startup(sapi_module_struct *sapi_module)
{
	if (php_module_startup(sapi_module)==FAILURE
		|| zend_startup_module(&php_isapi_module)==FAILURE) {
		return FAILURE;
	} else {
		bTerminateThreadsOnError = (zend_bool) INI_INT("isapi.terminate_threads_on_error");
		return SUCCESS;
	}
}

static int sapi_isapi_read_post(char *buffer, uint count_bytes TSRMLS_DC)
{
	LPEXTENSION_CONTROL_BLOCK lpECB = (LPEXTENSION_CONTROL_BLOCK) SG(server_context);
	DWORD read_from_buf=0;
	DWORD read_from_input=0;
	DWORD total_read=0;

	if ((DWORD) SG(read_post_bytes) < lpECB->cbAvailable) {
		read_from_buf = MIN(lpECB->cbAvailable-SG(read_post_bytes), count_bytes);
		memcpy(buffer, lpECB->lpbData+SG(read_post_bytes), read_from_buf);
		total_read += read_from_buf;
	}
	if (read_from_buf<count_bytes
		&& (SG(read_post_bytes)+read_from_buf) < lpECB->cbTotalBytes) {
		DWORD cbRead=0, cbSize;

		read_from_input = MIN(count_bytes-read_from_buf, lpECB->cbTotalBytes-SG(read_post_bytes)-read_from_buf);
		while (cbRead < read_from_input) {
			cbSize = read_from_input - cbRead;
			if (!lpECB->ReadClient(lpECB->ConnID, buffer+read_from_buf+cbRead, &cbSize) || cbSize==0) {
				break;
			}
			cbRead += cbSize;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -