|
1 # 2007 April 6 |
|
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 # This file implements regression tests for SQLite library. The |
|
12 # focus of this script is database locks. |
|
13 # |
|
14 # $Id: lock4.test,v 1.8 2008/03/14 08:57:42 danielk1977 Exp $ |
|
15 |
|
16 |
|
17 set testdir [file dirname $argv0] |
|
18 source $testdir/tester.tcl |
|
19 |
|
20 # Initialize the test.db database so that it is non-empty |
|
21 # |
|
22 do_test lock4-1.1 { |
|
23 db eval { |
|
24 PRAGMA auto_vacuum=OFF; |
|
25 CREATE TABLE t1(x); |
|
26 } |
|
27 file delete -force test2.db test2.db-journal |
|
28 sqlite3 db2 test2.db |
|
29 db2 eval { |
|
30 PRAGMA auto_vacuum=OFF; |
|
31 CREATE TABLE t2(x) |
|
32 } |
|
33 db2 close |
|
34 list [file size test.db] [file size test2.db] |
|
35 } {2048 2048} |
|
36 |
|
37 # Create a script to drive a separate process that will |
|
38 # |
|
39 # 1. Create a second database test2.db |
|
40 # 2. Get an exclusive lock on test2.db |
|
41 # 3. Add an entry to test.db in table t1, waiting as necessary. |
|
42 # 4. Commit the change to test2.db. |
|
43 # |
|
44 # Meanwhile, this process will: |
|
45 # |
|
46 # A. Get an exclusive lock on test.db |
|
47 # B. Attempt to read from test2.db but get an SQLITE_BUSY error. |
|
48 # C. Commit the changes to test.db thus alloing the other process |
|
49 # to continue. |
|
50 # |
|
51 do_test lock4-1.2 { |
|
52 |
|
53 # Create a script for the second process to run. |
|
54 # |
|
55 set out [open test2-script.tcl w] |
|
56 puts $out "set sqlite_pending_byte [set sqlite_pending_byte]" |
|
57 puts $out { |
|
58 sqlite3 db2 test2.db |
|
59 db2 eval { |
|
60 BEGIN; |
|
61 INSERT INTO t2 VALUES(2); |
|
62 } |
|
63 sqlite3 db test.db |
|
64 db timeout 1000000 |
|
65 db eval { |
|
66 INSERT INTO t1 VALUES(2); |
|
67 } |
|
68 db close |
|
69 db2 eval COMMIT |
|
70 exit |
|
71 } |
|
72 close $out |
|
73 |
|
74 # Begin a transaction on test.db. |
|
75 db eval { |
|
76 BEGIN EXCLUSIVE; |
|
77 INSERT INTO t1 VALUES(1); |
|
78 } |
|
79 |
|
80 # Kick off the second process. |
|
81 exec [info nameofexec] ./test2-script.tcl & |
|
82 |
|
83 # Wait until the second process has started its transaction on test2.db. |
|
84 while {![file exists test2.db-journal]} { |
|
85 after 10 |
|
86 } |
|
87 |
|
88 # Try to write to test2.db. We are locked out. |
|
89 sqlite3 db2 test2.db |
|
90 catchsql { |
|
91 INSERT INTO t2 VALUES(1) |
|
92 } db2 |
|
93 } {1 {database is locked}} |
|
94 do_test lock4-1.3 { |
|
95 db eval { |
|
96 COMMIT; |
|
97 } |
|
98 while {[file exists test2.db-journal]} { |
|
99 after 10 |
|
100 } |
|
101 # The other process has committed its transaction on test2.db by |
|
102 # deleting the journal file. But it might retain the lock for a |
|
103 # fraction longer |
|
104 # |
|
105 db2 eval { |
|
106 SELECT * FROM t2 |
|
107 } |
|
108 } {2} |
|
109 |
|
110 |
|
111 do_test lock4-999.1 { |
|
112 rename db2 {} |
|
113 } {} |
|
114 |
|
115 finish_test |