1/* 2 +----------------------------------------------------------------------+ 3 | PHP Version 5 | 4 +----------------------------------------------------------------------+ 5 | Copyright (c) 1997-2013 The PHP Group | 6 +----------------------------------------------------------------------+ 7 | This source file is subject to version 3.01 of the PHP license, | 8 | that is bundled with this package in the file LICENSE, and is | 9 | available at through the world-wide-web at the following url: | 10 | http://www.php.net/license/3_01.txt. | 11 | If you did not receive a copy of the PHP license and are unable to | 12 | obtain it through the world-wide-web, please send a note to | 13 | license@php.net so we can mail you a copy immediately. | 14 +----------------------------------------------------------------------+ 15 | Author: George Wang <gwang@litespeedtech.com> | 16 +----------------------------------------------------------------------+ 17*/ 18 19/* $Id$ */ 20 21#include "php.h" 22#include "SAPI.h" 23#include "php_main.h" 24#include "php_ini.h" 25#include "php_variables.h" 26#include "zend_highlight.h" 27#include "zend.h" 28 29#include "lsapilib.h" 30 31#include <stdio.h> 32 33#if HAVE_STDLIB_H 34#include <stdlib.h> 35#endif 36 37#if HAVE_UNISTD_H 38#include <unistd.h> 39#endif 40 41#ifdef PHP_WIN32 42 43#include <io.h> 44#include <fcntl.h> 45#include "win32/php_registry.h" 46 47#else 48 49#include <sys/wait.h> 50 51#endif 52 53#include <sys/stat.h> 54 55#if HAVE_SYS_TYPES_H 56 57#include <sys/types.h> 58 59#endif 60 61#if HAVE_SIGNAL_H 62 63#include <signal.h> 64 65#endif 66 67#include <sys/socket.h> 68#include <arpa/inet.h> 69#include <netinet/in.h> 70 71 72#define SAPI_LSAPI_MAX_HEADER_LENGTH 2048 73 74static int lsapi_mode = 1; 75static char *php_self = ""; 76static char *script_filename = ""; 77static int source_highlight = 0; 78 79#ifdef ZTS 80zend_compiler_globals *compiler_globals; 81zend_executor_globals *executor_globals; 82php_core_globals *core_globals; 83sapi_globals_struct *sapi_globals; 84void ***tsrm_ls; 85#endif 86 87zend_module_entry litespeed_module_entry; 88 89/* {{{ php_lsapi_startup 90 */ 91static int php_lsapi_startup(sapi_module_struct *sapi_module) 92{ 93 if (php_module_startup(sapi_module, NULL, 0)==FAILURE) { 94 return FAILURE; 95 } 96 return SUCCESS; 97} 98/* }}} */ 99 100 101 102/* {{{ sapi_lsapi_ub_write 103 */ 104static int sapi_lsapi_ub_write(const char *str, uint str_length TSRMLS_DC) 105{ 106 int ret; 107 int remain; 108 if ( lsapi_mode ) { 109 ret = LSAPI_Write( str, str_length ); 110 if ( ret < str_length ) { 111 php_handle_aborted_connection(); 112 return str_length - ret; 113 } 114 } else { 115 remain = str_length; 116 while( remain > 0 ) { 117 ret = write( 1, str, remain ); 118 if ( ret <= 0 ) { 119 php_handle_aborted_connection(); 120 return str_length - remain; 121 } 122 str += ret; 123 remain -= ret; 124 } 125 } 126 return str_length; 127} 128/* }}} */ 129 130 131/* {{{ sapi_lsapi_flush 132 */ 133static void sapi_lsapi_flush( void * server_context ) 134{ 135 if ( lsapi_mode ) { 136 if ( LSAPI_Flush() == -1) { 137 php_handle_aborted_connection(); 138 } 139 } 140} 141/* }}} */ 142 143 144/* {{{ sapi_lsapi_deactivate 145 */ 146static int sapi_lsapi_deactivate(TSRMLS_D) 147{ 148 LSAPI_Finish(); 149 return SUCCESS; 150} 151/* }}} */ 152 153 154 155 156/* {{{ sapi_lsapi_getenv 157 */ 158static char *sapi_lsapi_getenv( char * name, size_t name_len TSRMLS_DC ) 159{ 160 if ( lsapi_mode ) { 161 return LSAPI_GetEnv( name ); 162 } else { 163 return getenv( name ); 164 } 165} 166/* }}} */ 167 168 169 170static int add_variable( const char * pKey, int keyLen, const char * pValue, int valLen, 171 void * arg ) 172{ 173 php_register_variable_safe((char *)pKey, (char *)pValue, valLen, (zval *)arg TSRMLS_CC); 174 return 1; 175} 176 177 178 179/* {{{ sapi_lsapi_register_variables 180 */ 181static void sapi_lsapi_register_variables(zval *track_vars_array TSRMLS_DC) 182{ 183 184 if ( lsapi_mode ) { 185 LSAPI_ForeachHeader( add_variable, track_vars_array ); 186 LSAPI_ForeachEnv( add_variable, track_vars_array ); 187 php_import_environment_variables(track_vars_array TSRMLS_CC); 188 189 php_register_variable("PHP_SELF", (SG(request_info).request_uri ? SG(request_info).request_uri:""), track_vars_array TSRMLS_CC); 190 } else { 191 php_import_environment_variables(track_vars_array TSRMLS_CC); 192 193 php_register_variable("PHP_SELF", php_self, track_vars_array TSRMLS_CC); 194 php_register_variable("SCRIPT_NAME", php_self, track_vars_array TSRMLS_CC); 195 php_register_variable("SCRIPT_FILENAME", script_filename, track_vars_array TSRMLS_CC); 196 php_register_variable("PATH_TRANSLATED", script_filename, track_vars_array TSRMLS_CC); 197 php_register_variable("DOCUMENT_ROOT", "", track_vars_array TSRMLS_CC); 198 199 } 200} 201/* }}} */ 202 203 204/* {{{ sapi_lsapi_read_post 205 */ 206static int sapi_lsapi_read_post(char *buffer, uint count_bytes TSRMLS_DC) 207{ 208 if ( lsapi_mode ) { 209 return LSAPI_ReadReqBody( buffer, count_bytes ); 210 } else { 211 return 0; 212 } 213} 214/* }}} */ 215 216 217 218 219/* {{{ sapi_lsapi_read_cookies 220 */ 221static char *sapi_lsapi_read_cookies(TSRMLS_D) 222{ 223 if ( lsapi_mode ) { 224 return LSAPI_GetHeader( H_COOKIE ); 225 } else { 226 return NULL; 227 } 228} 229/* }}} */ 230 231 232/* {{{ sapi_lsapi_send_headers 233 */ 234static int sapi_lsapi_send_headers(sapi_headers_struct *sapi_headers TSRMLS_DC) 235{ 236 sapi_header_struct *h; 237 zend_llist_position pos; 238 if ( lsapi_mode ) { 239 LSAPI_SetRespStatus( SG(sapi_headers).http_response_code ); 240 241 h = zend_llist_get_first_ex(&sapi_headers->headers, &pos); 242 while (h) { 243 if ( h->header_len > 0 ) { 244 LSAPI_AppendRespHeader(h->header, h->header_len); 245 } 246 h = zend_llist_get_next_ex(&sapi_headers->headers, &pos); 247 } 248 if (SG(sapi_headers).send_default_content_type) { 249 char *hd; 250 int len; 251 char headerBuf[SAPI_LSAPI_MAX_HEADER_LENGTH]; 252 253 hd = sapi_get_default_content_type(TSRMLS_C); 254 len = snprintf( headerBuf, SAPI_LSAPI_MAX_HEADER_LENGTH - 1, 255 "Content-type: %s", hd ); 256 efree(hd); 257 258 LSAPI_AppendRespHeader( headerBuf, len ); 259 } 260 } 261 LSAPI_FinalizeRespHeaders(); 262 return SAPI_HEADER_SENT_SUCCESSFULLY; 263 264 265} 266/* }}} */ 267 268 269/* {{{ sapi_lsapi_send_headers 270 */ 271static void sapi_lsapi_log_message(char *message TSRMLS_DC) 272{ 273 int len = strlen( message ); 274 LSAPI_Write_Stderr( message, len); 275} 276/* }}} */ 277 278 279/* {{{ sapi_module_struct cgi_sapi_module 280 */ 281static sapi_module_struct lsapi_sapi_module = 282{ 283 "litespeed", 284 "LiteSpeed", 285 286 php_lsapi_startup, /* startup */ 287 php_module_shutdown_wrapper, /* shutdown */ 288 289 NULL, /* activate */ 290 sapi_lsapi_deactivate, /* deactivate */ 291 292 sapi_lsapi_ub_write, /* unbuffered write */ 293 sapi_lsapi_flush, /* flush */ 294 NULL, /* get uid */ 295 sapi_lsapi_getenv, /* getenv */ 296 297 php_error, /* error handler */ 298 299 NULL, /* header handler */ 300 sapi_lsapi_send_headers, /* send headers handler */ 301 NULL, /* send header handler */ 302 303 sapi_lsapi_read_post, /* read POST data */ 304 sapi_lsapi_read_cookies, /* read Cookies */ 305 306 sapi_lsapi_register_variables, /* register server variables */ 307 sapi_lsapi_log_message, /* Log message */ 308 309 NULL, /* php.ini path override */ 310 NULL, /* block interruptions */ 311 NULL, /* unblock interruptions */ 312 NULL, /* default post reader */ 313 NULL, /* treat data */ 314 NULL, /* executable location */ 315 316 0, /* php.ini ignore */ 317 318 STANDARD_SAPI_MODULE_PROPERTIES 319 320}; 321/* }}} */ 322 323static int init_request_info( TSRMLS_D ) 324{ 325 char * pContentType = LSAPI_GetHeader( H_CONTENT_TYPE ); 326 char * pAuth; 327 328 SG(request_info).content_type = pContentType ? pContentType : ""; 329 SG(request_info).request_method = LSAPI_GetRequestMethod(); 330 SG(request_info).query_string = LSAPI_GetQueryString(); 331 SG(request_info).request_uri = LSAPI_GetScriptName(); 332 SG(request_info).content_length = LSAPI_GetReqBodyLen(); 333 SG(request_info).path_translated = LSAPI_GetScriptFileName(); 334 335 /* It is not reset by zend engine, set it to 0. */ 336 SG(sapi_headers).http_response_code = 0; 337 338 pAuth = LSAPI_GetHeader( H_AUTHORIZATION ); 339 php_handle_auth_data(pAuth TSRMLS_CC); 340} 341 342static int lsapi_module_main(int show_source TSRMLS_DC) 343{ 344 zend_file_handle file_handle = {0}; 345 346 if (php_request_startup(TSRMLS_C) == FAILURE ) { 347 return -1; 348 } 349 if (show_source) { 350 zend_syntax_highlighter_ini syntax_highlighter_ini; 351 352 php_get_highlight_struct(&syntax_highlighter_ini); 353 highlight_file(SG(request_info).path_translated, &syntax_highlighter_ini TSRMLS_CC); 354 } else { 355 file_handle.type = ZEND_HANDLE_FILENAME; 356 file_handle.handle.fd = 0; 357 file_handle.filename = SG(request_info).path_translated; 358 file_handle.free_filename = 0; 359 file_handle.opened_path = NULL; 360 361 php_execute_script(&file_handle TSRMLS_CC); 362 } 363 zend_try { 364 php_request_shutdown(NULL); 365 } zend_end_try(); 366 return 0; 367} 368 369 370static int alter_ini( const char * pKey, int keyLen, const char * pValue, int valLen, 371 void * arg ) 372{ 373 int type = ZEND_INI_PERDIR; 374 if ( '\001' == *pKey ) { 375 ++pKey; 376 if ( *pKey == 4 ) { 377 type = ZEND_INI_SYSTEM; 378 } 379 ++pKey; 380 --keyLen; 381 zend_alter_ini_entry((char *)pKey, keyLen, 382 (char *)pValue, valLen, 383 type, PHP_INI_STAGE_ACTIVATE); 384 } 385 return 1; 386} 387 388 389static void override_ini() 390{ 391 392 LSAPI_ForeachSpecialEnv( alter_ini, NULL ); 393 394} 395 396static int processReq( TSRMLS_D ) 397{ 398 int ret = 0; 399 zend_first_try { 400 /* avoid server_context==NULL checks */ 401 SG(server_context) = (void *) 1; 402 403 init_request_info( TSRMLS_C ); 404 405 override_ini(); 406 407 if ( lsapi_module_main( source_highlight TSRMLS_CC ) == -1 ) { 408 ret = -1; 409 } 410 } zend_end_try(); 411 return ret; 412} 413 414static void cli_usage( TSRMLS_D ) 415{ 416 static const char * usage = 417 "Usage: php\n" 418 " php -[b|c|h|i|q|s|v|?] [<file>] [args...]\n" 419 " Run in LSAPI mode, only '-b', '-s' and '-c' are effective\n" 420 " Run in Command Line Interpreter mode when parameters are specified\n" 421 "\n" 422 " -b <address:port>|<port> Bind Path for external LSAPI Server mode\n" 423 " -c <path>|<file> Look for php.ini file in this directory\n" 424 " -h This help\n" 425 " -i PHP information\n" 426 " -q Quiet-mode. Suppress HTTP Header output.\n" 427 " -s Display colour syntax highlighted source.\n" 428 " -v Version number\n" 429 " -? This help\n" 430 "\n" 431 " args... Arguments passed to script.\n"; 432 php_output_startup(); 433 php_output_activate(TSRMLS_C); 434 php_printf( "%s", usage ); 435#ifdef PHP_OUTPUT_NEWAPI 436 php_output_end_all(TSRMLS_C); 437#else 438 php_end_ob_buffers(1 TSRMLS_CC); 439#endif 440} 441 442static int parse_opt( int argc, char * argv[], int *climode, 443 char **php_ini_path, char ** php_bind ) 444{ 445 char ** p = &argv[1]; 446 char ** argend= &argv[argc]; 447 int c; 448 while (( p < argend )&&(**p == '-' )) { 449 c = *((*p)+1); 450 ++p; 451 switch( c ) { 452 case 'b': 453 if ( p >= argend ) { 454 fprintf( stderr, "TCP or socket address must be specified following '-b' option.\n"); 455 return -1; 456 } 457 *php_bind = *p++; 458 break; 459 460 case 'c': 461 if ( p >= argend ) { 462 fprintf( stderr, "<path> or <file> must be specified following '-c' option.\n"); 463 464 return -1; 465 } 466 *php_ini_path = *p++; 467 break; 468 case 's': 469 source_highlight = 1; 470 break; 471 case 'h': 472 case 'i': 473 case 'q': 474 case 'v': 475 case '?': 476 default: 477 *climode = 1; 478 break; 479 } 480 } 481 if ( p - argv < argc ) { 482 *climode = 1; 483 } 484 return 0; 485} 486 487static int cli_main( int argc, char * argv[] ) 488{ 489 490 static const char * ini_defaults[] = { 491 "report_zend_debug", "0", 492 "display_errors", "1", 493 "register_argc_argv", "1", 494 "html_errors", "0", 495 "implicit_flush", "1", 496 "output_buffering", "0", 497 "max_execution_time", "0", 498 "max_input_time", "-1", 499 NULL 500 }; 501 502 const char ** ini; 503 char ** p = &argv[1]; 504 char ** argend= &argv[argc]; 505 int ret = 0; 506 int c; 507 lsapi_mode = 0; /* enter CLI mode */ 508 509#ifdef PHP_WIN32 510 _fmode = _O_BINARY; /*sets default for file streams to binary */ 511 setmode(_fileno(stdin), O_BINARY); /* make the stdio mode be binary */ 512 setmode(_fileno(stdout), O_BINARY); /* make the stdio mode be binary */ 513 setmode(_fileno(stderr), O_BINARY); /* make the stdio mode be binary */ 514#endif 515 516 zend_first_try { 517 SG(server_context) = (void *) 1; 518 519 zend_uv.html_errors = 0; /* tell the engine we're in non-html mode */ 520 CG(in_compilation) = 0; /* not initialized but needed for several options */ 521 EG(uninitialized_zval_ptr) = NULL; 522 523 for( ini = ini_defaults; *ini; ini+=2 ) { 524 zend_alter_ini_entry( (char *)*ini, strlen( *ini )+1, 525 (char *)*(ini+1), strlen( *(ini+1) ), 526 PHP_INI_SYSTEM, PHP_INI_STAGE_ACTIVATE); 527 } 528 529 while (( p < argend )&&(**p == '-' )) { 530 c = *((*p)+1); 531 ++p; 532 switch( c ) { 533 case 'q': 534 break; 535 case 'i': 536 if (php_request_startup(TSRMLS_C) != FAILURE) { 537 php_print_info(0xFFFFFFFF TSRMLS_CC); 538#ifdef PHP_OUTPUT_NEWAPI 539 php_output_end_all(TSRMLS_C); 540#else 541 php_end_ob_buffers(1 TSRMLS_CC); 542#endif 543 php_request_shutdown( NULL ); 544 } 545 ret = 1; 546 break; 547 case 'v': 548 if (php_request_startup(TSRMLS_C) != FAILURE) { 549#if ZEND_DEBUG 550 php_printf("PHP %s (%s) (built: %s %s) (DEBUG)\nCopyright (c) 1997-2013 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version()); 551#else 552 php_printf("PHP %s (%s) (built: %s %s)\nCopyright (c) 1997-2013 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version()); 553#endif 554#ifdef PHP_OUTPUT_NEWAPI 555 php_output_end_all(TSRMLS_C); 556#else 557 php_end_ob_buffers(1 TSRMLS_CC); 558#endif 559 php_request_shutdown( NULL ); 560 } 561 ret = 1; 562 break; 563 case 'c': 564 ++p; 565 /* fall through */ 566 case 's': 567 break; 568 569 case 'h': 570 case '?': 571 default: 572 cli_usage(TSRMLS_C); 573 ret = 1; 574 break; 575 576 } 577 } 578 if ( !ret ) { 579 if ( *p ) { 580 zend_file_handle file_handle = {0}; 581 582 file_handle.type = ZEND_HANDLE_FP; 583 file_handle.handle.fp = VCWD_FOPEN(*p, "rb"); 584 585 if ( file_handle.handle.fp ) { 586 script_filename = *p; 587 php_self = *p; 588 589 SG(request_info).path_translated = *p; 590 SG(request_info).argc = argc - (p - argv); 591 SG(request_info).argv = p; 592 593 if (php_request_startup(TSRMLS_C) == FAILURE ) { 594 fclose( file_handle.handle.fp ); 595 ret = 2; 596 } else { 597 if (source_highlight) { 598 zend_syntax_highlighter_ini syntax_highlighter_ini; 599 600 php_get_highlight_struct(&syntax_highlighter_ini); 601 highlight_file(SG(request_info).path_translated, &syntax_highlighter_ini TSRMLS_CC); 602 } else { 603 file_handle.filename = *p; 604 file_handle.free_filename = 0; 605 file_handle.opened_path = NULL; 606 607 php_execute_script(&file_handle TSRMLS_CC); 608 } 609 610 php_request_shutdown( NULL ); 611 } 612 } else { 613 php_printf("Could not open input file: %s.\n", *p); 614 } 615 } else { 616 cli_usage(TSRMLS_C); 617 } 618 } 619 620 }zend_end_try(); 621 622 php_module_shutdown(TSRMLS_C); 623 624#ifdef ZTS 625 tsrm_shutdown(); 626#endif 627 return ret; 628} 629 630static int s_stop; 631void litespeed_cleanup(int signal) 632{ 633 s_stop = signal; 634} 635 636 637void start_children( int children ) 638{ 639 struct sigaction act, old_term, old_quit, old_int, old_usr1; 640 int running = 0; 641 int status; 642 pid_t pid; 643 644 /* Create a process group */ 645 setsid(); 646 647 /* Set up handler to kill children upon exit */ 648 act.sa_flags = 0; 649 act.sa_handler = litespeed_cleanup; 650 if( sigaction( SIGTERM, &act, &old_term ) || 651 sigaction( SIGINT, &act, &old_int ) || 652 sigaction( SIGUSR1, &act, &old_usr1 ) || 653 sigaction( SIGQUIT, &act, &old_quit )) { 654 perror( "Can't set signals" ); 655 exit( 1 ); 656 } 657 s_stop = 0; 658 while( 1 ) { 659 while((!s_stop )&&( running < children )) { 660 pid = fork(); 661 switch( pid ) { 662 case 0: /* children process */ 663 664 /* don't catch our signals */ 665 sigaction( SIGTERM, &old_term, 0 ); 666 sigaction( SIGQUIT, &old_quit, 0 ); 667 sigaction( SIGINT, &old_int, 0 ); 668 sigaction( SIGUSR1, &old_usr1, 0 ); 669 return ; 670 case -1: 671 perror( "php (pre-forking)" ); 672 exit( 1 ); 673 break; 674 default: /* parent process */ 675 running++; 676 break; 677 } 678 } 679 if ( s_stop ) { 680 break; 681 } 682 pid = wait( &status ); 683 running--; 684 } 685 kill( -getpgrp(), SIGUSR1 ); 686 exit( 0 ); 687} 688 689 690 691#include <fcntl.h> 692int main( int argc, char * argv[] ) 693{ 694 int ret; 695 int bindFd; 696 697 char * php_ini_path = NULL; 698 char * php_bind = NULL; 699 char * p; 700 int n; 701 int climode = 0; 702 703#ifdef HAVE_SIGNAL_H 704#if defined(SIGPIPE) && defined(SIG_IGN) 705 signal(SIGPIPE, SIG_IGN); 706#endif 707#endif 708 709#ifdef ZTS 710 tsrm_startup(1, 1, 0, NULL); 711#endif 712 713 if (argc > 1 ) { 714 if ( parse_opt( argc, argv, &climode, 715 &php_ini_path, &php_bind ) == -1 ) { 716 return 1; 717 } 718 } 719 if ( climode ) { 720 lsapi_sapi_module.phpinfo_as_text = 1; 721 } 722 sapi_startup(&lsapi_sapi_module); 723 724#ifdef ZTS 725 compiler_globals = ts_resource(compiler_globals_id); 726 executor_globals = ts_resource(executor_globals_id); 727 core_globals = ts_resource(core_globals_id); 728 sapi_globals = ts_resource(sapi_globals_id); 729 tsrm_ls = ts_resource(0); 730 731 SG(request_info).path_translated = NULL; 732#endif 733 734 lsapi_sapi_module.executable_location = argv[0]; 735 736 if ( php_ini_path ) { 737 lsapi_sapi_module.php_ini_path_override = php_ini_path; 738 } 739 740 if (php_module_startup(&lsapi_sapi_module, &litespeed_module_entry, 1) == FAILURE) { 741#ifdef ZTS 742 tsrm_shutdown(); 743#endif 744 return FAILURE; 745 } 746 747 if ( climode ) { 748 return cli_main(argc, argv); 749 } 750 751 752 if ( php_bind ) { 753 bindFd = LSAPI_CreateListenSock( php_bind, 10 ); 754 if ( bindFd == -1 ) { 755 fprintf( stderr, 756 "Failed to bind socket [%s]: %s\n", php_bind, strerror( errno ) ); 757 exit( 2 ); 758 } 759 if ( bindFd != 0 ) { 760 dup2( bindFd, 0 ); 761 close( bindFd ); 762 } 763 } 764 765 LSAPI_Init(); 766 767 LSAPI_Init_Env_Parameters( NULL ); 768 769 if ( php_bind ) { 770 LSAPI_No_Check_ppid(); 771 } 772 773 while( LSAPI_Prefork_Accept_r( &g_req ) >= 0 ) { 774 ret = processReq(TSRMLS_C); 775 LSAPI_Finish(); 776 if ( ret ) { 777 break; 778 } 779 } 780 php_module_shutdown(TSRMLS_C); 781 782#ifdef ZTS 783 tsrm_shutdown(); 784#endif 785 return ret; 786} 787 788 789/* LiteSpeed PHP module starts here */ 790 791/* {{{ arginfo */ 792ZEND_BEGIN_ARG_INFO(arginfo_litespeed__void, 0) 793ZEND_END_ARG_INFO() 794/* }}} */ 795 796PHP_FUNCTION(litespeed_request_headers); 797PHP_FUNCTION(litespeed_response_headers); 798 799PHP_MINFO_FUNCTION(litespeed); 800 801zend_function_entry litespeed_functions[] = { 802 PHP_FE(litespeed_request_headers, arginfo_litespeed__void) 803 PHP_FE(litespeed_response_headers, arginfo_litespeed__void) 804 PHP_FALIAS(getallheaders, litespeed_request_headers, arginfo_litespeed__void) 805 PHP_FALIAS(apache_request_headers, litespeed_request_headers, arginfo_litespeed__void) 806 PHP_FALIAS(apache_response_headers, litespeed_response_headers, arginfo_litespeed__void) 807 {NULL, NULL, NULL} 808}; 809 810static PHP_MINIT_FUNCTION(litespeed) 811{ 812 /* REGISTER_INI_ENTRIES(); */ 813 return SUCCESS; 814} 815 816 817static PHP_MSHUTDOWN_FUNCTION(litespeed) 818{ 819 /* UNREGISTER_INI_ENTRIES(); */ 820 return SUCCESS; 821} 822 823zend_module_entry litespeed_module_entry = { 824 STANDARD_MODULE_HEADER, 825 "litespeed", 826 litespeed_functions, 827 PHP_MINIT(litespeed), 828 PHP_MSHUTDOWN(litespeed), 829 NULL, 830 NULL, 831 NULL, 832 NO_VERSION_YET, 833 STANDARD_MODULE_PROPERTIES 834}; 835 836static int add_associate_array( const char * pKey, int keyLen, const char * pValue, int valLen, 837 void * arg ) 838{ 839 add_assoc_string_ex( (zval *)arg, (char *)pKey, keyLen+1, (char *)pValue, 1 ); 840 return 1; 841} 842 843 844/* {{{ proto array litespeed_request_headers(void) 845 Fetch all HTTP request headers */ 846PHP_FUNCTION(litespeed_request_headers) 847{ 848 /* TODO: */ 849 if (ZEND_NUM_ARGS() > 0) { 850 WRONG_PARAM_COUNT; 851 } 852 array_init(return_value); 853 854 LSAPI_ForeachOrgHeader( add_associate_array, return_value ); 855 856} 857/* }}} */ 858 859 860 861/* {{{ proto array litespeed_response_headers(void) 862 Fetch all HTTP response headers */ 863PHP_FUNCTION(litespeed_response_headers) 864{ 865 sapi_header_struct *h; 866 zend_llist_position pos; 867 char * p; 868 int len; 869 char headerBuf[SAPI_LSAPI_MAX_HEADER_LENGTH]; 870 871 if (ZEND_NUM_ARGS() > 0) { 872 WRONG_PARAM_COUNT; 873 } 874 875 if (!&SG(sapi_headers).headers) { 876 RETURN_FALSE; 877 } 878 array_init(return_value); 879 880 h = zend_llist_get_first_ex(&SG(sapi_headers).headers, &pos); 881 while (h) { 882 if ( h->header_len > 0 ) { 883 p = strchr( h->header, ':' ); 884 len = p - h->header; 885 if (( p )&&( len > 0 )) { 886 memmove( headerBuf, h->header, len ); 887 while( len > 0 && (isspace( headerBuf[len-1])) ) { 888 --len; 889 } 890 headerBuf[len] = 0; 891 if ( len ) { 892 while( isspace(*++p)); 893 add_assoc_string_ex(return_value, headerBuf, len+1, p, 1 ); 894 } 895 } 896 } 897 h = zend_llist_get_next_ex(&SG(sapi_headers).headers, &pos); 898 } 899} 900 901/* }}} */ 902 903 904/* 905 * Local variables: 906 * tab-width: 4 907 * c-basic-offset: 4 908 * End: 909 * vim600: sw=4 ts=4 fdm=marker 910 * vim<600: sw=4 ts=4 911 */ 912 913 914