| OLD | NEW | 
 | (Empty) | 
|    1 /* |  | 
|    2 ** 2005 November 29 |  | 
|    3 ** |  | 
|    4 ** The author disclaims copyright to this source code.  In place of |  | 
|    5 ** a legal notice, here is a blessing: |  | 
|    6 ** |  | 
|    7 **    May you do good and not evil. |  | 
|    8 **    May you find forgiveness for yourself and forgive others. |  | 
|    9 **    May you share freely, never taking more than you give. |  | 
|   10 ** |  | 
|   11 ****************************************************************************** |  | 
|   12 ** |  | 
|   13 ** This file contains OS interface code that is common to all |  | 
|   14 ** architectures. |  | 
|   15 ** |  | 
|   16 ** $Id: os.c,v 1.127 2009/07/27 11:41:21 danielk1977 Exp $ |  | 
|   17 */ |  | 
|   18 #define _SQLITE_OS_C_ 1 |  | 
|   19 #include "sqliteInt.h" |  | 
|   20 #undef _SQLITE_OS_C_ |  | 
|   21  |  | 
|   22 /* |  | 
|   23 ** The default SQLite sqlite3_vfs implementations do not allocate |  | 
|   24 ** memory (actually, os_unix.c allocates a small amount of memory |  | 
|   25 ** from within OsOpen()), but some third-party implementations may. |  | 
|   26 ** So we test the effects of a malloc() failing and the sqlite3OsXXX() |  | 
|   27 ** function returning SQLITE_IOERR_NOMEM using the DO_OS_MALLOC_TEST macro. |  | 
|   28 ** |  | 
|   29 ** The following functions are instrumented for malloc() failure  |  | 
|   30 ** testing: |  | 
|   31 ** |  | 
|   32 **     sqlite3OsOpen() |  | 
|   33 **     sqlite3OsRead() |  | 
|   34 **     sqlite3OsWrite() |  | 
|   35 **     sqlite3OsSync() |  | 
|   36 **     sqlite3OsLock() |  | 
|   37 ** |  | 
|   38 */ |  | 
|   39 #if defined(SQLITE_TEST) && (SQLITE_OS_WIN==0) |  | 
|   40   #define DO_OS_MALLOC_TEST(x) if (!x || !sqlite3IsMemJournal(x)) {     \ |  | 
|   41     void *pTstAlloc = sqlite3Malloc(10);                             \ |  | 
|   42     if (!pTstAlloc) return SQLITE_IOERR_NOMEM;                       \ |  | 
|   43     sqlite3_free(pTstAlloc);                                         \ |  | 
|   44   } |  | 
|   45 #else |  | 
|   46   #define DO_OS_MALLOC_TEST(x) |  | 
|   47 #endif |  | 
|   48  |  | 
|   49 /* |  | 
|   50 ** The following routines are convenience wrappers around methods |  | 
|   51 ** of the sqlite3_file object.  This is mostly just syntactic sugar. All |  | 
|   52 ** of this would be completely automatic if SQLite were coded using |  | 
|   53 ** C++ instead of plain old C. |  | 
|   54 */ |  | 
|   55 int sqlite3OsClose(sqlite3_file *pId){ |  | 
|   56   int rc = SQLITE_OK; |  | 
|   57   if( pId->pMethods ){ |  | 
|   58     rc = pId->pMethods->xClose(pId); |  | 
|   59     pId->pMethods = 0; |  | 
|   60   } |  | 
|   61   return rc; |  | 
|   62 } |  | 
|   63 int sqlite3OsRead(sqlite3_file *id, void *pBuf, int amt, i64 offset){ |  | 
|   64   DO_OS_MALLOC_TEST(id); |  | 
|   65   return id->pMethods->xRead(id, pBuf, amt, offset); |  | 
|   66 } |  | 
|   67 int sqlite3OsWrite(sqlite3_file *id, const void *pBuf, int amt, i64 offset){ |  | 
|   68   DO_OS_MALLOC_TEST(id); |  | 
|   69   return id->pMethods->xWrite(id, pBuf, amt, offset); |  | 
|   70 } |  | 
|   71 int sqlite3OsTruncate(sqlite3_file *id, i64 size){ |  | 
|   72   return id->pMethods->xTruncate(id, size); |  | 
|   73 } |  | 
|   74 int sqlite3OsSync(sqlite3_file *id, int flags){ |  | 
|   75   DO_OS_MALLOC_TEST(id); |  | 
|   76   return id->pMethods->xSync(id, flags); |  | 
|   77 } |  | 
|   78 int sqlite3OsFileSize(sqlite3_file *id, i64 *pSize){ |  | 
|   79   DO_OS_MALLOC_TEST(id); |  | 
|   80   return id->pMethods->xFileSize(id, pSize); |  | 
|   81 } |  | 
|   82 int sqlite3OsLock(sqlite3_file *id, int lockType){ |  | 
|   83   DO_OS_MALLOC_TEST(id); |  | 
|   84   return id->pMethods->xLock(id, lockType); |  | 
|   85 } |  | 
|   86 int sqlite3OsUnlock(sqlite3_file *id, int lockType){ |  | 
|   87   return id->pMethods->xUnlock(id, lockType); |  | 
|   88 } |  | 
|   89 int sqlite3OsCheckReservedLock(sqlite3_file *id, int *pResOut){ |  | 
|   90   DO_OS_MALLOC_TEST(id); |  | 
|   91   return id->pMethods->xCheckReservedLock(id, pResOut); |  | 
|   92 } |  | 
|   93 int sqlite3OsFileControl(sqlite3_file *id, int op, void *pArg){ |  | 
|   94   return id->pMethods->xFileControl(id, op, pArg); |  | 
|   95 } |  | 
|   96 int sqlite3OsSectorSize(sqlite3_file *id){ |  | 
|   97   int (*xSectorSize)(sqlite3_file*) = id->pMethods->xSectorSize; |  | 
|   98   return (xSectorSize ? xSectorSize(id) : SQLITE_DEFAULT_SECTOR_SIZE); |  | 
|   99 } |  | 
|  100 int sqlite3OsDeviceCharacteristics(sqlite3_file *id){ |  | 
|  101   return id->pMethods->xDeviceCharacteristics(id); |  | 
|  102 } |  | 
|  103  |  | 
|  104 /* |  | 
|  105 ** The next group of routines are convenience wrappers around the |  | 
|  106 ** VFS methods. |  | 
|  107 */ |  | 
|  108 int sqlite3OsOpen( |  | 
|  109   sqlite3_vfs *pVfs,  |  | 
|  110   const char *zPath,  |  | 
|  111   sqlite3_file *pFile,  |  | 
|  112   int flags,  |  | 
|  113   int *pFlagsOut |  | 
|  114 ){ |  | 
|  115   int rc; |  | 
|  116   DO_OS_MALLOC_TEST(0); |  | 
|  117   /* 0x7f1f is a mask of SQLITE_OPEN_ flags that are valid to be passed |  | 
|  118   ** down into the VFS layer.  Some SQLITE_OPEN_ flags (for example, |  | 
|  119   ** SQLITE_OPEN_FULLMUTEX or SQLITE_OPEN_SHAREDCACHE) are blocked before |  | 
|  120   ** reaching the VFS. */ |  | 
|  121   rc = pVfs->xOpen(pVfs, zPath, pFile, flags & 0x7f1f, pFlagsOut); |  | 
|  122   assert( rc==SQLITE_OK || pFile->pMethods==0 ); |  | 
|  123   return rc; |  | 
|  124 } |  | 
|  125 int sqlite3OsDelete(sqlite3_vfs *pVfs, const char *zPath, int dirSync){ |  | 
|  126   return pVfs->xDelete(pVfs, zPath, dirSync); |  | 
|  127 } |  | 
|  128 int sqlite3OsAccess( |  | 
|  129   sqlite3_vfs *pVfs,  |  | 
|  130   const char *zPath,  |  | 
|  131   int flags,  |  | 
|  132   int *pResOut |  | 
|  133 ){ |  | 
|  134   DO_OS_MALLOC_TEST(0); |  | 
|  135   return pVfs->xAccess(pVfs, zPath, flags, pResOut); |  | 
|  136 } |  | 
|  137 int sqlite3OsFullPathname( |  | 
|  138   sqlite3_vfs *pVfs,  |  | 
|  139   const char *zPath,  |  | 
|  140   int nPathOut,  |  | 
|  141   char *zPathOut |  | 
|  142 ){ |  | 
|  143   return pVfs->xFullPathname(pVfs, zPath, nPathOut, zPathOut); |  | 
|  144 } |  | 
|  145 #ifndef SQLITE_OMIT_LOAD_EXTENSION |  | 
|  146 void *sqlite3OsDlOpen(sqlite3_vfs *pVfs, const char *zPath){ |  | 
|  147   return pVfs->xDlOpen(pVfs, zPath); |  | 
|  148 } |  | 
|  149 void sqlite3OsDlError(sqlite3_vfs *pVfs, int nByte, char *zBufOut){ |  | 
|  150   pVfs->xDlError(pVfs, nByte, zBufOut); |  | 
|  151 } |  | 
|  152 void (*sqlite3OsDlSym(sqlite3_vfs *pVfs, void *pHdle, const char *zSym))(void){ |  | 
|  153   return pVfs->xDlSym(pVfs, pHdle, zSym); |  | 
|  154 } |  | 
|  155 void sqlite3OsDlClose(sqlite3_vfs *pVfs, void *pHandle){ |  | 
|  156   pVfs->xDlClose(pVfs, pHandle); |  | 
|  157 } |  | 
|  158 #endif /* SQLITE_OMIT_LOAD_EXTENSION */ |  | 
|  159 int sqlite3OsRandomness(sqlite3_vfs *pVfs, int nByte, char *zBufOut){ |  | 
|  160   return pVfs->xRandomness(pVfs, nByte, zBufOut); |  | 
|  161 } |  | 
|  162 int sqlite3OsSleep(sqlite3_vfs *pVfs, int nMicro){ |  | 
|  163   return pVfs->xSleep(pVfs, nMicro); |  | 
|  164 } |  | 
|  165 int sqlite3OsCurrentTime(sqlite3_vfs *pVfs, double *pTimeOut){ |  | 
|  166   return pVfs->xCurrentTime(pVfs, pTimeOut); |  | 
|  167 } |  | 
|  168  |  | 
|  169 int sqlite3OsOpenMalloc( |  | 
|  170   sqlite3_vfs *pVfs,  |  | 
|  171   const char *zFile,  |  | 
|  172   sqlite3_file **ppFile,  |  | 
|  173   int flags, |  | 
|  174   int *pOutFlags |  | 
|  175 ){ |  | 
|  176   int rc = SQLITE_NOMEM; |  | 
|  177   sqlite3_file *pFile; |  | 
|  178   pFile = (sqlite3_file *)sqlite3Malloc(pVfs->szOsFile); |  | 
|  179   if( pFile ){ |  | 
|  180     rc = sqlite3OsOpen(pVfs, zFile, pFile, flags, pOutFlags); |  | 
|  181     if( rc!=SQLITE_OK ){ |  | 
|  182       sqlite3_free(pFile); |  | 
|  183     }else{ |  | 
|  184       *ppFile = pFile; |  | 
|  185     } |  | 
|  186   } |  | 
|  187   return rc; |  | 
|  188 } |  | 
|  189 int sqlite3OsCloseFree(sqlite3_file *pFile){ |  | 
|  190   int rc = SQLITE_OK; |  | 
|  191   assert( pFile ); |  | 
|  192   rc = sqlite3OsClose(pFile); |  | 
|  193   sqlite3_free(pFile); |  | 
|  194   return rc; |  | 
|  195 } |  | 
|  196  |  | 
|  197 /* |  | 
|  198 ** This function is a wrapper around the OS specific implementation of |  | 
|  199 ** sqlite3_os_init(). The purpose of the wrapper is to provide the |  | 
|  200 ** ability to simulate a malloc failure, so that the handling of an |  | 
|  201 ** error in sqlite3_os_init() by the upper layers can be tested. |  | 
|  202 */ |  | 
|  203 int sqlite3OsInit(void){ |  | 
|  204   void *p = sqlite3_malloc(10); |  | 
|  205   if( p==0 ) return SQLITE_NOMEM; |  | 
|  206   sqlite3_free(p); |  | 
|  207   return sqlite3_os_init(); |  | 
|  208 } |  | 
|  209  |  | 
|  210 /* |  | 
|  211 ** The list of all registered VFS implementations. |  | 
|  212 */ |  | 
|  213 static sqlite3_vfs * SQLITE_WSD vfsList = 0; |  | 
|  214 #define vfsList GLOBAL(sqlite3_vfs *, vfsList) |  | 
|  215  |  | 
|  216 /* |  | 
|  217 ** Locate a VFS by name.  If no name is given, simply return the |  | 
|  218 ** first VFS on the list. |  | 
|  219 */ |  | 
|  220 sqlite3_vfs *sqlite3_vfs_find(const char *zVfs){ |  | 
|  221   sqlite3_vfs *pVfs = 0; |  | 
|  222 #if SQLITE_THREADSAFE |  | 
|  223   sqlite3_mutex *mutex; |  | 
|  224 #endif |  | 
|  225 #ifndef SQLITE_OMIT_AUTOINIT |  | 
|  226   int rc = sqlite3_initialize(); |  | 
|  227   if( rc ) return 0; |  | 
|  228 #endif |  | 
|  229 #if SQLITE_THREADSAFE |  | 
|  230   mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); |  | 
|  231 #endif |  | 
|  232   sqlite3_mutex_enter(mutex); |  | 
|  233   for(pVfs = vfsList; pVfs; pVfs=pVfs->pNext){ |  | 
|  234     if( zVfs==0 ) break; |  | 
|  235     if( strcmp(zVfs, pVfs->zName)==0 ) break; |  | 
|  236   } |  | 
|  237   sqlite3_mutex_leave(mutex); |  | 
|  238   return pVfs; |  | 
|  239 } |  | 
|  240  |  | 
|  241 /* |  | 
|  242 ** Unlink a VFS from the linked list |  | 
|  243 */ |  | 
|  244 static void vfsUnlink(sqlite3_vfs *pVfs){ |  | 
|  245   assert( sqlite3_mutex_held(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER)) ); |  | 
|  246   if( pVfs==0 ){ |  | 
|  247     /* No-op */ |  | 
|  248   }else if( vfsList==pVfs ){ |  | 
|  249     vfsList = pVfs->pNext; |  | 
|  250   }else if( vfsList ){ |  | 
|  251     sqlite3_vfs *p = vfsList; |  | 
|  252     while( p->pNext && p->pNext!=pVfs ){ |  | 
|  253       p = p->pNext; |  | 
|  254     } |  | 
|  255     if( p->pNext==pVfs ){ |  | 
|  256       p->pNext = pVfs->pNext; |  | 
|  257     } |  | 
|  258   } |  | 
|  259 } |  | 
|  260  |  | 
|  261 /* |  | 
|  262 ** Register a VFS with the system.  It is harmless to register the same |  | 
|  263 ** VFS multiple times.  The new VFS becomes the default if makeDflt is |  | 
|  264 ** true. |  | 
|  265 */ |  | 
|  266 int sqlite3_vfs_register(sqlite3_vfs *pVfs, int makeDflt){ |  | 
|  267   sqlite3_mutex *mutex = 0; |  | 
|  268 #ifndef SQLITE_OMIT_AUTOINIT |  | 
|  269   int rc = sqlite3_initialize(); |  | 
|  270   if( rc ) return rc; |  | 
|  271 #endif |  | 
|  272   mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); |  | 
|  273   sqlite3_mutex_enter(mutex); |  | 
|  274   vfsUnlink(pVfs); |  | 
|  275   if( makeDflt || vfsList==0 ){ |  | 
|  276     pVfs->pNext = vfsList; |  | 
|  277     vfsList = pVfs; |  | 
|  278   }else{ |  | 
|  279     pVfs->pNext = vfsList->pNext; |  | 
|  280     vfsList->pNext = pVfs; |  | 
|  281   } |  | 
|  282   assert(vfsList); |  | 
|  283   sqlite3_mutex_leave(mutex); |  | 
|  284   return SQLITE_OK; |  | 
|  285 } |  | 
|  286  |  | 
|  287 /* |  | 
|  288 ** Unregister a VFS so that it is no longer accessible. |  | 
|  289 */ |  | 
|  290 int sqlite3_vfs_unregister(sqlite3_vfs *pVfs){ |  | 
|  291 #if SQLITE_THREADSAFE |  | 
|  292   sqlite3_mutex *mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); |  | 
|  293 #endif |  | 
|  294   sqlite3_mutex_enter(mutex); |  | 
|  295   vfsUnlink(pVfs); |  | 
|  296   sqlite3_mutex_leave(mutex); |  | 
|  297   return SQLITE_OK; |  | 
|  298 } |  | 
| OLD | NEW |