From: dan Date: Tue, 10 Aug 2010 09:58:57 +0000 (+0000) Subject: Add variable pager.dbHintSize, used to limit the number of calls made to the xFileCon... X-Git-Tag: version-3.7.2~53^2~1 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=c864912ad16cc8b86e3b371e35cbd45ff7067008;p=thirdparty%2Fsqlite.git Add variable pager.dbHintSize, used to limit the number of calls made to the xFileControl(FCNTL_SIZE_HINT) method. FossilOrigin-Name: eb3ac895bd92c880ac6acca58de8cf9643c2b5e4 --- diff --git a/manifest b/manifest index 866a7705ba..4ff62443c9 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Modify\ssome\scomments\sin\spager.c. -D 2010-08-09T19:17:29 +C Add\svariable\spager.dbHintSize,\sused\sto\slimit\sthe\snumber\sof\scalls\smade\sto\sthe\sxFileControl(FCNTL_SIZE_HINT)\smethod. +D 2010-08-10T09:58:57 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in ec08dc838fd8110fe24c92e5130bcd91cbb1ff2e F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -156,7 +156,7 @@ F src/os_common.h a8f95b81eca8a1ab8593d23e94f8a35f35d4078f F src/os_os2.c 72d0b2e562952a2464308c4ce5f7913ac10bef3e F src/os_unix.c ae5ca8a6031380708f3fec7be325233d49944914 F src/os_win.c 51cb62f76262d961ea4249489383d714501315a7 -F src/pager.c df8e60594f095c3bd6b74c7c8a2585655b055536 +F src/pager.c 6e8316c94f4ce46480f7f628c3e819d922af2111 F src/pager.h 80726162dc3942f59ab27b738fb667b9ba0a89d5 F src/parse.y 12b7ebd61ea54f0e1b1083ff69cc2c8ce9353d58 F src/pcache.c 1e9aa2dbc0845b52e1b51cc39753b6d1e041cb07 @@ -843,7 +843,7 @@ F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e F tool/vdbe-compress.tcl d70ea6d8a19e3571d7ab8c9b75cba86d1173ff0f -P aecbd890327dc676d6c2366b07f3d2e636a4983e -R f5e40f8996c812e7f2b0312f4a214200 +P 5662da6d4f648e5d07d7cbea6bbd92fa684c02c9 +R 016b700a84062c14051dadc45f2eaff7 U dan -Z 6addb6181e8f60b5f4d1be2660768d4f +Z bdf1c4ed8f87e806444ebc6f32ecd642 diff --git a/manifest.uuid b/manifest.uuid index 2f79639b12..4d160d37cb 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -5662da6d4f648e5d07d7cbea6bbd92fa684c02c9 \ No newline at end of file +eb3ac895bd92c880ac6acca58de8cf9643c2b5e4 \ No newline at end of file diff --git a/src/pager.c b/src/pager.c index 3544032e3d..e2c2f715a3 100644 --- a/src/pager.c +++ b/src/pager.c @@ -565,7 +565,30 @@ struct PagerSavepoint { ** Throughout a write-transaction, dbFileSize contains the size of ** the file on disk in pages. It is set to a copy of dbSize when the ** write-transaction is first opened, and updated when VFS calls are made -** to write or truncate the database file on disk. +** to write or truncate the database file on disk. +** +** The only reason the dbFileSize variable is required is to suppress +** unnecessary calls to xTruncate() after committing a transaction. If, +** when a transaction is committed, the dbFileSize variable indicates +** that the database file is larger than the database image (Pager.dbSize), +** pager_truncate() is called. The pager_truncate() call uses xFilesize() +** to measure the database file on disk, and then truncates it if required. +** dbFileSize is not used when rolling back a transaction. In this case +** pager_truncate() is called unconditionally (which means there may be +** a call to xFilesize() that is not strictly required). In either case, +** pager_truncate() may cause the file to become smaller or larger. +** +** dbHintSize +** +** The dbHintSize variable is used to limit the number of calls made to +** the VFS xFileControl(FCNTL_SIZE_HINT) method. +** +** dbHintSize is set to a copy of the dbSize variable when a +** write-transaction is opened (at the same time as dbFileSize and +** dbOrigSize). If the xFileControl(FCNTL_SIZE_HINT) method is called, +** dbHintSize is increased to the number of pages that correspond to the +** size-hint passed to the method call. See pager_write_pagelist() for +** details. ** ** errCode ** @@ -619,6 +642,7 @@ struct Pager { Pgno dbSize; /* Number of pages in the database */ Pgno dbOrigSize; /* dbSize before the current transaction */ Pgno dbFileSize; /* Number of pages in the database file */ + Pgno dbHintSize; /* Value passed to FCNTL_SIZE_HINT call */ int errCode; /* One of several kinds of errors */ int nRec; /* Pages journalled since last j-header written */ u32 cksumInit; /* Quasi-random value added to every checksum */ @@ -831,6 +855,7 @@ static int assert_pager_state(Pager *p){ } assert( pPager->dbSize==pPager->dbOrigSize ); assert( pPager->dbOrigSize==pPager->dbFileSize ); + assert( pPager->dbOrigSize==pPager->dbHintSize ); assert( pPager->setMaster==0 ); break; @@ -850,6 +875,7 @@ static int assert_pager_state(Pager *p){ ); } assert( pPager->dbOrigSize==pPager->dbFileSize ); + assert( pPager->dbOrigSize==pPager->dbHintSize ); break; case PAGER_WRITER_DBMOD: @@ -861,6 +887,7 @@ static int assert_pager_state(Pager *p){ || p->journalMode==PAGER_JOURNALMODE_OFF || p->journalMode==PAGER_JOURNALMODE_WAL ); + assert( pPager->dbOrigSize<=pPager->dbHintSize ); break; case PAGER_WRITER_FINISHED: @@ -3829,41 +3856,12 @@ static int syncJournal(Pager *pPager, int newHdr){ ** be obtained, SQLITE_BUSY is returned. */ static int pager_write_pagelist(Pager *pPager, PgHdr *pList){ - int rc; /* Return code */ + int rc = SQLITE_OK; /* Return code */ - /* Normally, this function is called in WRITER_DBMOD state. - ** - ** However it may be called in WRITER_CACHEMOD state if the page being - ** written (and all other pages that reside on the same disk sector) was - ** a free-list leaf page at the start of the transaction. In that case - ** the database file is not really being modified, so it is Ok to write - ** to it in CACHEMOD state. - */ + /* This function is only called for rollback pagers in WRITER_DBMOD state. */ assert( !pagerUseWal(pPager) ); - assert( pPager->eState==PAGER_WRITER_DBMOD - || pPager->eState==PAGER_WRITER_CACHEMOD - ); - assert( pPager->eState==PAGER_WRITER_DBMOD - || (pList->pDirty==0 && pList->pgno<=pPager->dbFileSize) - ); - - /* At this point there may be either a RESERVED or EXCLUSIVE lock on the - ** database file. If there is already an EXCLUSIVE lock, the following - ** call is a no-op. - ** - ** Moving the lock from RESERVED to EXCLUSIVE actually involves going - ** through an intermediate state PENDING. A PENDING lock prevents new - ** readers from attaching to the database but is unsufficient for us to - ** write. The idea of a PENDING lock is to prevent new readers from - ** coming in while we wait for existing readers to clear. - ** - ** While the pager is in the RESERVED state, the original database file - ** is unchanged and we can rollback without having to playback the - ** journal into the original database file. Once we transition to - ** EXCLUSIVE, it means the database file has been changed and any rollback - ** will require a journal playback. - */ - rc = pager_wait_on_lock(pPager, EXCLUSIVE_LOCK); + assert( pPager->eState==PAGER_WRITER_DBMOD ); + assert( pPager->eLock==EXCLUSIVE_LOCK ); /* If the file is a temp-file has not yet been opened, open it now. It ** is not possible for rc to be other than SQLITE_OK if this branch @@ -3878,9 +3876,10 @@ static int pager_write_pagelist(Pager *pPager, PgHdr *pList){ ** file size will be. */ assert( rc!=SQLITE_OK || isOpen(pPager->fd) ); - if( rc==SQLITE_OK && pPager->dbSize>pPager->dbOrigSize ){ + if( rc==SQLITE_OK && pPager->dbSize>pPager->dbHintSize ){ sqlite3_int64 szFile = pPager->pageSize * (sqlite3_int64)pPager->dbSize; sqlite3OsFileControl(pPager->fd, SQLITE_FCNTL_SIZE_HINT, &szFile); + pPager->dbHintSize = pPager->dbSize; } while( rc==SQLITE_OK && pList ){ @@ -4062,7 +4061,9 @@ static int pagerStress(void *p, PgHdr *pPg){ }else{ /* Sync the journal file if required. */ - if( pPg->flags&PGHDR_NEED_SYNC ){ + if( pPg->flags&PGHDR_NEED_SYNC + || pPager->eState==PAGER_WRITER_CACHEMOD + ){ rc = syncJournal(pPager, 1); } @@ -5124,7 +5125,9 @@ int sqlite3PagerBegin(Pager *pPager, int exFlag, int subjInMemory){ ** WAL mode. */ pPager->eState = PAGER_WRITER_LOCKED; - pPager->dbFileSize = pPager->dbOrigSize = pPager->dbSize; + pPager->dbHintSize = pPager->dbSize; + pPager->dbFileSize = pPager->dbSize; + pPager->dbOrigSize = pPager->dbSize; pPager->journalOff = 0; }