diff options
Diffstat (limited to 'main')
-rw-r--r-- | main/SAPI.c | 106 | ||||
-rw-r--r-- | main/SAPI.h | 5 | ||||
-rw-r--r-- | main/main.c | 14 | ||||
-rw-r--r-- | main/php_globals.h | 6 | ||||
-rw-r--r-- | main/php_ticks.c | 77 | ||||
-rw-r--r-- | main/php_ticks.h | 41 | ||||
-rw-r--r-- | main/php_version.h | 4 |
7 files changed, 221 insertions, 32 deletions
diff --git a/main/SAPI.c b/main/SAPI.c index f409583160..54ed0bc018 100644 --- a/main/SAPI.c +++ b/main/SAPI.c @@ -177,36 +177,65 @@ SAPI_POST_READER_FUNC(sapi_read_standard_form_data) } +SAPI_API char *sapi_get_default_content_type(SLS_D) +{ + char *mimetype, *charset, *content_type; + + mimetype = SG(default_mimetype) ? SG(default_mimetype) : SAPI_DEFAULT_MIMETYPE; + charset = SG(default_charset) ? SG(default_charset) : SAPI_DEFAULT_CHARSET; + + if (strncasecmp(mimetype, "text/", 5) == 0 && strcasecmp(charset, "none") != 0) { + int len = strlen(mimetype) + sizeof(";charset=") + strlen(charset); + content_type = emalloc(len); + strlcpy(content_type, mimetype, len); + strlcat(content_type, ";charset=", len); + strlcat(content_type, charset, len); + } else { + content_type = estrdup(mimetype); + } + return content_type; +} + /* - * Called from php_request_startup() for every request. + * Add charset on content-type header if the MIME type starts with + * "text/", the default_charset directive is not set to "none" and + * there is not already a charset option in there. + * + * If "mimetype" is non-NULL, it should point to a pointer allocated + * with emalloc(). If a charset is added, the string will be + * re-allocated and the new length is returned. If mimetype is + * unchanged, 0 is returned. + * */ -SAPI_API void sapi_activate(SLS_D PLS_DC) +SAPI_API size_t sapi_apply_default_charset(char **mimetype, size_t len SLS_DC) { - int len; + char *charset, *newtype; + int newlen; + charset = SG(default_charset) ? SG(default_charset) : SAPI_DEFAULT_CHARSET; + + if (strcasecmp(charset, "none") != 0 && strncmp(*mimetype, "text/", 5) == 0 && strstr(*mimetype, "charset=") == NULL) { + newlen = len + (sizeof(";charset=")-1) + strlen(charset); + newtype = emalloc(newlen + 1); + strlcpy(newtype, *mimetype, len); + strlcat(newtype, ";charset=", len); + if (*mimetype != NULL) { + efree(*mimetype); + } + *mimetype = newtype; + return newlen; + } + return 0; +} + +/* + * Called from php_request_startup() for every request. + */ +SAPI_API void sapi_activate(SLS_D) +{ zend_llist_init(&SG(sapi_headers).headers, sizeof(sapi_header_struct), (void (*)(void *)) sapi_free_header, 0); SG(sapi_headers).send_default_content_type = 1; - if (PG(default_mimetype) != NULL) { - if (strncasecmp(PG(default_mimetype), "text/", 5) == 0) { - len = strlen(PG(default_mimetype)) + sizeof(";charset=") + strlen(PG(default_charset)); - /* add charset for text output */ - SG(sapi_headers).default_content_type = emalloc(len); - strcpy(SG(sapi_headers).default_content_type, PG(default_mimetype)); - strlcat(SG(sapi_headers).default_content_type, ";charset=", len); - strlcat(SG(sapi_headers).default_content_type, PG(default_charset), len); - } else { - /* don't add charset */ - len = strlen(PG(default_mimetype)) + 1; - SG(sapi_headers).default_content_type = emalloc(len); - strcpy(SG(sapi_headers).default_content_type, PG(default_mimetype)); - } - SG(sapi_headers).default_content_type[len - 1] = '\0'; - SG(sapi_headers).default_content_type_size = len; - } else { - SG(sapi_headers).default_content_type = NULL; - SG(sapi_headers).default_content_type_size = 0; - } SG(sapi_headers).http_response_code = 200; SG(sapi_headers).http_status_line = NULL; SG(headers_sent) = 0; @@ -295,7 +324,7 @@ static int sapi_extract_response_code(const char *header_line) */ SAPI_API int sapi_add_header(char *header_line, uint header_line_len) { - int retval; + int retval, free_header = 0; sapi_header_struct sapi_header; char *colon_offset; SLS_FETCH(); @@ -329,6 +358,25 @@ SAPI_API int sapi_add_header(char *header_line, uint header_line_len) if (colon_offset) { *colon_offset = 0; if (!STRCASECMP(header_line, "Content-Type")) { + char *ptr = colon_offset, *mimetype = NULL, *newheader; + size_t len = header_line_len - (ptr - header_line), newlen; + while (*ptr == ' ' && *ptr != '\0') { + ptr++; + } + mimetype = estrdup(ptr); + newlen = sapi_apply_default_charset(&mimetype, len); + if (newlen != 0) { + newlen += sizeof("Content-type: "); + newheader = emalloc(newlen); + strlcpy(newheader, "Content-type: ", newlen); + strlcpy(newheader, mimetype, newlen); + sapi_header.header = newheader; + sapi_header.header_len = newlen - 1; + colon_offset = strchr(newheader, ':'); + *colon_offset = '\0'; + free_header = 1; + } + efree(mimetype); SG(sapi_headers).send_default_content_type = 0; } else if (!STRCASECMP(header_line, "Location")) { SG(sapi_headers).http_response_code = 302; /* redirect */ @@ -350,6 +398,9 @@ SAPI_API int sapi_add_header(char *header_line, uint header_line_len) if (retval & SAPI_HEADER_ADD) { zend_llist_add_element(&SG(sapi_headers).headers, (void *) &sapi_header); } + if (free_header) { + efree(sapi_header.header); + } return SUCCESS; } @@ -488,3 +539,10 @@ SAPI_API char *sapi_getenv(char *name, int name_len) return NULL; } } + +/* + * Local variables: + * tab-width: 4 + * c-basic-offset: 4 + * End: + */ diff --git a/main/SAPI.h b/main/SAPI.h index 8cb83a38f1..71b25104b7 100644 --- a/main/SAPI.h +++ b/main/SAPI.h @@ -100,6 +100,8 @@ typedef struct { uint read_post_bytes; unsigned char headers_sent; struct stat global_stat; + char *default_mimetype; + char *default_charset; } sapi_globals_struct; @@ -142,6 +144,9 @@ SAPI_API int sapi_flush(); SAPI_API struct stat *sapi_get_stat(); SAPI_API char *sapi_getenv(char *name, int name_len); +SAPI_API char *sapi_get_default_content_type(SLS_D); +SAPI_API size_t sapi_apply_default_charset(char **mimetype, size_t len SLS_DC); + struct _sapi_module_struct { char *name; diff --git a/main/main.c b/main/main.c index bbbd9a4321..877f6119aa 100644 --- a/main/main.c +++ b/main/main.c @@ -66,6 +66,7 @@ #include "zend_indent.h" #include "php_content_types.h" +#include "php_ticks.h" #include "SAPI.h" @@ -202,8 +203,8 @@ PHP_INI_BEGIN() STD_PHP_INI_ENTRY("auto_append_file", NULL, PHP_INI_ALL, OnUpdateString, auto_append_file, php_core_globals, core_globals) STD_PHP_INI_ENTRY("auto_prepend_file", NULL, PHP_INI_ALL, OnUpdateString, auto_prepend_file, php_core_globals, core_globals) STD_PHP_INI_ENTRY("doc_root", NULL, PHP_INI_SYSTEM, OnUpdateStringUnempty, doc_root, php_core_globals, core_globals) - STD_PHP_INI_ENTRY("default_charset", SAPI_DEFAULT_MIMETYPE, PHP_INI_ALL, OnUpdateStringUnempty, default_charset, php_core_globals, core_globals) - STD_PHP_INI_ENTRY("default_mimetype",SAPI_DEFAULT_CHARSET, PHP_INI_ALL, OnUpdateStringUnempty, default_mimetype, php_core_globals, core_globals) + STD_PHP_INI_ENTRY("default_charset", SAPI_DEFAULT_CHARSET, PHP_INI_ALL, OnUpdateStringUnempty, default_charset, sapi_globals_struct,sapi_globals) + STD_PHP_INI_ENTRY("default_mimetype",SAPI_DEFAULT_MIMETYPE, PHP_INI_ALL, OnUpdateStringUnempty, default_mimetype, sapi_globals_struct,sapi_globals) STD_PHP_INI_ENTRY("error_log", NULL, PHP_INI_ALL, OnUpdateString, error_log, php_core_globals, core_globals) STD_PHP_INI_ENTRY("extension_dir", NULL, PHP_INI_SYSTEM, OnUpdateStringUnempty, extension_dir, php_core_globals, core_globals) STD_PHP_INI_ENTRY("gpc_order", "GPC", PHP_INI_ALL, OnUpdateStringUnempty, gpc_order, php_core_globals, core_globals) @@ -801,7 +802,7 @@ int php_module_startup(sapi_module_struct *sf) zuf.block_interruptions = sapi_module.block_interruptions; zuf.unblock_interruptions = sapi_module.unblock_interruptions; zuf.get_ini_entry = php_get_ini_entry_for_zend; - zuf.ticks_function = NULL; + zuf.ticks_function = php_run_ticks; zend_startup(&zuf, NULL); #ifdef ZTS @@ -851,6 +852,11 @@ int php_module_startup(sapi_module_struct *sf) REGISTER_MAIN_STRINGL_CONSTANT("PHP_VERSION", PHP_VERSION, sizeof(PHP_VERSION)-1, CONST_PERSISTENT | CONST_CS); REGISTER_MAIN_STRINGL_CONSTANT("PHP_OS", php_os, strlen(php_os), CONST_PERSISTENT | CONST_CS); + if (php_startup_ticks(PLS_C) == FAILURE) { + php_printf("Unable to start PHP ticks\n"); + return FAILURE; + } + if (php_startup_internal_extensions() == FAILURE) { php_printf("Unable to start builtin modules\n"); return FAILURE; @@ -878,6 +884,7 @@ int php_module_shutdown_wrapper(sapi_module_struct *sapi_globals) void php_module_shutdown() { int module_number=0; /* for UNREGISTER_INI_ENTRIES() */ + PLS_FETCH(); if (!module_initialized) { return; @@ -891,6 +898,7 @@ void php_module_shutdown() WSACleanup(); #endif + php_shutdown_ticks(PLS_C); sapi_flush(); global_lock_destroy(); diff --git a/main/php_globals.h b/main/php_globals.h index b7d1b391a4..9c3ee04294 100644 --- a/main/php_globals.h +++ b/main/php_globals.h @@ -42,6 +42,7 @@ extern PHPAPI int core_globals_id; extern ZEND_API struct _php_core_globals core_globals; #endif +struct _php_tick_function_entry; struct _php_core_globals { zend_bool magic_quotes_gpc; @@ -83,9 +84,6 @@ struct _php_core_globals { char *gpc_order; char *variables_order; - char *default_mimetype; - char *default_charset; - zend_bool expose_php; zend_bool track_vars; @@ -100,6 +98,8 @@ struct _php_core_globals { long max_execution_time; unsigned char header_is_being_sent; + + zend_llist tick_functions; }; diff --git a/main/php_ticks.c b/main/php_ticks.c new file mode 100644 index 0000000000..7f53ef3741 --- /dev/null +++ b/main/php_ticks.c @@ -0,0 +1,77 @@ +/* + +----------------------------------------------------------------------+ + | PHP version 4.0 | + +----------------------------------------------------------------------+ + | Copyright (c) 1997, 1998, 1999, 2000 The PHP Group | + +----------------------------------------------------------------------+ + | This source file is subject to version 2.0 of the PHP license, | + | that is bundled with this package in the file LICENSE, and is | + | available at through the world-wide-web at | + | http://www.php.net/license/2_0.txt. | + | If you did not receive a copy of the PHP license and are unable to | + | obtain it through the world-wide-web, please send a note to | + | license@php.net so we can mail you a copy immediately. | + +----------------------------------------------------------------------+ + | Authors: Stig Bakken <ssb@fast.no> | + | | + +----------------------------------------------------------------------+ + */ + +#include "php.h" +#include "php_ticks.h" + +int php_startup_ticks(PLS_D) +{ + zend_llist_init(&PG(tick_functions), sizeof(PG(tick_functions)), NULL, 1); + return SUCCESS; +} + +void php_shutdown_ticks(PLS_D) +{ + zend_llist_destroy(&PG(tick_functions)); +} + +static int php_compare_tick_functions(void *elem1, void *elem2) +{ + return ((void (*)(int))elem1 == (void (*)(int))elem2); +} + +PHPAPI int php_add_tick_function(void (*func)(int)) +{ + PLS_FETCH(); + + zend_llist_add_element(&PG(tick_functions), func); + + return SUCCESS; +} + +PHPAPI int php_remove_tick_function(void (*func)(int)) +{ + PLS_FETCH(); + + zend_llist_del_element(&PG(tick_functions), func, + (int(*)(void*,void*))php_compare_tick_functions); + return SUCCESS; +} + +void php_tick_iterator(void *data, void *arg) +{ + void (*func)(int); + func = (void(*)(int))data; + func(*((int *)arg)); +} + +void php_run_ticks(int count) +{ + PLS_FETCH(); + + zend_llist_apply_with_argument(&PG(tick_functions), (void(*)(void*,void*))php_tick_iterator, &count); +} + + +/* + * Local variables: + * tab-width: 4 + * c-basic-offset: 4 + * End: + */ diff --git a/main/php_ticks.h b/main/php_ticks.h new file mode 100644 index 0000000000..3b06448c1c --- /dev/null +++ b/main/php_ticks.h @@ -0,0 +1,41 @@ +/* + +----------------------------------------------------------------------+ + | PHP version 4.0 | + +----------------------------------------------------------------------+ + | Copyright (c) 1997, 1998, 1999, 2000 The PHP Group | + +----------------------------------------------------------------------+ + | This source file is subject to version 2.0 of the PHP license, | + | that is bundled with this package in the file LICENSE, and is | + | available at through the world-wide-web at | + | http://www.php.net/license/2_0.txt. | + | If you did not receive a copy of the PHP license and are unable to | + | obtain it through the world-wide-web, please send a note to | + | license@php.net so we can mail you a copy immediately. | + +----------------------------------------------------------------------+ + | Authors: Stig Bakken <ssb@fast.no> | + | | + +----------------------------------------------------------------------+ + */ + +#ifndef _PHP_TICKS_H +#define _PHP_TICKS_H + +struct _php_tick_function_entry { + void (*func)(int count); + struct _php_tick_function_entry *next; +}; + +int php_startup_ticks(PLS_D); +void php_shutdown_ticks(PLS_D); +void php_run_ticks(int count); +PHPAPI int php_add_tick_function(void (*func)(int count)); +PHPAPI int php_remove_tick_function(void (*func)(int count)); + +#endif + +/* + * Local variables: + * tab-width: 4 + * c-basic-offset: 4 + * End: + */ diff --git a/main/php_version.h b/main/php_version.h index 7a86df4256..abcfe084c4 100644 --- a/main/php_version.h +++ b/main/php_version.h @@ -1,3 +1,3 @@ /* automatically generated by configure */ -/* edit configure.in to change version number */ -#define PHP_VERSION "4.0b5-dev" +/* edit configure.in.in to change version number */ +#define PHP_VERSION "4.0b4-dev" |