]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
Fix a race condition in OP_ParseSchema.
authordan <dan@noemail.net>
Sat, 2 Apr 2011 09:44:43 +0000 (09:44 +0000)
committerdan <dan@noemail.net>
Sat, 2 Apr 2011 09:44:43 +0000 (09:44 +0000)
FossilOrigin-Name: 71a799b02a3b3cf2e12758dea29fd2465bbec3e1

manifest
manifest.uuid
src/vdbe.c

index 04c1085d8012621cefa440e78f6191d866098864..8411b2239fcc8f8ca08825ba0b11abac8ff2ca49 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Do\snot\sattempt\sto\srun\stests\sthat\suse\sthe\s'wholenumber'\svirtual\stable\sif\sthe\sbuild\sdoes\snot\ssupport\svirtual\stables.
-D 2011-04-02T09:25:14.909
+C Fix\sa\srace\scondition\sin\sOP_ParseSchema.
+D 2011-04-02T09:44:43
 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f
 F Makefile.in 7a4d9524721d40ef9ee26f93f9bd6a51dba106f2
 F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23
@@ -235,7 +235,7 @@ F src/update.c 81911be16ece3c3e7716aa18565b4814ec41f8b9
 F src/utf.c d83650c3ea08f7407bd9d0839d9885241c209c60
 F src/util.c cd997077bad039efc0597eb027c929658f93c018
 F src/vacuum.c 924bd1bcee2dfb05376f79845bd3b4cec7b54b2f
-F src/vdbe.c e3f37ca0afdd72e883475e2a32a06167df2810d0
+F src/vdbe.c a45a6a0daf2161797d50b3b5b8a3e0e4debf2d2b
 F src/vdbe.h 4de0efb4b0fdaaa900cf419b35c458933ef1c6d2
 F src/vdbeInt.h e1c6254641168507d25b46affb6dfb53c782f553
 F src/vdbeapi.c a09ad9164cafc505250d5dd6b69660c960f1308c
@@ -926,7 +926,7 @@ F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224
 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e
 F tool/split-sqlite3c.tcl d9be87f1c340285a3e081eb19b4a247981ed290c
 F tool/vdbe-compress.tcl d70ea6d8a19e3571d7ab8c9b75cba86d1173ff0f
-P 139bc5655ed1d0fd1b7ca86d05a998fcc5fbc18e
-R 85c1ab3db7c73393d878faa825bb79d8
+P 20afd81a4cf4d23962ec841bbd375f36a5156fb6
+R 25d34b3e2efbdd1c8e0ceadec6512306
 U dan
-Z 27401d3cc561174a4c3aaa99ccf5b680
+Z 659aea6fa897bf521b0a686e5d197299
index 201bc67d246bd8f232dfad5bd96a3b8e2629752b..fa61c3c6519bcfb23e049cbd1e585ef4ce128a37 100644 (file)
@@ -1 +1 @@
-20afd81a4cf4d23962ec841bbd375f36a5156fb6
\ No newline at end of file
+71a799b02a3b3cf2e12758dea29fd2465bbec3e1
\ No newline at end of file
index 43d132f1bad87a498147e0ffa1443d2620e884c0..ddf507ee9da2458c8bd0b6511ef8d7545cbd2d87 100644 (file)
@@ -4625,23 +4625,26 @@ case OP_ParseSchema: {
   iDb = pOp->p1;
   assert( iDb>=0 && iDb<db->nDb );
 
-  /* Although the mutex on the BtShared object that corresponds to
-  ** database iDb (the database containing the sqlite_master table
-  ** read by this instruction) is currently held, it is necessary to
-  ** obtain the mutexes on all attached databases before checking if
-  ** the schema of iDb is loaded. This is because, at the start of
-  ** the sqlite3_exec() call below, SQLite will invoke 
-  ** sqlite3BtreeEnterAll(). If all mutexes are not already held, the
-  ** iDb mutex may be temporarily released to avoid deadlock. If 
-  ** this happens, then some other thread may delete the in-memory 
-  ** schema of database iDb before the SQL statement runs. The schema
-  ** will not be reloaded becuase the db->init.busy flag is set. This
-  ** can result in a "no such table: sqlite_master" or "malformed
-  ** database schema" error being returned to the user.
+  /* When this opcode is invoked, it is guaranteed that the b-tree mutex
+  ** is held and the schema is loaded for database iDb. However, at the 
+  ** start of the sqlite3_exec() call below, SQLite will invoke 
+  ** sqlite3BtreeEnterAll(). If all mutexes are not already held, the iDb 
+  ** mutex may be temporarily released to avoid deadlock. If this happens, 
+  ** then some other thread may delete the in-memory schema of database iDb 
+  ** before the SQL statement runs. The schema will not be reloaded because 
+  ** the db->init.busy flag is set. This can result in a "no such table: 
+  ** sqlite_master" or "malformed database schema" error being returned to 
+  ** the user. 
+  **
+  ** To avoid this, obtain all mutexes and check that no other thread has
+  ** deleted the schema before calling sqlite3_exec(). If we find that the
+  ** another thread has deleted the schema, there is no need to update it.
+  ** The updated schema will be loaded from disk when it is next required.
   */
   assert( sqlite3BtreeHoldsMutex(db->aDb[iDb].pBt) );
+  assert( DbHasProperty(db, iDb, DB_SchemaLoaded) );
   sqlite3BtreeEnterAll(db);
-  if( ALWAYS(DbHasProperty(db, iDb, DB_SchemaLoaded)) ){
+  if( DbHasProperty(db, iDb, DB_SchemaLoaded) ){
     zMaster = SCHEMA_TABLE(iDb);
     initData.db = db;
     initData.iDb = pOp->p1;