1# 2010 June 15 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 13set testdir [file dirname $argv0] 14source $testdir/tester.tcl 15source $testdir/lock_common.tcl 16source $testdir/malloc_common.tcl 17source $testdir/wal_common.tcl 18set testprefix pager1 19 20if {[atomic_batch_write test.db]} { 21 finish_test 22 return 23} 24 25# Do not use a codec for tests in this file, as the database file is 26# manipulated directly using tcl scripts (using the [hexio_write] command). 27# 28do_not_use_codec 29 30# 31# pager1-1.*: Test inter-process locking (clients in multiple processes). 32# 33# pager1-2.*: Test intra-process locking (multiple clients in this process). 34# 35# pager1-3.*: Savepoint related tests. 36# 37# pager1-4.*: Hot-journal related tests. 38# 39# pager1-5.*: Cases related to multi-file commits. 40# 41# pager1-6.*: Cases related to "PRAGMA max_page_count" 42# 43# pager1-7.*: Cases specific to "PRAGMA journal_mode=TRUNCATE" 44# 45# pager1-8.*: Cases using temporary and in-memory databases. 46# 47# pager1-9.*: Tests related to the backup API. 48# 49# pager1-10.*: Test that the assumed file-system sector-size is limited to 50# 64KB. 51# 52# pager1-12.*: Tests involving "PRAGMA page_size" 53# 54# pager1-13.*: Cases specific to "PRAGMA journal_mode=PERSIST" 55# 56# pager1-14.*: Cases specific to "PRAGMA journal_mode=OFF" 57# 58# pager1-15.*: Varying sqlite3_vfs.szOsFile 59# 60# pager1-16.*: Varying sqlite3_vfs.mxPathname 61# 62# pager1-17.*: Tests related to "PRAGMA omit_readlock" 63# (The omit_readlock pragma has been removed and so have 64# these tests.) 65# 66# pager1-18.*: Test that the pager layer responds correctly if the b-tree 67# requests an invalid page number (due to db corruption). 68# 69 70proc recursive_select {id table {script {}}} { 71 set cnt 0 72 db eval "SELECT rowid, * FROM $table WHERE rowid = ($id-1)" { 73 recursive_select $rowid $table $script 74 incr cnt 75 } 76 if {$cnt==0} { eval $script } 77} 78 79set a_string_counter 1 80proc a_string {n} { 81 global a_string_counter 82 incr a_string_counter 83 string range [string repeat "${a_string_counter}." $n] 1 $n 84} 85db func a_string a_string 86 87do_multiclient_test tn { 88 89 # Create and populate a database table using connection [db]. Check 90 # that connections [db2] and [db3] can see the schema and content. 91 # 92 do_test pager1-$tn.1 { 93 sql1 { 94 CREATE TABLE t1(a PRIMARY KEY, b); 95 CREATE INDEX i1 ON t1(b); 96 INSERT INTO t1 VALUES(1, 'one'); INSERT INTO t1 VALUES(2, 'two'); 97 } 98 } {} 99 do_test pager1-$tn.2 { sql2 { SELECT * FROM t1 } } {1 one 2 two} 100 do_test pager1-$tn.3 { sql3 { SELECT * FROM t1 } } {1 one 2 two} 101 102 # Open a transaction and add a row using [db]. This puts [db] in 103 # RESERVED state. Check that connections [db2] and [db3] can still 104 # read the database content as it was before the transaction was 105 # opened. [db] should see the inserted row. 106 # 107 do_test pager1-$tn.4 { 108 sql1 { 109 BEGIN; 110 INSERT INTO t1 VALUES(3, 'three'); 111 } 112 } {} 113 do_test pager1-$tn.5 { sql2 { SELECT * FROM t1 } } {1 one 2 two} 114 do_test pager1-$tn.7 { sql1 { SELECT * FROM t1 } } {1 one 2 two 3 three} 115 116 # [db] still has an open write transaction. Check that this prevents 117 # other connections (specifically [db2]) from writing to the database. 118 # 119 # Even if [db2] opens a transaction first, it may not write to the 120 # database. After the attempt to write the db within a transaction, 121 # [db2] is left with an open transaction, but not a read-lock on 122 # the main database. So it does not prevent [db] from committing. 123 # 124 do_test pager1-$tn.8 { 125 csql2 { UPDATE t1 SET a = a + 10 } 126 } {1 {database is locked}} 127 do_test pager1-$tn.9 { 128 csql2 { 129 BEGIN; 130 UPDATE t1 SET a = a + 10; 131 } 132 } {1 {database is locked}} 133 134 # Have [db] commit its transactions. Check the other connections can 135 # now see the new database content. 136 # 137 do_test pager1-$tn.10 { sql1 { COMMIT } } {} 138 do_test pager1-$tn.11 { sql1 { SELECT * FROM t1 } } {1 one 2 two 3 three} 139 do_test pager1-$tn.12 { sql2 { SELECT * FROM t1 } } {1 one 2 two 3 three} 140 do_test pager1-$tn.13 { sql3 { SELECT * FROM t1 } } {1 one 2 two 3 three} 141 142 # Check that, as noted above, [db2] really did keep an open transaction 143 # after the attempt to write the database failed. 144 # 145 do_test pager1-$tn.14 { 146 csql2 { BEGIN } 147 } {1 {cannot start a transaction within a transaction}} 148 do_test pager1-$tn.15 { sql2 { ROLLBACK } } {} 149 150 # Have [db2] open a transaction and take a read-lock on the database. 151 # Check that this prevents [db] from writing to the database (outside 152 # of any transaction). After this fails, check that [db3] can read 153 # the db (showing that [db] did not take a PENDING lock etc.) 154 # 155 do_test pager1-$tn.15 { 156 sql2 { BEGIN; SELECT * FROM t1; } 157 } {1 one 2 two 3 three} 158 do_test pager1-$tn.16 { 159 csql1 { UPDATE t1 SET a = a + 10 } 160 } {1 {database is locked}} 161 do_test pager1-$tn.17 { sql3 { SELECT * FROM t1 } } {1 one 2 two 3 three} 162 163 # This time, have [db] open a transaction before writing the database. 164 # This works - [db] gets a RESERVED lock which does not conflict with 165 # the SHARED lock [db2] is holding. 166 # 167 do_test pager1-$tn.18 { 168 sql1 { 169 BEGIN; 170 UPDATE t1 SET a = a + 10; 171 } 172 } {} 173 do_test pager1-$tn-19 { 174 sql1 { PRAGMA lock_status } 175 } {main reserved temp closed} 176 do_test pager1-$tn-20 { 177 sql2 { PRAGMA lock_status } 178 } {main shared temp closed} 179 180 # Check that all connections can still read the database. Only [db] sees 181 # the updated content (as the transaction has not been committed yet). 182 # 183 do_test pager1-$tn.21 { sql1 { SELECT * FROM t1 } } {11 one 12 two 13 three} 184 do_test pager1-$tn.22 { sql2 { SELECT * FROM t1 } } {1 one 2 two 3 three} 185 do_test pager1-$tn.23 { sql3 { SELECT * FROM t1 } } {1 one 2 two 3 three} 186 187 # Because [db2] still has the SHARED lock, [db] is unable to commit the 188 # transaction. If it tries, an error is returned and the connection 189 # upgrades to a PENDING lock. 190 # 191 # Once this happens, [db] can read the database and see the new content, 192 # [db2] (still holding SHARED) can still read the old content, but [db3] 193 # (not holding any lock) is prevented by [db]'s PENDING from reading 194 # the database. 195 # 196 do_test pager1-$tn.24 { csql1 { COMMIT } } {1 {database is locked}} 197 do_test pager1-$tn-25 { 198 sql1 { PRAGMA lock_status } 199 } {main pending temp closed} 200 do_test pager1-$tn.26 { sql1 { SELECT * FROM t1 } } {11 one 12 two 13 three} 201 do_test pager1-$tn.27 { sql2 { SELECT * FROM t1 } } {1 one 2 two 3 three} 202 do_test pager1-$tn.28 { csql3 { SELECT * FROM t1 } } {1 {database is locked}} 203 204 # Have [db2] commit its read transaction, releasing the SHARED lock it 205 # is holding. Now, neither [db2] nor [db3] may read the database (as [db] 206 # is still holding a PENDING). 207 # 208 do_test pager1-$tn.29 { sql2 { COMMIT } } {} 209 do_test pager1-$tn.30 { csql2 { SELECT * FROM t1 } } {1 {database is locked}} 210 do_test pager1-$tn.31 { csql3 { SELECT * FROM t1 } } {1 {database is locked}} 211 212 # [db] is now able to commit the transaction. Once the transaction is 213 # committed, all three connections can read the new content. 214 # 215 do_test pager1-$tn.25 { sql1 { UPDATE t1 SET a = a+10 } } {} 216 do_test pager1-$tn.26 { sql1 { COMMIT } } {} 217 do_test pager1-$tn.27 { sql1 { SELECT * FROM t1 } } {21 one 22 two 23 three} 218 do_test pager1-$tn.27 { sql2 { SELECT * FROM t1 } } {21 one 22 two 23 three} 219 do_test pager1-$tn.28 { sql3 { SELECT * FROM t1 } } {21 one 22 two 23 three} 220 221 # Install a busy-handler for connection [db]. 222 # 223 set ::nbusy [list] 224 proc busy {n} { 225 lappend ::nbusy $n 226 if {$n>5} { sql2 COMMIT } 227 return 0 228 } 229 db busy busy 230 231 do_test pager1-$tn.29 { 232 sql1 { BEGIN ; INSERT INTO t1 VALUES('x', 'y') } 233 } {} 234 do_test pager1-$tn.30 { 235 sql2 { BEGIN ; SELECT * FROM t1 } 236 } {21 one 22 two 23 three} 237 do_test pager1-$tn.31 { sql1 COMMIT } {} 238 do_test pager1-$tn.32 { set ::nbusy } {0 1 2 3 4 5 6} 239} 240 241#------------------------------------------------------------------------- 242# Savepoint related test cases. 243# 244# pager1-3.1.2.*: Force a savepoint rollback to cause the database file 245# to grow. 246# 247# pager1-3.1.3.*: Use a journal created in synchronous=off mode as part 248# of a savepoint rollback. 249# 250do_test pager1-3.1.1 { 251 faultsim_delete_and_reopen 252 execsql { 253 CREATE TABLE t1(a PRIMARY KEY, b); 254 CREATE TABLE counter( 255 i CHECK (i<5), 256 u CHECK (u<10) 257 ); 258 INSERT INTO counter VALUES(0, 0); 259 CREATE TRIGGER tr1 AFTER INSERT ON t1 BEGIN 260 UPDATE counter SET i = i+1; 261 END; 262 CREATE TRIGGER tr2 AFTER UPDATE ON t1 BEGIN 263 UPDATE counter SET u = u+1; 264 END; 265 } 266 execsql { SELECT * FROM counter } 267} {0 0} 268 269do_execsql_test pager1-3.1.2 { 270 PRAGMA cache_size = 10; 271 BEGIN; 272 INSERT INTO t1 VALUES(1, randomblob(1500)); 273 INSERT INTO t1 VALUES(2, randomblob(1500)); 274 INSERT INTO t1 VALUES(3, randomblob(1500)); 275 SELECT * FROM counter; 276} {3 0} 277do_catchsql_test pager1-3.1.3 { 278 INSERT INTO t1 SELECT a+3, randomblob(1500) FROM t1 279} {1 {CHECK constraint failed: i<5}} 280do_execsql_test pager1-3.4 { SELECT * FROM counter } {3 0} 281do_execsql_test pager1-3.5 { SELECT a FROM t1 } {1 2 3} 282do_execsql_test pager1-3.6 { COMMIT } {} 283 284foreach {tn sql tcl} { 285 7 { PRAGMA synchronous = NORMAL ; PRAGMA temp_store = 0 } { 286 testvfs tv -default 1 287 tv devchar safe_append 288 } 289 8 { PRAGMA synchronous = NORMAL ; PRAGMA temp_store = 2 } { 290 testvfs tv -default 1 291 tv devchar sequential 292 } 293 9 { PRAGMA synchronous = FULL } { } 294 10 { PRAGMA synchronous = NORMAL } { } 295 11 { PRAGMA synchronous = OFF } { } 296 12 { PRAGMA synchronous = FULL ; PRAGMA fullfsync = 1 } { } 297 13 { PRAGMA synchronous = FULL } { 298 testvfs tv -default 1 299 tv devchar sequential 300 } 301 14 { PRAGMA locking_mode = EXCLUSIVE } { 302 } 303} { 304 do_test pager1-3.$tn.1 { 305 eval $tcl 306 faultsim_delete_and_reopen 307 db func a_string a_string 308 execsql $sql 309 execsql { 310 PRAGMA auto_vacuum = 2; 311 PRAGMA cache_size = 10; 312 CREATE TABLE z(x INTEGER PRIMARY KEY, y); 313 BEGIN; 314 INSERT INTO z VALUES(NULL, a_string(800)); 315 INSERT INTO z SELECT NULL, a_string(800) FROM z; -- 2 316 INSERT INTO z SELECT NULL, a_string(800) FROM z; -- 4 317 INSERT INTO z SELECT NULL, a_string(800) FROM z; -- 8 318 INSERT INTO z SELECT NULL, a_string(800) FROM z; -- 16 319 INSERT INTO z SELECT NULL, a_string(800) FROM z; -- 32 320 INSERT INTO z SELECT NULL, a_string(800) FROM z; -- 64 321 INSERT INTO z SELECT NULL, a_string(800) FROM z; -- 128 322 INSERT INTO z SELECT NULL, a_string(800) FROM z; -- 256 323 COMMIT; 324 } 325 execsql { PRAGMA auto_vacuum } 326 } {2} 327 do_execsql_test pager1-3.$tn.2 { 328 BEGIN; 329 INSERT INTO z VALUES(NULL, a_string(800)); 330 INSERT INTO z VALUES(NULL, a_string(800)); 331 SAVEPOINT one; 332 UPDATE z SET y = NULL WHERE x>256; 333 PRAGMA incremental_vacuum; 334 SELECT count(*) FROM z WHERE x < 100; 335 ROLLBACK TO one; 336 COMMIT; 337 } {99} 338 339 do_execsql_test pager1-3.$tn.3 { 340 BEGIN; 341 SAVEPOINT one; 342 UPDATE z SET y = y||x; 343 ROLLBACK TO one; 344 COMMIT; 345 SELECT count(*) FROM z; 346 } {258} 347 348 do_execsql_test pager1-3.$tn.4 { 349 SAVEPOINT one; 350 UPDATE z SET y = y||x; 351 ROLLBACK TO one; 352 } {} 353 do_execsql_test pager1-3.$tn.5 { 354 SELECT count(*) FROM z; 355 RELEASE one; 356 PRAGMA integrity_check; 357 } {258 ok} 358 359 do_execsql_test pager1-3.$tn.6 { 360 SAVEPOINT one; 361 RELEASE one; 362 } {} 363 364 db close 365 catch { tv delete } 366} 367 368#------------------------------------------------------------------------- 369# Hot journal rollback related test cases. 370# 371# pager1.4.1.*: Test that the pager module deletes very small invalid 372# journal files. 373# 374# pager1.4.2.*: Test that if the master journal pointer at the end of a 375# hot-journal file appears to be corrupt (checksum does not 376# compute) the associated journal is rolled back (and no 377# xAccess() call to check for the presence of any master 378# journal file is made). 379# 380# pager1.4.3.*: Test that the contents of a hot-journal are ignored if the 381# page-size or sector-size in the journal header appear to 382# be invalid (too large, too small or not a power of 2). 383# 384# pager1.4.4.*: Test hot-journal rollback of journal file with a master 385# journal pointer generated in various "PRAGMA synchronous" 386# modes. 387# 388# pager1.4.5.*: Test that hot-journal rollback stops if it encounters a 389# journal-record for which the checksum fails. 390# 391# pager1.4.6.*: Test that when rolling back a hot-journal that contains a 392# master journal pointer, the master journal file is deleted 393# after all the hot-journals that refer to it are deleted. 394# 395# pager1.4.7.*: Test that if a hot-journal file exists but a client can 396# open it for reading only, the database cannot be accessed and 397# SQLITE_CANTOPEN is returned. 398# 399do_test pager1.4.1.1 { 400 faultsim_delete_and_reopen 401 execsql { 402 CREATE TABLE x(y, z); 403 INSERT INTO x VALUES(1, 2); 404 } 405 set fd [open test.db-journal w] 406 puts -nonewline $fd "helloworld" 407 close $fd 408 file exists test.db-journal 409} {1} 410do_test pager1.4.1.2 { execsql { SELECT * FROM x } } {1 2} 411do_test pager1.4.1.3 { file exists test.db-journal } {0} 412 413# Set up a [testvfs] to snapshot the file-system just before SQLite 414# deletes the master-journal to commit a multi-file transaction. 415# 416# In subsequent test cases, invoking [faultsim_restore_and_reopen] sets 417# up the file system to contain two databases, two hot-journal files and 418# a master-journal. 419# 420do_test pager1.4.2.1 { 421 testvfs tstvfs -default 1 422 tstvfs filter xDelete 423 tstvfs script xDeleteCallback 424 proc xDeleteCallback {method file args} { 425 set file [file tail $file] 426 if { [string match *mj* $file] } { faultsim_save } 427 } 428 faultsim_delete_and_reopen 429 db func a_string a_string 430 execsql { 431 ATTACH 'test.db2' AS aux; 432 PRAGMA journal_mode = DELETE; 433 PRAGMA main.cache_size = 10; 434 PRAGMA aux.cache_size = 10; 435 CREATE TABLE t1(a UNIQUE, b UNIQUE); 436 CREATE TABLE aux.t2(a UNIQUE, b UNIQUE); 437 INSERT INTO t1 VALUES(a_string(200), a_string(300)); 438 INSERT INTO t1 SELECT a_string(200), a_string(300) FROM t1; 439 INSERT INTO t1 SELECT a_string(200), a_string(300) FROM t1; 440 INSERT INTO t2 SELECT * FROM t1; 441 BEGIN; 442 INSERT INTO t1 SELECT a_string(201), a_string(301) FROM t1; 443 INSERT INTO t1 SELECT a_string(202), a_string(302) FROM t1; 444 INSERT INTO t1 SELECT a_string(203), a_string(303) FROM t1; 445 INSERT INTO t1 SELECT a_string(204), a_string(304) FROM t1; 446 REPLACE INTO t2 SELECT * FROM t1; 447 COMMIT; 448 } 449 db close 450 tstvfs delete 451} {} 452 453if {$::tcl_platform(platform)!="windows"} { 454do_test pager1.4.2.2 { 455 faultsim_restore_and_reopen 456 execsql { 457 SELECT count(*) FROM t1; 458 PRAGMA integrity_check; 459 } 460} {4 ok} 461do_test pager1.4.2.3 { 462 faultsim_restore_and_reopen 463 foreach f [glob test.db-mj*] { forcedelete $f } 464 execsql { 465 SELECT count(*) FROM t1; 466 PRAGMA integrity_check; 467 } 468} {64 ok} 469do_test pager1.4.2.4 { 470 faultsim_restore_and_reopen 471 hexio_write test.db-journal [expr [file size test.db-journal]-30] 123456 472 execsql { 473 SELECT count(*) FROM t1; 474 PRAGMA integrity_check; 475 } 476} {4 ok} 477do_test pager1.4.2.5 { 478 faultsim_restore_and_reopen 479 hexio_write test.db-journal [expr [file size test.db-journal]-30] 123456 480 foreach f [glob test.db-mj*] { forcedelete $f } 481 execsql { 482 SELECT count(*) FROM t1; 483 PRAGMA integrity_check; 484 } 485} {4 ok} 486} 487 488do_test pager1.4.3.1 { 489 testvfs tstvfs -default 1 490 tstvfs filter xSync 491 tstvfs script xSyncCallback 492 proc xSyncCallback {method file args} { 493 set file [file tail $file] 494 if { 0==[string match *journal $file] } { faultsim_save } 495 } 496 faultsim_delete_and_reopen 497 execsql { 498 PRAGMA journal_mode = DELETE; 499 CREATE TABLE t1(a, b); 500 INSERT INTO t1 VALUES(1, 2); 501 INSERT INTO t1 VALUES(3, 4); 502 } 503 db close 504 tstvfs delete 505} {} 506 507foreach {tn ofst value result} { 508 2 20 31 {1 2 3 4} 509 3 20 32 {1 2 3 4} 510 4 20 33 {1 2 3 4} 511 5 20 65536 {1 2 3 4} 512 6 20 131072 {1 2 3 4} 513 514 7 24 511 {1 2 3 4} 515 8 24 513 {1 2 3 4} 516 9 24 131072 {1 2 3 4} 517 518 10 32 65536 {1 2} 519} { 520 do_test pager1.4.3.$tn { 521 faultsim_restore_and_reopen 522 hexio_write test.db-journal $ofst [format %.8x $value] 523 execsql { SELECT * FROM t1 } 524 } $result 525} 526db close 527 528# Set up a VFS that snapshots the file-system just before a master journal 529# file is deleted to commit a multi-file transaction. Specifically, the 530# file-system is saved just before the xDelete() call to remove the 531# master journal file from the file-system. 532# 533set pwd [get_pwd] 534testvfs tv -default 1 535tv script copy_on_mj_delete 536set ::mj_filename_length 0 537set ::mj_delete_cnt 0 538proc copy_on_mj_delete {method filename args} { 539 if {[string match *mj* [file tail $filename]]} { 540 # 541 # NOTE: Is the file name relative? If so, add the length of the current 542 # directory. 543 # 544 if {[is_relative_file $filename]} { 545 set ::mj_filename_length \ 546 [expr {[string length $filename] + [string length $::pwd]}] 547 } else { 548 set ::mj_filename_length [string length $filename] 549 } 550 faultsim_save 551 incr ::mj_delete_cnt 552 } 553 return SQLITE_OK 554} 555 556foreach {tn1 tcl} { 557 1 { set prefix "test.db" } 558 2 { 559 # This test depends on the underlying VFS being able to open paths 560 # 512 bytes in length. The idea is to create a hot-journal file that 561 # contains a master-journal pointer so large that it could contain 562 # a valid page record (if the file page-size is 512 bytes). So as to 563 # make sure SQLite doesn't get confused by this. 564 # 565 set nPadding [expr 511 - $::mj_filename_length] 566 if {$tcl_platform(platform)=="windows"} { 567 # TBD need to figure out how to do this correctly for Windows!!! 568 set nPadding [expr 255 - $::mj_filename_length] 569 } 570 571 # We cannot just create a really long database file name to open, as 572 # Linux limits a single component of a path to 255 bytes by default 573 # (and presumably other systems have limits too). So create a directory 574 # hierarchy to work in. 575 # 576 set dirname "d123456789012345678901234567890/" 577 set nDir [expr $nPadding / 32] 578 if { $nDir } { 579 set p [string repeat $dirname $nDir] 580 file mkdir $p 581 cd $p 582 } 583 584 set padding [string repeat x [expr $nPadding %32]] 585 set prefix "test.db${padding}" 586 } 587} { 588 eval $tcl 589 foreach {tn2 sql usesMJ} { 590 o { 591 PRAGMA main.synchronous=OFF; 592 PRAGMA aux.synchronous=OFF; 593 PRAGMA journal_mode = DELETE; 594 } 0 595 o512 { 596 PRAGMA main.synchronous=OFF; 597 PRAGMA aux.synchronous=OFF; 598 PRAGMA main.page_size = 512; 599 PRAGMA aux.page_size = 512; 600 PRAGMA journal_mode = DELETE; 601 } 0 602 n { 603 PRAGMA main.synchronous=NORMAL; 604 PRAGMA aux.synchronous=NORMAL; 605 PRAGMA journal_mode = DELETE; 606 } 1 607 f { 608 PRAGMA main.synchronous=FULL; 609 PRAGMA aux.synchronous=FULL; 610 PRAGMA journal_mode = DELETE; 611 } 1 612 w1 { 613 PRAGMA main.synchronous=NORMAL; 614 PRAGMA aux.synchronous=NORMAL; 615 PRAGMA journal_mode = WAL; 616 } 0 617 w2 { 618 PRAGMA main.synchronous=NORMAL; 619 PRAGMA aux.synchronous=NORMAL; 620 PRAGMA main.journal_mode=DELETE; 621 PRAGMA aux.journal_mode=WAL; 622 } 0 623 o1a { 624 PRAGMA main.synchronous=FULL; 625 PRAGMA aux.synchronous=OFF; 626 PRAGMA journal_mode=DELETE; 627 } 0 628 o1b { 629 PRAGMA main.synchronous=OFF; 630 PRAGMA aux.synchronous=NORMAL; 631 PRAGMA journal_mode=DELETE; 632 } 0 633 m1 { 634 PRAGMA main.synchronous=NORMAL; 635 PRAGMA aux.synchronous=NORMAL; 636 PRAGMA main.journal_mode=DELETE; 637 PRAGMA aux.journal_mode = MEMORY; 638 } 0 639 t1 { 640 PRAGMA main.synchronous=NORMAL; 641 PRAGMA aux.synchronous=NORMAL; 642 PRAGMA main.journal_mode=DELETE; 643 PRAGMA aux.journal_mode = TRUNCATE; 644 } 1 645 p1 { 646 PRAGMA main.synchronous=NORMAL; 647 PRAGMA aux.synchronous=NORMAL; 648 PRAGMA main.journal_mode=DELETE; 649 PRAGMA aux.journal_mode = PERSIST; 650 } 1 651 } { 652 653 set tn "${tn1}.${tn2}" 654 655 # Set up a connection to have two databases, test.db (main) and 656 # test.db2 (aux). Then run a multi-file transaction on them. The 657 # VFS will snapshot the file-system just before the master-journal 658 # file is deleted to commit the transaction. 659 # 660 tv filter xDelete 661 do_test pager1-4.4.$tn.1 { 662 set ::mj_delete_cnt 0 663 faultsim_delete_and_reopen $prefix 664 execsql " 665 ATTACH '${prefix}2' AS aux; 666 $sql 667 CREATE TABLE a(x); 668 CREATE TABLE aux.b(x); 669 INSERT INTO a VALUES('double-you'); 670 INSERT INTO a VALUES('why'); 671 INSERT INTO a VALUES('zed'); 672 INSERT INTO b VALUES('won'); 673 INSERT INTO b VALUES('too'); 674 INSERT INTO b VALUES('free'); 675 " 676 execsql { 677 BEGIN; 678 INSERT INTO a SELECT * FROM b WHERE rowid<=3; 679 INSERT INTO b SELECT * FROM a WHERE rowid<=3; 680 COMMIT; 681 } 682 } {} 683 tv filter {} 684 685 # Verify that a master journal was deleted only for those cases where 686 # master journals really ought to be used 687 # 688 do_test pager1-4.4.$tn.1b { 689 set ::mj_delete_cnt 690 } $usesMJ 691 692 # Check that the transaction was committed successfully. 693 # 694 do_execsql_test pager1-4.4.$tn.2 { 695 SELECT * FROM a 696 } {double-you why zed won too free} 697 do_execsql_test pager1-4.4.$tn.3 { 698 SELECT * FROM b 699 } {won too free double-you why zed} 700 701 if {$usesMJ} { 702 # Restore the file-system and reopen the databases. Check that it now 703 # appears that the transaction was not committed (because the file-system 704 # was restored to the state where it had not been). 705 # 706 do_test pager1-4.4.$tn.4 { 707 faultsim_restore_and_reopen $prefix 708 execsql "ATTACH '${prefix}2' AS aux" 709 } {} 710 do_execsql_test pager1-4.4.$tn.5 {SELECT * FROM a} {double-you why zed} 711 do_execsql_test pager1-4.4.$tn.6 {SELECT * FROM b} {won too free} 712 } 713 714 # Restore the file-system again. This time, before reopening the databases, 715 # delete the master-journal file from the file-system. It now appears that 716 # the transaction was committed (no master-journal file == no rollback). 717 # 718 do_test pager1-4.4.$tn.7 { 719 if {$::mj_delete_cnt>0} { 720 faultsim_restore_and_reopen $prefix 721 foreach f [glob ${prefix}-mj*] { forcedelete $f } 722 } else { 723 db close 724 sqlite3 db $prefix 725 } 726 execsql "ATTACH '${prefix}2' AS aux" 727 glob -nocomplain ${prefix}-mj* 728 } {} 729 do_execsql_test pager1-4.4.$tn.8 { 730 SELECT * FROM a 731 } {double-you why zed won too free} 732 do_execsql_test pager1-4.4.$tn.9 { 733 SELECT * FROM b 734 } {won too free double-you why zed} 735 } 736 737 cd $pwd 738} 739db close 740tv delete 741forcedelete $dirname 742 743# Set up a VFS to make a copy of the file-system just before deleting a 744# journal file to commit a transaction. The transaction modifies exactly 745# two database pages (and page 1 - the change counter). 746# 747testvfs tv -default 1 748tv sectorsize 512 749tv script copy_on_journal_delete 750tv filter xDelete 751proc copy_on_journal_delete {method filename args} { 752 if {[string match *journal $filename]} faultsim_save 753 return SQLITE_OK 754} 755faultsim_delete_and_reopen 756do_execsql_test pager1.4.5.1 { 757 PRAGMA journal_mode = DELETE; 758 PRAGMA page_size = 1024; 759 CREATE TABLE t1(a, b); 760 CREATE TABLE t2(a, b); 761 INSERT INTO t1 VALUES('I', 'II'); 762 INSERT INTO t2 VALUES('III', 'IV'); 763 BEGIN; 764 INSERT INTO t1 VALUES(1, 2); 765 INSERT INTO t2 VALUES(3, 4); 766 COMMIT; 767} {delete} 768tv filter {} 769 770# Check the transaction was committed: 771# 772do_execsql_test pager1.4.5.2 { 773 SELECT * FROM t1; 774 SELECT * FROM t2; 775} {I II 1 2 III IV 3 4} 776 777# Now try four tests: 778# 779# pager1-4.5.3: Restore the file-system. Check that the whole transaction 780# is rolled back. 781# 782# pager1-4.5.4: Restore the file-system. Corrupt the first record in the 783# journal. Check the transaction is not rolled back. 784# 785# pager1-4.5.5: Restore the file-system. Corrupt the second record in the 786# journal. Check that the first record in the transaction is 787# played back, but not the second. 788# 789# pager1-4.5.6: Restore the file-system. Try to open the database with a 790# readonly connection. This should fail, as a read-only 791# connection cannot roll back the database file. 792# 793faultsim_restore_and_reopen 794do_execsql_test pager1.4.5.3 { 795 SELECT * FROM t1; 796 SELECT * FROM t2; 797} {I II III IV} 798faultsim_restore_and_reopen 799hexio_write test.db-journal [expr 512+4+1024 - 202] 0123456789ABCDEF 800do_execsql_test pager1.4.5.4 { 801 SELECT * FROM t1; 802 SELECT * FROM t2; 803} {I II 1 2 III IV 3 4} 804faultsim_restore_and_reopen 805hexio_write test.db-journal [expr 512+4+1024+4+4+1024 - 202] 0123456789ABCDEF 806do_execsql_test pager1.4.5.5 { 807 SELECT * FROM t1; 808 SELECT * FROM t2; 809} {I II III IV 3 4} 810 811faultsim_restore_and_reopen 812db close 813sqlite3 db test.db -readonly 1 814do_catchsql_test pager1.4.5.6 { 815 SELECT * FROM t1; 816 SELECT * FROM t2; 817} {1 {attempt to write a readonly database}} 818db close 819 820# Snapshot the file-system just before multi-file commit. Save the name 821# of the master journal file in $::mj_filename. 822# 823tv script copy_on_mj_delete 824tv filter xDelete 825proc copy_on_mj_delete {method filename args} { 826 if {[string match *mj* [file tail $filename]]} { 827 set ::mj_filename $filename 828 faultsim_save 829 } 830 return SQLITE_OK 831} 832do_test pager1.4.6.1 { 833 faultsim_delete_and_reopen 834 execsql { 835 PRAGMA journal_mode = DELETE; 836 ATTACH 'test.db2' AS two; 837 CREATE TABLE t1(a, b); 838 CREATE TABLE two.t2(a, b); 839 INSERT INTO t1 VALUES(1, 't1.1'); 840 INSERT INTO t2 VALUES(1, 't2.1'); 841 BEGIN; 842 UPDATE t1 SET b = 't1.2'; 843 UPDATE t2 SET b = 't2.2'; 844 COMMIT; 845 } 846 tv filter {} 847 db close 848} {} 849 850faultsim_restore_and_reopen 851do_execsql_test pager1.4.6.2 { SELECT * FROM t1 } {1 t1.1} 852do_test pager1.4.6.3 { file exists $::mj_filename } {1} 853do_execsql_test pager1.4.6.4 { 854 ATTACH 'test.db2' AS two; 855 SELECT * FROM t2; 856} {1 t2.1} 857do_test pager1.4.6.5 { file exists $::mj_filename } {0} 858 859faultsim_restore_and_reopen 860db close 861do_test pager1.4.6.8 { 862 set ::mj_filename1 $::mj_filename 863 tv filter xDelete 864 sqlite3 db test.db2 865 execsql { 866 PRAGMA journal_mode = DELETE; 867 ATTACH 'test.db3' AS three; 868 CREATE TABLE three.t3(a, b); 869 INSERT INTO t3 VALUES(1, 't3.1'); 870 BEGIN; 871 UPDATE t2 SET b = 't2.3'; 872 UPDATE t3 SET b = 't3.3'; 873 COMMIT; 874 } 875 expr {$::mj_filename1 != $::mj_filename} 876} {1} 877faultsim_restore_and_reopen 878tv filter {} 879 880# The file-system now contains: 881# 882# * three databases 883# * three hot-journal files 884# * two master-journal files. 885# 886# The hot-journals associated with test.db2 and test.db3 point to 887# master journal $::mj_filename. The hot-journal file associated with 888# test.db points to master journal $::mj_filename1. So reading from 889# test.db should delete $::mj_filename1. 890# 891do_test pager1.4.6.9 { 892 lsort [glob test.db*] 893} [lsort [list \ 894 test.db test.db2 test.db3 \ 895 test.db-journal test.db2-journal test.db3-journal \ 896 [file tail $::mj_filename] [file tail $::mj_filename1] 897]] 898 899# The master-journal $::mj_filename1 contains pointers to test.db and 900# test.db2. However the hot-journal associated with test.db2 points to 901# a different master-journal. Therefore, reading from test.db only should 902# be enough to cause SQLite to delete $::mj_filename1. 903# 904do_test pager1.4.6.10 { file exists $::mj_filename } {1} 905do_test pager1.4.6.11 { file exists $::mj_filename1 } {1} 906do_execsql_test pager1.4.6.12 { SELECT * FROM t1 } {1 t1.1} 907do_test pager1.4.6.13 { file exists $::mj_filename } {1} 908do_test pager1.4.6.14 { file exists $::mj_filename1 } {0} 909 910do_execsql_test pager1.4.6.12 { 911 ATTACH 'test.db2' AS two; 912 SELECT * FROM t2; 913} {1 t2.1} 914do_test pager1.4.6.13 { file exists $::mj_filename } {1} 915do_execsql_test pager1.4.6.14 { 916 ATTACH 'test.db3' AS three; 917 SELECT * FROM t3; 918} {1 t3.1} 919do_test pager1.4.6.15 { file exists $::mj_filename } {0} 920 921db close 922tv delete 923 924testvfs tv -default 1 925tv sectorsize 512 926tv script copy_on_journal_delete 927tv filter xDelete 928proc copy_on_journal_delete {method filename args} { 929 if {[string match *journal $filename]} faultsim_save 930 return SQLITE_OK 931} 932faultsim_delete_and_reopen 933do_execsql_test pager1.4.7.1 { 934 PRAGMA journal_mode = DELETE; 935 CREATE TABLE t1(x PRIMARY KEY, y); 936 CREATE INDEX i1 ON t1(y); 937 INSERT INTO t1 VALUES('I', 'one'); 938 INSERT INTO t1 VALUES('II', 'four'); 939 INSERT INTO t1 VALUES('III', 'nine'); 940 BEGIN; 941 INSERT INTO t1 VALUES('IV', 'sixteen'); 942 INSERT INTO t1 VALUES('V' , 'twentyfive'); 943 COMMIT; 944} {delete} 945tv filter {} 946db close 947tv delete 948catch { 949 test_syscall install fchmod 950 test_syscall fault 1 1 951} 952do_test pager1.4.7.2 { 953 faultsim_restore_and_reopen 954 catch {file attributes test.db-journal -permissions r--------} 955 catch {file attributes test.db-journal -readonly 1} 956 catchsql { SELECT * FROM t1 } 957} {1 {unable to open database file}} 958catch { 959 test_syscall reset 960 test_syscall fault 0 0 961} 962do_test pager1.4.7.3 { 963 db close 964 catch {file attributes test.db-journal -permissions rw-rw-rw-} 965 catch {file attributes test.db-journal -readonly 0} 966 delete_file test.db-journal 967 file exists test.db-journal 968} {0} 969do_test pager1.4.8.1 { 970 catch {file attributes test.db -permissions r--------} 971 catch {file attributes test.db -readonly 1} 972 sqlite3 db test.db 973 db eval { SELECT * FROM t1 } 974 sqlite3_db_readonly db main 975} {1} 976do_test pager1.4.8.2 { 977 sqlite3_db_readonly db xyz 978} {-1} 979do_test pager1.4.8.3 { 980 db close 981 catch {file attributes test.db -readonly 0} 982 catch {file attributes test.db -permissions rw-rw-rw-} msg 983 sqlite3 db test.db 984 db eval { SELECT * FROM t1 } 985 sqlite3_db_readonly db main 986} {0} 987 988#------------------------------------------------------------------------- 989# The following tests deal with multi-file commits. 990# 991# pager1-5.1.*: The case where a multi-file cannot be committed because 992# another connection is holding a SHARED lock on one of the 993# files. After the SHARED lock is removed, the COMMIT succeeds. 994# 995# pager1-5.2.*: Multi-file commits with journal_mode=memory. 996# 997# pager1-5.3.*: Multi-file commits with journal_mode=memory. 998# 999# pager1-5.4.*: Check that with synchronous=normal, the master-journal file 1000# name is added to a journal file immediately after the last 1001# journal record. But with synchronous=full, extra unused space 1002# is allocated between the last journal record and the 1003# master-journal file name so that the master-journal file 1004# name does not lie on the same sector as the last journal file 1005# record. 1006# 1007# pager1-5.5.*: Check that in journal_mode=PERSIST mode, a journal file is 1008# truncated to zero bytes when a multi-file transaction is 1009# committed (instead of the first couple of bytes being zeroed). 1010# 1011# 1012do_test pager1-5.1.1 { 1013 faultsim_delete_and_reopen 1014 execsql { 1015 ATTACH 'test.db2' AS aux; 1016 CREATE TABLE t1(a, b); 1017 CREATE TABLE aux.t2(a, b); 1018 INSERT INTO t1 VALUES(17, 'Lenin'); 1019 INSERT INTO t1 VALUES(22, 'Stalin'); 1020 INSERT INTO t1 VALUES(53, 'Khrushchev'); 1021 } 1022} {} 1023do_test pager1-5.1.2 { 1024 execsql { 1025 BEGIN; 1026 INSERT INTO t1 VALUES(64, 'Brezhnev'); 1027 INSERT INTO t2 SELECT * FROM t1; 1028 } 1029 sqlite3 db2 test.db2 1030 execsql { 1031 BEGIN; 1032 SELECT * FROM t2; 1033 } db2 1034} {} 1035do_test pager1-5.1.3 { 1036 catchsql COMMIT 1037} {1 {database is locked}} 1038do_test pager1-5.1.4 { 1039 execsql COMMIT db2 1040 execsql COMMIT 1041 execsql { SELECT * FROM t2 } db2 1042} {17 Lenin 22 Stalin 53 Khrushchev 64 Brezhnev} 1043do_test pager1-5.1.5 { 1044 db2 close 1045} {} 1046 1047do_test pager1-5.2.1 { 1048 execsql { 1049 PRAGMA journal_mode = memory; 1050 BEGIN; 1051 INSERT INTO t1 VALUES(84, 'Andropov'); 1052 INSERT INTO t2 VALUES(84, 'Andropov'); 1053 COMMIT; 1054 } 1055} {memory} 1056do_test pager1-5.3.1 { 1057 execsql { 1058 PRAGMA journal_mode = off; 1059 BEGIN; 1060 INSERT INTO t1 VALUES(85, 'Gorbachev'); 1061 INSERT INTO t2 VALUES(85, 'Gorbachev'); 1062 COMMIT; 1063 } 1064} {off} 1065 1066do_test pager1-5.4.1 { 1067 db close 1068 testvfs tv 1069 sqlite3 db test.db -vfs tv 1070 execsql { ATTACH 'test.db2' AS aux } 1071 1072 tv filter xDelete 1073 tv script max_journal_size 1074 tv sectorsize 512 1075 set ::max_journal 0 1076 proc max_journal_size {method args} { 1077 set sz 0 1078 catch { set sz [file size test.db-journal] } 1079 if {$sz > $::max_journal} { 1080 set ::max_journal $sz 1081 } 1082 return SQLITE_OK 1083 } 1084 execsql { 1085 PRAGMA journal_mode = DELETE; 1086 PRAGMA synchronous = NORMAL; 1087 BEGIN; 1088 INSERT INTO t1 VALUES(85, 'Gorbachev'); 1089 INSERT INTO t2 VALUES(85, 'Gorbachev'); 1090 COMMIT; 1091 } 1092 1093 # The size of the journal file is now: 1094 # 1095 # 1) 512 byte header + 1096 # 2) 2 * (1024+8) byte records + 1097 # 3) 20+N bytes of master-journal pointer, where N is the size of 1098 # the master-journal name encoded as utf-8 with no nul term. 1099 # 1100 set mj_pointer [expr { 1101 20 + [string length "test.db-mjXXXXXX9XX"] 1102 }] 1103 # 1104 # NOTE: For item 3 above, if the current SQLite VFS lacks the concept of a 1105 # current directory, the length of the current directory name plus 1 1106 # character for the directory separator character are NOT counted as 1107 # part of the total size; otherwise, they are. 1108 # 1109 ifcapable curdir { 1110 set mj_pointer [expr {$mj_pointer + [string length [get_pwd]] + 1}] 1111 } 1112 expr {$::max_journal==(512+2*(1024+8)+$mj_pointer)} 1113} 1 1114do_test pager1-5.4.2 { 1115 set ::max_journal 0 1116 execsql { 1117 PRAGMA synchronous = full; 1118 BEGIN; 1119 DELETE FROM t1 WHERE b = 'Lenin'; 1120 DELETE FROM t2 WHERE b = 'Lenin'; 1121 COMMIT; 1122 } 1123 1124 # In synchronous=full mode, the master-journal pointer is not written 1125 # directly after the last record in the journal file. Instead, it is 1126 # written starting at the next (in this case 512 byte) sector boundary. 1127 # 1128 set mj_pointer [expr { 1129 20 + [string length "test.db-mjXXXXXX9XX"] 1130 }] 1131 # 1132 # NOTE: If the current SQLite VFS lacks the concept of a current directory, 1133 # the length of the current directory name plus 1 character for the 1134 # directory separator character are NOT counted as part of the total 1135 # size; otherwise, they are. 1136 # 1137 ifcapable curdir { 1138 set mj_pointer [expr {$mj_pointer + [string length [get_pwd]] + 1}] 1139 } 1140 expr {$::max_journal==(((512+2*(1024+8)+511)/512)*512 + $mj_pointer)} 1141} 1 1142db close 1143tv delete 1144 1145do_test pager1-5.5.1 { 1146 sqlite3 db test.db 1147 execsql { 1148 ATTACH 'test.db2' AS aux; 1149 PRAGMA journal_mode = PERSIST; 1150 CREATE TABLE t3(a, b); 1151 INSERT INTO t3 SELECT randomblob(1500), randomblob(1500) FROM t1; 1152 UPDATE t3 SET b = randomblob(1501); 1153 } 1154 expr [file size test.db-journal] > 15000 1155} {1} 1156do_test pager1-5.5.2 { 1157 execsql { 1158 PRAGMA synchronous = full; 1159 BEGIN; 1160 DELETE FROM t1 WHERE b = 'Stalin'; 1161 DELETE FROM t2 WHERE b = 'Stalin'; 1162 COMMIT; 1163 } 1164 file size test.db-journal 1165} {0} 1166 1167 1168#------------------------------------------------------------------------- 1169# The following tests work with "PRAGMA max_page_count" 1170# 1171do_test pager1-6.1 { 1172 faultsim_delete_and_reopen 1173 execsql { 1174 PRAGMA auto_vacuum = none; 1175 PRAGMA max_page_count = 10; 1176 CREATE TABLE t2(a, b); 1177 CREATE TABLE t3(a, b); 1178 CREATE TABLE t4(a, b); 1179 CREATE TABLE t5(a, b); 1180 CREATE TABLE t6(a, b); 1181 CREATE TABLE t7(a, b); 1182 CREATE TABLE t8(a, b); 1183 CREATE TABLE t9(a, b); 1184 CREATE TABLE t10(a, b); 1185 } 1186} {10} 1187do_catchsql_test pager1-6.2 { 1188 CREATE TABLE t11(a, b) 1189} {1 {database or disk is full}} 1190do_execsql_test pager1-6.4 { PRAGMA max_page_count } {10} 1191do_execsql_test pager1-6.5 { PRAGMA max_page_count = 15 } {15} 1192do_execsql_test pager1-6.6 { CREATE TABLE t11(a, b) } {} 1193do_execsql_test pager1-6.7 { 1194 BEGIN; 1195 INSERT INTO t11 VALUES(1, 2); 1196 PRAGMA max_page_count = 13; 1197} {13} 1198do_execsql_test pager1-6.8 { 1199 INSERT INTO t11 VALUES(3, 4); 1200 PRAGMA max_page_count = 10; 1201} {11} 1202do_execsql_test pager1-6.9 { COMMIT } {} 1203 1204do_execsql_test pager1-6.10 { PRAGMA max_page_count = 10 } {11} 1205do_execsql_test pager1-6.11 { SELECT * FROM t11 } {1 2 3 4} 1206do_execsql_test pager1-6.12 { PRAGMA max_page_count } {11} 1207 1208 1209#------------------------------------------------------------------------- 1210# The following tests work with "PRAGMA journal_mode=TRUNCATE" and 1211# "PRAGMA locking_mode=EXCLUSIVE". 1212# 1213# Each test is specified with 5 variables. As follows: 1214# 1215# $tn: Test Number. Used as part of the [do_test] test names. 1216# $sql: SQL to execute. 1217# $res: Expected result of executing $sql. 1218# $js: The expected size of the journal file, in bytes, after executing 1219# the SQL script. Or -1 if the journal is not expected to exist. 1220# $ws: The expected size of the WAL file, in bytes, after executing 1221# the SQL script. Or -1 if the WAL is not expected to exist. 1222# 1223ifcapable wal { 1224 faultsim_delete_and_reopen 1225 foreach {tn sql res js ws} [subst { 1226 1227 1 { 1228 CREATE TABLE t1(a, b); 1229 PRAGMA auto_vacuum=OFF; 1230 PRAGMA synchronous=NORMAL; 1231 PRAGMA page_size=1024; 1232 PRAGMA locking_mode=EXCLUSIVE; 1233 PRAGMA journal_mode=TRUNCATE; 1234 INSERT INTO t1 VALUES(1, 2); 1235 } {exclusive truncate} 0 -1 1236 1237 2 { 1238 BEGIN IMMEDIATE; 1239 SELECT * FROM t1; 1240 COMMIT; 1241 } {1 2} 0 -1 1242 1243 3 { 1244 BEGIN; 1245 SELECT * FROM t1; 1246 COMMIT; 1247 } {1 2} 0 -1 1248 1249 4 { PRAGMA journal_mode = WAL } wal -1 -1 1250 5 { INSERT INTO t1 VALUES(3, 4) } {} -1 [wal_file_size 1 1024] 1251 6 { PRAGMA locking_mode = NORMAL } exclusive -1 [wal_file_size 1 1024] 1252 7 { INSERT INTO t1 VALUES(5, 6); } {} -1 [wal_file_size 2 1024] 1253 1254 8 { PRAGMA journal_mode = TRUNCATE } truncate 0 -1 1255 9 { INSERT INTO t1 VALUES(7, 8) } {} 0 -1 1256 10 { SELECT * FROM t1 } {1 2 3 4 5 6 7 8} 0 -1 1257 1258 }] { 1259 do_execsql_test pager1-7.1.$tn.1 $sql $res 1260 catch { set J -1 ; set J [file size test.db-journal] } 1261 catch { set W -1 ; set W [file size test.db-wal] } 1262 do_test pager1-7.1.$tn.2 { list $J $W } [list $js $ws] 1263 } 1264} 1265 1266do_test pager1-7.2.1 { 1267 faultsim_delete_and_reopen 1268 execsql { 1269 PRAGMA locking_mode = EXCLUSIVE; 1270 CREATE TABLE t1(a, b); 1271 BEGIN; 1272 PRAGMA journal_mode = delete; 1273 PRAGMA journal_mode = truncate; 1274 } 1275} {exclusive delete truncate} 1276do_test pager1-7.2.2 { 1277 execsql { INSERT INTO t1 VALUES(1, 2) } 1278 execsql { PRAGMA journal_mode = persist } 1279} {truncate} 1280do_test pager1-7.2.3 { 1281 execsql { COMMIT } 1282 execsql { 1283 PRAGMA journal_mode = persist; 1284 PRAGMA journal_size_limit; 1285 } 1286} {persist -1} 1287 1288#------------------------------------------------------------------------- 1289# The following tests, pager1-8.*, test that the special filenames 1290# ":memory:" and "" open temporary databases. 1291# 1292foreach {tn filename} { 1293 1 :memory: 1294 2 "" 1295} { 1296 do_test pager1-8.$tn.1 { 1297 faultsim_delete_and_reopen 1298 db close 1299 sqlite3 db $filename 1300 execsql { 1301 PRAGMA auto_vacuum = 1; 1302 CREATE TABLE x1(x); 1303 INSERT INTO x1 VALUES('Charles'); 1304 INSERT INTO x1 VALUES('James'); 1305 INSERT INTO x1 VALUES('Mary'); 1306 SELECT * FROM x1; 1307 } 1308 } {Charles James Mary} 1309 1310 do_test pager1-8.$tn.2 { 1311 sqlite3 db2 $filename 1312 catchsql { SELECT * FROM x1 } db2 1313 } {1 {no such table: x1}} 1314 1315 do_execsql_test pager1-8.$tn.3 { 1316 BEGIN; 1317 INSERT INTO x1 VALUES('William'); 1318 INSERT INTO x1 VALUES('Anne'); 1319 ROLLBACK; 1320 } {} 1321} 1322 1323#------------------------------------------------------------------------- 1324# The next block of tests - pager1-9.* - deal with interactions between 1325# the pager and the backup API. Test cases: 1326# 1327# pager1-9.1.*: Test that a backup completes successfully even if the 1328# source db is written to during the backup op. 1329# 1330# pager1-9.2.*: Test that a backup completes successfully even if the 1331# source db is written to and then rolled back during a 1332# backup operation. 1333# 1334do_test pager1-9.0.1 { 1335 faultsim_delete_and_reopen 1336 db func a_string a_string 1337 execsql { 1338 PRAGMA cache_size = 10; 1339 BEGIN; 1340 CREATE TABLE ab(a, b, UNIQUE(a, b)); 1341 INSERT INTO ab VALUES( a_string(200), a_string(300) ); 1342 INSERT INTO ab SELECT a_string(200), a_string(300) FROM ab; 1343 INSERT INTO ab SELECT a_string(200), a_string(300) FROM ab; 1344 INSERT INTO ab SELECT a_string(200), a_string(300) FROM ab; 1345 INSERT INTO ab SELECT a_string(200), a_string(300) FROM ab; 1346 INSERT INTO ab SELECT a_string(200), a_string(300) FROM ab; 1347 INSERT INTO ab SELECT a_string(200), a_string(300) FROM ab; 1348 INSERT INTO ab SELECT a_string(200), a_string(300) FROM ab; 1349 COMMIT; 1350 } 1351} {} 1352do_test pager1-9.0.2 { 1353 sqlite3 db2 test.db2 1354 db2 eval { PRAGMA cache_size = 10 } 1355 sqlite3_backup B db2 main db main 1356 list [B step 10000] [B finish] 1357} {SQLITE_DONE SQLITE_OK} 1358do_test pager1-9.0.3 { 1359 db one {SELECT md5sum(a, b) FROM ab} 1360} [db2 one {SELECT md5sum(a, b) FROM ab}] 1361 1362do_test pager1-9.1.1 { 1363 execsql { UPDATE ab SET a = a_string(201) } 1364 sqlite3_backup B db2 main db main 1365 B step 30 1366} {SQLITE_OK} 1367do_test pager1-9.1.2 { 1368 execsql { UPDATE ab SET b = a_string(301) } 1369 list [B step 10000] [B finish] 1370} {SQLITE_DONE SQLITE_OK} 1371do_test pager1-9.1.3 { 1372 db one {SELECT md5sum(a, b) FROM ab} 1373} [db2 one {SELECT md5sum(a, b) FROM ab}] 1374do_test pager1-9.1.4 { execsql { SELECT count(*) FROM ab } } {128} 1375 1376do_test pager1-9.2.1 { 1377 execsql { UPDATE ab SET a = a_string(202) } 1378 sqlite3_backup B db2 main db main 1379 B step 30 1380} {SQLITE_OK} 1381do_test pager1-9.2.2 { 1382 execsql { 1383 BEGIN; 1384 UPDATE ab SET b = a_string(301); 1385 ROLLBACK; 1386 } 1387 list [B step 10000] [B finish] 1388} {SQLITE_DONE SQLITE_OK} 1389do_test pager1-9.2.3 { 1390 db one {SELECT md5sum(a, b) FROM ab} 1391} [db2 one {SELECT md5sum(a, b) FROM ab}] 1392do_test pager1-9.2.4 { execsql { SELECT count(*) FROM ab } } {128} 1393db close 1394db2 close 1395 1396do_test pager1-9.3.1 { 1397 testvfs tv -default 1 1398 tv sectorsize 4096 1399 faultsim_delete_and_reopen 1400 1401 execsql { PRAGMA page_size = 1024 } 1402 for {set ii 0} {$ii < 4} {incr ii} { execsql "CREATE TABLE t${ii}(a, b)" } 1403} {} 1404if {[nonzero_reserved_bytes]} { 1405 # backup with a page size changes is not possible with the codec 1406 # 1407 do_test pager1-9.3.2codec { 1408 sqlite3 db2 test.db2 1409 execsql { 1410 PRAGMA page_size = 4096; 1411 PRAGMA synchronous = OFF; 1412 CREATE TABLE t1(a, b); 1413 CREATE TABLE t2(a, b); 1414 } db2 1415 sqlite3_backup B db2 main db main 1416 B step 30 1417 list [B step 10000] [B finish] 1418 } {SQLITE_READONLY SQLITE_READONLY} 1419 do_test pager1-9.3.3codec { 1420 db2 close 1421 db close 1422 tv delete 1423 file size test.db2 1424 } [file size test.db2] 1425} else { 1426 do_test pager1-9.3.2 { 1427 sqlite3 db2 test.db2 1428 execsql { 1429 PRAGMA page_size = 4096; 1430 PRAGMA synchronous = OFF; 1431 CREATE TABLE t1(a, b); 1432 CREATE TABLE t2(a, b); 1433 } db2 1434 sqlite3_backup B db2 main db main 1435 B step 30 1436 list [B step 10000] [B finish] 1437 } {SQLITE_DONE SQLITE_OK} 1438 do_test pager1-9.3.3 { 1439 db2 close 1440 db close 1441 tv delete 1442 file size test.db2 1443 } [file size test.db] 1444} 1445 1446do_test pager1-9.4.1 { 1447 faultsim_delete_and_reopen 1448 sqlite3 db2 test.db2 1449 execsql { 1450 PRAGMA page_size = 4096; 1451 CREATE TABLE t1(a, b); 1452 CREATE TABLE t2(a, b); 1453 } db2 1454 sqlite3_backup B db2 main db main 1455 list [B step 10000] [B finish] 1456} {SQLITE_DONE SQLITE_OK} 1457do_test pager1-9.4.2 { 1458 list [file size test.db2] [file size test.db] 1459} {1024 0} 1460db2 close 1461 1462#------------------------------------------------------------------------- 1463# Test that regardless of the value returned by xSectorSize(), the 1464# minimum effective sector-size is 512 and the maximum 65536 bytes. 1465# 1466testvfs tv -default 1 1467foreach sectorsize { 1468 16 1469 32 64 128 256 512 1024 2048 1470 4096 8192 16384 32768 65536 131072 262144 1471} { 1472 tv sectorsize $sectorsize 1473 tv devchar {} 1474 set eff $sectorsize 1475 if {$sectorsize < 512} { set eff 512 } 1476 if {$sectorsize > 65536} { set eff 65536 } 1477 1478 do_test pager1-10.$sectorsize.1 { 1479 faultsim_delete_and_reopen 1480 db func a_string a_string 1481 execsql { 1482 PRAGMA journal_mode = PERSIST; 1483 PRAGMA page_size = 1024; 1484 BEGIN; 1485 CREATE TABLE t1(a, b); 1486 CREATE TABLE t2(a, b); 1487 CREATE TABLE t3(a, b); 1488 COMMIT; 1489 } 1490 file size test.db-journal 1491 } [expr $sectorsize > 65536 ? 65536 : ($sectorsize<32 ? 512 : $sectorsize)] 1492 1493 do_test pager1-10.$sectorsize.2 { 1494 execsql { 1495 INSERT INTO t3 VALUES(a_string(300), a_string(300)); 1496 INSERT INTO t3 SELECT * FROM t3; /* 2 */ 1497 INSERT INTO t3 SELECT * FROM t3; /* 4 */ 1498 INSERT INTO t3 SELECT * FROM t3; /* 8 */ 1499 INSERT INTO t3 SELECT * FROM t3; /* 16 */ 1500 INSERT INTO t3 SELECT * FROM t3; /* 32 */ 1501 } 1502 } {} 1503 1504 do_test pager1-10.$sectorsize.3 { 1505 db close 1506 sqlite3 db test.db 1507 execsql { 1508 PRAGMA cache_size = 10; 1509 BEGIN; 1510 } 1511 recursive_select 32 t3 {db eval "INSERT INTO t2 VALUES(1, 2)"} 1512 execsql { 1513 COMMIT; 1514 SELECT * FROM t2; 1515 } 1516 } {1 2} 1517 1518 do_test pager1-10.$sectorsize.4 { 1519 execsql { 1520 CREATE TABLE t6(a, b); 1521 CREATE TABLE t7(a, b); 1522 CREATE TABLE t5(a, b); 1523 DROP TABLE t6; 1524 DROP TABLE t7; 1525 } 1526 execsql { 1527 BEGIN; 1528 CREATE TABLE t6(a, b); 1529 } 1530 recursive_select 32 t3 {db eval "INSERT INTO t5 VALUES(1, 2)"} 1531 execsql { 1532 COMMIT; 1533 SELECT * FROM t5; 1534 } 1535 } {1 2} 1536 1537} 1538db close 1539 1540tv sectorsize 4096 1541do_test pager1.10.x.1 { 1542 faultsim_delete_and_reopen 1543 execsql { 1544 PRAGMA auto_vacuum = none; 1545 PRAGMA page_size = 1024; 1546 CREATE TABLE t1(x); 1547 } 1548 for {set i 0} {$i<30} {incr i} { 1549 execsql { INSERT INTO t1 VALUES(zeroblob(900)) } 1550 } 1551 file size test.db 1552} {32768} 1553do_test pager1.10.x.2 { 1554 execsql { 1555 CREATE TABLE t2(x); 1556 DROP TABLE t2; 1557 } 1558 file size test.db 1559} {33792} 1560do_test pager1.10.x.3 { 1561 execsql { 1562 BEGIN; 1563 CREATE TABLE t2(x); 1564 } 1565 recursive_select 30 t1 1566 execsql { 1567 CREATE TABLE t3(x); 1568 COMMIT; 1569 } 1570} {} 1571 1572db close 1573tv delete 1574 1575testvfs tv -default 1 1576faultsim_delete_and_reopen 1577db func a_string a_string 1578do_execsql_test pager1-11.1 { 1579 PRAGMA journal_mode = DELETE; 1580 PRAGMA cache_size = 10; 1581 BEGIN; 1582 CREATE TABLE zz(top PRIMARY KEY); 1583 INSERT INTO zz VALUES(a_string(222)); 1584 INSERT INTO zz SELECT a_string((SELECT 222+max(rowid) FROM zz)) FROM zz; 1585 INSERT INTO zz SELECT a_string((SELECT 222+max(rowid) FROM zz)) FROM zz; 1586 INSERT INTO zz SELECT a_string((SELECT 222+max(rowid) FROM zz)) FROM zz; 1587 INSERT INTO zz SELECT a_string((SELECT 222+max(rowid) FROM zz)) FROM zz; 1588 INSERT INTO zz SELECT a_string((SELECT 222+max(rowid) FROM zz)) FROM zz; 1589 COMMIT; 1590 BEGIN; 1591 UPDATE zz SET top = a_string(345); 1592} {delete} 1593 1594proc lockout {method args} { return SQLITE_IOERR } 1595tv script lockout 1596tv filter {xWrite xTruncate xSync} 1597do_catchsql_test pager1-11.2 { COMMIT } {1 {disk I/O error}} 1598 1599tv script {} 1600do_test pager1-11.3 { 1601 sqlite3 db2 test.db 1602 execsql { 1603 PRAGMA journal_mode = TRUNCATE; 1604 PRAGMA integrity_check; 1605 } db2 1606} {truncate ok} 1607do_test pager1-11.4 { 1608 db2 close 1609 file exists test.db-journal 1610} {0} 1611do_execsql_test pager1-11.5 { SELECT count(*) FROM zz } {32} 1612db close 1613tv delete 1614 1615#------------------------------------------------------------------------- 1616# Test "PRAGMA page_size" 1617# 1618testvfs tv -default 1 1619tv sectorsize 1024 1620foreach pagesize { 1621 512 1024 2048 4096 8192 16384 32768 1622} { 1623 faultsim_delete_and_reopen 1624 1625 # The sector-size (according to the VFS) is 1024 bytes. So if the 1626 # page-size requested using "PRAGMA page_size" is greater than the 1627 # compile time value of SQLITE_MAX_PAGE_SIZE, then the effective 1628 # page-size remains 1024 bytes. 1629 # 1630 set eff $pagesize 1631 if {$eff > $::SQLITE_MAX_PAGE_SIZE} { set eff 1024 } 1632 1633 do_test pager1-12.$pagesize.1 { 1634 sqlite3 db2 test.db 1635 execsql " 1636 PRAGMA page_size = $pagesize; 1637 CREATE VIEW v AS SELECT * FROM sqlite_master; 1638 " db2 1639 file size test.db 1640 } $eff 1641 do_test pager1-12.$pagesize.2 { 1642 sqlite3 db2 test.db 1643 execsql { 1644 SELECT count(*) FROM v; 1645 PRAGMA main.page_size; 1646 } db2 1647 } [list 1 $eff] 1648 do_test pager1-12.$pagesize.3 { 1649 execsql { 1650 SELECT count(*) FROM v; 1651 PRAGMA main.page_size; 1652 } 1653 } [list 1 $eff] 1654 db2 close 1655} 1656db close 1657tv delete 1658 1659#------------------------------------------------------------------------- 1660# Test specal "PRAGMA journal_mode=PERSIST" test cases. 1661# 1662# pager1-13.1.*: This tests a special case encountered in persistent 1663# journal mode: If the journal associated with a transaction 1664# is smaller than the journal file (because a previous 1665# transaction left a very large non-hot journal file in the 1666# file-system), then SQLite has to be careful that there is 1667# not a journal-header left over from a previous transaction 1668# immediately following the journal content just written. 1669# If there is, and the process crashes so that the journal 1670# becomes a hot-journal and must be rolled back by another 1671# process, there is a danger that the other process may roll 1672# back the aborted transaction, then continue copying data 1673# from an older transaction from the remainder of the journal. 1674# See the syncJournal() function for details. 1675# 1676# pager1-13.2.*: Same test as the previous. This time, throw an index into 1677# the mix to make the integrity-check more likely to catch 1678# errors. 1679# 1680testvfs tv -default 1 1681tv script xSyncCb 1682tv filter xSync 1683proc xSyncCb {method filename args} { 1684 set t [file tail $filename] 1685 if {$t == "test.db"} faultsim_save 1686 return SQLITE_OK 1687} 1688faultsim_delete_and_reopen 1689db func a_string a_string 1690 1691# The UPDATE statement at the end of this test case creates a really big 1692# journal. Since the cache-size is only 10 pages, the journal contains 1693# frequent journal headers. 1694# 1695do_execsql_test pager1-13.1.1 { 1696 PRAGMA page_size = 1024; 1697 PRAGMA journal_mode = PERSIST; 1698 PRAGMA cache_size = 10; 1699 BEGIN; 1700 CREATE TABLE t1(a INTEGER PRIMARY KEY, b BLOB); 1701 INSERT INTO t1 VALUES(NULL, a_string(400)); 1702 INSERT INTO t1 SELECT NULL, a_string(400) FROM t1; /* 2 */ 1703 INSERT INTO t1 SELECT NULL, a_string(400) FROM t1; /* 4 */ 1704 INSERT INTO t1 SELECT NULL, a_string(400) FROM t1; /* 8 */ 1705 INSERT INTO t1 SELECT NULL, a_string(400) FROM t1; /* 16 */ 1706 INSERT INTO t1 SELECT NULL, a_string(400) FROM t1; /* 32 */ 1707 INSERT INTO t1 SELECT NULL, a_string(400) FROM t1; /* 64 */ 1708 INSERT INTO t1 SELECT NULL, a_string(400) FROM t1; /* 128 */ 1709 COMMIT; 1710 UPDATE t1 SET b = a_string(400); 1711} {persist} 1712 1713if {$::tcl_platform(platform)!="windows"} { 1714# Run transactions of increasing sizes. Eventually, one (or more than one) 1715# of these will write just enough content that one of the old headers created 1716# by the transaction in the block above lies immediately after the content 1717# journalled by the current transaction. 1718# 1719for {set nUp 1} {$nUp<64} {incr nUp} { 1720 do_execsql_test pager1-13.1.2.$nUp.1 { 1721 UPDATE t1 SET b = a_string(399) WHERE a <= $nUp 1722 } {} 1723 do_execsql_test pager1-13.1.2.$nUp.2 { PRAGMA integrity_check } {ok} 1724 1725 # Try to access the snapshot of the file-system. 1726 # 1727 sqlite3 db2 sv_test.db 1728 do_test pager1-13.1.2.$nUp.3 { 1729 execsql { SELECT sum(length(b)) FROM t1 } db2 1730 } [expr {128*400 - ($nUp-1)}] 1731 do_test pager1-13.1.2.$nUp.4 { 1732 execsql { PRAGMA integrity_check } db2 1733 } {ok} 1734 db2 close 1735} 1736} 1737 1738if {$::tcl_platform(platform)!="windows"} { 1739# Same test as above. But this time with an index on the table. 1740# 1741do_execsql_test pager1-13.2.1 { 1742 CREATE INDEX i1 ON t1(b); 1743 UPDATE t1 SET b = a_string(400); 1744} {} 1745for {set nUp 1} {$nUp<64} {incr nUp} { 1746 do_execsql_test pager1-13.2.2.$nUp.1 { 1747 UPDATE t1 SET b = a_string(399) WHERE a <= $nUp 1748 } {} 1749 do_execsql_test pager1-13.2.2.$nUp.2 { PRAGMA integrity_check } {ok} 1750 sqlite3 db2 sv_test.db 1751 do_test pager1-13.2.2.$nUp.3 { 1752 execsql { SELECT sum(length(b)) FROM t1 } db2 1753 } [expr {128*400 - ($nUp-1)}] 1754 do_test pager1-13.2.2.$nUp.4 { 1755 execsql { PRAGMA integrity_check } db2 1756 } {ok} 1757 db2 close 1758} 1759} 1760 1761db close 1762tv delete 1763 1764#------------------------------------------------------------------------- 1765# Test specal "PRAGMA journal_mode=OFF" test cases. 1766# 1767faultsim_delete_and_reopen 1768do_execsql_test pager1-14.1.1 { 1769 PRAGMA journal_mode = OFF; 1770 CREATE TABLE t1(a, b); 1771 BEGIN; 1772 INSERT INTO t1 VALUES(1, 2); 1773 COMMIT; 1774 SELECT * FROM t1; 1775} {off 1 2} 1776do_catchsql_test pager1-14.1.2 { 1777 BEGIN; 1778 INSERT INTO t1 VALUES(3, 4); 1779 ROLLBACK; 1780} {0 {}} 1781do_execsql_test pager1-14.1.3 { 1782 SELECT * FROM t1; 1783} {1 2} 1784do_catchsql_test pager1-14.1.4 { 1785 BEGIN; 1786 INSERT INTO t1(rowid, a, b) SELECT a+3, b, b FROM t1; 1787 INSERT INTO t1(rowid, a, b) SELECT a+3, b, b FROM t1; 1788} {1 {UNIQUE constraint failed: t1.rowid}} 1789do_execsql_test pager1-14.1.5 { 1790 COMMIT; 1791 SELECT * FROM t1; 1792} {1 2 2 2} 1793 1794#------------------------------------------------------------------------- 1795# Test opening and closing the pager sub-system with different values 1796# for the sqlite3_vfs.szOsFile variable. 1797# 1798faultsim_delete_and_reopen 1799do_execsql_test pager1-15.0 { 1800 CREATE TABLE tx(y, z); 1801 INSERT INTO tx VALUES('Ayutthaya', 'Beijing'); 1802 INSERT INTO tx VALUES('London', 'Tokyo'); 1803} {} 1804db close 1805for {set i 0} {$i<513} {incr i 3} { 1806 testvfs tv -default 1 -szosfile $i 1807 sqlite3 db test.db 1808 do_execsql_test pager1-15.$i.1 { 1809 SELECT * FROM tx; 1810 } {Ayutthaya Beijing London Tokyo} 1811 db close 1812 tv delete 1813} 1814 1815#------------------------------------------------------------------------- 1816# Check that it is not possible to open a database file if the full path 1817# to the associated journal file will be longer than sqlite3_vfs.mxPathname. 1818# 1819testvfs tv -default 1 1820tv script xOpenCb 1821tv filter xOpen 1822proc xOpenCb {method filename args} { 1823 set ::file_len [string length $filename] 1824} 1825sqlite3 db test.db 1826db close 1827tv delete 1828 1829for {set ii [expr $::file_len-5]} {$ii < [expr $::file_len+20]} {incr ii} { 1830 testvfs tv -default 1 -mxpathname $ii 1831 1832 # The length of the full path to file "test.db-journal" is ($::file_len+8). 1833 # If the configured sqlite3_vfs.mxPathname value greater than or equal to 1834 # this, then the file can be opened. Otherwise, it cannot. 1835 # 1836 if {$ii >= [expr $::file_len+8]} { 1837 set res {0 {}} 1838 } else { 1839 set res {1 {unable to open database file}} 1840 } 1841 1842 do_test pager1-16.1.$ii { 1843 list [catch { sqlite3 db test.db } msg] $msg 1844 } $res 1845 1846 catch {db close} 1847 tv delete 1848} 1849 1850 1851#------------------------------------------------------------------------- 1852# Test the pagers response to the b-tree layer requesting illegal page 1853# numbers: 1854# 1855# + The locking page, 1856# + Page 0, 1857# + A page with a page number greater than (2^31-1). 1858# 1859# These tests will not work if SQLITE_DIRECT_OVERFLOW_READ is defined. In 1860# that case IO errors are sometimes reported instead of SQLITE_CORRUPT. 1861# 1862ifcapable !direct_read { 1863do_test pager1-18.1 { 1864 faultsim_delete_and_reopen 1865 db func a_string a_string 1866 execsql { 1867 PRAGMA page_size = 1024; 1868 CREATE TABLE t1(a, b); 1869 INSERT INTO t1 VALUES(a_string(500), a_string(200)); 1870 INSERT INTO t1 SELECT a_string(500), a_string(200) FROM t1; 1871 INSERT INTO t1 SELECT a_string(500), a_string(200) FROM t1; 1872 INSERT INTO t1 SELECT a_string(500), a_string(200) FROM t1; 1873 INSERT INTO t1 SELECT a_string(500), a_string(200) FROM t1; 1874 INSERT INTO t1 SELECT a_string(500), a_string(200) FROM t1; 1875 INSERT INTO t1 SELECT a_string(500), a_string(200) FROM t1; 1876 INSERT INTO t1 SELECT a_string(500), a_string(200) FROM t1; 1877 } 1878} {} 1879do_test pager1-18.2 { 1880 set root [db one "SELECT rootpage FROM sqlite_master"] 1881 set lockingpage [expr (0x10000/1024) + 1] 1882 sqlite3_db_config db DEFENSIVE 0 1883 execsql { 1884 PRAGMA writable_schema = 1; 1885 UPDATE sqlite_master SET rootpage = $lockingpage; 1886 } 1887 sqlite3 db2 test.db 1888 catchsql { SELECT count(*) FROM t1 } db2 1889} {1 {database disk image is malformed}} 1890db2 close 1891do_test pager1-18.3.1 { 1892 execsql { 1893 CREATE TABLE t2(x); 1894 INSERT INTO t2 VALUES(a_string(5000)); 1895 } 1896 set pgno [expr ([file size test.db] / 1024)-2] 1897 hexio_write test.db [expr ($pgno-1)*1024] 00000000 1898 sqlite3 db2 test.db 1899 # even though x is malformed, because typeof() does 1900 # not load the content of x, the error is not noticed. 1901 catchsql { SELECT typeof(x) FROM t2 } db2 1902} {0 text} 1903do_test pager1-18.3.2 { 1904 # in this case, the value of x is loaded and so the error is 1905 # detected 1906 catchsql { SELECT length(x||'') FROM t2 } db2 1907} {1 {database disk image is malformed}} 1908db2 close 1909do_test pager1-18.3.3 { 1910 execsql { 1911 DELETE FROM t2; 1912 INSERT INTO t2 VALUES(randomblob(5000)); 1913 } 1914 set pgno [expr ([file size test.db] / 1024)-2] 1915 hexio_write test.db [expr ($pgno-1)*1024] 00000000 1916 sqlite3 db2 test.db 1917 # even though x is malformed, because length() and typeof() do 1918 # not load the content of x, the error is not noticed. 1919 catchsql { SELECT length(x), typeof(x) FROM t2 } db2 1920} {0 {5000 blob}} 1921do_test pager1-18.3.4 { 1922 # in this case, the value of x is loaded and so the error is 1923 # detected 1924 catchsql { SELECT length(x||'') FROM t2 } db2 1925} {1 {database disk image is malformed}} 1926db2 close 1927do_test pager1-18.4 { 1928 hexio_write test.db [expr ($pgno-1)*1024] 90000000 1929 sqlite3 db2 test.db 1930 catchsql { SELECT length(x||'') FROM t2 } db2 1931} {1 {database disk image is malformed}} 1932db2 close 1933extra_schema_checks 0 1934do_test pager1-18.5 { 1935 sqlite3 db "" 1936 sqlite3_db_config db DEFENSIVE 0 1937 execsql { 1938 CREATE TABLE t1(a, b); 1939 CREATE TABLE t2(a, b); 1940 PRAGMA writable_schema = 1; 1941 UPDATE sqlite_master SET rootpage=5 WHERE tbl_name = 't1'; 1942 PRAGMA writable_schema = 0; 1943 ALTER TABLE t1 RENAME TO x1; 1944 } 1945 catchsql { SELECT * FROM x1 } 1946} {1 {database disk image is malformed}} 1947db close 1948extra_schema_checks 1 1949 1950do_test pager1-18.6 { 1951 faultsim_delete_and_reopen 1952 db func a_string a_string 1953 execsql { 1954 PRAGMA page_size = 1024; 1955 CREATE TABLE t1(x); 1956 INSERT INTO t1 VALUES(a_string(800)); 1957 INSERT INTO t1 VALUES(a_string(800)); 1958 } 1959 1960 set root [db one "SELECT rootpage FROM sqlite_master"] 1961 db close 1962 1963 hexio_write test.db [expr ($root-1)*1024 + 8] 00000000 1964 sqlite3 db test.db 1965 catchsql { SELECT length(x) FROM t1 } 1966} {1 {database disk image is malformed}} 1967} 1968 1969do_test pager1-19.1 { 1970 sqlite3 db "" 1971 db func a_string a_string 1972 execsql { 1973 PRAGMA page_size = 512; 1974 PRAGMA auto_vacuum = 1; 1975 CREATE TABLE t1(aa, ab, ac, ad, ae, af, ag, ah, ai, aj, ak, al, am, an, 1976 ba, bb, bc, bd, be, bf, bg, bh, bi, bj, bk, bl, bm, bn, 1977 ca, cb, cc, cd, ce, cf, cg, ch, ci, cj, ck, cl, cm, cn, 1978 da, db, dc, dd, de, df, dg, dh, di, dj, dk, dl, dm, dn, 1979 ea, eb, ec, ed, ee, ef, eg, eh, ei, ej, ek, el, em, en, 1980 fa, fb, fc, fd, fe, ff, fg, fh, fi, fj, fk, fl, fm, fn, 1981 ga, gb, gc, gd, ge, gf, gg, gh, gi, gj, gk, gl, gm, gn, 1982 ha, hb, hc, hd, he, hf, hg, hh, hi, hj, hk, hl, hm, hn, 1983 ia, ib, ic, id, ie, if, ig, ih, ii, ij, ik, il, im, ix, 1984 ja, jb, jc, jd, je, jf, jg, jh, ji, jj, jk, jl, jm, jn, 1985 ka, kb, kc, kd, ke, kf, kg, kh, ki, kj, kk, kl, km, kn, 1986 la, lb, lc, ld, le, lf, lg, lh, li, lj, lk, ll, lm, ln, 1987 ma, mb, mc, md, me, mf, mg, mh, mi, mj, mk, ml, mm, mn 1988 ); 1989 CREATE TABLE t2(aa, ab, ac, ad, ae, af, ag, ah, ai, aj, ak, al, am, an, 1990 ba, bb, bc, bd, be, bf, bg, bh, bi, bj, bk, bl, bm, bn, 1991 ca, cb, cc, cd, ce, cf, cg, ch, ci, cj, ck, cl, cm, cn, 1992 da, db, dc, dd, de, df, dg, dh, di, dj, dk, dl, dm, dn, 1993 ea, eb, ec, ed, ee, ef, eg, eh, ei, ej, ek, el, em, en, 1994 fa, fb, fc, fd, fe, ff, fg, fh, fi, fj, fk, fl, fm, fn, 1995 ga, gb, gc, gd, ge, gf, gg, gh, gi, gj, gk, gl, gm, gn, 1996 ha, hb, hc, hd, he, hf, hg, hh, hi, hj, hk, hl, hm, hn, 1997 ia, ib, ic, id, ie, if, ig, ih, ii, ij, ik, il, im, ix, 1998 ja, jb, jc, jd, je, jf, jg, jh, ji, jj, jk, jl, jm, jn, 1999 ka, kb, kc, kd, ke, kf, kg, kh, ki, kj, kk, kl, km, kn, 2000 la, lb, lc, ld, le, lf, lg, lh, li, lj, lk, ll, lm, ln, 2001 ma, mb, mc, md, me, mf, mg, mh, mi, mj, mk, ml, mm, mn 2002 ); 2003 INSERT INTO t1(aa) VALUES( a_string(100000) ); 2004 INSERT INTO t2(aa) VALUES( a_string(100000) ); 2005 VACUUM; 2006 } 2007} {} 2008 2009#------------------------------------------------------------------------- 2010# Test a couple of special cases that come up while committing 2011# transactions: 2012# 2013# pager1-20.1.*: Committing an in-memory database transaction when the 2014# database has not been modified at all. 2015# 2016# pager1-20.2.*: As above, but with a normal db in exclusive-locking mode. 2017# 2018# pager1-20.3.*: Committing a transaction in WAL mode where the database has 2019# been modified, but all dirty pages have been flushed to 2020# disk before the commit. 2021# 2022do_test pager1-20.1.1 { 2023 catch {db close} 2024 sqlite3 db :memory: 2025 execsql { 2026 CREATE TABLE one(two, three); 2027 INSERT INTO one VALUES('a', 'b'); 2028 } 2029} {} 2030do_test pager1-20.1.2 { 2031 execsql { 2032 BEGIN EXCLUSIVE; 2033 COMMIT; 2034 } 2035} {} 2036 2037do_test pager1-20.2.1 { 2038 faultsim_delete_and_reopen 2039 execsql { 2040 PRAGMA locking_mode = exclusive; 2041 PRAGMA journal_mode = persist; 2042 CREATE TABLE one(two, three); 2043 INSERT INTO one VALUES('a', 'b'); 2044 } 2045} {exclusive persist} 2046do_test pager1-20.2.2 { 2047 execsql { 2048 BEGIN EXCLUSIVE; 2049 COMMIT; 2050 } 2051} {} 2052 2053ifcapable wal { 2054 do_test pager1-20.3.1 { 2055 faultsim_delete_and_reopen 2056 db func a_string a_string 2057 execsql { 2058 PRAGMA cache_size = 10; 2059 PRAGMA journal_mode = wal; 2060 BEGIN; 2061 CREATE TABLE t1(x); 2062 CREATE TABLE t2(y); 2063 INSERT INTO t1 VALUES(a_string(800)); 2064 INSERT INTO t1 SELECT a_string(800) FROM t1; /* 2 */ 2065 INSERT INTO t1 SELECT a_string(800) FROM t1; /* 4 */ 2066 INSERT INTO t1 SELECT a_string(800) FROM t1; /* 8 */ 2067 INSERT INTO t1 SELECT a_string(800) FROM t1; /* 16 */ 2068 INSERT INTO t1 SELECT a_string(800) FROM t1; /* 32 */ 2069 COMMIT; 2070 } 2071 } {wal} 2072 do_test pager1-20.3.2 { 2073 execsql { 2074 BEGIN; 2075 INSERT INTO t2 VALUES('xxxx'); 2076 } 2077 recursive_select 32 t1 2078 execsql COMMIT 2079 } {} 2080} 2081 2082#------------------------------------------------------------------------- 2083# Test that a WAL database may not be opened if: 2084# 2085# pager1-21.1.*: The VFS has an iVersion less than 2, or 2086# pager1-21.2.*: The VFS does not provide xShmXXX() methods. 2087# 2088ifcapable wal { 2089 do_test pager1-21.0 { 2090 faultsim_delete_and_reopen 2091 execsql { 2092 PRAGMA journal_mode = WAL; 2093 CREATE TABLE ko(c DEFAULT 'abc', b DEFAULT 'def'); 2094 INSERT INTO ko DEFAULT VALUES; 2095 } 2096 } {wal} 2097 do_test pager1-21.1 { 2098 testvfs tv -noshm 1 2099 sqlite3 db2 test.db -vfs tv 2100 catchsql { SELECT * FROM ko } db2 2101 } {1 {unable to open database file}} 2102 db2 close 2103 tv delete 2104 do_test pager1-21.2 { 2105 testvfs tv -iversion 1 2106 sqlite3 db2 test.db -vfs tv 2107 catchsql { SELECT * FROM ko } db2 2108 } {1 {unable to open database file}} 2109 db2 close 2110 tv delete 2111} 2112 2113#------------------------------------------------------------------------- 2114# Test that a "PRAGMA wal_checkpoint": 2115# 2116# pager1-22.1.*: is a no-op on a non-WAL db, and 2117# pager1-22.2.*: does not cause xSync calls with a synchronous=off db. 2118# 2119ifcapable wal { 2120 do_test pager1-22.1.1 { 2121 faultsim_delete_and_reopen 2122 execsql { 2123 CREATE TABLE ko(c DEFAULT 'abc', b DEFAULT 'def'); 2124 INSERT INTO ko DEFAULT VALUES; 2125 } 2126 execsql { PRAGMA wal_checkpoint } 2127 } {0 -1 -1} 2128 do_test pager1-22.2.1 { 2129 testvfs tv -default 1 2130 tv filter xSync 2131 tv script xSyncCb 2132 proc xSyncCb {args} {incr ::synccount} 2133 set ::synccount 0 2134 sqlite3 db test.db 2135 execsql { 2136 PRAGMA synchronous = off; 2137 PRAGMA journal_mode = WAL; 2138 INSERT INTO ko DEFAULT VALUES; 2139 } 2140 execsql { PRAGMA wal_checkpoint } 2141 set synccount 2142 } {0} 2143 db close 2144 tv delete 2145} 2146 2147#------------------------------------------------------------------------- 2148# Tests for changing journal mode. 2149# 2150# pager1-23.1.*: Test that when changing from PERSIST to DELETE mode, 2151# the journal file is deleted. 2152# 2153# pager1-23.2.*: Same test as above, but while a shared lock is held 2154# on the database file. 2155# 2156# pager1-23.3.*: Same test as above, but while a reserved lock is held 2157# on the database file. 2158# 2159# pager1-23.4.*: And, for fun, while holding an exclusive lock. 2160# 2161# pager1-23.5.*: Try to set various different journal modes with an 2162# in-memory database (only MEMORY and OFF should work). 2163# 2164# pager1-23.6.*: Try to set locking_mode=normal on an in-memory database 2165# (doesn't work - in-memory databases always use 2166# locking_mode=exclusive). 2167# 2168do_test pager1-23.1.1 { 2169 faultsim_delete_and_reopen 2170 execsql { 2171 PRAGMA journal_mode = PERSIST; 2172 CREATE TABLE t1(a, b); 2173 } 2174 file exists test.db-journal 2175} {1} 2176do_test pager1-23.1.2 { 2177 execsql { PRAGMA journal_mode = DELETE } 2178 file exists test.db-journal 2179} {0} 2180 2181do_test pager1-23.2.1 { 2182 execsql { 2183 PRAGMA journal_mode = PERSIST; 2184 INSERT INTO t1 VALUES('Canberra', 'ACT'); 2185 } 2186 db eval { SELECT * FROM t1 } { 2187 db eval { PRAGMA journal_mode = DELETE } 2188 } 2189 execsql { PRAGMA journal_mode } 2190} {delete} 2191do_test pager1-23.2.2 { 2192 file exists test.db-journal 2193} {0} 2194 2195do_test pager1-23.3.1 { 2196 execsql { 2197 PRAGMA journal_mode = PERSIST; 2198 INSERT INTO t1 VALUES('Darwin', 'NT'); 2199 BEGIN IMMEDIATE; 2200 } 2201 db eval { PRAGMA journal_mode = DELETE } 2202 execsql { PRAGMA journal_mode } 2203} {delete} 2204do_test pager1-23.3.2 { 2205 file exists test.db-journal 2206} {0} 2207do_test pager1-23.3.3 { 2208 execsql COMMIT 2209} {} 2210 2211do_test pager1-23.4.1 { 2212 execsql { 2213 PRAGMA journal_mode = PERSIST; 2214 INSERT INTO t1 VALUES('Adelaide', 'SA'); 2215 BEGIN EXCLUSIVE; 2216 } 2217 db eval { PRAGMA journal_mode = DELETE } 2218 execsql { PRAGMA journal_mode } 2219} {delete} 2220do_test pager1-23.4.2 { 2221 file exists test.db-journal 2222} {0} 2223do_test pager1-23.4.3 { 2224 execsql COMMIT 2225} {} 2226 2227do_test pager1-23.5.1 { 2228 faultsim_delete_and_reopen 2229 sqlite3 db :memory: 2230} {} 2231foreach {tn mode possible} { 2232 2 off 1 2233 3 memory 1 2234 4 persist 0 2235 5 delete 0 2236 6 wal 0 2237 7 truncate 0 2238} { 2239 do_test pager1-23.5.$tn.1 { 2240 execsql "PRAGMA journal_mode = off" 2241 execsql "PRAGMA journal_mode = $mode" 2242 } [if $possible {list $mode} {list off}] 2243 do_test pager1-23.5.$tn.2 { 2244 execsql "PRAGMA journal_mode = memory" 2245 execsql "PRAGMA journal_mode = $mode" 2246 } [if $possible {list $mode} {list memory}] 2247} 2248do_test pager1-23.6.1 { 2249 execsql {PRAGMA locking_mode = normal} 2250} {exclusive} 2251do_test pager1-23.6.2 { 2252 execsql {PRAGMA locking_mode = exclusive} 2253} {exclusive} 2254do_test pager1-23.6.3 { 2255 execsql {PRAGMA locking_mode} 2256} {exclusive} 2257do_test pager1-23.6.4 { 2258 execsql {PRAGMA main.locking_mode} 2259} {exclusive} 2260 2261#------------------------------------------------------------------------- 2262# 2263do_test pager1-24.1.1 { 2264 faultsim_delete_and_reopen 2265 db func a_string a_string 2266 execsql { 2267 PRAGMA cache_size = 10; 2268 PRAGMA auto_vacuum = FULL; 2269 CREATE TABLE x1(x, y, z, PRIMARY KEY(y, z)); 2270 CREATE TABLE x2(x, y, z, PRIMARY KEY(y, z)); 2271 INSERT INTO x2 VALUES(a_string(400), a_string(500), a_string(600)); 2272 INSERT INTO x2 SELECT a_string(600), a_string(400), a_string(500) FROM x2; 2273 INSERT INTO x2 SELECT a_string(500), a_string(600), a_string(400) FROM x2; 2274 INSERT INTO x2 SELECT a_string(400), a_string(500), a_string(600) FROM x2; 2275 INSERT INTO x2 SELECT a_string(600), a_string(400), a_string(500) FROM x2; 2276 INSERT INTO x2 SELECT a_string(500), a_string(600), a_string(400) FROM x2; 2277 INSERT INTO x2 SELECT a_string(400), a_string(500), a_string(600) FROM x2; 2278 INSERT INTO x1 SELECT * FROM x2; 2279 } 2280} {} 2281do_test pager1-24.1.2 { 2282 execsql { 2283 BEGIN; 2284 DELETE FROM x1 WHERE rowid<32; 2285 } 2286 recursive_select 64 x2 2287} {} 2288do_test pager1-24.1.3 { 2289 execsql { 2290 UPDATE x1 SET z = a_string(300) WHERE rowid>40; 2291 COMMIT; 2292 PRAGMA integrity_check; 2293 SELECT count(*) FROM x1; 2294 } 2295} {ok 33} 2296 2297do_test pager1-24.1.4 { 2298 execsql { 2299 DELETE FROM x1; 2300 INSERT INTO x1 SELECT * FROM x2; 2301 BEGIN; 2302 DELETE FROM x1 WHERE rowid<32; 2303 UPDATE x1 SET z = a_string(299) WHERE rowid>40; 2304 } 2305 recursive_select 64 x2 {db eval COMMIT} 2306 execsql { 2307 PRAGMA integrity_check; 2308 SELECT count(*) FROM x1; 2309 } 2310} {ok 33} 2311 2312do_test pager1-24.1.5 { 2313 execsql { 2314 DELETE FROM x1; 2315 INSERT INTO x1 SELECT * FROM x2; 2316 } 2317 recursive_select 64 x2 { db eval {CREATE TABLE x3(x, y, z)} } 2318 execsql { SELECT * FROM x3 } 2319} {} 2320 2321#------------------------------------------------------------------------- 2322# 2323do_test pager1-25-1 { 2324 faultsim_delete_and_reopen 2325 execsql { 2326 BEGIN; 2327 SAVEPOINT abc; 2328 CREATE TABLE t1(a, b); 2329 ROLLBACK TO abc; 2330 COMMIT; 2331 } 2332 db close 2333} {} 2334do_test pager1-25-2 { 2335 faultsim_delete_and_reopen 2336 execsql { 2337 SAVEPOINT abc; 2338 CREATE TABLE t1(a, b); 2339 ROLLBACK TO abc; 2340 COMMIT; 2341 } 2342 db close 2343} {} 2344 2345#------------------------------------------------------------------------- 2346# Sector-size tests. 2347# 2348do_test pager1-26.1 { 2349 testvfs tv -default 1 2350 tv sectorsize 4096 2351 faultsim_delete_and_reopen 2352 db func a_string a_string 2353 execsql { 2354 PRAGMA page_size = 512; 2355 CREATE TABLE tbl(a PRIMARY KEY, b UNIQUE); 2356 BEGIN; 2357 INSERT INTO tbl VALUES(a_string(25), a_string(600)); 2358 INSERT INTO tbl SELECT a_string(25), a_string(600) FROM tbl; 2359 INSERT INTO tbl SELECT a_string(25), a_string(600) FROM tbl; 2360 INSERT INTO tbl SELECT a_string(25), a_string(600) FROM tbl; 2361 INSERT INTO tbl SELECT a_string(25), a_string(600) FROM tbl; 2362 INSERT INTO tbl SELECT a_string(25), a_string(600) FROM tbl; 2363 INSERT INTO tbl SELECT a_string(25), a_string(600) FROM tbl; 2364 INSERT INTO tbl SELECT a_string(25), a_string(600) FROM tbl; 2365 COMMIT; 2366 } 2367} {} 2368do_execsql_test pager1-26.1 { 2369 UPDATE tbl SET b = a_string(550); 2370} {} 2371db close 2372tv delete 2373 2374#------------------------------------------------------------------------- 2375# 2376do_test pager1.27.1 { 2377 faultsim_delete_and_reopen 2378 sqlite3_pager_refcounts db 2379 execsql { 2380 BEGIN; 2381 CREATE TABLE t1(a, b); 2382 } 2383 sqlite3_pager_refcounts db 2384 execsql COMMIT 2385} {} 2386 2387#------------------------------------------------------------------------- 2388# Test that attempting to open a write-transaction with 2389# locking_mode=exclusive in WAL mode fails if there are other clients on 2390# the same database. 2391# 2392catch { db close } 2393ifcapable wal { 2394 do_multiclient_test tn { 2395 do_test pager1-28.$tn.1 { 2396 sql1 { 2397 PRAGMA journal_mode = WAL; 2398 CREATE TABLE t1(a, b); 2399 INSERT INTO t1 VALUES('a', 'b'); 2400 } 2401 } {wal} 2402 do_test pager1-28.$tn.2 { sql2 { SELECT * FROM t1 } } {a b} 2403 2404 do_test pager1-28.$tn.3 { sql1 { PRAGMA locking_mode=exclusive } } {exclusive} 2405 do_test pager1-28.$tn.4 { 2406 csql1 { BEGIN; INSERT INTO t1 VALUES('c', 'd'); } 2407 } {1 {database is locked}} 2408 code2 { db2 close ; sqlite3 db2 test.db } 2409 do_test pager1-28.$tn.4 { 2410 sql1 { INSERT INTO t1 VALUES('c', 'd'); COMMIT } 2411 } {} 2412 } 2413} 2414 2415#------------------------------------------------------------------------- 2416# Normally, when changing from journal_mode=PERSIST to DELETE the pager 2417# attempts to delete the journal file. However, if it cannot obtain a 2418# RESERVED lock on the database file, this step is skipped. 2419# 2420do_multiclient_test tn { 2421 do_test pager1-28.$tn.1 { 2422 sql1 { 2423 PRAGMA journal_mode = PERSIST; 2424 CREATE TABLE t1(a, b); 2425 INSERT INTO t1 VALUES('a', 'b'); 2426 } 2427 } {persist} 2428 do_test pager1-28.$tn.2 { file exists test.db-journal } 1 2429 do_test pager1-28.$tn.3 { sql1 { PRAGMA journal_mode = DELETE } } delete 2430 do_test pager1-28.$tn.4 { file exists test.db-journal } 0 2431 2432 do_test pager1-28.$tn.5 { 2433 sql1 { 2434 PRAGMA journal_mode = PERSIST; 2435 INSERT INTO t1 VALUES('c', 'd'); 2436 } 2437 } {persist} 2438 do_test pager1-28.$tn.6 { file exists test.db-journal } 1 2439 do_test pager1-28.$tn.7 { 2440 sql2 { BEGIN; INSERT INTO t1 VALUES('e', 'f'); } 2441 } {} 2442 do_test pager1-28.$tn.8 { file exists test.db-journal } 1 2443 do_test pager1-28.$tn.9 { sql1 { PRAGMA journal_mode = DELETE } } delete 2444 do_test pager1-28.$tn.10 { file exists test.db-journal } 1 2445 2446 do_test pager1-28.$tn.11 { sql2 COMMIT } {} 2447 do_test pager1-28.$tn.12 { file exists test.db-journal } 0 2448 2449 do_test pager1-28-$tn.13 { 2450 code1 { set channel [db incrblob -readonly t1 a 2] } 2451 sql1 { 2452 PRAGMA journal_mode = PERSIST; 2453 INSERT INTO t1 VALUES('g', 'h'); 2454 } 2455 } {persist} 2456 do_test pager1-28.$tn.14 { file exists test.db-journal } 1 2457 do_test pager1-28.$tn.15 { 2458 sql2 { BEGIN; INSERT INTO t1 VALUES('e', 'f'); } 2459 } {} 2460 do_test pager1-28.$tn.16 { sql1 { PRAGMA journal_mode = DELETE } } delete 2461 do_test pager1-28.$tn.17 { file exists test.db-journal } 1 2462 2463 do_test pager1-28.$tn.17 { csql2 { COMMIT } } {1 {database is locked}} 2464 do_test pager1-28-$tn.18 { code1 { read $channel } } c 2465 do_test pager1-28-$tn.19 { code1 { close $channel } } {} 2466 do_test pager1-28.$tn.20 { sql2 { COMMIT } } {} 2467} 2468 2469do_test pager1-29.1 { 2470 faultsim_delete_and_reopen 2471 execsql { 2472 PRAGMA page_size = 1024; 2473 PRAGMA auto_vacuum = full; 2474 PRAGMA locking_mode=exclusive; 2475 CREATE TABLE t1(a, b); 2476 INSERT INTO t1 VALUES(1, 2); 2477 } 2478 file size test.db 2479} [expr 1024*3] 2480if {[nonzero_reserved_bytes]} { 2481 # VACUUM with size changes is not possible with the codec. 2482 do_test pager1-29.2 { 2483 catchsql { 2484 PRAGMA page_size = 4096; 2485 VACUUM; 2486 } 2487 } {1 {attempt to write a readonly database}} 2488} else { 2489 do_test pager1-29.2 { 2490 execsql { 2491 PRAGMA page_size = 4096; 2492 VACUUM; 2493 } 2494 file size test.db 2495 } [expr 4096*3] 2496} 2497 2498#------------------------------------------------------------------------- 2499# Test that if an empty database file (size 0 bytes) is opened in 2500# exclusive-locking mode, any journal file is deleted from the file-system 2501# without being rolled back. And that the RESERVED lock obtained while 2502# doing this is not released. 2503# 2504do_test pager1-30.1 { 2505 db close 2506 delete_file test.db 2507 delete_file test.db-journal 2508 set fd [open test.db-journal w] 2509 seek $fd [expr 512+1032*2] 2510 puts -nonewline $fd x 2511 close $fd 2512 2513 sqlite3 db test.db 2514 execsql { 2515 PRAGMA locking_mode=EXCLUSIVE; 2516 SELECT count(*) FROM sqlite_master; 2517 PRAGMA lock_status; 2518 } 2519} {exclusive 0 main reserved temp closed} 2520 2521#------------------------------------------------------------------------- 2522# Test that if the "page-size" field in a journal-header is 0, the journal 2523# file can still be rolled back. This is required for backward compatibility - 2524# versions of SQLite prior to 3.5.8 always set this field to zero. 2525# 2526if {$tcl_platform(platform)=="unix"} { 2527do_test pager1-31.1 { 2528 faultsim_delete_and_reopen 2529 execsql { 2530 PRAGMA cache_size = 10; 2531 PRAGMA page_size = 1024; 2532 CREATE TABLE t1(x, y, UNIQUE(x, y)); 2533 INSERT INTO t1 VALUES(randomblob(1500), randomblob(1500)); 2534 INSERT INTO t1 SELECT randomblob(1500), randomblob(1500) FROM t1; 2535 INSERT INTO t1 SELECT randomblob(1500), randomblob(1500) FROM t1; 2536 INSERT INTO t1 SELECT randomblob(1500), randomblob(1500) FROM t1; 2537 INSERT INTO t1 SELECT randomblob(1500), randomblob(1500) FROM t1; 2538 INSERT INTO t1 SELECT randomblob(1500), randomblob(1500) FROM t1; 2539 INSERT INTO t1 SELECT randomblob(1500), randomblob(1500) FROM t1; 2540 INSERT INTO t1 SELECT randomblob(1500), randomblob(1500) FROM t1; 2541 INSERT INTO t1 SELECT randomblob(1500), randomblob(1500) FROM t1; 2542 INSERT INTO t1 SELECT randomblob(1500), randomblob(1500) FROM t1; 2543 INSERT INTO t1 SELECT randomblob(1500), randomblob(1500) FROM t1; 2544 BEGIN; 2545 UPDATE t1 SET y = randomblob(1499); 2546 } 2547 copy_file test.db test.db2 2548 copy_file test.db-journal test.db2-journal 2549 2550 hexio_write test.db2-journal 24 00000000 2551 sqlite3 db2 test.db2 2552 execsql { PRAGMA integrity_check } db2 2553} {ok} 2554} 2555 2556#------------------------------------------------------------------------- 2557# Test that a database file can be "pre-hinted" to a certain size and that 2558# subsequent spilling of the pager cache does not result in the database 2559# file being shrunk. 2560# 2561catch {db close} 2562forcedelete test.db 2563 2564do_test pager1-32.1 { 2565 sqlite3 db test.db 2566 execsql { 2567 CREATE TABLE t1(x, y); 2568 } 2569 db close 2570 sqlite3 db test.db 2571 execsql { 2572 BEGIN; 2573 INSERT INTO t1 VALUES(1, randomblob(10000)); 2574 } 2575 file_control_chunksize_test db main 1024 2576 file_control_sizehint_test db main 20971520; # 20MB 2577 execsql { 2578 PRAGMA cache_size = 10; 2579 INSERT INTO t1 VALUES(1, randomblob(10000)); 2580 INSERT INTO t1 VALUES(2, randomblob(10000)); 2581 INSERT INTO t1 SELECT x+2, randomblob(10000) from t1; 2582 INSERT INTO t1 SELECT x+4, randomblob(10000) from t1; 2583 INSERT INTO t1 SELECT x+8, randomblob(10000) from t1; 2584 INSERT INTO t1 SELECT x+16, randomblob(10000) from t1; 2585 SELECT count(*) FROM t1; 2586 COMMIT; 2587 } 2588 db close 2589 file size test.db 2590} {20971520} 2591 2592# Cleanup 20MB file left by the previous test. 2593forcedelete test.db 2594 2595#------------------------------------------------------------------------- 2596# Test that if a transaction is committed in journal_mode=DELETE mode, 2597# and the call to unlink() returns an ENOENT error, the COMMIT does not 2598# succeed. 2599# 2600if {$::tcl_platform(platform)=="unix"} { 2601 do_test pager1-33.1 { 2602 sqlite3 db test.db 2603 execsql { 2604 CREATE TABLE t1(x); 2605 INSERT INTO t1 VALUES('one'); 2606 INSERT INTO t1 VALUES('two'); 2607 BEGIN; 2608 INSERT INTO t1 VALUES('three'); 2609 INSERT INTO t1 VALUES('four'); 2610 } 2611 forcedelete bak-journal 2612 file rename test.db-journal bak-journal 2613 2614 catchsql COMMIT 2615 } {1 {disk I/O error}} 2616 2617 do_test pager1-33.2 { 2618 file rename bak-journal test.db-journal 2619 execsql { SELECT * FROM t1 } 2620 } {one two} 2621} 2622 2623#------------------------------------------------------------------------- 2624# Test that appending pages to the database file then moving those pages 2625# to the free-list before the transaction is committed does not cause 2626# an error. 2627# 2628foreach {tn pragma strsize} { 2629 1 { PRAGMA mmap_size = 0 } 2400 2630 2 { } 2400 2631 3 { PRAGMA mmap_size = 0 } 4400 2632 4 { } 4400 2633} { 2634 reset_db 2635 db func a_string a_string 2636 db eval $pragma 2637 do_execsql_test 34.$tn.1 { 2638 CREATE TABLE t1(a, b); 2639 INSERT INTO t1 VALUES(1, 2); 2640 } 2641 do_execsql_test 34.$tn.2 { 2642 BEGIN; 2643 INSERT INTO t1 VALUES(2, a_string($strsize)); 2644 DELETE FROM t1 WHERE oid=2; 2645 COMMIT; 2646 PRAGMA integrity_check; 2647 } {ok} 2648} 2649 2650#------------------------------------------------------------------------- 2651# 2652reset_db 2653do_test 35 { 2654 sqlite3 db test.db 2655 2656 execsql { 2657 CREATE TABLE t1(x, y); 2658 PRAGMA journal_mode = WAL; 2659 INSERT INTO t1 VALUES(1, 2); 2660 } 2661 2662 execsql { 2663 BEGIN; 2664 CREATE TABLE t2(a, b); 2665 } 2666 2667 hexio_write test.db-shm [expr 16*1024] [string repeat 0055 8192] 2668 catchsql ROLLBACK 2669} {0 {}} 2670 2671do_multiclient_test tn { 2672 sql1 { 2673 PRAGMA auto_vacuum = 0; 2674 CREATE TABLE t1(x, y); 2675 INSERT INTO t1 VALUES(1, 2); 2676 } 2677 2678 do_test 36.$tn.1 { 2679 sql2 { PRAGMA max_page_count = 2 } 2680 list [catch { sql2 { CREATE TABLE t2(x) } } msg] $msg 2681 } {1 {database or disk is full}} 2682 2683 sql1 { PRAGMA checkpoint_fullfsync = 1 } 2684 sql1 { CREATE TABLE t2(x) } 2685 2686 do_test 36.$tn.2 { 2687 sql2 { INSERT INTO t2 VALUES('xyz') } 2688 list [catch { sql2 { CREATE TABLE t3(x) } } msg] $msg 2689 } {1 {database or disk is full}} 2690} 2691 2692forcedelete test1 test2 2693foreach {tn uri} { 2694 1 {file:?mode=memory&cache=shared} 2695 2 {file:one?mode=memory&cache=shared} 2696 3 {file:test1?cache=shared} 2697 4 {file:test2?another=parameter&yet=anotherone} 2698} { 2699 do_test 37.$tn { 2700 catch { db close } 2701 sqlite3_shutdown 2702 sqlite3_config_uri 1 2703 sqlite3 db $uri 2704 2705 db eval { 2706 CREATE TABLE t1(x); 2707 INSERT INTO t1 VALUES(1); 2708 SELECT * FROM t1; 2709 } 2710 } {1} 2711 2712 do_execsql_test 37.$tn.2 { 2713 VACUUM; 2714 SELECT * FROM t1; 2715 } {1} 2716 2717 db close 2718 sqlite3_shutdown 2719 sqlite3_config_uri 0 2720} 2721 2722do_test 38.1 { 2723 catch { db close } 2724 forcedelete test.db 2725 set fd [open test.db w] 2726 puts $fd "hello world" 2727 close $fd 2728 sqlite3 db test.db 2729 catchsql { CREATE TABLE t1(x) } 2730} {1 {file is not a database}} 2731do_test 38.2 { 2732 catch { db close } 2733 forcedelete test.db 2734} {} 2735 2736do_test 39.1 { 2737 sqlite3 db test.db 2738 execsql { 2739 PRAGMA auto_vacuum = 1; 2740 CREATE TABLE t1(x); 2741 INSERT INTO t1 VALUES('xxx'); 2742 INSERT INTO t1 VALUES('two'); 2743 INSERT INTO t1 VALUES(randomblob(400)); 2744 INSERT INTO t1 VALUES(randomblob(400)); 2745 INSERT INTO t1 VALUES(randomblob(400)); 2746 INSERT INTO t1 VALUES(randomblob(400)); 2747 BEGIN; 2748 UPDATE t1 SET x = 'one' WHERE rowid=1; 2749 } 2750 set ::stmt [sqlite3_prepare db "SELECT * FROM t1 ORDER BY rowid" -1 dummy] 2751 sqlite3_step $::stmt 2752 sqlite3_column_text $::stmt 0 2753} {one} 2754do_test 39.2 { 2755 execsql { CREATE TABLE t2(x) } 2756 sqlite3_step $::stmt 2757 sqlite3_column_text $::stmt 0 2758} {two} 2759do_test 39.3 { 2760 sqlite3_finalize $::stmt 2761 execsql COMMIT 2762} {} 2763 2764do_execsql_test 39.4 { 2765 PRAGMA auto_vacuum = 2; 2766 CREATE TABLE t3(x); 2767 CREATE TABLE t4(x); 2768 2769 DROP TABLE t2; 2770 DROP TABLE t3; 2771 DROP TABLE t4; 2772} 2773do_test 39.5 { 2774 db close 2775 sqlite3 db test.db 2776 execsql { 2777 PRAGMA cache_size = 1; 2778 PRAGMA incremental_vacuum; 2779 PRAGMA integrity_check; 2780 } 2781} {ok} 2782 2783do_test 40.1 { 2784 reset_db 2785 execsql { 2786 PRAGMA auto_vacuum = 1; 2787 CREATE TABLE t1(x PRIMARY KEY); 2788 INSERT INTO t1 VALUES(randomblob(1200)); 2789 PRAGMA page_count; 2790 } 2791} {6} 2792do_test 40.2 { 2793 execsql { 2794 INSERT INTO t1 VALUES(randomblob(1200)); 2795 INSERT INTO t1 VALUES(randomblob(1200)); 2796 INSERT INTO t1 VALUES(randomblob(1200)); 2797 } 2798} {} 2799do_test 40.3 { 2800 db close 2801 sqlite3 db test.db 2802 execsql { 2803 PRAGMA cache_size = 1; 2804 CREATE TABLE t2(x); 2805 PRAGMA integrity_check; 2806 } 2807} {ok} 2808 2809do_test 41.1 { 2810 reset_db 2811 execsql { 2812 CREATE TABLE t1(x PRIMARY KEY); 2813 INSERT INTO t1 VALUES(randomblob(200)); 2814 INSERT INTO t1 SELECT randomblob(200) FROM t1; 2815 INSERT INTO t1 SELECT randomblob(200) FROM t1; 2816 INSERT INTO t1 SELECT randomblob(200) FROM t1; 2817 INSERT INTO t1 SELECT randomblob(200) FROM t1; 2818 INSERT INTO t1 SELECT randomblob(200) FROM t1; 2819 INSERT INTO t1 SELECT randomblob(200) FROM t1; 2820 } 2821} {} 2822do_test 41.2 { 2823 testvfs tv -default 1 2824 tv sectorsize 16384; 2825 tv devchar [list] 2826 db close 2827 sqlite3 db test.db 2828 execsql { 2829 PRAGMA cache_size = 1; 2830 DELETE FROM t1 WHERE rowid%4; 2831 PRAGMA integrity_check; 2832 } 2833} {ok} 2834db close 2835tv delete 2836 2837set pending_prev [sqlite3_test_control_pending_byte 0x1000000] 2838do_test 42.1 { 2839 reset_db 2840 execsql { 2841 CREATE TABLE t1(x, y); 2842 INSERT INTO t1 VALUES(randomblob(200), randomblob(200)); 2843 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2844 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2845 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2846 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2847 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2848 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2849 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2850 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2851 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2852 } 2853 db close 2854 sqlite3_test_control_pending_byte 0x0010000 2855 sqlite3 db test.db 2856 db eval { PRAGMA mmap_size = 0 } 2857 catchsql { SELECT sum(length(y)) FROM t1 } 2858} {1 {database disk image is malformed}} 2859do_test 42.2 { 2860 reset_db 2861 execsql { 2862 CREATE TABLE t1(x, y); 2863 INSERT INTO t1 VALUES(randomblob(200), randomblob(200)); 2864 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2865 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2866 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2867 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2868 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2869 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2870 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2871 INSERT INTO t1 SELECT randomblob(200), randomblob(200) FROM t1; 2872 } 2873 db close 2874 2875 testvfs tv -default 1 2876 tv sectorsize 16384; 2877 tv devchar [list] 2878 sqlite3 db test.db -vfs tv 2879 execsql { UPDATE t1 SET x = randomblob(200) } 2880} {} 2881db close 2882tv delete 2883sqlite3_test_control_pending_byte $pending_prev 2884 2885do_test 43.1 { 2886 reset_db 2887 execsql { 2888 CREATE TABLE t1(x, y); 2889 INSERT INTO t1 VALUES(1, 2); 2890 CREATE TABLE t2(x, y); 2891 INSERT INTO t2 VALUES(1, 2); 2892 CREATE TABLE t3(x, y); 2893 INSERT INTO t3 VALUES(1, 2); 2894 } 2895 db close 2896 sqlite3 db test.db 2897 2898 db eval { PRAGMA mmap_size = 0 } 2899 db eval { SELECT * FROM t1 } 2900 sqlite3_db_status db CACHE_MISS 0 2901} {0 2 0} 2902 2903do_test 43.2 { 2904 db eval { SELECT * FROM t2 } 2905 sqlite3_db_status db CACHE_MISS 1 2906} {0 3 0} 2907 2908do_test 43.3 { 2909 db eval { SELECT * FROM t3 } 2910 sqlite3_db_status db CACHE_MISS 0 2911} {0 1 0} 2912 2913finish_test 2914