1 # 2004 September 2 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 testing the callback-free C/C++ API and in 13 # particular the behavior of sqlite3_step() when trying to commit 14 # with lock contention. 15 # 16 # $Id: capi3b.test,v 1.4 2007/08/10 19:46:14 drh Exp $ 17 # 18 19 set testdir [file dirname $argv0] 20 source $testdir/tester.tcl 21 22 23 # These tests depend on the pager holding changes in cache 24 # until it is time to commit. But that won't happen if the 25 # soft-heap-limit is set too low. So disable the soft heap limit 26 # for the duration of this test. 27 # 28 sqlite3_soft_heap_limit 0 29 30 31 set DB [sqlite3_connection_pointer db] 32 sqlite3 db2 test.db 33 set DB2 [sqlite3_connection_pointer db2] 34 35 # Create some data in the database 36 # 37 do_test capi3b-1.1 { 38 execsql { 39 CREATE TABLE t1(x); 40 INSERT INTO t1 VALUES(1); 41 INSERT INTO t1 VALUES(2); 42 SELECT * FROM t1 43 } 44 } {1 2} 45 46 # Make sure the second database connection can see the data 47 # 48 do_test capi3b-1.2 { 49 execsql { 50 SELECT * FROM t1 51 } db2 52 } {1 2} 53 54 # First database connection acquires a shared lock 55 # 56 do_test capi3b-1.3 { 57 execsql { 58 BEGIN; 59 SELECT * FROM t1; 60 } 61 } {1 2} 62 63 # Second database connection tries to write. The sqlite3_step() 64 # function returns SQLITE_BUSY because it cannot commit. 65 # 66 do_test capi3b-1.4 { 67 set VM [sqlite3_prepare $DB2 {INSERT INTO t1 VALUES(3)} -1 TAIL] 68 sqlite3_step $VM 69 } SQLITE_BUSY 70 71 # The sqlite3_step call can be repeated multiple times. 72 # 73 do_test capi3b-1.5.1 { 74 sqlite3_step $VM 75 } SQLITE_BUSY 76 do_test capi3b-1.5.2 { 77 sqlite3_step $VM 78 } SQLITE_BUSY 79 80 # The first connection closes its transaction. This allows the second 81 # connections sqlite3_step to succeed. 82 # 83 do_test capi3b-1.6 { 84 execsql COMMIT 85 sqlite3_step $VM 86 } SQLITE_DONE 87 do_test capi3b-1.7 { 88 sqlite3_finalize $VM 89 } SQLITE_OK 90 do_test capi3b-1.8 { 91 execsql {SELECT * FROM t1} db2 92 } {1 2 3} 93 do_test capi3b-1.9 { 94 execsql {SELECT * FROM t1} 95 } {1 2 3} 96 97 # Start doing a SELECT with one connection. This gets a SHARED lock. 98 # Then do an INSERT with the other connection. The INSERT should 99 # not be able to complete until the SELECT finishes. 100 # 101 do_test capi3b-2.1 { 102 set VM1 [sqlite3_prepare $DB {SELECT * FROM t1} -1 TAIL] 103 sqlite3_step $VM1 104 } SQLITE_ROW 105 do_test capi3b-2.2 { 106 sqlite3_column_text $VM1 0 107 } 1 108 do_test capi3b-2.3 { 109 set VM2 [sqlite3_prepare $DB2 {INSERT INTO t1 VALUES(4)} -1 TAIL] 110 sqlite3_step $VM2 111 } SQLITE_BUSY 112 do_test capi3b-2.4 { 113 sqlite3_step $VM1 114 } SQLITE_ROW 115 do_test capi3b-2.5 { 116 sqlite3_column_text $VM1 0 117 } 2 118 do_test capi3b-2.6 { 119 sqlite3_step $VM2 120 } SQLITE_BUSY 121 do_test capi3b-2.7 { 122 sqlite3_step $VM1 123 } SQLITE_ROW 124 do_test capi3b-2.8 { 125 sqlite3_column_text $VM1 0 126 } 3 127 do_test capi3b-2.9 { 128 sqlite3_step $VM2 129 } SQLITE_BUSY 130 do_test capi3b-2.10 { 131 sqlite3_step $VM1 132 } SQLITE_DONE 133 do_test capi3b-2.11 { 134 sqlite3_step $VM2 135 } SQLITE_DONE 136 do_test capi3b-2.12 { 137 sqlite3_finalize $VM1 138 sqlite3_finalize $VM2 139 execsql {SELECT * FROM t1} 140 } {1 2 3 4} 141 142 catch {db2 close} 143 144 sqlite3_soft_heap_limit $cmdlinearg(soft-heap-limit) 145 finish_test 146