From bf086dc984d4ee87e6a7857b0f44b6c1ed033df8 Mon Sep 17 00:00:00 2001 From: Georgiy Lebedev <g.lebedev@tarantool.org> Date: Thu, 20 Apr 2023 09:59:31 +0300 Subject: [PATCH] box: add `space_by_name` and `space_index_by_name` for arbitrary strings Change original `space_by_name` to `space_by_name0` and `space_index_by_name` to `space_index_by_name0`, since they accept NULL-terminated names, and add `space_by_name` and `space_index_by_name` for arbitrary strings. Needed for #8146 NO_CHANGELOG=refactoring NO_DOC=refactoring NO_TEST=refactoring --- src/box/alter.cc | 2 +- src/box/space.h | 17 +++++++++++++++-- src/box/space_cache.c | 6 ++---- src/box/space_cache.h | 11 ++++++++++- src/box/sql/alter.c | 4 ++-- src/box/sql/build.c | 20 ++++++++++---------- src/box/sql/delete.c | 4 ++-- src/box/sql/insert.c | 2 +- src/box/sql/pragma.c | 8 ++++---- src/box/sql/tokenize.c | 2 +- 10 files changed, 48 insertions(+), 28 deletions(-) diff --git a/src/box/alter.cc b/src/box/alter.cc index 6caa02a458..29199285ec 100644 --- a/src/box/alter.cc +++ b/src/box/alter.cc @@ -1854,7 +1854,7 @@ update_view_references(struct Select *select, int update_value, */ if (sql_select_constains_cte(select, space_name)) continue; - struct space *space = space_by_name(space_name); + struct space *space = space_by_name0(space_name); if (space == NULL) { if (! suppress_error) { assert(not_found_space != NULL); diff --git a/src/box/space.h b/src/box/space.h index afcddebc5f..e8a10b52b0 100644 --- a/src/box/space.h +++ b/src/box/space.h @@ -364,20 +364,33 @@ space_index(struct space *space, uint32_t id) * * @param space Space index belongs to. * @param index_name Name of index to be found. + * @param index_name_len Length of index name. * * @retval NULL if the index is not found. */ static inline struct index * -space_index_by_name(struct space *space, const char *index_name) +space_index_by_name(struct space *space, const char *index_name, + uint32_t index_name_len) { for(uint32_t i = 0; i < space->index_count; i++) { struct index *index = space->index[i]; - if (strcmp(index_name, index->def->name) == 0) + if (strlen(index->def->name) != index_name_len) + continue; + if (strncmp(index_name, index->def->name, index_name_len) == 0) return index; } return NULL; } +/** + * `space_index_by_name` for NULL-terminated index names. + */ +static inline struct index * +space_index_by_name0(struct space *space, const char *index_name) +{ + return space_index_by_name(space, index_name, strlen(index_name)); +} + /** * Return true if the unique constraint must be checked for * the index with the given id before inserting a tuple into diff --git a/src/box/space_cache.c b/src/box/space_cache.c index 05e162ba96..e5a41478d3 100644 --- a/src/box/space_cache.c +++ b/src/box/space_cache.c @@ -58,12 +58,10 @@ space_by_id(uint32_t id) return (struct space *)mh_i32ptr_node(spaces, space)->val; } -/** Return space by its name */ struct space * -space_by_name(const char *name) +space_by_name(const char *name, uint32_t len) { - mh_int_t space = mh_strnptr_find_str(spaces_by_name, name, - strlen(name)); + mh_int_t space = mh_strnptr_find_str(spaces_by_name, name, len); if (space == mh_end(spaces_by_name)) return NULL; return (struct space *)mh_strnptr_node(spaces_by_name, space)->val; diff --git a/src/box/space_cache.h b/src/box/space_cache.h index 56d8d2e737..344f8359ec 100644 --- a/src/box/space_cache.h +++ b/src/box/space_cache.h @@ -95,7 +95,16 @@ space_by_id(uint32_t id); * @return NULL if space not found, otherwise space object. */ struct space * -space_by_name(const char *name); +space_by_name(const char *name, uint32_t len); + +/** + * `space_by_name` for NULL-terminated names. + */ +static inline struct space * +space_by_name0(const char *name) +{ + return space_by_name(name, strlen(name)); +} /** * Find minimal unused id, which is greater than cur_id. diff --git a/src/box/sql/alter.c b/src/box/sql/alter.c index f793553228..f2f76bf715 100644 --- a/src/box/sql/alter.c +++ b/src/box/sql/alter.c @@ -47,12 +47,12 @@ sql_alter_table_rename(struct Parse *parse) assert(src_tab->nSrc == 1); char *new_name = sql_name_from_token(&rename_def->new_name); /* Check that new name isn't occupied by another table. */ - if (space_by_name(new_name) != NULL) { + if (space_by_name0(new_name) != NULL) { diag_set(ClientError, ER_SPACE_EXISTS, new_name); goto tnt_error; } const char *tbl_name = src_tab->a[0].zName; - struct space *space = space_by_name(tbl_name); + struct space *space = space_by_name0(tbl_name); if (space == NULL) { diag_set(ClientError, ER_NO_SUCH_SPACE, tbl_name); goto tnt_error; diff --git a/src/box/sql/build.c b/src/box/sql/build.c index f0e7041a8d..945aa38d60 100644 --- a/src/box/sql/build.c +++ b/src/box/sql/build.c @@ -338,7 +338,7 @@ sql_create_column_start(struct Parse *parse) if (is_alter) { const char *space_name = alter_entity_def->entity_name->a[0].zName; - space = space_by_name(space_name); + space = space_by_name0(space_name); if (space == NULL) { diag_set(ClientError, ER_NO_SUCH_SPACE, space_name); goto tnt_error; @@ -760,7 +760,7 @@ sql_create_check_contraint(struct Parse *parser, bool is_field_ck) ck_def->name[name_len] = '\0'; if (is_alter_add_constr) { const char *space_name = alter_def->entity_name->a[0].zName; - struct space *space = space_by_name(space_name); + struct space *space = space_by_name0(space_name); if (space == NULL) { diag_set(ClientError, ER_NO_SUCH_SPACE, space_name); parser->is_aborted = true; @@ -1254,7 +1254,7 @@ vdbe_emit_create_constraints(struct Parse *parse, int reg_space_id) */ if (is_alter) { space = parse->create_column_def.space; - i = space_by_name(space->def->name)->index_count; + i = space_by_name0(space->def->name)->index_count; } assert(space != NULL); for (; i < space->index_count; ++i) { @@ -1758,7 +1758,7 @@ sql_drop_table(struct Parse *parse_context) assert(!parse_context->is_aborted); assert(table_name_list->nSrc == 1); const char *space_name = table_name_list->a[0].zName; - struct space *space = space_by_name(space_name); + struct space *space = space_by_name0(space_name); if (space == NULL) { if (!drop_def.if_exist) { diag_set(ClientError, ER_NO_SUCH_SPACE, space_name); @@ -1919,7 +1919,7 @@ sql_create_foreign_key(struct Parse *parse_context) assert(constraint_name != NULL); if (is_alter_add_constr) { const char *child_name = alter_def->entity_name->a[0].zName; - child_space = space_by_name(child_name); + child_space = space_by_name0(child_name); if (child_space == NULL) { diag_set(ClientError, ER_NO_SUCH_SPACE, child_name); goto tnt_error; @@ -1955,7 +1955,7 @@ sql_create_foreign_key(struct Parse *parse_context) */ is_self_referenced = !is_alter_add_constr && strcmp(parent_name, space->def->name) == 0; - struct space *parent_space = space_by_name(parent_name); + struct space *parent_space = space_by_name0(parent_name); if (parent_space == NULL && !is_self_referenced) { diag_set(ClientError, ER_NO_SUCH_SPACE, parent_name); goto tnt_error; @@ -2103,7 +2103,7 @@ sql_drop_constraint(struct Parse *parse_context) assert(drop_def->base.alter_action == ALTER_ACTION_DROP); const char *table_name = drop_def->base.entity_name->a[0].zName; assert(table_name != NULL); - struct space *space = space_by_name(table_name); + struct space *space = space_by_name0(table_name); if (space == NULL) { diag_set(ClientError, ER_NO_SUCH_SPACE, table_name); parse_context->is_aborted = true; @@ -2426,7 +2426,7 @@ sql_create_index(struct Parse *parse) { if (tbl_name != NULL) { assert(token.n > 0 && token.z != NULL); const char *name = tbl_name->a[0].zName; - space = space_by_name(name); + space = space_by_name0(name); if (space == NULL) { if (! create_entity_def->if_not_exist) { diag_set(ClientError, ER_NO_SUCH_SPACE, name); @@ -2474,7 +2474,7 @@ sql_create_index(struct Parse *parse) { if (!is_create_table_or_add_col) { assert(token.z != NULL); name = sql_name_from_token(&token); - if (space_index_by_name(space, name) != NULL) { + if (space_index_by_name0(space, name) != NULL) { if (! create_entity_def->if_not_exist) { diag_set(ClientError, ER_INDEX_EXISTS_IN_SPACE, name, def->name); @@ -2739,7 +2739,7 @@ sql_drop_index(struct Parse *parse_context) char *table_name = table_list->a[0].zName; char *index_name = NULL; sqlVdbeCountChanges(v); - struct space *space = space_by_name(table_name); + struct space *space = space_by_name0(table_name); bool if_exists = drop_def->if_exist; if (space == NULL) { if (!if_exists) { diff --git a/src/box/sql/delete.c b/src/box/sql/delete.c index 1015616f9a..9ac7ec20db 100644 --- a/src/box/sql/delete.c +++ b/src/box/sql/delete.c @@ -39,7 +39,7 @@ sql_lookup_space(struct Parse *parse, struct SrcList_item *space_name) { assert(space_name != NULL); assert(space_name->space == NULL); - struct space *space = space_by_name(space_name->zName); + struct space *space = space_by_name0(space_name->zName); if (space == NULL) { diag_set(ClientError, ER_NO_SUCH_SPACE, space_name->zName); parse->is_aborted = true; @@ -87,7 +87,7 @@ sql_table_truncate(struct Parse *parse, struct SrcList *tab_list) struct Vdbe *v = sqlGetVdbe(parse); const char *tab_name = tab_list->a->zName; - struct space *space = space_by_name(tab_name); + struct space *space = space_by_name0(tab_name); if (space == NULL) { diag_set(ClientError, ER_NO_SUCH_SPACE, tab_name); goto tarantool_error; diff --git a/src/box/sql/insert.c b/src/box/sql/insert.c index 52ee831f7c..e94b2d8a63 100644 --- a/src/box/sql/insert.c +++ b/src/box/sql/insert.c @@ -1071,7 +1071,7 @@ xferOptimization(Parse * pParse, /* Parser context */ * we have to check the semantics. */ pItem = pSelect->pSrc->a; - struct space *src = space_by_name(pItem->zName); + struct space *src = space_by_name0(pItem->zName); /* FROM clause does not contain a real table. */ if (src == NULL) return 0; diff --git a/src/box/sql/pragma.c b/src/box/sql/pragma.c index 47662d0f32..c00cdc3080 100644 --- a/src/box/sql/pragma.c +++ b/src/box/sql/pragma.c @@ -100,7 +100,7 @@ sql_pragma_table_info(struct Parse *parse, const char *tbl_name) { if (tbl_name == NULL) return; - struct space *space = space_by_name(tbl_name); + struct space *space = space_by_name0(tbl_name); if (space == NULL) return; struct index *pk = space_index(space, 0); @@ -187,10 +187,10 @@ sql_pragma_index_info(struct Parse *parse, { if (idx_name == NULL || tbl_name == NULL) return; - struct space *space = space_by_name(tbl_name); + struct space *space = space_by_name0(tbl_name); if (space == NULL) return; - struct index *idx = space_index_by_name(space, idx_name); + struct index *idx = space_index_by_name0(space, idx_name); if (idx == NULL) return; parse->nMem = 6; @@ -267,7 +267,7 @@ sql_pragma_index_list(struct Parse *parse, const char *tbl_name) { if (tbl_name == NULL) return; - struct space *space = space_by_name(tbl_name); + struct space *space = space_by_name0(tbl_name); if (space == NULL) return; parse->nMem = 3; diff --git a/src/box/sql/tokenize.c b/src/box/sql/tokenize.c index 415d3e6a4c..101dc87764 100644 --- a/src/box/sql/tokenize.c +++ b/src/box/sql/tokenize.c @@ -456,7 +456,7 @@ parser_space_delete(struct space *space) if (space == NULL) return; assert(space->def->opts.is_ephemeral); - struct space *altered_space = space_by_name(space->def->name); + struct space *altered_space = space_by_name0(space->def->name); uint32_t i = 0; /* * Don't delete already existing defs and start from new -- GitLab