mirror of
https://github.com/sqlite/sqlite.git
synced 2025-08-08 14:02:16 +03:00
Fix a race condition that can lead to deadlock in the memdb VFS if one
thread is trying to open an existing database at the same moment that another thread that is the only prior user of that database is trying to close it. FossilOrigin-Name: b635375dbe22bd31c437ca574eb0c014c0b045de6cc0816c32d2ceceff9191fb
This commit is contained in:
32
src/memdb.c
32
src/memdb.c
@@ -196,29 +196,33 @@ static void memdbLeave(MemStore *p){
|
||||
*/
|
||||
static int memdbClose(sqlite3_file *pFile){
|
||||
MemStore *p = ((MemFile*)pFile)->pStore;
|
||||
memdbEnter(p);
|
||||
p->nRef--;
|
||||
if( p->nRef<=0 ){
|
||||
if( p->mFlags & SQLITE_DESERIALIZE_FREEONCLOSE ){
|
||||
sqlite3_free(p->aData);
|
||||
}
|
||||
if( p->zFName ){
|
||||
int i;
|
||||
if( p->zFName ){
|
||||
int i;
|
||||
#ifndef SQLITE_MUTEX_OMIT
|
||||
sqlite3_mutex *pVfsMutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1);
|
||||
sqlite3_mutex *pVfsMutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1);
|
||||
#endif
|
||||
sqlite3_mutex_enter(pVfsMutex);
|
||||
for(i=0; ALWAYS(i<memdb_g.nMemStore); i++){
|
||||
if( memdb_g.apMemStore[i]==p ){
|
||||
sqlite3_mutex_enter(pVfsMutex);
|
||||
for(i=0; ALWAYS(i<memdb_g.nMemStore); i++){
|
||||
if( memdb_g.apMemStore[i]==p ){
|
||||
memdbEnter(p);
|
||||
if( p->nRef==1 ){
|
||||
memdb_g.apMemStore[i] = memdb_g.apMemStore[--memdb_g.nMemStore];
|
||||
if( memdb_g.nMemStore==0 ){
|
||||
sqlite3_free(memdb_g.apMemStore);
|
||||
memdb_g.apMemStore = 0;
|
||||
}
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
sqlite3_mutex_leave(pVfsMutex);
|
||||
}
|
||||
sqlite3_mutex_leave(pVfsMutex);
|
||||
}else{
|
||||
memdbEnter(p);
|
||||
}
|
||||
p->nRef--;
|
||||
if( p->nRef<=0 ){
|
||||
if( p->mFlags & SQLITE_DESERIALIZE_FREEONCLOSE ){
|
||||
sqlite3_free(p->aData);
|
||||
}
|
||||
memdbLeave(p);
|
||||
sqlite3_mutex_free(p->pMutex);
|
||||
|
Reference in New Issue
Block a user