SQLite

Check-in [ccc9c211a2]
Login

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

Overview
Comment:Make the same change as (6121) (accidentally reverted). Also enhance test_journal.c to catch this kind of bug. (CVS 6136)
Downloads: Tarball | ZIP archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA1: ccc9c211a285fd4da68b69e15594f080371be522
User & Date: danielk1977 2009-01-07 18:08:49.000
Context
2009-01-07
18:24
Fix a bug in the LIKE query optimization. (Found by coverage testing.) (CVS 6137) (check-in: fe90e9116b user: drh tags: trunk)
18:08
Make the same change as (6121) (accidentally reverted). Also enhance test_journal.c to catch this kind of bug. (CVS 6136) (check-in: ccc9c211a2 user: danielk1977 tags: trunk)
17:06
Add a "synchronous = off" variant to savepoint6.test. (CVS 6135) (check-in: 0f57011e3b user: danielk1977 tags: trunk)
Changes
Unified Diff Ignore Whitespace Patch
Changes to src/pager.c.
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
** The pager is used to access a database disk file.  It implements
** atomic commit and rollback through the use of a journal file that
** is separate from the database file.  The pager also implements file
** locking to prevent two processes from writing the same database
** file simultaneously, or one process from reading the database while
** another is writing.
**
** @(#) $Id: pager.c,v 1.539 2009/01/07 15:33:46 drh Exp $
*/
#ifndef SQLITE_OMIT_DISKIO
#include "sqliteInt.h"

/*
** Macros for troubleshooting.  Normally turned off
*/







|







14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
** The pager is used to access a database disk file.  It implements
** atomic commit and rollback through the use of a journal file that
** is separate from the database file.  The pager also implements file
** locking to prevent two processes from writing the same database
** file simultaneously, or one process from reading the database while
** another is writing.
**
** @(#) $Id: pager.c,v 1.540 2009/01/07 18:08:49 danielk1977 Exp $
*/
#ifndef SQLITE_OMIT_DISKIO
#include "sqliteInt.h"

/*
** Macros for troubleshooting.  Normally turned off
*/
3922
3923
3924
3925
3926
3927
3928
3929
3930
3931
3932
3933
3934
3935
3936
          ** being discarded by the truncation must be written to the journal
          ** file.
          */
          Pgno i;
          Pgno iSkip = PAGER_MJ_PGNO(pPager);
          Pgno dbSize = pPager->dbSize;
          pPager->dbSize = pPager->dbOrigSize;
          for( i=pPager->dbSize+1; i<=pPager->dbOrigSize; i++ ){
            if( !sqlite3BitvecTest(pPager->pInJournal, i) && i!=iSkip ){
              rc = sqlite3PagerGet(pPager, i, &pPg);
              if( rc!=SQLITE_OK ) goto sync_exit;
              rc = sqlite3PagerWrite(pPg);
              sqlite3PagerUnref(pPg);
              if( rc!=SQLITE_OK ) goto sync_exit;
            }







|







3922
3923
3924
3925
3926
3927
3928
3929
3930
3931
3932
3933
3934
3935
3936
          ** being discarded by the truncation must be written to the journal
          ** file.
          */
          Pgno i;
          Pgno iSkip = PAGER_MJ_PGNO(pPager);
          Pgno dbSize = pPager->dbSize;
          pPager->dbSize = pPager->dbOrigSize;
          for( i=dbSize+1; i<=pPager->dbOrigSize; i++ ){
            if( !sqlite3BitvecTest(pPager->pInJournal, i) && i!=iSkip ){
              rc = sqlite3PagerGet(pPager, i, &pPg);
              if( rc!=SQLITE_OK ) goto sync_exit;
              rc = sqlite3PagerWrite(pPg);
              sqlite3PagerUnref(pPg);
              if( rc!=SQLITE_OK ) goto sync_exit;
            }
Changes to src/test_journal.c.
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
** bug in SQLite - writing data to a database file page when:
**
**   a) the original page data is not stored in a synced portion of the
**      journal file, and
**   b) the page was not a free-list leaf page when the transaction was
**      first opened.
**
** $Id: test_journal.c,v 1.6 2009/01/06 17:52:44 danielk1977 Exp $
*/
#if SQLITE_TEST          /* This file is used for testing only */

#include "sqlite3.h"
#include "sqliteInt.h"

/*







|







15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
** bug in SQLite - writing data to a database file page when:
**
**   a) the original page data is not stored in a synced portion of the
**      journal file, and
**   b) the page was not a free-list leaf page when the transaction was
**      first opened.
**
** $Id: test_journal.c,v 1.7 2009/01/07 18:08:49 danielk1977 Exp $
*/
#if SQLITE_TEST          /* This file is used for testing only */

#include "sqlite3.h"
#include "sqliteInt.h"

/*
327
328
329
330
331
332
333







334
335
336
337
338
339
340
*/
static int jtTruncate(sqlite3_file *pFile, sqlite_int64 size){
  jt_file *p = (jt_file *)pFile;
  if( p->flags&SQLITE_OPEN_MAIN_JOURNAL && size==0 ){
    /* Truncating a journal file. This is the end of a transaction. */
    jt_file *pMain = locateDatabaseHandle(p->zName);
    closeTransaction(pMain);







  }
  return sqlite3OsTruncate(p->pReal, size);
}

/*
** The first argument to this function is a handle open on a journal file.
** This function reads the journal file and adds the page number for each







>
>
>
>
>
>
>







327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
*/
static int jtTruncate(sqlite3_file *pFile, sqlite_int64 size){
  jt_file *p = (jt_file *)pFile;
  if( p->flags&SQLITE_OPEN_MAIN_JOURNAL && size==0 ){
    /* Truncating a journal file. This is the end of a transaction. */
    jt_file *pMain = locateDatabaseHandle(p->zName);
    closeTransaction(pMain);
  }
  if( p->flags&SQLITE_OPEN_MAIN_DB && p->pWritable ){
    u32 pgno;
    u32 locking_page = (u32)(PENDING_BYTE/p->nPagesize+1);
    for(pgno=size/p->nPagesize+1; pgno<=p->nPage; pgno++){
      assert( pgno==locking_page || sqlite3BitvecTest(p->pWritable, pgno) );
    }
  }
  return sqlite3OsTruncate(p->pReal, size);
}

/*
** The first argument to this function is a handle open on a journal file.
** This function reads the journal file and adds the page number for each
368
369
370
371
372
373
374

375
376
377
378
379
380
381
      /* A trick. There might be another journal-header immediately 
      ** following this one. In this case, 0 records means 0 records, 
      ** not "read until the end of the file". See also ticket #2565.
      */
      if( iSize>=(iOff+nSector) ){
        rc = sqlite3OsRead(pReal, zBuf, 28, iOff);
        if( rc!=SQLITE_OK || 0==decodeJournalHdr(zBuf, 0, 0, 0, 0) ){

          continue;
        }
      }
      nRec = (iSize-iOff) / (pMain->nPagesize+8);
    }
    for(ii=0; rc==SQLITE_OK && ii<nRec && iOff<iSize; ii++){
      u32 pgno;







>







375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
      /* A trick. There might be another journal-header immediately 
      ** following this one. In this case, 0 records means 0 records, 
      ** not "read until the end of the file". See also ticket #2565.
      */
      if( iSize>=(iOff+nSector) ){
        rc = sqlite3OsRead(pReal, zBuf, 28, iOff);
        if( rc!=SQLITE_OK || 0==decodeJournalHdr(zBuf, 0, 0, 0, 0) ){
assert(rc!=SQLITE_OK);
          continue;
        }
      }
      nRec = (iSize-iOff) / (pMain->nPagesize+8);
    }
    for(ii=0; rc==SQLITE_OK && ii<nRec && iOff<iSize; ii++){
      u32 pgno;