1# 2020 June 30 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 test the busy handler 12# 13# TESTRUNNER: slow 14 15 16set testdir [file dirname $argv0] 17source $testdir/tester.tcl 18source $testdir/lock_common.tcl 19set testprefix busy2 20 21do_multiclient_test tn { 22 do_test 1.$tn.0 { 23 sql2 { 24 CREATE TABLE t1(a, b); 25 PRAGMA journal_mode = wal; 26 INSERT INTO t1 VALUES('A', 'B'); 27 } 28 } {wal} 29 30 do_test 1.$tn.1 { 31 code1 { db timeout 1000 } 32 sql1 { SELECT * FROM t1 } 33 } {A B} 34 35 do_test 1.$tn.2 { 36 sql2 { 37 BEGIN; 38 INSERT INTO t1 VALUES('C', 'D'); 39 } 40 } {} 41 42 do_test 1.$tn.3 { 43 set us [lindex [time { catch { sql1 { BEGIN EXCLUSIVE } } }] 0] 44 expr {$us>950000 && $us<1500000} 45 } {1} 46 47 do_test 1.$tn.4 { 48 sql2 { 49 COMMIT 50 } 51 } {} 52} 53 54#------------------------------------------------------------------------- 55 56do_multiclient_test tn { 57 # Make the db a WAL mode db. And add a table and a row to it. Then open 58 # a second connection within process 1. Process 1 now has connections 59 # [db] and [db1.2], process 2 has connection [db2] only. 60 # 61 # Configure all connections to use a 1000 ms timeout. 62 # 63 do_test 2.$tn.0 { 64 code1 { 65 sqlite3 db1.2 test.db 66 } 67 sql1 { 68 PRAGMA auto_vacuum = off; 69 PRAGMA journal_mode = wal; 70 CREATE TABLE t1(a, b); 71 INSERT INTO t1 VALUES(1, 2); 72 } 73 code2 { 74 db2 timeout 1000 75 } 76 code1 { 77 db1.2 timeout 1000 78 db timeout 1000 79 db1.2 eval {SELECT * FROM t1} 80 } 81 } {1 2} 82 83 # Take a read lock with [db] in process 1. 84 # 85 do_test 2.$tn.1 { 86 sql1 { 87 BEGIN; 88 SELECT * FROM t1; 89 } 90 } {1 2} 91 92 # Insert a row using [db2] in process 2. Then try a passive checkpoint. 93 # It fails to checkpoint the final frame (due to the readlock taken by 94 # [db]), and returns in less than 250ms. 95 do_test 2.$tn.2 { 96 sql2 { INSERT INTO t1 VALUES(3, 4) } 97 set us [lindex [time { 98 set res [code2 { db2 eval { PRAGMA wal_checkpoint } }] 99 }] 0] 100 list [expr $us < 250000] $res 101 } {1 {0 4 3}} 102 103 # Now try a FULL checkpoint with [db2]. It returns SQLITE_BUSY. And takes 104 # over 950ms to do so. 105 do_test 2.$tn.3 { 106 set us [lindex [time { 107 set res [code2 { db2 eval { PRAGMA wal_checkpoint = FULL } }] 108 }] 0] 109 list [expr $us > 950000] $res 110 } {1 {1 4 3}} 111 112 # Passive checkpoint with [db1.2] (process 1). No SQLITE_BUSY, returns 113 # in under 250ms. 114 do_test 2.$tn.4 { 115 set us [lindex [time { 116 set res [code1 { db1.2 eval { PRAGMA wal_checkpoint } }] 117 }] 0] 118 list [expr $us < 250000] $res 119 } {1 {0 4 3}} 120 121 # Full checkpoint with [db1.2] (process 1). SQLITE_BUSY returned in 122 # a bit over 950ms. 123 do_test 2.$tn.5 { 124 set us [lindex [time { 125 set res [code1 { db1.2 eval { PRAGMA wal_checkpoint = FULL } }] 126 }] 0] 127 list [expr $us > 950000] $res 128 } {1 {1 4 3}} 129 130 code1 { 131 db1.2 close 132 } 133} 134 135#------------------------------------------------------------------------- 136# Check that even if the busy-handler fails (returns zero) within a 137# call to sqlite3_prepare() (or _v2(), or _v3()), it is still invoked 138# the next time an SQLITE_BUSY is encountered. 139# 140do_multiclient_test tn { 141 code1 { 142 set ::busy_called 0 143 proc busy {args} { 144 if {$::busy_called} { return 1 } 145 set ::busy_called 1 146 return 0 147 } 148 db busy busy 149 } 150 151 do_test 3.$tn.1 { 152 sql2 { 153 CREATE TABLE t1(x); 154 BEGIN EXCLUSIVE; 155 INSERT INTO t1 VALUES('x'); 156 } 157 } {} 158 159 do_test 3.$tn.2 { 160 set ::busy_called 0 161 list [catch { sql1 { SELECT * FROM t1 } } msg] $::busy_called 162 } {1 1} 163 164 do_test 3.$tn.3 { 165 set ::busy_called 0 166 list [catch { sql1 { SELECT * FROM t1 } } msg] $::busy_called 167 } {1 1} 168 169} 170 171finish_test 172