From fe43991e3dc6c46e2781d21369f5e268de7baef9 Mon Sep 17 00:00:00 2001 From: jvoisin Date: Tue, 10 Oct 2017 18:11:31 +0200 Subject: Implement match on arguments position --- src/sp_config.h | 2 ++ src/sp_config_keywords.c | 7 +++++++ src/sp_disabled_functions.c | 14 ++++++++++---- src/tests/config/disabled_functions_pos.ini | 1 + src/tests/disabled_functions_param_pos.phpt | 12 ++++++++++++ 5 files changed, 32 insertions(+), 4 deletions(-) create mode 100644 src/tests/config/disabled_functions_pos.ini create mode 100644 src/tests/disabled_functions_param_pos.phpt (limited to 'src') diff --git a/src/sp_config.h b/src/sp_config.h index 0877ebb..c005206 100644 --- a/src/sp_config.h +++ b/src/sp_config.h @@ -77,6 +77,7 @@ typedef struct { char *param; pcre *r_param; sp_php_type param_type; + int pos; char *ret; pcre *r_ret; @@ -183,6 +184,7 @@ typedef struct { #define SP_TOKEN_RET_TYPE ".ret_type(" #define SP_TOKEN_VALUE ".value(" #define SP_TOKEN_VALUE_REGEXP ".value_r(" +#define SP_TOKEN_VALUE_ARG_POS ".pos(" // cookies encryption #define SP_TOKEN_NAME ".cookie(" diff --git a/src/sp_config_keywords.c b/src/sp_config_keywords.c index 29f1bfc..1f48852 100644 --- a/src/sp_config_keywords.c +++ b/src/sp_config_keywords.c @@ -144,7 +144,9 @@ int parse_cookie_encryption(char *line) { int parse_disabled_functions(char *line) { int ret = 0; bool enable = true, disable = false; + char *pos = NULL; sp_disabled_function *df = pecalloc(sizeof(*df), 1, 1); + df->pos = -1; sp_config_functions sp_config_funcs_disabled_functions[] = { {parse_empty, SP_TOKEN_ENABLE, &(enable)}, @@ -169,6 +171,7 @@ int parse_disabled_functions(char *line) { {parse_regexp, SP_TOKEN_RET_REGEXP, &(df->r_ret)}, {parse_php_type, SP_TOKEN_RET_TYPE, &(df->ret_type)}, {parse_str, SP_TOKEN_LOCAL_VAR, &(df->var)}, + {parse_str, SP_TOKEN_VALUE_ARG_POS, &(pos)}, {0}}; ret = parse_keywords(sp_config_funcs_disabled_functions, line); @@ -233,6 +236,10 @@ int parse_disabled_functions(char *line) { return -1; } + if (pos) { + df->pos = atoi(pos) > 128 ? 128: atoi(pos); // FIXME do the strtol dance + } + if (df->function) { df->functions_list = parse_functions_list(df->function); } diff --git a/src/sp_disabled_functions.c b/src/sp_disabled_functions.c index c8c723a..b05d949 100644 --- a/src/sp_disabled_functions.c +++ b/src/sp_disabled_functions.c @@ -178,11 +178,17 @@ bool should_disable(zend_execute_data* execute_data) { } /* Check if we filter on parameter value*/ - if (config_node->param || config_node->r_param) { - const unsigned int nb_param = execute_data->func->common.num_args; + if (config_node->param || config_node->r_param || (config_node->pos != -1)) { + unsigned int nb_param = execute_data->func->common.num_args; bool arg_matched = false; + int i = 0; - for (unsigned int i = 0; i < nb_param; i++) { + if (config_node->pos != -1) {//&& nb_param <= config_node->pos) { + i = config_node->pos; + nb_param = (config_node->pos) + 1; + } + + for (; i < nb_param; i++) { arg_matched = false; if (ZEND_USER_CODE(execute_data->func->type)) { // yay consistency arg_name = ZSTR_VAL(execute_data->func->common.arg_info[i].name); @@ -197,7 +203,7 @@ bool should_disable(zend_execute_data* execute_data) { (true == is_regexp_matching(config_node->r_param, arg_name)); /* This is the parameter name we're looking for. */ - if (true == arg_matching || true == pcre_matching) { + if (true == arg_matching || true == pcre_matching || (config_node->pos != -1)) { zval* arg_value = ZEND_CALL_VAR_NUM(execute_data, i); if (config_node->param_type) { // Are we matching on the `type`? diff --git a/src/tests/config/disabled_functions_pos.ini b/src/tests/config/disabled_functions_pos.ini new file mode 100644 index 0000000..81a524e --- /dev/null +++ b/src/tests/config/disabled_functions_pos.ini @@ -0,0 +1 @@ +sp.disable_functions.function("system").pos("0").value("id").drop(); diff --git a/src/tests/disabled_functions_param_pos.phpt b/src/tests/disabled_functions_param_pos.phpt new file mode 100644 index 0000000..de578b2 --- /dev/null +++ b/src/tests/disabled_functions_param_pos.phpt @@ -0,0 +1,12 @@ +--TEST-- +Disable functions - match on argument's position +--SKIPIF-- + +--INI-- +sp.configuration_file={PWD}/config/disabled_functions_pos.ini +--FILE-- + +--EXPECTF-- +[snuffleupagus][0.0.0.0][disabled_function][drop] The call to the function 'system' in %a/disabled_functions_param_pos.php:%d has been disabled, because its argument 'command' content (id) matched a rule. -- cgit v1.3