From 97c9fb4deca20743301fafa69290e59267b9ec70 Mon Sep 17 00:00:00 2001 From: adofsauron Date: Sat, 22 Oct 2022 22:35:29 +0800 Subject: [PATCH] fix(tianmu): Fixed tianmu syntax compatibility issue when continuous equivalent predicates are eliminated (#733) The root cause is that the tianmu syntax tree conversion cannot support continuous null-value elimination, and the cleaned equal-value elimination items are retained to be compatible with the tianmu execution plan --- mysql-test/suite/tianmu/r/issue301.result | 46 ++++++++++++++++++++++- mysql-test/suite/tianmu/t/issue301.test | 13 +++++++ sql/sql_optimizer.cc | 14 ++----- 3 files changed, 61 insertions(+), 12 deletions(-) diff --git a/mysql-test/suite/tianmu/r/issue301.result b/mysql-test/suite/tianmu/r/issue301.result index 706a93598..c4a79f56a 100644 --- a/mysql-test/suite/tianmu/r/issue301.result +++ b/mysql-test/suite/tianmu/r/issue301.result @@ -6,8 +6,6 @@ a b 1 1 1 2 1 3 -Warnings: -Note 1105 Query syntax not implemented in Tianmu, executed by MySQL engine. select * from t1 where b>2 or 1=2; a b 1 3 @@ -79,6 +77,45 @@ a b 1 1 1 2 1 3 +select * from t1 where ( 1 = 1 and 1 = 1 ) or b>2; +a b +1 1 +1 2 +1 3 +select * from t1 where ( 1 = 1 and 1 != 1 ) or b>2; +a b +1 3 +select * from t1 where ( 1 = 1 and 1 = 1 ) and b>2; +a b +1 3 +select * from t1 where ( 1 = 1 and 1 != 1 ) and b>2; +a b +select * from t1 where ( 1 = 1 and 1 = 1 and 1 = 1 ) or b>2; +a b +1 1 +1 2 +1 3 +select * from t1 where ( 1 = 1 and 1 = 1 and 1 != 1 ) or b>2; +a b +1 3 +select * from t1 where ( a = a and 1 = 1 and 1 = 1 ) or b>2; +a b +1 1 +1 2 +1 3 +select * from t1 where ( a = a and 1 = 1 and 1 != 1 ) or b>2; +a b +1 3 +select * from t1 where ( 1 = 1 and 1 = 1 and 1 = 1 ) and b>2; +a b +1 3 +select * from t1 where ( 1 = 1 and 1 = 1 and 1 != 1 ) and b>2; +a b +select * from t1 where ( a = a and 1 = 1 and 1 = 1 ) and b>2; +a b +1 3 +select * from t1 where ( a = a and 1 = 1 and 1 != 1 ) and b>2; +a b select * from t1 where ((((1=1) or (3=3)) and (3=3)) or ((1=100) and (5=a))); a b 1 1 @@ -98,6 +135,11 @@ a b 1 3 select * from t1 where ((((1=2) or (3=3)) and (3=1)) or ((1>1) and (5=a))); a b +select * from t1 where ((((1=2) or (3=3)) and (3!=1)) or ((1>1) and (5=a))); +a b +1 1 +1 2 +1 3 drop table t1; CREATE TABLE t1 (a INT NOT NULL, b INT)engine=tianmu; INSERT INTO t1 VALUES (1, 1); diff --git a/mysql-test/suite/tianmu/t/issue301.test b/mysql-test/suite/tianmu/t/issue301.test index 88b468157..3ba80de0c 100644 --- a/mysql-test/suite/tianmu/t/issue301.test +++ b/mysql-test/suite/tianmu/t/issue301.test @@ -20,11 +20,24 @@ select * from t1 where ( a = b ) or b>2; select * from t1 where ( a != b ) or b>2; select * from t1 where ( a is null ) or b>2; select * from t1 where ( null is null ) or b>2; +select * from t1 where ( 1 = 1 and 1 = 1 ) or b>2; +select * from t1 where ( 1 = 1 and 1 != 1 ) or b>2; +select * from t1 where ( 1 = 1 and 1 = 1 ) and b>2; +select * from t1 where ( 1 = 1 and 1 != 1 ) and b>2; +select * from t1 where ( 1 = 1 and 1 = 1 and 1 = 1 ) or b>2; +select * from t1 where ( 1 = 1 and 1 = 1 and 1 != 1 ) or b>2; +select * from t1 where ( a = a and 1 = 1 and 1 = 1 ) or b>2; +select * from t1 where ( a = a and 1 = 1 and 1 != 1 ) or b>2; +select * from t1 where ( 1 = 1 and 1 = 1 and 1 = 1 ) and b>2; +select * from t1 where ( 1 = 1 and 1 = 1 and 1 != 1 ) and b>2; +select * from t1 where ( a = a and 1 = 1 and 1 = 1 ) and b>2; +select * from t1 where ( a = a and 1 = 1 and 1 != 1 ) and b>2; select * from t1 where ((((1=1) or (3=3)) and (3=3)) or ((1=100) and (5=a))); select * from t1 where ((((1=1) or (3=3)) and (3=4)) or ((1=100) and (5=a))); select * from t1 where ((((1=2) or (3=3)) and (3=3)) or ((1=100) and (5=a))); select * from t1 where ((((1>2) or (3=3)) and (3=3)) or ((1=1) and (5=a))); select * from t1 where ((((1=2) or (3=3)) and (3=1)) or ((1>1) and (5=a))); +select * from t1 where ((((1=2) or (3=3)) and (3!=1)) or ((1>1) and (5=a))); drop table t1; diff --git a/sql/sql_optimizer.cc b/sql/sql_optimizer.cc index ef3bdcfa5..ab11189e3 100644 --- a/sql/sql_optimizer.cc +++ b/sql/sql_optimizer.cc @@ -10162,15 +10162,13 @@ static bool internal_remove_eq_conds(THD *thd, Item *cond, Item_cond *const item_cond= down_cast(cond); const auto& item_func_type = item_cond->functype(); const bool and_level = Item_func::COND_AND_FUNC == item_func_type; + const bool or_level = Item_func::COND_OR_FUNC == item_func_type; List_iterator li(*item_cond->argument_list()); bool should_fix_fields= false; *cond_value=Item::COND_UNDEF; Item *item; - bool is_cond_or = Item_func::Functype::COND_OR_FUNC == item_func_type; - bool is_cond_and = Item_func::Functype::COND_AND_FUNC == item_func_type; - while ((item=li++)) { Item *new_item; @@ -10294,17 +10292,13 @@ static bool internal_remove_eq_conds(THD *thd, Item *cond, if (cond_replace) { - if ((is_cond_or && cond_value_equivalent) - || (is_cond_and && (!cond_value_equivalent))) + if ((or_level && cond_value_equivalent) + || (and_level && (!cond_value_equivalent))) { - *cond_value = tmp_cond_value; + *cond_value = Item::COND_OK; *retcond = NULL; return false; } - else - { - li.remove(); - } } } else if (item != new_item)