aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/btree.c5
-rw-r--r--src/os_unix.c5
-rw-r--r--src/pager.c9
-rw-r--r--src/wal.c3
4 files changed, 16 insertions, 6 deletions
diff --git a/src/btree.c b/src/btree.c
index 064856635..25a9b1b4a 100644
--- a/src/btree.c
+++ b/src/btree.c
@@ -3697,11 +3697,10 @@ static SQLITE_NOINLINE int btreeBeginTrans(
(void)sqlite3PagerWalWriteLock(pPager, 0);
unlockBtreeIfUnused(pBt);
}
-#if defined(SQLITE_ENABLE_SETLK_TIMEOUT) && defined(SQLITE_ENABLE_SNAPSHOT)
+#if defined(SQLITE_ENABLE_SETLK_TIMEOUT)
if( rc==SQLITE_BUSY_TIMEOUT ){
/* If a blocking lock timed out, break out of the loop here so that
- ** the busy-handler is not invoked. This can only happen when opening
- ** a transaction on a snapshot. */
+ ** the busy-handler is not invoked. */
break;
}
#endif
diff --git a/src/os_unix.c b/src/os_unix.c
index 1146545fe..5bbd7ceb6 100644
--- a/src/os_unix.c
+++ b/src/os_unix.c
@@ -5043,13 +5043,14 @@ static int unixShmLock(
** occur later in the above list than the lock being obtained may be
** held.
**
- ** It is not permitted to block on the RECOVER lock.
+ ** It is not permitted to block on the RECOVER lock if any other
+ ** locks are held.
*/
#if defined(SQLITE_ENABLE_SETLK_TIMEOUT) && defined(SQLITE_DEBUG)
{
u16 lockMask = (p->exclMask|p->sharedMask);
assert( (flags & SQLITE_SHM_UNLOCK) || pDbFd->iBusyTimeout==0 || (
- (ofst!=2) /* not RECOVER */
+ (ofst!=2 || lockMask==0) /* not RECOVER */
&& (ofst!=1 || lockMask==0 || lockMask==2)
&& (ofst!=0 || lockMask<3)
&& (ofst<3 || lockMask<(1<<ofst))
diff --git a/src/pager.c b/src/pager.c
index 21f3ac5f6..1850ba37b 100644
--- a/src/pager.c
+++ b/src/pager.c
@@ -700,6 +700,9 @@ struct Pager {
Wal *pWal; /* Write-ahead log used by "journal_mode=wal" */
char *zWal; /* File name for write-ahead log */
#endif
+#ifdef SQLITE_ENABLE_SETLK_TIMEOUT
+ sqlite3 *dbWal;
+#endif
};
/*
@@ -7581,6 +7584,11 @@ static int pagerOpenWal(Pager *pPager){
pPager->fd, pPager->zWal, pPager->exclusiveMode,
pPager->journalSizeLimit, &pPager->pWal
);
+#ifdef SQLITE_ENABLE_SETLK_TIMEOUT
+ if( rc==SQLITE_OK ){
+ sqlite3WalDb(pPager->pWal, pPager->dbWal);
+ }
+#endif
}
pagerFixMaplimit(pPager);
@@ -7700,6 +7708,7 @@ int sqlite3PagerWalWriteLock(Pager *pPager, int bLock){
** blocking locks are required.
*/
void sqlite3PagerWalDb(Pager *pPager, sqlite3 *db){
+ pPager->dbWal = db;
if( pagerUseWal(pPager) ){
sqlite3WalDb(pPager->pWal, db);
}
diff --git a/src/wal.c b/src/wal.c
index 5fe2296d6..fc176988b 100644
--- a/src/wal.c
+++ b/src/wal.c
@@ -3062,7 +3062,6 @@ static int walTryBeginRead(Wal *pWal, int *pChanged, int useWal, int *pCnt){
rc = walIndexReadHdr(pWal, pChanged);
}
#ifdef SQLITE_ENABLE_SETLK_TIMEOUT
- walDisableBlocking(pWal);
if( rc==SQLITE_BUSY_TIMEOUT ){
rc = SQLITE_BUSY;
*pCnt |= WAL_RETRY_BLOCKED_MASK;
@@ -3077,6 +3076,7 @@ static int walTryBeginRead(Wal *pWal, int *pChanged, int useWal, int *pCnt){
** WAL_RETRY this routine will be called again and will probably be
** right on the second iteration.
*/
+ walEnableBlocking(pWal);
if( pWal->apWiData[0]==0 ){
/* This branch is taken when the xShmMap() method returns SQLITE_BUSY.
** We assume this is a transient condition, so return WAL_RETRY. The
@@ -3093,6 +3093,7 @@ static int walTryBeginRead(Wal *pWal, int *pChanged, int useWal, int *pCnt){
rc = SQLITE_BUSY_RECOVERY;
}
}
+ walDisableBlocking(pWal);
if( rc!=SQLITE_OK ){
return rc;
}