Index: src/sqlite.h.in ================================================================== --- src/sqlite.h.in +++ src/sqlite.h.in @@ -506,11 +506,10 @@ #define SQLITE_BUSY_SNAPSHOT (SQLITE_BUSY | (2<<8)) #define SQLITE_CANTOPEN_NOTEMPDIR (SQLITE_CANTOPEN | (1<<8)) #define SQLITE_CANTOPEN_ISDIR (SQLITE_CANTOPEN | (2<<8)) #define SQLITE_CANTOPEN_FULLPATH (SQLITE_CANTOPEN | (3<<8)) #define SQLITE_CANTOPEN_CONVPATH (SQLITE_CANTOPEN | (4<<8)) -#define SQLITE_CANTOPEN_DIRTYWAL (SQLITE_CANTOPEN | (5<<8)) #define SQLITE_CORRUPT_VTAB (SQLITE_CORRUPT | (1<<8)) #define SQLITE_READONLY_RECOVERY (SQLITE_READONLY | (1<<8)) #define SQLITE_READONLY_CANTLOCK (SQLITE_READONLY | (2<<8)) #define SQLITE_READONLY_ROLLBACK (SQLITE_READONLY | (3<<8)) #define SQLITE_READONLY_DBMOVED (SQLITE_READONLY | (4<<8)) @@ -1059,10 +1058,24 @@ ** [SQLITE_FCNTL_BEGIN_ATOMIC_WRITE] to be rolled back. ** ^This file control takes the file descriptor out of batch write mode ** so that all subsequent write operations are independent. ** ^SQLite will never invoke SQLITE_FCNTL_ROLLBACK_ATOMIC_WRITE without ** a prior successful call to [SQLITE_FCNTL_BEGIN_ATOMIC_WRITE]. +** +**
)^ +** Before returning, this operation allocates a buffer large enough for +** the entire shared-memory using sqlite3_malloc() and populates it with +** a copy thereof. ReadShmArg.pBuf is set to point to the buffer, and +** ReadShmArg to its size in bytes. It is the responsibility of the caller +** to eventually free the buffer using sqlite3_free(). ** */ #define SQLITE_FCNTL_LOCKSTATE 1 #define SQLITE_FCNTL_GET_LOCKPROXYFILE 2 #define SQLITE_FCNTL_SET_LOCKPROXYFILE 3 Index: src/wal.c ================================================================== --- src/wal.c +++ src/wal.c @@ -2343,11 +2343,12 @@ if( !useWal ){ rc = walIndexReadHdr(pWal, pChanged); if( rc==SQLITE_READONLY_CANTLOCK ){ /* This is a readonly_shm connection and there are no other connections ** to the database. So the *-shm file may not be accessed using mmap. - ** Take WAL_READ_LOCK(0) before proceding. */ + ** Try to open an "unlocked" transaction - one that loads the *-shm + ** file into memory using read() - instead. */ assert( pWal->nWiData>0 && pWal->apWiData[0]==0 ); assert( pWal->readOnly & WAL_SHM_RDONLY ); return walBeginUnlocked(pWal, pChanged); } if( rc==SQLITE_BUSY ){+** struct ReadShmArg { void *pBuf; int nBuf }; +**