]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
Fix a problem to do with detecting unlocked transaction conflicts if another client...
authordan <dan@noemail.net>
Sat, 22 Aug 2015 20:32:39 +0000 (20:32 +0000)
committerdan <dan@noemail.net>
Sat, 22 Aug 2015 20:32:39 +0000 (20:32 +0000)
FossilOrigin-Name: e3968b256282d8c0a87c26667b1ba02faf7a5a17

manifest
manifest.uuid
src/wal.c
test/unlocked2.test
test/unlocked3.test

index bc04296ba05ca98c818798dc68eb8aa6bd4f322f..1778b942535e1a9c730536948bfa6087d2428e62 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Add\sfurther\stests\sfor\sdeferred\spage\sallocation.\sAnd\sfixes\sfor\sthe\ssame.
-D 2015-08-22T17:28:55.533
+C Fix\sa\sproblem\sto\sdo\swith\sdetecting\sunlocked\stransaction\sconflicts\sif\sanother\sclient\srestarts\sthe\swal\swhile\sthe\stransaction\sis\srunning.
+D 2015-08-22T20:32:39.272
 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f
 F Makefile.in e2218eb228374422969de7b1680eda6864affcef
 F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23
@@ -411,7 +411,7 @@ F src/vdbesort.c f5009e7a35e3065635d8918b9a31f498a499976b
 F src/vdbetrace.c 8befe829faff6d9e6f6e4dee5a7d3f85cc85f1a0
 F src/vtab.c d31174e4c8f592febab3fa7f69e18320b4fd657a
 F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb
-F src/wal.c 0ba4899f02457be91fe5bc734638fee00c807f64
+F src/wal.c 4c69d27ed7ec7006008d8309dc5c9ab742273c12
 F src/wal.h a701096b9bf5761b8c5f4b07082249e1950afc9a
 F src/walker.c 2e14d17f592d176b6dc879c33fbdec4fbccaa2ba
 F src/where.c 66518a14a1238611aa0744d6980b6b7f544f4816
@@ -1228,8 +1228,8 @@ F test/unique.test 93f8b2ef5ea51b9495f8d6493429b1fd0f465264
 F test/unique2.test 41e7f83c6827605991160a31380148a9fc5f1339
 F test/unixexcl.test cd6c765f75e50e8e2c2ba763149e5d340ea19825
 F test/unlocked.test d143a871bd874311d4e5c98ce458218ca6b579fd
-F test/unlocked2.test 7f913b404cda03f22bc7b299e8eb82a34d2880c5
-F test/unlocked3.test 4facd06286885faa9bd53713fa3d701ca403aeb2
+F test/unlocked2.test aaa42a08052a146466220b6c3a062ff3c4776ad6
+F test/unlocked3.test 06173e406a8c1a550448f79329ed4c3311905062
 F test/unordered.test ca7adce0419e4ca0c50f039885e76ed2c531eda8
 F test/update.test 6c68446b8a0a33d522a7c72b320934596a2d7d32
 F test/uri.test 23662b7b61958b0f0e47082de7d06341ccf85d5b
@@ -1381,7 +1381,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1
 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4
 F tool/warnings.sh 48bd54594752d5be3337f12c72f28d2080cb630b
 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f
-P c2327a3b8e5d604ab948b1e9f6cfc401429e51db
-R c62a3f455b34280d099a1332c1c4f1e4
+P ed0a31be726e60115a5dd73d4ed580201b400ab7
+R 4d5e4d57de949c83b8660752ea3918ee
 U dan
-Z 1442e612d3eba52580ab50755ceb943f
+Z 75094882a86841f2760b97ee8543ae22
index 545070a4322267c2c4dd3024e43e0f676ddb5d95..c18cc52736f4820f604f37d54a1bfc1373e0ad5d 100644 (file)
@@ -1 +1 @@
-ed0a31be726e60115a5dd73d4ed580201b400ab7
\ No newline at end of file
+e3968b256282d8c0a87c26667b1ba02faf7a5a17
\ No newline at end of file
index a9d8a44086179e936cac9b2052c967ea3dbafb94..fcf5a15044b58c214a1c3157f90c927df50735d6 100644 (file)
--- a/src/wal.c
+++ b/src/wal.c
@@ -2594,13 +2594,14 @@ int sqlite3WalLockForCommit(Wal *pWal, PgHdr *pPage1, Bitvec *pAllRead){
     /* TODO: Check header checksum is good here. */
 
     if( memcmp(&pWal->hdr, (void*)pHead, sizeof(WalIndexHdr))!=0 ){
-      /* TODO: Is this safe? Because it holds the WRITER lock this thread
-      ** has exclusive access to the live header, but might it be corrupt? 
-      ** This code should check that the wal-index-header is Ok, and return
-      ** SQLITE_BUSY_SNAPSHOT if it is not. */
       int iHash;
       int iLastHash = walFramePage(pHead->mxFrame);
-      for(iHash=walFramePage(pWal->hdr.mxFrame+1); iHash<=iLastHash; iHash++){
+      u32 iFirst = pWal->hdr.mxFrame+1;     /* First wal frame to check */
+      if( memcmp(pWal->hdr.aSalt, (u32*)pHead->aSalt, sizeof(u32)*2) ){
+        assert( pWal->readLock==0 );
+        iFirst = 1;
+      }
+      for(iHash=walFramePage(iFirst); iHash<=iLastHash; iHash++){
         volatile ht_slot *aHash;
         volatile u32 *aPgno;
         u32 iZero;
@@ -2608,7 +2609,7 @@ int sqlite3WalLockForCommit(Wal *pWal, PgHdr *pPage1, Bitvec *pAllRead){
         rc = walHashGet(pWal, iHash, &aHash, &aPgno, &iZero);
         if( rc==SQLITE_OK ){
           int i;
-          int iMin = (pWal->hdr.mxFrame+1 - iZero);
+          int iMin = (iFirst - iZero);
           int iMax = (iHash==0) ? HASHTABLE_NPAGE_ONE : HASHTABLE_NPAGE;
           if( iMin<1 ) iMin = 1;
           if( iMax>pHead->mxFrame ) iMax = pHead->mxFrame;
index 927fe3e6752f69dddeda1fb526a16524b6da442e..6953753643e42d32c992535832e2e03305c873bd 100644 (file)
@@ -257,5 +257,40 @@ do_multiclient_test tn {
   do_test 5.$tn.5 { sql3 { PRAGMA integrity_check } } {ok}
 }
 
+#-------------------------------------------------------------------------
+#
+do_multiclient_test tn {
+  do_test 6.$tn.1 {
+    sql1 {
+      PRAGMA journal_mode = wal;
+      CREATE TABLE t1(x);
+      INSERT INTO t1 VALUES(randomblob(1500));
+      PRAGMA wal_checkpoint;
+    }
+  } {wal 0 5 5}
+
+  do_test 6.$tn.2 {
+    sql1 { 
+      BEGIN UNLOCKED;
+        INSERT INTO t1 VALUES(randomblob(1500));
+        INSERT INTO t1 VALUES(randomblob(1500));
+    }
+  } {}
+
+  do_test 6.$tn.3 {
+    sql2 {
+      BEGIN;
+        INSERT INTO t1 VALUES(randomblob(1500));
+        INSERT INTO t1 VALUES(randomblob(1500));
+      COMMIT;
+    }
+  } {}
+
+  do_test 6.$tn.4 { 
+    list [catch { sql1 COMMIT } msg] $msg
+  } {1 {database is locked}}
+  do_test 6.$tn.5 { sql3 { PRAGMA integrity_check } } {ok}
+  do_test 6.$tn.5 { sql3 { SELECT count(*) from t1 } } {3}
+}
 finish_test
 
index 04e741dc5b146315f3118652ca79798d62043411..b4deaf9a92c65499627e3d3526626a047bdbaedc 100644 (file)
@@ -55,6 +55,22 @@ proc do_sql_op {iTbl iOp} {
       "
     }
 
+    "D" {
+      set sql "
+        DELETE FROM t$iTbl WHERE rowid IN (
+          SELECT rowid FROM t$iTbl o WHERE (
+            SELECT count(*) FROM t$iTbl i WHERE i.rowid<o.rowid
+          ) % 2
+        )
+      "
+    }
+
+    "I" {
+      set sql "
+        INSERT INTO t$iTbl SELECT randomblob(800), randomblob(800) FROM t$iTbl;
+      "
+    }
+
     default {
       error "bad iOp parameter: $iOp"
     }
@@ -78,7 +94,9 @@ foreach {tn oplist} {
   6 {1iii 2iii 3iii 4iii}
   7 {1di  2id  3iii 4ddd}
   8 {1iii 2iii 3iii 4iii}
+
 } {
+  # 9 {1D  2II}
   if {[string range $oplist 0 0]=="-"} {
     reset_db
     create_schema