From: drh Date: Wed, 6 Mar 2013 01:55:27 +0000 (+0000) Subject: Fix a bug (ticket [fc7bd6358f59]) that caused incorrect query results in X-Git-Tag: version-3.7.16~13 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=459f63e7edb1d04af7f70bb9c898929e0a188101;p=thirdparty%2Fsqlite.git Fix a bug (ticket [fc7bd6358f59]) that caused incorrect query results in three way queries that involved comparing INTEGER and TEXT columns for equality. FossilOrigin-Name: 7097241c1220ada318f8eda938c3e3430b94a606 --- diff --git a/manifest b/manifest index 4aae4dfca5..aacba4cf11 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\sthe\sSQLITE_READONLY_ROLLBACK\sextended\serror\scode.\nDo\snot\stry\sto\sset\sthe\spermissions\son\sjournal\sor\swal\sfiles\sexcept\sif\sthe\nfilesize\sis\sinitially\szero\s(indicating\sthat\sit\sis\sa\snew\sfile.) -D 2013-03-06T01:48:20.423 +C Fix\sa\sbug\s(ticket\s[fc7bd6358f59])\sthat\scaused\sincorrect\squery\sresults\sin\nthree\sway\squeries\sthat\sinvolved\scomparing\sINTEGER\sand\sTEXT\scolumns\sfor\nequality. +D 2013-03-06T01:55:27.319 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 9a804abbd3cae82d196e4d33aba13239e32522a5 F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -252,7 +252,7 @@ F src/vtab.c b05e5f1f4902461ba9f5fc49bb7eb7c3a0741a83 F src/wal.c f5c7b5027d0ed0e9bc9afeb4a3a8dfea762ec7d2 F src/wal.h 29c197540b19044e6cd73487017e5e47a1d3dac6 F src/walker.c 3d75ba73de15e0f8cd0737643badbeb0e002f07b -F src/where.c 43e05406f0e05960a62d4719ed77f551f8204d3f +F src/where.c 8b7690cae8700b385d8a53a39387cf8054d8cc47 F test/8_3_names.test 631ea964a3edb091cf73c3b540f6bcfdb36ce823 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 F test/aggnested.test 45c0201e28045ad38a530b5a144b73cd4aa2cfd6 @@ -809,6 +809,7 @@ F test/tkt-f7b4edec.test d998a08ff2b18b7f62edce8e3044317c45efe6c7 F test/tkt-f973c7ac31.test 1da0ed15ec2c7749fb5ce2828cd69d07153ad9f4 F test/tkt-fa7bf5ec.test 9102dfea58aa371d78969da735f9392c57e2e035 F test/tkt-fc62af4523.test 72825d3febdedcd5593a27989fc05accdbfc2bb4 +F test/tkt-fc7bd6358f.test 634bb4af7d661e82d6b61b80c86727bad698e08f F test/tkt1435.test f8c52c41de6e5ca02f1845f3a46e18e25cadac00 F test/tkt1443.test bacc311da5c96a227bf8c167e77a30c99f8e8368 F test/tkt1444.test a9d72f9e942708bd82dde6c707da61c489e213e9 @@ -1036,7 +1037,7 @@ F tool/vdbe-compress.tcl f12c884766bd14277f4fcedcae07078011717381 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh fbc018d67fd7395f440c28f33ef0f94420226381 F tool/win/sqlite.vsix 97894c2790eda7b5bce3cc79cb2a8ec2fde9b3ac -P 717863fca6d58828bf9321bc8b169e385ad4263f 4f5f3aebe81c3cbe539db3e33ec38fa3de47e90b -R 4624808bc8666139dd43b7c21e0d98ea +P ce4ac66a4b623a3cee1a63089dd5ba8341244f1e +R d68087991aff1a0f42c82b57cc68e943 U drh -Z 5a1f66c8d1d16d93a8aa4820fbcfcadc +Z 8c08911ad7848ca72da641a08c68b6f0 diff --git a/manifest.uuid b/manifest.uuid index 1a841a4e80..e12fd1d206 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -ce4ac66a4b623a3cee1a63089dd5ba8341244f1e \ No newline at end of file +7097241c1220ada318f8eda938c3e3430b94a606 \ No newline at end of file diff --git a/src/where.c b/src/where.c index 3db76b5339..aa81dabd47 100644 --- a/src/where.c +++ b/src/where.c @@ -643,9 +643,8 @@ static u16 operatorMask(int op){ ** then try for the one with no dependencies on - in other words where ** is a constant expression of some kind. Only return entries of ** the form "X Y" where Y is a column in another table if no terms of -** the form "X " exist. Other than this priority, if there -** are two or more terms that match, then the choice of which term to return -** is arbitrary. +** the form "X " exist. If no terms with a constant RHS +** exist, try to return a term that does not use WO_EQUIV. */ static WhereTerm *findTerm( WhereClause *pWC, /* The WHERE clause to be searched */ @@ -704,8 +703,12 @@ static WhereTerm *findTerm( continue; } } - pResult = pTerm; - if( pTerm->prereqRight==0 ) goto findTerm_success; + if( pTerm->prereqRight==0 ){ + pResult = pTerm; + goto findTerm_success; + }else if( pResult==0 ){ + pResult = pTerm; + } } if( (pTerm->eOperator & WO_EQUIV)!=0 && nEquivaddrNxt; sqlite3VdbeAddOp2(v, OP_MustBeInt, iRowidReg, addrNxt); sqlite3VdbeAddOp3(v, OP_NotExists, iCur, addrNxt, iRowidReg); + sqlite3ExprCacheAffinityChange(pParse, iRowidReg, 1); sqlite3ExprCacheStore(pParse, iCur, -1, iRowidReg); VdbeComment((v, "pk")); pLevel->op = OP_Noop; diff --git a/test/tkt-fc7bd6358f.test b/test/tkt-fc7bd6358f.test new file mode 100644 index 0000000000..a1b13c463c --- /dev/null +++ b/test/tkt-fc7bd6358f.test @@ -0,0 +1,78 @@ +# 2013 March 05 +# +# The author disclaims copyright to this source code. In place of +# a legal notice, here is a blessing: +# +# May you do good and not evil. +# May you find forgiveness for yourself and forgive others. +# May you share freely, never taking more than you give. +# +#*********************************************************************** +# This file implements regression tests for SQLite library. Specifically, +# it tests that ticket [fc7bd6358f]: +# +# The following SQL yields an incorrect result (zero rows) in all +# versions of SQLite between 3.6.14 and 3.7.15.2: +# +# CREATE TABLE t(textid TEXT); +# INSERT INTO t VALUES('12'); +# INSERT INTO t VALUES('34'); +# CREATE TABLE i(intid INTEGER PRIMARY KEY); +# INSERT INTO i VALUES(12); +# INSERT INTO i VALUES(34); +# +# SELECT t1.textid AS a, i.intid AS b, t2.textid AS c +# FROM t t1, i, t t2 +# WHERE t1.textid = i.intid +# AND t1.textid = t2.textid; +# +# The correct result should be two rows, one with 12|12|12 and the other +# with 34|34|34. With this bug, no rows are returned. Bisecting shows that +# this bug was introduced with check-in [dd4d67a67454] on 2009-04-23. +# + +set testdir [file dirname $argv0] +source $testdir/tester.tcl + +do_test tkt-fc7bd6358f.100 { + db eval { + CREATE TABLE t(textid TEXT); + INSERT INTO t VALUES('12'); + INSERT INTO t VALUES('34'); + CREATE TABLE i(intid INTEGER PRIMARY KEY); + INSERT INTO i VALUES(12); + INSERT INTO i VALUES(34); + } +} {} +unset -nocomplain from +unset -nocomplain where +unset -nocomplain a +unset -nocomplain b +foreach {a from} { + 1 {FROM t t1, i, t t2} + 2 {FROM i, t t1, t t2} + 3 {FROM t t1, t t2, i} +} { + foreach {b where} { + 1 {WHERE t1.textid=i.intid AND t1.textid=t2.textid} + 2 {WHERE i.intid=t1.textid AND t1.textid=t2.textid} + 3 {WHERE t1.textid=i.intid AND i.intid=t2.textid} + 4 {WHERE t1.textid=i.intid AND t2.textid=i.intid} + 5 {WHERE i.intid=t1.textid AND i.intid=t2.textid} + 6 {WHERE i.intid=t1.textid AND t2.textid=i.intid} + 7 {WHERE t1.textid=t2.textid AND i.intid=t2.textid} + 8 {WHERE t1.textid=t2.textid AND t2.textid=i.intid} + } { + do_test tkt-fc7bd6358f.110.$a.$b.1 { + db eval {PRAGMA automatic_index=ON} + db eval "SELECT t1.textid, i.intid, t2.textid $from $where" + } {12 12 12 34 34 34} + do_test tkt-fc7bd6358f.110.$a.$b.2 { + db eval {PRAGMA automatic_index=OFF} + db eval "SELECT t1.textid, i.intid, t2.textid $from $where" + } {12 12 12 34 34 34} + } +} + + +finish_test