mirror of
https://github.com/sqlite/sqlite.git
synced 2025-08-08 14:02:16 +03:00
Combine subjRequiresPage() and subjournalPage() into a single
subjournalPageIfRequired() routine. FossilOrigin-Name: 3b65eb56c422855ca47f709247205f0c77d98a5c
This commit is contained in:
55
src/pager.c
55
src/pager.c
@@ -4320,8 +4320,6 @@ static int openSubJournal(Pager *pPager){
|
||||
|
||||
/*
|
||||
** Append a record of the current state of page pPg to the sub-journal.
|
||||
** It is the callers responsibility to use subjRequiresPage() to check
|
||||
** that it is really required before calling this function.
|
||||
**
|
||||
** If successful, set the bit corresponding to pPg->pgno in the bitvecs
|
||||
** for all open savepoints before returning.
|
||||
@@ -4368,6 +4366,13 @@ static int subjournalPage(PgHdr *pPg){
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
static int subjournalPageIfRequired(PgHdr *pPg){
|
||||
if( subjRequiresPage(pPg) ){
|
||||
return subjournalPage(pPg);
|
||||
}else{
|
||||
return SQLITE_OK;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
** This function is called by the pcache layer when it has reached some
|
||||
@@ -4425,9 +4430,7 @@ static int pagerStress(void *p, PgHdr *pPg){
|
||||
pPg->pDirty = 0;
|
||||
if( pagerUseWal(pPager) ){
|
||||
/* Write a single frame for this page to the log. */
|
||||
if( subjRequiresPage(pPg) ){
|
||||
rc = subjournalPage(pPg);
|
||||
}
|
||||
rc = subjournalPageIfRequired(pPg);
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = pagerWalFrames(pPager, pPg, 0, 0);
|
||||
}
|
||||
@@ -4440,39 +4443,6 @@ static int pagerStress(void *p, PgHdr *pPg){
|
||||
rc = syncJournal(pPager, 1);
|
||||
}
|
||||
|
||||
/* If the page number of this page is larger than the current size of
|
||||
** the database image, it may need to be written to the sub-journal.
|
||||
** This is because the call to pager_write_pagelist() below will not
|
||||
** actually write data to the file in this case.
|
||||
**
|
||||
** Consider the following sequence of events:
|
||||
**
|
||||
** BEGIN;
|
||||
** <journal page X>
|
||||
** <modify page X>
|
||||
** SAVEPOINT sp;
|
||||
** <shrink database file to Y pages>
|
||||
** pagerStress(page X)
|
||||
** ROLLBACK TO sp;
|
||||
**
|
||||
** If (X>Y), then when pagerStress is called page X will not be written
|
||||
** out to the database file, but will be dropped from the cache. Then,
|
||||
** following the "ROLLBACK TO sp" statement, reading page X will read
|
||||
** data from the database file. This will be the copy of page X as it
|
||||
** was when the transaction started, not as it was when "SAVEPOINT sp"
|
||||
** was executed.
|
||||
**
|
||||
** The solution is to write the current data for page X into the
|
||||
** sub-journal file now (if it is not already there), so that it will
|
||||
** be restored to its current value when the "ROLLBACK TO sp" is
|
||||
** executed.
|
||||
*/
|
||||
if( NEVER(
|
||||
rc==SQLITE_OK && pPg->pgno>pPager->dbSize && subjRequiresPage(pPg)
|
||||
) ){
|
||||
rc = subjournalPage(pPg);
|
||||
}
|
||||
|
||||
/* Write the contents of the page out to the database file. */
|
||||
if( rc==SQLITE_OK ){
|
||||
assert( (pPg->flags&PGHDR_NEED_SYNC)==0 );
|
||||
@@ -5781,8 +5751,8 @@ static int pager_write(PgHdr *pPg){
|
||||
/* If the statement journal is open and the page is not in it,
|
||||
** then write the page into the statement journal.
|
||||
*/
|
||||
if( pPager->nSavepoint>0 && subjRequiresPage(pPg) ){
|
||||
rc = subjournalPage(pPg);
|
||||
if( pPager->nSavepoint>0 ){
|
||||
rc = subjournalPageIfRequired(pPg);
|
||||
}
|
||||
|
||||
/* Update the database size and return. */
|
||||
@@ -6772,9 +6742,8 @@ int sqlite3PagerMovepage(Pager *pPager, DbPage *pPg, Pgno pgno, int isCommit){
|
||||
** one or more savepoint bitvecs. This is the reason this function
|
||||
** may return SQLITE_NOMEM.
|
||||
*/
|
||||
if( pPg->flags&PGHDR_DIRTY
|
||||
&& subjRequiresPage(pPg)
|
||||
&& SQLITE_OK!=(rc = subjournalPage(pPg))
|
||||
if( (pPg->flags & PGHDR_DIRTY)!=0
|
||||
&& SQLITE_OK!=(rc = subjournalPageIfRequired(pPg))
|
||||
){
|
||||
return rc;
|
||||
}
|
||||
|
Reference in New Issue
Block a user