]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
When a statement causes a ROLLBACK due to an ON CONFLICT clause, other active
authordrh <drh@noemail.net>
Wed, 30 Jun 2004 11:14:18 +0000 (11:14 +0000)
committerdrh <drh@noemail.net>
Wed, 30 Jun 2004 11:14:18 +0000 (11:14 +0000)
VMs abort. (CVS 1778)

FossilOrigin-Name: 0fedf74e30026afe2c8caacff3d62cf5c1b1f528

manifest
manifest.uuid
src/vdbeInt.h
src/vdbeapi.c
src/vdbeaux.c
test/rollback.test [new file with mode: 0644]

index e87b6d1389464152a337a182c34bdc83ddaded1a..d46ad5d84ca24a7f683f4a3259312389b4abed6a 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Make\ssure\svacuum.test\scloses\sall\sfiles.\s(CVS\s1777)
-D 2004-06-30T10:54:30
+C When\sa\sstatement\scauses\sa\sROLLBACK\sdue\sto\san\sON\sCONFLICT\sclause,\sother\sactive\nVMs\sabort.\s(CVS\s1778)
+D 2004-06-30T11:14:19
 F Makefile.in cb7a9889c38723f72b2506c4236ff30a05ff172b
 F Makefile.linux-gcc a9e5a0d309fa7c38e7c14d3ecf7690879d3a5457
 F README f1de682fbbd94899d50aca13d387d1b3fd3be2dd
@@ -75,9 +75,9 @@ F src/util.c b267d0fe10cffa3301fe9fab6592a6808a38bce6
 F src/vacuum.c b8546f4921719458cc537b9e736df52a8256399c
 F src/vdbe.c 4629151c9995b8b6a895c42de8808df1969bdcc7
 F src/vdbe.h 75b241c02431b9c0f16eaa9cdbb34146c6287f52
-F src/vdbeInt.h d83fd7389838453d8392915c21f432014afc99cf
-F src/vdbeapi.c ba3722f45db3d3c3509bf5d24f4f868f4c64449d
-F src/vdbeaux.c f9b1b3d4d2f1c31f6db1ae1536e17e4eb5454205
+F src/vdbeInt.h 7160653a006b6d2c4a00d204112a095bdf842ab6
+F src/vdbeapi.c 7c3c3d818fad427881b65c51999d06bf393ebeaf
+F src/vdbeaux.c f97b4b5e922fe74152e084bcea7b4468156bde50
 F src/vdbemem.c 053f8adcb644bca1c1e4ad08f4016cb7ee6bf1b8
 F src/where.c 6507074d8ce3f78e7a4cd33f667f11e62020553e
 F test/all.test 3b692eb43583b52c99c344b2fa8934512d179016
@@ -147,6 +147,7 @@ F test/printf.test 5ed2e033a0b47f901764096bf1907915d6e39406
 F test/progress.test 76c722f090b1ccb575e7e4e203a71608c5763beb x
 F test/quick.test bbe4abf7f434d71c0de26626c8cbb4858e1bcb18
 F test/quote.test 08f23385c685d3dc7914ec760d492cacea7f6e3d
+F test/rollback.test 4097328d44510277244ef4fa51b22b2f11d7ef4c
 F test/rowid.test b3d059f5c8d8874fa1c31030e0636f67405d20ea
 F test/select1.test 813a270ac7996b31ff228e8109cd2d1e8c3fa255
 F test/select2.test 91a2225926039b0d1687840735c284dbbf89f0bc
@@ -232,7 +233,7 @@ F www/tclsqlite.tcl 19191cf2a1010eaeff74c51d83fd5f5a4d899075
 F www/vdbe.tcl 59288db1ac5c0616296b26dce071c36cb611dfe9
 F www/version3.tcl 563ba3ac02f64da27ab17f3edbe8e56bfd0293fb
 F www/whentouse.tcl a8335bce47cc2fddb07f19052cb0cb4d9129a8e4
-P 152e9940b919a53fcd0da4091dbf75ab8ef15b38
-R 7c0d14b9c00314801ef156d50cb14232
-U danielk1977
-Z 744e63435b1a53bb66bf937c6227be06
+P 4077f9a30b0c30a8749a596031aa4f7adc3a4891
+R c74b8042375ac1ecced768631e1e7c90
+U drh
+Z bbd3e84a33ffc460275952232aa91883
index 8c80df17ceda0f4e9a621a9b7b5a984be8ab72cb..3ab60f36421e72927051fd8c9897993397799007 100644 (file)
@@ -1 +1 @@
-4077f9a30b0c30a8749a596031aa4f7adc3a4891
\ No newline at end of file
+0fedf74e30026afe2c8caacff3d62cf5c1b1f528
\ No newline at end of file
index 9ccb4d42724a958244dbb8781fd13e3ec3a42899..5a5a5d34af667d350006fd68a9beb5734d836347 100644 (file)
@@ -342,8 +342,9 @@ struct Vdbe {
   u8 resOnStack;          /* True if there are result values on the stack */
   u8 explain;             /* True if EXPLAIN present on SQL command */
   u8 autoCommitOn;        /* True if autocommit got turned on by this program */
-  int nChange;            /* Number of db changes made since last reset */
   u8 changeCntOn;         /* True to update the change-counter */
+  u8 aborted;             /* True if ROLLBACK in another VM causes an abort */
+  int nChange;            /* Number of db changes made since last reset */
 };
 
 /*
index 6935ca7d1a01bb657465474aad9a783e44cab4f6..6f0fbb20a97cdf1eb4e3cca60eb14cdc92f83787 100644 (file)
@@ -149,6 +149,9 @@ int sqlite3_step(sqlite3_stmt *pStmt){
   if( p->magic!=VDBE_MAGIC_RUN ){
     return SQLITE_MISUSE;
   }
+  if( p->aborted ){
+    return SQLITE_ABORT;
+  }
   db = p->db;
   if( sqlite3SafetyOn(db) ){
     p->rc = SQLITE_MISUSE;
index 8bed685871e8dcabb3ebbf05ab208cbeed33b868..8e0522ff372d1557df38d32ff32e3f0d73baca04 100644 (file)
@@ -1090,6 +1090,20 @@ static int vdbeCommit(sqlite *db){
   return rc;
 }
 
+/*
+** Find every active VM other than pVdbe and change its status to
+** aborted.  This happens when on VM causes a rollback.
+*/
+static void abortOtherActiveVdbes(Vdbe *pVdbe){
+  Vdbe *pOther;
+  for(pOther=pVdbe->db->pVdbe; pOther; pOther=pOther->pNext){
+    if( pOther==pVdbe ) continue;
+    if( pOther->magic!=VDBE_MAGIC_RUN || pOther->pc<0 ) continue;
+    closeAllCursors(pOther);
+    pOther->aborted = 1;
+  }
+}
+
 /* 
 ** This routine checks that the sqlite3.activeVdbeCnt count variable
 ** matches the number of vdbe's in the list sqlite3.pVdbe that are
@@ -1183,6 +1197,7 @@ int sqlite3VdbeReset(Vdbe *p){
     }else{
       xFunc = sqlite3BtreeRollback;
       db->autoCommit = 1;
+      abortOtherActiveVdbes(p);
     }
   }
   p->autoCommitOn = 0;
@@ -1245,6 +1260,7 @@ int sqlite3VdbeReset(Vdbe *p){
   }
 #endif
   p->magic = VDBE_MAGIC_INIT;
+  p->aborted = 0;
   return p->rc;
 }
 
diff --git a/test/rollback.test b/test/rollback.test
new file mode 100644 (file)
index 0000000..af1aeda
--- /dev/null
@@ -0,0 +1,78 @@
+# 2004 June 30
+#
+# 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.  The
+# focus of this file is verifying that a rollback in one statement
+# caused by an ON CONFLICT ROLLBACK clause aborts any other pending
+# statements.
+#
+# $Id: rollback.test,v 1.1 2004/06/30 11:14:19 drh Exp $
+
+set testdir [file dirname $argv0]
+source $testdir/tester.tcl
+
+db close
+set DB [sqlite3 db test.db]
+
+do_test rollback-1.1 {
+  execsql {
+    CREATE TABLE t1(a);
+    INSERT INTO t1 VALUES(1);
+    INSERT INTO t1 VALUES(2);
+    INSERT INTO t1 VALUES(3);
+    INSERT INTO t1 VALUES(4);
+    SELECT * FROM t1;
+  }
+} {1 2 3 4}
+
+do_test rollback-1.2 {
+  execsql {
+    CREATE TABLE t3(a unique on conflict rollback);
+    INSERT INTO t3 SELECT a FROM t1;
+    BEGIN;
+    INSERT INTO t1 SELECT * FROM t1;
+  }
+} {}
+do_test rollback-1.3 {
+  set STMT [sqlite3_prepare $DB "SELECT a FROM t1" -1 TAIL]
+  sqlite3_step $STMT
+} {SQLITE_ROW}
+
+# This causes a ROLLBACK, which deletes the table out from underneath the
+# SELECT statement.
+#
+do_test rollback-1.4 {
+  catchsql {
+    INSERT INTO t3 SELECT a FROM t1;
+  }
+} {1 {column a is not unique}}
+
+# Try to continue with the SELECT statement
+#
+do_test rollback-1.5 {
+  sqlite3_step $STMT
+} {SQLITE_ABORT}
+
+# Restart the SELECT statement
+#
+do_test rollback-1.6 {
+  sqlite3_reset $STMT
+} {}
+do_test rollback-1.7 {
+  sqlite3_step $STMT
+} {SQLITE_ROW}
+do_test rollback-1.8 {
+  sqlite3_step $STMT
+} {SQLITE_ROW}
+do_test rollback-1.9 {
+  sqlite3_finalize $STMT
+} {SQLITE_OK}
+
+finish_test