mirror of
https://github.com/MariaDB/server.git
synced 2025-07-29 05:21:33 +03:00
MDEV-36716 A case expression with ROW arguments in THEN crashes
The patch for SYS_REFCURSOR (MDEV-20034) overrode these methods: - Item_func_case_searched::check_arguments() - Item_func_if::check_arguments() to validate WHEN-style arguments (e.g. args[0] in case of IF) for being able to return a boolean result. However, this unintentionally removed the test for the THEN-style arguments that they are not expressions of the ROW data type. This led to a crash inside Type_handler_hybrid_field_type::aggregate_for_result on a DBUG_ASSERT that arguments are not of the ROW data type. Fix: The fix restores blocking ROW expressions in the not supported cases, to avoid the DBUG_ASSERT and to raise an SQL error instead. Blocking ROW_RESULT expressions is done per Item_func_case_expression descendant individually, instead of blocking any ROW_RESULT arguments at the Item_func_case_expression level. The fix is done taking into account the upcoming patch for associative arrays (MDEV-34319). It should be possible to pass associative array expressions into some hybrid type functions, where ROW type expressions are not possible. As a side effect, some lecagy ER_OPERAND_COLUMNS changed to a newer ER_ILLEGAL_PARAMETER_DATA_TYPE_FOR_OPERATION Changes in the top affected class Item_func_case_expression: - item_func.h: Overriding Item_func_case_expression::check_arguments() to return false, without checking any arguments. Descendant validate arguments in a various different ways. No needs to block all non-scalar data type at this level, to prevent disallowing associative arrays. Changes in descendants: - item_cmpfunc.cc: Adding a test in Item_func_case_simple::aggregate_switch_and_when_arguments() preventing passing ROW_RESULT expression in predicant and WHEN in a simple CASE: CASE predicant WHEN when1 THEN .. WHEN when2 THEN .. END; This is not supported yet. Should be preferrably fixed before MDEV-34319. - item_cmpfunc.cc: Calling args[0]->type_handler()->Item_hybrid_func_fix_attributes() from Item_func_nullif::fix_length_and_dec(). This prevents a ROW expression to be passed to args[0] of NULLIF(). But will allow to pass associative arrays. args[1] is still only checked to be comparable with args[0]. No needs to add additional tests for it. - item_cmpfunc.h: Adding a call for Item_hybrid_func_fix_attributes() in Item_func_case_abbreviation2::cache_type_info(). This prevents calling the descendant functions with a ROW expression in combination with an explicit NULL in the THEN-style arguments (but will allow to pass associative arrays): IFNULL(row_expression, NULL) IFNULL(NULL, row_expression) IF(switch, row_expression, NULL) IF(switch, NULL, row_expression) NVL2(switch, row_expression, NULL) NVL2(switch, NULL, row_expression) Adding a THD* argument into involved methods. - item_cmpfunc.h: Overriding Item_func_case_abbreviation2_switch::check_arguments() to check that the first argument in IF() and NVL2() can return bool. Removing Item_func_if::check_arguments(), as it become redundant. - sql_type.cc: Fixing sql_type.cc not to disallow items[0] with ROW_RESULT. This makes it call Item_hybrid_func_fix_attributes() at the end, which block ROW arguments into THEN-style arguments of hybrid functions. But this will allow to pass Type_handler_assoc_array expressions. - sql_type.cc: Changing Type_handler_row::Item_hybrid_func_fix_attributes to raise the ER_ILLEGAL_PARAMETER_DATA_TYPE_FOR_OPERATION error instead of the DBUG_ASSERT.
This commit is contained in:
@ -4937,11 +4937,7 @@ public:
|
||||
Type_handler_hybrid_field_type *,
|
||||
Type_all_attributes *atrr,
|
||||
Item **items, uint nitems)
|
||||
const override
|
||||
{
|
||||
MY_ASSERT_UNREACHABLE();
|
||||
return true;
|
||||
}
|
||||
const override;
|
||||
bool Item_sum_hybrid_fix_length_and_dec(Item_sum_hybrid *) const override
|
||||
{
|
||||
MY_ASSERT_UNREACHABLE();
|
||||
|
Reference in New Issue
Block a user