]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
Disallow the one-pass optimization for DELETE if the WHERE clause contains
authordrh <>
Wed, 15 Mar 2023 18:05:02 +0000 (18:05 +0000)
committerdrh <>
Wed, 15 Mar 2023 18:05:02 +0000 (18:05 +0000)
a subquery.

FossilOrigin-Name: 25e1831885e8de370482a1e9f664f1590fa49995048fb16e1f948acd2a29c3e3

manifest
manifest.uuid
src/delete.c
src/resolve.c
src/sqliteInt.h
test/delete.test

index 8d1d6f3ec8bbfbe1a22af045884cf6b108218eff..bc353304270d832b8caac2f68d7953dfa818cba1 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Fix\sBloom\sfilters\son\san\sexpression\sindex.
-D 2023-03-14T20:16:48.299
+C Disallow\sthe\sone-pass\soptimization\sfor\sDELETE\sif\sthe\sWHERE\sclause\scontains\na\ssubquery.
+D 2023-03-15T18:05:02.324
 F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
 F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
 F LICENSE.md df5091916dbb40e6e9686186587125e1b2ff51f022cc334e886c19a0e9982724
@@ -570,7 +570,7 @@ F src/ctime.c 20507cc0b0a6c19cd882fcd0eaeda32ae6a4229fb4b024cfdf3183043d9b703d
 F src/date.c f21815ca7172ce073db3163ac54c8d9f2841077165c1a6123b4d1c376a0c7ec7
 F src/dbpage.c d47549716549311f79dc39fe5c8fb19390a6eb2c960f8e37c89a9c4de0c1052e
 F src/dbstat.c ec92074baa61d883de58c945162d9e666c13cd7cf3a23bc38b4d1c4d0b2c2bef
-F src/delete.c 86573edae75e3d3e9a8b590d87db8e47222103029df4f3e11fa56044459b514e
+F src/delete.c 201fe0763c52783d205c8c13cdd9d55c1bd5cb21c1f036753f99103b43284b90
 F src/expr.c 0bb501fd89d30dcb2569c7e479d765c2b92d969cf36c9dc5aa54db3d35c55d2a
 F src/fault.c 460f3e55994363812d9d60844b2a6de88826e007
 F src/fkey.c 722f20779f5342a787922deded3628d8c74b5249cab04098cf17ee2f2aaff002
@@ -619,14 +619,14 @@ F src/pragma.h e690a356c18e98414d2e870ea791c1be1545a714ba623719deb63f7f226d8bb7
 F src/prepare.c ce87a08cfddd45a147150db34190b1986f2d4a0e0828858cb6bd908c78fb02e3
 F src/printf.c ff4b05e38bf928ff1b80d3dda4f977b10fe39ecbfe69c018224c7e5594fb2455
 F src/random.c 606b00941a1d7dd09c381d3279a058d771f406c5213c9932bbd93d5587be4b9c
-F src/resolve.c 4233c3030341bf1a21cea90890e6b3d3531721acc62ede147e899d36ffad8238
+F src/resolve.c 6a0253379cc15b3f80321362a61f487a8ef7cd2487fe62e1eb2317b3f871c61f
 F src/rowset.c ba9515a922af32abe1f7d39406b9d35730ed65efab9443dc5702693b60854c92
 F src/select.c 9c6f537469c54af6e5b981d68ac18714562c497e6ff57782f338bb17b3ec9777
 F src/shell.c.in 6f36f5ca05f1bebf74935a7fcf2dce983016e807a09cbd752a673583ad7da087
 F src/sqlite.h.in 662a2fa083d093896b92560c871dea6d86792b49dc4bf7b4e8dbeca8e7171488
 F src/sqlite3.rc 5121c9e10c3964d5755191c80dd1180c122fc3a8
 F src/sqlite3ext.h da473ce2b3d0ae407a6300c4a164589b9a6bfdbec9462688a8593ff16f3bb6e4
-F src/sqliteInt.h 107157709ddfb05583343b69f14b0fa159f3ff8899ae2115415977a64815b364
+F src/sqliteInt.h e6f8331d9d78cee8f3d9b0f424680a4dbafaa72401b6ab3b92a3bd699aaafa7f
 F src/sqliteLimit.h d7323ffea5208c6af2734574bae933ca8ed2ab728083caa117c9738581a31657
 F src/status.c 160c445d7d28c984a0eae38c144f6419311ed3eace59b44ac6dafc20db4af749
 F src/table.c 0f141b58a16de7e2fbe81c308379e7279f4c6b50eb08efeec5892794a0ba30d1
@@ -924,7 +924,7 @@ F test/dbstatus.test 4a4221a883025ffd39696b3d1b3910b928fb097d77e671351acb35f3aed
 F test/dbstatus2.test f5fe0afed3fa45e57cfa70d1147606c20d2ba23feac78e9a172f2fe8ab5b78ef
 F test/decimal.test fcf403fd5585f47342234e153c4a4338cd737b8e0884ac66fc484df47dbcf1a7
 F test/default.test 9687cfb16717e4b8238c191697c98be88c0b16e568dd5368cd9284154097ef50
-F test/delete.test 31832b0c45ecb51a54348c68db173be462985901e6ed7f403d6d7a8f70ab4ef0
+F test/delete.test f66581a22960dae89b05f14755a576d935dcb94aa3aeacc0005b29bdbaa9949c
 F test/delete2.test 3a03f2cca1f9a67ec469915cb8babd6485db43fa
 F test/delete3.test 555e84a00a99230b7d049d477a324a631126a6ab
 F test/delete4.test 51fafebe9503a40796d1aae1565c60524cada720e50eecac01b7fd0419d9ea0b
@@ -2045,9 +2045,9 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93
 F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc
 F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e
 F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0
-P 6d6d95fcedbc8758ab284d3014ae4a97af6247003bb3d0a7056f2e6bffa6cae4
-Q +c028fb669a5ae34dbaf50fffab1ae49bc568b994435cf02e145d24da3cfb48d7
-R dcdf38ad3013ce771821ecfbfb219809
+P 11e0256b8c6f29bd2e60a0820f740e9927112bf6a0814751b7a73896298b4826
+Q +73f0036f045bf37193b6e87ae45b578c5831614c530488257c69666178da3aa5
+R 2cd55a1efd71979f677dd69b07b32a06
 U drh
-Z d6b69aca9364487c409ab687d0cabf73
+Z 60bb5fb96b693c918389f608d5ae659c
 # Remove this line to create a well-formed Fossil manifest.
index 56882271c07b0e0cfd15b0a9e6d0d195c6146bab..6141b8a7962334b6024781946ece1209f4b62b60 100644 (file)
@@ -1 +1 @@
-11e0256b8c6f29bd2e60a0820f740e9927112bf6a0814751b7a73896298b4826
\ No newline at end of file
+25e1831885e8de370482a1e9f664f1590fa49995048fb16e1f948acd2a29c3e3
\ No newline at end of file
index 704a3c71104a2e46b0a1a1ed71fd4f58dfef6dee..22ef7ab658137051778edaca2defad236a4915d0 100644 (file)
@@ -483,7 +483,7 @@ void sqlite3DeleteFrom(
 #endif /* SQLITE_OMIT_TRUNCATE_OPTIMIZATION */
   {
     u16 wcf = WHERE_ONEPASS_DESIRED|WHERE_DUPLICATES_OK;
-    if( sNC.ncFlags & NC_VarSelect ) bComplex = 1;
+    if( sNC.ncFlags & NC_Subquery ) bComplex = 1;
     wcf |= (bComplex ? 0 : WHERE_ONEPASS_MULTIROW);
     if( HasRowid(pTab) ){
       /* For a rowid table, initialize the RowSet to an empty set */
index dfb3434396b7b27dcda7a73a78c35b3fb9782348..4b36ecca3487ec62e32d5626705c7fcf195a7e8c 100644 (file)
@@ -1252,8 +1252,8 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){
         assert( pNC->nRef>=nRef );
         if( nRef!=pNC->nRef ){
           ExprSetProperty(pExpr, EP_VarSelect);
-          pNC->ncFlags |= NC_VarSelect;
         }
+        pNC->ncFlags |= NC_Subquery;
       }
       break;
     }
index 59637eb9e4bbf4f9475d1ab4e8b7a12666acdc5d..b7cf1c85c852dd9ddcfac31234147f06ecfd5c35 100644 (file)
@@ -3341,7 +3341,7 @@ struct NameContext {
 #define NC_HasAgg    0x000010 /* One or more aggregate functions seen */
 #define NC_IdxExpr   0x000020 /* True if resolving columns of CREATE INDEX */
 #define NC_SelfRef   0x00002e /* Combo: PartIdx, isCheck, GenCol, and IdxExpr */
-#define NC_VarSelect 0x000040 /* A correlated subquery has been seen */
+#define NC_Subquery  0x000040 /* A subquery has been seen */
 #define NC_UEList    0x000080 /* True if uNC.pEList is used */
 #define NC_UAggInfo  0x000100 /* True if uNC.pAggInfo is used */
 #define NC_UUpsert   0x000200 /* True if uNC.pUpsert is used */
index a448e52dd285847fb7241aba9bded79e920b7bf2..cdf6798ea6da89440ed1bdae346a800ea689054f 100644 (file)
@@ -416,4 +416,25 @@ do_execsql_test delete-11.1 {
 } {6 2 12 4 18 6 19 23 20 40}
 
 
+# 2023-03-15
+# https://sqlite.org/forum/forumpost/e61252062c9d286d
+#
+# When the WHERE clause of a DELETE statement contains a subquery
+# which uses the table that is being deleted from and there is a
+# short-circuit operator of some kind in the WHERE clause such that
+# the subquery might not run right away, then the subquery might
+# run after one or more rows have been deleted, which can change
+# the result of the subquery, and result in the wrong answer.
+#
+reset_db
+do_execsql_test delete-12.0 {
+  CREATE TABLE t0(vkey INTEGER, pkey INTEGER,c1 INTEGER);
+  INSERT INTO t0 VALUES(2,1,-20),(2,2,NULL),(2,3,0),(8,4,95);
+  DELETE FROM t0 WHERE NOT (
+    (t0.vkey <= t0.c1) AND
+    (t0.vkey <> (SELECT vkey FROM t0 ORDER BY vkey LIMIT 1 OFFSET 2))
+  );
+  SELECT * FROM t0;
+} {8 4 95}
+
 finish_test