/ Check-in [79f573cc]
Login

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

Overview
Comment:Write the page-size into the first journal-header of each journal file. (CVS 4894)
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA1: 79f573cc7be89b3dd5540c45ef132b5cedc98e9b
User & Date: danielk1977 2008-03-20 04:45:49
Context
2008-03-20
10:44
stick everything that sqlite links against into Libs.private (CVS 4895) check-in: 8b198617 user: vapier tags: trunk
04:45
Write the page-size into the first journal-header of each journal file. (CVS 4894) check-in: 79f573cc user: danielk1977 tags: trunk
02:25
Make out-of-tree builds work as expected when using configure script (CVS 4893) check-in: e2d05ea3 user: mlcreech tags: trunk
Changes
Hide Diffs Side-by-Side Diffs Ignore Whitespace Patch

Changes to src/pager.c.

    14     14   ** The pager is used to access a database disk file.  It implements
    15     15   ** atomic commit and rollback through the use of a journal file that
    16     16   ** is separate from the database file.  The pager also implements file
    17     17   ** locking to prevent two processes from writing the same database
    18     18   ** file simultaneously, or one process from reading the database while
    19     19   ** another is writing.
    20     20   **
    21         -** @(#) $Id: pager.c,v 1.418 2008/03/19 14:15:35 drh Exp $
           21  +** @(#) $Id: pager.c,v 1.419 2008/03/20 04:45:49 danielk1977 Exp $
    22     22   */
    23     23   #ifndef SQLITE_OMIT_DISKIO
    24     24   #include "sqliteInt.h"
    25     25   #include <assert.h>
    26     26   #include <string.h>
    27     27   
    28     28   /*
................................................................................
   967    967   **
   968    968   ** The format for the journal header is as follows:
   969    969   ** - 8 bytes: Magic identifying journal format.
   970    970   ** - 4 bytes: Number of records in journal, or -1 no-sync mode is on.
   971    971   ** - 4 bytes: Random number used for page hash.
   972    972   ** - 4 bytes: Initial database page count.
   973    973   ** - 4 bytes: Sector size used by the process that wrote this journal.
          974  +** - 4 bytes: Database page size.
   974    975   ** 
   975         -** Followed by (JOURNAL_HDR_SZ - 24) bytes of unused space.
          976  +** Followed by (JOURNAL_HDR_SZ - 28) bytes of unused space.
   976    977   */
   977    978   static int writeJournalHdr(Pager *pPager){
   978         -  char zHeader[sizeof(aJournalMagic)+16];
          979  +  char zHeader[sizeof(aJournalMagic)+20];
   979    980     int rc;
   980    981   
   981    982     if( pPager->stmtHdrOff==0 ){
   982    983       pPager->stmtHdrOff = pPager->journalOff;
   983    984     }
   984    985   
   985    986     seekJournalHdr(pPager);
................................................................................
  1019   1020     /* The random check-hash initialiser */ 
  1020   1021     sqlite3_randomness(sizeof(pPager->cksumInit), &pPager->cksumInit);
  1021   1022     put32bits(&zHeader[sizeof(aJournalMagic)+4], pPager->cksumInit);
  1022   1023     /* The initial database size */
  1023   1024     put32bits(&zHeader[sizeof(aJournalMagic)+8], pPager->dbSize);
  1024   1025     /* The assumed sector size for this process */
  1025   1026     put32bits(&zHeader[sizeof(aJournalMagic)+12], pPager->sectorSize);
         1027  +  if( pPager->journalHdr==0 ){
         1028  +    /* The page size */
         1029  +    put32bits(&zHeader[sizeof(aJournalMagic)+16], pPager->pageSize);
         1030  +  }
  1026   1031     IOTRACE(("JHDR %p %lld %d\n", pPager, pPager->journalHdr, sizeof(zHeader)))
  1027   1032     rc = sqlite3OsWrite(pPager->jfd, zHeader, sizeof(zHeader),pPager->journalOff);
  1028   1033     pPager->journalOff += JOURNAL_HDR_SZ(pPager);
  1029   1034   
  1030   1035     /* The journal header has been written successfully. Seek the journal
  1031   1036     ** file descriptor to the end of the journal header sector.
  1032   1037     */
................................................................................
  1058   1063     i64 journalSize,
  1059   1064     u32 *pNRec, 
  1060   1065     u32 *pDbSize
  1061   1066   ){
  1062   1067     int rc;
  1063   1068     unsigned char aMagic[8]; /* A buffer to hold the magic header */
  1064   1069     i64 jrnlOff;
         1070  +  int iPageSize;
  1065   1071   
  1066   1072     seekJournalHdr(pPager);
  1067   1073     if( pPager->journalOff+JOURNAL_HDR_SZ(pPager) > journalSize ){
  1068   1074       return SQLITE_DONE;
  1069   1075     }
  1070   1076     jrnlOff = pPager->journalOff;
  1071   1077   
................................................................................
  1081   1087     if( rc ) return rc;
  1082   1088   
  1083   1089     rc = read32bits(pPager->jfd, jrnlOff+4, &pPager->cksumInit);
  1084   1090     if( rc ) return rc;
  1085   1091   
  1086   1092     rc = read32bits(pPager->jfd, jrnlOff+8, pDbSize);
  1087   1093     if( rc ) return rc;
         1094  +
         1095  +  rc = read32bits(pPager->jfd, jrnlOff+16, (u32 *)&iPageSize);
         1096  +  if( rc==SQLITE_OK 
         1097  +   && iPageSize>=512 
         1098  +   && iPageSize<=SQLITE_MAX_PAGE_SIZE 
         1099  +   && ((iPageSize-1)&iPageSize)==0 
         1100  +  ){
         1101  +    u16 pagesize = iPageSize;
         1102  +    rc = sqlite3PagerSetPagesize(pPager, &pagesize);
         1103  +  }
         1104  +  if( rc ) return rc;
  1088   1105   
  1089   1106     /* Update the assumed sector-size to match the value used by 
  1090   1107     ** the process that created this journal. If this journal was
  1091   1108     ** created by a process other than this one, then this routine
  1092   1109     ** is being called from within pager_playback(). The local value
  1093   1110     ** of Pager.sectorSize is restored at the end of that routine.
  1094   1111     */

Added test/crash6.test.

            1  +# 2001 September 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  +# This file tests that rollback journals for databases that use a 
           12  +# page-size other than the default page-size can be rolled back Ok.
           13  +#
           14  +# $Id: crash6.test,v 1.1 2008/03/20 04:45:49 danielk1977 Exp $
           15  +
           16  +set testdir [file dirname $argv0]
           17  +source $testdir/tester.tcl
           18  +
           19  +ifcapable !crashtest {
           20  +  finish_test
           21  +  return
           22  +}
           23  +
           24  +for {set ii 0} {$ii < 10} {incr ii} {
           25  +  catch {db close}
           26  +  file delete -force test.db test.db-journal
           27  +  crashsql -delay 2 -file test.db {
           28  +    PRAGMA auto_vacuum=OFF;
           29  +    PRAGMA page_size=4096;
           30  +    BEGIN;
           31  +    CREATE TABLE abc AS SELECT 1 AS a, 2 AS b, 3 AS c;
           32  +    COMMIT;
           33  +    BEGIN;
           34  +    CREATE TABLE def AS SELECT 1 AS d, 2 AS e, 3 AS f;
           35  +    COMMIT;
           36  +  }
           37  +  sqlite3 db test.db
           38  +  integrity_check crash6-1.$ii
           39  +}
           40  +
           41  +for {set ii 0} {$ii < 10} {incr ii} {
           42  +  catch {db close}
           43  +  file delete -force test.db test.db-journal
           44  +  sqlite3 db test.db
           45  +  execsql {
           46  +    PRAGMA auto_vacuum=OFF;
           47  +    PRAGMA page_size=2048;
           48  +    BEGIN;
           49  +    CREATE TABLE abc AS SELECT 1 AS a, 2 AS b, 3 AS c;
           50  +    COMMIT;
           51  +  }
           52  +  db close
           53  +  crashsql -delay 1 -file test.db {
           54  +    INSERT INTO abc VALUES(5, 6, 7);
           55  +  }
           56  +  sqlite3 db test.db
           57  +  integrity_check crash6-2.$ii
           58  +}
           59  +
           60  +proc signature {} {
           61  +  return [db eval {SELECT count(*), md5sum(a), md5sum(b), md5sum(c) FROM abc}]
           62  +}
           63  +
           64  +# Test case for crashing during database sync with page-size values 
           65  +# from 1024 to 8192.
           66  +#
           67  +for {set ii 0} {$ii < 30} {incr ii} {
           68  +  db close
           69  +  file delete -force test.db
           70  +  sqlite3 db test.db
           71  +
           72  +  set pagesize [expr 1024 << ($ii % 4)]
           73  +  do_test crash6-3.$ii.0 {
           74  +    execsql "pragma page_size = $pagesize"
           75  +    execsql "pragma page_size"
           76  +  } $pagesize
           77  +
           78  +  do_test crash6-3.$ii.1 {
           79  +  
           80  +    execsql BEGIN
           81  +    execsql {CREATE TABLE abc(a, b, c)}
           82  +    for {set n 0} {$n < 1000} {incr n} {
           83  +      execsql "INSERT INTO abc VALUES($n, [expr 2*$n], [expr 3*$n])"
           84  +    }
           85  +    execsql {
           86  +      INSERT INTO abc SELECT * FROM abc;
           87  +      INSERT INTO abc SELECT * FROM abc;
           88  +      INSERT INTO abc SELECT * FROM abc;
           89  +      INSERT INTO abc SELECT * FROM abc;
           90  +      INSERT INTO abc SELECT * FROM abc;
           91  +    }
           92  +    execsql COMMIT
           93  +    expr ([file size test.db] / 1024) > 450
           94  +  } {1}
           95  +
           96  +  set sig [signature]
           97  +  db close
           98  +
           99  +  do_test crash6-3.$ii.2 {
          100  +     crashsql -file test.db "
          101  +       BEGIN;
          102  +       SELECT random() FROM abc LIMIT $ii;
          103  +       INSERT INTO abc SELECT randstr(10,10), 0, 0 FROM abc WHERE random()%2==0;
          104  +       DELETE FROM abc WHERE random()%2!=0;
          105  +       COMMIT;
          106  +     "
          107  +  } {1 {child process exited abnormally}}
          108  +
          109  +  do_test crash6-3.$ii.3 {
          110  +    sqlite3 db test.db
          111  +    signature
          112  +  } $sig
          113  +} 
          114  +
          115  +finish_test

Changes to test/quick.test.

     2      2   #    May you do good and not evil.
     3      3   #    May you find forgiveness for yourself and forgive others.
     4      4   #    May you share freely, never taking more than you give.
     5      5   #
     6      6   #***********************************************************************
     7      7   # This file runs all tests.
     8      8   #
     9         -# $Id: quick.test,v 1.69 2008/01/16 18:20:42 danielk1977 Exp $
            9  +# $Id: quick.test,v 1.70 2008/03/20 04:45:49 danielk1977 Exp $
    10     10   
    11     11   proc lshift {lvar} {
    12     12     upvar $lvar l
    13     13     set ret [lindex $l 0]
    14     14     set l [lrange $l 1 end]
    15     15     return $ret
    16     16   }
................................................................................
    45     45     btree5.test
    46     46     btree6.test
    47     47     corrupt.test
    48     48     crash.test
    49     49     crash2.test
    50     50     crash3.test
    51     51     crash4.test
           52  +  crash6.test
    52     53     exclusive3.test
    53     54     fts3.test
    54     55     fuzz.test
    55     56     fuzz_malloc.test
    56     57     in2.test
    57     58     loadext.test
    58     59     mallocAll.test