diff options
author | unknown <bell@sanja.is.com.ua> | 2005-08-19 08:55:38 +0300 |
---|---|---|
committer | unknown <bell@sanja.is.com.ua> | 2005-08-19 08:55:38 +0300 |
commit | bba824eb857088269a22fdd408121a5cb78918af (patch) | |
tree | b37d2b55a860f05f612858b544e4cc1840fab561 | |
parent | adf56c8c8401ca6040e9f1d6dfb2007ab1bb4b67 (diff) | |
parent | 341f82212642e3be70f9237bb9604ab725e6033f (diff) | |
download | mariadb-git-bba824eb857088269a22fdd408121a5cb78918af.tar.gz |
Merge sanja.is.com.ua:/home/bell/mysql/bk/mysql-5.0
into sanja.is.com.ua:/home/bell/mysql/bk/work-bug2-5.0
sql/item_cmpfunc.cc:
Auto merged
-rw-r--r-- | mysql-test/r/row.result | 8 | ||||
-rw-r--r-- | mysql-test/t/row.test | 6 | ||||
-rw-r--r-- | sql/item_cmpfunc.cc | 26 | ||||
-rw-r--r-- | sql/item_cmpfunc.h | 4 |
4 files changed, 38 insertions, 6 deletions
diff --git a/mysql-test/r/row.result b/mysql-test/r/row.result index f7f7e3e8429..1762587415d 100644 --- a/mysql-test/r/row.result +++ b/mysql-test/r/row.result @@ -58,7 +58,7 @@ SELECT (1,2,3)=(1,NULL,3); NULL SELECT (1,2,3)=(1,NULL,0); (1,2,3)=(1,NULL,0) -NULL +0 SELECT ROW(1,2,3)=ROW(1,2,3); ROW(1,2,3)=ROW(1,2,3) 1 @@ -175,3 +175,9 @@ ROW(2,10) <=> ROW(3,4) SELECT ROW(NULL,10) <=> ROW(3,NULL); ROW(NULL,10) <=> ROW(3,NULL) 0 +SELECT ROW(1,1,1) = ROW(1,1,1) as `1`, ROW(1,1,1) = ROW(1,2,1) as `0`, ROW(1,NULL,1) = ROW(2,2,1) as `0`, ROW(1,NULL,1) = ROW(1,2,2) as `0`, ROW(1,NULL,1) = ROW(1,2,1) as `null` ; +1 0 0 0 null +1 0 0 0 NULL +select row(NULL,1)=(2,0); +row(NULL,1)=(2,0) +0 diff --git a/mysql-test/t/row.test b/mysql-test/t/row.test index 4becef1c2b7..6301cc0f584 100644 --- a/mysql-test/t/row.test +++ b/mysql-test/t/row.test @@ -86,3 +86,9 @@ SELECT ROW(2,10) <=> ROW(3,4); SELECT ROW(NULL,10) <=> ROW(3,NULL); # End of 4.1 tests + +# +# Correct NULL handling in row comporison (BUG#12509) +# +SELECT ROW(1,1,1) = ROW(1,1,1) as `1`, ROW(1,1,1) = ROW(1,2,1) as `0`, ROW(1,NULL,1) = ROW(2,2,1) as `0`, ROW(1,NULL,1) = ROW(1,2,2) as `0`, ROW(1,NULL,1) = ROW(1,2,1) as `null` ; +select row(NULL,1)=(2,0); diff --git a/sql/item_cmpfunc.cc b/sql/item_cmpfunc.cc index b513fb26bdb..1bae5f1c9af 100644 --- a/sql/item_cmpfunc.cc +++ b/sql/item_cmpfunc.cc @@ -614,17 +614,35 @@ int Arg_comparator::compare_e_int_diff_signedness() int Arg_comparator::compare_row() { int res= 0; + bool was_null= 0; (*a)->bring_value(); (*b)->bring_value(); uint n= (*a)->cols(); for (uint i= 0; i<n; i++) { - if ((res= comparators[i].compare())) - return res; + res= comparators[i].compare(); if (owner->null_value) - return -1; + { + // NULL was compared + if (owner->abort_on_null) + return -1; // We do not need correct NULL returning + was_null= 1; + owner->null_value= 0; + res= 0; // continue comparison (maybe we will meet explicit difference) + } + if (res) + return res; } - return res; + if (was_null) + { + /* + There was NULL(s) in comparison in some parts, but there was not + explicit difference in other parts, so we have to return NULL + */ + owner->null_value= 1; + return -1; + } + return 0; } int Arg_comparator::compare_e_row() diff --git a/sql/item_cmpfunc.h b/sql/item_cmpfunc.h index a4165407159..6b0cf3e80c2 100644 --- a/sql/item_cmpfunc.h +++ b/sql/item_cmpfunc.h @@ -193,10 +193,11 @@ class Item_bool_func2 :public Item_int_func protected: Arg_comparator cmp; String tmp_value1,tmp_value2; + bool abort_on_null; public: Item_bool_func2(Item *a,Item *b) - :Item_int_func(a,b), cmp(tmp_arg, tmp_arg+1) {} + :Item_int_func(a,b), cmp(tmp_arg, tmp_arg+1), abort_on_null(FALSE) {} void fix_length_and_dec(); void set_cmp_func() { @@ -210,6 +211,7 @@ public: bool is_bool_func() { return 1; } CHARSET_INFO *compare_collation() { return cmp.cmp_collation.collation; } uint decimal_precision() const { return 1; } + void top_level_item() { abort_on_null=1; } friend class Arg_comparator; }; |