From f25a74c0b094f23e1600ed9499a81420cfab663b Mon Sep 17 00:00:00 2001 From: Monty Date: Sun, 18 Jun 2023 12:11:18 +0300 Subject: [PATCH] Fixed typo on opt_range.cc: SEL_ARG::number_of_eq_groups() It could cause wrong range estimation for GROUP BY queries that are using 'WHERE index_part >= constant'. (The function was trying to check for 'index_part = constant') Reporter: Yuty Chaikou --- mysql-test/main/explain_json.result | 6 +++--- sql/opt_range.cc | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/mysql-test/main/explain_json.result b/mysql-test/main/explain_json.result index 969e069da83..38bea4b4d6a 100644 --- a/mysql-test/main/explain_json.result +++ b/mysql-test/main/explain_json.result @@ -1375,7 +1375,7 @@ id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t1 index NULL idx_t1_1 163 NULL 128 Using where; Using index explain select count(distinct a1,a2,b) from t1 where a1 >= "" and (a2 >= 'b') and (b = 'a'); id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range idx_t1_0,idx_t1_1,idx_t1_2 idx_t1_1 147 NULL 1 Using where; Using index for group-by +1 SIMPLE t1 range idx_t1_0,idx_t1_1,idx_t1_2 idx_t1_2 147 NULL 17 Using where; Using index for group-by explain format=json select count(distinct a1,a2,b) from t1 where (a2 >= 'b') and (b = 'a'); EXPLAIN { @@ -1438,11 +1438,11 @@ EXPLAIN "table_name": "t1", "access_type": "range", "possible_keys": ["idx_t1_0", "idx_t1_1", "idx_t1_2"], - "key": "idx_t1_1", + "key": "idx_t1_2", "key_length": "147", "used_key_parts": ["a1", "a2", "b"], "loops": 1, - "rows": 1, + "rows": 17, "cost": "COST_REPLACED", "filtered": 100, "attached_condition": "t1.b = 'a' and t1.a1 >= '' and t1.a2 >= 'b'", diff --git a/sql/opt_range.cc b/sql/opt_range.cc index 4d4a61f8228..475c1b0328b 100644 --- a/sql/opt_range.cc +++ b/sql/opt_range.cc @@ -11177,7 +11177,7 @@ int SEL_ARG::number_of_eq_groups(uint group_key_parts) const cur= first(); do { - if ((cur->min_flag | cur->min_flag) & + if ((cur->min_flag | cur->max_flag) & (NO_MIN_RANGE | NO_MAX_RANGE | NEAR_MIN | NEAR_MAX | GEOM_FLAG)) return -1; if (min_value != max_value && !min_max_are_equal())