PHP kernel-Apache2 SAPI_PHP tutorial

Source: Internet
Author: User
Tags sapi
PHP kernel-SAPI of Apache2. We know before defining SAPI, first we need to define sapi_module_struct this structure, look at the source code: softphp-5.2.9sapiapache2handlersapi_apache2.c, you can see the definition of this structure, I am straight we know before defining SAPI, first we need to define sapi_module_struct this structure, look at the source code:/soft/php-5.2.9/sapi/apache2handler/sapi_apache2.c, you can see the definition of this structure, I directly copy it over:

[Cpp]
Static sapi_module_struct apache2_sapi_module = {
"Apache2handler ",
"Apache 2.0 Handler ",

Php_apache2_startup,/* startup */
Php_module_shutdown_wrapper,/* shutdown */

NULL,/* activate */
NULL,/* deactivate */

Php_apache_sapi_ub_write,/* unbuffered write */
Php_apache_sapi_flush,/* flush */
Php_apache_sapi_get_stat,/* get uid */
Php_apache_sapi_getenv,/* getenv */

Php_error,/* error handler */

Php_apache_sapi_header_handler,/* header handler */
Php_apache_sapi_send_headers,/* send headers handler */
NULL,/* send header handler */

Php_apache_sapi_read_post,/* read POST data */
Php_apache_sapi_read_cookies,/* read Cookies */

Php_apache_sapi_register_variables,
Php_apache_sapi_log_message,/* Log message */
Php_apache_sapi_get_request_time,/* Request Time */

STANDARD_SAPI_MODULE_PROPERTIES
};
1. php_apache2_startup: This function is called When PHP is called through apache. This function is defined as follows, mainly to initialize PHP.
[Cpp]
Static int php_apache2_startup (sapi_module_struct * sapi_module)
{
If (php_module_startup (sapi_module, & php_apache_module, 1) = FAILURE ){
Return FAILURE;
}
Return SUCCESS;
}

2. php_module_shutdown_wrapper: disable the function of PHP.
3. PHP processes initialization and resource allocation transactions for each request. This part is to be defined by the activate field.

4. the Function with activate is deactiveate, which provides a handler to deal with the final work.

5. php_apache_sapi_ub_write: provides an interface for writing data to Response.

[Cpp]
Static int
Php_apache_sapi_ub_write (const char * str, uint str_length TSRMLS_DC)
{
Request_rec * r;
Php_struct * ctx;

Ctx = SG (server_context );
R = ctx-> r;

If (ap_rwrite (str, str_length, r) <0 ){
Php_handle_aborted_connection ();
}

Return str_length;/* we always consume all the data passed to us .*/
}


6. php_apache_sapi_flush: the handle that is provided to zend to refresh the cache.

[Cpp]
Static void
Php_apache_sapi_flush (void * server_context)
{
Php_struct * ctx;
Request_rec * r;
TSRMLS_FETCH ();

Ctx = server_context;

/* If we haven't registered a server_context yet,
* Then don't bother flushing .*/
If (! Server_context ){
Return;
}

R = ctx-> r;

Sapi_send_headers (TSRMLS_C );

R-> status = SG (sapi_headers). http_response_code;
SG (headers_sent) = 1;

If (ap_rflush (r) <0 | r-> connection-> aborted ){
Php_handle_aborted_connection ();
}
}
7. php_apache_sapi_get_stat: This part allows Zend to verify the state of the script file to be executed and determine whether the file has execution permissions.
[Cpp]
Static struct stat *
Php_apache_sapi_get_stat (TSRMLS_D)
{
Php_struct * ctx = SG (server_context );

Ctx-> finfo. st_uid = ctx-> r-> finfo. user;
Ctx-> finfo. st_gid = ctx-> r-> finfo. group;
Ctx-> finfo. st_dev = ctx-> r-> finfo. device;
Ctx-> finfo. st_ino = ctx-> r-> finfo. inode;
# If defined (NETWARE) & defined (CLIB_STAT_PATCH)
Ctx-> finfo. st_atime. TV _sec = apr_time_sec (ctx-> r-> finfo. atime );
Ctx-> finfo. st_mtime. TV _sec = apr_time_sec (ctx-> r-> finfo. mtime );
Ctx-> finfo. st_ctime. TV _sec = apr_time_sec (ctx-> r-> finfo. ctime );
# Else
Ctx-> finfo. st_atime = apr_time_sec (ctx-> r-> finfo. atime );
Ctx-> finfo. st_mtime = apr_time_sec (ctx-> r-> finfo. mtime );
Ctx-> finfo. st_ctime = apr_time_sec (ctx-> r-> finfo. ctime );
# Endif

Ctx-> finfo. st_size = ctx-> r-> finfo. size;
Ctx-> finfo. st_nlink = ctx-> r-> finfo. nlink;

Return & ctx-> finfo;
}

8. php_apache_sapi_getenv: provides an interface for Zend to find environment variables based on name. when we call getenv in a script, this handle is indirectly called.
[Cpp]
Static char *
Php_apache_sapi_getenv (char * name, size_t name_len TSRMLS_DC)
{
Php_struct * ctx = SG (server_context );
Const char * env_var;

Env_var = apr_table_get (ctx-> r-> subprocess_env, name );

Return (char *) env_var;
}

9. php_error: Error handling function, which calls the PHP error handling function directly.
10. php_apache_sapi_header_handler: This function is called when the PHP header () function is called.

[Cpp]
Static int
Php_apache_sapi_header_handler (sapi_header_struct * sapi_header, sapi_headers_struct * sapi_headers TSRMLS_DC)
{
Php_struct * ctx;
Char * val, * ptr;

Ctx = SG (server_context );

Val = strchr (sapi_header-> header ,':');

If (! Val ){
Sapi_free_header (sapi_header );
Return 0;
}
Ptr = val;

* Val = '\ 0 ';

Do {
Val ++;
} While (* val = '');
If (! Strcasecmp (sapi_header-> header, "content-type ")){
If (ctx-> content_type ){
Efree (ctx-> content_type );
}
Ctx-> content_type = estrdup (val );
} Else if (sapi_header-> replace ){
Apr_table_set (ctx-> r-> headers_out, sapi_header-> header, val );
} Else {
Apr_table_add (ctx-> r-> headers_out, sapi_header-> header, val );
}
* Ptr = ':';

Return SAPI_HEADER_ADD;
}
11. php_apache_sapi_send_headers: This function will be called to actually send the header.
[Cpp]
Static int
Php_apache_sapi_send_headers (sapi_headers_struct * sapi_headers TSRMLS_DC)
{
Php_struct * ctx = SG (server_context );
Const char * sline = SG (sapi_headers). http_status_line;

Ctx-> r-> status = SG (sapi_headers). http_response_code;

/* Httpd requires that r-> status_line is set to the first digit
* The status-code :*/
If (sline & strlen (sline)> 12 & strncmp (sline, "HTTP/1. ", 7) = 0 & sline [8] = ''){
Ctx-> r-> status_line = apr_pstrdup (ctx-> r-> pool, sline + 9 );
Ctx-> r-> proto_num = 1000 + (sline [7]-'0 ');
If (sline [7]-'0') = 0 ){
Apr_table_set (ctx-> r-> subprocess_env, "force-response-1.0", "true ");
}
}

/* Call ap_set_content_type only once, else each time we call it,
Configured output filters for that content type will be added */
If (! Ctx-> content_type ){
Ctx-> content_type = sapi_get_default_content_type (TSRMLS_C );
}
Ap_set_content_type (ctx-> r, apr_pstrdup (ctx-> r-> pool, ctx-> content_type ));
Efree (ctx-> content_type );
Ctx-> content_type = NULL;

Return SAPI_HEADER_SENT_SUCCESSFULLY;
}

12. there is a field under the php_apache_sapi_send_headers pointer to indicate that it is called when each separate header is sent.
13. php_apache_sapi_read_post: indicates how to read POST data.

[Cpp]
Static int
Php_apache_sapi_read_post (char * buf, uint count_bytes TSRMLS_DC)
{
Apr_size_t len, tlen = 0;
Php_struct * ctx = SG (server_context );
Request_rec * r;
Apr_bucket_brigade * brigade;

R = ctx-> r;
Brigade = ctx-> brigade;
Len = count_bytes;

/*
* This loop is needed because ap_get_brigade () can return us partial data
* Which wocould cause premature termination of request read. Therefor we
* Need to make sure that if data is available we fill the buffer completely.
*/

While (ap_get_brigade (r-> input_filters, brigade, AP_MODE_READBYTES, APR_BLOCK_READ, len) = APR_SUCCESS ){
Apr_brigade_flatten (brigade, buf, & len );
Apr_brigade_cleanup (brigade );
Tlen + = len;
If (tlen = count_bytes |! Len ){
Break;
}
Buf + = len;
Len = count_bytes-tlen;
}

Return tlen;
}


14. php_apache_sapi_read_cookie: how to read the cookie.

[Cpp]
Static char *
Php_apache_sapi_read_cookies (TSRMLS_D)
{
Php_struct * ctx = SG (server_context );
Const char * http_cookie;

Http_cookie = apr_table_get (ctx-> r-> headers_in, "cookie ");

/* The SAPI interface shoshould use 'const char *'*/
Return (char *) http_cookie;
}

15. php_apache_sapi_register_variables: provides an interface to provide variables to the $ _ SERVER [] array.
[Cpp]
Static void
Php_apache_sapi_register_variables (zval * track_vars_array TSRMLS_DC)
{
Php_struct * ctx = SG (server_context );
Const apr_array_header_t * arr = apr_table_elts (ctx-> r-> subprocess_env );
Char * key, * val;
Int new_val_len;

APR_ARRAY_FOREACH_OPEN (arr, key, val)
If (! Val ){
Val = "";
}
If (sapi_module.input_filter (PARSE_SERVER, key, & val, strlen (val), & new_val_len TSRMLS_CC )){
Php_register_variable_safe (key, val, new_val_len, track_vars_array TSRMLS_CC );
}
APR_ARRAY_FOREACH_CLOSE ()

If (sapi_module.input_filter (PARSE_SERVER, "PHP_SELF", & ctx-> r-> uri, strlen (ctx-> r-> uri), & new_val_len TSRMLS_CC )){
Php_register_variable_safe ("PHP_SELF", ctx-> r-> uri, new_val_len, track_vars_array TSRMLS_CC );
}
}

16, php_apache_sapi_log_message: output error message.
[Cpp]
Static void php_apache_sapi_log_message (char * msg)
{
Php_struct * ctx;
TSRMLS_FETCH ();

Ctx = SG (server_context );

If (ctx = NULL) {/* we haven' t initialized our ctx yet, oh well */
Ap_log_error (APLOG_MARK, APLOG_ERR | APLOG_STARTUP, 0, NULL, "% s", msg );
} Else {
Ap_log_rerror (APLOG_MARK, APLOG_ERR, 0, ctx-> r, "% s", msg );
}
}


17, php_apache_sapi_get_request_time: Gets the request time.

[Cpp]
Static time_t php_apache_sapi_get_request_time (TSRMLS_D ){
Php_struct * ctx = SG (server_context );
Return apr_time_sec (ctx-> r-> request_time );
}

This completes the SAPI definition of apache. Then, when the user uses a URL to request the apache service, these function pointers will play a role (called) when appropriate ).

...

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.