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

📄 session.c

📁 php-4.4.7学习linux时下载的源代码
💻 C
📖 第 1 页 / 共 4 页
字号:
/*   +----------------------------------------------------------------------+   | PHP Version 4                                                        |   +----------------------------------------------------------------------+   | Copyright (c) 1997-2007 The PHP Group                                |   +----------------------------------------------------------------------+   | This source file is subject to version 3.01 of the PHP license,      |   | that is bundled with this package in the file LICENSE, and is        |   | available through the world-wide-web at the following url:           |   | http://www.php.net/license/3_01.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: Sascha Schumann <sascha@schumann.cx>                        |   |          Andrei Zmievski <andrei@php.net>                            |   +----------------------------------------------------------------------+ *//* $Id: session.c,v 1.336.2.53.2.17 2007/04/04 19:52:26 tony2001 Exp $ */#ifdef HAVE_CONFIG_H#include "config.h"#endif#include "php.h"#ifdef PHP_WIN32#include "win32/time.h"#else#include <sys/time.h>#endif#include <sys/stat.h>#include <fcntl.h>#include "php_ini.h"#include "SAPI.h"#include "php_session.h"#include "ext/standard/md5.h"#include "ext/standard/php_var.h"#include "ext/standard/datetime.h"#include "ext/standard/php_lcg.h"#include "ext/standard/url_scanner_ex.h"#include "ext/standard/php_rand.h"                   /* for RAND_MAX */#include "ext/standard/info.h"#include "ext/standard/php_smart_str.h"#include "mod_files.h"#include "mod_user.h"#ifdef HAVE_LIBMM#include "mod_mm.h"#endif/* {{{ session_functions[] */function_entry session_functions[] = {	PHP_FE(session_name,              NULL)	PHP_FE(session_module_name,       NULL)	PHP_FE(session_save_path,         NULL)	PHP_FE(session_id,                NULL)	PHP_FE(session_regenerate_id,     NULL)	PHP_FE(session_decode,            NULL)	PHP_FE(session_register,          NULL)	PHP_FE(session_unregister,        NULL)	PHP_FE(session_is_registered,     NULL)	PHP_FE(session_encode,            NULL)	PHP_FE(session_start,             NULL)	PHP_FE(session_destroy,           NULL)	PHP_FE(session_unset,             NULL)	PHP_FE(session_set_save_handler,  NULL)	PHP_FE(session_cache_limiter,     NULL)	PHP_FE(session_cache_expire,      NULL)	PHP_FE(session_set_cookie_params, NULL)	PHP_FE(session_get_cookie_params, NULL)	PHP_FE(session_write_close,       NULL)	PHP_FALIAS(session_commit, session_write_close, NULL)	{NULL, NULL, NULL} };/* }}} */PHPAPI ZEND_DECLARE_MODULE_GLOBALS(ps);static ps_module *_php_find_ps_module(char *name TSRMLS_DC);static const ps_serializer *_php_find_ps_serializer(char *name TSRMLS_DC);#define SESSION_CHECK_ACTIVE_STATE	\	if (PS(session_status) == php_session_active) { \		php_error_docref(NULL TSRMLS_CC, E_WARNING, "A session is active. You cannot change the session module's ini settings at this time."); \		return FAILURE; \	}static PHP_INI_MH(OnUpdateSaveHandler){	SESSION_CHECK_ACTIVE_STATE;	PS(mod) = _php_find_ps_module(new_value TSRMLS_CC);	if (PG(modules_activated) && !PS(mod)) {		php_error_docref(NULL TSRMLS_CC, E_ERROR, "Cannot find save handler %s", new_value);	}	return SUCCESS;}static PHP_INI_MH(OnUpdateSerializer){	SESSION_CHECK_ACTIVE_STATE;	PS(serializer) = _php_find_ps_serializer(new_value TSRMLS_CC);	if (PG(modules_activated) && !PS(serializer)) {		php_error_docref(NULL TSRMLS_CC, E_ERROR, "Cannot find serialization handler %s", new_value);	}	return SUCCESS;}static PHP_INI_MH(OnUpdateSaveDir) {	/* Only do the safemode/open_basedir check at runtime */	if(stage == PHP_INI_STAGE_RUNTIME) {		if (memchr(new_value, '\0', new_value_length) != NULL) {			return FAILURE;		}		if (PG(safe_mode) && (!php_checkuid(new_value, NULL, CHECKUID_ALLOW_ONLY_DIR))) {			return FAILURE;   		}   		if (php_check_open_basedir(new_value TSRMLS_CC)) {			return FAILURE;   		}	}	OnUpdateString(entry, new_value, new_value_length, mh_arg1, mh_arg2, mh_arg3, stage TSRMLS_CC);	return SUCCESS;}/* {{{ PHP_INI */PHP_INI_BEGIN()	STD_PHP_INI_BOOLEAN("session.bug_compat_42",    "1",         PHP_INI_ALL, OnUpdateBool,   bug_compat,         php_ps_globals,    ps_globals)	STD_PHP_INI_BOOLEAN("session.bug_compat_warn",  "1",         PHP_INI_ALL, OnUpdateBool,   bug_compat_warn,    php_ps_globals,    ps_globals)#ifdef PHP_WIN32	STD_PHP_INI_ENTRY("session.save_path",          "",          PHP_INI_ALL, OnUpdateSaveDir,save_path,          php_ps_globals,    ps_globals)#else	STD_PHP_INI_ENTRY("session.save_path",          "/tmp",      PHP_INI_ALL, OnUpdateSaveDir,save_path,          php_ps_globals,    ps_globals)#endif	STD_PHP_INI_ENTRY("session.name",               "PHPSESSID", PHP_INI_ALL, OnUpdateString, session_name,       php_ps_globals,    ps_globals)	PHP_INI_ENTRY("session.save_handler",           "files",     PHP_INI_ALL, OnUpdateSaveHandler)	STD_PHP_INI_BOOLEAN("session.auto_start",       "0",         PHP_INI_ALL, OnUpdateBool,   auto_start,         php_ps_globals,    ps_globals)	STD_PHP_INI_ENTRY("session.gc_probability",     "1",         PHP_INI_ALL, OnUpdateInt,    gc_probability,     php_ps_globals,    ps_globals)	STD_PHP_INI_ENTRY("session.gc_divisor",         "100",       PHP_INI_ALL, OnUpdateInt,    gc_divisor,         php_ps_globals,    ps_globals)	STD_PHP_INI_ENTRY("session.gc_maxlifetime",     "1440",      PHP_INI_ALL, OnUpdateInt,    gc_maxlifetime,     php_ps_globals,    ps_globals)	PHP_INI_ENTRY("session.serialize_handler",      "php",       PHP_INI_ALL, OnUpdateSerializer)	STD_PHP_INI_ENTRY("session.cookie_lifetime",    "0",         PHP_INI_ALL, OnUpdateInt,    cookie_lifetime,    php_ps_globals,    ps_globals)	STD_PHP_INI_ENTRY("session.cookie_path",        "/",         PHP_INI_ALL, OnUpdateString, cookie_path,        php_ps_globals,    ps_globals)	STD_PHP_INI_ENTRY("session.cookie_domain",      "",          PHP_INI_ALL, OnUpdateString, cookie_domain,      php_ps_globals,    ps_globals)	STD_PHP_INI_BOOLEAN("session.cookie_secure",    "",          PHP_INI_ALL, OnUpdateBool,   cookie_secure,      php_ps_globals,    ps_globals)	STD_PHP_INI_BOOLEAN("session.use_cookies",      "1",         PHP_INI_ALL, OnUpdateBool,   use_cookies,        php_ps_globals,    ps_globals)	STD_PHP_INI_BOOLEAN("session.use_only_cookies", "0",         PHP_INI_ALL, OnUpdateBool,   use_only_cookies,   php_ps_globals,    ps_globals)	STD_PHP_INI_ENTRY("session.referer_check",      "",          PHP_INI_ALL, OnUpdateString, extern_referer_chk, php_ps_globals,    ps_globals)	STD_PHP_INI_ENTRY("session.entropy_file",       "",          PHP_INI_ALL, OnUpdateString, entropy_file,       php_ps_globals,    ps_globals)	STD_PHP_INI_ENTRY("session.entropy_length",     "0",         PHP_INI_ALL, OnUpdateInt,    entropy_length,     php_ps_globals,    ps_globals)	STD_PHP_INI_ENTRY("session.cache_limiter",      "nocache",   PHP_INI_ALL, OnUpdateString, cache_limiter,      php_ps_globals,    ps_globals)	STD_PHP_INI_ENTRY("session.cache_expire",       "180",       PHP_INI_ALL, OnUpdateInt,    cache_expire,       php_ps_globals,    ps_globals)	STD_PHP_INI_BOOLEAN("session.use_trans_sid",    "0",         PHP_INI_SYSTEM|PHP_INI_PERDIR, OnUpdateBool,   use_trans_sid,      php_ps_globals,    ps_globals)	/* Commented out until future discussion */	/* PHP_INI_ENTRY("session.encode_sources", "globals,track", PHP_INI_ALL, NULL) */PHP_INI_END()/* }}} */PS_SERIALIZER_FUNCS(php);PS_SERIALIZER_FUNCS(php_binary);#define MAX_SERIALIZERS 10static ps_serializer ps_serializers[MAX_SERIALIZERS + 1] = {	PS_SERIALIZER_ENTRY(php),	PS_SERIALIZER_ENTRY(php_binary)};#define MAX_MODULES 10#define PREDEFINED_MODULES 2static ps_module *ps_modules[MAX_MODULES + 1] = {	ps_files_ptr,	ps_user_ptr};#define IF_SESSION_VARS() \	if (PS(http_session_vars) && PS(http_session_vars)->type == IS_ARRAY)PHPAPI int php_session_register_serializer(const char *name, 		int (*encode)(PS_SERIALIZER_ENCODE_ARGS),		int (*decode)(PS_SERIALIZER_DECODE_ARGS)){	int ret = -1;	int i;	for (i = 0; i < MAX_SERIALIZERS; i++) {		if (ps_serializers[i].name == NULL) {			ps_serializers[i].name = name;			ps_serializers[i].encode = encode;			ps_serializers[i].decode = decode;			ps_serializers[i + 1].name = NULL;			ret = 0;			break;		}	}	return ret;}PHPAPI int php_session_register_module(ps_module *ptr){	int ret = -1;	int i;	for (i = 0; i < MAX_MODULES; i++) {		if (!ps_modules[i]) {			ps_modules[i] = ptr;			ret = 0;			break;		}		}		return ret;}PHP_MINIT_FUNCTION(session);PHP_RINIT_FUNCTION(session);PHP_MSHUTDOWN_FUNCTION(session);PHP_RSHUTDOWN_FUNCTION(session);PHP_MINFO_FUNCTION(session);static void php_rinit_session_globals(TSRMLS_D);static void php_rshutdown_session_globals(TSRMLS_D);static zend_bool php_session_destroy(TSRMLS_D);zend_module_entry session_module_entry = {	STANDARD_MODULE_HEADER,	"session",	session_functions,	PHP_MINIT(session), PHP_MSHUTDOWN(session),	PHP_RINIT(session), PHP_RSHUTDOWN(session),	PHP_MINFO(session),	NO_VERSION_YET,	STANDARD_MODULE_PROPERTIES};#ifdef COMPILE_DL_SESSIONZEND_GET_MODULE(session)#endiftypedef struct {	char *name;	void (*func)(TSRMLS_D);} php_session_cache_limiter_t;#define CACHE_LIMITER(name) _php_cache_limiter_##name#define CACHE_LIMITER_FUNC(name) static void CACHE_LIMITER(name)(TSRMLS_D)#define CACHE_LIMITER_ENTRY(name) { #name, CACHE_LIMITER(name) },#define ADD_HEADER(a) sapi_add_header(a, strlen(a), 1);#define MAX_STR 512void php_add_session_var(char *name, size_t namelen TSRMLS_DC){	zval **sym_track = NULL;		IF_SESSION_VARS() {		zend_hash_find(Z_ARRVAL_P(PS(http_session_vars)), name, namelen + 1,				(void *) &sym_track);	} else {		return;	}	/*	 * Set up a proper reference between $_SESSION["x"] and $x.	 */	if (PG(register_globals)) {		zval **sym_global = NULL;				if (zend_hash_find(&EG(symbol_table), name, namelen + 1, (void *) &sym_global) == SUCCESS) {			if ((Z_TYPE_PP(sym_global) == IS_ARRAY && Z_ARRVAL_PP(sym_global) == &EG(symbol_table)) || *sym_global == PS(http_session_vars)) {				return;			}		}		if (sym_global == NULL && sym_track == NULL) {			zval *empty_var;			ALLOC_INIT_ZVAL(empty_var); /* this sets refcount to 1 */			ZVAL_DELREF(empty_var); /* our module does not maintain a ref */			/* The next call will increase refcount by NR_OF_SYM_TABLES==2 */			zend_set_hash_symbol(empty_var, name, namelen, 1, 2, Z_ARRVAL_P(PS(http_session_vars)), &EG(symbol_table));		} else if (sym_global == NULL) {			SEPARATE_ZVAL_IF_NOT_REF(sym_track);			zend_set_hash_symbol(*sym_track, name, namelen, 1, 1, &EG(symbol_table));		} else if (sym_track == NULL) {			SEPARATE_ZVAL_IF_NOT_REF(sym_global);			zend_set_hash_symbol(*sym_global, name, namelen, 1, 1, Z_ARRVAL_P(PS(http_session_vars)));		}	} else {		if (sym_track == NULL) {			zval *empty_var;				ALLOC_INIT_ZVAL(empty_var);			ZEND_SET_SYMBOL_WITH_LENGTH(Z_ARRVAL_P(PS(http_session_vars)), name, namelen+1, empty_var, 1, 0);		}	}}void php_set_session_var(char *name, size_t namelen, zval *state_val, php_unserialize_data_t *var_hash TSRMLS_DC){	if (PG(register_globals)) {		zval **old_symbol;		if (zend_hash_find(&EG(symbol_table),name,namelen+1,(void *)&old_symbol) == SUCCESS) { 			if ((Z_TYPE_PP(old_symbol) == IS_ARRAY && Z_ARRVAL_PP(old_symbol) == &EG(symbol_table)) || *old_symbol == PS(http_session_vars)) {				return;			}			/* 			 * A global symbol with the same name exists already. That			 * symbol might have been created by other means (e.g. $_GET).			 *			 * hash_update in zend_set_hash_symbol is not good, because			 * it will leave referenced variables (such as local instances			 * of a global variable) dangling.			 *			 * BTW: if you use register_globals references between			 * session-vars won't work because of this very reason!			 */						REPLACE_ZVAL_VALUE(old_symbol,state_val,1);			/*			 * The following line will update the reference table used for			 * unserialization.  It is optional, because some storage 			 * formats may not be able to represent references.			 */			if (var_hash) {				PHP_VAR_UNSERIALIZE_ZVAL_CHANGED(var_hash,state_val,*old_symbol);			}			zend_set_hash_symbol(*old_symbol, name, namelen, 1, 1, Z_ARRVAL_P(PS(http_session_vars)));		} else {			zend_set_hash_symbol(state_val, name, namelen, 1, 2, Z_ARRVAL_P(PS(http_session_vars)), &EG(symbol_table));		}	} else IF_SESSION_VARS() {		zend_set_hash_symbol(state_val, name, namelen, PZVAL_IS_REF(state_val), 1, Z_ARRVAL_P(PS(http_session_vars)));	}}int php_get_session_var(char *name, size_t namelen, zval ***state_var TSRMLS_DC){	int ret = FAILURE;	IF_SESSION_VARS() {		ret = zend_hash_find(Z_ARRVAL_P(PS(http_session_vars)), name, 				namelen+1, (void **) state_var);		/*		 * If register_globals is enabled, and		 * if there is an entry for the slot in $_SESSION, and		 * if that entry is still set to NULL, and		 * if the global var exists, then		 * we prefer the same key in the global sym table		 */				if (PG(register_globals) && ret == SUCCESS 				&& Z_TYPE_PP(*state_var) == IS_NULL) {			zval **tmp;			if (zend_hash_find(&EG(symbol_table), name, namelen + 1,						(void **) &tmp) == SUCCESS) {				*state_var = tmp;			}		}	}		return ret;}#define PS_BIN_NR_OF_BITS 8#define PS_BIN_UNDEF (1<<(PS_BIN_NR_OF_BITS-1))#define PS_BIN_MAX (PS_BIN_UNDEF-1)PS_SERIALIZER_ENCODE_FUNC(php_binary){	smart_str buf = {0};	php_serialize_data_t var_hash;	PS_ENCODE_VARS;	PHP_VAR_SERIALIZE_INIT(var_hash);	PS_ENCODE_LOOP(			if (key_length > PS_BIN_MAX) continue;			smart_str_appendc(&buf, (unsigned char) key_length);			smart_str_appendl(&buf, key, key_length);						php_var_serialize(&buf, struc, &var_hash TSRMLS_CC);		} else {			if (key_length > PS_BIN_MAX) continue;			smart_str_appendc(&buf, (unsigned char) (key_length & PS_BIN_UNDEF));			smart_str_appendl(&buf, key, key_length);	);		if (newlen) *newlen = buf.len;	*newstr = buf.c;	PHP_VAR_SERIALIZE_DESTROY(var_hash);	return SUCCESS;}PS_SERIALIZER_DECODE_FUNC(php_binary){	const char *p;	char *name;	const char *endptr = val + vallen;	zval *current;	int namelen;	int has_value;	php_unserialize_data_t var_hash;	PHP_VAR_UNSERIALIZE_INIT(var_hash);	for (p = val; p < endptr; ) {		zval **tmp;		namelen = *p & (~PS_BIN_UNDEF);		if (namelen > PS_BIN_MAX || (p + namelen) >= endptr) {			return FAILURE;		}		has_value = *p & PS_BIN_UNDEF ? 0 : 1;		name = estrndup(p + 1, namelen);				p += namelen + 1;		if (zend_hash_find(&EG(symbol_table), name, namelen + 1, (void **) &tmp) == SUCCESS) {			if ((Z_TYPE_PP(tmp) == IS_ARRAY && Z_ARRVAL_PP(tmp) == &EG(symbol_table)) || *tmp == PS(http_session_vars)) {				efree(name);				continue;			}		}		if (has_value) {			ALLOC_INIT_ZVAL(current);			if (php_var_unserialize(&current, (const unsigned char **)&p, endptr, &var_hash TSRMLS_CC)) {				php_set_session_var(name, namelen, current, &var_hash  TSRMLS_CC);			}			zval_ptr_dtor(&current);

⌨️ 快捷键说明

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