美文网首页PHP实战
php运行生命周期--模块初始化php_module_start

php运行生命周期--模块初始化php_module_start

作者: 程序员小饭 | 来源:发表于2020-02-06 20:49 被阅读0次

    php_module_startup过程调用图如下

    php_module_startup.png

    1、sapi_initialize_request_empty函数

    // main/SAPI.cSAPI_API void sapi_initialize_empty_request(void){
        SG(server_context) = NULL;
        SG(request_info).request_method = NULL;
        SG(request_info).auth_digest = SG(request_info).auth_user = SG(request_info).auth_password = NULL;
        SG(request_info).content_type_dup = NULL;
    }
    

    这个函数主要为前面定义的SG宏中的成员变量进行初始化。

    2、sapi_activate函数

    // main/SAPI.cSAPI_API void sapi_activate(void){
        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;    /*
        SG(sapi_headers).http_response_code = 200;
        */
        SG(sapi_headers).http_status_line = NULL;
        SG(sapi_headers).mimetype = NULL;
        SG(headers_sent) = 0;
        ZVAL_UNDEF(&SG(callback_func));
        SG(read_post_bytes) = 0;
        SG(request_info).request_body = NULL;
        SG(request_info).current_user = NULL;
        SG(request_info).current_user_length = 0;
        SG(request_info).no_headers = 0;
        SG(request_info).post_entry = NULL;
        SG(request_info).proto_num = 1000; /* Default to HTTP 1.0 */
        SG(global_request_time) = 0;
        SG(post_read) = 0;    /* It's possible to override this general case in the activate() callback, if necessary. */
        if (SG(request_info).request_method && !strcmp(SG(request_info).request_method, "HEAD")) {
            SG(request_info).headers_only = 1;
        } else {
            SG(request_info).headers_only = 0;
        }
        SG(rfc1867_uploaded_files) = NULL;    /* Handle request method */
        if (SG(server_context)) {        if (PG(enable_post_data_reading)
            &&  SG(request_info).content_type
            &&  SG(request_info).request_method
            && !strcmp(SG(request_info).request_method, "POST")) {            /* HTTP POST may contain form data to be processed into variables
                 * depending on given content type */
                sapi_read_post_data();
            } else {
                SG(request_info).content_type_dup = NULL;
            }        /* Cookies */
            SG(request_info).cookie_data = sapi_module.read_cookies();        if (sapi_module.activate) {
                sapi_module.activate();
            }
        }    if (sapi_module.input_filter_init) {
            sapi_module.input_filter_init();
        }
    }
    

    函数的前半部分主要还是对SG宏的成员变量进行初始化。后半部分先是调用了sapi_module_struct内部实现的activate函数,又调用了input_filter_init函数,但是在CLI模式并没有实现这两个函数,只是返回了NULL。代码如下:

    NULL,                           /* activate */
    

    3、php_output_startup函数

    //main/output.cPHPAPI void php_output_startup(void){
        ZEND_INIT_MODULE_GLOBALS(output, php_output_init_globals, NULL);
        zend_hash_init(&php_output_handler_aliases, 8, NULL, NULL, 1);
        zend_hash_init(&php_output_handler_conflicts, 8, NULL, NULL, 1);
        zend_hash_init(&php_output_handler_reverse_conflicts, 8, NULL, reverse_conflict_dtor, 1);
        php_output_direct = php_output_stdout;
    }
    

    我们先来看ZEND_INIT_MODULE_GLOBALS宏做了什么事情:

    #define ZEND_INIT_MODULE_GLOBALS(module_name, globals_ctor, globals_dtor)   \
        globals_ctor(&module_name##_globals);
    

    由代码得知,该宏只是做了一层替换,替换后的内容为:

    php_output_init_globals(&output_globals);
    

    那php_output_init_globals函数又做了什么呢?

    //main/output.cstatic inline void php_output_init_globals(zend_output_globals *G){
        ZEND_TSRMLS_CACHE_UPDATE();    memset(G, 0, sizeof(*G));
    }
    

    该函数通过memset函数对output_globals进行了内存相关的初始化,我们可以在main/php_output.h中的155行找到它的宏定义OG。

    //main/php_output.h# define OG(v) (output_globals.v)
    

    OG对应的结构体是php_output_init_globals的入参zend_output_globals,在这里花了些时间,因为没找到定义在哪里,最后发现它也是通过宏定义替换得来的,代码如下:

    //main/php_output.hZEND_BEGIN_MODULE_GLOBALS(output)
        zend_stack handlers;
        php_output_handler *active;
        php_output_handler *running;    const char *output_start_filename;    int output_start_lineno;    int flags;
    ZEND_END_MODULE_GLOBALS(output)
    

    看似是定义了一个结构体,但是代码中又出现了两个宏,我们再来瞅瞅这两个宏是干嘛的:

    //Zend/zend_API.h#define ZEND_BEGIN_MODULE_GLOBALS(module_name)      \
        typedef struct _zend_##module_name##_globals {#define ZEND_END_MODULE_GLOBALS(module_name)        \
        } zend_##module_name##_globals;
    

    原来只是做了个替换而已,替换后的代码如下:

    //这个是意淫出来的代码typedef struct _zend_output_globals {
        zend_stack handlers;
        php_output_handler *active;
        php_output_handler *running;    const char *output_start_filename;    int output_start_lineno;    int flags;
    } zend_output_globals
    

    这才是zend_output_globals最纯粹的定义,写的很是骚气,差点看断片。这样看来我们的OG宏对应的就是这个结构体了,姑且认为它是PHP输出相关的结构体。我们继续往下看:

    zend_hash_init(&php_output_handler_aliases, 8, NULL, NULL, 1);
    zend_hash_init(&php_output_handler_conflicts, 8, NULL, NULL, 1);
    zend_hash_init(&php_output_handler_reverse_conflicts, 8, NULL, reverse_conflict_dtor, 1);
    php_output_direct = php_output_stdout;
    

    接下来又对三个HashTable进行了初始化,初始化完成后,将php_output_direct指针指向了php_output_stdout函数。php_output_stdout函数的作用是调用fwrite函数,输出字符串到stdout中。代码如下:

    //main/output.cstatic size_t php_output_stdout(const char *str, size_t str_len){
        fwrite(str, 1, str_len, stdout);    return str_len;
    }
    

    4、php_startup_ticks函数

    int php_startup_ticks(void){
        zend_llist_init(&PG(tick_functions), sizeof(struct st_tick_function), NULL, 1);    return SUCCESS;
    }
    

    这里又出现了一个PG宏,来看下它的定义

    define PG(v) (core_globals.v)

    PG对应的结构体是core_globals,core_globals又对应_php_core_globals,代码如下

    extern ZEND_API struct _php_core_globals core_globals;
    

    php_core_globals顾名思义,就是php核心的全局变量,定义很多PHP相关的参数,比如内存上限、是否显示错误信息、上传文件大小限制、输入输出编码、禁用的函数等等,这里不再赘述,感兴趣的同学可以去看一下源码。

    //main/php_globals.hstruct _php_core_globals {
        zend_bool implicit_flush;
    
        zend_long output_buffering;
    
        zend_bool sql_safe_mode;
        zend_bool enable_dl;    char *output_handler;    char *unserialize_callback_func;
        zend_long serialize_precision;
    
        zend_long memory_limit;
        zend_long max_input_time;
    
        zend_bool track_errors;
        zend_bool display_errors;
        zend_bool display_startup_errors;
        zend_bool log_errors;
        zend_long      log_errors_max_len;
        zend_bool ignore_repeated_errors;
        zend_bool ignore_repeated_source;
        zend_bool report_memleaks;    char *error_log;    char *doc_root;    char *user_dir;    char *include_path;    char *open_basedir;    char *extension_dir;    char *php_binary;    char *sys_temp_dir;    char *upload_tmp_dir;
        zend_long upload_max_filesize;    char *error_append_string;    char *error_prepend_string;    char *auto_prepend_file;    char *auto_append_file;    char *input_encoding;    char *internal_encoding;    char *output_encoding;
    
        arg_separators arg_separator;    char *variables_order;
    
        HashTable rfc1867_protected_variables;    short connection_status;    short ignore_user_abort;    unsigned char header_is_being_sent;
    
        zend_llist tick_functions;
    
        zval http_globals[6];
    
        zend_bool expose_php;
    
        zend_bool register_argc_argv;
        zend_bool auto_globals_jit;    char *docref_root;    char *docref_ext;
    
        zend_bool html_errors;
        zend_bool xmlrpc_errors;
    
        zend_long xmlrpc_error_number;
    
        zend_bool activated_auto_globals[8];
    
        zend_bool modules_activated;
        zend_bool file_uploads;
        zend_bool during_request_startup;
        zend_bool allow_url_fopen;
        zend_bool enable_post_data_reading;
        zend_bool report_zend_debug;    int last_error_type;    char *last_error_message;    char *last_error_file;    int  last_error_lineno;    char *php_sys_temp_dir;    char *disable_functions;    char *disable_classes;
        zend_bool allow_url_include;
        zend_bool exit_on_timeout;#ifdef PHP_WIN32
        zend_bool com_initialized;#endif
        zend_long max_input_nesting_level;
        zend_long max_input_vars;
        zend_bool in_user_include;    char *user_ini_filename;
        zend_long user_ini_cache_ttl;    char *request_order;
    
        zend_bool mail_x_header;    char *mail_log;
    
        zend_bool in_error_log;#ifdef PHP_WIN32
        zend_bool windows_show_crt_warning;#endif};
    

    而php_startup_ticks函数就是对PG宏的成员变量tick_functions进行初始化。

    5、gc_globals_ctor函数

    ZEND_API void gc_globals_ctor(void){
        gc_globals_ctor_ex(&gc_globals);
    }
    

    这里又出现了一个gc_globals,PHP的全局变量就是多啊,在这里我们只要先记住它是PHP垃圾回收相关的结构体即可,后面我们做详细介绍。这段代码是对gc_globals进行初始化。

    //Zend/zend_gc.ctypedef struct _zend_gc_globals {
        zend_bool         gc_enabled;
        zend_bool         gc_active;
        zend_bool         gc_full;
    
        gc_root_buffer   *buf;              /* preallocated arrays of buffers   */
        gc_root_buffer    roots;            /* list of possible roots of cycles */
        gc_root_buffer   *unused;           /* list of unused buffers           */
        gc_root_buffer   *first_unused;     /* pointer to first unused buffer   */
        gc_root_buffer   *last_unused;      /* pointer to last unused buffer    */
    
        gc_root_buffer    to_free;          /* list to free                     */
        gc_root_buffer   *next_to_free;    uint32_t gc_runs;    uint32_t collected;#if GC_BENCH
        uint32_t root_buf_length;    uint32_t root_buf_peak;    uint32_t zval_possible_root;    uint32_t zval_buffered;    uint32_t zval_remove_from_buffer;    uint32_t zval_marked_grey;#endif} zend_gc_globals;
    

    6、zend_startup函数
    6.1、start_memory_manager
    初始化内存管理器,对结构体alloc_globals进行初始化。

    //Zend/zend_alloc.cstatic void alloc_globals_ctor(zend_alloc_globals *alloc_globals){#if ZEND_MM_CUSTOM
        char *tmp = getenv("USE_ZEND_ALLOC");    if (tmp && !zend_atoi(tmp, 0)) {
            alloc_globals->mm_heap = malloc(sizeof(zend_mm_heap));        memset(alloc_globals->mm_heap, 0, sizeof(zend_mm_heap));
            alloc_globals->mm_heap->use_custom_heap = ZEND_MM_CUSTOM_HEAP_STD;
            alloc_globals->mm_heap->custom_heap.std._malloc = __zend_malloc;
            alloc_globals->mm_heap->custom_heap.std._free = free;
            alloc_globals->mm_heap->custom_heap.std._realloc = __zend_realloc;        return;
        }#endif#ifdef MAP_HUGETLB
        tmp = getenv("USE_ZEND_ALLOC_HUGE_PAGES");    if (tmp && zend_atoi(tmp, 0)) {
            zend_mm_use_huge_pages = 1;
        }#endif
        ZEND_TSRMLS_CACHE_UPDATE();
        alloc_globals->mm_heap = zend_mm_init();
    }
    

    6.2、virtual_cwd_startup
    virtual_cwd_startup初始化了cwd_globals,根据源码可以看出成员变量都与realpath_cache有关,realpath_cache是什么呢?我们平时在写代码的时候,经常会使用include、include_once、require、require_once等语句导入文件,如果每次使用这些语句都要去对应的目录中寻找目标文件,势必会降低性能,所以官方加入了缓存,以便PHP再次使用时不必到include_path中查找,加快PHP的执行速度。

    //Zend/zend_virtual_cwd.ctypedef struct _virtual_cwd_globals {
        cwd_state cwd;
        zend_long                   realpath_cache_size;
        zend_long                   realpath_cache_size_limit;
        zend_long                   realpath_cache_ttl;
        realpath_cache_bucket *realpath_cache[1024];
    } virtual_cwd_globals;
    

    6.3、zend_startup_extensions_mechanism
    启动扩展机制,初始化zend_extensions结构体

    int zend_startup_extensions_mechanism(){    /* Startup extensions mechanism */
        zend_llist_init(&zend_extensions, sizeof(zend_extension), (void (*)(void *)) zend_extension_dtor, 1);
        last_resource_number = 0;    return SUCCESS;
    }
    

    6.4、提供编译与执行入口

    zend_compile_file = compile_file;
    zend_execute_ex = execute_ex;
    

    6.5、zend_init_opcodes_handlers
    初始化Zend虚拟机的handler

    6.6、初始化CG、EG
    初始化CG(function_table)、CG(class_table)、CG(auto_globals)、EG(zend_constants),这里不再赘述,我们后续讲解。

    GLOBAL_FUNCTION_TABLE = (HashTable *) malloc(sizeof(HashTable));
    GLOBAL_CLASS_TABLE = (HashTable *) malloc(sizeof(HashTable));
    GLOBAL_AUTO_GLOBALS_TABLE = (HashTable *) malloc(sizeof(HashTable));
    GLOBAL_CONSTANTS_TABLE = (HashTable *) malloc(sizeof(HashTable));
    

    6.7、ini_scanner_globals_ctor
    初始化ini_scanner_globals

    6.8、php_scanner_globals_ctor
    初始化language_scanner_globals

    6.9、zend_set_default_compile_time_values
    设置了编译相关的配置

    //Zend/zend.cstatic void zend_set_default_compile_time_values(void) /* {{{ */{    /* default compile-time values */
        CG(short_tags) = short_tags_default;
        CG(compiler_options) = compiler_options_default;
    }
    

    6.10、EG(error_reporting) = E_ALL & ~E_NOTICE;
    EG宏就是executor_globals,Zend执行器相关的全局变量,在这里对我们熟知的error_reporting进行配置。

    //Zend/zend_globals.hstruct _zend_executor_globals {
        zval uninitialized_zval;
        zval error_zval;    /* symbol table cache */
        zend_array *symtable_cache[SYMTABLE_CACHE_SIZE];
        zend_array **symtable_cache_limit;
        zend_array **symtable_cache_ptr;
        ......
    }
    

    6.11、zend_interned_strings_init
    初始化内部字符串

    //Zend/zend_string.cvoid zend_interned_strings_init(void){#ifndef ZTS
        zend_string *str;
    
        zend_hash_init(&CG(interned_strings), 1024, NULL, _str_dtor, 1);
        ......
    }
    

    6.12、zend_startup_builtin_functions
    初始化内部函数

    //Zend/zend_builtin_functions.cint zend_startup_builtin_functions(void) /* {{{ */{
        zend_builtin_module.module_number = 0;
        zend_builtin_module.type = MODULE_PERSISTENT;    return (EG(current_module) = zend_register_module_ex(&zend_builtin_module)) == NULL ? FAILURE : SUCCESS;
    }
    

    6.13、zend_register_standard_constants
    注册常量,比如E_ERROR、E_WARNING、E_NOTICE、E_CORE_ERROR等。

    //Zend/zend_constants.cvoid zend_register_standard_constants(void){
        REGISTER_MAIN_LONG_CONSTANT("E_ERROR", E_ERROR, CONST_PERSISTENT | CONST_CS);
        REGISTER_MAIN_LONG_CONSTANT("E_RECOVERABLE_ERROR", E_RECOVERABLE_ERROR, CONST_PERSISTENT | CONST_CS);
        REGISTER_MAIN_LONG_CONSTANT("E_WARNING", E_WARNING, CONST_PERSISTENT | CONST_CS);
        ......
    }
    

    6.14、zend_register_auto_global
    将GLOBALS加入CG(auto_globals)

    //Zend/zend.czend_register_auto_global(zend_string_init("GLOBALS", sizeof("GLOBALS") - 1, 1), 1, php_auto_globals_create_globals);
    

    6.15、zend_init_rsrc_plist
    初始化持久化符号表

    int zend_init_rsrc_plist(void){
        zend_hash_init_ex(&EG(persistent_list), 8, NULL, plist_entry_destructor, 1, 0);    return SUCCESS;
    }
    

    6.16、zend_init_exception_op
    初始化EG(exception_op)

    6.17、zend_init_call_trampoline_op
    初始化EG(call_trampoline_op)

    6.18、zend_ini_startup
    初始化与php.ini解析相关的变量

    //Zend/zend_ini.cZEND_API int zend_ini_startup(void) /* {{{ */{
        registered_zend_ini_directives = (HashTable *) malloc(sizeof(HashTable));
    
        EG(ini_directives) = registered_zend_ini_directives;
        EG(modified_ini_directives) = NULL;
        EG(error_reporting_ini_entry) = NULL;
        zend_hash_init_ex(registered_zend_ini_directives, 128, NULL, free_ini_entry, 1, 0);    return SUCCESS;
    }
    

    7、zend_register_list_destructors_ex函数
    初始化析构函数

    //Zend/zend_list.cZEND_API int zend_register_list_destructors_ex(rsrc_dtor_func_t ld, rsrc_dtor_func_t pld, const char *type_name, int module_number){
        zend_rsrc_list_dtors_entry *lde;
        zval zv;
    
        lde = malloc(sizeof(zend_rsrc_list_dtors_entry));
        lde->list_dtor_ex = ld;
        lde->plist_dtor_ex = pld;
        lde->module_number = module_number;
        lde->resource_id = list_destructors.nNextFreeElement;
        lde->type_name = type_name;
        ZVAL_PTR(&zv, lde);    if (zend_hash_next_index_insert(&list_destructors, &zv) == NULL) {        return FAILURE;
        }    return list_destructors.nNextFreeElement-1;
    }
    

    8、php_binary_init函数
    获取PHP执行的二进制路径

    static void php_binary_init(void){    char *binary_location;#ifdef PHP_WIN32
        binary_location = (char *)malloc(MAXPATHLEN);    if (GetModuleFileName(0, binary_location, MAXPATHLEN) == 0) {        free(binary_location);
            PG(php_binary) = NULL;
        }#else
        if (sapi_module.executable_location) {
            binary_location = (char *)malloc(MAXPATHLEN);        if (!strchr(sapi_module.executable_location, '/')) {            char *envpath, *path;            int found = 0;
                ......
    }
    

    9、php_output_register_constants函数
    初始化输出相关的预定义常量

    //main/output.cPHPAPI void php_output_register_constants(void){
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_START", PHP_OUTPUT_HANDLER_START, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_WRITE", PHP_OUTPUT_HANDLER_WRITE, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_FLUSH", PHP_OUTPUT_HANDLER_FLUSH, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_CLEAN", PHP_OUTPUT_HANDLER_CLEAN, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_FINAL", PHP_OUTPUT_HANDLER_FINAL, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_CONT", PHP_OUTPUT_HANDLER_WRITE, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_END", PHP_OUTPUT_HANDLER_FINAL, CONST_CS | CONST_PERSISTENT);
    
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_CLEANABLE", PHP_OUTPUT_HANDLER_CLEANABLE, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_FLUSHABLE", PHP_OUTPUT_HANDLER_FLUSHABLE, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_REMOVABLE", PHP_OUTPUT_HANDLER_REMOVABLE, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_STDFLAGS", PHP_OUTPUT_HANDLER_STDFLAGS, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_STARTED", PHP_OUTPUT_HANDLER_STARTED, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("PHP_OUTPUT_HANDLER_DISABLED", PHP_OUTPUT_HANDLER_DISABLED, CONST_CS | CONST_PERSISTENT);
    }
    

    10、php_rfc1867_register_constants函数
    注册文件上传相关的预定义常量

    //main/rfc1867.cvoid php_rfc1867_register_constants(void) /* {{{ */{
        REGISTER_MAIN_LONG_CONSTANT("UPLOAD_ERR_OK",         UPLOAD_ERROR_OK, CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("UPLOAD_ERR_INI_SIZE",   UPLOAD_ERROR_A,  CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("UPLOAD_ERR_FORM_SIZE",  UPLOAD_ERROR_B,  CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("UPLOAD_ERR_PARTIAL",    UPLOAD_ERROR_C,  CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("UPLOAD_ERR_NO_FILE",    UPLOAD_ERROR_D,  CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("UPLOAD_ERR_NO_TMP_DIR", UPLOAD_ERROR_E,  CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("UPLOAD_ERR_CANT_WRITE", UPLOAD_ERROR_F,  CONST_CS | CONST_PERSISTENT);
        REGISTER_MAIN_LONG_CONSTANT("UPLOAD_ERR_EXTENSION",  UPLOAD_ERROR_X,  CONST_CS | CONST_PERSISTENT);
    }
    

    11、php_init_config函数
    初始化配置文件php.ini,并通过zend_parse_ini_file解析。

    12、zend_register_standard_ini_entries函数
    初始化ini相关的变量

    void zend_register_standard_ini_entries(void) /* {{{ */{    int module_number = 0;
    
        REGISTER_INI_ENTRIES();
    }
    

    13、php_startup_auto_globals函数
    注册我们熟知的全局变量_GET、_POST、$_COOKIE等等

    //main/php_variables.cvoid php_startup_auto_globals(void){
        zend_register_auto_global(zend_string_init("_GET", sizeof("_GET")-1, 1), 0, php_auto_globals_create_get);
        zend_register_auto_global(zend_string_init("_POST", sizeof("_POST")-1, 1), 0, php_auto_globals_create_post);
        zend_register_auto_global(zend_string_init("_COOKIE", sizeof("_COOKIE")-1, 1), 0, php_auto_globals_create_cookie);
        zend_register_auto_global(zend_string_init("_SERVER", sizeof("_SERVER")-1, 1), PG(auto_globals_jit), php_auto_globals_create_server);
        zend_register_auto_global(zend_string_init("_ENV", sizeof("_ENV")-1, 1), PG(auto_globals_jit), php_auto_globals_create_env);
        zend_register_auto_global(zend_string_init("_REQUEST", sizeof("_REQUEST")-1, 1), PG(auto_globals_jit), php_auto_globals_create_request);
        zend_register_auto_global(zend_string_init("_FILES", sizeof("_FILES")-1, 1), 0, php_auto_globals_create_files);
    }
    

    14、php_startup_sapi_content_types函数
    初始化针对不同内容类型的处理函数

    //main/php_content_types.cint php_startup_sapi_content_types(void){
        sapi_register_default_post_reader(php_default_post_reader);
        sapi_register_treat_data(php_default_treat_data);
        sapi_register_input_filter(php_default_input_filter, NULL);    return SUCCESS;
    }
    

    15、php_register_internal_extensions_func函数
    注册内部扩展函数

    16、php_register_extensions_bc函数
    注册PHP的附加扩展

    17、zend_startup_modules函数
    启动Zend模块

    18、zend_startup_extensions函数
    启动Zend扩展

    19、php_disable_functions函数
    对PHP的禁用函数进行设置

    static void php_disable_functions(void){    char *s = NULL, *e;    if (!*(INI_STR("disable_functions"))) {        return;
        }
    
        e = PG(disable_functions) = strdup(INI_STR("disable_functions"));    if (e == NULL) {        return;
        }    while (*e) {        switch (*e) {            case ' ':            case ',':                if (s) {
                        *e = '\0';
                        zend_disable_function(s, e-s);
                        s = NULL;
                    }                break;            default:                if (!s) {
                        s = e;
                    }                break;
            }
            e++;
        }    if (s) {
            zend_disable_function(s, e-s);
        }
    }
    

    20、php_disable_classes函数
    对PHP的禁用类进行设置

    static void php_disable_classes(void){    char *s = NULL, *e;    if (!*(INI_STR("disable_classes"))) {        return;
        }
    
        e = PG(disable_classes) = strdup(INI_STR("disable_classes"));    while (*e) {        switch (*e) {            case ' ':            case ',':                if (s) {
                        *e = '\0';
                        zend_disable_class(s, e-s);
                        s = NULL;
                    }                break;            default:                if (!s) {
                        s = e;
                    }                break;
            }
            e++;
        }    if (s) {
            zend_disable_class(s, e-s);
        }
    }
    

    相关文章

      网友评论

        本文标题:php运行生命周期--模块初始化php_module_start

        本文链接:https://www.haomeiwen.com/subject/ebzjxhtx.html