Index: third_party/sqlite/sqlite-src-3070603/src/os.c |
diff --git a/third_party/sqlite/sqlite-src-3070603/src/os.c b/third_party/sqlite/sqlite-src-3070603/src/os.c |
new file mode 100644 |
index 0000000000000000000000000000000000000000..ba0438adef021ee3e0f5de840e3373390a0da611 |
--- /dev/null |
+++ b/third_party/sqlite/sqlite-src-3070603/src/os.c |
@@ -0,0 +1,331 @@ |
+/* |
+** 2005 November 29 |
+** |
+** The author disclaims copyright to this source code. In place of |
+** a legal notice, here is a blessing: |
+** |
+** May you do good and not evil. |
+** May you find forgiveness for yourself and forgive others. |
+** May you share freely, never taking more than you give. |
+** |
+****************************************************************************** |
+** |
+** This file contains OS interface code that is common to all |
+** architectures. |
+*/ |
+#define _SQLITE_OS_C_ 1 |
+#include "sqliteInt.h" |
+#undef _SQLITE_OS_C_ |
+ |
+/* |
+** The default SQLite sqlite3_vfs implementations do not allocate |
+** memory (actually, os_unix.c allocates a small amount of memory |
+** from within OsOpen()), but some third-party implementations may. |
+** So we test the effects of a malloc() failing and the sqlite3OsXXX() |
+** function returning SQLITE_IOERR_NOMEM using the DO_OS_MALLOC_TEST macro. |
+** |
+** The following functions are instrumented for malloc() failure |
+** testing: |
+** |
+** sqlite3OsOpen() |
+** sqlite3OsRead() |
+** sqlite3OsWrite() |
+** sqlite3OsSync() |
+** sqlite3OsLock() |
+** |
+*/ |
+#if defined(SQLITE_TEST) |
+int sqlite3_memdebug_vfs_oom_test = 1; |
+ #define DO_OS_MALLOC_TEST(x) \ |
+ if (sqlite3_memdebug_vfs_oom_test && (!x || !sqlite3IsMemJournal(x))) { \ |
+ void *pTstAlloc = sqlite3Malloc(10); \ |
+ if (!pTstAlloc) return SQLITE_IOERR_NOMEM; \ |
+ sqlite3_free(pTstAlloc); \ |
+ } |
+#else |
+ #define DO_OS_MALLOC_TEST(x) |
+#endif |
+ |
+/* |
+** The following routines are convenience wrappers around methods |
+** of the sqlite3_file object. This is mostly just syntactic sugar. All |
+** of this would be completely automatic if SQLite were coded using |
+** C++ instead of plain old C. |
+*/ |
+int sqlite3OsClose(sqlite3_file *pId){ |
+ int rc = SQLITE_OK; |
+ if( pId->pMethods ){ |
+ rc = pId->pMethods->xClose(pId); |
+ pId->pMethods = 0; |
+ } |
+ return rc; |
+} |
+int sqlite3OsRead(sqlite3_file *id, void *pBuf, int amt, i64 offset){ |
+ DO_OS_MALLOC_TEST(id); |
+ return id->pMethods->xRead(id, pBuf, amt, offset); |
+} |
+int sqlite3OsWrite(sqlite3_file *id, const void *pBuf, int amt, i64 offset){ |
+ DO_OS_MALLOC_TEST(id); |
+ return id->pMethods->xWrite(id, pBuf, amt, offset); |
+} |
+int sqlite3OsTruncate(sqlite3_file *id, i64 size){ |
+ return id->pMethods->xTruncate(id, size); |
+} |
+int sqlite3OsSync(sqlite3_file *id, int flags){ |
+ DO_OS_MALLOC_TEST(id); |
+ return id->pMethods->xSync(id, flags); |
+} |
+int sqlite3OsFileSize(sqlite3_file *id, i64 *pSize){ |
+ DO_OS_MALLOC_TEST(id); |
+ return id->pMethods->xFileSize(id, pSize); |
+} |
+int sqlite3OsLock(sqlite3_file *id, int lockType){ |
+ DO_OS_MALLOC_TEST(id); |
+ return id->pMethods->xLock(id, lockType); |
+} |
+int sqlite3OsUnlock(sqlite3_file *id, int lockType){ |
+ return id->pMethods->xUnlock(id, lockType); |
+} |
+int sqlite3OsCheckReservedLock(sqlite3_file *id, int *pResOut){ |
+ DO_OS_MALLOC_TEST(id); |
+ return id->pMethods->xCheckReservedLock(id, pResOut); |
+} |
+int sqlite3OsFileControl(sqlite3_file *id, int op, void *pArg){ |
+ return id->pMethods->xFileControl(id, op, pArg); |
+} |
+int sqlite3OsSectorSize(sqlite3_file *id){ |
+ int (*xSectorSize)(sqlite3_file*) = id->pMethods->xSectorSize; |
+ return (xSectorSize ? xSectorSize(id) : SQLITE_DEFAULT_SECTOR_SIZE); |
+} |
+int sqlite3OsDeviceCharacteristics(sqlite3_file *id){ |
+ return id->pMethods->xDeviceCharacteristics(id); |
+} |
+int sqlite3OsShmLock(sqlite3_file *id, int offset, int n, int flags){ |
+ return id->pMethods->xShmLock(id, offset, n, flags); |
+} |
+void sqlite3OsShmBarrier(sqlite3_file *id){ |
+ id->pMethods->xShmBarrier(id); |
+} |
+int sqlite3OsShmUnmap(sqlite3_file *id, int deleteFlag){ |
+ return id->pMethods->xShmUnmap(id, deleteFlag); |
+} |
+int sqlite3OsShmMap( |
+ 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, bExtend, pp); |
+} |
+ |
+/* |
+** The next group of routines are convenience wrappers around the |
+** VFS methods. |
+*/ |
+int sqlite3OsOpen( |
+ sqlite3_vfs *pVfs, |
+ const char *zPath, |
+ sqlite3_file *pFile, |
+ int flags, |
+ int *pFlagsOut |
+){ |
+ int rc; |
+ DO_OS_MALLOC_TEST(0); |
+ /* 0x87f3f is a mask of SQLITE_OPEN_ flags that are valid to be passed |
+ ** down into the VFS layer. Some SQLITE_OPEN_ flags (for example, |
+ ** SQLITE_OPEN_FULLMUTEX or SQLITE_OPEN_SHAREDCACHE) are blocked before |
+ ** reaching the VFS. */ |
+ rc = pVfs->xOpen(pVfs, zPath, pFile, flags & 0x87f3f, pFlagsOut); |
+ assert( rc==SQLITE_OK || pFile->pMethods==0 ); |
+ return rc; |
+} |
+int sqlite3OsDelete(sqlite3_vfs *pVfs, const char *zPath, int dirSync){ |
+ return pVfs->xDelete(pVfs, zPath, dirSync); |
+} |
+int sqlite3OsAccess( |
+ sqlite3_vfs *pVfs, |
+ const char *zPath, |
+ int flags, |
+ int *pResOut |
+){ |
+ DO_OS_MALLOC_TEST(0); |
+ return pVfs->xAccess(pVfs, zPath, flags, pResOut); |
+} |
+int sqlite3OsFullPathname( |
+ sqlite3_vfs *pVfs, |
+ const char *zPath, |
+ int nPathOut, |
+ char *zPathOut |
+){ |
+ zPathOut[0] = 0; |
+ return pVfs->xFullPathname(pVfs, zPath, nPathOut, zPathOut); |
+} |
+#ifndef SQLITE_OMIT_LOAD_EXTENSION |
+void *sqlite3OsDlOpen(sqlite3_vfs *pVfs, const char *zPath){ |
+ return pVfs->xDlOpen(pVfs, zPath); |
+} |
+void sqlite3OsDlError(sqlite3_vfs *pVfs, int nByte, char *zBufOut){ |
+ pVfs->xDlError(pVfs, nByte, zBufOut); |
+} |
+void (*sqlite3OsDlSym(sqlite3_vfs *pVfs, void *pHdle, const char *zSym))(void){ |
+ return pVfs->xDlSym(pVfs, pHdle, zSym); |
+} |
+void sqlite3OsDlClose(sqlite3_vfs *pVfs, void *pHandle){ |
+ pVfs->xDlClose(pVfs, pHandle); |
+} |
+#endif /* SQLITE_OMIT_LOAD_EXTENSION */ |
+int sqlite3OsRandomness(sqlite3_vfs *pVfs, int nByte, char *zBufOut){ |
+ return pVfs->xRandomness(pVfs, nByte, zBufOut); |
+} |
+int sqlite3OsSleep(sqlite3_vfs *pVfs, int nMicro){ |
+ return pVfs->xSleep(pVfs, nMicro); |
+} |
+int sqlite3OsCurrentTimeInt64(sqlite3_vfs *pVfs, sqlite3_int64 *pTimeOut){ |
+ int rc; |
+ /* IMPLEMENTATION-OF: R-49045-42493 SQLite will use the xCurrentTimeInt64() |
+ ** method to get the current date and time if that method is available |
+ ** (if iVersion is 2 or greater and the function pointer is not NULL) and |
+ ** will fall back to xCurrentTime() if xCurrentTimeInt64() is |
+ ** unavailable. |
+ */ |
+ if( pVfs->iVersion>=2 && pVfs->xCurrentTimeInt64 ){ |
+ rc = pVfs->xCurrentTimeInt64(pVfs, pTimeOut); |
+ }else{ |
+ double r; |
+ rc = pVfs->xCurrentTime(pVfs, &r); |
+ *pTimeOut = (sqlite3_int64)(r*86400000.0); |
+ } |
+ return rc; |
+} |
+ |
+int sqlite3OsOpenMalloc( |
+ sqlite3_vfs *pVfs, |
+ const char *zFile, |
+ sqlite3_file **ppFile, |
+ int flags, |
+ int *pOutFlags |
+){ |
+ int rc = SQLITE_NOMEM; |
+ sqlite3_file *pFile; |
+ pFile = (sqlite3_file *)sqlite3Malloc(pVfs->szOsFile); |
+ if( pFile ){ |
+ rc = sqlite3OsOpen(pVfs, zFile, pFile, flags, pOutFlags); |
+ if( rc!=SQLITE_OK ){ |
+ sqlite3_free(pFile); |
+ }else{ |
+ *ppFile = pFile; |
+ } |
+ } |
+ return rc; |
+} |
+int sqlite3OsCloseFree(sqlite3_file *pFile){ |
+ int rc = SQLITE_OK; |
+ assert( pFile ); |
+ rc = sqlite3OsClose(pFile); |
+ sqlite3_free(pFile); |
+ return rc; |
+} |
+ |
+/* |
+** This function is a wrapper around the OS specific implementation of |
+** sqlite3_os_init(). The purpose of the wrapper is to provide the |
+** ability to simulate a malloc failure, so that the handling of an |
+** error in sqlite3_os_init() by the upper layers can be tested. |
+*/ |
+int sqlite3OsInit(void){ |
+ void *p = sqlite3_malloc(10); |
+ if( p==0 ) return SQLITE_NOMEM; |
+ sqlite3_free(p); |
+ return sqlite3_os_init(); |
+} |
+ |
+/* |
+** The list of all registered VFS implementations. |
+*/ |
+static sqlite3_vfs * SQLITE_WSD vfsList = 0; |
+#define vfsList GLOBAL(sqlite3_vfs *, vfsList) |
+ |
+/* |
+** Locate a VFS by name. If no name is given, simply return the |
+** first VFS on the list. |
+*/ |
+sqlite3_vfs *sqlite3_vfs_find(const char *zVfs){ |
+ sqlite3_vfs *pVfs = 0; |
+#if SQLITE_THREADSAFE |
+ sqlite3_mutex *mutex; |
+#endif |
+#ifndef SQLITE_OMIT_AUTOINIT |
+ int rc = sqlite3_initialize(); |
+ if( rc ) return 0; |
+#endif |
+#if SQLITE_THREADSAFE |
+ mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); |
+#endif |
+ sqlite3_mutex_enter(mutex); |
+ for(pVfs = vfsList; pVfs; pVfs=pVfs->pNext){ |
+ if( zVfs==0 ) break; |
+ if( strcmp(zVfs, pVfs->zName)==0 ) break; |
+ } |
+ sqlite3_mutex_leave(mutex); |
+ return pVfs; |
+} |
+ |
+/* |
+** Unlink a VFS from the linked list |
+*/ |
+static void vfsUnlink(sqlite3_vfs *pVfs){ |
+ assert( sqlite3_mutex_held(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER)) ); |
+ if( pVfs==0 ){ |
+ /* No-op */ |
+ }else if( vfsList==pVfs ){ |
+ vfsList = pVfs->pNext; |
+ }else if( vfsList ){ |
+ sqlite3_vfs *p = vfsList; |
+ while( p->pNext && p->pNext!=pVfs ){ |
+ p = p->pNext; |
+ } |
+ if( p->pNext==pVfs ){ |
+ p->pNext = pVfs->pNext; |
+ } |
+ } |
+} |
+ |
+/* |
+** Register a VFS with the system. It is harmless to register the same |
+** VFS multiple times. The new VFS becomes the default if makeDflt is |
+** true. |
+*/ |
+int sqlite3_vfs_register(sqlite3_vfs *pVfs, int makeDflt){ |
+ sqlite3_mutex *mutex = 0; |
+#ifndef SQLITE_OMIT_AUTOINIT |
+ int rc = sqlite3_initialize(); |
+ if( rc ) return rc; |
+#endif |
+ mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); |
+ sqlite3_mutex_enter(mutex); |
+ vfsUnlink(pVfs); |
+ if( makeDflt || vfsList==0 ){ |
+ pVfs->pNext = vfsList; |
+ vfsList = pVfs; |
+ }else{ |
+ pVfs->pNext = vfsList->pNext; |
+ vfsList->pNext = pVfs; |
+ } |
+ assert(vfsList); |
+ sqlite3_mutex_leave(mutex); |
+ return SQLITE_OK; |
+} |
+ |
+/* |
+** Unregister a VFS so that it is no longer accessible. |
+*/ |
+int sqlite3_vfs_unregister(sqlite3_vfs *pVfs){ |
+#if SQLITE_THREADSAFE |
+ sqlite3_mutex *mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); |
+#endif |
+ sqlite3_mutex_enter(mutex); |
+ vfsUnlink(pVfs); |
+ sqlite3_mutex_leave(mutex); |
+ return SQLITE_OK; |
+} |