mirror of
https://github.com/MariaDB/server.git
synced 2025-07-30 16:24:05 +03:00
Fix for MDEV-4836 fix: take into account situation where "notnull_col IS NULL" is not
a direct child of the WHERE clause item, but rather is embedded inside Item_cond_and or Item_cond_or.
This commit is contained in:
@ -2150,6 +2150,14 @@ id d i
|
|||||||
1 0000-00-00 NULL
|
1 0000-00-00 NULL
|
||||||
2 0000-00-00 NULL
|
2 0000-00-00 NULL
|
||||||
DROP TABLE t1,t2;
|
DROP TABLE t1,t2;
|
||||||
|
CREATE TABLE t1 (i1 INT, d1 DATE NOT NULL);
|
||||||
|
INSERT INTO t1 VALUES (1,'2012-12-21'),(2,'0000-00-00');
|
||||||
|
CREATE TABLE t2 (i2 INT, j2 INT);
|
||||||
|
INSERT INTO t2 VALUES (1,10),(2,20);
|
||||||
|
SELECT * FROM t1 LEFT JOIN t2 ON i1 = j2 WHERE d1 IS NULL AND 1 OR i1 = i2;
|
||||||
|
i1 d1 i2 j2
|
||||||
|
2 0000-00-00 NULL NULL
|
||||||
|
DROP TABLE t1,t2;
|
||||||
#
|
#
|
||||||
# Bug mdev-4942: LEFT JOIN with conjunctive
|
# Bug mdev-4942: LEFT JOIN with conjunctive
|
||||||
# <non-nullable datetime field> IS NULL in WHERE
|
# <non-nullable datetime field> IS NULL in WHERE
|
||||||
|
@ -2161,6 +2161,14 @@ id d i
|
|||||||
1 0000-00-00 NULL
|
1 0000-00-00 NULL
|
||||||
2 0000-00-00 NULL
|
2 0000-00-00 NULL
|
||||||
DROP TABLE t1,t2;
|
DROP TABLE t1,t2;
|
||||||
|
CREATE TABLE t1 (i1 INT, d1 DATE NOT NULL);
|
||||||
|
INSERT INTO t1 VALUES (1,'2012-12-21'),(2,'0000-00-00');
|
||||||
|
CREATE TABLE t2 (i2 INT, j2 INT);
|
||||||
|
INSERT INTO t2 VALUES (1,10),(2,20);
|
||||||
|
SELECT * FROM t1 LEFT JOIN t2 ON i1 = j2 WHERE d1 IS NULL AND 1 OR i1 = i2;
|
||||||
|
i1 d1 i2 j2
|
||||||
|
2 0000-00-00 NULL NULL
|
||||||
|
DROP TABLE t1,t2;
|
||||||
#
|
#
|
||||||
# Bug mdev-4942: LEFT JOIN with conjunctive
|
# Bug mdev-4942: LEFT JOIN with conjunctive
|
||||||
# <non-nullable datetime field> IS NULL in WHERE
|
# <non-nullable datetime field> IS NULL in WHERE
|
||||||
|
@ -1696,6 +1696,17 @@ CREATE TABLE t2 (i INT);
|
|||||||
SELECT * FROM t1 LEFT JOIN t2 ON (id=i) WHERE NULL OR d IS NULL;
|
SELECT * FROM t1 LEFT JOIN t2 ON (id=i) WHERE NULL OR d IS NULL;
|
||||||
DROP TABLE t1,t2;
|
DROP TABLE t1,t2;
|
||||||
|
|
||||||
|
|
||||||
|
CREATE TABLE t1 (i1 INT, d1 DATE NOT NULL);
|
||||||
|
INSERT INTO t1 VALUES (1,'2012-12-21'),(2,'0000-00-00');
|
||||||
|
|
||||||
|
CREATE TABLE t2 (i2 INT, j2 INT);
|
||||||
|
INSERT INTO t2 VALUES (1,10),(2,20);
|
||||||
|
|
||||||
|
SELECT * FROM t1 LEFT JOIN t2 ON i1 = j2 WHERE d1 IS NULL AND 1 OR i1 = i2;
|
||||||
|
DROP TABLE t1,t2;
|
||||||
|
|
||||||
|
|
||||||
--echo #
|
--echo #
|
||||||
--echo # Bug mdev-4942: LEFT JOIN with conjunctive
|
--echo # Bug mdev-4942: LEFT JOIN with conjunctive
|
||||||
--echo # <non-nullable datetime field> IS NULL in WHERE
|
--echo # <non-nullable datetime field> IS NULL in WHERE
|
||||||
|
@ -4302,7 +4302,7 @@ Item_cond::fix_fields(THD *thd, Item **ref)
|
|||||||
used_tables_cache|= item->used_tables();
|
used_tables_cache|= item->used_tables();
|
||||||
if (item->const_item())
|
if (item->const_item())
|
||||||
{
|
{
|
||||||
if (!item->is_expensive() && !cond_is_datetime_is_null(item) &&
|
if (!item->is_expensive() && !cond_has_datetime_is_null(item) &&
|
||||||
item->val_int() == 0)
|
item->val_int() == 0)
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
@ -4355,7 +4355,7 @@ Item_cond::eval_not_null_tables(uchar *opt_arg)
|
|||||||
table_map tmp_table_map;
|
table_map tmp_table_map;
|
||||||
if (item->const_item())
|
if (item->const_item())
|
||||||
{
|
{
|
||||||
if (!item->is_expensive() && !cond_is_datetime_is_null(item) &&
|
if (!item->is_expensive() && !cond_has_datetime_is_null(item) &&
|
||||||
item->val_int() == 0)
|
item->val_int() == 0)
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
|
@ -13526,6 +13526,28 @@ void propagate_new_equalities(THD *thd, Item *cond,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
Check if cond_is_datetime_is_null() is true for the condition cond, or
|
||||||
|
for any of its AND/OR-children
|
||||||
|
*/
|
||||||
|
bool cond_has_datetime_is_null(Item *cond)
|
||||||
|
{
|
||||||
|
if (cond_is_datetime_is_null(cond))
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if (cond->type() == Item::COND_ITEM)
|
||||||
|
{
|
||||||
|
List<Item> *cond_arg_list= ((Item_cond*) cond)->argument_list();
|
||||||
|
List_iterator<Item> li(*cond_arg_list);
|
||||||
|
Item *item;
|
||||||
|
while ((item= li++))
|
||||||
|
{
|
||||||
|
if (cond_has_datetime_is_null(item))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
Check if passed condtition has for of
|
Check if passed condtition has for of
|
||||||
|
@ -1796,6 +1796,7 @@ bool const_expression_in_where(COND *cond, Item *comp_item,
|
|||||||
Field *comp_field= NULL,
|
Field *comp_field= NULL,
|
||||||
Item **const_item= NULL);
|
Item **const_item= NULL);
|
||||||
bool cond_is_datetime_is_null(Item *cond);
|
bool cond_is_datetime_is_null(Item *cond);
|
||||||
|
bool cond_has_datetime_is_null(Item *cond);
|
||||||
|
|
||||||
/* Table elimination entry point function */
|
/* Table elimination entry point function */
|
||||||
void eliminate_tables(JOIN *join);
|
void eliminate_tables(JOIN *join);
|
||||||
|
Reference in New Issue
Block a user