/ Check-in [8f8b373e]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Fix test cases so that they work with SQLITE_DEFAULT_WAL_SAFETYLEVEL defined.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | apple-osx
Files: files | file ages | folders
SHA1: 8f8b373eed7052e6e93c1805fc1effcf1db09366
User & Date: dan 2011-06-25 16:35:41
Context
2011-06-25
21:43
Changes to make pragma synchronous sticky when SQLITE_DEFAULT_WAL_SAFETYLEVEL is used check-in: c6158b25 user: adam tags: apple-osx
16:35
Fix test cases so that they work with SQLITE_DEFAULT_WAL_SAFETYLEVEL defined. check-in: 8f8b373e user: dan tags: apple-osx
2011-06-24
21:47
Fix the build. check-in: 97729542 user: drh tags: apple-osx
Changes
Hide Diffs Side-by-Side Diffs Ignore Whitespace Patch

Changes to src/btree.c.

  2355   2355         rc = sqlite3PagerOpenWal(pBt->pPager, &isOpen);
  2356   2356         if( rc!=SQLITE_OK ){
  2357   2357           goto page1_init_failed;
  2358   2358         }else if( isOpen==0 ){
  2359   2359   #ifdef SQLITE_DEFAULT_WAL_SAFETYLEVEL
  2360   2360           /* Default to specified safety_level for WAL mode */
  2361   2361           if( pBt->db!=0 && pBt->db->aDb!=0 ){
         2362  +          int iDb;
  2362   2363             sqlite3 *db = pBt->db;
  2363         -          if( db->aDb[0].safety_level != SQLITE_DEFAULT_WAL_SAFETYLEVEL) {
  2364         -            db->aDb[0].safety_level = SQLITE_DEFAULT_WAL_SAFETYLEVEL;
         2364  +          Db *aDb = db->aDb;
         2365  +          for(iDb=0; iDb<db->nDb; iDb++){
         2366  +            if( aDb[iDb].pBt && aDb[iDb].pBt->pBt==pBt ) break;
         2367  +          }
         2368  +          assert( iDb<db->nDb );
         2369  +          if( aDb[iDb].safety_level != SQLITE_DEFAULT_WAL_SAFETYLEVEL) {
         2370  +            aDb[iDb].safety_level = SQLITE_DEFAULT_WAL_SAFETYLEVEL;
  2365   2371               sqlite3PagerSetSafetyLevel(pBt->pPager, SQLITE_DEFAULT_WAL_SAFETYLEVEL, 
  2366   2372                                          (db->flags&SQLITE_FullFSync)!=0,
  2367   2373                                          (db->flags&SQLITE_CkptFullFSync)!=0);
  2368   2374             }
  2369   2375           }
  2370   2376   #endif
  2371   2377           releasePage(pPage1);

Changes to test/incrvacuum2.test.

    11     11   # This file implements regression tests for SQLite library.  The
    12     12   # focus of this file is testing the incremental vacuum feature.
    13     13   #
    14     14   # $Id: incrvacuum2.test,v 1.6 2009/07/25 13:42:50 danielk1977 Exp $
    15     15   
    16     16   set testdir [file dirname $argv0]
    17     17   source $testdir/tester.tcl
           18  +source $testdir/wal_common.tcl
    18     19   
    19     20   # If this build of the library does not support auto-vacuum, omit this
    20     21   # whole file.
    21     22   ifcapable {!autovacuum || !pragma} {
    22     23     finish_test
    23     24     return
    24     25   }
................................................................................
   184    185       DELETE FROM t1;
   185    186     }
   186    187   
   187    188     do_test 4.2 {
   188    189       execsql { 
   189    190         PRAGMA journal_mode = WAL;
   190    191         PRAGMA incremental_vacuum(1);
   191         -      PRAGMA wal_checkpoint;
   192    192       }
          193  +  } {wal}
          194  +  do_test 4.2.1 {
          195  +    execsql { PRAGMA wal_checkpoint }
   193    196       file size test.db-wal
   194         -  } {1640}
          197  +  } [wal_file_size [wal_frames db 2 1] 512]
   195    198   
   196    199     do_test 4.3 {
   197    200       db close
   198    201       sqlite3 db test.db
   199    202       set maxsz 0
   200    203       while {[file size test.db] > [expr 512*3]} {
   201    204         execsql { PRAGMA journal_mode = WAL }
   202    205         execsql { PRAGMA wal_checkpoint }
   203    206         execsql { PRAGMA incremental_vacuum(1) }
   204    207         set newsz [file size test.db-wal]
   205    208         if {$newsz>$maxsz} {set maxsz $newsz}
   206    209       }
   207    210       set maxsz 
   208         -  } {2176}
          211  +  } [wal_file_size [wal_frames db 3 1] 512]
   209    212   }
   210    213   
   211    214   finish_test

Changes to test/pager1.test.

  2004   2004     execsql { PRAGMA wal_checkpoint }
  2005   2005   } {0 -1 -1}
  2006   2006   do_test pager1-22.2.1 {
  2007   2007     testvfs tv -default 1
  2008   2008     tv filter xSync
  2009   2009     tv script xSyncCb
  2010   2010     proc xSyncCb {args} {incr ::synccount}
  2011         -  set ::synccount 0
  2012   2011     sqlite3 db test.db
         2012  +
         2013  +  # Switch the db to WAL mode. And then execute a SELECT to make sure
         2014  +  # that the WAL file is open. Note that this may change the synchronous
         2015  +  # setting if DEFAULT_WAL_SAFETYLEVEL is defined.
         2016  +  execsql { PRAGMA journal_mode = WAL ; SELECT * FROM ko }
         2017  +
         2018  +  # Set synchronous=OFF. Insert some data and run a checkpoint. Since
         2019  +  # sync=off, this should not cause any calls to the xSync() method.
         2020  +  set ::synccount 0
  2013   2021     execsql {
  2014         -    PRAGMA journal_mode = WAL;
  2015   2022       PRAGMA synchronous = off;
  2016   2023       INSERT INTO ko DEFAULT VALUES;
         2024  +    PRAGMA wal_checkpoint;
  2017   2025     }
  2018         -  execsql { PRAGMA wal_checkpoint }
  2019   2026     set synccount
  2020   2027   } {0}
  2021         -db close
  2022         -tv delete
  2023   2028   
  2024   2029   #-------------------------------------------------------------------------
  2025   2030   # Tests for changing journal mode.
  2026   2031   #
  2027   2032   #   pager1-23.1.*: Test that when changing from PERSIST to DELETE mode,
  2028   2033   #                  the journal file is deleted.
  2029   2034   #

Changes to test/superlock.test.

     9      9   #
    10     10   #***********************************************************************
    11     11   #
    12     12   
    13     13   set testdir [file dirname $argv0]
    14     14   source $testdir/tester.tcl
    15     15   source $testdir/lock_common.tcl
           16  +source $testdir/wal_common.tcl
    16     17   
    17     18   set testprefix superlock
    18     19   
    19     20   # Test organization:
    20     21   #
    21     22   #   1.*: Test superlock on a rollback database. Test that once the db is
    22     23   #        superlocked, it is not possible for a second client to read from
................................................................................
    73     74   
    74     75   do_test 3.2 { sqlite3demo_superlock unlock test.db } {unlock}
    75     76   do_catchsql_test 3.3 { SELECT * FROM t1 }           {1 {database is locked}}
    76     77   do_catchsql_test 3.4 { INSERT INTO t1 VALUES(5, 6)} {1 {database is locked}}
    77     78   do_catchsql_test 3.5 { PRAGMA wal_checkpoint }      {0 {1 -1 -1}}
    78     79   do_test 3.6 { unlock } {}
    79     80   
    80         -do_execsql_test 4.1 { PRAGMA wal_checkpoint } {0 2 2}
           81  +do_execsql_test 4.1 { PRAGMA wal_checkpoint } [
           82  +  list 0 [wal_frames db 1 1] [wal_frames db 1 1]
           83  +]
    81     84   
    82     85   do_test 4.2 { sqlite3demo_superlock unlock test.db } {unlock}
    83     86   do_catchsql_test 4.3 { SELECT * FROM t1 }           {1 {database is locked}}
    84     87   do_catchsql_test 4.4 { INSERT INTO t1 VALUES(5, 6)} {1 {database is locked}}
    85     88   do_catchsql_test 4.5 { PRAGMA wal_checkpoint }      {0 {1 -1 -1}}
    86     89   do_test 4.6 { unlock } {}
    87     90   

Changes to test/wal.test.

   544    544     # Open a read transaction with [db2]. Check that this prevents [db] from
   545    545     # checkpointing the database. But not from writing to it.
   546    546     #
   547    547     do_test wal-10.$tn.11 {
   548    548       sql2 { BEGIN; SELECT * FROM t1 }
   549    549     } {1 2 3 4 5 6 7 8 9 10}
   550    550     do_test wal-10.$tn.12 {
   551         -    catchsql { PRAGMA wal_checkpoint } 
   552         -  } {0 {0 13 13}}   ;# Reader no longer block checkpoints
          551  +    # Reader no longer blocks checkpoint:
          552  +    execsql { PRAGMA wal_checkpoint } 
          553  +  } [list 0 [wal_frames db 8 5] [wal_frames db 8 5]] 
   553    554     do_test wal-10.$tn.13 {
   554    555       execsql { INSERT INTO t1 VALUES(11, 12) }
   555    556       sql2 {SELECT * FROM t1}
   556    557     } {1 2 3 4 5 6 7 8 9 10}
   557    558   
   558    559     # Writers do not block checkpoints any more either.
   559    560     #
   560    561     do_test wal-10.$tn.14 {
   561         -    catchsql { PRAGMA wal_checkpoint } 
   562         -  } {0 {0 15 13}}
          562  +    execsql { PRAGMA wal_checkpoint } 
          563  +  } [list 0 [wal_frames db 9 6] [wal_frames db 8 5]]
   563    564   
   564    565     # The following series of test cases used to verify another blocking
   565    566     # case in WAL - a case which no longer blocks.
   566    567     #
   567    568     do_test wal-10.$tn.15 {
   568    569       sql2 { COMMIT; BEGIN; SELECT * FROM t1; }
   569    570     } {1 2 3 4 5 6 7 8 9 10 11 12}
   570    571     do_test wal-10.$tn.16 {
   571         -    catchsql { PRAGMA wal_checkpoint } 
   572         -  } {0 {0 15 15}}
          572  +    execsql { PRAGMA wal_checkpoint } 
          573  +  } [list 0 [wal_frames db 9 6] [wal_frames db 9 6]]
   573    574     do_test wal-10.$tn.17 {
   574    575       execsql { PRAGMA wal_checkpoint } 
   575         -  } {0 15 15}
          576  +  } [list 0 [wal_frames db 9 6] [wal_frames db 9 6]]
   576    577     do_test wal-10.$tn.18 {
   577    578       sql3 { BEGIN; SELECT * FROM t1 }
   578    579     } {1 2 3 4 5 6 7 8 9 10 11 12}
   579    580     do_test wal-10.$tn.19 {
   580    581       catchsql { INSERT INTO t1 VALUES(13, 14) }
   581    582     } {0 {}}
   582    583     do_test wal-10.$tn.20 {
................................................................................
   591    592     } {1 2 3 4 5 6 7 8 9 10 11 12 13 14}
   592    593   
   593    594     # Another series of tests that used to demonstrate blocking behavior
   594    595     # but which now work.
   595    596     #
   596    597     do_test wal-10.$tn.23 {
   597    598       execsql { PRAGMA wal_checkpoint }
   598         -  } {0 17 17}
          599  +  } [list 0 [wal_frames db 10 7] [wal_frames db 10 7]]
   599    600     do_test wal-10.$tn.24 {
   600    601       sql2 { BEGIN; SELECT * FROM t1; }
   601    602     } {1 2 3 4 5 6 7 8 9 10 11 12 13 14}
   602    603     do_test wal-10.$tn.25 {
   603    604       execsql { PRAGMA wal_checkpoint }
   604         -  } {0 17 17}
          605  +  } [list 0 [wal_frames db 10 7] [wal_frames db 10 7]]
   605    606     do_test wal-10.$tn.26 {
   606    607       catchsql { INSERT INTO t1 VALUES(15, 16) }
   607    608     } {0 {}}
   608    609     do_test wal-10.$tn.27 {
   609    610       sql3 { INSERT INTO t1 VALUES(17, 18) }
   610    611     } {}
   611    612     do_test wal-10.$tn.28 {
................................................................................
   613    614         set ::STMT [sqlite3_prepare db3 "SELECT * FROM t1" -1 TAIL]
   614    615         sqlite3_step $::STMT
   615    616       }
   616    617       execsql { SELECT * FROM t1 }
   617    618     } {1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18}
   618    619     do_test wal-10.$tn.29 {
   619    620       execsql { INSERT INTO t1 VALUES(19, 20) }
   620         -    catchsql { PRAGMA wal_checkpoint }
   621         -  } {0 {0 6 0}}
          621  +    execsql { PRAGMA wal_checkpoint }
          622  +  } [list 0 [wal_frames db 4 2] 0]
   622    623     do_test wal-10.$tn.30 {
   623    624       code3 { sqlite3_finalize $::STMT }
   624    625       execsql { PRAGMA wal_checkpoint }
   625         -  } {0 6 0}
          626  +  } [list 0 [wal_frames db 4 2] 0]
   626    627   
   627    628     # At one point, if a reader failed to upgrade to a writer because it
   628    629     # was reading an old snapshot, the write-locks were not being released.
   629    630     # Test that this bug has been fixed.
   630    631     #
   631    632     do_test wal-10.$tn.31 {
   632    633       sql2 COMMIT
................................................................................
   656    657       }
   657    658       sql2 {
   658    659         BEGIN;
   659    660           SELECT * FROM t1;
   660    661       }
   661    662     } {a b c d}
   662    663     do_test wal-10.$tn.36 {
   663         -    catchsql { PRAGMA wal_checkpoint }
   664         -  } {0 {0 16 16}}
          664  +    execsql { PRAGMA wal_checkpoint }
          665  +  } [list 0 [wal_frames db 11 5] [wal_frames db 11 5]]
   665    666     do_test wal-10.$tn.36 {
   666    667       sql3 { INSERT INTO t1 VALUES('e', 'f') }
   667    668       sql2 { SELECT * FROM t1 }
   668    669     } {a b c d}
   669    670     do_test wal-10.$tn.37 {
   670    671       sql2 COMMIT
   671    672       execsql { PRAGMA wal_checkpoint }
   672         -  } {0 18 18}
          673  +  } [list 0 [wal_frames db 13 5] [wal_frames db 13 5]]
   673    674   }
   674    675   
   675    676   #-------------------------------------------------------------------------
   676    677   # This block of tests, wal-11.*, test that nothing goes terribly wrong
   677    678   # if frames must be written to the log file before a transaction is
   678    679   # committed (in order to free up memory).
   679    680   #
................................................................................
  1053   1054       sqlite3 db test.db
  1054   1055       execsql {
  1055   1056         ATTACH 'test2.db' AS aux;
  1056   1057         PRAGMA main.auto_vacuum = 0;
  1057   1058         PRAGMA aux.auto_vacuum = 0;
  1058   1059         PRAGMA main.journal_mode = WAL;
  1059   1060         PRAGMA aux.journal_mode = WAL;
         1061  +      SELECT count(*) FROM main.sqlite_master, aux.sqlite_master;
  1060   1062         PRAGMA synchronous = NORMAL;
         1063  +      PRAGMA aux.synchronous = FULL;
  1061   1064       }
  1062         -  } {wal wal}
         1065  +  } {wal wal 0}
  1063   1066   
  1064   1067     do_test wal-16.$tn.2 {
  1065   1068       execsql {
  1066   1069         CREATE TABLE main.t1(a, b, PRIMARY KEY(a, b));
  1067   1070         CREATE TABLE aux.t2(a, b, PRIMARY KEY(a, b));
  1068   1071   
  1069   1072         INSERT INTO t2 VALUES(1, randomblob(1000));
................................................................................
  1125   1128     sqlite3 db test.db -vfs devsym
  1126   1129   
  1127   1130     do_test wal-17.$tn.1 {
  1128   1131       execsql {
  1129   1132         PRAGMA auto_vacuum = 0;
  1130   1133         PRAGMA page_size = 512;
  1131   1134         PRAGMA journal_mode = WAL;
         1135  +      SELECT * FROM sqlite_master;
  1132   1136         PRAGMA synchronous = FULL;
  1133   1137       }
  1134   1138       execsql {
  1135   1139         BEGIN;
  1136   1140         CREATE TABLE t(x);
  1137   1141       }
  1138   1142       for {set i 0} {$i<166} {incr i} {
................................................................................
  1552   1556         PRAGMA incremental_vacuum;
  1553   1557         PRAGMA wal_checkpoint;
  1554   1558       }
  1555   1559       file size test.db
  1556   1560     } [expr 3 * 1024]
  1557   1561     do_test 24.5 {
  1558   1562       file size test.db-wal
  1559         -  } 2128
         1563  +  } [wal_file_size [wal_frames db 1 1] 1024]
  1560   1564   }
  1561   1565   
  1562   1566   db close
  1563   1567   sqlite3_shutdown
  1564   1568   test_sqlite3_log
  1565   1569   sqlite3_initialize
  1566   1570   
  1567   1571   finish_test

Changes to test/wal2.test.

   352    352   
   353    353   }
   354    354   
   355    355   #-------------------------------------------------------------------------
   356    356   # Test that a database connection using a VFS that does not support the
   357    357   # xShmXXX interfaces cannot open a WAL database.
   358    358   #
   359         -do_test wal2-4.1 {
          359  +do_test wal2-4.1.1 {
   360    360     sqlite3 db test.db
   361    361     execsql {
   362    362       PRAGMA auto_vacuum = 0;
   363    363       PRAGMA journal_mode = WAL;
   364    364       CREATE TABLE data(x);
   365    365       INSERT INTO data VALUES('need xShmOpen to see this');
          366  +  }
          367  +} {wal}
          368  +do_test wal2-4.1.2 {
          369  +  execsql {
   366    370       PRAGMA wal_checkpoint;
   367    371     }
   368         -} {wal 0 5 5}
          372  +} [list 0 [wal_frames db 3 2] [wal_frames db 3 2]]
   369    373   do_test wal2-4.2 {
   370    374     db close
   371    375     testvfs tvfs -noshm 1
   372    376     sqlite3 db test.db -vfs tvfs
   373    377     catchsql { SELECT * FROM data }
   374    378   } {1 {unable to open database file}}
   375    379   do_test wal2-4.3 {
................................................................................
   718    722     do_test wal2-6.4.$tn.1 { execsql $S } $res
   719    723     do_test wal2-6.4.$tn.2 { set ::locks  } $L
   720    724   }
   721    725   
   722    726   db close
   723    727   tvfs delete
   724    728   
   725         -do_test wal2-6.5.1 {
          729  +do_test wal2-6.5.1.1 {
   726    730     sqlite3 db test.db
   727    731     execsql {
   728    732       PRAGMA auto_vacuum = 0;
   729    733       PRAGMA journal_mode = wal;
   730    734       PRAGMA locking_mode = exclusive;
   731    735       CREATE TABLE t2(a, b);
          736  +  }
          737  +} {wal exclusive}
          738  +do_test wal2-6.5.1.2 {
          739  +  execsql {
   732    740       PRAGMA wal_checkpoint;
   733    741       INSERT INTO t2 VALUES('I', 'II');
   734    742       PRAGMA journal_mode;
   735    743     }
   736         -} {wal exclusive 0 3 3 wal}
          744  +} [list 0 [wal_frames db 2 1] [wal_frames db 2 1] wal]
   737    745   do_test wal2-6.5.2 {
   738    746     execsql {
   739    747       PRAGMA locking_mode = normal;
   740    748       INSERT INTO t2 VALUES('III', 'IV');
   741    749       PRAGMA locking_mode = exclusive;
   742    750       SELECT * FROM t2;
   743    751     }
   744    752   } {normal exclusive I II III IV}
   745    753   do_test wal2-6.5.3 {
   746    754     execsql { PRAGMA wal_checkpoint }
   747         -} {0 4 4}
          755  +} [list 0 [wal_frames db 2 2] [wal_frames db 2 2]]
   748    756   db close
   749    757   
   750    758   proc lock_control {method filename handle spec} {
   751    759     foreach {start n op type} $spec break
   752    760     if {$op == "lock"} { return SQLITE_IOERR }
   753    761     return SQLITE_OK
   754    762   }
................................................................................
  1174   1182       catch { db close }
  1175   1183     }
  1176   1184   }
  1177   1185   
  1178   1186   #-------------------------------------------------------------------------
  1179   1187   # Test that "PRAGMA checkpoint_fullsync" appears to be working.
  1180   1188   #
  1181         -foreach {tn sql reslist} {
  1182         -  1 { }                                 {8 0 3 0 5 0}
  1183         -  2 { PRAGMA checkpoint_fullfsync = 1 } {8 4 3 2 5 2}
  1184         -  3 { PRAGMA checkpoint_fullfsync = 0 } {8 0 3 0 5 0}
         1189  +foreach {tn sql} {
         1190  +  1 { } 
         1191  +  2 { PRAGMA checkpoint_fullfsync = 1 }
         1192  +  3 { PRAGMA checkpoint_fullfsync = 0 }
  1185   1193   } {
  1186         -  if { $::sqlite_options(default_ckptfullfsync) && $tn == 1} {
  1187         -    # checkpoint_fullfsync on by default
  1188         -    set reslist {8 4 3 2 5 2}
  1189         -  }
  1190         -
  1191   1194     faultsim_delete_and_reopen
  1192   1195   
  1193   1196     execsql {PRAGMA auto_vacuum = 0}
  1194   1197     execsql $sql
  1195         -  do_execsql_test wal2-14.$tn.1 { PRAGMA journal_mode = WAL } {wal}
         1198  +  do_execsql_test wal2-14.$tn.1 { 
         1199  +    PRAGMA journal_mode = WAL;
         1200  +    PRAGMA wal_autocheckpoint = 10;
         1201  +  } {wal 10}
         1202  +
         1203  +  unset -nocomplain res
         1204  +  set res(0,1) {5 0 2 0 2 0}      ;# checkpoint_fullfsync=0 sync=NORMAL
         1205  +  set res(0,2) {8 0 3 0 5 0}      ;# checkpoint_fullfsync=0 sync=FULL
         1206  +  set res(1,1) {5 4 2 2 2 2}      ;# checkpoint_fullfsync=1 sync=NORMAL
         1207  +  set res(1,2) {8 4 3 2 5 2}      ;# checkpoint_fullfsync=1 sync=FULL
         1208  +
         1209  +  set key1 [db one {PRAGMA checkpoint_fullfsync}]
         1210  +  set key2 [db one {PRAGMA main.synchronous}]
         1211  +  set reslist $res($key1,$key2)
  1196   1212   
  1197   1213     set sqlite_sync_count 0
  1198   1214     set sqlite_fullsync_count 0
  1199   1215   
  1200   1216     do_execsql_test wal2-14.$tn.2 {
  1201         -    PRAGMA wal_autocheckpoint = 10;
  1202   1217       CREATE TABLE t1(a, b);                -- 2 wal syncs
  1203   1218       INSERT INTO t1 VALUES(1, 2);          -- 1 wal sync
  1204   1219       PRAGMA wal_checkpoint;                -- 1 wal sync, 1 db sync
  1205   1220       BEGIN;
  1206   1221         INSERT INTO t1 VALUES(3, 4);
  1207   1222         INSERT INTO t1 VALUES(5, 6);
  1208   1223       COMMIT;                               -- 1 wal sync
  1209   1224       PRAGMA wal_checkpoint;                -- 1 wal sync, 1 db sync
  1210         -  } {10 0 5 5 0 2 2}
         1225  +  } [list 0 [wal_frames db 3 2] [wal_frames db 3 2] \
         1226  +          0 [wal_frames db 1 1] [wal_frames db 1 1] \
         1227  +  ]
  1211   1228   
  1212   1229     do_test wal2-14.$tn.3 {
  1213   1230       cond_incr_sync_count 1
  1214   1231       list $sqlite_sync_count $sqlite_fullsync_count
  1215   1232     } [lrange $reslist 0 1]
  1216   1233   
  1217   1234     set sqlite_sync_count 0
................................................................................
  1237   1254   
  1238   1255   catch { db close }
  1239   1256   
  1240   1257   # PRAGMA checkpoint_fullsync
  1241   1258   # PRAGMA fullfsync
  1242   1259   # PRAGMA synchronous
  1243   1260   #
  1244         -foreach {tn settings commit_sync ckpt_sync} {
  1245         -  1  {0 0 off}     {0 0}  {0 0}
  1246         -  2  {0 0 normal}  {0 0}  {2 0}
  1247         -  3  {0 0 full}    {1 0}  {2 0}
         1261  +foreach {tn settings} {
         1262  +  1  {0 0 off}    
         1263  +  2  {0 0 normal}
         1264  +  3  {0 0 full} 
  1248   1265   
  1249         -  4  {0 1 off}     {0 0}  {0 0}
  1250         -  5  {0 1 normal}  {0 0}  {0 2}
  1251         -  6  {0 1 full}    {0 1}  {0 2}
         1266  +  4  {0 1 off} 
         1267  +  5  {0 1 normal} 
         1268  +  6  {0 1 full}  
         1269  +
         1270  +  7  {1 0 off}  
         1271  +  8  {1 0 normal}
         1272  +  9  {1 0 full} 
  1252   1273   
  1253         -  7  {1 0 off}     {0 0}  {0 0}
  1254         -  8  {1 0 normal}  {0 0}  {0 2}
  1255         -  9  {1 0 full}    {1 0}  {0 2}
  1256         -
  1257         -  10 {1 1 off}     {0 0}  {0 0}
  1258         -  11 {1 1 normal}  {0 0}  {0 2}
  1259         -  12 {1 1 full}    {0 1}  {0 2}
         1274  +  10 {1 1 off} 
         1275  +  11 {1 1 normal}
         1276  +  12 {1 1 full} 
  1260   1277   } {
  1261   1278     forcedelete test.db
  1262   1279   
  1263   1280     testvfs tvfs -default 1
  1264   1281     tvfs filter xSync
  1265   1282     tvfs script xSyncCb
  1266   1283     proc xSyncCb {method file fileid flags} {
................................................................................
  1270   1287     sqlite3 db test.db
  1271   1288     do_execsql_test 15.$tn.1 "
  1272   1289       CREATE TABLE t1(x);
  1273   1290       PRAGMA journal_mode = WAL;
  1274   1291       PRAGMA checkpoint_fullfsync = [lindex $settings 0];
  1275   1292       PRAGMA fullfsync = [lindex $settings 1];
  1276   1293       PRAGMA synchronous = [lindex $settings 2];
  1277         -  " {wal}
         1294  +    SELECT count(*) FROM sqlite_master;
         1295  +  " {wal 1}
         1296  +
         1297  +  unset -nocomplain res
         1298  +  set res(0,0,0) {{0 0}  {0 0}}
         1299  +  set res(0,0,1) {{0 0}  {2 0}}
         1300  +  set res(0,0,2) {{1 0}  {2 0}}
         1301  +  set res(0,1,0) {{0 0}  {0 0}}
         1302  +  set res(0,1,1) {{0 0}  {0 2}}
         1303  +  set res(0,1,2) {{0 1}  {0 2}}
         1304  +  set res(1,0,0) {{0 0}  {0 0}}
         1305  +  set res(1,0,1) {{0 0}  {0 2}}
         1306  +  set res(1,0,2) {{1 0}  {0 2}}
         1307  +  set res(1,1,0) {{0 0}  {0 0}}
         1308  +  set res(1,1,1) {{0 0}  {0 2}}
         1309  +  set res(1,1,2) {{0 1}  {0 2}}
         1310  +
         1311  +  set key1 [db one {PRAGMA checkpoint_fullfsync}]
         1312  +  set key2 [db one {PRAGMA fullfsync}]
         1313  +  set key3 [db one {PRAGMA synchronous}]
         1314  +
         1315  +  set commit_sync [lindex $res($key1,$key2,$key3) 0]
         1316  +  set ckpt_sync   [lindex $res($key1,$key2,$key3) 1]
  1278   1317   
  1279   1318     do_test 15.$tn.2 {
  1280   1319       set sync(normal) 0
  1281   1320       set sync(full) 0
  1282   1321       execsql { INSERT INTO t1 VALUES('abc') }
  1283   1322       list $::sync(normal) $::sync(full)
  1284   1323     } $commit_sync

Changes to test/wal3.test.

   225    225       file delete -force test.db test.db-wal test.db-journal
   226    226     
   227    227       testvfs T
   228    228       T filter {} 
   229    229       T script sync_counter
   230    230       sqlite3 db test.db -vfs T
   231    231     
   232         -    execsql "PRAGMA synchronous = $syncmode"
   233    232       execsql { PRAGMA journal_mode = WAL }
          233  +    execsql { SELECT * FROM sqlite_master }
          234  +    execsql "PRAGMA synchronous = $syncmode"
   234    235   
   235    236       set ::syncs [list]
   236    237       T filter xSync
   237    238       execsql {
   238    239         CREATE TABLE x(y);
   239    240         INSERT INTO x VALUES('z');
   240    241         PRAGMA wal_checkpoint;
................................................................................
   438    439   do_test wal3-6.1.2 {
   439    440     sqlite3 db2 test.db
   440    441     sqlite3 db3 test.db
   441    442     execsql { BEGIN ; SELECT * FROM t1 } db3
   442    443   } {o t t f}
   443    444   do_test wal3-6.1.3 {
   444    445     execsql { PRAGMA wal_checkpoint } db2
   445         -} {0 7 7}
          446  +} [list 0 [wal_frames db 4 3] [wal_frames db 4 3]]
   446    447   
   447    448   # At this point the log file has been fully checkpointed. However, 
   448    449   # connection [db3] holds a lock that prevents the log from being wrapped.
   449    450   # Test case 3.6.1.4 has [db] attempt a read-lock on aReadMark[0]. But
   450    451   # as it is obtaining the lock, [db2] appends to the log file.
   451    452   #
   452    453   T filter xShmLock
................................................................................
   527    528         BEGIN;
   528    529         SELECT * FROM t1;
   529    530       }]
   530    531     }
   531    532   }
   532    533   do_test wal3-6.2.2 {
   533    534     execsql { PRAGMA wal_checkpoint }
   534         -} {0 7 7}
          535  +} [list 0 [wal_frames db 4 3] [wal_frames db 4 3]]
   535    536   do_test wal3-6.2.3 {
   536    537     set ::R
   537    538   } {h h l b}
   538    539   do_test wal3-6.2.4 {
   539    540     set sz1 [file size test.db-wal]
   540    541     execsql { INSERT INTO t1 VALUES('b', 'c'); }
   541    542     set sz2 [file size test.db-wal]
................................................................................
   624    625   
   625    626   db close
   626    627   db2 close
   627    628   T delete
   628    629   
   629    630   #-------------------------------------------------------------------------
   630    631   # 
   631         -do_test wal3-8.1 {
          632  +do_test wal3-8.1.1 {
   632    633     file delete -force test.db test.db-journal test.db wal .test.db-conch
   633    634     sqlite3 db test.db
   634    635     sqlite3 db2 test.db
   635    636     execsql {
   636    637       PRAGMA auto_vacuum = off;
   637    638       PRAGMA journal_mode = WAL;
   638    639       CREATE TABLE b(c);
   639    640       INSERT INTO b VALUES('Tehran');
   640    641       INSERT INTO b VALUES('Qom');
   641    642       INSERT INTO b VALUES('Markazi');
   642         -    PRAGMA wal_checkpoint;
   643    643     }
   644         -} {wal 0 9 9}
          644  +} {wal}
          645  +
          646  +do_test wal3.8.1.2 {
          647  +  execsql { PRAGMA wal_checkpoint; }
          648  +} [list 0 [wal_frames db 5 4] [wal_frames db 5 4]]
   645    649   do_test wal3-8.2 {
   646    650     execsql { SELECT * FROM b }
   647    651   } {Tehran Qom Markazi}
   648    652   do_test wal3-8.3 {
   649    653     db eval { SELECT * FROM b } {
   650    654       db eval { INSERT INTO b VALUES('Qazvin') }
   651    655       set r [db2 eval { SELECT * FROM b }]

Changes to test/wal5.test.

   193    193         sql1 {
   194    194           CREATE TABLE t1(a, b);
   195    195           INSERT INTO t1 VALUES(1, 2);
   196    196           CREATE TABLE aux.t2(a, b);
   197    197           INSERT INTO t2 VALUES(1, 2);
   198    198         }
   199    199       } {}
   200         -    do_test 2.2.$tn.2 { file_page_counts } {1 5 1 5}
   201         -    do_test 2.1.$tn.3 { code1 { do_wal_checkpoint db } } {0 5 5}
   202         -    do_test 2.1.$tn.4 { file_page_counts } {2 5 2 5}
          200  +    do_test 2.2.$tn.2 { file_page_counts } [
          201  +      list 1 [wal_frames db 3 2] 1 [wal_frames db 3 2]
          202  +    ]
          203  +    do_test 2.1.$tn.3 { code1 { do_wal_checkpoint db } } [
          204  +      list 0 [wal_frames db 3 2] [wal_frames db 3 2]
          205  +    ]
          206  +    do_test 2.1.$tn.4 { file_page_counts } [
          207  +      list 2 [wal_frames db 3 2] 2 [wal_frames db 3 2]
          208  +    ]
   203    209     }
   204    210   
   205    211     do_multiclient_test tn {
   206    212       setup_and_attach_aux
   207    213       do_test 2.2.$tn.1 {
   208    214         execsql {
   209    215           CREATE TABLE t1(a, b);
   210    216           INSERT INTO t1 VALUES(1, 2);
   211    217           CREATE TABLE aux.t2(a, b);
   212    218           INSERT INTO t2 VALUES(1, 2);
   213    219           INSERT INTO t2 VALUES(3, 4);
   214    220         }
   215    221       } {}
   216         -    do_test 2.2.$tn.2 { file_page_counts } {1 5 1 7}
          222  +    do_test 2.2.$tn.2 { file_page_counts } [
          223  +      list 1 [wal_frames db 3 2] 1 [wal_frames db 4 3]
          224  +    ]
   217    225       do_test 2.2.$tn.3 { sql2 { BEGIN; SELECT * FROM t1 } } {1 2}
   218         -    do_test 2.2.$tn.4 { code1 { do_wal_checkpoint db -mode restart } } {1 5 5}
   219         -    do_test 2.2.$tn.5 { file_page_counts } {2 5 2 7}
          226  +    do_test 2.2.$tn.4 { code1 { do_wal_checkpoint db -mode restart } } [
          227  +      list 1 [wal_frames db 3 2] [wal_frames db 3 2]
          228  +    ]
          229  +    do_test 2.2.$tn.5 { file_page_counts } [
          230  +      list 2 [wal_frames db 3 2] 2 [wal_frames db 4 3]
          231  +    ]
   220    232     }
   221    233   
   222    234     do_multiclient_test tn {
   223    235       setup_and_attach_aux
   224    236       do_test 2.3.$tn.1 {
   225    237         execsql {
   226    238           CREATE TABLE t1(a, b);
   227    239           INSERT INTO t1 VALUES(1, 2);
   228    240           CREATE TABLE aux.t2(a, b);
   229    241           INSERT INTO t2 VALUES(1, 2);
   230    242         }
   231    243       } {}
   232         -    do_test 2.3.$tn.2 { file_page_counts } {1 5 1 5}
          244  +    do_test 2.3.$tn.2 { file_page_counts } [
          245  +      list 1 [wal_frames db 3 2] 1 [wal_frames db 3 2]
          246  +    ]
   233    247       do_test 2.3.$tn.3 { sql2 { BEGIN; SELECT * FROM t1 } } {1 2}
   234    248       do_test 2.3.$tn.4 { sql1 { INSERT INTO t1 VALUES(3, 4) } } {}
   235    249       do_test 2.3.$tn.5 { sql1 { INSERT INTO t2 VALUES(3, 4) } } {}
   236         -    do_test 2.3.$tn.6 { file_page_counts } {1 7 1 7}
   237         -    do_test 2.3.$tn.7 { code1 { do_wal_checkpoint db -mode full } } {1 7 5}
          250  +    do_test 2.3.$tn.6 { file_page_counts } [
          251  +      list 1 [wal_frames db 4 3] 1 [wal_frames db 4 3]
          252  +    ]
          253  +    do_test 2.3.$tn.7 { code1 { do_wal_checkpoint db -mode full } } [
          254  +      list 1 [wal_frames db 4 3] [wal_frames db 3 2]
          255  +    ]
   238    256       if {$tcl_platform(platform) == "windows"} {
   239    257           # on unix, the size_hint is a no-op if no chunk size is set.
   240    258           # the windows implementation does not have a similar check,
   241    259           # and because of this, the db file size has an extra page.
   242    260           do_test 2.3.$tn.8 { file_page_counts } {2 7 2 7}
   243    261       } {
   244         -        do_test 2.3.$tn.8 { file_page_counts } {1 7 2 7}
          262  +        do_test 2.3.$tn.8 { file_page_counts } [
          263  +          list 1 [wal_frames db 4 3] 2 [wal_frames db 4 3]
          264  +        ]
   245    265       }
   246    266     }
   247    267   
   248    268     # Check that checkpoints block on the correct locks. And respond correctly
   249    269     # if they cannot obtain those locks. There are three locks that a checkpoint
   250    270     # may block on (in the following order):
   251    271     #
................................................................................
   297    317             CREATE TABLE t1(a, b);
   298    318             INSERT INTO t1 VALUES(1, 2);
   299    319           }
   300    320           sql2 { BEGIN; INSERT INTO t1 VALUES(3, 4) }
   301    321           sql3 { BEGIN; SELECT * FROM t1 }
   302    322         } {1 2}
   303    323   
          324  +      # The value in ckpt_expected assumes that synchronous=FULL. If
          325  +      # synchronous=NORMAL, decrease the WAL size by 2 frames.
          326  +      if {$tn==1 && [db one {PRAGMA main.synchronous}] == 1} {
          327  +        lset ckpt_expected 1 [expr [lindex $ckpt_expected 1] - 2]
          328  +        lset ckpt_expected 2 [expr [lindex $ckpt_expected 2] - 2]
          329  +      }
          330  +  
   304    331         do_test 2.4.$tn1.$tn.2 {
   305    332           code1 { db busy busyhandler }
   306    333           code1 { do_wal_checkpoint db -mode [string tolower $checkpoint] }
   307    334         } $ckpt_expected
   308    335         do_test 2.4.$tn1.$tn.3 { set ::max_busyhandler } $expected
   309    336       }
   310    337     }

Changes to test/wal_common.tcl.

    28     28     upvar $ckv1 c1
    29     29     upvar $ckv2 c2
    30     30     foreach {v1 v2} $intlist {
    31     31       set c1 [expr {($c1 + $v1 + $c2)&0xFFFFFFFF}]
    32     32       set c2 [expr {($c2 + $v2 + $c1)&0xFFFFFFFF}]
    33     33     }
    34     34   }
           35  +
           36  +# If the synchronous mode for the main database of db handle $db
           37  +# is either OFF or NORMAL, return $nRight. Otherwise, if it is
           38  +# FULL, return $nWrite+$nTrans.
           39  +#
           40  +proc wal_frames {db nWrite nTrans} {
           41  +  set nRet $nWrite
           42  +  switch -- [$db one {PRAGMA main.synchronous}] {
           43  +    0 { }
           44  +    1 { }
           45  +    default { incr nRet $nTrans }
           46  +  }
           47  +  set nRet
           48  +}
    35     49   
    36     50   
    37     51   # This proc calculates checksums in the same way as those used by SQLite 
    38     52   # in WAL files. If the $endian argument is "big", then checksums are
    39     53   # calculated by interpreting data as an array of big-endian integers. If
    40     54   # it is "little", data is interpreted as an array of little-endian integers.
    41     55   #

Changes to test/walmode.test.

    55     55     execsql { PRAGMA page_size = 1024 }
    56     56     execsql { PRAGMA journal_mode = wal }
    57     57   } {wal}
    58     58   do_test walmode-1.2 {
    59     59     file size test.db
    60     60   } {1024}
    61     61   
    62         -set expected_sync_count 3
           62  +# Determine how many sync() calls to expect from the "journal_mode=WAL" 
           63  +# command above. Note that if DEFAULT_WAL_SAFETYLEVEL is defined, the
           64  +# safety-level may have been modified while compiling the "journal_mode=WAL"
           65  +# statement.
           66  +switch -- [db eval {PRAGMA main.synchronous}] {
           67  +  0        { set expected_sync_count 0 }
           68  +  1        { set expected_sync_count 2 }
           69  +  default  { set expected_sync_count 3 }
           70  +}
    63     71   if {$::tcl_platform(platform)!="windows"} {
    64     72     ifcapable dirsync {
    65     73       incr expected_sync_count
    66     74     }
    67     75   }
    68     76   do_test walmode-1.3 {
    69     77     set sqlite_sync_count