xref: /sqlite-3.40.0/test/nolock.test (revision dfe4e6bb)
1# 2014-05-07
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# This file implements regression tests for SQLite library.  The
13# focus of this file is testing the nolock=1 and immutable=1 query
14# parameters and the SQLITE_IOCAP_IMMUTABLE device characteristic.
15#
16
17set testdir [file dirname $argv0]
18source $testdir/tester.tcl
19
20unset -nocomplain tvfs_calls
21proc tvfs_reset {} {
22  global tvfs_calls
23  array set tvfs_calls {xLock 0 xUnlock 0 xCheckReservedLock 0 xAccess 0}
24}
25proc tvfs_callback {op args} {
26  global tvfs_calls
27  incr tvfs_calls($op)
28  return SQLITE_OK
29}
30tvfs_reset
31
32testvfs tvfs
33tvfs script tvfs_callback
34tvfs filter {xLock xUnlock xCheckReservedLock xAccess}
35
36############################################################################
37# Verify that the nolock=1 query parameter for URI filenames disables all
38# calls to xLock and xUnlock for rollback databases.
39#
40do_test nolock-1.0 {
41  db close
42  forcedelete test.db
43  tvfs_reset
44  sqlite db test.db -vfs tvfs
45  db eval {CREATE TABLE t1(a,b,c); INSERT INTO t1 VALUES(1,2,3);}
46  list xLock $::tvfs_calls(xLock) xUnlock $::tvfs_calls(xUnlock) \
47       xCheckReservedLock $::tvfs_calls(xCheckReservedLock)
48} {xLock 7 xUnlock 5 xCheckReservedLock 0}
49
50do_test nolock-1.1 {
51  db close
52  forcedelete test.db
53  tvfs_reset
54  sqlite db file:test.db?nolock=0 -vfs tvfs -uri 1
55  db eval {CREATE TABLE t1(a,b,c); INSERT INTO t1 VALUES(1,2,3);}
56  list xLock $::tvfs_calls(xLock) xUnlock $::tvfs_calls(xUnlock) \
57       xCheckReservedLock $::tvfs_calls(xCheckReservedLock)
58} {xLock 7 xUnlock 5 xCheckReservedLock 0}
59
60do_test nolock-1.2 {
61  db close
62  forcedelete test.db
63  tvfs_reset
64  sqlite db file:test.db?nolock=1 -vfs tvfs -uri 1
65  db eval {CREATE TABLE t1(a,b,c); INSERT INTO t1 VALUES(1,2,3);}
66  list xLock $::tvfs_calls(xLock) xUnlock $::tvfs_calls(xUnlock) \
67       xCheckReservedLock $::tvfs_calls(xCheckReservedLock)
68} {xLock 0 xUnlock 0 xCheckReservedLock 0}
69
70do_test nolock-1.3 {
71  db close
72  tvfs_reset
73  sqlite db file:test.db?nolock=0 -vfs tvfs -uri 1 -readonly 1
74  db eval {SELECT * FROM t1}
75  list xLock $::tvfs_calls(xLock) xUnlock $::tvfs_calls(xUnlock) \
76       xCheckReservedLock $::tvfs_calls(xCheckReservedLock)
77} {xLock 2 xUnlock 2 xCheckReservedLock 0}
78
79do_test nolock-1.4 {
80  db close
81  tvfs_reset
82  sqlite db file:test.db?nolock=1 -vfs tvfs -uri 1 -readonly 1
83  db eval {SELECT * FROM t1}
84  list xLock $::tvfs_calls(xLock) xUnlock $::tvfs_calls(xUnlock) \
85       xCheckReservedLock $::tvfs_calls(xCheckReservedLock)
86} {xLock 0 xUnlock 0 xCheckReservedLock 0}
87
88#############################################################################
89# Verify that immutable=1 disables both locking and xAccess calls to the
90# journal files.
91#
92do_test nolock-2.0 {
93  db close
94  forcedelete test.db
95  # begin by creating a test database
96  sqlite3 db test.db
97  db eval {
98     CREATE TABLE t1(a,b);
99     INSERT INTO t1 VALUES('hello','world');
100     CREATE TABLE t2(x,y);
101     INSERT INTO t2 VALUES(12345,67890);
102     SELECT * FROM t1, t2;
103  }
104} {hello world 12345 67890}
105do_test nolock-2.1 {
106  tvfs_reset
107  sqlite3 db2 test.db -vfs tvfs
108  db2 eval {SELECT * FROM t1, t2}
109} {hello world 12345 67890}
110do_test nolock-2.2 {
111  list xLock $::tvfs_calls(xLock) xUnlock $::tvfs_calls(xUnlock) \
112       xCheckReservedLock $::tvfs_calls(xCheckReservedLock) \
113       xAccess $::tvfs_calls(xAccess)
114} {xLock 2 xUnlock 2 xCheckReservedLock 0 xAccess 4}
115
116
117do_test nolock-2.11 {
118  db2 close
119  tvfs_reset
120  sqlite3 db2 file:test.db?immutable=0 -vfs tvfs -uri 1
121  db2 eval {SELECT * FROM t1, t2}
122} {hello world 12345 67890}
123do_test nolock-2.12 {
124  list xLock $::tvfs_calls(xLock) xUnlock $::tvfs_calls(xUnlock) \
125       xCheckReservedLock $::tvfs_calls(xCheckReservedLock) \
126       xAccess $::tvfs_calls(xAccess)
127} {xLock 2 xUnlock 2 xCheckReservedLock 0 xAccess 4}
128
129
130do_test nolock-2.21 {
131  db2 close
132  tvfs_reset
133  sqlite3 db2 file:test.db?immutable=1 -vfs tvfs -uri 1
134  db2 eval {SELECT * FROM t1, t2}
135} {hello world 12345 67890}
136do_test nolock-2.22 {
137  list xLock $::tvfs_calls(xLock) xUnlock $::tvfs_calls(xUnlock) \
138       xCheckReservedLock $::tvfs_calls(xCheckReservedLock) \
139       xAccess $::tvfs_calls(xAccess)
140} {xLock 0 xUnlock 0 xCheckReservedLock 0 xAccess 0}
141
142do_test nolock-2.31 {
143  db2 close
144  tvfs_reset
145  sqlite3 db2 file:test.db?immutable=1 -vfs tvfs -uri 1 -readonly 1
146  db2 eval {SELECT * FROM t1, t2}
147} {hello world 12345 67890}
148do_test nolock-2.32 {
149  list xLock $::tvfs_calls(xLock) xUnlock $::tvfs_calls(xUnlock) \
150       xCheckReservedLock $::tvfs_calls(xCheckReservedLock) \
151       xAccess $::tvfs_calls(xAccess)
152} {xLock 0 xUnlock 0 xCheckReservedLock 0 xAccess 0}
153
154############################################################################
155# Verify that the SQLITE_IOCAP_IMMUTABLE flag works
156#
157do_test nolock-3.1 {
158  db2 close
159  tvfs devchar immutable
160  tvfs_reset
161  sqlite3 db2 test.db -vfs tvfs
162  db2 eval {SELECT * FROM t1, t2}
163} {hello world 12345 67890}
164do_test nolock-3.2 {
165  list xLock $::tvfs_calls(xLock) xUnlock $::tvfs_calls(xUnlock) \
166       xCheckReservedLock $::tvfs_calls(xCheckReservedLock) \
167       xAccess $::tvfs_calls(xAccess)
168} {xLock 0 xUnlock 0 xCheckReservedLock 0 xAccess 0}
169
170do_test nolock-3.11 {
171  db2 close
172  tvfs_reset
173  sqlite3 db2 test.db -vfs tvfs -readonly 1
174  db2 eval {SELECT * FROM t1, t2}
175} {hello world 12345 67890}
176do_test nolock-3.12 {
177  list xLock $::tvfs_calls(xLock) xUnlock $::tvfs_calls(xUnlock) \
178       xCheckReservedLock $::tvfs_calls(xCheckReservedLock) \
179       xAccess $::tvfs_calls(xAccess)
180} {xLock 0 xUnlock 0 xCheckReservedLock 0 xAccess 0}
181
182db2 close
183db close
184tvfs delete
185
186if {[permutation]!="inmemory_journal"} {
187  # 2016-03-11:  Make sure all works when transitioning to WAL mode
188  # under nolock.
189  #
190  do_test nolock-4.1 {
191    forcedelete test.db
192    sqlite3 db file:test.db?nolock=1 -uri 1
193    db eval {
194       PRAGMA journal_mode=WAL;
195       CREATE TABLE t1(x);
196       INSERT INTO t1 VALUES('youngling');
197       SELECT * FROM t1;
198    }
199  } {delete youngling}
200  db close
201
202  do_test nolock-4.2 {
203    forcedelete test.db
204    sqlite3 db test.db
205    db eval {
206      PRAGMA journal_mode=WAL;
207      CREATE TABLE t1(x);
208      INSERT INTO t1 VALUES('catbird');
209      SELECT * FROM t1;
210    }
211  } {wal catbird}
212  do_test nolock-4.3 {
213    db close
214    sqlite3 db file:test.db?nolock=1 -uri 1
215    set rc [catch {db eval {SELECT * FROM t1}} msg]
216    lappend rc $msg
217  } {1 {unable to open database file}}
218}
219
220finish_test
221