diff --git a/storage/spider/mysql-test/spider/bugfix/r/mdev_31117.result b/storage/spider/mysql-test/spider/bugfix/r/mdev_31117.result new file mode 100644 index 00000000000..2b09addac0e --- /dev/null +++ b/storage/spider/mysql-test/spider/bugfix/r/mdev_31117.result @@ -0,0 +1,19 @@ +# +# MDEV-31117 Spider UBSAN runtime error: applying non-zero offset x to null pointer in st_spider_param_string_parse::restore_delims +# +for master_1 +for child2 +for child3 +CREATE TABLE t (c INT) ENGINE=Spider COMMENT='abc'; +ERROR HY000: The connect info 'abc' is invalid +ALTER TABLE mysql.help_topic ENGINE=Spider; +ERROR HY000: The connect info 'help topics' is invalid +CREATE SERVER srv FOREIGN DATA WRAPPER MYSQL OPTIONS (SOCKET "$MASTER_1_MYSOCK", DATABASE 'test',user 'root'); +create table t2 (c int); +create table t1 (c int) ENGINE=Spider COMMENT='WRAPPER "mysql", "srv" "srv",TABLE "t2"'; +ERROR HY000: The connect info '"srv" "srv",TABLE "t2"' is invalid +create table t1 (c int) ENGINE=Spider CONNECTION='WRAPPER "mysql", srv \'srv\',TABLE "t2", password "say \\"hello\\ world!\\""'; +drop table t1, t2; +for master_1 +for child2 +for child3 diff --git a/storage/spider/mysql-test/spider/bugfix/t/mdev_31117.test b/storage/spider/mysql-test/spider/bugfix/t/mdev_31117.test new file mode 100644 index 00000000000..e03bc874254 --- /dev/null +++ b/storage/spider/mysql-test/spider/bugfix/t/mdev_31117.test @@ -0,0 +1,30 @@ +--echo # +--echo # MDEV-31117 Spider UBSAN runtime error: applying non-zero offset x to null pointer in st_spider_param_string_parse::restore_delims +--echo # + +--disable_query_log +--disable_result_log +--source ../../t/test_init.inc +--enable_result_log +--enable_query_log + +--error 12501 +CREATE TABLE t (c INT) ENGINE=Spider COMMENT='abc'; + +--error 12501 +ALTER TABLE mysql.help_topic ENGINE=Spider; + +evalp CREATE SERVER srv FOREIGN DATA WRAPPER MYSQL OPTIONS (SOCKET "$MASTER_1_MYSOCK", DATABASE 'test',user 'root'); +create table t2 (c int); +# param title should not have delimiter +--error 12501 +create table t1 (c int) ENGINE=Spider COMMENT='WRAPPER "mysql", "srv" "srv",TABLE "t2"'; +# test escaping +create table t1 (c int) ENGINE=Spider CONNECTION='WRAPPER "mysql", srv \'srv\',TABLE "t2", password "say \\"hello\\ world!\\""'; +drop table t1, t2; + +--disable_query_log +--disable_result_log +--source ../t/test_deinit.inc +--enable_query_log +--enable_result_log diff --git a/storage/spider/spd_copy_tables.cc b/storage/spider/spd_copy_tables.cc index c8c3cef5693..aeeccbc349a 100644 --- a/storage/spider/spd_copy_tables.cc +++ b/storage/spider/spd_copy_tables.cc @@ -76,134 +76,78 @@ int spider_udf_set_copy_tables_param_default( #define SPIDER_PARAM_STR_LEN(name) name ## _length #define SPIDER_PARAM_STR(title_name, param_name) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (!copy_tables->param_name) \ { \ - if ((copy_tables->param_name = spider_get_string_between_quote( \ - start_ptr, TRUE, ¶m_string_parse))) \ + if ((copy_tables->param_name = spider_create_string(parse.start_value, \ + value_length))) \ copy_tables->SPIDER_PARAM_STR_LEN(param_name) = \ strlen(copy_tables->param_name); \ else { \ - error_num = param_string_parse.print_param_error(); \ + error_num= parse.fail(true); \ goto error; \ } \ DBUG_PRINT("info",("spider " title_name "=%s", copy_tables->param_name)); \ } \ break; \ } -#define SPIDER_PARAM_HINT_WITH_MAX(title_name, param_name, check_length, max_size, min_val, max_val) \ - if (!strncasecmp(tmp_ptr, title_name, check_length)) \ - { \ - DBUG_PRINT("info",("spider " title_name " start")); \ - DBUG_PRINT("info",("spider max_size=%d", max_size)); \ - int hint_num = atoi(tmp_ptr + check_length) - 1; \ - DBUG_PRINT("info",("spider hint_num=%d", hint_num)); \ - DBUG_PRINT("info",("spider copy_tables->param_name=%x", \ - copy_tables->param_name)); \ - if (copy_tables->param_name) \ - { \ - if (hint_num < 0 || hint_num >= max_size) \ - { \ - error_num = param_string_parse.print_param_error(); \ - goto error; \ - } else if (copy_tables->param_name[hint_num] != -1) \ - break; \ - char *hint_str = spider_get_string_between_quote(start_ptr, FALSE); \ - if (hint_str) \ - { \ - copy_tables->param_name[hint_num] = atoi(hint_str); \ - if (copy_tables->param_name[hint_num] < min_val) \ - copy_tables->param_name[hint_num] = min_val; \ - else if (copy_tables->param_name[hint_num] > max_val) \ - copy_tables->param_name[hint_num] = max_val; \ - } else { \ - error_num = param_string_parse.print_param_error(); \ - goto error; \ - } \ - DBUG_PRINT("info",("spider " title_name "[%d]=%d", hint_num, \ - copy_tables->param_name[hint_num])); \ - } else { \ - error_num = param_string_parse.print_param_error(); \ - goto error; \ - } \ - break; \ - } #define SPIDER_PARAM_INT_WITH_MAX(title_name, param_name, min_val, max_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (copy_tables->param_name == -1) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - copy_tables->param_name = atoi(tmp_ptr2); \ - if (copy_tables->param_name < min_val) \ - copy_tables->param_name = min_val; \ - else if (copy_tables->param_name > max_val) \ - copy_tables->param_name = max_val; \ - param_string_parse.set_param_value(tmp_ptr2, \ - tmp_ptr2 + \ - strlen(tmp_ptr2) + 1); \ - } else { \ - error_num = param_string_parse.print_param_error(); \ - goto error; \ - } \ + copy_tables->param_name = atoi(parse.start_value); \ + if (copy_tables->param_name < min_val) \ + copy_tables->param_name = min_val; \ + else if (copy_tables->param_name > max_val) \ + copy_tables->param_name = max_val; \ DBUG_PRINT("info",("spider " title_name "=%d", copy_tables->param_name)); \ } \ break; \ } #define SPIDER_PARAM_INT(title_name, param_name, min_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (copy_tables->param_name == -1) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - copy_tables->param_name = atoi(tmp_ptr2); \ - if (copy_tables->param_name < min_val) \ - copy_tables->param_name = min_val; \ - param_string_parse.set_param_value(tmp_ptr2, \ - tmp_ptr2 + \ - strlen(tmp_ptr2) + 1); \ - } else { \ - error_num = param_string_parse.print_param_error(); \ - goto error; \ - } \ + copy_tables->param_name = atoi(parse.start_value); \ + if (copy_tables->param_name < min_val) \ + copy_tables->param_name = min_val; \ DBUG_PRINT("info",("spider " title_name "=%d", copy_tables->param_name)); \ } \ break; \ } #define SPIDER_PARAM_LONGLONG(title_name, param_name, min_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (copy_tables->param_name == -1) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - copy_tables->param_name = \ - my_strtoll10(tmp_ptr2, (char**) NULL, &error_num); \ - if (copy_tables->param_name < min_val) \ - copy_tables->param_name = min_val; \ - param_string_parse.set_param_value(tmp_ptr2, \ - tmp_ptr2 + \ - strlen(tmp_ptr2) + 1); \ - } else { \ - error_num = param_string_parse.print_param_error(); \ - goto error; \ - } \ + copy_tables->param_name = \ + my_strtoll10(parse.start_value, (char**) NULL, &error_num); \ + if (copy_tables->param_name < min_val) \ + copy_tables->param_name = min_val; \ DBUG_PRINT("info",("spider " title_name "=%lld", \ - copy_tables->param_name)); \ + copy_tables->param_name)); \ } \ break; \ } +static void spider_minus_1(SPIDER_COPY_TABLES *copy_tables) +{ + copy_tables->bulk_insert_interval = -1; + copy_tables->bulk_insert_rows = -1; + copy_tables->use_table_charset = -1; + copy_tables->use_transaction = -1; +#ifndef WITHOUT_SPIDER_BG_SEARCH + copy_tables->bg_mode = -1; +#endif +} + int spider_udf_parse_copy_tables_param( SPIDER_COPY_TABLES *copy_tables, char *param, @@ -211,69 +155,40 @@ int spider_udf_parse_copy_tables_param( ) { int error_num = 0; char *param_string = NULL; - char *sprit_ptr; - char *tmp_ptr, *tmp_ptr2, *start_ptr; - int title_length; - SPIDER_PARAM_STRING_PARSE param_string_parse; + char *start_param; + int title_length, value_length; + SPIDER_PARAM_STRING_PARSE parse; DBUG_ENTER("spider_udf_parse_copy_tables_param"); - copy_tables->bulk_insert_interval = -1; - copy_tables->bulk_insert_rows = -1; - copy_tables->use_table_charset = -1; - copy_tables->use_transaction = -1; -#ifndef WITHOUT_SPIDER_BG_SEARCH - copy_tables->bg_mode = -1; -#endif - + spider_minus_1(copy_tables); if (param_length == 0) goto set_default; DBUG_PRINT("info",("spider create param_string string")); - if ( - !(param_string = spider_create_string( - param, - param_length)) - ) { + if (!(param_string = spider_create_string(param, param_length))) + { error_num = HA_ERR_OUT_OF_MEM; my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM); goto error_alloc_param_string; } DBUG_PRINT("info",("spider param_string=%s", param_string)); - sprit_ptr = param_string; - param_string_parse.init(param_string, ER_SPIDER_INVALID_UDF_PARAM_NUM); - while (sprit_ptr) + start_param = param_string; + parse.error_num = ER_SPIDER_INVALID_UDF_PARAM_NUM; + while (*start_param != '\0') { - tmp_ptr = sprit_ptr; - while (*tmp_ptr == ' ' || *tmp_ptr == '\r' || - *tmp_ptr == '\n' || *tmp_ptr == '\t') - tmp_ptr++; - - if (*tmp_ptr == '\0') - break; - - title_length = 0; - start_ptr = tmp_ptr; - while (*start_ptr != ' ' && *start_ptr != '\'' && - *start_ptr != '"' && *start_ptr != '\0' && - *start_ptr != '\r' && *start_ptr != '\n' && - *start_ptr != '\t') - { - title_length++; - start_ptr++; - } - param_string_parse.set_param_title(tmp_ptr, tmp_ptr + title_length); - if ((error_num = param_string_parse.get_next_parameter_head( - start_ptr, &sprit_ptr))) + if (parse.locate_param_def(start_param)) { + error_num= parse.fail(false); goto error; } + /* Null the end of the parameter value. */ + *parse.end_value= '\0'; + value_length= (int) (parse.end_value - parse.start_value); - switch (title_length) + switch (title_length = (int) (parse.end_title - parse.start_title)) { case 0: - error_num = param_string_parse.print_param_error(); - if (error_num) - goto error; - continue; + error_num= parse.fail(true); + goto error; case 3: #ifndef WITHOUT_SPIDER_BG_SEARCH SPIDER_PARAM_INT_WITH_MAX("bgm", bg_mode, 0, 1); @@ -283,55 +198,45 @@ int spider_udf_parse_copy_tables_param( SPIDER_PARAM_STR("dtb", database); SPIDER_PARAM_INT_WITH_MAX("utc", use_table_charset, 0, 1); SPIDER_PARAM_INT_WITH_MAX("utr", use_transaction, 0, 1); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; #ifndef WITHOUT_SPIDER_BG_SEARCH case 7: SPIDER_PARAM_INT_WITH_MAX("bg_mode", bg_mode, 0, 1); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; #endif case 8: SPIDER_PARAM_STR("database", database); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 15: SPIDER_PARAM_INT_WITH_MAX("use_transaction", use_transaction, 0, 1); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 16: SPIDER_PARAM_LONGLONG("bulk_insert_rows", bulk_insert_rows, 1); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 17: SPIDER_PARAM_INT_WITH_MAX( "use_table_charset", use_table_charset, 0, 1); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 20: SPIDER_PARAM_INT("bulk_insert_interval", bulk_insert_interval, 0); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; default: - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; } - - /* Verify that the remainder of the parameter value is whitespace */ - if ((error_num = param_string_parse.has_extra_parameter_values())) - goto error; + /* Restore delim */ + *parse.end_value= parse.delim_value; } set_default: - if ((error_num = spider_udf_set_copy_tables_param_default( - copy_tables - ))) - goto error; - - if (param_string) - spider_free(spider_current_trx, param_string, MYF(0)); - DBUG_RETURN(0); - + error_num = spider_udf_set_copy_tables_param_default(copy_tables); error: if (param_string) spider_free(spider_current_trx, param_string, MYF(0)); diff --git a/storage/spider/spd_direct_sql.cc b/storage/spider/spd_direct_sql.cc index 13de11d9673..8cfa1114f2e 100644 --- a/storage/spider/spd_direct_sql.cc +++ b/storage/spider/spd_direct_sql.cc @@ -1035,17 +1035,16 @@ error: #define SPIDER_PARAM_STR_LEN(name) name ## _length #define SPIDER_PARAM_STR(title_name, param_name) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (!direct_sql->param_name) \ { \ - if ((direct_sql->param_name = spider_get_string_between_quote( \ - start_ptr, TRUE, ¶m_string_parse))) \ - direct_sql->SPIDER_PARAM_STR_LEN(param_name) = \ - strlen(direct_sql->param_name); \ + if ((direct_sql->param_name = spider_create_string(parse.start_value, \ + value_length))) \ + direct_sql->SPIDER_PARAM_STR_LEN(param_name) = strlen(direct_sql->param_name); \ else { \ - error_num = param_string_parse.print_param_error(); \ + error_num= parse.fail(true); \ goto error; \ } \ DBUG_PRINT("info",("spider " title_name "=%s", direct_sql->param_name)); \ @@ -1053,130 +1052,81 @@ error: break; \ } #define SPIDER_PARAM_HINT_WITH_MAX(title_name, param_name, check_length, max_size, min_val, max_val) \ - if (!strncasecmp(tmp_ptr, title_name, check_length)) \ + if (!strncasecmp(parse.start_title, title_name, check_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ DBUG_PRINT("info",("spider max_size=%d", max_size)); \ - int hint_num = atoi(tmp_ptr + check_length) - 1; \ + int hint_num = atoi(parse.start_title + check_length) - 1; \ DBUG_PRINT("info",("spider hint_num=%d", hint_num)); \ DBUG_PRINT("info",("spider direct_sql->param_name=%p", \ - direct_sql->param_name)); \ + direct_sql->param_name)); \ if (direct_sql->param_name) \ { \ if (hint_num < 0 || hint_num >= max_size) \ { \ - error_num = param_string_parse.print_param_error(); \ + error_num= parse.fail(true); \ goto error; \ } else if (direct_sql->param_name[hint_num] != -1) \ break; \ - char *hint_str = spider_get_string_between_quote(start_ptr, FALSE); \ - if (hint_str) \ - { \ - direct_sql->param_name[hint_num] = atoi(hint_str); \ - if (direct_sql->param_name[hint_num] < min_val) \ - direct_sql->param_name[hint_num] = min_val; \ - else if (direct_sql->param_name[hint_num] > max_val) \ - direct_sql->param_name[hint_num] = max_val; \ - } else { \ - error_num = param_string_parse.print_param_error(); \ - goto error; \ - } \ + direct_sql->param_name[hint_num] = atoi(parse.start_value); \ + if (direct_sql->param_name[hint_num] < min_val) \ + direct_sql->param_name[hint_num] = min_val; \ + else if (direct_sql->param_name[hint_num] > max_val) \ + direct_sql->param_name[hint_num] = max_val; \ DBUG_PRINT("info",("spider " title_name "[%d]=%d", hint_num, \ - direct_sql->param_name[hint_num])); \ + direct_sql->param_name[hint_num])); \ } else { \ - error_num = param_string_parse.print_param_error(); \ + error_num= parse.fail(true); \ goto error; \ } \ break; \ } #define SPIDER_PARAM_INT_WITH_MAX(title_name, param_name, min_val, max_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (direct_sql->param_name == -1) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - direct_sql->param_name = atoi(tmp_ptr2); \ - if (direct_sql->param_name < min_val) \ - direct_sql->param_name = min_val; \ - else if (direct_sql->param_name > max_val) \ - direct_sql->param_name = max_val; \ - param_string_parse.set_param_value(tmp_ptr2, \ - tmp_ptr2 + \ - strlen(tmp_ptr2) + 1); \ - } else { \ - error_num = param_string_parse.print_param_error(); \ - goto error; \ - } \ + direct_sql->param_name = atoi(parse.start_value); \ + if (direct_sql->param_name < min_val) \ + direct_sql->param_name = min_val; \ + else if (direct_sql->param_name > max_val) \ + direct_sql->param_name = max_val; \ DBUG_PRINT("info",("spider " title_name "=%d", \ - (int) direct_sql->param_name)); \ + (int) direct_sql->param_name)); \ } \ break; \ } #define SPIDER_PARAM_INT(title_name, param_name, min_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (direct_sql->param_name == -1) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - direct_sql->param_name = atoi(tmp_ptr2); \ - if (direct_sql->param_name < min_val) \ - direct_sql->param_name = min_val; \ - param_string_parse.set_param_value(tmp_ptr2, \ - tmp_ptr2 + \ - strlen(tmp_ptr2) + 1); \ - } else { \ - error_num = param_string_parse.print_param_error(); \ - goto error; \ - } \ + direct_sql->param_name = atoi(parse.start_value); \ + if (direct_sql->param_name < min_val) \ + direct_sql->param_name = min_val; \ DBUG_PRINT("info",("spider " title_name "=%d", direct_sql->param_name)); \ } \ break; \ } #define SPIDER_PARAM_LONGLONG(title_name, param_name, min_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (direct_sql->param_name == -1) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - direct_sql->param_name = \ - my_strtoll10(tmp_ptr2, (char**) NULL, &error_num); \ - if (direct_sql->param_name < min_val) \ - direct_sql->param_name = min_val; \ - param_string_parse.set_param_value(tmp_ptr2, \ - tmp_ptr2 + \ - strlen(tmp_ptr2) + 1); \ - } else { \ - error_num = param_string_parse.print_param_error(); \ - goto error; \ - } \ - DBUG_PRINT("info",("spider " title_name "=%lld", \ - direct_sql->param_name)); \ + direct_sql->param_name = my_strtoll10(parse.start_value, (char**) NULL, \ + &error_num); \ + if (direct_sql->param_name < min_val) \ + direct_sql->param_name = min_val; \ + DBUG_PRINT("info",("spider " title_name "=%lld", direct_sql->param_name)); \ } \ break; \ } -int spider_udf_parse_direct_sql_param( - SPIDER_TRX *trx, - SPIDER_DIRECT_SQL *direct_sql, - const char *param, - int param_length -) { - int error_num = 0, roop_count; - char *param_string = NULL; - char *sprit_ptr; - char *tmp_ptr, *tmp_ptr2, *start_ptr; - int title_length; - SPIDER_PARAM_STRING_PARSE param_string_parse; - DBUG_ENTER("spider_udf_parse_direct_sql_param"); +static void spider_minus_1(SPIDER_DIRECT_SQL *direct_sql) +{ direct_sql->tgt_port = -1; direct_sql->tgt_ssl_vsc = -1; direct_sql->table_loop_mode = -1; @@ -1194,59 +1144,53 @@ int spider_udf_parse_direct_sql_param( direct_sql->use_real_table = -1; #endif direct_sql->error_rw_mode = -1; - for (roop_count = 0; roop_count < direct_sql->table_count; roop_count++) - direct_sql->iop[roop_count] = -1; + for (int i = 0; i < direct_sql->table_count; i++) + direct_sql->iop[i] = -1; +} +int spider_udf_parse_direct_sql_param( + SPIDER_TRX *trx, + SPIDER_DIRECT_SQL *direct_sql, + const char *param, + int param_length +) { + int error_num = 0; + char *param_string = NULL; + char *start_param; + int title_length, value_length; + SPIDER_PARAM_STRING_PARSE parse; + DBUG_ENTER("spider_udf_parse_direct_sql_param"); + + spider_minus_1(direct_sql); if (param_length == 0) goto set_default; DBUG_PRINT("info",("spider create param_string string")); - if ( - !(param_string = spider_create_string( - param, - param_length)) - ) { + if (!(param_string = spider_create_string(param, param_length))) + { error_num = HA_ERR_OUT_OF_MEM; my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM); goto error_alloc_param_string; } DBUG_PRINT("info",("spider param_string=%s", param_string)); - sprit_ptr = param_string; - param_string_parse.init(param_string, ER_SPIDER_INVALID_UDF_PARAM_NUM); - while (sprit_ptr) + start_param = param_string; + parse.error_num = ER_SPIDER_INVALID_UDF_PARAM_NUM; + while (*start_param != '\0') { - tmp_ptr = sprit_ptr; - while (*tmp_ptr == ' ' || *tmp_ptr == '\r' || - *tmp_ptr == '\n' || *tmp_ptr == '\t') - tmp_ptr++; - - if (*tmp_ptr == '\0') - break; - - title_length = 0; - start_ptr = tmp_ptr; - while (*start_ptr != ' ' && *start_ptr != '\'' && - *start_ptr != '"' && *start_ptr != '\0' && - *start_ptr != '\r' && *start_ptr != '\n' && - *start_ptr != '\t') - { - title_length++; - start_ptr++; - } - param_string_parse.set_param_title(tmp_ptr, tmp_ptr + title_length); - if ((error_num = param_string_parse.get_next_parameter_head( - start_ptr, &sprit_ptr))) + if (parse.locate_param_def(start_param)) { + error_num= parse.fail(false); goto error; } + /* Null the end of the parameter value. */ + *parse.end_value= '\0'; + value_length= (int) (parse.end_value - parse.start_value); - switch (title_length) + switch (title_length = (int) (parse.end_title - parse.start_title)) { case 0: - error_num = param_string_parse.print_param_error(); - if (error_num) - goto error; - continue; + error_num= parse.fail(true); + goto error; case 3: #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET) SPIDER_PARAM_INT_WITH_MAX("acm", access_mode, 0, 2); @@ -1272,112 +1216,97 @@ int spider_udf_parse_direct_sql_param( SPIDER_PARAM_INT_WITH_MAX("urt", use_real_table, 0, 1); #endif SPIDER_PARAM_INT("wto", net_write_timeout, 0); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 4: SPIDER_PARAM_INT_WITH_MAX("erwm", error_rw_mode, 0, 1); SPIDER_PARAM_STR("host", tgt_host); SPIDER_PARAM_INT_WITH_MAX("port", tgt_port, 0, 65535); SPIDER_PARAM_STR("user", tgt_username); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 6: SPIDER_PARAM_STR("server", server_name); SPIDER_PARAM_STR("socket", tgt_socket); SPIDER_PARAM_HINT_WITH_MAX("iop", iop, 3, direct_sql->table_count, 0, 2); SPIDER_PARAM_STR("ssl_ca", tgt_ssl_ca); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 7: SPIDER_PARAM_STR("wrapper", tgt_wrapper); SPIDER_PARAM_STR("ssl_key", tgt_ssl_key); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 8: SPIDER_PARAM_STR("database", tgt_default_db_name); SPIDER_PARAM_STR("password", tgt_password); SPIDER_PARAM_LONGLONG("priority", priority, 0); SPIDER_PARAM_STR("ssl_cert", tgt_ssl_cert); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 10: SPIDER_PARAM_STR("ssl_cipher", tgt_ssl_cipher); SPIDER_PARAM_STR("ssl_capath", tgt_ssl_capath); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 11: #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET) SPIDER_PARAM_INT_WITH_MAX("access_mode", access_mode, 0, 2); #endif - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 12: SPIDER_PARAM_STR("default_file", tgt_default_file); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 13: SPIDER_PARAM_STR("default_group", tgt_default_group); SPIDER_PARAM_INT_WITH_MAX("error_rw_mode", error_rw_mode, 0, 1); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 14: #if MYSQL_VERSION_ID < 50500 #else SPIDER_PARAM_INT_WITH_MAX("use_real_table", use_real_table, 0, 1); #endif - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 15: SPIDER_PARAM_INT_WITH_MAX("table_loop_mode", table_loop_mode, 0, 2); SPIDER_PARAM_INT("connect_timeout", connect_timeout, 0); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 16: SPIDER_PARAM_LONGLONG("bulk_insert_rows", bulk_insert_rows, 1); SPIDER_PARAM_INT("net_read_timeout", net_read_timeout, 0); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 17: SPIDER_PARAM_INT("net_write_timeout", net_write_timeout, 0); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 18: SPIDER_PARAM_INT_WITH_MAX( "connection_channel", connection_channel, 0, 63); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; case 22: SPIDER_PARAM_INT_WITH_MAX("ssl_verify_server_cert", tgt_ssl_vsc, 0, 1); - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; default: - error_num = param_string_parse.print_param_error(); + error_num= parse.fail(true); goto error; } - - /* Verify that the remainder of the parameter value is whitespace */ - if ((error_num = param_string_parse.has_extra_parameter_values())) - goto error; + /* Restore delim */ + *parse.end_value= parse.delim_value; } set_default: - if ((error_num = spider_udf_set_direct_sql_param_default( - trx, - direct_sql - ))) - goto error; - - if (param_string) - { - spider_free(spider_current_trx, param_string, MYF(0)); - } - DBUG_RETURN(0); - + error_num = spider_udf_set_direct_sql_param_default(trx, direct_sql); error: if (param_string) - { spider_free(spider_current_trx, param_string, MYF(0)); - } error_alloc_param_string: DBUG_RETURN(error_num); } diff --git a/storage/spider/spd_table.cc b/storage/spider/spd_table.cc index 34d46d48403..36948baabf0 100644 --- a/storage/spider/spd_table.cc +++ b/storage/spider/spd_table.cc @@ -1053,89 +1053,12 @@ void spider_free_tmp_share_alloc( DBUG_VOID_RETURN; } -char *spider_get_string_between_quote( - char *ptr, - bool alloc, - SPIDER_PARAM_STRING_PARSE *param_string_parse -) { - char *start_ptr, *end_ptr, *tmp_ptr, *esc_ptr; - bool find_flg = FALSE; - DBUG_ENTER("spider_get_string_between_quote"); - - start_ptr = strchr(ptr, '\''); - end_ptr = strchr(ptr, '"'); - if (start_ptr && (!end_ptr || start_ptr < end_ptr)) - { - tmp_ptr = ++start_ptr; - while (!find_flg) - { - if (!(end_ptr = strchr(tmp_ptr, '\''))) - DBUG_RETURN(NULL); - esc_ptr = tmp_ptr; - while (!find_flg) - { - esc_ptr = strchr(esc_ptr, '\\'); - if (!esc_ptr || esc_ptr > end_ptr) - find_flg = TRUE; - else if (esc_ptr == end_ptr - 1) - { - tmp_ptr = end_ptr + 1; - break; - } else { - esc_ptr += 2; - } - } - } - } else if (end_ptr) - { - start_ptr = end_ptr; - tmp_ptr = ++start_ptr; - while (!find_flg) - { - if (!(end_ptr = strchr(tmp_ptr, '"'))) - DBUG_RETURN(NULL); - esc_ptr = tmp_ptr; - while (!find_flg) - { - esc_ptr = strchr(esc_ptr, '\\'); - if (!esc_ptr || esc_ptr > end_ptr) - find_flg = TRUE; - else if (esc_ptr == end_ptr - 1) - { - tmp_ptr = end_ptr + 1; - break; - } else { - esc_ptr += 2; - } - } - } - } else - DBUG_RETURN(NULL); - - *end_ptr = '\0'; - - if (param_string_parse) - param_string_parse->set_param_value(start_ptr, start_ptr + strlen(start_ptr) + 1); - - if (alloc) - { - DBUG_RETURN( - spider_create_string( - start_ptr, - strlen(start_ptr)) - ); - } else { - DBUG_RETURN(start_ptr); - } -} - int spider_create_string_list( char ***string_list, uint **string_length_list, uint *list_length, char *str, - uint length, - SPIDER_PARAM_STRING_PARSE *param_string_parse + uint length ) { int roop_count; char *tmp_ptr, *tmp_ptr2, *tmp_ptr3, *tmp_ptr4, *esc_ptr; @@ -1143,7 +1066,6 @@ int spider_create_string_list( DBUG_ENTER("spider_create_string_list"); *list_length = 0; - param_string_parse->init_param_value(); if (!str) { *string_list = NULL; @@ -1343,9 +1265,6 @@ int spider_create_string_list( } } - param_string_parse->set_param_value(tmp_ptr3, - tmp_ptr3 + strlen(tmp_ptr3) + 1); - DBUG_PRINT("info",("spider string_list[%d]=%s", roop_count, (*string_list)[roop_count])); @@ -1358,15 +1277,13 @@ int spider_create_long_list( char *str, uint length, long min_val, - long max_val, - SPIDER_PARAM_STRING_PARSE *param_string_parse + long max_val ) { int roop_count; char *tmp_ptr; DBUG_ENTER("spider_create_long_list"); *list_length = 0; - param_string_parse->init_param_value(); if (!str) { *long_list = NULL; @@ -1422,9 +1339,6 @@ int spider_create_long_list( (*long_list)[roop_count] = max_val; } - param_string_parse->set_param_value(tmp_ptr, - tmp_ptr + strlen(tmp_ptr) + 1); - #ifndef DBUG_OFF for (roop_count = 0; roop_count < (int) *list_length; roop_count++) { @@ -1442,15 +1356,13 @@ int spider_create_longlong_list( char *str, uint length, longlong min_val, - longlong max_val, - SPIDER_PARAM_STRING_PARSE *param_string_parse + longlong max_val ) { int error_num, roop_count; char *tmp_ptr; DBUG_ENTER("spider_create_longlong_list"); *list_length = 0; - param_string_parse->init_param_value(); if (!str) { *longlong_list = NULL; @@ -1507,9 +1419,6 @@ int spider_create_longlong_list( (*longlong_list)[roop_count] = max_val; } - param_string_parse->set_param_value(tmp_ptr, - tmp_ptr + strlen(tmp_ptr) + 1); - #ifndef DBUG_OFF for (roop_count = 0; roop_count < (int) *list_length; roop_count++) { @@ -1749,50 +1658,18 @@ static int spider_set_ll_value( DBUG_RETURN(error_num); } -/** - Print a parameter string error message. - - @return Error code. -*/ - -int st_spider_param_string_parse::print_param_error() -{ - if (start_title_ptr) - { - /* Restore the input delimiter characters */ - restore_delims(); - - /* Print the error message */ - switch (error_num) - { - case ER_SPIDER_INVALID_UDF_PARAM_NUM: - my_printf_error(error_num, ER_SPIDER_INVALID_UDF_PARAM_STR, - MYF(0), start_title_ptr); - break; - case ER_SPIDER_INVALID_CONNECT_INFO_NUM: - default: - my_printf_error(error_num, ER_SPIDER_INVALID_CONNECT_INFO_STR, - MYF(0), start_title_ptr); - } - - return error_num; - } - else - return 0; -} - #define SPIDER_PARAM_STR_LEN(name) name ## _length #define SPIDER_PARAM_STR(title_name, param_name) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (!share->param_name) \ { \ - if ((share->param_name = spider_get_string_between_quote( \ - start_ptr, TRUE, &connect_string_parse))) \ + if ((share->param_name = spider_create_string(parse.start_value, \ + value_length))) \ share->SPIDER_PARAM_STR_LEN(param_name) = strlen(share->param_name); \ else { \ - error_num = connect_string_parse.print_param_error(); \ + error_num= parse.fail(true); \ goto error; \ } \ DBUG_PRINT("info",("spider " title_name "=%s", share->param_name)); \ @@ -1802,272 +1679,171 @@ int st_spider_param_string_parse::print_param_error() #define SPIDER_PARAM_STR_LENS(name) name ## _lengths #define SPIDER_PARAM_STR_CHARLEN(name) name ## _charlen #define SPIDER_PARAM_STR_LIST(title_name, param_name) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ - DBUG_PRINT("info",("spider " title_name " start")); \ + DBUG_PRINT("info", ("spider " title_name " start")); \ if (!share->param_name) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - share->SPIDER_PARAM_STR_CHARLEN(param_name) = strlen(tmp_ptr2); \ - if ((error_num = spider_create_string_list( \ - &share->param_name, \ - &share->SPIDER_PARAM_STR_LENS(param_name), \ - &share->SPIDER_PARAM_STR_LEN(param_name), \ - tmp_ptr2, \ - share->SPIDER_PARAM_STR_CHARLEN(param_name), \ - &connect_string_parse))) \ - goto error; \ - } else { \ - error_num = connect_string_parse.print_param_error(); \ + share->SPIDER_PARAM_STR_CHARLEN(param_name)= value_length; \ + if ((error_num= spider_create_string_list( \ + &share->param_name, \ + &share->SPIDER_PARAM_STR_LENS(param_name), \ + &share->SPIDER_PARAM_STR_LEN(param_name), \ + parse.start_value, \ + share->SPIDER_PARAM_STR_CHARLEN(param_name)))) \ goto error; \ - } \ } \ break; \ } #define SPIDER_PARAM_HINT(title_name, param_name, check_length, max_size, append_method) \ - if (!strncasecmp(tmp_ptr, title_name, check_length)) \ + if (!strncasecmp(parse.start_title, title_name, check_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ DBUG_PRINT("info",("spider max_size=%d", max_size)); \ - int hint_num = atoi(tmp_ptr + check_length); \ + int hint_num = atoi(parse.start_title + check_length); \ DBUG_PRINT("info",("spider hint_num=%d", hint_num)); \ - DBUG_PRINT("info",("spider share->param_name=%p", share->param_name)); \ + DBUG_PRINT("info",("spider share->param_name=%p", \ + share->param_name)); \ if (share->param_name) \ { \ if (hint_num < 0 || hint_num >= max_size) \ { \ - error_num = connect_string_parse.print_param_error(); \ + error_num= parse.fail(true); \ goto error; \ } else if (share->param_name[hint_num].length() > 0) \ break; \ - char *hint_str = spider_get_string_between_quote(start_ptr, FALSE); \ - if ((error_num = \ - append_method(&share->param_name[hint_num], hint_str))) \ + if ((error_num= append_method(&share->param_name[hint_num], \ + parse.start_value))) \ goto error; \ DBUG_PRINT("info",("spider " title_name "[%d]=%s", hint_num, \ - share->param_name[hint_num].ptr())); \ + share->param_name[hint_num].ptr())); \ } else { \ - error_num = connect_string_parse.print_param_error(); \ + error_num= parse.fail(true); \ goto error; \ } \ break; \ } #define SPIDER_PARAM_NUMHINT(title_name, param_name, check_length, max_size, append_method) \ - if (!strncasecmp(tmp_ptr, title_name, check_length)) \ + if (!strncasecmp(parse.start_title, title_name, check_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ DBUG_PRINT("info",("spider max_size=%d", max_size)); \ - int hint_num = atoi(tmp_ptr + check_length); \ + int hint_num = atoi(parse.start_title + check_length); \ DBUG_PRINT("info",("spider hint_num=%d", hint_num)); \ DBUG_PRINT("info",("spider share->param_name=%p", share->param_name)); \ if (share->param_name) \ { \ if (hint_num < 0 || hint_num >= max_size) \ { \ - error_num = connect_string_parse.print_param_error(); \ + error_num= parse.fail(true); \ goto error; \ } else if (share->param_name[hint_num] != -1) \ break; \ - char *hint_str = spider_get_string_between_quote(start_ptr, FALSE); \ if ((error_num = \ - append_method(&share->param_name[hint_num], hint_str))) \ + append_method(&share->param_name[hint_num], parse.start_value))) \ goto error; \ DBUG_PRINT("info",("spider " title_name "[%d]=%lld", hint_num, \ - share->param_name[hint_num])); \ + share->param_name[hint_num])); \ } else { \ - error_num = connect_string_parse.print_param_error(); \ + error_num= parse.fail(true); \ goto error; \ } \ break; \ } #define SPIDER_PARAM_LONG_LEN(name) name ## _length #define SPIDER_PARAM_LONG_LIST_WITH_MAX(title_name, param_name, \ - min_val, max_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + min_val, max_val) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (!share->param_name) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - if ((error_num = spider_create_long_list( \ - &share->param_name, \ - &share->SPIDER_PARAM_LONG_LEN(param_name), \ - tmp_ptr2, \ - strlen(tmp_ptr2), \ - min_val, max_val, \ - &connect_string_parse))) \ - goto error; \ - } else { \ - error_num = connect_string_parse.print_param_error(); \ + if ((error_num = spider_create_long_list( \ + &share->param_name, \ + &share->SPIDER_PARAM_LONG_LEN(param_name), \ + parse.start_value, \ + value_length, \ + min_val, max_val))) \ goto error; \ - } \ } \ break; \ } #define SPIDER_PARAM_LONGLONG_LEN(name) name ## _length #define SPIDER_PARAM_LONGLONG_LIST_WITH_MAX(title_name, param_name, \ - min_val, max_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + min_val, max_val) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (!share->param_name) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - if ((error_num = spider_create_longlong_list( \ - &share->param_name, \ - &share->SPIDER_PARAM_LONGLONG_LEN(param_name), \ - tmp_ptr2, \ - strlen(tmp_ptr2), \ - min_val, max_val, \ - &connect_string_parse))) \ - goto error; \ - } else { \ - error_num = connect_string_parse.print_param_error(); \ + if ((error_num = spider_create_longlong_list( \ + &share->param_name, \ + &share->SPIDER_PARAM_LONGLONG_LEN(param_name), \ + parse.start_value, \ + value_length, \ + min_val, max_val))) \ goto error; \ - } \ } \ break; \ } #define SPIDER_PARAM_INT_WITH_MAX(title_name, param_name, min_val, max_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (share->param_name == -1) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - share->param_name = atoi(tmp_ptr2); \ - if (share->param_name < min_val) \ - share->param_name = min_val; \ - else if (share->param_name > max_val) \ - share->param_name = max_val; \ - connect_string_parse.set_param_value(tmp_ptr2, \ - tmp_ptr2 + \ - strlen(tmp_ptr2) + 1); \ - } else { \ - error_num = connect_string_parse.print_param_error(); \ - goto error; \ - } \ + share->param_name = atoi(parse.start_value); \ + if (share->param_name < min_val) \ + share->param_name = min_val; \ + else if (share->param_name > max_val) \ + share->param_name = max_val; \ DBUG_PRINT("info",("spider " title_name "=%d", share->param_name)); \ } \ break; \ } #define SPIDER_PARAM_INT(title_name, param_name, min_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (share->param_name == -1) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - share->param_name = atoi(tmp_ptr2); \ - if (share->param_name < min_val) \ - share->param_name = min_val; \ - connect_string_parse.set_param_value(tmp_ptr2, \ - tmp_ptr2 + \ - strlen(tmp_ptr2) + 1); \ - } else { \ - error_num = connect_string_parse.print_param_error(); \ - goto error; \ - } \ + share->param_name = atoi(parse.start_value); \ + if (share->param_name < min_val) \ + share->param_name = min_val; \ DBUG_PRINT("info",("spider " title_name "=%d", share->param_name)); \ } \ break; \ } #define SPIDER_PARAM_DOUBLE(title_name, param_name, min_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (share->param_name == -1) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - share->param_name = my_atof(tmp_ptr2); \ - if (share->param_name < min_val) \ - share->param_name = min_val; \ - connect_string_parse.set_param_value(tmp_ptr2, \ - tmp_ptr2 + \ - strlen(tmp_ptr2) + 1); \ - } else { \ - error_num = connect_string_parse.print_param_error(); \ - goto error; \ - } \ + share->param_name = my_atof(parse.start_value); \ + if (share->param_name < min_val) \ + share->param_name = min_val; \ DBUG_PRINT("info",("spider " title_name "=%f", share->param_name)); \ } \ break; \ } #define SPIDER_PARAM_LONGLONG(title_name, param_name, min_val) \ - if (!strncasecmp(tmp_ptr, title_name, title_length)) \ + if (!strncasecmp(parse.start_title, title_name, title_length)) \ { \ DBUG_PRINT("info",("spider " title_name " start")); \ if (share->param_name == -1) \ { \ - if ((tmp_ptr2 = spider_get_string_between_quote( \ - start_ptr, FALSE))) \ - { \ - share->param_name = my_strtoll10(tmp_ptr2, (char**) NULL, &error_num); \ - if (share->param_name < min_val) \ - share->param_name = min_val; \ - connect_string_parse.set_param_value(tmp_ptr2, \ - tmp_ptr2 + \ - strlen(tmp_ptr2) + 1); \ - } else { \ - error_num = connect_string_parse.print_param_error(); \ - goto error; \ - } \ + share->param_name = my_strtoll10(parse.start_value, (char**) NULL, \ + &error_num); \ + if (share->param_name < min_val) \ + share->param_name = min_val; \ DBUG_PRINT("info",("spider " title_name "=%lld", share->param_name)); \ } \ break; \ } -int spider_parse_connect_info( - SPIDER_SHARE *share, - TABLE_SHARE *table_share, -#ifdef WITH_PARTITION_STORAGE_ENGINE - partition_info *part_info, -#endif - uint create_table -) { - int error_num = 0; - char *connect_string = NULL; - char *sprit_ptr; - char *tmp_ptr, *tmp_ptr2, *start_ptr; - int roop_count; - int title_length; - SPIDER_PARAM_STRING_PARSE connect_string_parse; - SPIDER_ALTER_TABLE *share_alter; -#ifdef WITH_PARTITION_STORAGE_ENGINE - partition_element *part_elem; - partition_element *sub_elem; -#endif - DBUG_ENTER("spider_parse_connect_info"); -#ifdef WITH_PARTITION_STORAGE_ENGINE -#if MYSQL_VERSION_ID < 50500 - DBUG_PRINT("info",("spider partition_info=%s", table_share->partition_info)); -#else - DBUG_PRINT("info",("spider partition_info=%s", - table_share->partition_info_str)); -#endif - DBUG_PRINT("info",("spider part_info=%p", part_info)); -#endif - DBUG_PRINT("info",("spider s->db=%s", table_share->db.str)); - DBUG_PRINT("info",("spider s->table_name=%s", table_share->table_name.str)); - DBUG_PRINT("info",("spider s->path=%s", table_share->path.str)); - DBUG_PRINT("info", - ("spider s->normalized_path=%s", table_share->normalized_path.str)); -#ifdef WITH_PARTITION_STORAGE_ENGINE - spider_get_partition_info(share->table_name, share->table_name_length, - table_share, part_info, &part_elem, &sub_elem); -#endif +static void spider_minus_1(SPIDER_SHARE *share, TABLE_SHARE *table_share) +{ #ifndef WITHOUT_SPIDER_BG_SEARCH share->sts_bg_mode = -1; #endif @@ -2154,13 +1930,275 @@ int spider_parse_connect_info( share->delete_all_rows_type = -1; share->static_records_for_status = -1; share->static_mean_rec_length = -1; - for (roop_count = 0; roop_count < (int) table_share->keys; roop_count++) + for (uint i = 0; i < table_share->keys; i++) { - share->static_key_cardinality[roop_count] = -1; + share->static_key_cardinality[i] = -1; } +} +/** + Get the connect info of a certain type. + + @param type The type of the connect info. + 4: partition; 3: subpartition; 2: comment; + 1: connect_string + @retval 0 Success + @retval 1 Not applicable. That is, the info with the + type is missing + @retval HA_ERR_OUT_OF_MEM Failure +*/ +static int spider_get_connect_info(const int type, + const partition_element *part_elem, + const partition_element *sub_elem, + const TABLE_SHARE* table_share, + char*& out) +{ + switch (type) + { #ifdef WITH_PARTITION_STORAGE_ENGINE - for (roop_count = 4; roop_count > 0; roop_count--) + case 4: + if (!sub_elem || !sub_elem->part_comment) + return 1; + if (!(out = spider_create_string( + sub_elem->part_comment, strlen(sub_elem->part_comment)))) + return HA_ERR_OUT_OF_MEM; + break; + case 3: + if (!part_elem || !part_elem->part_comment) + return 1; + if (!(out = spider_create_string( + part_elem->part_comment, strlen(part_elem->part_comment)))) + return HA_ERR_OUT_OF_MEM; + break; +#endif + case 2: + if (table_share->comment.length == 0) + return 1; + if (!(out = spider_create_string( + table_share->comment.str, table_share->comment.length))) + return HA_ERR_OUT_OF_MEM; + break; + default: + if (table_share->connect_string.length == 0) + return 1; + DBUG_PRINT("info",("spider create out string")); + if (!(out = spider_create_string( + table_share->connect_string.str, table_share->connect_string.length))) + return HA_ERR_OUT_OF_MEM; + break; + } + return 0; +} + +/** + Find the beginning and end of a parameter title + + Skip over whitespace to find the beginning of the parameter + title. Then skip over non-whitespace/quote/nul chars to find the end + of the parameter title + + @param start_title The start of the param definition. Will be + moved to the start of the param title + @param end_title Will be moved to the end of the param title + @retval false Success + @retval true Failure +*/ +static bool spider_parse_find_title(char*& start_title, char*& end_title) +{ + /* Skip leading whitespaces. */ + while (*start_title == ' ' || *start_title == '\r' || + *start_title == '\n' || *start_title == '\t') + start_title++; + + if (*start_title == '\0') + return true; + + end_title = start_title; + /* Move over non-whitespace/comma/nul/quote chars (parameter title). */ + while (*end_title != ' ' && *end_title != '\r' && + *end_title != '\n' && *end_title != '\t' && + *end_title != '\0' && *end_title != ',' && + *end_title != '\'' && *end_title != '"') + end_title++; + + /* Fail on invalid end: there should be at least one space between + title and value, and the value should be non-empty. */ + if (*end_title == '\'' || *end_title == '"' || + *end_title == '\0' || *end_title == ',') + return true; + + return false; +} + +/** + Find the beginning and the end of a paramter value, and the value + delimiter + + Skip over whitespaces to find the start delimiter, then skip over + the param value to find the end delimiter + + @param start_value The end of the param title. Will be moved to + the start of the param value, just after the + delimiter + @param end_value Will be moved to the end of the param value, at + the delimiter + @param delim Will be assigned the param value delimiter, + either the single or double quote + @retval false Success + @retval true Failure +*/ +static bool spider_parse_find_value(char*& start_value, char*& end_value, + char& delim) +{ + /* Skip over whitespaces */ + while (*start_value == ' ' || *start_value == '\r' || + *start_value == '\n' || *start_value == '\t') + start_value++; + if (*start_value != '"' && *start_value != '\'') + return true; + delim= *start_value; + end_value= start_value++; + + while (1) + { + end_value++; + /* Escaping */ + if (*end_value == '\\') + { + end_value++; + /* The backslash cannot be at the end */ + if (*end_value == '\0') + return true; + } + else if (*end_value == delim) + return false; + else if (*end_value == '\0') + return true; + } +} + +/** + Find the beginning of the next parameter + + Skip over whitespaces, then check that the first non-whitespace char + is a comma or the end of string + + @param start_param The end of the param value. Will be moved to + the start of the next param definition, just + after the comma, if there's one; otherwise will + be moved to the end of the string + @retval false Success + @retval true Failure +*/ +static bool spider_parse_find_next(char*& start_param) +{ + /* Skip over whitespaces */ + while (*start_param == ' ' || *start_param == '\r' || + *start_param == '\n' || *start_param == '\t') + start_param++; + /* No more param definitions */ + if (*start_param == '\0') + return false; + else if (*start_param == ',') + { + start_param++; + return false; + } + else + return true; +} + +/** + Find the start and end of the current param title and value and the + value deliminator. + + @param start_param The beginning of the current param + definition. Will be mutated to the beginning + of the next param definition. + @retval false success + @retval true failure +*/ +bool st_spider_param_string_parse::locate_param_def(char*& start_param) +{ + DBUG_ENTER("parse::locate_param_def"); + start_title= start_param; + if (spider_parse_find_title(start_title, end_title)) + DBUG_RETURN(TRUE); + start_value= end_title; + if (spider_parse_find_value(start_value, end_value, delim_value)) + DBUG_RETURN(TRUE); + /* skip the delim */ + start_param= end_value + 1; + if (spider_parse_find_next(start_param)) + DBUG_RETURN(TRUE); + DBUG_RETURN(FALSE); +} + +/** + Handle parsing failure. + + Print error and optionally restore param value end delimiter that + has been nulled before. + + @param restore_delim If true, restore the end value delimiter + @return The error number +*/ +int st_spider_param_string_parse::fail(bool restore_delim) +{ + DBUG_ENTER("spider_parse_print_param_error"); + DBUG_ASSERT(error_num != 0); + /* Print the error message */ + switch (error_num) + { + case ER_SPIDER_INVALID_UDF_PARAM_NUM: + my_printf_error(error_num, ER_SPIDER_INVALID_UDF_PARAM_STR, + MYF(0), start_title); + break; + case ER_SPIDER_INVALID_CONNECT_INFO_NUM: + default: + my_printf_error(error_num, ER_SPIDER_INVALID_CONNECT_INFO_STR, + MYF(0), start_title); + } + if (restore_delim) + *end_value = delim_value; + DBUG_RETURN(error_num); +} + +/* + Parse connection information specified by COMMENT, CONNECT, or engine-defined + options. + + TODO: Deprecate the connection specification by COMMENT and CONNECT, + and then solely utilize engine-defined options. +*/ +int spider_parse_connect_info( + SPIDER_SHARE *share, + TABLE_SHARE *table_share, + partition_info *part_info, + uint create_table +) { + int error_num = 0; + char *connect_string = NULL; + char *start_param; + int title_length, value_length; + SPIDER_PARAM_STRING_PARSE parse; + SPIDER_ALTER_TABLE *share_alter; + partition_element *part_elem; + partition_element *sub_elem; + DBUG_ENTER("spider_parse_connect_info"); + DBUG_PRINT("info",("spider partition_info=%s", + table_share->partition_info_str)); + DBUG_PRINT("info",("spider part_info=%p", part_info)); + DBUG_PRINT("info",("spider s->db=%s", table_share->db.str)); + DBUG_PRINT("info",("spider s->table_name=%s", table_share->table_name.str)); + DBUG_PRINT("info",("spider s->path=%s", table_share->path.str)); + DBUG_PRINT("info", + ("spider s->normalized_path=%s", table_share->normalized_path.str)); + spider_get_partition_info(share->table_name, share->table_name_length, + table_share, part_info, &part_elem, &sub_elem); + spider_minus_1(share, table_share); +#ifdef WITH_PARTITION_STORAGE_ENGINE + for (int i = 4; i > 0; i--) #else for (roop_count = 2; roop_count > 0; roop_count--) #endif @@ -2170,104 +2208,35 @@ int spider_parse_connect_info( spider_free(spider_current_trx, connect_string, MYF(0)); connect_string = NULL; } - switch (roop_count) + + int error_num_1 = spider_get_connect_info(i, part_elem, sub_elem, + table_share, connect_string); + if (error_num_1 == 1) + continue; + if (error_num_1 == HA_ERR_OUT_OF_MEM) { -#ifdef WITH_PARTITION_STORAGE_ENGINE - case 4: - if (!sub_elem || !sub_elem->part_comment) - continue; - DBUG_PRINT("info",("spider create sub comment string")); - if ( - !(connect_string = spider_create_string( - sub_elem->part_comment, - strlen(sub_elem->part_comment))) - ) { - error_num = HA_ERR_OUT_OF_MEM; - goto error_alloc_conn_string; - } - DBUG_PRINT("info",("spider sub comment string=%s", connect_string)); - break; - case 3: - if (!part_elem || !part_elem->part_comment) - continue; - DBUG_PRINT("info",("spider create part comment string")); - if ( - !(connect_string = spider_create_string( - part_elem->part_comment, - strlen(part_elem->part_comment))) - ) { - error_num = HA_ERR_OUT_OF_MEM; - goto error_alloc_conn_string; - } - DBUG_PRINT("info",("spider part comment string=%s", connect_string)); - break; -#endif - case 2: - if (table_share->comment.length == 0) - continue; - DBUG_PRINT("info",("spider create comment string")); - if ( - !(connect_string = spider_create_string( - table_share->comment.str, - table_share->comment.length)) - ) { - error_num = HA_ERR_OUT_OF_MEM; - goto error_alloc_conn_string; - } - DBUG_PRINT("info",("spider comment string=%s", connect_string)); - break; - default: - if (table_share->connect_string.length == 0) - continue; - DBUG_PRINT("info",("spider create connect_string string")); - if ( - !(connect_string = spider_create_string( - table_share->connect_string.str, - table_share->connect_string.length)) - ) { - error_num = HA_ERR_OUT_OF_MEM; - goto error_alloc_conn_string; - } - DBUG_PRINT("info",("spider connect_string=%s", connect_string)); - break; + error_num= HA_ERR_OUT_OF_MEM; + goto error_alloc_conn_string; } + DBUG_ASSERT(error_num_1 == 0); - sprit_ptr = connect_string; - connect_string_parse.init(connect_string, ER_SPIDER_INVALID_CONNECT_INFO_NUM); - while (sprit_ptr) + start_param = connect_string; + parse.error_num = ER_SPIDER_INVALID_CONNECT_INFO_NUM; + while (*start_param != '\0') { - tmp_ptr = sprit_ptr; - while (*tmp_ptr == ' ' || *tmp_ptr == '\r' || - *tmp_ptr == '\n' || *tmp_ptr == '\t') - tmp_ptr++; - - if (*tmp_ptr == '\0') - break; - - title_length = 0; - start_ptr = tmp_ptr; - while (*start_ptr != ' ' && *start_ptr != '\'' && - *start_ptr != '"' && *start_ptr != '\0' && - *start_ptr != '\r' && *start_ptr != '\n' && - *start_ptr != '\t') - { - title_length++; - start_ptr++; - } - connect_string_parse.set_param_title(tmp_ptr, tmp_ptr + title_length); - if ((error_num = connect_string_parse.get_next_parameter_head( - start_ptr, &sprit_ptr))) + if (parse.locate_param_def(start_param)) { + error_num= parse.fail(false); goto error; } - - switch (title_length) + /* Null the end of the parameter value. */ + *parse.end_value= '\0'; + value_length= (int) (parse.end_value - parse.start_value); + switch (title_length = (int) (parse.end_title - parse.start_title)) { case 0: - error_num = connect_string_parse.print_param_error(); - if (error_num) - goto error; - continue; + error_num= parse.fail(true); + goto error; case 3: SPIDER_PARAM_LONG_LIST_WITH_MAX("abl", access_balances, 0, 2147483647); @@ -2410,17 +2379,17 @@ int spider_parse_connect_info( #endif SPIDER_PARAM_INT_WITH_MAX("upu", use_pushdown_udf, 0, 1); SPIDER_PARAM_INT_WITH_MAX("utc", use_table_charset, 0, 1); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 4: SPIDER_PARAM_STR_LIST("host", tgt_hosts); SPIDER_PARAM_STR_LIST("user", tgt_usernames); SPIDER_PARAM_LONG_LIST_WITH_MAX("port", tgt_ports, 0, 65535); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 5: SPIDER_PARAM_STR_LIST("table", tgt_table_names); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 6: SPIDER_PARAM_STR_LIST("server", server_names); @@ -2430,13 +2399,13 @@ int spider_parse_connect_info( SPIDER_PARAM_STR_LIST("ssl_ca", tgt_ssl_cas); SPIDER_PARAM_NUMHINT("skc", static_key_cardinality, 3, (int) table_share->keys, spider_set_ll_value); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 7: SPIDER_PARAM_STR_LIST("wrapper", tgt_wrappers); SPIDER_PARAM_STR_LIST("ssl_key", tgt_ssl_keys); SPIDER_PARAM_STR_LIST("pk_name", tgt_pk_names); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 8: SPIDER_PARAM_STR_LIST("database", tgt_dbs); @@ -2456,14 +2425,14 @@ int spider_parse_connect_info( #endif SPIDER_PARAM_STR_LIST("ssl_cert", tgt_ssl_certs); SPIDER_PARAM_INT_WITH_MAX("bka_mode", bka_mode, 0, 2); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 9: SPIDER_PARAM_INT("max_order", max_order, 0); SPIDER_PARAM_INT("bulk_size", bulk_size, 0); SPIDER_PARAM_DOUBLE("scan_rate", scan_rate, 0); SPIDER_PARAM_DOUBLE("read_rate", read_rate, 0); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 10: SPIDER_PARAM_DOUBLE("crd_weight", crd_weight, 1); @@ -2473,7 +2442,7 @@ int spider_parse_connect_info( SPIDER_PARAM_STR_LIST("ssl_capath", tgt_ssl_capaths); SPIDER_PARAM_STR("bka_engine", bka_engine); SPIDER_PARAM_LONGLONG("first_read", first_read, 0); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 11: SPIDER_PARAM_INT_WITH_MAX("query_cache", query_cache, 0, 2); @@ -2488,7 +2457,7 @@ int spider_parse_connect_info( #endif SPIDER_PARAM_INT_WITH_MAX("casual_read", casual_read, 0, 63); SPIDER_PARAM_INT("buffer_size", buffer_size, 0); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 12: SPIDER_PARAM_DOUBLE("sts_interval", sts_interval, 0); @@ -2501,7 +2470,7 @@ int spider_parse_connect_info( SPIDER_PARAM_LONG_LIST_WITH_MAX( "hs_read_port", hs_read_ports, 0, 65535); #endif - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 13: SPIDER_PARAM_STR_LIST("default_group", tgt_default_groups); @@ -2510,7 +2479,7 @@ int spider_parse_connect_info( "hs_write_port", hs_write_ports, 0, 65535); #endif SPIDER_PARAM_STR_LIST("sequence_name", tgt_sequence_names); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 14: SPIDER_PARAM_LONGLONG("internal_limit", internal_limit, 0); @@ -2527,7 +2496,7 @@ int spider_parse_connect_info( SPIDER_PARAM_STR_LIST("static_link_id", static_link_ids); SPIDER_PARAM_INT_WITH_MAX("store_last_crd", store_last_crd, 0, 1); SPIDER_PARAM_INT_WITH_MAX("store_last_sts", store_last_sts, 0, 1); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 15: SPIDER_PARAM_LONGLONG("internal_offset", internal_offset, 0); @@ -2550,7 +2519,7 @@ int spider_parse_connect_info( SPIDER_PARAM_LONG_LIST_WITH_MAX("strict_group_by", strict_group_bys, 0, 1); SPIDER_PARAM_INT_WITH_MAX("error_read_mode", error_read_mode, 0, 1); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 16: SPIDER_PARAM_INT_WITH_MAX( @@ -2580,7 +2549,7 @@ int spider_parse_connect_info( #endif SPIDER_PARAM_INT_WITH_MAX( "query_cache_sync", query_cache_sync, 0, 3); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 17: SPIDER_PARAM_INT_WITH_MAX( @@ -2600,7 +2569,7 @@ int spider_parse_connect_info( SPIDER_PARAM_INT_WITH_MAX( "force_bulk_update", force_bulk_update, 0, 1); #endif - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 18: SPIDER_PARAM_INT_WITH_MAX( @@ -2613,7 +2582,7 @@ int spider_parse_connect_info( #endif SPIDER_PARAM_LONGLONG( "direct_order_limit", direct_order_limit, 0); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 19: SPIDER_PARAM_INT("init_sql_alloc_size", init_sql_alloc_size, 0); @@ -2628,7 +2597,7 @@ int spider_parse_connect_info( "load_crd_at_startup", load_crd_at_startup, 0, 1); SPIDER_PARAM_INT_WITH_MAX( "load_sts_at_startup", load_sts_at_startup, 0, 1); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 20: SPIDER_PARAM_LONGLONG_LIST_WITH_MAX( @@ -2637,12 +2606,12 @@ int spider_parse_connect_info( "delete_all_rows_type", delete_all_rows_type, 0, 1); SPIDER_PARAM_INT_WITH_MAX( "skip_parallel_search", skip_parallel_search, 0, 3); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 21: SPIDER_PARAM_LONGLONG( "semi_split_read_limit", semi_split_read_limit, 0); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 22: SPIDER_PARAM_LONG_LIST_WITH_MAX( @@ -2655,38 +2624,36 @@ int spider_parse_connect_info( "skip_default_condition", skip_default_condition, 0, 1); SPIDER_PARAM_LONGLONG( "static_mean_rec_length", static_mean_rec_length, 0); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 23: SPIDER_PARAM_INT_WITH_MAX( "internal_optimize_local", internal_optimize_local, 0, 1); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 25: SPIDER_PARAM_LONGLONG("static_records_for_status", static_records_for_status, 0); SPIDER_PARAM_NUMHINT("static_key_cardinality", static_key_cardinality, 3, (int) table_share->keys, spider_set_ll_value); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 26: SPIDER_PARAM_INT_WITH_MAX( "semi_table_lock_connection", semi_table_lock_conn, 0, 1); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; case 32: SPIDER_PARAM_LONG_LIST_WITH_MAX("monitoring_binlog_pos_at_failing", monitoring_binlog_pos_at_failing, 0, 2); - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; default: - error_num = connect_string_parse.print_param_error(); + error_num = parse.fail(true); goto error; } - - /* Verify that the remainder of the parameter value is whitespace */ - if ((error_num = connect_string_parse.has_extra_parameter_values())) - goto error; + /* Restore delim */ + *parse.end_value= parse.delim_value; } } @@ -3296,8 +3263,8 @@ int spider_parse_connect_info( if (create_table) { - for (roop_count = 0; roop_count < (int) share->all_link_count; - roop_count++) + for (int roop_count = 0; roop_count < (int) share->all_link_count; + roop_count++) { int roop_count2; for (roop_count2 = 0; roop_count2 < SPIDER_DBTON_SIZE; roop_count2++) diff --git a/storage/spider/spd_table.h b/storage/spider/spd_table.h index 6952dd3e4ea..c87f91ac08b 100644 --- a/storage/spider/spd_table.h +++ b/storage/spider/spd_table.h @@ -30,281 +30,21 @@ typedef struct st_spider_param_string_parse { - char *start_ptr; /* Pointer to the start of the parameter string */ - char *end_ptr; /* Pointer to the end of the parameter string */ - char *start_title_ptr; /* Pointer to the start of the current parameter - title */ - char *end_title_ptr; /* Pointer to the end of the current parameter - title */ - char *start_value_ptr; /* Pointer to the start of the current parameter - value */ - char *end_value_ptr; /* Pointer to the end of the current parameter - value */ - int error_num; /* Error code of the error message to print when - an error is detected */ - uint delim_title_len; /* Length of the paramater title's delimiter */ - uint delim_value_len; /* Length of the paramater value's delimiter */ - char delim_title; /* Current parameter title's delimiter character */ - char delim_value; /* Current parameter value's delimiter character */ + char *start_title; /* Pointer to the start of the current parameter + title */ + char *end_title; /* Pointer to the end of the current + parameter value */ + char *start_value; /* Pointer to the start of the current parameter + value */ + char *end_value; /* Pointer to the end of the current parameter + value */ + char delim_value; /* Current parameter value's delimiter + character, either a single or a double quote */ + int error_num; /* Error code of the error message to print when + an error is detected */ - /** - Initialize the parameter string parse information. - - @param param_string Pointer to the parameter string being parsed. - @param error_code Error code of the error message to print when - an error is detected. - */ - - inline void init(char *param_string, int error_code) - { - start_ptr = param_string; - end_ptr = start_ptr + strlen(start_ptr); - - init_param_title(); - init_param_value(); - - error_num = error_code; - } - - /** - Initialize the current parameter title. - */ - - inline void init_param_title() - { - start_title_ptr = end_title_ptr = NULL; - delim_title_len = 0; - delim_title = '\0'; - } - - /** - Save pointers to the start and end positions of the current parameter - title in the parameter string. Also save the parameter title's - delimiter character. - - @param start_value Pointer to the start position of the current - parameter title. - @param end_value Pointer to the end position of the current - parameter title. - */ - - inline void set_param_title(char *start_title, char *end_title) - { - start_title_ptr = start_title; - end_title_ptr = end_title; - - if (*start_title == '"' || - *start_title == '\'') - { - delim_title = *start_title; - - if (start_title >= start_ptr && *--start_title == '\\') - delim_title_len = 2; - else - delim_title_len = 1; - } - } - - /** - Initialize the current parameter value. - */ - - inline void init_param_value() - { - start_value_ptr = end_value_ptr = NULL; - delim_value_len = 0; - delim_value = '\0'; - } - - /** - Save pointers to the start and end positions of the current parameter - value in the parameter string. Also save the parameter value's - delimiter character. - - @param start_value Pointer to the start position of the current - parameter value. - @param end_value Pointer to the end position of the current - parameter value. - */ - - inline void set_param_value(char *start_value, char *end_value) - { - start_value_ptr = start_value--; - end_value_ptr = end_value; - - if (*start_value == '"' || - *start_value == '\'') - { - delim_value = *start_value; - - if (*--start_value == '\\') - delim_value_len = 2; - else - delim_value_len = 1; - } - } - - /** - Determine whether the current parameter in the parameter string has - extra parameter values. - - @return 0 Current parameter value in the parameter string - does not have extra parameter values. - <> 0 Error code indicating that the current parameter - value in the parameter string has extra - parameter values. - */ - - inline int has_extra_parameter_values() - { - int error_num = 0; - DBUG_ENTER("has_extra_parameter_values"); - - if (end_value_ptr) - { - /* There is a current parameter value */ - char *end_param_ptr = end_value_ptr; - - while (end_param_ptr < end_ptr && - (*end_param_ptr == ' ' || *end_param_ptr == '\r' || - *end_param_ptr == '\n' || *end_param_ptr == '\t')) - end_param_ptr++; - - if (end_param_ptr < end_ptr && *end_param_ptr != '\0') - { - /* Extra values in parameter definition */ - error_num = print_param_error(); - } - } - - DBUG_RETURN(error_num); - } - - inline int get_next_parameter_head(char *st, char **nx) - { - DBUG_ENTER("get_next_parameter_head"); - char *sq = strchr(st, '\''); - char *dq = strchr(st, '"'); - if (!sq && !dq) - { - DBUG_RETURN(print_param_error()); - } - - if (dq && (!sq || sq > dq)) - { - while (1) - { - ++dq; - if (*dq == '\\') - { - ++dq; - } - else if (*dq == '"') - { - break; - } - else if (*dq == '\0') - { - DBUG_RETURN(print_param_error()); - } - } - while (1) - { - ++dq; - if (*dq == '\0') - { - *nx = dq; - break; - } - else if (*dq == ',') - { - *dq = '\0'; - *nx = dq + 1; - break; - } - else if (*dq != ' ' && *dq != '\r' && *dq != '\n' && *dq != '\t') - { - DBUG_RETURN(print_param_error()); - } - } - } - else /* sq && (!dq || sq <= dq) */ - { - while (1) - { - ++sq; - if (*sq == '\\') - { - ++sq; - } - else if (*sq == '\'') - { - break; - } - else if (*sq == '\0') - { - DBUG_RETURN(print_param_error()); - } - } - while (1) - { - ++sq; - if (*sq == '\0') - { - *nx = sq; - break; - } - else if (*sq == ',') - { - *sq = '\0'; - *nx = sq + 1; - break; - } - else if (*sq != ' ' && *sq != '\r' && *sq != '\n' && *sq != '\t') - { - DBUG_RETURN(print_param_error()); - } - } - } - DBUG_RETURN(0); - } - - /** - Restore the current parameter's input delimiter characters in the - parameter string. They were NULLed during parameter parsing. - */ - - inline void restore_delims() - { - char *end = end_title_ptr - 1; - - switch (delim_title_len) - { - case 2: - *end++ = '\\'; - /* Fall through */ - case 1: - *end = delim_title; - } - - end = end_value_ptr - 1; - switch (delim_value_len) - { - case 2: - *end++ = '\\'; - /* Fall through */ - case 1: - *end = delim_value; - } - } - - /** - Print a parameter string error message. - - @return Error code. - */ - - int print_param_error(); + int fail(bool restore_delim); + bool locate_param_def(char*& start_param); } SPIDER_PARAM_STRING_PARSE; uchar *spider_tbl_get_key( @@ -344,19 +84,12 @@ void spider_free_tmp_share_alloc( SPIDER_SHARE *share ); -char *spider_get_string_between_quote( - char *ptr, - bool alloc, - SPIDER_PARAM_STRING_PARSE *param_string_parse = NULL -); - int spider_create_string_list( char ***string_list, uint **string_length_list, uint *list_length, char *str, - uint length, - SPIDER_PARAM_STRING_PARSE *param_string_parse + uint length ); int spider_create_long_list( @@ -365,8 +98,7 @@ int spider_create_long_list( char *str, uint length, long min_val, - long max_val, - SPIDER_PARAM_STRING_PARSE *param_string_parse + long max_val ); int spider_create_longlong_list( @@ -375,8 +107,7 @@ int spider_create_longlong_list( char *str, uint length, longlong min_val, - longlong max_val, - SPIDER_PARAM_STRING_PARSE *param_string_parse + longlong max_val ); int spider_increase_string_list(