diff options
author | dan <dan@noemail.net> | 2010-07-13 18:44:03 +0000 |
---|---|---|
committer | dan <dan@noemail.net> | 2010-07-13 18:44:03 +0000 |
commit | da9fe0c327ae952c3e16587e069a878888b3c089 (patch) | |
tree | 51672674ac3f9f56756916f34f48d0bc4663c624 | |
parent | 2103245e75a2b3c9eb76af75700f800d718a66a7 (diff) | |
download | sqlite-da9fe0c327ae952c3e16587e069a878888b3c089.tar.gz sqlite-da9fe0c327ae952c3e16587e069a878888b3c089.zip |
Changes so that the xShmOpen VFS method is no longer required. Its job can be done by the first call to xShmMap. Rename xShmClose to xShmUnmap.
FossilOrigin-Name: f4780bde62c6c19146d2723c101540b8db898d38
-rw-r--r-- | manifest | 46 | ||||
-rw-r--r-- | manifest.uuid | 2 | ||||
-rw-r--r-- | src/os.c | 17 | ||||
-rw-r--r-- | src/os.h | 3 | ||||
-rw-r--r-- | src/os_unix.c | 280 | ||||
-rw-r--r-- | src/os_win.c | 63 | ||||
-rw-r--r-- | src/pager.c | 2 | ||||
-rw-r--r-- | src/sqlite.h.in | 2 | ||||
-rw-r--r-- | src/test6.c | 6 | ||||
-rw-r--r-- | src/test_devsym.c | 8 | ||||
-rw-r--r-- | src/test_onefile.c | 6 | ||||
-rw-r--r-- | src/test_osinst.c | 30 | ||||
-rw-r--r-- | src/test_vfs.c | 26 | ||||
-rw-r--r-- | src/wal.c | 20 |
14 files changed, 233 insertions, 278 deletions
@@ -1,8 +1,5 @@ ------BEGIN PGP SIGNED MESSAGE----- -Hash: SHA1 - -C Improved\sdocumentation\sfor\sthe\sSQLITE_ACCESS_*\sconstants\sthat\sare\sused\nwith\sthe\sxAccess()\smethod\sof\sthe\sVFS. -D 2010-07-13T14:48:27 +C Changes\sso\sthat\sthe\sxShmOpen\sVFS\smethod\sis\sno\slonger\srequired.\sIts\sjob\scan\sbe\sdone\sby\sthe\sfirst\scall\sto\sxShmMap.\sRename\sxShmClose\sto\sxShmUnmap. +D 2010-07-13T18:44:04 F Makefile.arm-wince-mingw32ce-gcc fcd5e9cd67fe88836360bb4f9ef4cb7f8e2fb5a0 F Makefile.in ec08dc838fd8110fe24c92e5130bcd91cbb1ff2e F Makefile.linux-gcc d53183f4aa6a9192d249731c90dbdffbd2c68654 @@ -153,13 +150,13 @@ F src/mutex_os2.c 6a62583e374ba3ac1a3fcc0da2bfdac7d3942689 F src/mutex_unix.c cf84466b4fdd2baa0d5a10bb19f08b2abc1ce42e F src/mutex_w32.c 1fe0e735897be20e09dd6f53c3fb516c6b48c0eb F src/notify.c cbfa66a836da3a51567209636e6a94059c137930 -F src/os.c c34882169b2f8ee0942c4f6aff9ee705e6110cdf -F src/os.h d7775504a51e6e0d40315aa427b3e229ff9ff9ca +F src/os.c a45484100b8e86718eb117d92feae082ac2530f8 +F src/os.h 93cb145b93bd971055cf4d55ac44eaaa51e148fc F src/os_common.h a8f95b81eca8a1ab8593d23e94f8a35f35d4078f F src/os_os2.c 665876d5eec7585226b0a1cf5e18098de2b2da19 -F src/os_unix.c c6112f0ae34f23ae5ca0189a685e084befbdcf26 -F src/os_win.c 04c8828e4c5c2e7d5abcb9ce170ae6bfb02aa98d -F src/pager.c 1d42e2cdaa9b1765f7df8e350509318917cd651d +F src/os_unix.c abefe4129fe19f03232ecdbcf67f7cfa1d58e2a2 +F src/os_win.c 3bb7e081045aa4c811197ead66febdf8d6209275 +F src/pager.c 78ca1e1f3315c8227431c403c04d791dccf242fb F src/pager.h 879fdde5a102d2f21a3135d6f647530b21c2796c F src/parse.y ace5c7a125d9f2a410e431ee3209034105045f7e F src/pcache.c 1e9aa2dbc0845b52e1b51cc39753b6d1e041cb07 @@ -173,7 +170,7 @@ F src/resolve.c 1c0f32b64f8e3f555fe1f732f9d6f501a7f05706 F src/rowset.c 69afa95a97c524ba6faf3805e717b5b7ae85a697 F src/select.c 4903ff1bbd08b55cbce00ea43c645530de41b362 F src/shell.c fd4ccdb37c3b68de0623eb938a649e0990710714 -F src/sqlite.h.in abe351b1a4c32b140b2db0a68224e85690ea5e60 +F src/sqlite.h.in b82b926ef9c10ca12373c2ecc8bbd2f5a9aad1dc F src/sqlite3ext.h 69dfb8116af51b84a029cddb3b35062354270c89 F src/sqliteInt.h 8eb5d1c63fff70ed30f4b861aeaf8485e663129c F src/sqliteLimit.h 196e2f83c3b444c4548fc1874f52f84fdbda40f3 @@ -185,7 +182,7 @@ F src/test2.c e3f564ab1e9fd0b47b0c9e23e7054e38bf0836cf F src/test3.c 4c21700c73a890a47fc685c1097bfb661346ac94 F src/test4.c ad03bb987ddedce928f4258c1e7fa4109a73497d F src/test5.c cc55900118fa4add8ec9cf69fc4225a4662f76b1 -F src/test6.c a1217a210fd6e2bcd11ddff4ad2484ec65998043 +F src/test6.c e328b5047ef9b7a8c2d64617625855ae38639708 F src/test7.c 3f2d63e4ccf97f8c2cf1a7fa0a3c8e2e2a354e6e F src/test8.c f959db9a22d882013b64c92753fa793b2ce3bdea F src/test9.c bea1e8cf52aa93695487badedd6e1886c321ea60 @@ -195,7 +192,7 @@ F src/test_backup.c c129c91127e9b46e335715ae2e75756e25ba27de F src/test_btree.c 47cd771250f09cdc6e12dda5bc71bc0b3abc96e2 F src/test_config.c 5a11c51af2156e2d07186930b36f2b8239a4393f F src/test_demovfs.c da81a5f7785bb352bda7911c332a983ec4f17f27 -F src/test_devsym.c 5a99203fb7ff43047d7e493d1b159585983d4ea6 +F src/test_devsym.c 85286d641bda3f9ecd0e34fcc0b884de198a83b5 F src/test_func.c 13b582345fb1185a93e46c53310fae8547dcce20 F src/test_hexio.c 1237f000ec7a491009b1233f5c626ea71bce1ea2 F src/test_init.c 5d624ffd0409d424cf9adbfe1f056b200270077c @@ -205,15 +202,15 @@ F src/test_journal.c 424a334cdfdc8a6f975abe3641440147bded3185 F src/test_loadext.c df586c27176e3c2cb2e099c78da67bf14379a56e F src/test_malloc.c 4ab85f2b8ae3a237f4e6557b0a641181a19ffab1 F src/test_mutex.c ce06b59aca168cd8c520b77159a24352a7469bd3 -F src/test_onefile.c 701553cecc466c13fbebdb27cc7022839512f7bd -F src/test_osinst.c 700a39f4b7d3959fb65b1a97a5503a9b6d952c6b +F src/test_onefile.c 01e7a0b0cf27cc974de3b2f825eca5a22185437a +F src/test_osinst.c f408c6a181f2fb04c56273afd5c3e1e82f60392c F src/test_pcache.c 7bf828972ac0d2403f5cfa4cd14da41f8ebe73d8 F src/test_schema.c 8c06ef9ddb240c7a0fcd31bc221a6a2aade58bf0 F src/test_server.c bbba05c144b5fc4b52ff650a4328027b3fa5fcc6 F src/test_stat.c 6ebaf2a86d01ccda24e49c148f1d33e8badda06e F src/test_tclvar.c f4dc67d5f780707210d6bb0eb6016a431c04c7fa F src/test_thread.c bedd05cad673dba53326f3aa468cc803038896c0 -F src/test_vfs.c bea0f0bdee9b033a62d057bf3451c25760b0414d +F src/test_vfs.c 7e291f85256516ebde6633bc381ff7eedfa30234 F src/test_wsd.c 41cadfd9d97fe8e3e4e44f61a4a8ccd6f7ca8fe9 F src/tokenize.c 25ceb0f0a746ea1d0f9553787f3f0a56853cfaeb F src/trigger.c 67e95c76d625b92d43409ace771c8e0d02a09ac2 @@ -230,7 +227,7 @@ F src/vdbeblob.c 258a6010ba7a82b72b327fb24c55790655689256 F src/vdbemem.c 5e579abf6532001dfbee0e640dc34eae897a9807 F src/vdbetrace.c 864cef96919323482ebd9986f2132435115e9cc2 F src/vtab.c a0f8a40274e4261696ef57aa806de2776ab72cda -F src/wal.c c1783e405f0ac19923fd1743ff7a3b29cb27709c +F src/wal.c 1a63156c661ff22c4c5fc2e6e3ee054017ea8493 F src/wal.h 906c85760598b18584921fe08008435aa4eeeeb2 F src/walker.c 3112bb3afe1d85dc52317cb1d752055e9a781f8f F src/where.c 926c83c6394e132a1c62b6b12ceeba7d55a34c19 @@ -837,14 +834,7 @@ F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e F tool/vdbe-compress.tcl d70ea6d8a19e3571d7ab8c9b75cba86d1173ff0f -P 52577bb5e723d8de4fc609286666b581f8d9c746 -R c858da9982d7ccbc52ee004b587c3119 -U drh -Z 9b0064c7115f9f6527e0f36107e7bcea ------BEGIN PGP SIGNATURE----- -Version: GnuPG v1.4.6 (GNU/Linux) - -iD8DBQFMPHy+oxKgR168RlERAi4kAJwIB0nNqDnT2kidWrwZhTF/FIEmHgCfZcxg -GY3yVCZFLW50/Dz5D0SGQsc= -=vRcP ------END PGP SIGNATURE----- +P 3d4bb65f10ed0297f38e732ce57e5440cba8deef +R dddad50687797f0e228c401381867528 +U dan +Z 1a8aae2f2d97f7f97b0d409af0e6f96f diff --git a/manifest.uuid b/manifest.uuid index 9dff117cb..0af99ad77 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -3d4bb65f10ed0297f38e732ce57e5440cba8deef
\ No newline at end of file +f4780bde62c6c19146d2723c101540b8db898d38
\ No newline at end of file @@ -100,9 +100,6 @@ int sqlite3OsSectorSize(sqlite3_file *id){ int sqlite3OsDeviceCharacteristics(sqlite3_file *id){ return id->pMethods->xDeviceCharacteristics(id); } -int sqlite3OsShmOpen(sqlite3_file *id){ - return id->pMethods->xShmOpen(id); -} int sqlite3OsShmLock(sqlite3_file *id, int offset, int n, int flags){ return id->pMethods->xShmLock(id, offset, n, flags); } @@ -110,16 +107,16 @@ void sqlite3OsShmBarrier(sqlite3_file *id){ id->pMethods->xShmBarrier(id); } int sqlite3OsShmClose(sqlite3_file *id, int deleteFlag){ - return id->pMethods->xShmClose(id, deleteFlag); + return id->pMethods->xShmUnmap(id, deleteFlag); } int sqlite3OsShmMap( - sqlite3_file *id, - int iPage, - int pgsz, - int isWrite, - void volatile **pp + sqlite3_file *id, /* Database file handle */ + int iPage, + int pgsz, + int bExtend, /* True to extend file if necessary */ + void volatile **pp /* OUT: Pointer to mapping */ ){ - return id->pMethods->xShmMap(id, iPage, pgsz, isWrite, pp); + return id->pMethods->xShmMap(id, iPage, pgsz, bExtend, pp); } /* @@ -247,11 +247,10 @@ int sqlite3OsFileControl(sqlite3_file*,int,void*); #define SQLITE_FCNTL_DB_UNCHANGED 0xca093fa0 int sqlite3OsSectorSize(sqlite3_file *id); int sqlite3OsDeviceCharacteristics(sqlite3_file *id); -int sqlite3OsShmOpen(sqlite3_file *id); +int sqlite3OsShmMap(sqlite3_file *,int,int,int,void volatile **); int sqlite3OsShmLock(sqlite3_file *id, int, int, int); void sqlite3OsShmBarrier(sqlite3_file *id); int sqlite3OsShmClose(sqlite3_file *id, int); -int sqlite3OsShmMap(sqlite3_file *,int,int,int,void volatile **); /* ** Functions for accessing sqlite3_vfs methods diff --git a/src/os_unix.c b/src/os_unix.c index 23b558b09..e3fafca08 100644 --- a/src/os_unix.c +++ b/src/os_unix.c @@ -3275,7 +3275,7 @@ static void unixShmPurge(unixFile *pFd){ } /* -** Open a shared-memory area associated with open database file fd. +** Open a shared-memory area associated with open database file pDbFd. ** This particular implementation uses mmapped files. ** ** The file used to implement shared-memory is in the same directory @@ -3294,27 +3294,22 @@ static void unixShmPurge(unixFile *pFd){ ** file are currently open, in this process or in other processes, then ** the file must be truncated to zero length or have its header cleared. */ -static int unixShmOpen( - sqlite3_file *fd /* The file descriptor of the associated database */ -){ - struct unixShm *p = 0; /* The connection to be opened */ - struct unixShmNode *pShmNode = 0; /* The underlying mmapped file */ - int rc; /* Result code */ - struct unixFile *pDbFd; /* Underlying database file */ - unixInodeInfo *pInode; /* The inode of fd */ - char *zShmFilename; /* Name of the file used for SHM */ - int nShmFilename; /* Size of the SHM filename in bytes */ - - /* Allocate space for the new sqlite3_shm object. - */ +static int unixOpenSharedMemory(unixFile *pDbFd){ + struct unixShm *p = 0; /* The connection to be opened */ + struct unixShmNode *pShmNode; /* The underlying mmapped file */ + int rc; /* Result code */ + unixInodeInfo *pInode; /* The inode of fd */ + char *zShmFilename; /* Name of the file used for SHM */ + int nShmFilename; /* Size of the SHM filename in bytes */ + + /* Allocate space for the new unixShm object. */ p = sqlite3_malloc( sizeof(*p) ); if( p==0 ) return SQLITE_NOMEM; memset(p, 0, sizeof(*p)); - pDbFd = (struct unixFile*)fd; assert( pDbFd->pShm==0 ); - /* Check to see if a unixShmNode object already exists. Reuse an existing - ** one if present. Create a new one if necessary. + /* Check to see if a unixShmNode object already exists. Reuse an existing + ** one if present. Create a new one if necessary. */ unixEnterMutex(); pInode = pDbFd->pInode; @@ -3380,49 +3375,107 @@ shm_open_err: } /* -** Close a connection to shared-memory. Delete the underlying -** storage if deleteFlag is true. +** This function is called to obtain a pointer to region iRegion of the +** shared-memory associated with the database file fd. Shared-memory regions +** are numbered starting from zero. Each shared-memory region is szRegion +** bytes in size. +** +** If an error occurs, an error code is returned and *pp is set to NULL. +** +** Otherwise, if the bExtend parameter is 0 and the requested shared-memory +** region has not been allocated (by any client, including one running in a +** separate process), then *pp is set to NULL and SQLITE_OK returned. If +** bExtend is non-zero and the requested shared-memory region has not yet +** been allocated, it is allocated by this function. +** +** If the shared-memory region has already been allocated or is allocated by +** this call as described above, then it is mapped into this processes +** address space (if it is not already), *pp is set to point to the mapped +** memory and SQLITE_OK returned. */ -static int unixShmClose( - sqlite3_file *fd, /* The underlying database file */ - int deleteFlag /* Delete shared-memory if true */ +static int unixShmMap( + sqlite3_file *fd, /* Handle open on database file */ + int iRegion, /* Region to retrieve */ + int szRegion, /* Size of regions */ + int bExtend, /* True to extend file if necessary */ + void volatile **pp /* OUT: Mapped memory */ ){ - unixShm *p; /* The connection to be closed */ - unixShmNode *pShmNode; /* The underlying shared-memory file */ - unixShm **pp; /* For looping over sibling connections */ - unixFile *pDbFd; /* The underlying database file */ + unixFile *pDbFd = (unixFile*)fd; + unixShm *p; + unixShmNode *pShmNode; + int rc = SQLITE_OK; + + /* If the shared-memory file has not yet been opened, open it now. */ + if( pDbFd->pShm==0 ){ + rc = unixOpenSharedMemory(pDbFd); + if( rc!=SQLITE_OK ) return rc; + } - pDbFd = (unixFile*)fd; p = pDbFd->pShm; - if( p==0 ) return SQLITE_OK; pShmNode = p->pShmNode; + sqlite3_mutex_enter(pShmNode->mutex); + assert( szRegion==pShmNode->szRegion || pShmNode->nRegion==0 ); - assert( pShmNode==pDbFd->pInode->pShmNode ); - assert( pShmNode->pInode==pDbFd->pInode ); + if( pShmNode->nRegion<=iRegion ){ + char **apNew; /* New apRegion[] array */ + int nByte = (iRegion+1)*szRegion; /* Minimum required file size */ + struct stat sStat; /* Used by fstat() */ - /* Remove connection p from the set of connections associated - ** with pShmNode */ - sqlite3_mutex_enter(pShmNode->mutex); - for(pp=&pShmNode->pFirst; (*pp)!=p; pp = &(*pp)->pNext){} - *pp = p->pNext; + pShmNode->szRegion = szRegion; - /* Free the connection p */ - sqlite3_free(p); - pDbFd->pShm = 0; - sqlite3_mutex_leave(pShmNode->mutex); + /* The requested region is not mapped into this processes address space. + ** Check to see if it has been allocated (i.e. if the wal-index file is + ** large enough to contain the requested region). + */ + if( fstat(pShmNode->h, &sStat) ){ + rc = SQLITE_IOERR_SHMSIZE; + goto shmpage_out; + } - /* If pShmNode->nRef has reached 0, then close the underlying - ** shared-memory file, too */ - unixEnterMutex(); - assert( pShmNode->nRef>0 ); - pShmNode->nRef--; - if( pShmNode->nRef==0 ){ - if( deleteFlag ) unlink(pShmNode->zFilename); - unixShmPurge(pDbFd); + if( sStat.st_size<nByte ){ + /* The requested memory region does not exist. If bExtend is set to + ** false, exit early. *pp will be set to NULL and SQLITE_OK returned. + ** + ** Alternatively, if bExtend is true, use ftruncate() to allocate + ** the requested memory region. + */ + if( !bExtend ) goto shmpage_out; + if( ftruncate(pShmNode->h, nByte) ){ + rc = SQLITE_IOERR_SHMSIZE; + goto shmpage_out; + } + } + + /* Map the requested memory region into this processes address space. */ + apNew = (char **)sqlite3_realloc( + pShmNode->apRegion, (iRegion+1)*sizeof(char *) + ); + if( !apNew ){ + rc = SQLITE_IOERR_NOMEM; + goto shmpage_out; + } + pShmNode->apRegion = apNew; + while(pShmNode->nRegion<=iRegion){ + void *pMem = mmap(0, szRegion, PROT_READ|PROT_WRITE, + MAP_SHARED, pShmNode->h, iRegion*szRegion + ); + if( pMem==MAP_FAILED ){ + rc = SQLITE_IOERR; + goto shmpage_out; + } + pShmNode->apRegion[pShmNode->nRegion] = pMem; + pShmNode->nRegion++; + } } - unixLeaveMutex(); - return SQLITE_OK; +shmpage_out: + if( pShmNode->nRegion>iRegion ){ + *pp = pShmNode->apRegion[iRegion]; + }else{ + *pp = 0; + } + sqlite3_mutex_leave(pShmNode->mutex); + return rc; } /* @@ -3552,107 +3605,57 @@ static void unixShmBarrier( } /* -** This function is called to obtain a pointer to region iRegion of the -** shared-memory associated with the database file fd. Shared-memory regions -** are numbered starting from zero. Each shared-memory region is szRegion -** bytes in size. -** -** If an error occurs, an error code is returned and *pp is set to NULL. -** -** Otherwise, if the isWrite parameter is 0 and the requested shared-memory -** region has not been allocated (by any client, including one running in a -** separate process), then *pp is set to NULL and SQLITE_OK returned. If -** isWrite is non-zero and the requested shared-memory region has not yet -** been allocated, it is allocated by this function. -** -** If the shared-memory region has already been allocated or is allocated by -** this call as described above, then it is mapped into this processes -** address space (if it is not already), *pp is set to point to the mapped -** memory and SQLITE_OK returned. +** Close a connection to shared-memory. Delete the underlying +** storage if deleteFlag is true. */ -static int unixShmMap( - sqlite3_file *fd, /* Handle open on database file */ - int iRegion, /* Region to retrieve */ - int szRegion, /* Size of regions */ - int isWrite, /* True to extend file if necessary */ - void volatile **pp /* OUT: Mapped memory */ +static int unixShmUnmap( + sqlite3_file *fd, /* The underlying database file */ + int deleteFlag /* Delete shared-memory if true */ ){ - unixFile *pDbFd = (unixFile*)fd; - unixShm *p = pDbFd->pShm; - unixShmNode *pShmNode = p->pShmNode; - int rc = SQLITE_OK; - - sqlite3_mutex_enter(pShmNode->mutex); - assert( szRegion==pShmNode->szRegion || pShmNode->nRegion==0 ); + unixShm *p; /* The connection to be closed */ + unixShmNode *pShmNode; /* The underlying shared-memory file */ + unixShm **pp; /* For looping over sibling connections */ + unixFile *pDbFd; /* The underlying database file */ - if( pShmNode->nRegion<=iRegion ){ - char **apNew; /* New apRegion[] array */ - int nByte = (iRegion+1)*szRegion; /* Minimum required file size */ - struct stat sStat; /* Used by fstat() */ + pDbFd = (unixFile*)fd; + p = pDbFd->pShm; + if( p==0 ) return SQLITE_OK; + pShmNode = p->pShmNode; - pShmNode->szRegion = szRegion; + assert( pShmNode==pDbFd->pInode->pShmNode ); + assert( pShmNode->pInode==pDbFd->pInode ); - /* The requested region is not mapped into this processes address space. - ** Check to see if it has been allocated (i.e. if the wal-index file is - ** large enough to contain the requested region). - */ - if( fstat(pShmNode->h, &sStat) ){ - rc = SQLITE_IOERR_SHMSIZE; - goto shmpage_out; - } + /* Remove connection p from the set of connections associated + ** with pShmNode */ + sqlite3_mutex_enter(pShmNode->mutex); + for(pp=&pShmNode->pFirst; (*pp)!=p; pp = &(*pp)->pNext){} + *pp = p->pNext; - if( sStat.st_size<nByte ){ - /* The requested memory region does not exist. If isWrite is set to - ** zero, exit early. *pp will be set to NULL and SQLITE_OK returned. - ** - ** Alternatively, if isWrite is non-zero, use ftruncate() to allocate - ** the requested memory region. - */ - if( !isWrite ) goto shmpage_out; - if( ftruncate(pShmNode->h, nByte) ){ - rc = SQLITE_IOERR_SHMSIZE; - goto shmpage_out; - } - } + /* Free the connection p */ + sqlite3_free(p); + pDbFd->pShm = 0; + sqlite3_mutex_leave(pShmNode->mutex); - /* Map the requested memory region into this processes address space. */ - apNew = (char **)sqlite3_realloc( - pShmNode->apRegion, (iRegion+1)*sizeof(char *) - ); - if( !apNew ){ - rc = SQLITE_IOERR_NOMEM; - goto shmpage_out; - } - pShmNode->apRegion = apNew; - while(pShmNode->nRegion<=iRegion){ - void *pMem = mmap(0, szRegion, PROT_READ|PROT_WRITE, - MAP_SHARED, pShmNode->h, iRegion*szRegion - ); - if( pMem==MAP_FAILED ){ - rc = SQLITE_IOERR; - goto shmpage_out; - } - pShmNode->apRegion[pShmNode->nRegion] = pMem; - pShmNode->nRegion++; - } + /* If pShmNode->nRef has reached 0, then close the underlying + ** shared-memory file, too */ + unixEnterMutex(); + assert( pShmNode->nRef>0 ); + pShmNode->nRef--; + if( pShmNode->nRef==0 ){ + if( deleteFlag ) unlink(pShmNode->zFilename); + unixShmPurge(pDbFd); } + unixLeaveMutex(); -shmpage_out: - if( pShmNode->nRegion>iRegion ){ - *pp = pShmNode->apRegion[iRegion]; - }else{ - *pp = 0; - } - sqlite3_mutex_leave(pShmNode->mutex); - return rc; + return SQLITE_OK; } + #else -# define unixShmOpen 0 -# define unixShmLock 0 # define unixShmMap 0 +# define unixShmLock 0 # define unixShmBarrier 0 -# define unixShmClose 0 +# define unixShmUnmap 0 #endif /* #ifndef SQLITE_OMIT_WAL */ /* @@ -3710,11 +3713,10 @@ static const sqlite3_io_methods METHOD = { \ unixFileControl, /* xFileControl */ \ unixSectorSize, /* xSectorSize */ \ unixDeviceCharacteristics, /* xDeviceCapabilities */ \ - unixShmOpen, /* xShmOpen */ \ - unixShmLock, /* xShmLock */ \ unixShmMap, /* xShmMap */ \ + unixShmLock, /* xShmLock */ \ unixShmBarrier, /* xShmBarrier */ \ - unixShmClose /* xShmClose */ \ + unixShmUnmap /* xShmUnmap */ \ }; \ static const sqlite3_io_methods *FINDER##Impl(const char *z, unixFile *p){ \ UNUSED_PARAMETER(z); UNUSED_PARAMETER(p); \ diff --git a/src/os_win.c b/src/os_win.c index 74ac9c89b..9349c4588 100644 --- a/src/os_win.c +++ b/src/os_win.c @@ -1374,31 +1374,19 @@ static void winShmPurge(sqlite3_vfs *pVfs, int deleteFlag){ } /* -** Open a shared-memory area. This particular implementation uses -** mmapped files. -** -** zName is a filename used to identify the shared-memory area. The -** implementation does not (and perhaps should not) use this name -** directly, but rather use it as a template for finding an appropriate -** name for the shared-memory storage. In this implementation, the -** string "-index" is appended to zName and used as the name of the -** mmapped file. +** Open the shared-memory area associated with database file pDbFd. ** ** When opening a new shared-memory file, if no other instances of that ** file are currently open, in this process or in other processes, then ** the file must be truncated to zero length or have its header cleared. */ -static int winShmOpen( - sqlite3_file *fd /* The file to which to attach shared memory */ -){ - struct winFile *pDbFd; /* Database to which to attach SHM */ +static int winOpenSharedMemory(winFile *pDbFd){ struct winShm *p; /* The connection to be opened */ struct winShmNode *pShmNode = 0; /* The underlying mmapped file */ int rc; /* Result code */ struct winShmNode *pNew; /* Newly allocated winShmNode */ int nName; /* Size of zName in bytes */ - pDbFd = (winFile*)fd; assert( pDbFd->pShm==0 ); /* Not previously opened */ /* Allocate space for the new sqlite3_shm object. Also speculatively @@ -1680,9 +1668,16 @@ static int winShmMap( ){ winFile *pDbFd = (winFile*)fd; winShm *p = pDbFd->pShm; - winShmNode *pShmNode = p->pShmNode; + winShmNode *pShmNode; int rc = SQLITE_OK; + if( !p ){ + rc = winOpenSharedMemory(pDbFd); + if( rc!=SQLITE_OK ) return rc; + p = pDbFd->pShm; + } + pShmNode = p->pShmNode; + sqlite3_mutex_enter(pShmNode->mutex); assert( szRegion==pShmNode->szRegion || pShmNode->nRegion==0 ); @@ -1765,9 +1760,8 @@ shmpage_out: } #else -# define winShmOpen 0 -# define winShmLock 0 # define winShmMap 0 +# define winShmLock 0 # define winShmBarrier 0 # define winShmClose 0 #endif /* #ifndef SQLITE_OMIT_WAL */ @@ -1783,24 +1777,23 @@ shmpage_out: ** sqlite3_file for win32. */ static const sqlite3_io_methods winIoMethod = { - 2, /* iVersion */ - winClose, - winRead, - winWrite, - winTruncate, - winSync, - winFileSize, - winLock, - winUnlock, - winCheckReservedLock, - winFileControl, - winSectorSize, - winDeviceCharacteristics, - winShmOpen, /* xShmOpen */ - winShmLock, /* xShmLock */ - winShmMap, /* xShmMap */ - winShmBarrier, /* xShmBarrier */ - winShmClose /* xShmClose */ + 2, /* iVersion */ + winClose, /* xClose */ + winRead, /* xRead */ + winWrite, /* xWrite */ + winTruncate, /* xTruncate */ + winSync, /* xSync */ + winFileSize, /* xFileSize */ + winLock, /* xLock */ + winUnlock, /* xUnlock */ + winCheckReservedLock, /* xCheckReservedLock */ + winFileControl, /* xFileControl */ + winSectorSize, /* xSectorSize */ + winDeviceCharacteristics, /* xDeviceCharacteristics */ + winShmMap, /* xShmMap */ + winShmLock, /* xShmLock */ + winShmBarrier, /* xShmBarrier */ + winShmClose /* xShmClose */ }; /**************************************************************************** diff --git a/src/pager.c b/src/pager.c index c972440df..dfb29e3df 100644 --- a/src/pager.c +++ b/src/pager.c @@ -6023,7 +6023,7 @@ int sqlite3PagerWalCallback(Pager *pPager){ */ int sqlite3PagerWalSupported(Pager *pPager){ const sqlite3_io_methods *pMethods = pPager->fd->pMethods; - return pMethods->iVersion>=2 && pMethods->xShmOpen!=0; + return pMethods->iVersion>=2 && pMethods->xShmMap!=0; } /* diff --git a/src/sqlite.h.in b/src/sqlite.h.in index 5d29de26b..4545a91fa 100644 --- a/src/sqlite.h.in +++ b/src/sqlite.h.in @@ -660,7 +660,7 @@ struct sqlite3_io_methods { int (*xSectorSize)(sqlite3_file*); int (*xDeviceCharacteristics)(sqlite3_file*); /* Methods above are valid for version 1 */ - int (*xShmMap)(sqlite3_file*, int iPg, int pgsz, int, int*, void volatile**); + int (*xShmMap)(sqlite3_file*, int iPg, int pgsz, int, void volatile**); int (*xShmLock)(sqlite3_file*, int offset, int n, int flags); void (*xShmBarrier)(sqlite3_file*); int (*xShmUnmap)(sqlite3_file*, int deleteFlag); diff --git a/src/test6.c b/src/test6.c index e5cfa0e99..cb87cf23c 100644 --- a/src/test6.c +++ b/src/test6.c @@ -523,9 +523,6 @@ static int cfDeviceCharacteristics(sqlite3_file *pFile){ /* ** Pass-throughs for WAL support. */ -static int cfShmOpen(sqlite3_file *pFile){ - return sqlite3OsShmOpen(((CrashFile*)pFile)->pRealFile); -} static int cfShmLock(sqlite3_file *pFile, int ofst, int n, int flags){ return sqlite3OsShmLock(((CrashFile*)pFile)->pRealFile, ofst, n, flags); } @@ -559,9 +556,8 @@ static const sqlite3_io_methods CrashFileVtab = { cfFileControl, /* xFileControl */ cfSectorSize, /* xSectorSize */ cfDeviceCharacteristics, /* xDeviceCharacteristics */ - cfShmOpen, /* xShmOpen */ - cfShmLock, /* xShmLock */ cfShmMap, /* xShmMap */ + cfShmLock, /* xShmLock */ cfShmBarrier, /* xShmBarrier */ cfShmClose /* xShmClose */ }; diff --git a/src/test_devsym.c b/src/test_devsym.c index f2b91f03c..b2ebd885a 100644 --- a/src/test_devsym.c +++ b/src/test_devsym.c @@ -50,7 +50,6 @@ static int devsymCheckReservedLock(sqlite3_file*, int *); static int devsymFileControl(sqlite3_file*, int op, void *pArg); static int devsymSectorSize(sqlite3_file*); static int devsymDeviceCharacteristics(sqlite3_file*); -static int devsymShmOpen(sqlite3_file*); static int devsymShmLock(sqlite3_file*,int,int,int); static int devsymShmMap(sqlite3_file*,int,int,int, void volatile **); static void devsymShmBarrier(sqlite3_file*); @@ -116,9 +115,8 @@ static sqlite3_io_methods devsym_io_methods = { devsymFileControl, /* xFileControl */ devsymSectorSize, /* xSectorSize */ devsymDeviceCharacteristics, /* xDeviceCharacteristics */ - devsymShmOpen, /* xShmOpen */ - devsymShmLock, /* xShmLock */ devsymShmMap, /* xShmMap */ + devsymShmLock, /* xShmLock */ devsymShmBarrier, /* xShmBarrier */ devsymShmClose /* xShmClose */ }; @@ -237,10 +235,6 @@ static int devsymDeviceCharacteristics(sqlite3_file *pFile){ /* ** Shared-memory methods are all pass-thrus. */ -static int devsymShmOpen(sqlite3_file *pFile){ - devsym_file *p = (devsym_file *)pFile; - return sqlite3OsShmOpen(p->pReal); -} static int devsymShmLock(sqlite3_file *pFile, int ofst, int n, int flags){ devsym_file *p = (devsym_file *)pFile; return sqlite3OsShmLock(p->pReal, ofst, n, flags); diff --git a/src/test_onefile.c b/src/test_onefile.c index 65c6b7afd..64d5a66a3 100644 --- a/src/test_onefile.c +++ b/src/test_onefile.c @@ -219,9 +219,8 @@ static sqlite3_io_methods fs_io_methods = { fsFileControl, /* xFileControl */ fsSectorSize, /* xSectorSize */ fsDeviceCharacteristics, /* xDeviceCharacteristics */ - 0, /* xShmOpen */ - 0, /* xShmLock */ 0, /* xShmMap */ + 0, /* xShmLock */ 0, /* xShmBarrier */ 0 /* xShmClose */ }; @@ -241,9 +240,8 @@ static sqlite3_io_methods tmp_io_methods = { tmpFileControl, /* xFileControl */ tmpSectorSize, /* xSectorSize */ tmpDeviceCharacteristics, /* xDeviceCharacteristics */ - 0, /* xShmOpen */ - 0, /* xShmLock */ 0, /* xShmMap */ + 0, /* xShmLock */ 0, /* xShmBarrier */ 0 /* xShmClose */ }; diff --git a/src/test_osinst.c b/src/test_osinst.c index d77eeafa5..25e9bcbfb 100644 --- a/src/test_osinst.c +++ b/src/test_osinst.c @@ -98,8 +98,7 @@ #define OS_TRUNCATE 18 #define OS_UNLOCK 19 #define OS_WRITE 20 -#define OS_SHMOPEN 21 -#define OS_SHMCLOSE 22 +#define OS_SHMUNMAP 22 #define OS_SHMMAP 23 #define OS_SHMLOCK 25 #define OS_SHMBARRIER 26 @@ -149,11 +148,10 @@ static int vfslogFileControl(sqlite3_file*, int op, void *pArg); static int vfslogSectorSize(sqlite3_file*); static int vfslogDeviceCharacteristics(sqlite3_file*); -static int vfslogShmOpen(sqlite3_file *pFile); static int vfslogShmLock(sqlite3_file *pFile, int ofst, int n, int flags); static int vfslogShmMap(sqlite3_file *pFile,int,int,int,volatile void **); static void vfslogShmBarrier(sqlite3_file*); -static int vfslogShmClose(sqlite3_file *pFile, int deleteFlag); +static int vfslogShmUnmap(sqlite3_file *pFile, int deleteFlag); /* ** Method declarations for vfslog_vfs. @@ -209,11 +207,10 @@ static sqlite3_io_methods vfslog_io_methods = { vfslogFileControl, /* xFileControl */ vfslogSectorSize, /* xSectorSize */ vfslogDeviceCharacteristics, /* xDeviceCharacteristics */ - vfslogShmOpen, /* xShmOpen */ - vfslogShmLock, /* xShmLock */ vfslogShmMap, /* xShmMap */ + vfslogShmLock, /* xShmLock */ vfslogShmBarrier, /* xShmBarrier */ - vfslogShmClose /* xShmClose */ + vfslogShmUnmap /* xShmUnmap */ }; #if defined(SQLITE_OS_UNIX) && !defined(NO_GETTOD) @@ -423,16 +420,6 @@ static int vfslogDeviceCharacteristics(sqlite3_file *pFile){ return rc; } -static int vfslogShmOpen(sqlite3_file *pFile){ - int rc; - sqlite3_uint64 t; - VfslogFile *p = (VfslogFile *)pFile; - t = vfslog_time(); - rc = p->pReal->pMethods->xShmOpen(p->pReal); - t = vfslog_time() - t; - vfslog_call(p->pVfslog, OS_SHMOPEN, p->iFileId, t, rc, 0, 0); - return rc; -} static int vfslogShmLock(sqlite3_file *pFile, int ofst, int n, int flags){ int rc; sqlite3_uint64 t; @@ -467,14 +454,14 @@ static void vfslogShmBarrier(sqlite3_file *pFile){ t = vfslog_time() - t; vfslog_call(p->pVfslog, OS_SHMBARRIER, p->iFileId, t, SQLITE_OK, 0, 0); } -static int vfslogShmClose(sqlite3_file *pFile, int deleteFlag){ +static int vfslogShmUnmap(sqlite3_file *pFile, int deleteFlag){ int rc; sqlite3_uint64 t; VfslogFile *p = (VfslogFile *)pFile; t = vfslog_time(); - rc = p->pReal->pMethods->xShmClose(p->pReal, deleteFlag); + rc = p->pReal->pMethods->xShmUnmap(p->pReal, deleteFlag); t = vfslog_time() - t; - vfslog_call(p->pVfslog, OS_SHMCLOSE, p->iFileId, t, rc, 0, 0); + vfslog_call(p->pVfslog, OS_SHMUNMAP, p->iFileId, t, rc, 0, 0); return rc; } @@ -794,8 +781,7 @@ static const char *vfslog_eventname(int eEvent){ case OS_SLEEP: zEvent = "xSleep"; break; case OS_CURRENTTIME: zEvent = "xCurrentTime"; break; - case OS_SHMCLOSE: zEvent = "xShmClose"; break; - case OS_SHMOPEN: zEvent = "xShmOpen"; break; + case OS_SHMUNMAP: zEvent = "xShmUnmap"; break; case OS_SHMLOCK: zEvent = "xShmLock"; break; case OS_SHMBARRIER: zEvent = "xShmBarrier"; break; case OS_SHMMAP: zEvent = "xShmMap"; break; diff --git a/src/test_vfs.c b/src/test_vfs.c index 1b5bd59fb..f577bf510 100644 --- a/src/test_vfs.c +++ b/src/test_vfs.c @@ -187,7 +187,7 @@ static int tvfsShmOpen(sqlite3_file*); static int tvfsShmLock(sqlite3_file*, int , int, int); static int tvfsShmMap(sqlite3_file*,int,int,int, void volatile **); static void tvfsShmBarrier(sqlite3_file*); -static int tvfsShmClose(sqlite3_file*, int); +static int tvfsShmUnmap(sqlite3_file*, int); static sqlite3_io_methods tvfs_io_methods = { 2, /* iVersion */ @@ -203,11 +203,10 @@ static sqlite3_io_methods tvfs_io_methods = { tvfsFileControl, /* xFileControl */ tvfsSectorSize, /* xSectorSize */ tvfsDeviceCharacteristics, /* xDeviceCharacteristics */ - tvfsShmOpen, /* xShmOpen */ - tvfsShmLock, /* xShmLock */ tvfsShmMap, /* xShmMap */ + tvfsShmLock, /* xShmLock */ tvfsShmBarrier, /* xShmBarrier */ - tvfsShmClose /* xShmClose */ + tvfsShmUnmap /* xShmUnmap */ }; static int tvfsResultCode(Testvfs *p, int *pRc){ @@ -580,15 +579,14 @@ static int tvfsOpen( if( pVfs->iVersion>1 ){ nByte = sizeof(sqlite3_io_methods); }else{ - nByte = offsetof(sqlite3_io_methods, xShmOpen); + nByte = offsetof(sqlite3_io_methods, xShmMap); } pMethods = (sqlite3_io_methods *)ckalloc(nByte); memcpy(pMethods, &tvfs_io_methods, nByte); pMethods->iVersion = pVfs->iVersion; if( pVfs->iVersion>1 && ((Testvfs *)pVfs->pAppData)->isNoshm ){ - pMethods->xShmOpen = 0; - pMethods->xShmClose = 0; + pMethods->xShmUnmap = 0; pMethods->xShmLock = 0; pMethods->xShmBarrier = 0; pMethods->xShmMap = 0; @@ -789,6 +787,13 @@ static int tvfsShmMap( TestvfsFd *pFd = tvfsGetFd(pFile); Testvfs *p = (Testvfs *)(pFd->pVfs->pAppData); + if( 0==pFd->pShm ){ + rc = tvfsShmOpen(pFile); + if( rc!=SQLITE_OK ){ + return rc; + } + } + if( p->pScript && p->mask&TESTVFS_SHMMAP_MASK ){ Tcl_Obj *pArg = Tcl_NewObj(); Tcl_IncrRefCount(pArg); @@ -888,7 +893,7 @@ static void tvfsShmBarrier(sqlite3_file *pFile){ } } -static int tvfsShmClose( +static int tvfsShmUnmap( sqlite3_file *pFile, int deleteFlag ){ @@ -898,10 +903,11 @@ static int tvfsShmClose( TestvfsBuffer *pBuffer = pFd->pShm; TestvfsFd **ppFd; + if( !pBuffer ) return SQLITE_OK; assert( pFd->pShmId && pFd->pShm ); if( p->pScript && p->mask&TESTVFS_SHMCLOSE_MASK ){ - tvfsExecTcl(p, "xShmClose", + tvfsExecTcl(p, "xShmUnmap", Tcl_NewStringObj(pFd->pShm->zFile, -1), pFd->pShmId, 0 ); tvfsResultCode(p, &rc); @@ -1023,7 +1029,7 @@ static int testvfs_obj_cmd( { "xShmOpen", TESTVFS_SHMOPEN_MASK }, { "xShmLock", TESTVFS_SHMLOCK_MASK }, { "xShmBarrier", TESTVFS_SHMBARRIER_MASK }, - { "xShmClose", TESTVFS_SHMCLOSE_MASK }, + { "xShmUnmap", TESTVFS_SHMCLOSE_MASK }, { "xShmMap", TESTVFS_SHMMAP_MASK }, { "xSync", TESTVFS_SYNC_MASK }, { "xDelete", TESTVFS_DELETE_MASK }, @@ -413,7 +413,6 @@ struct Wal { u16 szPage; /* Database page size */ i16 readLock; /* Which read lock is being held. -1 for none */ u8 exclusiveMode; /* Non-zero if connection is in exclusive mode */ - u8 isWIndexOpen; /* True if ShmOpen() called on pDbFd */ u8 writeLock; /* True if in a write transaction */ u8 ckptLock; /* True if holding a checkpoint lock */ WalIndexHdr hdr; /* Wal-index header for current transaction */ @@ -1168,10 +1167,7 @@ recovery_error: ** Close an open wal-index. */ static void walIndexClose(Wal *pWal, int isDelete){ - if( pWal->isWIndexOpen ){ - sqlite3OsShmClose(pWal->pDbFd, isDelete); - pWal->isWIndexOpen = 0; - } + sqlite3OsShmClose(pWal->pDbFd, isDelete); } /* @@ -1226,14 +1222,10 @@ int sqlite3WalOpen( pRet->pDbFd = pDbFd; pRet->readLock = -1; pRet->zWalName = zWalName; - rc = sqlite3OsShmOpen(pDbFd); /* Open file handle on the write-ahead log file. */ - if( rc==SQLITE_OK ){ - pRet->isWIndexOpen = 1; - flags = (SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE|SQLITE_OPEN_MAIN_JOURNAL); - rc = sqlite3OsOpen(pVfs, zWalName, pRet->pWalFd, flags, &flags); - } + flags = (SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE|SQLITE_OPEN_MAIN_JOURNAL); + rc = sqlite3OsOpen(pVfs, zWalName, pRet->pWalFd, flags, &flags); if( rc!=SQLITE_OK ){ walIndexClose(pRet, 0); @@ -2204,8 +2196,10 @@ int sqlite3WalBeginWriteTransaction(Wal *pWal){ ** routine merely releases the lock. */ int sqlite3WalEndWriteTransaction(Wal *pWal){ - walUnlockExclusive(pWal, WAL_WRITE_LOCK, 1); - pWal->writeLock = 0; + if( pWal->writeLock ){ + walUnlockExclusive(pWal, WAL_WRITE_LOCK, 1); + pWal->writeLock = 0; + } return SQLITE_OK; } |