]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
Import from trunk the new fix to ticket [df46dfb631f75694] in which
authordrh <drh@noemail.net>
Sat, 23 Feb 2019 00:56:05 +0000 (00:56 +0000)
committerdrh <drh@noemail.net>
Sat, 23 Feb 2019 00:56:05 +0000 (00:56 +0000)
all ephemeral tables used as the RHS of an IN operator be index btrees
and never table btrees so that they can always be reused.

FossilOrigin-Name: 0e64ac122aac469aff4ca7f55a494c8d2d34bbcc1b854f3d579db5926590a660

manifest
manifest.uuid
src/expr.c
src/insert.c
src/sqliteInt.h
src/vdbe.c
src/wherecode.c
test/where.test

index 93a4de4b8d0a4a2bfd747e61f846b7835066d546..9d19ede2739e20b67e3a2f991b4ebe8dc5852ce1 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Increment\sthe\sversion\snumber\sto\s3.27.2.
-D 2019-02-20T13:14:23.660
+C Import\sfrom\strunk\sthe\snew\sfix\sto\sticket\s[df46dfb631f75694]\sin\swhich\nall\sephemeral\stables\sused\sas\sthe\sRHS\sof\san\sIN\soperator\sbe\sindex\sbtrees\nand\snever\stable\sbtrees\sso\sthat\sthey\scan\salways\sbe\sreused.
+D 2019-02-23T00:56:05.548
 F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
 F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
 F Makefile.in 178d8eb6840771149cee40b322d1b3be30d330198c522c903c1b66fb5a1bfca4
@@ -466,7 +466,7 @@ F src/date.c ebe1dc7c8a347117bb02570f1a931c62dd78f4a2b1b516f4837d45b7d6426957
 F src/dbpage.c 135eb3b5e74f9ef74bde5cec2571192c90c86984fa534c88bf4a055076fa19b7
 F src/dbstat.c c12833de69cb655751487d2c5a59607e36be1c58ba1f4bd536609909ad47b319
 F src/delete.c d08c9e01a2664afd12edcfa3a9c6578517e8ff8735f35509582693adbe0edeaf
-F src/expr.c 182dc9ff30aa6a430b7f728ce84fda85ec10890e29fdf75be1e871d13222a99c
+F src/expr.c f2d0ecf68213770be4fad83128ce02e67667deebaa0a44061313f7e4f2a4ae28
 F src/fault.c 460f3e55994363812d9d60844b2a6de88826e007
 F src/fkey.c bd0138acdc008c1845ccf92f8e73787880562de649471804801c06fed814c765
 F src/func.c 0341881d22903aac5ba7f352b188806d6436e1d6ae4235ff01e44d56879dfe63
@@ -475,7 +475,7 @@ F src/hash.c a12580e143f10301ed5166ea4964ae2853d3905a511d4e0c44497245c7ce1f7a
 F src/hash.h ab34c5c54a9e9de2e790b24349ba5aab3dbb4fd4
 F src/hwtime.h 747c1bbe9df21a92e9c50f3bbec1de841dc5e5da
 F src/in-operator.md 10cd8f4bcd225a32518407c2fb2484089112fd71
-F src/insert.c 3ed9ceaa4b7d56a6f2613355e1cd1ae5cfe31712bce2bf5aa93c5f1f130704b2
+F src/insert.c 7b71ba94e3283b497c076068fdeea760ce93b9db7d6784bdf5404fc842b721e5
 F src/legacy.c d7874bc885906868cd51e6c2156698f2754f02d9eee1bae2d687323c3ca8e5aa
 F src/loadext.c e6f10875d52aca3b7e57ce1ec174aeafc9b6c00b43000cd30d791f9cb490b7a6
 F src/main.c 27d7265625ea6eaccdfe7c53ef41adc179c9357a077702a860c1a3b0a037a16f
@@ -519,7 +519,7 @@ F src/shell.c.in f2c1adbee3f6f36686b4a38d2168ebfc25298b4ad1e6d95199fc4e95b539251
 F src/sqlite.h.in 7da74fd5bd7a9dbe92297060f036935520b26e240457287c5e67c7b9db51a986
 F src/sqlite3.rc 5121c9e10c3964d5755191c80dd1180c122fc3a8
 F src/sqlite3ext.h 960f1b86c3610fa23cb6a267572a97dcf286e77aa0dd3b9b23292ffaa1ea8683
-F src/sqliteInt.h f657e35d824fdc17ddf46bb85f0193df3b965e8354ded9ec37825057e3224bcc
+F src/sqliteInt.h ea0b5769140ca4bed03aeca8e7abb5c7a3eef4ffac723c8db3cfde88c390f807
 F src/sqliteLimit.h 1513bfb7b20378aa0041e7022d04acb73525de35b80b252f1b83fedb4de6a76b
 F src/status.c 46e7aec11f79dad50965a5ca5fa9de009f7d6bde08be2156f1538a0a296d4d0e
 F src/table.c b46ad567748f24a326d9de40e5b9659f96ffff34
@@ -585,7 +585,7 @@ F src/upsert.c 0dd81b40206841814d46942a7337786932475f085716042d0cb2fc7791bf8ca4
 F src/utf.c 810fbfebe12359f10bc2a011520a6e10879ab2a163bcb26c74768eab82ea62a5
 F src/util.c 82a2e3f691a3b654be872e305dab1f455e565dedf5e6a90c818c1ab307c00432
 F src/vacuum.c a9f389f41556c0ec310bc9169dc9476603c30a0a913ad92bfbc75c86886967ca
-F src/vdbe.c b7b6f965153607072917dbd81d654a268abf4872c58d556701d1549550766c02
+F src/vdbe.c 2c61090f2328ad125c8e55b4dab0712a78cfdfac893152fae34bed7e015b7cd7
 F src/vdbe.h 712bca562eaed1c25506b9faf9680bdc75fc42e2f4a1cd518d883fa79c7a4237
 F src/vdbeInt.h a76d5eed62c76bcd8de7afd3147fac1bc40c5a870582664bcd7d071ef437c37f
 F src/vdbeapi.c 57a2d794a8833f269b878dbc24e955369bdb379af6c4e93ebc5ce1a20fa3daf4
@@ -601,7 +601,7 @@ F src/wal.h 606292549f5a7be50b6227bd685fa76e3a4affad71bb8ac5ce4cb5c79f6a176a
 F src/walker.c 7607f1a68130c028255d8d56094ea602fc402c79e1e35a46e6282849d90d5fe4
 F src/where.c 8a207cb2ca6b99e1edb1e4bbff9b0504385a759cbf66180d1deb34d80ca4b799
 F src/whereInt.h 5f14db426ca46a83eabab1ae9aa6d4b8f27504ad35b64c290916289b1ddb2e88
-F src/wherecode.c 5ee878f714218352a2f452907572d4bf1e4303393288458f87ffc86edaf2cfbe
+F src/wherecode.c 061848646cc46a137d9038e47e666a955b3b2a1b458365eeed76b004c0053f3b
 F src/whereexpr.c 36b47f7261d6b6f1a72d774c113b74beddf6745aba1018e64b196e29db233442
 F src/window.c df2456386e0b1553a8d1fcf3a0ddc4c058fe2c650ea8c74b6bf8862082ddafc9
 F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2
@@ -1645,7 +1645,7 @@ F test/walshared.test 0befc811dcf0b287efae21612304d15576e35417
 F test/walslow.test c05c68d4dc2700a982f89133ce103a1a84cc285f
 F test/walthread.test 14b20fcfa6ae152f5d8e12f5dc8a8a724b7ef189f5d8ef1e2ceab79f2af51747
 F test/walvfs.test c0faffda13d045a96dfc541347886bb1a3d6f3205857fc98e683edfab766ea88
-F test/where.test 8215d220633f08da331781cf9ede7fb7aed50eb113473c10acd39a643fd258ba
+F test/where.test 93738e224cd5e7819565a9f272c19fd0ee5893d9cd7f5238ce026bae09b8d710
 F test/where2.test 478d2170637b9211f593120648858593bf2445a1
 F test/where3.test 2341a294e17193a6b1699ea7f192124a5286ca6acfcc3f4b06d16c931fbcda2c
 F test/where4.test 4a371bfcc607f41d233701bdec33ac2972908ba8
@@ -1804,7 +1804,8 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93
 F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc
 F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e
 F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0
-P 55e38d53adf1b3e95b0931359f8e135f0b2c063f34676b8dd27d933acdd6af5f
-R 027b5d93617809fb316cea967931a5e7
+P a70d67d8af3dd41fb7139e213e433516e4469a71aaededd3c88cf6e225288bf1
+Q +d3915230e3ee5878fe2e65a0afb7e91ee124aaf46b4e28c6e00053d6df13d445
+R 529ec9abee9d7082d40b473e097c7f60
 U drh
-Z 9cf90ec2a6f82b28c22cd026c4884d86
+Z c36fc67223c62b267adb844e47f924d2
index 9dd174670c4e5b8501abdad4f62f851c501a113f..d92c5bcc038543b00614353651b731810abf730b 100644 (file)
@@ -1 +1 @@
-a70d67d8af3dd41fb7139e213e433516e4469a71aaededd3c88cf6e225288bf1
\ No newline at end of file
+0e64ac122aac469aff4ca7f55a494c8d2d34bbcc1b854f3d579db5926590a660
\ No newline at end of file
index 03ecf1567d57d3a3f3d55e8a55c81e69e5a98a34..e39b6408c4343287eed58e29bb6d344f2cd91046 100644 (file)
@@ -2552,14 +2552,11 @@ int sqlite3FindInIndex(
     eType = IN_INDEX_EPH;
     if( inFlags & IN_INDEX_LOOP ){
       pParse->nQueryLoop = 0;
-      if( pX->pLeft->iColumn<0 && !ExprHasProperty(pX, EP_xIsSelect) ){
-        eType = IN_INDEX_ROWID;
-      }
     }else if( prRhsHasNull ){
       *prRhsHasNull = rMayHaveNull = ++pParse->nMem;
     }
     assert( pX->op==TK_IN );
-    sqlite3CodeRhsOfIN(pParse, pX, iTab, eType==IN_INDEX_ROWID);
+    sqlite3CodeRhsOfIN(pParse, pX, iTab);
     if( rMayHaveNull ){
       sqlite3SetHasNullFlag(v, iTab, rMayHaveNull);
     }
@@ -2660,12 +2657,6 @@ void sqlite3VectorErrorMsg(Parse *pParse, Expr *pExpr){
 ** however the cursor number returned might not be the same, as it might
 ** have been duplicated using OP_OpenDup.
 **
-** If parameter isRowid is non-zero, then LHS of the IN operator is guaranteed
-** to be a non-null integer. In this case, the ephemeral table can be an
-** table B-Tree that keyed by only integers.  The more general cases uses
-** an index B-Tree which can have arbitrary keys, but is slower to both
-** read and write.
-**
 ** If the LHS expression ("x" in the examples) is a column value, or
 ** the SELECT statement returns a column value, then the affinity of that
 ** column is used to build the index keys. If both 'x' and the
@@ -2677,8 +2668,7 @@ void sqlite3VectorErrorMsg(Parse *pParse, Expr *pExpr){
 void sqlite3CodeRhsOfIN(
   Parse *pParse,          /* Parsing context */
   Expr *pExpr,            /* The IN operator */
-  int iTab,               /* Use this cursor number */
-  int isRowid             /* If true, LHS is a rowid */
+  int iTab                /* Use this cursor number */
 ){
   int addrOnce = 0;           /* Address of the OP_Once instruction at top */
   int addr;                   /* Address of OP_OpenEphemeral instruction */
@@ -2731,14 +2721,12 @@ void sqlite3CodeRhsOfIN(
   /* Check to see if this is a vector IN operator */
   pLeft = pExpr->pLeft;
   nVal = sqlite3ExprVectorSize(pLeft);
-  assert( !isRowid || nVal==1 );
 
   /* Construct the ephemeral table that will contain the content of
   ** RHS of the IN operator.
   */
   pExpr->iTable = iTab;
-  addr = sqlite3VdbeAddOp2(v, OP_OpenEphemeral, 
-      pExpr->iTable, (isRowid?0:nVal));
+  addr = sqlite3VdbeAddOp2(v, OP_OpenEphemeral, pExpr->iTable, nVal);
 #ifdef SQLITE_ENABLE_EXPLAIN_COMMENTS
   if( ExprHasProperty(pExpr, EP_xIsSelect) ){
     VdbeComment((v, "Result of SELECT %u", pExpr->x.pSelect->selId));
@@ -2746,7 +2734,7 @@ void sqlite3CodeRhsOfIN(
     VdbeComment((v, "RHS of IN operator"));
   }
 #endif
-  pKeyInfo = isRowid ? 0 : sqlite3KeyInfoAlloc(pParse->db, nVal, 1);
+  pKeyInfo = sqlite3KeyInfoAlloc(pParse->db, nVal, 1);
 
   if( ExprHasProperty(pExpr, EP_xIsSelect) ){
     /* Case 1:     expr IN (SELECT ...)
@@ -2760,7 +2748,6 @@ void sqlite3CodeRhsOfIN(
     ExplainQueryPlan((pParse, 1, "%sLIST SUBQUERY %d",
         addrOnce?"":"CORRELATED ", pSelect->selId
     ));
-    assert( !isRowid );
     /* If the LHS and RHS of the IN operator do not match, that
     ** error will have been caught long before we reach this point. */
     if( ALWAYS(pEList->nExpr==nVal) ){
@@ -2813,10 +2800,8 @@ void sqlite3CodeRhsOfIN(
     /* Loop through each expression in <exprlist>. */
     r1 = sqlite3GetTempReg(pParse);
     r2 = sqlite3GetTempReg(pParse);
-    if( isRowid ) sqlite3VdbeAddOp4(v, OP_Blob, 0, r2, 0, "", P4_STATIC);
     for(i=pList->nExpr, pItem=pList->a; i>0; i--, pItem++){
       Expr *pE2 = pItem->pExpr;
-      int iValToIns;
 
       /* If the expression is not constant then we will need to
       ** disable the test that was generated above that makes sure
@@ -2829,20 +2814,9 @@ void sqlite3CodeRhsOfIN(
       }
 
       /* Evaluate the expression and insert it into the temp table */
-      if( isRowid && sqlite3ExprIsInteger(pE2, &iValToIns) ){
-        sqlite3VdbeAddOp3(v, OP_InsertInt, iTab, r2, iValToIns);
-      }else{
-        r3 = sqlite3ExprCodeTarget(pParse, pE2, r1);
-        if( isRowid ){
-          sqlite3VdbeAddOp2(v, OP_MustBeInt, r3,
-                            sqlite3VdbeCurrentAddr(v)+2);
-          VdbeCoverage(v);
-          sqlite3VdbeAddOp3(v, OP_Insert, iTab, r2, r3);
-        }else{
-          sqlite3VdbeAddOp4(v, OP_MakeRecord, r3, 1, r2, &affinity, 1);
-          sqlite3VdbeAddOp4Int(v, OP_IdxInsert, iTab, r2, r3, 1);
-        }
-      }
+      r3 = sqlite3ExprCodeTarget(pParse, pE2, r1);
+      sqlite3VdbeAddOp4(v, OP_MakeRecord, r3, 1, r2, &affinity, 1);
+      sqlite3VdbeAddOp4Int(v, OP_IdxInsert, iTab, r2, r3, 1);
     }
     sqlite3ReleaseTempReg(pParse, r1);
     sqlite3ReleaseTempReg(pParse, r2);
index a69e625a11ad6496311d7828cd905f91f46470e3..8d069b00efc26bc0b89a7a3e08f231ad513bdb6f 100644 (file)
@@ -1919,10 +1919,13 @@ void sqlite3CompleteInsertion(
       pik_flags |= (update_flags & OPFLAG_SAVEPOSITION);
 #ifdef SQLITE_ENABLE_PREUPDATE_HOOK
       if( update_flags==0 ){
-        sqlite3VdbeAddOp4(v, OP_InsertInt, 
-            iIdxCur+i, aRegIdx[i], 0, (char*)pTab, P4_TABLE
+        int r = sqlite3GetTempReg(pParse);
+        sqlite3VdbeAddOp2(v, OP_Integer, 0, r);
+        sqlite3VdbeAddOp4(v, OP_Insert, 
+            iIdxCur+i, aRegIdx[i], r, (char*)pTab, P4_TABLE
         );
         sqlite3VdbeChangeP5(v, OPFLAG_ISNOOP);
+        sqlite3ReleaseTempReg(pParse, r);
       }
 #endif
     }
index 774d3e50115db5de50cce51b9e55cbe5068abe03..4940511dc448587a57b79a30c8981f9cc74413c9 100644 (file)
@@ -4279,7 +4279,7 @@ void sqlite3AlterRenameColumn(Parse*, SrcList*, Token*, Token*);
 int sqlite3GetToken(const unsigned char *, int *);
 void sqlite3NestedParse(Parse*, const char*, ...);
 void sqlite3ExpirePreparedStatements(sqlite3*, int);
-void sqlite3CodeRhsOfIN(Parse*, Expr*, int, int);
+void sqlite3CodeRhsOfIN(Parse*, Expr*, int);
 int sqlite3CodeSubselect(Parse*, Expr*);
 void sqlite3SelectPrep(Parse*, Select*, NameContext*);
 void sqlite3SelectWrongNumTermsError(Parse *pParse, Select *p);
index 98df0a39772f3f4df28b926a8c88fe3254bd7e50..9f37624b5989803b47ed01bf698c1300dcfaa941 100644 (file)
@@ -4580,14 +4580,7 @@ case OP_NewRowid: {           /* out2 */
 ** This instruction only works on tables.  The equivalent instruction
 ** for indices is OP_IdxInsert.
 */
-/* Opcode: InsertInt P1 P2 P3 P4 P5
-** Synopsis: intkey=P3 data=r[P2]
-**
-** This works exactly like OP_Insert except that the key is the
-** integer value P3, not the value of the integer stored in register P3.
-*/
-case OP_Insert: 
-case OP_InsertInt: {
+case OP_Insert: {
   Mem *pData;       /* MEM cell holding data for the record to be inserted */
   Mem *pKey;        /* MEM cell holding key  for the record */
   VdbeCursor *pC;   /* Cursor to table into which insert is written */
@@ -4608,16 +4601,11 @@ case OP_InsertInt: {
   REGISTER_TRACE(pOp->p2, pData);
   sqlite3VdbeIncrWriteCounter(p, pC);
 
-  if( pOp->opcode==OP_Insert ){
-    pKey = &aMem[pOp->p3];
-    assert( pKey->flags & MEM_Int );
-    assert( memIsValid(pKey) );
-    REGISTER_TRACE(pOp->p3, pKey);
-    x.nKey = pKey->u.i;
-  }else{
-    assert( pOp->opcode==OP_InsertInt );
-    x.nKey = pOp->p3;
-  }
+  pKey = &aMem[pOp->p3];
+  assert( pKey->flags & MEM_Int );
+  assert( memIsValid(pKey) );
+  REGISTER_TRACE(pOp->p3, pKey);
+  x.nKey = pKey->u.i;
 
   if( pOp->p4type==P4_TABLE && HAS_UPDATE_HOOK(db) ){
     assert( pC->iDb>=0 );
index 5441752ed18341f47e0a1b7430d5b0179a8149b2..79189386b63ed10d1d7cf5a257a73ebe63f49e9b 100644 (file)
@@ -582,7 +582,6 @@ static int codeEqualityTerm(
         if( pLoop->aLTerm[i]->pExpr==pX ){
           int iOut = iReg + i - iEq;
           if( eType==IN_INDEX_ROWID ){
-            testcase( nEq>1 );  /* Happens with a UNIQUE index on ROWID */
             pIn->addrInTop = sqlite3VdbeAddOp2(v, OP_Rowid, iTab, iOut);
           }else{
             int iCol = aiMap ? aiMap[iMap++] : 0;
@@ -1344,7 +1343,9 @@ Bitmask sqlite3WhereCodeOneLoopStart(
     sqlite3VdbeAddOp3(v, OP_SeekRowid, iCur, addrNxt, iRowidReg);
     VdbeCoverage(v);
     pLevel->op = OP_Noop;
-    pTerm->wtFlags |= TERM_CODED;
+    if( (pTerm->prereqAll & pLevel->notReady)==0 ){
+      pTerm->wtFlags |= TERM_CODED;
+    }
   }else if( (pLoop->wsFlags & WHERE_IPK)!=0
          && (pLoop->wsFlags & WHERE_COLUMN_RANGE)!=0
   ){
index 1f38065c65c3c161be5b3b0e67434290a830a4bd..e1b81aa053dd4c07e6a3c0e1a274b11f95485408 100644 (file)
@@ -1425,5 +1425,17 @@ do_execsql_test where-22.1 {
   SELECT count(*) FROM t1 LEFT JOIN t2 ON a IS NOT NULL;
 } {5}
 
+# 20190-02-22:  A bug introduced by checkin
+# https://www.sqlite.org/src/info/fa792714ae62fa98.
+#
+do_execsql_test where-23.0 {
+  DROP TABLE IF EXISTS t1;
+  DROP TABLE IF EXISTS t2;
+  CREATE TABLE t1(a INTEGER PRIMARY KEY);
+  INSERT INTO t1(a) VALUES(1),(2),(3);
+  CREATE TABLE t2(x INTEGER PRIMARY KEY, y INT);
+  INSERT INTO t2(y) VALUES(2),(3);
+  SELECT * FROM t1, t2 WHERE a=y AND y=3;
+} {3 2 3}
 
 finish_test