diff --git a/manifest b/manifest index 6120e9f28c..da44960d82 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Clean\sup\sthe\slocking\sin\sthe\sbtree\slogic.\s(CVS\s4316) -D 2007-08-28T22:24:35 +C The\sshared_err\stest\sruns\swith\sno\serrors.\s\sBut\sa\spotential\sdeadlock\shas\sbeen\ndiscovered\sand\sis\sstill\sunfixed.\s(CVS\s4317) +D 2007-08-28T23:28:08 F Makefile.in bfcc303429a5d9dcd552d807ee016c77427418c3 F Makefile.linux-gcc 65241babba6faf1152bf86574477baab19190499 F README 9c4e2d6706bdcc3efdd773ce752a8cdab4f90028 @@ -80,9 +80,9 @@ F src/alter.c fd78c6005456c727a6cb7c01c5266f2aacf6d401 F src/analyze.c a14237d869c6bea0846493b59317e4097e81a0b6 F src/attach.c a52225c75b107be8c5bc144a2b6d20201be3f8f8 F src/auth.c 083c1205b45e3f52291ec539d396b4fc557856b3 -F src/btmutex.c 3a19fcb311d0d09e63d397779be881d4273f4518 -F src/btree.c 8796aa42fd16feb587844489a0fce8c66e52ac02 -F src/btree.h a8fb26c56b745b57446c2bf29133619261313051 +F src/btmutex.c fc9d8316fccf491f1011ddc4087338f0ce3b5263 +F src/btree.c 0241f79766d718d524a28857c3899aee7a728194 +F src/btree.h 03895d1da697e616d918856a26ec63ef8f5aa497 F src/btreeInt.h 5b1bc919cb80f0dd6baec1cdbae737f9806a7e3b F src/build.c 99b0b0c44ce7673c00d8c0c97ce536e3b796328b F src/callback.c a542236a68060caad378efa30006ca46cf77b1b2 @@ -162,11 +162,11 @@ F src/update.c e89b980b443d44b68bfc0b1746cdb6308e049ac9 F src/utf.c 4af6259d5906b5a1bf3035cc387c4d7907bdd56e F src/util.c 3f9c0387b54f977726790f52ab92cd3d9379b367 F src/vacuum.c 5ec133b69edf581a232af7e2b01f45c9f2b8be32 -F src/vdbe.c 62d210babaac906a5847d7bd4c71e7b114595e85 +F src/vdbe.c f578e7f0905489ced1f05bc418dd51c0f79f9a04 F src/vdbe.h 498e9ddade4baf70f2fc39e585670131dde07caa -F src/vdbeInt.h a9dcd0688783abbd60981aff7ecc5b57a9559765 +F src/vdbeInt.h 630145b9bfaa19190ab491f52658a7db550f2247 F src/vdbeapi.c bdd0aea216744482dd1b7fab56de18ba5b6fbdf4 -F src/vdbeaux.c 0bbc8fbb6bcd610e98ce8eef77d0db660710f9dd +F src/vdbeaux.c 347d2c1d68f326c90c27660da86849c51134fe1d F src/vdbeblob.c d12ed95dac0992e1e372d079d76af047cc42f7c7 F src/vdbefifo.c 334c838c8f42d61a94813d136019ee566b5dc2f6 F src/vdbemem.c 896fa3f8df9d2661eb15c7ce361857741b447268 @@ -403,7 +403,7 @@ F test/server1.test e328b8e641ba8fe9273132cfef497383185dc1f5 F test/shared.test 08b30d5f1939efff0517e7ff8ec7b74ad31c151b F test/shared2.test 0ee9de8964d70e451936a48c41cb161d9134ccf4 F test/shared3.test 01e3e124dbb3859788aabc7cfb82f7ea04421749 -F test/shared_err.test 99d3d87924cedc1db2233ef59f38c389dd358698 +F test/shared_err.test 494a24f6ba5994d4e4e8fe57ce8c6253e545409a F test/soak.test 64f9b27fbcdec43335a88c546ce1983e6ba40d7b F test/softheap1.test 0c49aa6eee25e7d32943e85e8d1f20eff566b1dc F test/sort.test 0e4456e729e5a92a625907c63dcdedfbe72c5dc5 @@ -567,7 +567,7 @@ F www/tclsqlite.tcl 8be95ee6dba05eabcd27a9d91331c803f2ce2130 F www/vdbe.tcl 87a31ace769f20d3627a64fa1fade7fed47b90d0 F www/version3.tcl 890248cf7b70e60c383b0e84d77d5132b3ead42b F www/whentouse.tcl fc46eae081251c3c181bd79c5faef8195d7991a5 -P 6c617bd89fc57881a2a308a6360e8ebb42835d46 -R 45b11caba5c119849cdae69b051cb491 +P 967ab229af462a8ae663090ea36b4cc10e351653 +R 9c42e7c4d50fc0b5627cd0c4b7aa2569 U drh -Z 8c8847e04e8b6bae7d208c08aa3c66c5 +Z b0b14ea00679504633b7555caa0627b8 diff --git a/manifest.uuid b/manifest.uuid index 849256d4cf..f1c985484c 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -967ab229af462a8ae663090ea36b4cc10e351653 \ No newline at end of file +f84550be0a0c9e5859b852863b9a8f8ed3fd6919 \ No newline at end of file diff --git a/src/btmutex.c b/src/btmutex.c index 3b4d273718..f0f64c5704 100644 --- a/src/btmutex.c +++ b/src/btmutex.c @@ -10,7 +10,7 @@ ** ************************************************************************* ** -** $Id: btmutex.c,v 1.2 2007/08/28 16:44:20 drh Exp $ +** $Id: btmutex.c,v 1.3 2007/08/28 23:28:08 drh Exp $ ** ** This file contains code used to implement mutexes on Btree objects. ** This code really belongs in btree.c. But btree.c is getting too @@ -110,7 +110,7 @@ void sqlite3BtreeLeave(Btree *p){ } /* -** Potentially dd a new Btree pointer to a BtreeMutexSet. +** Potentially dd a new Btree pointer to a BtreeMutexArray. ** Really only add the Btree if it can possibly be shared with ** another database connection. ** @@ -122,7 +122,7 @@ void sqlite3BtreeLeave(Btree *p){ ** The number of shared btrees will always be small (usually 0 or 1) ** so an insertion sort is an adequate algorithm here. */ -void sqlite3BtreeMutexSetInsert(BtreeMutexSet *pSet, Btree *pBtree){ +void sqlite3BtreeMutexArrayInsert(BtreeMutexArray *pSet, Btree *pBtree){ int i, j; BtShared *pBt; if( !pBtree->sharable ) return; @@ -150,11 +150,11 @@ void sqlite3BtreeMutexSetInsert(BtreeMutexSet *pSet, Btree *pBtree){ } /* -** Enter the mutex of every btree in the set. This routine is +** Enter the mutex of every btree in the array. This routine is ** called at the beginning of sqlite3VdbeExec(). The mutexes are ** exited at the end of the same function. */ -void sqlite3BtreeMutexSetEnter(BtreeMutexSet *pSet){ +void sqlite3BtreeMutexArrayEnter(BtreeMutexArray *pSet){ int i; for(i=0; inMutex; i++){ Btree *p = pSet->aBtree[i]; @@ -175,9 +175,9 @@ void sqlite3BtreeMutexSetEnter(BtreeMutexSet *pSet){ } /* -** Leave the mutex of every btree in the set. +** Leave the mutex of every btree in the group. */ -void sqlite3BtreeMutexSetLeave(BtreeMutexSet *pSet){ +void sqlite3BtreeMutexArrayLeave(BtreeMutexArray *pSet){ int i; for(i=0; inMutex; i++){ Btree *p = pSet->aBtree[i]; diff --git a/src/btree.c b/src/btree.c index af8edac35d..800ea0508f 100644 --- a/src/btree.c +++ b/src/btree.c @@ -9,7 +9,7 @@ ** May you share freely, never taking more than you give. ** ************************************************************************* -** $Id: btree.c,v 1.414 2007/08/28 22:24:35 drh Exp $ +** $Id: btree.c,v 1.415 2007/08/28 23:28:08 drh Exp $ ** ** This file implements a external (disk-based) database using BTrees. ** See the header comment on "btreeInt.h" for additional information. @@ -2420,7 +2420,10 @@ int sqlite3BtreeRollback(Btree *p){ while( pBt->pCursor ){ sqlite3 *db = pBt->pCursor->pBtree->pSqlite; if( db ){ + /**** FIX ME: This can deadlock ****/ + sqlite3_mutex_enter(db->mutex); sqlite3AbortOtherActiveVdbes(db, 0); + sqlite3_mutex_leave(db->mutex); } } } diff --git a/src/btree.h b/src/btree.h index 2af90f7713..c21b01074b 100644 --- a/src/btree.h +++ b/src/btree.h @@ -13,7 +13,7 @@ ** subsystem. See comments in the source code for a detailed description ** of what each interface routine does. ** -** @(#) $Id: btree.h,v 1.87 2007/08/28 02:27:52 drh Exp $ +** @(#) $Id: btree.h,v 1.88 2007/08/28 23:28:08 drh Exp $ */ #ifndef _BTREE_H_ #define _BTREE_H_ @@ -41,7 +41,7 @@ typedef struct Btree Btree; typedef struct BtCursor BtCursor; typedef struct BtShared BtShared; -typedef struct BtreeMutexSet BtreeMutexSet; +typedef struct BtreeMutexArray BtreeMutexArray; /* ** This structure records all of the Btrees that need to hold @@ -49,7 +49,7 @@ typedef struct BtreeMutexSet BtreeMutexSet; ** are placed in aBtree[] in order of aBtree[]->pBt. That way, ** we can always lock and unlock them all quickly. */ -struct BtreeMutexSet { +struct BtreeMutexArray { int nMutex; Btree *aBtree[SQLITE_MAX_ATTACHED+1]; }; @@ -183,13 +183,13 @@ int sqlite3BtreePageDump(Btree*, int, int recursive); #endif #if !defined(SQLITE_OMIT_SHARED_CACHE) && SQLITE_THREADSAFE - void sqlite3BtreeMutexSetEnter(BtreeMutexSet*); - void sqlite3BtreeMutexSetLeave(BtreeMutexSet*); - void sqlite3BtreeMutexSetInsert(BtreeMutexSet*, Btree*); + void sqlite3BtreeMutexArrayEnter(BtreeMutexArray*); + void sqlite3BtreeMutexArrayLeave(BtreeMutexArray*); + void sqlite3BtreeMutexArrayInsert(BtreeMutexArray*, Btree*); #else -# define sqlite3BtreeMutexSetEnter(X) -# define sqlite3BtreeMutexSetLeave(X) -# define sqlite3BtreeMutexSetInsert(X,Y) +# define sqlite3BtreeMutexArrayEnter(X) +# define sqlite3BtreeMutexArrayLeave(X) +# define sqlite3BtreeMutexArrayInsert(X,Y) #endif diff --git a/src/vdbe.c b/src/vdbe.c index 4519fc032b..9f9e240447 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -43,7 +43,7 @@ ** in this file for details. If in doubt, do not deviate from existing ** commenting and indentation practices when changing or adding code. ** -** $Id: vdbe.c,v 1.645 2007/08/28 02:27:52 drh Exp $ +** $Id: vdbe.c,v 1.646 2007/08/28 23:28:08 drh Exp $ */ #include "sqliteInt.h" #include @@ -465,7 +465,7 @@ int sqlite3VdbeExec( if( p->magic!=VDBE_MAGIC_RUN ) return SQLITE_MISUSE; assert( db->magic==SQLITE_MAGIC_BUSY ); pTos = p->pTos; - sqlite3BtreeMutexSetEnter(&p->mtxSet); + sqlite3BtreeMutexArrayEnter(&p->aMutex); if( p->rc==SQLITE_NOMEM ){ /* This happens if a malloc() inside a call to sqlite3_column_text() or ** sqlite3_column_text16() failed. */ @@ -5202,7 +5202,7 @@ vdbe_halt: ** release the mutexes on btrees that were acquired at the ** top. */ vdbe_return: - sqlite3BtreeMutexSetLeave(&p->mtxSet); + sqlite3BtreeMutexArrayLeave(&p->aMutex); return rc; /* Jump to here if a string or blob larger than SQLITE_MAX_LENGTH diff --git a/src/vdbeInt.h b/src/vdbeInt.h index dc1b4b00d9..a807bdda33 100644 --- a/src/vdbeInt.h +++ b/src/vdbeInt.h @@ -333,7 +333,7 @@ struct Vdbe { int nChange; /* Number of db changes made since last reset */ i64 startTime; /* Time when query started - used for profiling */ int btreeMask; /* Bitmask of db->aDb[] entries referenced */ - BtreeMutexSet mtxSet; /* Set of Btree mutexes */ + BtreeMutexArray aMutex; /* An array of Btree used here and needing locks */ int nSql; /* Number of bytes in zSql */ char *zSql; /* Text of the SQL statement that generated this */ #ifdef SQLITE_DEBUG diff --git a/src/vdbeaux.c b/src/vdbeaux.c index 53a43255e9..5b58588a69 100644 --- a/src/vdbeaux.c +++ b/src/vdbeaux.c @@ -667,7 +667,7 @@ void sqlite3VdbeUsesBtree(Vdbe *p, int i, Btree *pBtree){ assert( ibtreeMask)*8 ); assert( p->db->aDb[i].pBt==pBtree ); p->btreeMask |= 1<mtxSet, pBtree); + sqlite3BtreeMutexArrayInsert(&p->aMutex, pBtree); } @@ -1331,7 +1331,7 @@ void sqlite3AbortOtherActiveVdbes(sqlite3 *db, Vdbe *pExcept){ ** lock contention, return SQLITE_BUSY. If SQLITE_BUSY is returned, it ** means the close did not happen and needs to be repeated. */ -int sqlite3VdbeHalt(Vdbe *p){ +static int sqlite3VdbeHaltLocked(Vdbe *p){ sqlite3 *db = p->db; int i; int (*xFunc)(Btree *pBt) = 0; /* Function to call on each btree backend */ @@ -1533,6 +1533,14 @@ int sqlite3VdbeHalt(Vdbe *p){ return SQLITE_OK; } +int sqlite3VdbeHalt(Vdbe *p){ + int rc; + sqlite3BtreeMutexArrayEnter(&p->aMutex); + rc = sqlite3VdbeHaltLocked(p); + sqlite3BtreeMutexArrayLeave(&p->aMutex); + return rc; +} + /* ** Each VDBE holds the result of the most recent sqlite3_step() call diff --git a/test/shared_err.test b/test/shared_err.test index 11cef5a4c5..0496cd37d5 100644 --- a/test/shared_err.test +++ b/test/shared_err.test @@ -13,7 +13,7 @@ # cache context. What happens to connection B if one connection A encounters # an IO-error whilst reading or writing the file-system? # -# $Id: shared_err.test,v 1.13 2007/08/28 22:24:35 drh Exp $ +# $Id: shared_err.test,v 1.14 2007/08/28 23:28:09 drh Exp $ proc skip {args} {} @@ -156,7 +156,6 @@ do_ioerr_test shared_ioerr-3 -tclprep { sqlite3_step $::STMT ;# Cursor points at 001.001.001.001 } -tclbody { -btree_breakpoint execsql { BEGIN; INSERT INTO t1 VALUES('201.201.201.201.201', NULL);