diff options
author | Oleksandr Byelkin <sanja@mariadb.com> | 2018-06-19 14:51:50 +0200 |
---|---|---|
committer | Oleksandr Byelkin <sanja@mariadb.com> | 2018-06-19 14:51:50 +0200 |
commit | 083279f7838d45c475344d20585ead72a147a21d (patch) | |
tree | c3ff5b3f6af1c9009b35d9b2560a7073be41ce90 /sql/item_subselect.cc | |
parent | 0121d5a790983c08dabedc66e70f862e47f7c8c7 (diff) | |
parent | 6b8802e8dd5467556a024d807a1df23940b00895 (diff) | |
download | mariadb-git-083279f7838d45c475344d20585ead72a147a21d.tar.gz |
Merge commit '6b8802e8dd5467556a024d807a1df23940b00895' into bb-10.3-fix_len_decbb-10.3-fix_len_dec
Diffstat (limited to 'sql/item_subselect.cc')
-rw-r--r-- | sql/item_subselect.cc | 71 |
1 files changed, 45 insertions, 26 deletions
diff --git a/sql/item_subselect.cc b/sql/item_subselect.cc index 4280a67e356..1947a45186a 100644 --- a/sql/item_subselect.cc +++ b/sql/item_subselect.cc @@ -310,10 +310,14 @@ bool Item_subselect::fix_fields(THD *thd_param, Item **ref) if (engine->cols() > max_columns) { my_error(ER_OPERAND_COLUMNS, MYF(0), 1); - + res= TRUE; + goto end; + } + if (fix_length_and_dec()) + { + res= TRUE; goto end; } - fix_length_and_dec(); } else goto end; @@ -910,9 +914,11 @@ Item::Type Item_subselect::type() const } -void Item_subselect::fix_length_and_dec() +bool Item_subselect::fix_length_and_dec() { - engine->fix_length_and_dec(0); + if (engine->fix_length_and_dec(0)) + return TRUE; + return FALSE; } @@ -1186,18 +1192,19 @@ const Type_handler *Item_singlerow_subselect::type_handler() const return engine->type_handler(); } -void Item_singlerow_subselect::fix_length_and_dec() +bool Item_singlerow_subselect::fix_length_and_dec() { if ((max_columns= engine->cols()) == 1) { - engine->fix_length_and_dec(row= &value); + if (engine->fix_length_and_dec(row= &value)) + return TRUE; } else { if (!(row= (Item_cache**) current_thd->alloc(sizeof(Item_cache*) * - max_columns))) - return; - engine->fix_length_and_dec(row); + max_columns)) || + engine->fix_length_and_dec(row)) + return TRUE; value= *row; } unsigned_flag= value->unsigned_flag; @@ -1213,6 +1220,7 @@ void Item_singlerow_subselect::fix_length_and_dec() for (uint i= 0; i < max_columns; i++) row[i]->maybe_null= TRUE; } + return FALSE; } @@ -1497,7 +1505,7 @@ void Item_exists_subselect::init_length_and_dec() } -void Item_exists_subselect::fix_length_and_dec() +bool Item_exists_subselect::fix_length_and_dec() { DBUG_ENTER("Item_exists_subselect::fix_length_and_dec"); init_length_and_dec(); @@ -1505,14 +1513,17 @@ void Item_exists_subselect::fix_length_and_dec() We need only 1 row to determine existence (i.e. any EXISTS that is not an IN always requires LIMIT 1) */ + Item *item= new (thd->mem_root) Item_int(thd, (int32) 1); + if (!item) + DBUG_RETURN(TRUE); thd->change_item_tree(&unit->global_parameters()->select_limit, - new (thd->mem_root) Item_int(thd, (int32) 1)); + item); DBUG_PRINT("info", ("Set limit to 1")); - DBUG_VOID_RETURN; + DBUG_RETURN(FALSE); } -void Item_in_subselect::fix_length_and_dec() +bool Item_in_subselect::fix_length_and_dec() { DBUG_ENTER("Item_in_subselect::fix_length_and_dec"); init_length_and_dec(); @@ -1520,7 +1531,7 @@ void Item_in_subselect::fix_length_and_dec() Unlike Item_exists_subselect, LIMIT 1 is set later for Item_in_subselect, depending on the chosen strategy. */ - DBUG_VOID_RETURN; + DBUG_RETURN(FALSE); } @@ -3705,11 +3716,11 @@ bool subselect_single_select_engine::no_rows() } -/* - makes storage for the output values for the subquery and calcuates +/** + Makes storage for the output values for the subquery and calcuates their data and column types and their nullability. -*/ -void subselect_engine::set_row(List<Item> &item_list, Item_cache **row) +*/ +bool subselect_engine::set_row(List<Item> &item_list, Item_cache **row) { Item *sel_item; List_iterator_fast<Item> li(item_list); @@ -3722,44 +3733,51 @@ void subselect_engine::set_row(List<Item> &item_list, Item_cache **row) item->unsigned_flag= sel_item->unsigned_flag; maybe_null= sel_item->maybe_null; if (!(row[i]= sel_item->get_cache(thd))) - return; + return TRUE; row[i]->setup(thd, sel_item); //psergey-backport-timours: row[i]->store(sel_item); } if (item_list.elements > 1) set_handler(&type_handler_row); + return FALSE; } -void subselect_single_select_engine::fix_length_and_dec(Item_cache **row) +bool subselect_single_select_engine::fix_length_and_dec(Item_cache **row) { DBUG_ASSERT(row || select_lex->item_list.elements==1); - set_row(select_lex->item_list, row); + if (set_row(select_lex->item_list, row)) + return TRUE; item->collation.set(row[0]->collation); if (cols() != 1) maybe_null= 0; + return FALSE; } -void subselect_union_engine::fix_length_and_dec(Item_cache **row) +bool subselect_union_engine::fix_length_and_dec(Item_cache **row) { DBUG_ASSERT(row || unit->first_select()->item_list.elements==1); if (unit->first_select()->item_list.elements == 1) { - set_row(unit->types, row); + if (set_row(unit->types, row)) + return TRUE; item->collation.set(row[0]->collation); } else { bool maybe_null_saved= maybe_null; - set_row(unit->types, row); + if (set_row(unit->types, row)) + return TRUE; maybe_null= maybe_null_saved; } + return FALSE; } -void subselect_uniquesubquery_engine::fix_length_and_dec(Item_cache **row) +bool subselect_uniquesubquery_engine::fix_length_and_dec(Item_cache **row) { //this never should be called DBUG_ASSERT(0); + return FALSE; } int read_first_record_seq(JOIN_TAB *tab); @@ -5586,9 +5604,10 @@ void subselect_hash_sj_engine::print(String *str, enum_query_type query_type) )); } -void subselect_hash_sj_engine::fix_length_and_dec(Item_cache** row) +bool subselect_hash_sj_engine::fix_length_and_dec(Item_cache** row) { DBUG_ASSERT(FALSE); + return FALSE; } void subselect_hash_sj_engine::exclude() |