diff options
| author | Ben Fuhrmannek | 2014-08-19 16:53:08 +0200 |
|---|---|---|
| committer | Ben Fuhrmannek | 2014-08-19 16:53:08 +0200 |
| commit | 9d00bb4b438d5cb21ea8fc038892ddf8563a9c26 (patch) | |
| tree | 4f82de0452b3fd3f15430dd613cf18a407cb7968 | |
| parent | 4dfbd136ed93c916909ad9c701a8be9226298d9e (diff) | |
| parent | b074d630123a28cbca3babc756cbec6dede996f7 (diff) | |
Merge branch 'cleanup'
| -rw-r--r-- | ex_imp.c | 102 | ||||
| -rw-r--r-- | execute.c | 8 | ||||
| -rw-r--r-- | ifilter.c | 116 | ||||
| -rw-r--r-- | log.c | 4 | ||||
| -rw-r--r-- | php_suhosin.h | 101 | ||||
| -rw-r--r-- | session.c | 2 | ||||
| -rw-r--r-- | suhosin.c | 219 | ||||
| -rw-r--r-- | ufilter.c | 52 |
8 files changed, 192 insertions, 412 deletions
| @@ -74,29 +74,7 @@ static int php_valid_var_name(char *var_name, int len) /* {{{ */ | |||
| 74 | } | 74 | } |
| 75 | } | 75 | } |
| 76 | 76 | ||
| 77 | if (var_name[0] == 'H') { | 77 | if (suhosin_is_protected_varname(var_name, len)) { |
| 78 | if ((strcmp(var_name, "HTTP_GET_VARS")==0)|| | ||
| 79 | (strcmp(var_name, "HTTP_POST_VARS")==0)|| | ||
| 80 | (strcmp(var_name, "HTTP_POST_FILES")==0)|| | ||
| 81 | (strcmp(var_name, "HTTP_ENV_VARS")==0)|| | ||
| 82 | (strcmp(var_name, "HTTP_SERVER_VARS")==0)|| | ||
| 83 | (strcmp(var_name, "HTTP_SESSION_VARS")==0)|| | ||
| 84 | (strcmp(var_name, "HTTP_COOKIE_VARS")==0)|| | ||
| 85 | (strcmp(var_name, "HTTP_RAW_POST_DATA")==0)) { | ||
| 86 | return 0; | ||
| 87 | } | ||
| 88 | } else if (var_name[0] == '_') { | ||
| 89 | if ((strcmp(var_name, "_COOKIE")==0)|| | ||
| 90 | (strcmp(var_name, "_ENV")==0)|| | ||
| 91 | (strcmp(var_name, "_FILES")==0)|| | ||
| 92 | (strcmp(var_name, "_GET")==0)|| | ||
| 93 | (strcmp(var_name, "_POST")==0)|| | ||
| 94 | (strcmp(var_name, "_REQUEST")==0)|| | ||
| 95 | (strcmp(var_name, "_SESSION")==0)|| | ||
| 96 | (strcmp(var_name, "_SERVER")==0)) { | ||
| 97 | return 0; | ||
| 98 | } | ||
| 99 | } else if (strcmp(var_name, "GLOBALS")==0) { | ||
| 100 | return 0; | 78 | return 0; |
| 101 | } | 79 | } |
| 102 | 80 | ||
| @@ -443,6 +421,14 @@ PHP_FUNCTION(suhosin_extract) | |||
| 443 | /* }}} */ | 421 | /* }}} */ |
| 444 | 422 | ||
| 445 | 423 | ||
| 424 | |||
| 425 | #if PHP_VERSION_ID < 50400 | ||
| 426 | /* import_request_variables() has been DEPRECATED as of PHP 5.3.0 and REMOVED as of PHP 5.4.0. */ | ||
| 427 | #define SUHOSIN_HAVE_IRV 1 | ||
| 428 | #endif | ||
| 429 | |||
| 430 | #ifdef SUHOSIN_HAVE_IRV | ||
| 431 | |||
| 446 | #if PHP_VERSION_ID >= 50300 | 432 | #if PHP_VERSION_ID >= 50300 |
| 447 | static int copy_request_variable(void *pDest TSRMLS_DC, int num_args, va_list args, zend_hash_key *hash_key) | 433 | static int copy_request_variable(void *pDest TSRMLS_DC, int num_args, va_list args, zend_hash_key *hash_key) |
| 448 | { | 434 | { |
| @@ -473,36 +459,7 @@ static int copy_request_variable(void *pDest TSRMLS_DC, int num_args, va_list ar | |||
| 473 | zval_dtor(&num); | 459 | zval_dtor(&num); |
| 474 | } | 460 | } |
| 475 | 461 | ||
| 476 | if (php_varname_check(Z_STRVAL(new_key), Z_STRLEN(new_key), 0 TSRMLS_CC) == FAILURE) { | 462 | if (php_varname_check(Z_STRVAL(new_key), Z_STRLEN(new_key), 1 TSRMLS_CC) == FAILURE || suhosin_is_protected_varname(Z_STRVAL(new_key), Z_STRLEN(new_key))) { |
| 477 | zval_dtor(&new_key); | ||
| 478 | return 0; | ||
| 479 | } | ||
| 480 | |||
| 481 | if (Z_STRVAL(new_key)[0] == 'H') { | ||
| 482 | if ((strcmp(Z_STRVAL(new_key), "HTTP_GET_VARS")==0)|| | ||
| 483 | (strcmp(Z_STRVAL(new_key), "HTTP_POST_VARS")==0)|| | ||
| 484 | (strcmp(Z_STRVAL(new_key), "HTTP_POST_FILES")==0)|| | ||
| 485 | (strcmp(Z_STRVAL(new_key), "HTTP_ENV_VARS")==0)|| | ||
| 486 | (strcmp(Z_STRVAL(new_key), "HTTP_SERVER_VARS")==0)|| | ||
| 487 | (strcmp(Z_STRVAL(new_key), "HTTP_SESSION_VARS")==0)|| | ||
| 488 | (strcmp(Z_STRVAL(new_key), "HTTP_COOKIE_VARS")==0)|| | ||
| 489 | (strcmp(Z_STRVAL(new_key), "HTTP_RAW_POST_DATA")==0)) { | ||
| 490 | zval_dtor(&new_key); | ||
| 491 | return 0; | ||
| 492 | } | ||
| 493 | } else if (Z_STRVAL(new_key)[0] == '_') { | ||
| 494 | if ((strcmp(Z_STRVAL(new_key), "_COOKIE")==0)|| | ||
| 495 | (strcmp(Z_STRVAL(new_key), "_ENV")==0)|| | ||
| 496 | (strcmp(Z_STRVAL(new_key), "_FILES")==0)|| | ||
| 497 | (strcmp(Z_STRVAL(new_key), "_GET")==0)|| | ||
| 498 | (strcmp(Z_STRVAL(new_key), "_POST")==0)|| | ||
| 499 | (strcmp(Z_STRVAL(new_key), "_REQUEST")==0)|| | ||
| 500 | (strcmp(Z_STRVAL(new_key), "_SESSION")==0)|| | ||
| 501 | (strcmp(Z_STRVAL(new_key), "_SERVER")==0)) { | ||
| 502 | zval_dtor(&new_key); | ||
| 503 | return 0; | ||
| 504 | } | ||
| 505 | } else if (strcmp(Z_STRVAL(new_key), "GLOBALS")==0) { | ||
| 506 | zval_dtor(&new_key); | 463 | zval_dtor(&new_key); |
| 507 | return 0; | 464 | return 0; |
| 508 | } | 465 | } |
| @@ -549,36 +506,7 @@ static int copy_request_variable(void *pDest, int num_args, va_list args, zend_h | |||
| 549 | new_key_len++; | 506 | new_key_len++; |
| 550 | } | 507 | } |
| 551 | 508 | ||
| 552 | if (php_varname_check(new_key, new_key_len-1, 0 TSRMLS_CC) == FAILURE) { | 509 | if (php_varname_check(new_key, new_key_len-1, 1 TSRMLS_CC) == FAILURE || suhosin_is_protected_varname(new_key, new_key_len-1)) { |
| 553 | zval_dtor(&new_key); | ||
| 554 | return 0; | ||
| 555 | } | ||
| 556 | |||
| 557 | if (new_key[0] == 'H') { | ||
| 558 | if ((strcmp(new_key, "HTTP_GET_VARS")==0)|| | ||
| 559 | (strcmp(new_key, "HTTP_POST_VARS")==0)|| | ||
| 560 | (strcmp(new_key, "HTTP_POST_FILES")==0)|| | ||
| 561 | (strcmp(new_key, "HTTP_ENV_VARS")==0)|| | ||
| 562 | (strcmp(new_key, "HTTP_SERVER_VARS")==0)|| | ||
| 563 | (strcmp(new_key, "HTTP_SESSION_VARS")==0)|| | ||
| 564 | (strcmp(new_key, "HTTP_COOKIE_VARS")==0)|| | ||
| 565 | (strcmp(new_key, "HTTP_RAW_POST_DATA")==0)) { | ||
| 566 | efree(new_key); | ||
| 567 | return 0; | ||
| 568 | } | ||
| 569 | } else if (new_key[0] == '_') { | ||
| 570 | if ((strcmp(new_key, "_COOKIE")==0)|| | ||
| 571 | (strcmp(new_key, "_ENV")==0)|| | ||
| 572 | (strcmp(new_key, "_FILES")==0)|| | ||
| 573 | (strcmp(new_key, "_GET")==0)|| | ||
| 574 | (strcmp(new_key, "_POST")==0)|| | ||
| 575 | (strcmp(new_key, "_REQUEST")==0)|| | ||
| 576 | (strcmp(new_key, "_SESSION")==0)|| | ||
| 577 | (strcmp(new_key, "_SERVER")==0)) { | ||
| 578 | efree(new_key); | ||
| 579 | return 0; | ||
| 580 | } | ||
| 581 | } else if (strcmp(new_key, "GLOBALS")==0) { | ||
| 582 | efree(new_key); | 510 | efree(new_key); |
| 583 | return 0; | 511 | return 0; |
| 584 | } | 512 | } |
| @@ -714,22 +642,28 @@ PHP_FUNCTION(suhosin_import_request_variables) | |||
| 714 | } | 642 | } |
| 715 | /* }}} */ | 643 | /* }}} */ |
| 716 | 644 | ||
| 645 | #endif /* SUHOSIN_HAVE_IRV */ | ||
| 646 | |||
| 717 | ZEND_BEGIN_ARG_INFO_EX(suhosin_arginfo_extract, 0, 0, 1) | 647 | ZEND_BEGIN_ARG_INFO_EX(suhosin_arginfo_extract, 0, 0, 1) |
| 718 | ZEND_ARG_INFO(ZEND_SEND_PREFER_REF, arg) /* ARRAY_INFO(0, arg, 0) */ | 648 | ZEND_ARG_INFO(ZEND_SEND_PREFER_REF, arg) /* ARRAY_INFO(0, arg, 0) */ |
| 719 | ZEND_ARG_INFO(0, extract_type) | 649 | ZEND_ARG_INFO(0, extract_type) |
| 720 | ZEND_ARG_INFO(0, prefix) | 650 | ZEND_ARG_INFO(0, prefix) |
| 721 | ZEND_END_ARG_INFO() | 651 | ZEND_END_ARG_INFO() |
| 722 | 652 | ||
| 653 | #ifdef SUHOSIN_HAVE_IRV | ||
| 723 | ZEND_BEGIN_ARG_INFO_EX(suhosin_arginfo_import_request_variables, 0, 0, 1) | 654 | ZEND_BEGIN_ARG_INFO_EX(suhosin_arginfo_import_request_variables, 0, 0, 1) |
| 724 | ZEND_ARG_INFO(0, types) | 655 | ZEND_ARG_INFO(0, types) |
| 725 | ZEND_ARG_INFO(0, prefix) | 656 | ZEND_ARG_INFO(0, prefix) |
| 726 | ZEND_END_ARG_INFO() | 657 | ZEND_END_ARG_INFO() |
| 658 | #endif | ||
| 727 | 659 | ||
| 728 | /* {{{ suhosin_ex_imp_functions[] | 660 | /* {{{ suhosin_ex_imp_functions[] |
| 729 | */ | 661 | */ |
| 730 | zend_function_entry suhosin_ex_imp_functions[] = { | 662 | zend_function_entry suhosin_ex_imp_functions[] = { |
| 731 | PHP_NAMED_FE(extract, PHP_FN(suhosin_extract), suhosin_arginfo_extract) | 663 | PHP_NAMED_FE(extract, PHP_FN(suhosin_extract), suhosin_arginfo_extract) |
| 664 | #ifdef SUHOSIN_HAVE_IRV | ||
| 732 | PHP_NAMED_FE(import_request_variables, PHP_FN(suhosin_import_request_variables), suhosin_arginfo_import_request_variables) | 665 | PHP_NAMED_FE(import_request_variables, PHP_FN(suhosin_import_request_variables), suhosin_arginfo_import_request_variables) |
| 666 | #endif | ||
| 733 | {NULL, NULL, NULL} | 667 | {NULL, NULL, NULL} |
| 734 | }; | 668 | }; |
| 735 | /* }}} */ | 669 | /* }}} */ |
| @@ -740,7 +674,9 @@ void suhosin_hook_ex_imp() | |||
| 740 | 674 | ||
| 741 | /* replace the extract and import_request_variables functions */ | 675 | /* replace the extract and import_request_variables functions */ |
| 742 | zend_hash_del(CG(function_table), "extract", sizeof("extract")); | 676 | zend_hash_del(CG(function_table), "extract", sizeof("extract")); |
| 677 | #ifdef SUHOSIN_HAVE_IRV | ||
| 743 | zend_hash_del(CG(function_table), "import_request_variables", sizeof("import_request_variables")); | 678 | zend_hash_del(CG(function_table), "import_request_variables", sizeof("import_request_variables")); |
| 679 | #endif | ||
| 744 | #ifndef ZEND_ENGINE_2 | 680 | #ifndef ZEND_ENGINE_2 |
| 745 | zend_register_functions(suhosin_ex_imp_functions, NULL, MODULE_PERSISTENT TSRMLS_CC); | 681 | zend_register_functions(suhosin_ex_imp_functions, NULL, MODULE_PERSISTENT TSRMLS_CC); |
| 746 | #else | 682 | #else |
| @@ -150,7 +150,7 @@ static int suhosin_check_filename(char *s, int len TSRMLS_DC) | |||
| 150 | return SUHOSIN_CODE_TYPE_MANYDOTS; | 150 | return SUHOSIN_CODE_TYPE_MANYDOTS; |
| 151 | } | 151 | } |
| 152 | 152 | ||
| 153 | SDEBUG("xxx %08x %08x",SUHOSIN_G(include_whitelist),SUHOSIN_G(include_blacklist)); | 153 | SDEBUG("xxx %p %p",SUHOSIN_G(include_whitelist),SUHOSIN_G(include_blacklist)); |
| 154 | /* no black or whitelist then disallow all */ | 154 | /* no black or whitelist then disallow all */ |
| 155 | if (SUHOSIN_G(include_whitelist)==NULL && SUHOSIN_G(include_blacklist)==NULL) { | 155 | if (SUHOSIN_G(include_whitelist)==NULL && SUHOSIN_G(include_blacklist)==NULL) { |
| 156 | /* disallow all URLs */ | 156 | /* disallow all URLs */ |
| @@ -519,7 +519,7 @@ static void suhosin_execute_ex(zend_op_array *op_array, int zo, long dummy TSRML | |||
| 519 | } else { | 519 | } else { |
| 520 | if (suhosin_zend_extension_entry.resource_number != -1) { | 520 | if (suhosin_zend_extension_entry.resource_number != -1) { |
| 521 | suhosin_flags = (unsigned long *) &op_array->reserved[suhosin_zend_extension_entry.resource_number]; | 521 | suhosin_flags = (unsigned long *) &op_array->reserved[suhosin_zend_extension_entry.resource_number]; |
| 522 | SDEBUG("suhosin flags: %08x", *suhosin_flags); | 522 | SDEBUG("suhosin flags: %08lx", *suhosin_flags); |
| 523 | 523 | ||
| 524 | if (*suhosin_flags & SUHOSIN_FLAG_CREATED_BY_EVAL) { | 524 | if (*suhosin_flags & SUHOSIN_FLAG_CREATED_BY_EVAL) { |
| 525 | SUHOSIN_G(in_code_type) = SUHOSIN_EVAL; | 525 | SUHOSIN_G(in_code_type) = SUHOSIN_EVAL; |
| @@ -632,7 +632,6 @@ not_evaled_code: | |||
| 632 | case SUHOSIN_CODE_TYPE_UNKNOWN: | 632 | case SUHOSIN_CODE_TYPE_UNKNOWN: |
| 633 | case SUHOSIN_CODE_TYPE_GOODFILE: | 633 | case SUHOSIN_CODE_TYPE_GOODFILE: |
| 634 | goto continue_execution; | 634 | goto continue_execution; |
| 635 | break; | ||
| 636 | } | 635 | } |
| 637 | 636 | ||
| 638 | continue_execution: | 637 | continue_execution: |
| @@ -1060,9 +1059,8 @@ int ih_fixusername(IH_HANDLER_PARAMS) | |||
| 1060 | if (!SUHOSIN_G(simulation)) { | 1059 | if (!SUHOSIN_G(simulation)) { |
| 1061 | RETVAL_FALSE; | 1060 | RETVAL_FALSE; |
| 1062 | return (1); | 1061 | return (1); |
| 1063 | } else { | ||
| 1064 | break; | ||
| 1065 | } | 1062 | } |
| 1063 | break; | ||
| 1066 | } | 1064 | } |
| 1067 | cp++; | 1065 | cp++; |
| 1068 | } | 1066 | } |
| @@ -29,6 +29,7 @@ | |||
| 29 | #include "ext/standard/info.h" | 29 | #include "ext/standard/info.h" |
| 30 | #include "php_suhosin.h" | 30 | #include "php_suhosin.h" |
| 31 | #include "php_variables.h" | 31 | #include "php_variables.h" |
| 32 | #include "ext/standard/php_var.h" | ||
| 32 | 33 | ||
| 33 | 34 | ||
| 34 | static void (*orig_register_server_variables)(zval *track_vars_array TSRMLS_DC) = NULL; | 35 | static void (*orig_register_server_variables)(zval *track_vars_array TSRMLS_DC) = NULL; |
| @@ -150,7 +151,6 @@ static void suhosin_server_encode(HashTable *arr, char *key, int klen) | |||
| 150 | 151 | ||
| 151 | temp = (unsigned char *)Z_STRVAL_PP(tzval); | 152 | temp = (unsigned char *)Z_STRVAL_PP(tzval); |
| 152 | 153 | ||
| 153 | t = temp; | ||
| 154 | for (t = temp; *t; t++) { | 154 | for (t = temp; *t; t++) { |
| 155 | if (suhosin_is_dangerous_char[*t]) { | 155 | if (suhosin_is_dangerous_char[*t]) { |
| 156 | extra += 2; | 156 | extra += 2; |
| @@ -186,30 +186,29 @@ static void suhosin_server_encode(HashTable *arr, char *key, int klen) | |||
| 186 | */ | 186 | */ |
| 187 | void suhosin_register_server_variables(zval *track_vars_array TSRMLS_DC) | 187 | void suhosin_register_server_variables(zval *track_vars_array TSRMLS_DC) |
| 188 | { | 188 | { |
| 189 | HashTable *svars; | 189 | HashTable *svars; |
| 190 | int retval, failure=0; | 190 | int retval = 0, failure = 0; |
| 191 | |||
| 192 | orig_register_server_variables(track_vars_array TSRMLS_CC); | ||
| 193 | 191 | ||
| 194 | svars = Z_ARRVAL_P(track_vars_array); | 192 | orig_register_server_variables(track_vars_array TSRMLS_CC); |
| 195 | 193 | ||
| 194 | svars = Z_ARRVAL_P(track_vars_array); | ||
| 196 | if (!SUHOSIN_G(simulation)) { | 195 | if (!SUHOSIN_G(simulation)) { |
| 197 | retval = zend_hash_del(svars, "HTTP_GET_VARS", sizeof("HTTP_GET_VARS")); | 196 | retval = zend_hash_del(svars, "HTTP_GET_VARS", sizeof("HTTP_GET_VARS")); |
| 198 | if (retval == SUCCESS) failure = 1; | 197 | if (retval == SUCCESS) failure = 1; |
| 199 | retval = zend_hash_del(svars, "HTTP_POST_VARS", sizeof("HTTP_POST_VARS")); | 198 | retval = zend_hash_del(svars, "HTTP_POST_VARS", sizeof("HTTP_POST_VARS")); |
| 200 | if (retval == SUCCESS) failure = 1; | 199 | if (retval == SUCCESS) failure = 1; |
| 201 | retval = zend_hash_del(svars, "HTTP_COOKIE_VARS", sizeof("HTTP_COOKIE_VARS")); | 200 | retval = zend_hash_del(svars, "HTTP_COOKIE_VARS", sizeof("HTTP_COOKIE_VARS")); |
| 202 | if (retval == SUCCESS) failure = 1; | 201 | if (retval == SUCCESS) failure = 1; |
| 203 | retval = zend_hash_del(svars, "HTTP_ENV_VARS", sizeof("HTTP_ENV_VARS")); | 202 | retval = zend_hash_del(svars, "HTTP_ENV_VARS", sizeof("HTTP_ENV_VARS")); |
| 204 | if (retval == SUCCESS) failure = 1; | 203 | if (retval == SUCCESS) failure = 1; |
| 205 | retval = zend_hash_del(svars, "HTTP_SERVER_VARS", sizeof("HTTP_SERVER_VARS")); | 204 | retval = zend_hash_del(svars, "HTTP_SERVER_VARS", sizeof("HTTP_SERVER_VARS")); |
| 206 | if (retval == SUCCESS) failure = 1; | 205 | if (retval == SUCCESS) failure = 1; |
| 207 | retval = zend_hash_del(svars, "HTTP_SESSION_VARS", sizeof("HTTP_SESSION_VARS")); | 206 | retval = zend_hash_del(svars, "HTTP_SESSION_VARS", sizeof("HTTP_SESSION_VARS")); |
| 208 | if (retval == SUCCESS) failure = 1; | 207 | if (retval == SUCCESS) failure = 1; |
| 209 | retval = zend_hash_del(svars, "HTTP_POST_FILES", sizeof("HTTP_POST_FILES")); | 208 | retval = zend_hash_del(svars, "HTTP_POST_FILES", sizeof("HTTP_POST_FILES")); |
| 210 | if (retval == SUCCESS) failure = 1; | 209 | if (retval == SUCCESS) failure = 1; |
| 211 | retval = zend_hash_del(svars, "HTTP_RAW_POST_DATA", sizeof("HTTP_RAW_POST_DATA")); | 210 | retval = zend_hash_del(svars, "HTTP_RAW_POST_DATA", sizeof("HTTP_RAW_POST_DATA")); |
| 212 | if (retval == SUCCESS) failure = 1; | 211 | if (retval == SUCCESS) failure = 1; |
| 213 | } else { | 212 | } else { |
| 214 | retval = zend_hash_exists(svars, "HTTP_GET_VARS", sizeof("HTTP_GET_VARS")); | 213 | retval = zend_hash_exists(svars, "HTTP_GET_VARS", sizeof("HTTP_GET_VARS")); |
| 215 | retval+= zend_hash_exists(svars, "HTTP_POST_VARS", sizeof("HTTP_POST_VARS")); | 214 | retval+= zend_hash_exists(svars, "HTTP_POST_VARS", sizeof("HTTP_POST_VARS")); |
| @@ -221,19 +220,19 @@ void suhosin_register_server_variables(zval *track_vars_array TSRMLS_DC) | |||
| 221 | retval+= zend_hash_exists(svars, "HTTP_RAW_POST_DATA", sizeof("HTTP_RAW_POST_DATA")); | 220 | retval+= zend_hash_exists(svars, "HTTP_RAW_POST_DATA", sizeof("HTTP_RAW_POST_DATA")); |
| 222 | if (retval > 0) failure = 1; | 221 | if (retval > 0) failure = 1; |
| 223 | } | 222 | } |
| 224 | 223 | ||
| 225 | if (failure) { | 224 | if (failure) { |
| 226 | suhosin_log(S_VARS, "Attacker tried to overwrite a superglobal through a HTTP header"); | 225 | suhosin_log(S_VARS, "Attacker tried to overwrite a superglobal through a HTTP header"); |
| 227 | } | 226 | } |
| 228 | 227 | ||
| 229 | if (SUHOSIN_G(raw_cookie)) { | 228 | if (SUHOSIN_G(raw_cookie)) { |
| 230 | zval *z; | 229 | zval *z; |
| 231 | MAKE_STD_ZVAL(z); | 230 | MAKE_STD_ZVAL(z); |
| 232 | ZVAL_STRING(z, SUHOSIN_G(raw_cookie), 1); | 231 | ZVAL_STRING(z, SUHOSIN_G(raw_cookie), 1); |
| 233 | zend_hash_add(svars, "RAW_HTTP_COOKIE", sizeof("RAW_HTTP_COOKIE"), (void **)&z, sizeof(zval *), NULL); | 232 | zend_hash_add(svars, "RAW_HTTP_COOKIE", sizeof("RAW_HTTP_COOKIE"), (void **)&z, sizeof(zval *), NULL); |
| 234 | } | 233 | } |
| 235 | if (SUHOSIN_G(decrypted_cookie)) { | 234 | if (SUHOSIN_G(decrypted_cookie)) { |
| 236 | zval *z; | 235 | zval *z; |
| 237 | MAKE_STD_ZVAL(z); | 236 | MAKE_STD_ZVAL(z); |
| 238 | ZVAL_STRING(z, SUHOSIN_G(decrypted_cookie), 0); | 237 | ZVAL_STRING(z, SUHOSIN_G(decrypted_cookie), 0); |
| 239 | zend_hash_update(svars, "HTTP_COOKIE", sizeof("HTTP_COOKIE"), (void **)&z, sizeof(zval *), NULL); | 238 | zend_hash_update(svars, "HTTP_COOKIE", sizeof("HTTP_COOKIE"), (void **)&z, sizeof(zval *), NULL); |
| @@ -629,47 +628,11 @@ unsigned int suhosin_input_filter(int arg, char *var, char **val, unsigned int v | |||
| 629 | 628 | ||
| 630 | /* Drop this variable if it is one of GLOBALS, _GET, _POST, ... */ | 629 | /* Drop this variable if it is one of GLOBALS, _GET, _POST, ... */ |
| 631 | /* This is to protect several silly scripts that do globalizing themself */ | 630 | /* This is to protect several silly scripts that do globalizing themself */ |
| 632 | 631 | if (suhosin_is_protected_varname(var, var_len)) { | |
| 633 | switch (var_len) { | 632 | suhosin_log(S_VARS, "tried to register forbidden variable '%s' through %s variables", var, arg == PARSE_GET ? "GET" : arg == PARSE_POST ? "POST" : "COOKIE"); |
| 634 | case 18: | 633 | if (!SUHOSIN_G(simulation)) { |
| 635 | if (memcmp(var, "HTTP_RAW_POST_DATA", 18)==0) goto protected_varname; | 634 | return 0; |
| 636 | break; | 635 | } |
| 637 | case 17: | ||
| 638 | if (memcmp(var, "HTTP_SESSION_VARS", 17)==0) goto protected_varname; | ||
| 639 | break; | ||
| 640 | case 16: | ||
| 641 | if (memcmp(var, "HTTP_SERVER_VARS", 16)==0) goto protected_varname; | ||
| 642 | if (memcmp(var, "HTTP_COOKIE_VARS", 16)==0) goto protected_varname; | ||
| 643 | break; | ||
| 644 | case 15: | ||
| 645 | if (memcmp(var, "HTTP_POST_FILES", 15)==0) goto protected_varname; | ||
| 646 | break; | ||
| 647 | case 14: | ||
| 648 | if (memcmp(var, "HTTP_POST_VARS", 14)==0) goto protected_varname; | ||
| 649 | break; | ||
| 650 | case 13: | ||
| 651 | if (memcmp(var, "HTTP_GET_VARS", 13)==0) goto protected_varname; | ||
| 652 | if (memcmp(var, "HTTP_ENV_VARS", 13)==0) goto protected_varname; | ||
| 653 | break; | ||
| 654 | case 8: | ||
| 655 | if (memcmp(var, "_SESSION", 8)==0) goto protected_varname; | ||
| 656 | if (memcmp(var, "_REQUEST", 8)==0) goto protected_varname; | ||
| 657 | break; | ||
| 658 | case 7: | ||
| 659 | if (memcmp(var, "GLOBALS", 7)==0) goto protected_varname; | ||
| 660 | if (memcmp(var, "_COOKIE", 7)==0) goto protected_varname; | ||
| 661 | if (memcmp(var, "_SERVER", 7)==0) goto protected_varname; | ||
| 662 | break; | ||
| 663 | case 6: | ||
| 664 | if (memcmp(var, "_FILES", 6)==0) goto protected_varname; | ||
| 665 | break; | ||
| 666 | case 5: | ||
| 667 | if (memcmp(var, "_POST", 5)==0) goto protected_varname; | ||
| 668 | break; | ||
| 669 | case 4: | ||
| 670 | if (memcmp(var, "_ENV", 4)==0) goto protected_varname; | ||
| 671 | if (memcmp(var, "_GET", 4)==0) goto protected_varname; | ||
| 672 | break; | ||
| 673 | } | 636 | } |
| 674 | 637 | ||
| 675 | /* Okay let PHP register this variable */ | 638 | /* Okay let PHP register this variable */ |
| @@ -691,13 +654,6 @@ unsigned int suhosin_input_filter(int arg, char *var, char **val, unsigned int v | |||
| 691 | } | 654 | } |
| 692 | 655 | ||
| 693 | return 1; | 656 | return 1; |
| 694 | protected_varname: | ||
| 695 | suhosin_log(S_VARS, "tried to register forbidden variable '%s' through %s variables", var, arg == PARSE_GET ? "GET" : arg == PARSE_POST ? "POST" : "COOKIE"); | ||
| 696 | if (!SUHOSIN_G(simulation)) { | ||
| 697 | return 0; | ||
| 698 | } else { | ||
| 699 | return 1; | ||
| 700 | } | ||
| 701 | } | 657 | } |
| 702 | /* }}} */ | 658 | /* }}} */ |
| 703 | 659 | ||
| @@ -122,7 +122,7 @@ PHP_SUHOSIN_API void suhosin_log(int loglevel, char *fmt, ...) | |||
| 122 | /* remove the S_GETCALLER flag */ | 122 | /* remove the S_GETCALLER flag */ |
| 123 | loglevel = loglevel & ~S_GETCALLER; | 123 | loglevel = loglevel & ~S_GETCALLER; |
| 124 | 124 | ||
| 125 | SDEBUG("(suhosin_log) loglevel: %d log_syslog: %u - log_sapi: %u - log_script: %u", loglevel, SUHOSIN_G(log_syslog), SUHOSIN_G(log_sapi), SUHOSIN_G(log_script)); | 125 | SDEBUG("(suhosin_log) loglevel: %d log_syslog: %ld - log_sapi: %ld - log_script: %ld", loglevel, SUHOSIN_G(log_syslog), SUHOSIN_G(log_sapi), SUHOSIN_G(log_script)); |
| 126 | 126 | ||
| 127 | /* dump core if wanted */ | 127 | /* dump core if wanted */ |
| 128 | if (SUHOSIN_G(coredump) && loglevel == S_MEMORY) { | 128 | if (SUHOSIN_G(coredump) && loglevel == S_MEMORY) { |
| @@ -281,7 +281,7 @@ log_file: | |||
| 281 | 281 | ||
| 282 | log_sapi: | 282 | log_sapi: |
| 283 | /* SAPI Logging activated? */ | 283 | /* SAPI Logging activated? */ |
| 284 | SDEBUG("(suhosin_log) log_syslog: %u - log_sapi: %u - log_script: %u - log_phpscript: %u", SUHOSIN_G(log_syslog), SUHOSIN_G(log_sapi), SUHOSIN_G(log_script), SUHOSIN_G(log_phpscript)); | 284 | SDEBUG("(suhosin_log) log_syslog: %ld - log_sapi: %ld - log_script: %ld - log_phpscript: %ld", SUHOSIN_G(log_syslog), SUHOSIN_G(log_sapi), SUHOSIN_G(log_script), SUHOSIN_G(log_phpscript)); |
| 285 | if (((SUHOSIN_G(log_sapi)|S_INTERNAL) & loglevel)!=0) { | 285 | if (((SUHOSIN_G(log_sapi)|S_INTERNAL) & loglevel)!=0) { |
| 286 | #if PHP_VERSION_ID < 50400 | 286 | #if PHP_VERSION_ID < 50400 |
| 287 | sapi_module.log_message(buf); | 287 | sapi_module.log_message(buf); |
diff --git a/php_suhosin.h b/php_suhosin.h index 4b460e4..b80d9b9 100644 --- a/php_suhosin.h +++ b/php_suhosin.h | |||
| @@ -22,7 +22,7 @@ | |||
| 22 | #ifndef PHP_SUHOSIN_H | 22 | #ifndef PHP_SUHOSIN_H |
| 23 | #define PHP_SUHOSIN_H | 23 | #define PHP_SUHOSIN_H |
| 24 | 24 | ||
| 25 | #define SUHOSIN_EXT_VERSION "0.9.36" | 25 | #define SUHOSIN_EXT_VERSION "0.9.37-dev" |
| 26 | 26 | ||
| 27 | /*#define SUHOSIN_DEBUG*/ | 27 | /*#define SUHOSIN_DEBUG*/ |
| 28 | #define SUHOSIN_LOG "/tmp/suhosin_log.txt" | 28 | #define SUHOSIN_LOG "/tmp/suhosin_log.txt" |
| @@ -39,6 +39,10 @@ | |||
| 39 | #endif | 39 | #endif |
| 40 | #endif | 40 | #endif |
| 41 | 41 | ||
| 42 | #ifndef PHP_VERSION_ID | ||
| 43 | #define PHP_VERSION_ID (PHP_MAJOR_VERSION * 10000 + PHP_MINOR_VERSION * 100 + PHP_RELEASE_VERSION) | ||
| 44 | #endif | ||
| 45 | |||
| 42 | extern zend_module_entry suhosin_module_entry; | 46 | extern zend_module_entry suhosin_module_entry; |
| 43 | #define phpext_suhosin_ptr &suhosin_module_entry | 47 | #define phpext_suhosin_ptr &suhosin_module_entry |
| 44 | 48 | ||
| @@ -66,6 +70,101 @@ PHP_MINFO_FUNCTION(suhosin); | |||
| 66 | 70 | ||
| 67 | #include "ext/standard/basic_functions.h" | 71 | #include "ext/standard/basic_functions.h" |
| 68 | 72 | ||
| 73 | static inline int suhosin_is_protected_varname(char *var, int var_len) | ||
| 74 | { | ||
| 75 | switch (var_len) { | ||
| 76 | case 18: | ||
| 77 | if (memcmp(var, "HTTP_RAW_POST_DATA", 18)==0) goto protected_varname; | ||
| 78 | break; | ||
| 79 | case 17: | ||
| 80 | if (memcmp(var, "HTTP_SESSION_VARS", 17)==0) goto protected_varname; | ||
| 81 | break; | ||
| 82 | case 16: | ||
| 83 | if (memcmp(var, "HTTP_SERVER_VARS", 16)==0) goto protected_varname; | ||
| 84 | if (memcmp(var, "HTTP_COOKIE_VARS", 16)==0) goto protected_varname; | ||
| 85 | break; | ||
| 86 | case 15: | ||
| 87 | if (memcmp(var, "HTTP_POST_FILES", 15)==0) goto protected_varname; | ||
| 88 | break; | ||
| 89 | case 14: | ||
| 90 | if (memcmp(var, "HTTP_POST_VARS", 14)==0) goto protected_varname; | ||
| 91 | break; | ||
| 92 | case 13: | ||
| 93 | if (memcmp(var, "HTTP_GET_VARS", 13)==0) goto protected_varname; | ||
| 94 | if (memcmp(var, "HTTP_ENV_VARS", 13)==0) goto protected_varname; | ||
| 95 | break; | ||
| 96 | case 8: | ||
| 97 | if (memcmp(var, "_SESSION", 8)==0) goto protected_varname; | ||
| 98 | if (memcmp(var, "_REQUEST", 8)==0) goto protected_varname; | ||
| 99 | break; | ||
| 100 | case 7: | ||
| 101 | if (memcmp(var, "GLOBALS", 7)==0) goto protected_varname; | ||
| 102 | if (memcmp(var, "_COOKIE", 7)==0) goto protected_varname; | ||
| 103 | if (memcmp(var, "_SERVER", 7)==0) goto protected_varname; | ||
| 104 | break; | ||
| 105 | case 6: | ||
| 106 | if (memcmp(var, "_FILES", 6)==0) goto protected_varname; | ||
| 107 | break; | ||
| 108 | case 5: | ||
| 109 | if (memcmp(var, "_POST", 5)==0) goto protected_varname; | ||
| 110 | break; | ||
| 111 | case 4: | ||
| 112 | if (memcmp(var, "_ENV", 4)==0) goto protected_varname; | ||
| 113 | if (memcmp(var, "_GET", 4)==0) goto protected_varname; | ||
| 114 | break; | ||
| 115 | } | ||
| 116 | |||
| 117 | return 0; | ||
| 118 | protected_varname: | ||
| 119 | return 1; | ||
| 120 | } | ||
| 121 | |||
| 122 | |||
| 123 | #if PHP_VERSION_ID < 50203 | ||
| 124 | static inline int php_varname_check(char *name, int name_len, zend_bool silent TSRMLS_DC) /* {{{ */ | ||
| 125 | { | ||
| 126 | if (name_len == sizeof("GLOBALS") - 1 && !memcmp(name, "GLOBALS", sizeof("GLOBALS") - 1)) { | ||
| 127 | if (!silent) { | ||
| 128 | php_error_docref(NULL TSRMLS_CC, E_WARNING, "Attempted GLOBALS variable overwrite"); | ||
| 129 | } | ||
| 130 | return FAILURE; | ||
| 131 | } else if (name[0] == '_' && | ||
| 132 | ( | ||
| 133 | (name_len == sizeof("_GET") - 1 && !memcmp(name, "_GET", sizeof("_GET") - 1)) || | ||
| 134 | (name_len == sizeof("_POST") - 1 && !memcmp(name, "_POST", sizeof("_POST") - 1)) || | ||
| 135 | (name_len == sizeof("_COOKIE") - 1 && !memcmp(name, "_COOKIE", sizeof("_COOKIE") - 1)) || | ||
| 136 | (name_len == sizeof("_ENV") - 1 && !memcmp(name, "_ENV", sizeof("_ENV") - 1)) || | ||
| 137 | (name_len == sizeof("_SERVER") - 1 && !memcmp(name, "_SERVER", sizeof("_SERVER") - 1)) || | ||
| 138 | (name_len == sizeof("_SESSION") - 1 && !memcmp(name, "_SESSION", sizeof("_SESSION") - 1)) || | ||
| 139 | (name_len == sizeof("_FILES") - 1 && !memcmp(name, "_FILES", sizeof("_FILES") - 1)) || | ||
| 140 | (name_len == sizeof("_REQUEST") -1 && !memcmp(name, "_REQUEST", sizeof("_REQUEST") - 1)) | ||
| 141 | ) | ||
| 142 | ) { | ||
| 143 | if (!silent) { | ||
| 144 | php_error_docref(NULL TSRMLS_CC, E_WARNING, "Attempted super-global (%s) variable overwrite", name); | ||
| 145 | } | ||
| 146 | return FAILURE; | ||
| 147 | } else if (name[0] == 'H' && | ||
| 148 | ( | ||
| 149 | (name_len == sizeof("HTTP_POST_VARS") - 1 && !memcmp(name, "HTTP_POST_VARS", sizeof("HTTP_POST_VARS") - 1)) || | ||
| 150 | (name_len == sizeof("HTTP_GET_VARS") - 1 && !memcmp(name, "HTTP_GET_VARS", sizeof("HTTP_GET_VARS") - 1)) || | ||
| 151 | (name_len == sizeof("HTTP_COOKIE_VARS") - 1 && !memcmp(name, "HTTP_COOKIE_VARS", sizeof("HTTP_COOKIE_VARS") - 1)) || | ||
| 152 | (name_len == sizeof("HTTP_ENV_VARS") - 1 && !memcmp(name, "HTTP_ENV_VARS", sizeof("HTTP_ENV_VARS") - 1)) || | ||
| 153 | (name_len == sizeof("HTTP_SERVER_VARS") - 1 && !memcmp(name, "HTTP_SERVER_VARS", sizeof("HTTP_SERVER_VARS") - 1)) || | ||
| 154 | (name_len == sizeof("HTTP_SESSION_VARS") - 1 && !memcmp(name, "HTTP_SESSION_VARS", sizeof("HTTP_SESSION_VARS") - 1)) || | ||
| 155 | (name_len == sizeof("HTTP_RAW_POST_DATA") - 1 && !memcmp(name, "HTTP_RAW_POST_DATA", sizeof("HTTP_RAW_POST_DATA") - 1)) || | ||
| 156 | (name_len == sizeof("HTTP_POST_FILES") - 1 && !memcmp(name, "HTTP_POST_FILES", sizeof("HTTP_POST_FILES") - 1)) | ||
| 157 | ) | ||
| 158 | ) { | ||
| 159 | if (!silent) { | ||
| 160 | php_error_docref(NULL TSRMLS_CC, E_WARNING, "Attempted long input array (%s) overwrite", name); | ||
| 161 | } | ||
| 162 | return FAILURE; | ||
| 163 | } | ||
| 164 | return SUCCESS; | ||
| 165 | } | ||
| 166 | #endif | ||
| 167 | |||
| 69 | ZEND_BEGIN_MODULE_GLOBALS(suhosin) | 168 | ZEND_BEGIN_MODULE_GLOBALS(suhosin) |
| 70 | zend_uint in_code_type; | 169 | zend_uint in_code_type; |
| 71 | long execution_depth; | 170 | long execution_depth; |
| @@ -1020,7 +1020,7 @@ static PHP_INI_MH(suhosin_OnUpdateSaveHandler) | |||
| 1020 | int r; | 1020 | int r; |
| 1021 | char *tmp; | 1021 | char *tmp; |
| 1022 | 1022 | ||
| 1023 | if ((ps_mod_user) && (SUHOSIN_G(s_original_mod) == ps_mod_user) && (strcmp(new_value, "user") == NULL)) { | 1023 | if ((ps_mod_user) && (SUHOSIN_G(s_original_mod) == ps_mod_user) && (strcmp(new_value, "user") == 0)) { |
| 1024 | return SUCCESS; | 1024 | return SUCCESS; |
| 1025 | } | 1025 | } |
| 1026 | 1026 | ||
| @@ -28,6 +28,7 @@ | |||
| 28 | #include "zend_extensions.h" | 28 | #include "zend_extensions.h" |
| 29 | #include "ext/standard/info.h" | 29 | #include "ext/standard/info.h" |
| 30 | #include "php_syslog.h" | 30 | #include "php_syslog.h" |
| 31 | #include "php_variables.h" | ||
| 31 | #include "php_suhosin.h" | 32 | #include "php_suhosin.h" |
| 32 | #include "zend_llist.h" | 33 | #include "zend_llist.h" |
| 33 | #include "zend_operators.h" | 34 | #include "zend_operators.h" |
| @@ -618,175 +619,6 @@ static ZEND_INI_MH(OnUpdate_fail) | |||
| 618 | return FAILURE; | 619 | return FAILURE; |
| 619 | } | 620 | } |
| 620 | 621 | ||
| 621 | /* {{{ proto void suhosin_register_cookie_variable(char *var, zval *val, zval *track_vars_array TSRMLS_DC) | ||
| 622 | Registers a cookie in the RAW cookie array */ | ||
| 623 | static void suhosin_register_cookie_variable(char *var, zval *val, zval *track_vars_array TSRMLS_DC) | ||
| 624 | { | ||
| 625 | char *p = NULL; | ||
| 626 | char *ip; /* index pointer */ | ||
| 627 | char *index, *escaped_index = NULL; | ||
| 628 | int var_len, index_len; | ||
| 629 | zval *gpc_element, **gpc_element_p; | ||
| 630 | zend_bool is_array = 0; | ||
| 631 | HashTable *symtable1 = NULL; | ||
| 632 | |||
| 633 | assert(var != NULL); | ||
| 634 | |||
| 635 | symtable1 = Z_ARRVAL_P(track_vars_array); | ||
| 636 | |||
| 637 | /* | ||
| 638 | * Prepare variable name | ||
| 639 | */ | ||
| 640 | |||
| 641 | /* ignore leading spaces in the variable name */ | ||
| 642 | while (*var && *var==' ') { | ||
| 643 | var++; | ||
| 644 | } | ||
| 645 | |||
| 646 | /* ensure that we don't have spaces or dots in the variable name (not binary safe) */ | ||
| 647 | for (p = var; *p; p++) { | ||
| 648 | if (*p == ' ' || *p == '.') { | ||
| 649 | *p='_'; | ||
| 650 | } else if (*p == '[') { | ||
| 651 | is_array = 1; | ||
| 652 | ip = p; | ||
| 653 | *p = 0; | ||
| 654 | break; | ||
| 655 | } | ||
| 656 | } | ||
| 657 | var_len = p - var; | ||
| 658 | |||
| 659 | if (var_len==0) { /* empty variable name, or variable name with a space in it */ | ||
| 660 | zval_dtor(val); | ||
| 661 | return; | ||
| 662 | } | ||
| 663 | |||
| 664 | index = var; | ||
| 665 | index_len = var_len; | ||
| 666 | |||
| 667 | if (is_array) { | ||
| 668 | while (1) { | ||
| 669 | char *index_s; | ||
| 670 | int new_idx_len = 0; | ||
| 671 | |||
| 672 | ip++; | ||
| 673 | index_s = ip; | ||
| 674 | if (isspace(*ip)) { | ||
| 675 | ip++; | ||
| 676 | } | ||
| 677 | if (*ip==']') { | ||
| 678 | index_s = NULL; | ||
| 679 | } else { | ||
| 680 | ip = strchr(ip, ']'); | ||
| 681 | if (!ip) { | ||
| 682 | /* PHP variables cannot contain '[' in their names, so we replace the character with a '_' */ | ||
| 683 | *(index_s - 1) = '_'; | ||
| 684 | |||
| 685 | index_len = var_len = 0; | ||
| 686 | if (index) { | ||
| 687 | index_len = var_len = strlen(index); | ||
| 688 | } | ||
| 689 | goto plain_var; | ||
| 690 | return; | ||
| 691 | } | ||
| 692 | *ip = 0; | ||
| 693 | new_idx_len = strlen(index_s); | ||
| 694 | } | ||
| 695 | |||
| 696 | if (!index) { | ||
| 697 | MAKE_STD_ZVAL(gpc_element); | ||
| 698 | array_init(gpc_element); | ||
| 699 | zend_hash_next_index_insert(symtable1, &gpc_element, sizeof(zval *), (void **) &gpc_element_p); | ||
| 700 | } else { | ||
| 701 | #if PHP_VERSION_ID < 50400 | ||
| 702 | if (PG(magic_quotes_gpc) && (index != var)) { | ||
| 703 | /* no need to addslashes() the index if it's the main variable name */ | ||
| 704 | escaped_index = php_addslashes(index, index_len, &index_len, 0 TSRMLS_CC); | ||
| 705 | } else { | ||
| 706 | #endif | ||
| 707 | escaped_index = index; | ||
| 708 | #if PHP_VERSION_ID < 50400 | ||
| 709 | } | ||
| 710 | #endif | ||
| 711 | if (zend_symtable_find(symtable1, escaped_index, index_len + 1, (void **) &gpc_element_p) == FAILURE | ||
| 712 | || Z_TYPE_PP(gpc_element_p) != IS_ARRAY) { | ||
| 713 | MAKE_STD_ZVAL(gpc_element); | ||
| 714 | array_init(gpc_element); | ||
| 715 | zend_symtable_update(symtable1, escaped_index, index_len + 1, &gpc_element, sizeof(zval *), (void **) &gpc_element_p); | ||
| 716 | } | ||
| 717 | if (index != escaped_index) { | ||
| 718 | efree(escaped_index); | ||
| 719 | } | ||
| 720 | } | ||
| 721 | symtable1 = Z_ARRVAL_PP(gpc_element_p); | ||
| 722 | /* ip pointed to the '[' character, now obtain the key */ | ||
| 723 | index = index_s; | ||
| 724 | index_len = new_idx_len; | ||
| 725 | |||
| 726 | ip++; | ||
| 727 | if (*ip == '[') { | ||
| 728 | is_array = 1; | ||
| 729 | *ip = 0; | ||
| 730 | } else { | ||
| 731 | goto plain_var; | ||
| 732 | } | ||
| 733 | } | ||
| 734 | } else { | ||
| 735 | plain_var: | ||
| 736 | MAKE_STD_ZVAL(gpc_element); | ||
| 737 | gpc_element->value = val->value; | ||
| 738 | Z_TYPE_P(gpc_element) = Z_TYPE_P(val); | ||
| 739 | if (!index) { | ||
| 740 | zend_hash_next_index_insert(symtable1, &gpc_element, sizeof(zval *), (void **) &gpc_element_p); | ||
| 741 | } else { | ||
| 742 | #if PHP_VERSION_ID < 50400 | ||
| 743 | if (PG(magic_quotes_gpc)) { | ||
| 744 | escaped_index = php_addslashes(index, index_len, &index_len, 0 TSRMLS_CC); | ||
| 745 | } else { | ||
| 746 | #endif | ||
| 747 | escaped_index = index; | ||
| 748 | #if PHP_VERSION_ID < 50400 | ||
| 749 | } | ||
| 750 | #endif | ||
| 751 | /* | ||
| 752 | * According to rfc2965, more specific paths are listed above the less specific ones. | ||
| 753 | * If we encounter a duplicate cookie name, we should skip it, since it is not possible | ||
| 754 | * to have the same (plain text) cookie name for the same path and we should not overwrite | ||
| 755 | * more specific cookies with the less specific ones. | ||
| 756 | */ | ||
| 757 | if (zend_symtable_exists(symtable1, escaped_index, index_len + 1)) { | ||
| 758 | zval_ptr_dtor(&gpc_element); | ||
| 759 | } else { | ||
| 760 | zend_symtable_update(symtable1, escaped_index, index_len + 1, &gpc_element, sizeof(zval *), (void **) &gpc_element_p); | ||
| 761 | } | ||
| 762 | if (escaped_index != index) { | ||
| 763 | efree(escaped_index); | ||
| 764 | } | ||
| 765 | } | ||
| 766 | } | ||
| 767 | } | ||
| 768 | /* }}} */ | ||
| 769 | |||
| 770 | static void suhosin_register_cookie_variable_safe(char *var, char *strval, int str_len, zval *track_vars_array TSRMLS_DC) | ||
| 771 | { | ||
| 772 | zval new_entry; | ||
| 773 | assert(strval != NULL); | ||
| 774 | |||
| 775 | /* Prepare value */ | ||
| 776 | Z_STRLEN(new_entry) = str_len; | ||
| 777 | #if PHP_VERSION_ID < 50400 | ||
| 778 | if (PG(magic_quotes_gpc)) { | ||
| 779 | Z_STRVAL(new_entry) = php_addslashes(strval, Z_STRLEN(new_entry), &Z_STRLEN(new_entry), 0 TSRMLS_CC); | ||
| 780 | } else { | ||
| 781 | #endif | ||
| 782 | Z_STRVAL(new_entry) = estrndup(strval, Z_STRLEN(new_entry)); | ||
| 783 | #if PHP_VERSION_ID < 50400 | ||
| 784 | } | ||
| 785 | #endif | ||
| 786 | Z_TYPE(new_entry) = IS_STRING; | ||
| 787 | |||
| 788 | suhosin_register_cookie_variable(var, &new_entry, track_vars_array TSRMLS_CC); | ||
| 789 | } | ||
| 790 | 622 | ||
| 791 | 623 | ||
| 792 | /* {{{ proto string suhosin_encrypt_cookie(string name, string value) | 624 | /* {{{ proto string suhosin_encrypt_cookie(string name, string value) |
| @@ -828,37 +660,43 @@ return_plain: | |||
| 828 | static PHP_FUNCTION(suhosin_get_raw_cookies) | 660 | static PHP_FUNCTION(suhosin_get_raw_cookies) |
| 829 | { | 661 | { |
| 830 | char *var, *val, *res; | 662 | char *var, *val, *res; |
| 831 | zval *array_ptr = return_value; | 663 | zval *array_ptr = return_value; |
| 832 | char *strtok_buf = NULL; | 664 | char *strtok_buf = NULL; |
| 833 | int val_len; | 665 | int val_len; |
| 834 | 666 | ||
| 835 | array_init(array_ptr); | 667 | array_init(array_ptr); |
| 836 | |||
| 837 | if (SUHOSIN_G(raw_cookie)) { | ||
| 838 | res = estrdup(SUHOSIN_G(raw_cookie)); | ||
| 839 | } else { | ||
| 840 | return; | ||
| 841 | } | ||
| 842 | |||
| 843 | var = php_strtok_r(res, ";", &strtok_buf); | ||
| 844 | 668 | ||
| 845 | while (var) { | 669 | if (SUHOSIN_G(raw_cookie)) { |
| 670 | res = estrdup(SUHOSIN_G(raw_cookie)); | ||
| 671 | } else { | ||
| 672 | return; | ||
| 673 | } | ||
| 674 | |||
| 675 | var = NULL; | ||
| 676 | while (var != res) { | ||
| 677 | var = strrchr(res, ';'); | ||
| 678 | if (var) { | ||
| 679 | *var++ = '\0'; | ||
| 680 | } else { | ||
| 681 | var = res; | ||
| 682 | } | ||
| 683 | if (!*var) { continue; } | ||
| 684 | |||
| 846 | val = strchr(var, '='); | 685 | val = strchr(var, '='); |
| 847 | if (val) { /* have a value */ | 686 | if (val) { /* have a value */ |
| 848 | *val++ = '\0'; | 687 | *val++ = '\0'; |
| 849 | php_url_decode(var, strlen(var)); | 688 | php_url_decode(var, strlen(var)); |
| 850 | val_len = php_url_decode(val, strlen(val)); | 689 | val_len = php_url_decode(val, strlen(val)); |
| 851 | suhosin_register_cookie_variable_safe(var, val, val_len, array_ptr TSRMLS_CC); | ||
| 852 | } else { | 690 | } else { |
| 853 | php_url_decode(var, strlen(var)); | 691 | php_url_decode(var, strlen(var)); |
| 854 | val_len = 0; | 692 | val_len = 0; |
| 855 | val = ""; | 693 | val = ""; |
| 856 | suhosin_register_cookie_variable_safe(var, "", 0, array_ptr TSRMLS_CC); | ||
| 857 | } | 694 | } |
| 858 | var = php_strtok_r(NULL, ";", &strtok_buf); | 695 | php_register_variable_safe(var, val, val_len, array_ptr TSRMLS_CC); |
| 696 | |||
| 859 | } | 697 | } |
| 860 | 698 | ||
| 861 | efree(res); | 699 | efree(res); |
| 862 | } | 700 | } |
| 863 | /* }}} */ | 701 | /* }}} */ |
| 864 | 702 | ||
| @@ -1049,7 +887,7 @@ char *suhosin_getenv(char *name, size_t name_len TSRMLS_DC) | |||
| 1049 | tmp = getenv(name); | 887 | tmp = getenv(name); |
| 1050 | efree(name); | 888 | efree(name); |
| 1051 | if (tmp) { | 889 | if (tmp) { |
| 1052 | return(estrdup(tmp)); | 890 | return estrdup(tmp); |
| 1053 | } | 891 | } |
| 1054 | } | 892 | } |
| 1055 | return NULL; | 893 | return NULL; |
| @@ -1144,11 +982,12 @@ PHP_MINIT_FUNCTION(suhosin) | |||
| 1144 | zend_ini_entry *i; | 982 | zend_ini_entry *i; |
| 1145 | if (zend_hash_find(EG(ini_directives), "display_errors", sizeof("display_errors"), (void **) &i) == SUCCESS) { | 983 | if (zend_hash_find(EG(ini_directives), "display_errors", sizeof("display_errors"), (void **) &i) == SUCCESS) { |
| 1146 | if (i->on_modify) { | 984 | if (i->on_modify) { |
| 985 | i->on_modify(i, "0", strlen("0"), i->mh_arg1, i->mh_arg2, i->mh_arg3, ZEND_INI_STAGE_STARTUP TSRMLS_CC); | ||
| 1147 | if (SUHOSIN_G(disable_display_errors) > 1) { | 986 | if (SUHOSIN_G(disable_display_errors) > 1) { |
| 1148 | zend_alter_ini_entry_ex("display_errors", sizeof("display_errors"), "0", sizeof("0"), ZEND_INI_SYSTEM, ZEND_INI_STAGE_STARTUP, 0 TSRMLS_CC); | 987 | i->value = estrdup("0"); |
| 988 | i->value_length = strlen(i->value); | ||
| 1149 | i->on_modify = OnUpdate_fail; | 989 | i->on_modify = OnUpdate_fail; |
| 1150 | } else { | 990 | } else { |
| 1151 | i->on_modify(i, "Off", sizeof("off"), i->mh_arg1, i->mh_arg2, i->mh_arg3, ZEND_INI_STAGE_STARTUP TSRMLS_CC); | ||
| 1152 | i->on_modify = NULL; | 991 | i->on_modify = NULL; |
| 1153 | } | 992 | } |
| 1154 | } | 993 | } |
| @@ -30,60 +30,13 @@ | |||
| 30 | #include "php_suhosin.h" | 30 | #include "php_suhosin.h" |
| 31 | #include "php_variables.h" | 31 | #include "php_variables.h" |
| 32 | #include "suhosin_rfc1867.h" | 32 | #include "suhosin_rfc1867.h" |
| 33 | #include "ext/standard/php_var.h" | ||
| 33 | 34 | ||
| 34 | PHP_SUHOSIN_API int (*old_rfc1867_callback)(unsigned int event, void *event_data, void **extra TSRMLS_DC) = NULL; | 35 | PHP_SUHOSIN_API int (*old_rfc1867_callback)(unsigned int event, void *event_data, void **extra TSRMLS_DC) = NULL; |
| 35 | #if !HAVE_RFC1867_CALLBACK | 36 | #if !HAVE_RFC1867_CALLBACK |
| 36 | PHP_SUHOSIN_API int (*php_rfc1867_callback)(unsigned int event, void *event_data, void **extra TSRMLS_DC) = NULL; | 37 | PHP_SUHOSIN_API int (*php_rfc1867_callback)(unsigned int event, void *event_data, void **extra TSRMLS_DC) = NULL; |
| 37 | #endif | 38 | #endif |
| 38 | 39 | ||
| 39 | static int is_protected_varname(char *var, int var_len) | ||
| 40 | { | ||
| 41 | switch (var_len) { | ||
| 42 | case 18: | ||
| 43 | if (memcmp(var, "HTTP_RAW_POST_DATA", 18)==0) goto protected_varname2; | ||
| 44 | break; | ||
| 45 | case 17: | ||
| 46 | if (memcmp(var, "HTTP_SESSION_VARS", 17)==0) goto protected_varname2; | ||
| 47 | break; | ||
| 48 | case 16: | ||
| 49 | if (memcmp(var, "HTTP_SERVER_VARS", 16)==0) goto protected_varname2; | ||
| 50 | if (memcmp(var, "HTTP_COOKIE_VARS", 16)==0) goto protected_varname2; | ||
| 51 | break; | ||
| 52 | case 15: | ||
| 53 | if (memcmp(var, "HTTP_POST_FILES", 15)==0) goto protected_varname2; | ||
| 54 | break; | ||
| 55 | case 14: | ||
| 56 | if (memcmp(var, "HTTP_POST_VARS", 14)==0) goto protected_varname2; | ||
| 57 | break; | ||
| 58 | case 13: | ||
| 59 | if (memcmp(var, "HTTP_GET_VARS", 13)==0) goto protected_varname2; | ||
| 60 | if (memcmp(var, "HTTP_ENV_VARS", 13)==0) goto protected_varname2; | ||
| 61 | break; | ||
| 62 | case 8: | ||
| 63 | if (memcmp(var, "_SESSION", 8)==0) goto protected_varname2; | ||
| 64 | if (memcmp(var, "_REQUEST", 8)==0) goto protected_varname2; | ||
| 65 | break; | ||
| 66 | case 7: | ||
| 67 | if (memcmp(var, "GLOBALS", 7)==0) goto protected_varname2; | ||
| 68 | if (memcmp(var, "_COOKIE", 7)==0) goto protected_varname2; | ||
| 69 | if (memcmp(var, "_SERVER", 7)==0) goto protected_varname2; | ||
| 70 | break; | ||
| 71 | case 6: | ||
| 72 | if (memcmp(var, "_FILES", 6)==0) goto protected_varname2; | ||
| 73 | break; | ||
| 74 | case 5: | ||
| 75 | if (memcmp(var, "_POST", 5)==0) goto protected_varname2; | ||
| 76 | break; | ||
| 77 | case 4: | ||
| 78 | if (memcmp(var, "_ENV", 4)==0) goto protected_varname2; | ||
| 79 | if (memcmp(var, "_GET", 4)==0) goto protected_varname2; | ||
| 80 | break; | ||
| 81 | } | ||
| 82 | |||
| 83 | return 0; | ||
| 84 | protected_varname2: | ||
| 85 | return 1; | ||
| 86 | } | ||
| 87 | 40 | ||
| 88 | /* {{{ SAPI_UPLOAD_VARNAME_FILTER_FUNC | 41 | /* {{{ SAPI_UPLOAD_VARNAME_FILTER_FUNC |
| 89 | */ | 42 | */ |
| @@ -180,8 +133,7 @@ static int check_fileupload_varname(char *varname) | |||
| 180 | 133 | ||
| 181 | /* Drop this variable if it is one of GLOBALS, _GET, _POST, ... */ | 134 | /* Drop this variable if it is one of GLOBALS, _GET, _POST, ... */ |
| 182 | /* This is to protect several silly scripts that do globalizing themself */ | 135 | /* This is to protect several silly scripts that do globalizing themself */ |
| 183 | 136 | if (php_varname_check(var, var_len, 1 TSRMLS_CC) == FAILURE || suhosin_is_protected_varname(var, var_len)) { | |
| 184 | if (is_protected_varname(var, var_len)) { | ||
| 185 | suhosin_log(S_FILES, "tried to register forbidden variable '%s' through FILE variables", var); | 137 | suhosin_log(S_FILES, "tried to register forbidden variable '%s' through FILE variables", var); |
| 186 | if (!SUHOSIN_G(simulation)) { | 138 | if (!SUHOSIN_G(simulation)) { |
| 187 | goto return_failure; | 139 | goto return_failure; |
