1
0
mirror of https://github.com/sqlite/sqlite.git synced 2025-11-15 11:41:13 +03:00

Fix pcache1TruncateUnsafe() run faster for the case where iLimit is

very close to iMaxKey.

FossilOrigin-Name: b07a26df06a2ffb946ff8a1cc7f43eaf701a94b5
This commit is contained in:
drh
2016-08-10 11:50:12 +00:00
parent c83db9e4e1
commit d9fabbcc5b
3 changed files with 35 additions and 14 deletions

View File

@@ -632,12 +632,30 @@ static void pcache1TruncateUnsafe(
PCache1 *pCache, /* The cache to truncate */
unsigned int iLimit /* Drop pages with this pgno or larger */
){
TESTONLY( unsigned int nPage = 0; ) /* To assert pCache->nPage is correct */
unsigned int h;
TESTONLY( int nPage = 0; ) /* To assert pCache->nPage is correct */
unsigned int h, iStop;
assert( sqlite3_mutex_held(pCache->pGroup->mutex) );
for(h=0; h<pCache->nHash; h++){
PgHdr1 **pp = &pCache->apHash[h];
assert( pCache->iMaxKey >= iLimit );
assert( pCache->nHash > 0 );
if( pCache->iMaxKey - iLimit < pCache->nHash/2 ){
/* If we are just shaving the last few pages off the end of the
** cache, then there is no point in scanning the entire hash table.
** Only scan those hash slots that might contain pages that need to
** be removed. */
iStop = iLimit % pCache->nHash;
h = pCache->iMaxKey % pCache->nHash;
TESTONLY( nPage = -10; ) /* Disable the pCache->nPage validity check */
}else{
/* This is the general case where many pages are being removed.
** It is necessary to scan the entire hash table */
iStop = 0;
h = pCache->nHash - 1;
}
for(;;){
PgHdr1 **pp;
PgHdr1 *pPage;
assert( h<pCache->nHash );
pp = &pCache->apHash[h];
while( (pPage = *pp)!=0 ){
if( pPage->iKey>=iLimit ){
pCache->nPage--;
@@ -646,11 +664,13 @@ static void pcache1TruncateUnsafe(
pcache1FreePage(pPage);
}else{
pp = &pPage->pNext;
TESTONLY( nPage++; )
TESTONLY( if( nPage>=0 ) nPage++; )
}
}
if( h==iStop ) break;
h = h ? h-1 : pCache->nHash - 1;
}
assert( pCache->nPage==nPage );
assert( nPage<0 || pCache->nPage==(unsigned)nPage );
}
/******************************************************************************/
@@ -1127,7 +1147,7 @@ static void pcache1Destroy(sqlite3_pcache *p){
PGroup *pGroup = pCache->pGroup;
assert( pCache->bPurgeable || (pCache->nMax==0 && pCache->nMin==0) );
pcache1EnterMutex(pGroup);
pcache1TruncateUnsafe(pCache, 0);
if( pCache->nPage ) pcache1TruncateUnsafe(pCache, 0);
assert( pGroup->nMaxPage >= pCache->nMax );
pGroup->nMaxPage -= pCache->nMax;
assert( pGroup->nMinPage >= pCache->nMin );