xref: /sqlite-3.40.0/test/savepoint7.test (revision dca595c4)
1# 2012 March 31
2#
3# The author disclaims copyright to this source code.  In place of
4# a legal notice, here is a blessing:
5#
6#    May you do good and not evil.
7#    May you find forgiveness for yourself and forgive others.
8#    May you share freely, never taking more than you give.
9#
10#***********************************************************************
11#
12# Focus on the interaction between RELEASE and ROLLBACK TO with
13# pending query aborts.  See ticket [27ca74af3c083f787a1c44b11fbb7c53bdbbcf1e].
14#
15
16set testdir [file dirname $argv0]
17source $testdir/tester.tcl
18
19# The RELEASE of an inner savepoint should not effect pending queries.
20#
21do_test savepoint7-1.1 {
22  db eval {
23    CREATE TABLE t1(a,b,c);
24    CREATE TABLE t2(x,y,z);
25    INSERT INTO t1 VALUES(1,2,3);
26    INSERT INTO t1 VALUES(4,5,6);
27    INSERT INTO t1 VALUES(7,8,9);
28    SAVEPOINT x1;
29  }
30  db eval {SELECT * FROM t1} {
31    db eval {
32      SAVEPOINT x2;
33      CREATE TABLE IF NOT EXISTS t3(xyz);
34      INSERT INTO t2 VALUES($a,$b,$c);
35      RELEASE x2;
36    }
37  }
38  db eval {SELECT * FROM t2; RELEASE x1}
39} {1 2 3 4 5 6 7 8 9}
40
41do_test savepoint7-1.2 {
42  db eval {DELETE FROM t2;}
43  db eval {SELECT * FROM t1} {
44    db eval {
45      SAVEPOINT x2;
46      INSERT INTO t2 VALUES($a,$b,$c);
47      RELEASE x2;
48    }
49  }
50  db eval {SELECT * FROM t2;}
51} {1 2 3 4 5 6 7 8 9}
52
53do_test savepoint7-1.3 {
54  db eval {DELETE FROM t2; BEGIN;}
55  db eval {SELECT * FROM t1} {
56    db eval {
57      SAVEPOINT x2;
58      INSERT INTO t2 VALUES($a,$b,$c);
59      RELEASE x2;
60    }
61  }
62  db eval {SELECT * FROM t2; ROLLBACK;}
63} {1 2 3 4 5 6 7 8 9}
64
65# However, a ROLLBACK of an inner savepoint will abort all queries, including
66# queries in outer contexts.
67#
68do_test savepoint7-2.1 {
69  db eval {DELETE FROM t2; SAVEPOINT x1; CREATE TABLE t4(abc);}
70  set rc [catch {
71    db eval {SELECT * FROM t1} {
72      db eval {
73        SAVEPOINT x2;
74        INSERT INTO t2 VALUES($a,$b,$c);
75        ROLLBACK TO x2;
76      }
77    }
78  } msg]
79  db eval {RELEASE x1}
80  list $rc $msg [db eval {SELECT * FROM t2}]
81} {1 {abort due to ROLLBACK} {}}
82
83do_test savepoint7-2.2 {
84  db eval {DELETE FROM t2;}
85  set rc [catch {
86    db eval {SELECT * FROM t1} {
87      db eval {
88        SAVEPOINT x2;
89        CREATE TABLE t5(pqr);
90        INSERT INTO t2 VALUES($a,$b,$c);
91        ROLLBACK TO x2;
92      }
93    }
94  } msg]
95  list $rc $msg [db eval {SELECT * FROM t2}]
96} {1 {abort due to ROLLBACK} {}}
97
98# Ticket: https://www.sqlite.org/src/tktview/7f7f8026eda387d544b
99# Segfault in the in-memory journal logic triggered by a tricky
100# combination of SAVEPOINT operations.
101#
102unset -nocomplain i
103for {set i 248} {$i<=253} {incr i} {
104  do_test savepoint7-3.$i {
105    db close
106    forcedelete test.db
107    sqlite3 db test.db
108    db eval {
109      PRAGMA page_size=1024;
110      PRAGMA temp_store=MEMORY;
111      BEGIN;
112      CREATE TABLE t1(x INTEGER PRIMARY KEY, y TEXT);
113      WITH RECURSIVE c(x) AS (VALUES(1) UNION SELECT x+1 FROM c WHERE x<$::i)
114      INSERT INTO t1(x,y) SELECT x*10, printf('%04d%.800c',x,'*') FROM c;
115      SAVEPOINT one;
116        SELECT count(*) FROM t1;
117        WITH RECURSIVE c(x) AS (VALUES(1) UNION SELECT x+1 FROM c WHERE x<$::i)
118        INSERT INTO t1(x,y) SELECT x*10+1, printf('%04d%.800c',x,'*') FROM c;
119      ROLLBACK TO one;
120        SELECT count(*) FROM t1;
121        SAVEPOINT twoB;
122          WITH RECURSIVE c(x) AS (VALUES(1) UNION SELECT x+1 FROM c WHERE x<10)
123          INSERT INTO t1(x,y) SELECT x*10+2, printf('%04d%.800c',x,'*') FROM c;
124        ROLLBACK TO twoB;
125      RELEASE one;
126      COMMIT;
127    }
128  } [list $i $i]
129}
130
131
132finish_test
133