1*c5c4113dSnw141292 2*c5c4113dSnw141292#pragma ident "%Z%%M% %I% %E% SMI" 3*c5c4113dSnw141292 4*c5c4113dSnw141292# 2001 September 15 5*c5c4113dSnw141292# 6*c5c4113dSnw141292# The author disclaims copyright to this source code. In place of 7*c5c4113dSnw141292# a legal notice, here is a blessing: 8*c5c4113dSnw141292# 9*c5c4113dSnw141292# May you do good and not evil. 10*c5c4113dSnw141292# May you find forgiveness for yourself and forgive others. 11*c5c4113dSnw141292# May you share freely, never taking more than you give. 12*c5c4113dSnw141292# 13*c5c4113dSnw141292#*********************************************************************** 14*c5c4113dSnw141292# This file implements regression tests for SQLite library. The 15*c5c4113dSnw141292# focus of this script is btree database backend 16*c5c4113dSnw141292# 17*c5c4113dSnw141292# $Id: btree2.test,v 1.10 2002/02/19 13:39:23 drh Exp $ 18*c5c4113dSnw141292 19*c5c4113dSnw141292 20*c5c4113dSnw141292set testdir [file dirname $argv0] 21*c5c4113dSnw141292source $testdir/tester.tcl 22*c5c4113dSnw141292 23*c5c4113dSnw141292if {[info commands btree_open]!=""} { 24*c5c4113dSnw141292 25*c5c4113dSnw141292# Create a new database file containing no entries. The database should 26*c5c4113dSnw141292# contain 5 tables: 27*c5c4113dSnw141292# 28*c5c4113dSnw141292# 2 The descriptor table 29*c5c4113dSnw141292# 3 The foreground table 30*c5c4113dSnw141292# 4 The background table 31*c5c4113dSnw141292# 5 The long key table 32*c5c4113dSnw141292# 6 The long data table 33*c5c4113dSnw141292# 34*c5c4113dSnw141292# An explanation for what all these tables are used for is provided below. 35*c5c4113dSnw141292# 36*c5c4113dSnw141292do_test btree2-1.1 { 37*c5c4113dSnw141292 expr srand(1) 38*c5c4113dSnw141292 file delete -force test2.bt 39*c5c4113dSnw141292 file delete -force test2.bt-journal 40*c5c4113dSnw141292 set ::b [btree_open test2.bt] 41*c5c4113dSnw141292 btree_begin_transaction $::b 42*c5c4113dSnw141292 btree_create_table $::b 43*c5c4113dSnw141292} {3} 44*c5c4113dSnw141292do_test btree2-1.2 { 45*c5c4113dSnw141292 btree_create_table $::b 46*c5c4113dSnw141292} {4} 47*c5c4113dSnw141292do_test btree2-1.3 { 48*c5c4113dSnw141292 btree_create_table $::b 49*c5c4113dSnw141292} {5} 50*c5c4113dSnw141292do_test btree2-1.4 { 51*c5c4113dSnw141292 btree_create_table $::b 52*c5c4113dSnw141292} {6} 53*c5c4113dSnw141292do_test btree2-1.5 { 54*c5c4113dSnw141292 set ::c2 [btree_cursor $::b 2 1] 55*c5c4113dSnw141292 btree_insert $::c2 {one} {1} 56*c5c4113dSnw141292 btree_delete $::c2 57*c5c4113dSnw141292 btree_close_cursor $::c2 58*c5c4113dSnw141292 btree_commit $::b 59*c5c4113dSnw141292 btree_integrity_check $::b 2 3 4 5 6 60*c5c4113dSnw141292} {} 61*c5c4113dSnw141292 62*c5c4113dSnw141292# This test module works by making lots of pseudo-random changes to a 63*c5c4113dSnw141292# database while simultaneously maintaining an invariant on that database. 64*c5c4113dSnw141292# Periodically, the script does a sanity check on the database and verifies 65*c5c4113dSnw141292# that the invariant is satisfied. 66*c5c4113dSnw141292# 67*c5c4113dSnw141292# The invariant is as follows: 68*c5c4113dSnw141292# 69*c5c4113dSnw141292# 1. The descriptor table always contains 2 enters. An entry keyed by 70*c5c4113dSnw141292# "N" is the number of elements in the foreground and background tables 71*c5c4113dSnw141292# combined. The entry keyed by "L" is the number of digits in the keys 72*c5c4113dSnw141292# for foreground and background tables. 73*c5c4113dSnw141292# 74*c5c4113dSnw141292# 2. The union of the foreground an background tables consists of N entries 75*c5c4113dSnw141292# where each entry an L-digit key. (Actually, some keys can be longer 76*c5c4113dSnw141292# than L characters, but they always start with L digits.) The keys 77*c5c4113dSnw141292# cover all integers between 1 and N. Whenever an entry is added to 78*c5c4113dSnw141292# the foreground it is removed form the background and vice versa. 79*c5c4113dSnw141292# 80*c5c4113dSnw141292# 3. Some entries in the foreground and background tables have keys that 81*c5c4113dSnw141292# begin with an L-digit number but are followed by additional characters. 82*c5c4113dSnw141292# For each such entry there is a corresponding entry in the long key 83*c5c4113dSnw141292# table. The long key table entry has a key which is just the L-digit 84*c5c4113dSnw141292# number and data which is the length of the key in the foreground and 85*c5c4113dSnw141292# background tables. 86*c5c4113dSnw141292# 87*c5c4113dSnw141292# 4. The data for both foreground and background entries is usually a 88*c5c4113dSnw141292# short string. But some entries have long data strings. For each 89*c5c4113dSnw141292# such entries there is an entry in the long data type. The key to 90*c5c4113dSnw141292# long data table is an L-digit number. (The extension on long keys 91*c5c4113dSnw141292# is omitted.) The data is the number of charaters in the data of the 92*c5c4113dSnw141292# foreground or background entry. 93*c5c4113dSnw141292# 94*c5c4113dSnw141292# The following function builds a database that satisfies all of the above 95*c5c4113dSnw141292# invariants. 96*c5c4113dSnw141292# 97*c5c4113dSnw141292proc build_db {N L} { 98*c5c4113dSnw141292 for {set i 2} {$i<=6} {incr i} { 99*c5c4113dSnw141292 catch {btree_close_cursor [set ::c$i]} 100*c5c4113dSnw141292 btree_clear_table $::b $i 101*c5c4113dSnw141292 set ::c$i [btree_cursor $::b $i 1] 102*c5c4113dSnw141292 } 103*c5c4113dSnw141292 btree_insert $::c2 N $N 104*c5c4113dSnw141292 btree_insert $::c2 L $L 105*c5c4113dSnw141292 set format %0${L}d 106*c5c4113dSnw141292 for {set i 1} {$i<=$N} {incr i} { 107*c5c4113dSnw141292 set key [format $format $i] 108*c5c4113dSnw141292 set data $key 109*c5c4113dSnw141292 btree_insert $::c3 $key $data 110*c5c4113dSnw141292 } 111*c5c4113dSnw141292} 112*c5c4113dSnw141292 113*c5c4113dSnw141292# Given a base key number and a length, construct the full text of the key 114*c5c4113dSnw141292# or data. 115*c5c4113dSnw141292# 116*c5c4113dSnw141292proc make_payload {keynum L len} { 117*c5c4113dSnw141292 set key [format %0${L}d $keynum] 118*c5c4113dSnw141292 set r $key 119*c5c4113dSnw141292 set i 1 120*c5c4113dSnw141292 while {[string length $r]<$len} { 121*c5c4113dSnw141292 append r " ($i) $key" 122*c5c4113dSnw141292 incr i 123*c5c4113dSnw141292 } 124*c5c4113dSnw141292 return [string range $r 0 [expr {$len-1}]] 125*c5c4113dSnw141292} 126*c5c4113dSnw141292 127*c5c4113dSnw141292# Verify the invariants on the database. Return an empty string on 128*c5c4113dSnw141292# success or an error message if something is amiss. 129*c5c4113dSnw141292# 130*c5c4113dSnw141292proc check_invariants {} { 131*c5c4113dSnw141292 set ck [btree_integrity_check $::b 2 3 4 5 6] 132*c5c4113dSnw141292 if {$ck!=""} { 133*c5c4113dSnw141292 puts "\n*** SANITY:\n$ck" 134*c5c4113dSnw141292 exit 135*c5c4113dSnw141292 return $ck 136*c5c4113dSnw141292 } 137*c5c4113dSnw141292 btree_move_to $::c3 {} 138*c5c4113dSnw141292 btree_move_to $::c4 {} 139*c5c4113dSnw141292 btree_move_to $::c2 N 140*c5c4113dSnw141292 set N [btree_data $::c2] 141*c5c4113dSnw141292 btree_move_to $::c2 L 142*c5c4113dSnw141292 set L [btree_data $::c2] 143*c5c4113dSnw141292 set LM1 [expr {$L-1}] 144*c5c4113dSnw141292 for {set i 1} {$i<=$N} {incr i} { 145*c5c4113dSnw141292 set key [btree_key $::c3] 146*c5c4113dSnw141292 if {[scan $key %d k]<1} {set k 0} 147*c5c4113dSnw141292 if {$k!=$i} { 148*c5c4113dSnw141292 set key [btree_key $::c4] 149*c5c4113dSnw141292 if {[scan $key %d k]<1} {set k 0} 150*c5c4113dSnw141292 if {$k!=$i} { 151*c5c4113dSnw141292 # puts "MISSING $i" 152*c5c4113dSnw141292 # puts {Page 3:}; btree_page_dump $::b 3 153*c5c4113dSnw141292 # puts {Page 4:}; btree_page_dump $::b 4 154*c5c4113dSnw141292 # exit 155*c5c4113dSnw141292 return "Key $i is missing from both foreground and background" 156*c5c4113dSnw141292 } 157*c5c4113dSnw141292 set data [btree_data $::c4] 158*c5c4113dSnw141292 btree_next $::c4 159*c5c4113dSnw141292 } else { 160*c5c4113dSnw141292 set data [btree_data $::c3] 161*c5c4113dSnw141292 btree_next $::c3 162*c5c4113dSnw141292 } 163*c5c4113dSnw141292 set skey [string range $key 0 $LM1] 164*c5c4113dSnw141292 if {[btree_move_to $::c5 $skey]==0} { 165*c5c4113dSnw141292 set keylen [btree_data $::c5] 166*c5c4113dSnw141292 } else { 167*c5c4113dSnw141292 set keylen $L 168*c5c4113dSnw141292 } 169*c5c4113dSnw141292 if {[string length $key]!=$keylen} { 170*c5c4113dSnw141292 return "Key $i is the wrong size.\ 171*c5c4113dSnw141292 Is \"$key\" but should be \"[make_payload $k $L $keylen]\"" 172*c5c4113dSnw141292 } 173*c5c4113dSnw141292 if {[make_payload $k $L $keylen]!=$key} { 174*c5c4113dSnw141292 return "Key $i has an invalid extension" 175*c5c4113dSnw141292 } 176*c5c4113dSnw141292 if {[btree_move_to $::c6 $skey]==0} { 177*c5c4113dSnw141292 set datalen [btree_data $::c6] 178*c5c4113dSnw141292 } else { 179*c5c4113dSnw141292 set datalen $L 180*c5c4113dSnw141292 } 181*c5c4113dSnw141292 if {[string length $data]!=$datalen} { 182*c5c4113dSnw141292 return "Data for $i is the wrong size.\ 183*c5c4113dSnw141292 Is [string length $data] but should be $datalen" 184*c5c4113dSnw141292 } 185*c5c4113dSnw141292 if {[make_payload $k $L $datalen]!=$data} { 186*c5c4113dSnw141292 return "Entry $i has an incorrect data" 187*c5c4113dSnw141292 } 188*c5c4113dSnw141292 } 189*c5c4113dSnw141292} 190*c5c4113dSnw141292 191*c5c4113dSnw141292# Make random changes to the database such that each change preserves 192*c5c4113dSnw141292# the invariants. The number of changes is $n*N where N is the parameter 193*c5c4113dSnw141292# from the descriptor table. Each changes begins with a random key. 194*c5c4113dSnw141292# the entry with that key is put in the foreground table with probability 195*c5c4113dSnw141292# $I and it is put in background with probability (1.0-$I). It gets 196*c5c4113dSnw141292# a long key with probability $K and long data with probability $D. 197*c5c4113dSnw141292# 198*c5c4113dSnw141292set chngcnt 0 199*c5c4113dSnw141292proc random_changes {n I K D} { 200*c5c4113dSnw141292 btree_move_to $::c2 N 201*c5c4113dSnw141292 set N [btree_data $::c2] 202*c5c4113dSnw141292 btree_move_to $::c2 L 203*c5c4113dSnw141292 set L [btree_data $::c2] 204*c5c4113dSnw141292 set LM1 [expr {$L-1}] 205*c5c4113dSnw141292 set total [expr {int($N*$n)}] 206*c5c4113dSnw141292 set format %0${L}d 207*c5c4113dSnw141292 for {set i 0} {$i<$total} {incr i} { 208*c5c4113dSnw141292 set k [expr {int(rand()*$N)+1}] 209*c5c4113dSnw141292 set insert [expr {rand()<=$I}] 210*c5c4113dSnw141292 set longkey [expr {rand()<=$K}] 211*c5c4113dSnw141292 set longdata [expr {rand()<=$D}] 212*c5c4113dSnw141292 # incr ::chngcnt 213*c5c4113dSnw141292 # if {$::chngcnt==251} {btree_tree_dump $::b 3} 214*c5c4113dSnw141292 # puts "CHANGE $::chngcnt: $k $insert $longkey $longdata" 215*c5c4113dSnw141292 if {$longkey} { 216*c5c4113dSnw141292 set x [expr {rand()}] 217*c5c4113dSnw141292 set keylen [expr {int($x*$x*$x*$x*3000)+10}] 218*c5c4113dSnw141292 } else { 219*c5c4113dSnw141292 set keylen $L 220*c5c4113dSnw141292 } 221*c5c4113dSnw141292 set key [make_payload $k $L $keylen] 222*c5c4113dSnw141292 if {$longdata} { 223*c5c4113dSnw141292 set x [expr {rand()}] 224*c5c4113dSnw141292 set datalen [expr {int($x*$x*$x*$x*3000)+10}] 225*c5c4113dSnw141292 } else { 226*c5c4113dSnw141292 set datalen $L 227*c5c4113dSnw141292 } 228*c5c4113dSnw141292 set data [make_payload $k $L $datalen] 229*c5c4113dSnw141292 set basekey [format $format $k] 230*c5c4113dSnw141292 if {[set c [btree_move_to $::c3 $basekey]]==0} { 231*c5c4113dSnw141292 btree_delete $::c3 232*c5c4113dSnw141292 } else { 233*c5c4113dSnw141292 if {$c<0} {btree_next $::c3} 234*c5c4113dSnw141292 if {[string match $basekey* [btree_key $::c3]]} { 235*c5c4113dSnw141292 btree_delete $::c3 236*c5c4113dSnw141292 } 237*c5c4113dSnw141292 } 238*c5c4113dSnw141292 if {[set c [btree_move_to $::c4 $basekey]]==0} { 239*c5c4113dSnw141292 btree_delete $::c4 240*c5c4113dSnw141292 } else { 241*c5c4113dSnw141292 if {$c<0} {btree_next $::c4} 242*c5c4113dSnw141292 if {[string match $basekey* [btree_key $::c4]]} { 243*c5c4113dSnw141292 btree_delete $::c4 244*c5c4113dSnw141292 } 245*c5c4113dSnw141292 } 246*c5c4113dSnw141292 if {[scan [btree_key $::c4] %d kx]<1} {set kx -1} 247*c5c4113dSnw141292 if {$kx==$k} { 248*c5c4113dSnw141292 btree_delete $::c4 249*c5c4113dSnw141292 } 250*c5c4113dSnw141292 if {$insert} { 251*c5c4113dSnw141292 btree_insert $::c3 $key $data 252*c5c4113dSnw141292 } else { 253*c5c4113dSnw141292 btree_insert $::c4 $key $data 254*c5c4113dSnw141292 } 255*c5c4113dSnw141292 if {$longkey} { 256*c5c4113dSnw141292 btree_insert $::c5 $basekey $keylen 257*c5c4113dSnw141292 } elseif {[btree_move_to $::c5 $basekey]==0} { 258*c5c4113dSnw141292 btree_delete $::c5 259*c5c4113dSnw141292 } 260*c5c4113dSnw141292 if {$longdata} { 261*c5c4113dSnw141292 btree_insert $::c6 $basekey $datalen 262*c5c4113dSnw141292 } elseif {[btree_move_to $::c6 $basekey]==0} { 263*c5c4113dSnw141292 btree_delete $::c6 264*c5c4113dSnw141292 } 265*c5c4113dSnw141292 # set ck [btree_integrity_check $::b 2 3 4 5 6] 266*c5c4113dSnw141292 # if {$ck!=""} { 267*c5c4113dSnw141292 # puts "\nSANITY CHECK FAILED!\n$ck" 268*c5c4113dSnw141292 # exit 269*c5c4113dSnw141292 # } 270*c5c4113dSnw141292 # puts "PAGE 3:"; btree_page_dump $::b 3 271*c5c4113dSnw141292 # puts "PAGE 4:"; btree_page_dump $::b 4 272*c5c4113dSnw141292 } 273*c5c4113dSnw141292} 274*c5c4113dSnw141292 275*c5c4113dSnw141292# Repeat this test sequence on database of various sizes 276*c5c4113dSnw141292# 277*c5c4113dSnw141292set testno 2 278*c5c4113dSnw141292foreach {N L} { 279*c5c4113dSnw141292 10 2 280*c5c4113dSnw141292 50 2 281*c5c4113dSnw141292 200 3 282*c5c4113dSnw141292 2000 5 283*c5c4113dSnw141292} { 284*c5c4113dSnw141292 puts "**** N=$N L=$L ****" 285*c5c4113dSnw141292 set hash [md5file test2.bt] 286*c5c4113dSnw141292 do_test btree2-$testno.1 [subst -nocommands { 287*c5c4113dSnw141292 set ::c2 [btree_cursor $::b 2 1] 288*c5c4113dSnw141292 set ::c3 [btree_cursor $::b 3 1] 289*c5c4113dSnw141292 set ::c4 [btree_cursor $::b 4 1] 290*c5c4113dSnw141292 set ::c5 [btree_cursor $::b 5 1] 291*c5c4113dSnw141292 set ::c6 [btree_cursor $::b 6 1] 292*c5c4113dSnw141292 btree_begin_transaction $::b 293*c5c4113dSnw141292 build_db $N $L 294*c5c4113dSnw141292 check_invariants 295*c5c4113dSnw141292 }] {} 296*c5c4113dSnw141292 do_test btree2-$testno.2 { 297*c5c4113dSnw141292 btree_close_cursor $::c2 298*c5c4113dSnw141292 btree_close_cursor $::c3 299*c5c4113dSnw141292 btree_close_cursor $::c4 300*c5c4113dSnw141292 btree_close_cursor $::c5 301*c5c4113dSnw141292 btree_close_cursor $::c6 302*c5c4113dSnw141292 btree_rollback $::b 303*c5c4113dSnw141292 md5file test2.bt 304*c5c4113dSnw141292 } $hash 305*c5c4113dSnw141292 do_test btree2-$testno.3 [subst -nocommands { 306*c5c4113dSnw141292 btree_begin_transaction $::b 307*c5c4113dSnw141292 set ::c2 [btree_cursor $::b 2 1] 308*c5c4113dSnw141292 set ::c3 [btree_cursor $::b 3 1] 309*c5c4113dSnw141292 set ::c4 [btree_cursor $::b 4 1] 310*c5c4113dSnw141292 set ::c5 [btree_cursor $::b 5 1] 311*c5c4113dSnw141292 set ::c6 [btree_cursor $::b 6 1] 312*c5c4113dSnw141292 build_db $N $L 313*c5c4113dSnw141292 check_invariants 314*c5c4113dSnw141292 }] {} 315*c5c4113dSnw141292 do_test btree2-$testno.4 { 316*c5c4113dSnw141292 btree_commit $::b 317*c5c4113dSnw141292 check_invariants 318*c5c4113dSnw141292 } {} 319*c5c4113dSnw141292 do_test btree2-$testno.5 { 320*c5c4113dSnw141292 lindex [btree_pager_stats $::b] 1 321*c5c4113dSnw141292 } {6} 322*c5c4113dSnw141292 do_test btree2-$testno.6 { 323*c5c4113dSnw141292 btree_close_cursor $::c2 324*c5c4113dSnw141292 btree_close_cursor $::c3 325*c5c4113dSnw141292 btree_close_cursor $::c4 326*c5c4113dSnw141292 btree_close_cursor $::c5 327*c5c4113dSnw141292 btree_close_cursor $::c6 328*c5c4113dSnw141292 lindex [btree_pager_stats $::b] 1 329*c5c4113dSnw141292 } {0} 330*c5c4113dSnw141292 do_test btree2-$testno.7 { 331*c5c4113dSnw141292 btree_close $::b 332*c5c4113dSnw141292 } {} 333*c5c4113dSnw141292after 100 334*c5c4113dSnw141292 # For each database size, run various changes tests. 335*c5c4113dSnw141292 # 336*c5c4113dSnw141292 set num2 1 337*c5c4113dSnw141292 foreach {n I K D} { 338*c5c4113dSnw141292 0.5 0.5 0.1 0.1 339*c5c4113dSnw141292 1.0 0.2 0.1 0.1 340*c5c4113dSnw141292 1.0 0.8 0.1 0.1 341*c5c4113dSnw141292 2.0 0.0 0.1 0.1 342*c5c4113dSnw141292 2.0 1.0 0.1 0.1 343*c5c4113dSnw141292 2.0 0.0 0.0 0.0 344*c5c4113dSnw141292 2.0 1.0 0.0 0.0 345*c5c4113dSnw141292 } { 346*c5c4113dSnw141292 set testid btree2-$testno.8.$num2 347*c5c4113dSnw141292 set hash [md5file test2.bt] 348*c5c4113dSnw141292 do_test $testid.0 { 349*c5c4113dSnw141292 set ::b [btree_open test2.bt] 350*c5c4113dSnw141292 set ::c2 [btree_cursor $::b 2 1] 351*c5c4113dSnw141292 set ::c3 [btree_cursor $::b 3 1] 352*c5c4113dSnw141292 set ::c4 [btree_cursor $::b 4 1] 353*c5c4113dSnw141292 set ::c5 [btree_cursor $::b 5 1] 354*c5c4113dSnw141292 set ::c6 [btree_cursor $::b 6 1] 355*c5c4113dSnw141292 check_invariants 356*c5c4113dSnw141292 } {} 357*c5c4113dSnw141292 set cnt 6 358*c5c4113dSnw141292 for {set i 2} {$i<=6} {incr i} { 359*c5c4113dSnw141292 if {[lindex [btree_cursor_dump [set ::c$i]] 0]!=$i} {incr cnt} 360*c5c4113dSnw141292 } 361*c5c4113dSnw141292 do_test $testid.1 { 362*c5c4113dSnw141292 btree_begin_transaction $::b 363*c5c4113dSnw141292 lindex [btree_pager_stats $::b] 1 364*c5c4113dSnw141292 } $cnt 365*c5c4113dSnw141292 # exec cp test2.bt test2.bt.bu1 366*c5c4113dSnw141292 do_test $testid.2 [subst { 367*c5c4113dSnw141292 random_changes $n $I $K $D 368*c5c4113dSnw141292 }] {} 369*c5c4113dSnw141292 do_test $testid.3 { 370*c5c4113dSnw141292 check_invariants 371*c5c4113dSnw141292 } {} 372*c5c4113dSnw141292 do_test $testid.4 { 373*c5c4113dSnw141292 btree_close_cursor $::c2 374*c5c4113dSnw141292 btree_close_cursor $::c3 375*c5c4113dSnw141292 btree_close_cursor $::c4 376*c5c4113dSnw141292 btree_close_cursor $::c5 377*c5c4113dSnw141292 btree_close_cursor $::c6 378*c5c4113dSnw141292 btree_rollback $::b 379*c5c4113dSnw141292 md5file test2.bt 380*c5c4113dSnw141292 } $hash 381*c5c4113dSnw141292 # exec cp test2.bt test2.bt.bu2 382*c5c4113dSnw141292 btree_begin_transaction $::b 383*c5c4113dSnw141292 set ::c2 [btree_cursor $::b 2 1] 384*c5c4113dSnw141292 set ::c3 [btree_cursor $::b 3 1] 385*c5c4113dSnw141292 set ::c4 [btree_cursor $::b 4 1] 386*c5c4113dSnw141292 set ::c5 [btree_cursor $::b 5 1] 387*c5c4113dSnw141292 set ::c6 [btree_cursor $::b 6 1] 388*c5c4113dSnw141292 do_test $testid.5 [subst { 389*c5c4113dSnw141292 random_changes $n $I $K $D 390*c5c4113dSnw141292 }] {} 391*c5c4113dSnw141292 do_test $testid.6 { 392*c5c4113dSnw141292 check_invariants 393*c5c4113dSnw141292 } {} 394*c5c4113dSnw141292 do_test $testid.7 { 395*c5c4113dSnw141292 btree_commit $::b 396*c5c4113dSnw141292 check_invariants 397*c5c4113dSnw141292 } {} 398*c5c4113dSnw141292 set hash [md5file test2.bt] 399*c5c4113dSnw141292 do_test $testid.8 { 400*c5c4113dSnw141292 btree_close_cursor $::c2 401*c5c4113dSnw141292 btree_close_cursor $::c3 402*c5c4113dSnw141292 btree_close_cursor $::c4 403*c5c4113dSnw141292 btree_close_cursor $::c5 404*c5c4113dSnw141292 btree_close_cursor $::c6 405*c5c4113dSnw141292 lindex [btree_pager_stats $::b] 1 406*c5c4113dSnw141292 } {0} 407*c5c4113dSnw141292 do_test $testid.9 { 408*c5c4113dSnw141292 btree_close $::b 409*c5c4113dSnw141292 set ::b [btree_open test2.bt] 410*c5c4113dSnw141292 set ::c2 [btree_cursor $::b 2 1] 411*c5c4113dSnw141292 set ::c3 [btree_cursor $::b 3 1] 412*c5c4113dSnw141292 set ::c4 [btree_cursor $::b 4 1] 413*c5c4113dSnw141292 set ::c5 [btree_cursor $::b 5 1] 414*c5c4113dSnw141292 set ::c6 [btree_cursor $::b 6 1] 415*c5c4113dSnw141292 check_invariants 416*c5c4113dSnw141292 } {} 417*c5c4113dSnw141292 do_test $testid.10 { 418*c5c4113dSnw141292 btree_close_cursor $::c2 419*c5c4113dSnw141292 btree_close_cursor $::c3 420*c5c4113dSnw141292 btree_close_cursor $::c4 421*c5c4113dSnw141292 btree_close_cursor $::c5 422*c5c4113dSnw141292 btree_close_cursor $::c6 423*c5c4113dSnw141292 lindex [btree_pager_stats $::b] 1 424*c5c4113dSnw141292 } {0} 425*c5c4113dSnw141292 do_test $testid.11 { 426*c5c4113dSnw141292 btree_close $::b 427*c5c4113dSnw141292 } {} 428*c5c4113dSnw141292 incr num2 429*c5c4113dSnw141292 } 430*c5c4113dSnw141292 incr testno 431*c5c4113dSnw141292 set ::b [btree_open test2.bt] 432*c5c4113dSnw141292} 433*c5c4113dSnw141292 434*c5c4113dSnw141292# Testing is complete. Shut everything down. 435*c5c4113dSnw141292# 436*c5c4113dSnw141292do_test btree-999.1 { 437*c5c4113dSnw141292 lindex [btree_pager_stats $::b] 1 438*c5c4113dSnw141292} {0} 439*c5c4113dSnw141292do_test btree-999.2 { 440*c5c4113dSnw141292 btree_close $::b 441*c5c4113dSnw141292} {} 442*c5c4113dSnw141292do_test btree-999.3 { 443*c5c4113dSnw141292 file delete -force test2.bt 444*c5c4113dSnw141292 file exists test2.bt-journal 445*c5c4113dSnw141292} {0} 446*c5c4113dSnw141292 447*c5c4113dSnw141292} ;# end if( not mem: and has pager_open command ); 448*c5c4113dSnw141292 449*c5c4113dSnw141292finish_test 450