Beispiel #1
0
/* deactivate SQLCipher, most imporantly decremeting the activation count and
   freeing the EVP structures on the final deactivation to ensure that 
   OpenSSL memory is cleaned up */
static int sqlcipher_openssl_deactivate(void *ctx) {
  CODEC_TRACE_MUTEX("sqlcipher_openssl_deactivate: entering static master mutex");
  sqlite3_mutex_enter(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));
  CODEC_TRACE_MUTEX("sqlcipher_openssl_deactivate: entered static master mutex");
  openssl_init_count--;

  if(openssl_init_count == 0) {
    if(openssl_external_init == 0) {
    /* if OpenSSL hasn't be initialized externally, and the counter reaches zero 
       after it's decremented, release EVP memory
       Note: this code will only be reached if OpensSSL_add_all_algorithms()
       is called by SQLCipher internally. This should prevent SQLCipher from 
       "cleaning up" openssl when it was initialized externally by the program */
#if (defined(OPENSSL_VERSION_NUMBER) && OPENSSL_VERSION_NUMBER < 0x10100000L) || (defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x20700000L)
      EVP_cleanup();
#endif
    } else {
      openssl_external_init = 0;
    }
#ifndef SQLCIPHER_OPENSSL_NO_MUTEX_RAND
    CODEC_TRACE_MUTEX("sqlcipher_openssl_deactivate: freeing openssl_rand_mutex %p", openssl_rand_mutex);
    sqlite3_mutex_free(openssl_rand_mutex);
    CODEC_TRACE_MUTEX("sqlcipher_openssl_deactivate: freed openssl_rand_mutex %p", openssl_rand_mutex);
    openssl_rand_mutex = NULL;
#endif
  }
  CODEC_TRACE_MUTEX("sqlcipher_openssl_deactivate: leaving static master mutex");
  sqlite3_mutex_leave(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));
  CODEC_TRACE_MUTEX("sqlcipher_openssl_deactivate: left static master mutex");
  return SQLITE_OK;
}
Beispiel #2
0
void sqlcipher_activate() {
  sqlite3_mutex_enter(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));

  if(sqlcipher_provider_mutex == NULL) {
    /* allocate a new mutex to guard access to the provider */
    sqlcipher_provider_mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_FAST);
  }

  /* check to see if there is a provider registered at this point
     if there no provider registered at this point, register the 
     default provider */
  if(sqlcipher_get_provider() == NULL) {
    sqlcipher_provider *p = sqlcipher_malloc(sizeof(sqlcipher_provider)); 
#if defined (SQLCIPHER_CRYPTO_CC)
    extern int sqlcipher_cc_setup(sqlcipher_provider *p);
    sqlcipher_cc_setup(p);
#elif defined (SQLCIPHER_CRYPTO_LIBTOMCRYPT)
    extern int sqlcipher_ltc_setup(sqlcipher_provider *p);
    sqlcipher_ltc_setup(p);
#elif defined (SQLCIPHER_CRYPTO_OPENSSL)
    extern int sqlcipher_openssl_setup(sqlcipher_provider *p);
    sqlcipher_openssl_setup(p);
#else
#error "NO DEFAULT SQLCIPHER CRYPTO PROVIDER DEFINED"
#endif
    sqlcipher_register_provider(p);
  }

  sqlcipher_activate_count++; /* increment activation count */

  sqlite3_mutex_leave(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));
}
Beispiel #3
0
/* activate and initialize sqlcipher. Most importantly, this will automatically
   intialize OpenSSL's EVP system if it hasn't already be externally. Note that 
   this function may be called multiple times as new codecs are intiialized. 
   Thus it performs some basic counting to ensure that only the last and final
   sqlcipher_openssl_deactivate() will free the EVP structures. 
*/
static int sqlcipher_openssl_activate(void *ctx) {
  /* initialize openssl and increment the internal init counter
     but only if it hasn't been initalized outside of SQLCipher by this program 
     e.g. on startup */
  sqlite3_mutex_enter(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));

  if(openssl_init_count == 0 && EVP_get_cipherbyname(CIPHER) != NULL) {
    /* if openssl has not yet been initialized by this library, but 
       a call to get_cipherbyname works, then the openssl library
       has been initialized externally already. */
    openssl_external_init = 1;
  }

  if(openssl_init_count == 0 && openssl_external_init == 0)  {
    /* if the library was not externally initialized, then should be now */
    OpenSSL_add_all_algorithms();
  } 

#ifndef SQLCIPHER_OPENSSL_NO_MUTEX_RAND
  if(openssl_rand_mutex == NULL) {
    /* allocate a mutex to guard against concurrent calls to RAND_bytes() */
    openssl_rand_mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_FAST);
  }
#endif

  openssl_init_count++; 
  sqlite3_mutex_leave(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));
  return SQLITE_OK;
}
Beispiel #4
0
/*
** Usage:   btree_open FILENAME NCACHE FLAGS
**
** Open a new database
*/
static int btree_open(
  void *NotUsed,
  Tcl_Interp *interp,    /* The TCL interpreter that invoked this command */
  int argc,              /* Number of arguments */
  const char **argv      /* Text of each argument */
){
  Btree *pBt;
  int rc, nCache, flags;
  char zBuf[100];
  if( argc!=4 ){
    Tcl_AppendResult(interp, "wrong # args: should be \"", argv[0],
       " FILENAME NCACHE FLAGS\"", 0);
    return TCL_ERROR;
  }
  if( Tcl_GetInt(interp, argv[2], &nCache) ) return TCL_ERROR;
  if( Tcl_GetInt(interp, argv[3], &flags) ) return TCL_ERROR;
  nRefSqlite3++;
  if( nRefSqlite3==1 ){
    sDb.pVfs = sqlite3_vfs_find(0);
    sDb.mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_RECURSIVE);
    sqlite3_mutex_enter(sDb.mutex);
  }
  rc = sqlite3BtreeOpen(argv[1], &sDb, &pBt, flags,
     SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE | SQLITE_OPEN_MAIN_DB);
  if( rc!=SQLITE_OK ){
    Tcl_AppendResult(interp, errorName(rc), 0);
    return TCL_ERROR;
  }
  sqlite3BtreeSetCacheSize(pBt, nCache);
  sqlite3_snprintf(sizeof(zBuf), zBuf,"%p", pBt);
  Tcl_AppendResult(interp, zBuf, 0);
  return TCL_OK;
}
static int sqlcipher_ltc_activate(void *ctx) {
  unsigned char random_buffer[FORTUNA_MAX_SZ];
#ifndef SQLCIPHER_LTC_NO_MUTEX_RAND
  if(ltc_rand_mutex == NULL){
    ltc_rand_mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_FAST);
  }
  sqlite3_mutex_enter(ltc_rand_mutex);
#endif
  sqlcipher_memset(random_buffer, 0, FORTUNA_MAX_SZ);
  if(ltc_init == 0) {
    if(register_prng(&fortuna_desc) < 0) return SQLITE_ERROR;
    if(register_cipher(&rijndael_desc) < 0) return SQLITE_ERROR;
    if(register_hash(&sha512_desc) < 0) return SQLITE_ERROR;
    if(register_hash(&sha256_desc) < 0) return SQLITE_ERROR;
    if(register_hash(&sha1_desc) < 0) return SQLITE_ERROR;
    if(fortuna_start(&prng) != CRYPT_OK) {
      return SQLITE_ERROR;
    }
    ltc_init = 1;
  }
  ltc_ref_count++;
#ifndef SQLCIPHER_TEST
  sqlite3_randomness(FORTUNA_MAX_SZ, random_buffer);
#endif
#ifndef SQLCIPHER_LTC_NO_MUTEX_RAND
  sqlite3_mutex_leave(ltc_rand_mutex);
#endif
  if(sqlcipher_ltc_add_random(ctx, random_buffer, FORTUNA_MAX_SZ) != SQLITE_OK) {
    return SQLITE_ERROR;
  }
  sqlcipher_memset(random_buffer, 0, FORTUNA_MAX_SZ);
  return SQLITE_OK;
}
Beispiel #6
0
/**
@SYMTestCaseID			PDS-SQLITE3-UT-4040
@SYMTestCaseDesc		SQLITE3 - mutex API tests.
						List of called SQLITE3 functions:
						 - sqlite3_mutex_alloc;
						 - sqlite3_mutex_enter;
						 - sqlite3_mutex_free;
						 - sqlite3_mutex_held;
						 - sqlite3_mutex_leave;
						 - sqlite3_mutex_notheld;
						 - sqlite3_mutex_try;
@SYMTestPriority		High
@SYMTestActions			SQLITE3 - mutex API tests.
@SYMTestExpectedResults Test must not fail
@SYMREQ					REQ10424
*/
static void TestSqliteMutexApi()
	{
	sqlite3_mutex* mtx = 0;
	int err;
	int type;
	
	TEST(TheDb != 0);
		
	for(type=SQLITE_MUTEX_FAST;type<=SQLITE_MUTEX_STATIC_LRU2;++type)
		{
		mtx = sqlite3_mutex_alloc(type);
		TEST(mtx != NULL);

		err = sqlite3_mutex_try(mtx);
		TEST(err == SQLITE_BUSY || err == SQLITE_OK);

		sqlite3_mutex_enter(mtx);

		sqlite3_mutex_leave(mtx);
		
		if(type <= SQLITE_MUTEX_RECURSIVE)
			{
			sqlite3_mutex_free(mtx);
			}
		mtx = 0;
		}
	}
Beispiel #7
0
/* activate and initialize sqlcipher. Most importantly, this will automatically
   intialize OpenSSL's EVP system if it hasn't already be externally. Note that 
   this function may be called multiple times as new codecs are intiialized. 
   Thus it performs some basic counting to ensure that only the last and final
   sqlcipher_openssl_deactivate() will free the EVP structures. 
*/
static int sqlcipher_openssl_activate(void *ctx) {
  /* initialize openssl and increment the internal init counter
     but only if it hasn't been initalized outside of SQLCipher by this program 
     e.g. on startup */
  CODEC_TRACE_MUTEX("sqlcipher_openssl_activate: entering static master mutex");
  sqlite3_mutex_enter(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));
  CODEC_TRACE_MUTEX("sqlcipher_openssl_activate: entered static master mutex");

  if(openssl_init_count == 0 && EVP_get_cipherbyname(OPENSSL_CIPHER) != NULL) {
    /* if openssl has not yet been initialized by this library, but 
       a call to get_cipherbyname works, then the openssl library
       has been initialized externally already. */
    openssl_external_init = 1;
  }

#ifdef SQLCIPHER_FIPS
  if(!FIPS_mode()){
    if(!FIPS_mode_set(1)){
      ERR_load_crypto_strings();
      ERR_print_errors_fp(stderr);
    }
  }
#endif

  if(openssl_init_count == 0 && openssl_external_init == 0)  {
    /* if the library was not externally initialized, then should be now */
#if (defined(OPENSSL_VERSION_NUMBER) && OPENSSL_VERSION_NUMBER < 0x10100000L) || (defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x20700000L)
    OpenSSL_add_all_algorithms();
#endif
  } 

#ifndef SQLCIPHER_OPENSSL_NO_MUTEX_RAND
  if(openssl_rand_mutex == NULL) {
    /* allocate a mutex to guard against concurrent calls to RAND_bytes() */
    CODEC_TRACE_MUTEX("sqlcipher_openssl_activate: allocating openssl_rand_mutex");
    openssl_rand_mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_FAST);
    CODEC_TRACE_MUTEX("sqlcipher_openssl_activate: allocated openssl_rand_mutex %p", openssl_rand_mutex);
  }
#endif

  openssl_init_count++; 
  CODEC_TRACE_MUTEX("sqlcipher_openssl_activate: leaving static master mutex");
  sqlite3_mutex_leave(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));
  CODEC_TRACE_MUTEX("sqlcipher_openssl_activate: left static master mutex");
  return SQLITE_OK;
}
Beispiel #8
0
/*
** Implementation of the sqlite3_pcache.xInit method.
*/
static int pcache1Init(void *NotUsed){
  UNUSED_PARAMETER(NotUsed);
  memset(&pcache1, 0, sizeof(pcache1));
  if( sqlite3GlobalConfig.bCoreMutex ){
    pcache1.mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_LRU);
  }
  return SQLITE_OK;
}
Beispiel #9
0
void init()
{
    d_owner->readonly = true;
    d_owner->creatable = false;
    
    sqlite3_initialize();
    db = NULL;
    mtx = sqlite3_mutex_alloc(SQLITE_MUTEX_FAST);
}
/*
** CAPI: Initialize the multiplex VFS shim - sqlite3_multiplex_initialize()
**
** Use the VFS named zOrigVfsName as the VFS that does the actual work.  
** Use the default if zOrigVfsName==NULL.  
**
** The multiplex VFS shim is named "multiplex".  It will become the default
** VFS if makeDefault is non-zero.
**
** THIS ROUTINE IS NOT THREADSAFE.  Call this routine exactly once
** during start-up.
*/
int sqlite3_multiplex_initialize(const char *zOrigVfsName, int makeDefault){
  sqlite3_vfs *pOrigVfs;
  if( gMultiplex.isInitialized ) return SQLITE_MISUSE;
  pOrigVfs = sqlite3_vfs_find(zOrigVfsName);
  if( pOrigVfs==0 ) return SQLITE_ERROR;
  assert( pOrigVfs!=&gMultiplex.sThisVfs );
  gMultiplex.pMutex = sqlite3_mutex_alloc(SQLITE_MUTEX_FAST);
  if( !gMultiplex.pMutex ){
    return SQLITE_NOMEM;
  }
  gMultiplex.pGroups = NULL;
  gMultiplex.isInitialized = 1;
  gMultiplex.pOrigVfs = pOrigVfs;
  gMultiplex.sThisVfs = *pOrigVfs;
  gMultiplex.sThisVfs.szOsFile += sizeof(multiplexConn);
  gMultiplex.sThisVfs.zName = SQLITE_MULTIPLEX_VFS_NAME;
  gMultiplex.sThisVfs.xOpen = multiplexOpen;
  gMultiplex.sThisVfs.xDelete = multiplexDelete;
  gMultiplex.sThisVfs.xAccess = multiplexAccess;
  gMultiplex.sThisVfs.xFullPathname = multiplexFullPathname;
  gMultiplex.sThisVfs.xDlOpen = multiplexDlOpen;
  gMultiplex.sThisVfs.xDlError = multiplexDlError;
  gMultiplex.sThisVfs.xDlSym = multiplexDlSym;
  gMultiplex.sThisVfs.xDlClose = multiplexDlClose;
  gMultiplex.sThisVfs.xRandomness = multiplexRandomness;
  gMultiplex.sThisVfs.xSleep = multiplexSleep;
  gMultiplex.sThisVfs.xCurrentTime = multiplexCurrentTime;
  gMultiplex.sThisVfs.xGetLastError = multiplexGetLastError;
  gMultiplex.sThisVfs.xCurrentTimeInt64 = multiplexCurrentTimeInt64;

  gMultiplex.sIoMethodsV1.iVersion = 1;
  gMultiplex.sIoMethodsV1.xClose = multiplexClose;
  gMultiplex.sIoMethodsV1.xRead = multiplexRead;
  gMultiplex.sIoMethodsV1.xWrite = multiplexWrite;
  gMultiplex.sIoMethodsV1.xTruncate = multiplexTruncate;
  gMultiplex.sIoMethodsV1.xSync = multiplexSync;
  gMultiplex.sIoMethodsV1.xFileSize = multiplexFileSize;
  gMultiplex.sIoMethodsV1.xLock = multiplexLock;
  gMultiplex.sIoMethodsV1.xUnlock = multiplexUnlock;
  gMultiplex.sIoMethodsV1.xCheckReservedLock = multiplexCheckReservedLock;
  gMultiplex.sIoMethodsV1.xFileControl = multiplexFileControl;
  gMultiplex.sIoMethodsV1.xSectorSize = multiplexSectorSize;
  gMultiplex.sIoMethodsV1.xDeviceCharacteristics =
                                            multiplexDeviceCharacteristics;
  gMultiplex.sIoMethodsV2 = gMultiplex.sIoMethodsV1;
  gMultiplex.sIoMethodsV2.iVersion = 2;
  gMultiplex.sIoMethodsV2.xShmMap = multiplexShmMap;
  gMultiplex.sIoMethodsV2.xShmLock = multiplexShmLock;
  gMultiplex.sIoMethodsV2.xShmBarrier = multiplexShmBarrier;
  gMultiplex.sIoMethodsV2.xShmUnmap = multiplexShmUnmap;
  sqlite3_vfs_register(&gMultiplex.sThisVfs, makeDefault);

  sqlite3_auto_extension((void*)multiplexFuncInit);

  return SQLITE_OK;
}
Beispiel #11
0
/*
** Enter the mutex mem.mutex. Allocate it if it is not already allocated.
**
** Also:  Initialize the memory allocation subsystem the first time
** this routine is called.
*/
static void memsys3Enter(void){
  if( mem.mutex==0 ){
    mem.mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MEM);
    mem.aPool[0].u.hdr.size = SQLITE_MEMORY_SIZE/8;
    mem.aPool[SQLITE_MEMORY_SIZE/8].u.hdr.prevSize = SQLITE_MEMORY_SIZE/8;
    mem.iMaster = 1;
    mem.szMaster = SQLITE_MEMORY_SIZE/8;
    mem.mnMaster = mem.szMaster;
  }
  sqlite3_mutex_enter(mem.mutex);
}
Beispiel #12
0
void sqlcipher_deactivate() {
  sqlite3_mutex_enter(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));
  sqlcipher_activate_count--;
  /* if no connections are using sqlcipher, cleanup globals */
  if(sqlcipher_activate_count < 1) {
    sqlite3_mutex_enter(sqlcipher_provider_mutex);
    if(default_provider != NULL) {
      sqlcipher_free(default_provider, sizeof(sqlcipher_provider));
      default_provider = NULL;
    }
    sqlite3_mutex_leave(sqlcipher_provider_mutex);
    
    /* last connection closed, free provider mutex*/
    sqlite3_mutex_free(sqlcipher_provider_mutex); 
    sqlcipher_provider_mutex = NULL;

    sqlcipher_activate_count = 0; /* reset activation count */
  }
  sqlite3_mutex_leave(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));
}
Beispiel #13
0
/*************************************************** General Interfaces ******
**
** Initialize and shutdown the page cache subsystem. Neither of these 
** functions are threadsafe.
*/
int sqlite3PcacheInitialize(void){
  assert( pcache_g.isInit==0 );
  memset(&pcache_g, 0, sizeof(pcache));
  if( sqlite3GlobalConfig.bCoreMutex ){
    /* No need to check the return value of sqlite3_mutex_alloc(). 
    ** Allocating a static mutex cannot fail.
    */
    pcache_g.mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_LRU);
  }
  pcache_g.isInit = 1;
  return SQLITE_OK;
}
Beispiel #14
0
/* deactivate SQLCipher, most imporantly decremeting the activation count and
   freeing the EVP structures on the final deactivation to ensure that 
   OpenSSL memory is cleaned up */
static int sqlcipher_openssl_deactivate(void *ctx) {
  sqlite3_mutex_enter(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));
  openssl_init_count--;

  if(openssl_init_count == 0) {
    if(openssl_external_init == 0) {
    /* if OpenSSL hasn't be initialized externally, and the counter reaches zero 
       after it's decremented, release EVP memory
       Note: this code will only be reached if OpensSSL_add_all_algorithms()
       is called by SQLCipher internally. This should prevent SQLCipher from 
       "cleaning up" openssl when it was initialized externally by the program */
      EVP_cleanup();
    }
#ifndef SQLCIPHER_OPENSSL_NO_MUTEX_RAND
    sqlite3_mutex_free(openssl_rand_mutex);
    openssl_rand_mutex = NULL;
#endif
  }
  sqlite3_mutex_leave(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER));
  return SQLITE_OK;
}
Beispiel #15
0
/*
** Return N random bytes.
*/
void sqlite3_randomness(int N, void *pBuf){
  unsigned char *zBuf = pBuf;
  static sqlite3_mutex *mutex = 0;
  if( mutex==0 ){
    mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_PRNG);
  }
  sqlite3_mutex_enter(mutex);
  while( N-- ){
    *(zBuf++) = randomByte();
  }
  sqlite3_mutex_leave(mutex);
}
Beispiel #16
0
int sqlite3_embedded_initialize(const char* zOrigVfsName, int makeDefault) {
  sqlite3_vfs* pOrigVfs;
  if (gEmbedded.isInitialized) return SQLITE_MISUSE;
  pOrigVfs = sqlite3_vfs_find(zOrigVfsName);
  if (pOrigVfs==0) return SQLITE_ERROR;
  assert(pOrigVfs!=&gEmbedded.sThisVfs);
  gEmbedded.pMutex = sqlite3_mutex_alloc(SQLITE_MUTEX_FAST);
  if (!gEmbedded.pMutex) {
    return SQLITE_NOMEM;
  }

  gEmbedded.isInitialized = 1;
  gEmbedded.pOrigVfs = pOrigVfs;
  gEmbedded.sThisVfs = *pOrigVfs;
  gEmbedded.sThisVfs.szOsFile += sizeof(embeddedConn);
  gEmbedded.sThisVfs.zName = "embedded";
  gEmbedded.sThisVfs.xOpen = embeddedOpen;
  gEmbedded.sThisVfs.xDelete = embeddedDelete;
  gEmbedded.sThisVfs.xAccess = embeddedAccess;
  gEmbedded.sThisVfs.xFullPathname = embeddedFullPathname;
  gEmbedded.sThisVfs.xDlOpen = embeddedDlOpen;
  gEmbedded.sThisVfs.xDlError = embeddedDlError;
  gEmbedded.sThisVfs.xDlSym = embeddedDlSym;
  gEmbedded.sThisVfs.xDlClose = embeddedDlClose;
  gEmbedded.sThisVfs.xRandomness = embeddedRandomness;
  gEmbedded.sThisVfs.xSleep = embeddedSleep;
  gEmbedded.sThisVfs.xCurrentTime = embeddedCurrentTime;
  gEmbedded.sThisVfs.xGetLastError = embeddedGetLastError;
  gEmbedded.sThisVfs.xCurrentTimeInt64 = embeddedCurrentTimeInt64;

  gEmbedded.sIoMethodsV1.iVersion = 1;
  gEmbedded.sIoMethodsV1.xClose = embeddedClose;
  gEmbedded.sIoMethodsV1.xRead = embeddedRead;
  gEmbedded.sIoMethodsV1.xWrite = embeddedWrite;
  gEmbedded.sIoMethodsV1.xTruncate = embeddedTruncate;
  gEmbedded.sIoMethodsV1.xSync = embeddedSync;
  gEmbedded.sIoMethodsV1.xFileSize = embeddedFileSize;
  gEmbedded.sIoMethodsV1.xLock = embeddedLock;
  gEmbedded.sIoMethodsV1.xUnlock = embeddedUnlock;
  gEmbedded.sIoMethodsV1.xCheckReservedLock = embeddedCheckReservedLock;
  gEmbedded.sIoMethodsV1.xFileControl = embeddedFileControl;
  gEmbedded.sIoMethodsV1.xSectorSize = embeddedSectorSize;
  gEmbedded.sIoMethodsV1.xDeviceCharacteristics =
    embeddedDeviceCharacteristics;

  sqlite3_vfs_register(&gEmbedded.sThisVfs, makeDefault);

  return SQLITE_OK;
}
Beispiel #17
0
int spmemvfs_env_init()
{
	int ret = 0;

	if( NULL == g_spmemvfs_env ) {
		spmemvfs_cb_t cb;

		g_spmemvfs_env = (spmemvfs_env_t*)calloc( sizeof( spmemvfs_env_t ), 1 );
		g_spmemvfs_env->mutex = sqlite3_mutex_alloc( SQLITE_MUTEX_FAST );

		cb.arg = g_spmemvfs_env;
		cb.load = load_cb;

		ret = spmemvfs_init( &cb );
	}

	return ret;
}
Beispiel #18
0
/*
** Initialize the quota VFS shim.  Use the VFS named zOrigVfsName
** as the VFS that does the actual work.  Use the default if
** zOrigVfsName==NULL.  
**
** The quota VFS shim is named "quota".  It will become the default
** VFS if makeDefault is non-zero.
**
** THIS ROUTINE IS NOT THREADSAFE.  Call this routine exactly once
** during start-up.
*/
int sqlite3_quota_initialize(const char *zOrigVfsName, int makeDefault){
  sqlite3_vfs *pOrigVfs;
  if( gQuota.isInitialized ) return SQLITE_MISUSE;
  pOrigVfs = sqlite3_vfs_find(zOrigVfsName);
  if( pOrigVfs==0 ) return SQLITE_ERROR;
  assert( pOrigVfs!=&gQuota.sThisVfs );
  gQuota.pMutex = sqlite3_mutex_alloc(SQLITE_MUTEX_FAST);
  if( !gQuota.pMutex ){
    return SQLITE_NOMEM;
  }
  gQuota.isInitialized = 1;
  gQuota.pOrigVfs = pOrigVfs;
  gQuota.sThisVfs = *pOrigVfs;
  gQuota.sThisVfs.xOpen = quotaOpen;
  gQuota.sThisVfs.xDelete = quotaDelete;
  gQuota.sThisVfs.szOsFile += sizeof(quotaConn);
  gQuota.sThisVfs.zName = "quota";
  gQuota.sIoMethodsV1.iVersion = 1;
  gQuota.sIoMethodsV1.xClose = quotaClose;
  gQuota.sIoMethodsV1.xRead = quotaRead;
  gQuota.sIoMethodsV1.xWrite = quotaWrite;
  gQuota.sIoMethodsV1.xTruncate = quotaTruncate;
  gQuota.sIoMethodsV1.xSync = quotaSync;
  gQuota.sIoMethodsV1.xFileSize = quotaFileSize;
  gQuota.sIoMethodsV1.xLock = quotaLock;
  gQuota.sIoMethodsV1.xUnlock = quotaUnlock;
  gQuota.sIoMethodsV1.xCheckReservedLock = quotaCheckReservedLock;
  gQuota.sIoMethodsV1.xFileControl = quotaFileControl;
  gQuota.sIoMethodsV1.xSectorSize = quotaSectorSize;
  gQuota.sIoMethodsV1.xDeviceCharacteristics = quotaDeviceCharacteristics;
  gQuota.sIoMethodsV2 = gQuota.sIoMethodsV1;
  gQuota.sIoMethodsV2.iVersion = 2;
  gQuota.sIoMethodsV2.xShmMap = quotaShmMap;
  gQuota.sIoMethodsV2.xShmLock = quotaShmLock;
  gQuota.sIoMethodsV2.xShmBarrier = quotaShmBarrier;
  gQuota.sIoMethodsV2.xShmUnmap = quotaShmUnmap;
  sqlite3_vfs_register(&gQuota.sThisVfs, makeDefault);
  return SQLITE_OK;
}
Beispiel #19
0
/*
** Enter the mutex mem.mutex. Allocate it if it is not already allocated.
*/
static void enterMem(void) {
    if( mem.mutex==0 ) {
        mem.mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MEM);
    }
    sqlite3_mutex_enter(mem.mutex);
}
static void leaveJtMutex(void){
  sqlite3_mutex_leave(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_PRNG));
}
/*
** Functions to obtain and relinquish a mutex to protect g.pList. The
** STATIC_PRNG mutex is reused, purely for the sake of convenience.
*/
static void enterJtMutex(void){
  sqlite3_mutex_enter(sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_PRNG));
}
Beispiel #22
0
int yap_vfs_shim_register(const char *yap_vfs_name,        // Name for yap VFS shim
                          const char *underlying_vfs_name) // Name of the underlying VFS
{
	// We do this here because this method is typically only called once.
	// And is expected to be called in a thread-safe manner.
	if (yap_file_wal_linked_list_mutex == NULL) {
		yap_file_wal_linked_list_mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_FAST);
	}
	
	if (yap_vfs_name == NULL)
	{
		// yap_vfs_name is required
		return SQLITE_MISUSE;
	}
	
	sqlite3_vfs *realVFS = sqlite3_vfs_find(underlying_vfs_name);
	if (realVFS == NULL) {
		return SQLITE_NOTFOUND;
	}
	
	size_t baseLen = sizeof(yap_vfs);
	size_t nameLen = strlen(yap_vfs_name) + 1;
	
	yap_vfs *yapVFS = sqlite3_malloc((int)(baseLen + nameLen));
	if (yapVFS == NULL) {
		return SQLITE_NOMEM;
	}
	memset(yapVFS, 0, (int)(baseLen + nameLen));
	
	// yapVFS memory = {struct yap_vfs, char[nameLen]}
	
	char *name = (char *)&yapVFS[1];
	strncpy(name, yap_vfs_name, nameLen);
	
	yapVFS->base.iVersion   = realVFS->iVersion;
	yapVFS->base.szOsFile   = sizeof(yap_file) + realVFS->szOsFile;
	yapVFS->base.mxPathname = realVFS->mxPathname;
	yapVFS->base.zName      = name;
	
	yapVFS->base.xOpen         = yap_vfs_open;
	yapVFS->base.xDelete       = yap_vfs_delete;
	yapVFS->base.xAccess       = yap_vfs_access;
	yapVFS->base.xFullPathname = yap_vfs_fullPathname;
	yapVFS->base.xDlOpen       = realVFS->xDlOpen  ? yap_vfs_dlOpen  : NULL;
	yapVFS->base.xDlError      = realVFS->xDlError ? yap_vfs_dlError : NULL;
	yapVFS->base.xDlSym        = realVFS->xDlSym   ? yap_vfs_dlSym   : NULL;
	yapVFS->base.xDlClose      = realVFS->xDlClose ? yap_vfs_dlClose : NULL;
	yapVFS->base.xRandomness   = yap_vfs_randomness;
	yapVFS->base.xSleep        = yap_vfs_sleep;
	yapVFS->base.xCurrentTime  = yap_vfs_currentTime;
	yapVFS->base.xGetLastError = realVFS->xGetLastError ? yap_vfs_getLastError : NULL;
	
	if (realVFS->iVersion >= 2)
	{
		yapVFS->base.xCurrentTimeInt64 = realVFS->xCurrentTimeInt64 ? yap_vfs_currentTimeInt64 : NULL;
		
		if (realVFS->iVersion >= 3)
		{
			yapVFS->base.xSetSystemCall  = realVFS->xSetSystemCall  ? yap_vfs_setSystemCall  : NULL;
			yapVFS->base.xGetSystemCall  = realVFS->xGetSystemCall  ? yap_vfs_getSystemCall  : NULL;
			yapVFS->base.xNextSystemCall = realVFS->xNextSystemCall ? yap_vfs_nextSystemCall : NULL;
		}
	}
	
	yapVFS->pReal = realVFS;
	
	int makeDefault = 0; // NO
	int result = sqlite3_vfs_register((sqlite3_vfs *)yapVFS, makeDefault);
	if (result != SQLITE_OK)
	{
		sqlite3_free(yapVFS);
	}
	
	return result;
}
Beispiel #23
0
/*
** This routine does the work of opening a database on behalf of
** sqlite3_open() and sqlite3_open16(). The database filename "zFilename"  
** is UTF-8 encoded.
*/
static int openDatabase(
  const char *zFilename, /* Database filename UTF-8 encoded */
  sqlite3 **ppDb,        /* OUT: Returned database handle */
  unsigned flags,        /* Operational flags */
  const char *zVfs       /* Name of the VFS to use */
){
  sqlite3 *db;
  int rc;
  CollSeq *pColl;


  /* Allocate the sqlite data structure */
  db = (sqlite3*)sqlite3MallocZero( sizeof(sqlite3) );
  if( db==0 ) goto opendb_out;
  db->mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_RECURSIVE);
  if( db->mutex==0 ){
    sqlite3_free(db);
    db = 0;
    goto opendb_out;
  }
  sqlite3_mutex_enter(db->mutex);
  db->errMask = 0xff;
  db->priorNewRowid = 0;
  db->nDb = 2;
  db->magic = SQLITE_MAGIC_BUSY;
  db->aDb = db->aDbStatic;
  db->autoCommit = 1;
  db->nextAutovac = -1;
  db->flags |= SQLITE_ShortColNames
#if SQLITE_DEFAULT_FILE_FORMAT<4
                 | SQLITE_LegacyFileFmt
#endif
#ifdef SQLITE_ENABLE_LOAD_EXTENSION
                 | SQLITE_LoadExtension
#endif
      ;
  sqlite3HashInit(&db->aFunc, SQLITE_HASH_STRING, 0);
  sqlite3HashInit(&db->aCollSeq, SQLITE_HASH_STRING, 0);
#ifndef SQLITE_OMIT_VIRTUALTABLE
  sqlite3HashInit(&db->aModule, SQLITE_HASH_STRING, 0);
#endif

  db->pVfs = sqlite3OsDefaultVfs();//sqlite3_vfs_find(zVfs);
  if( !db->pVfs ){
    rc = SQLITE_ERROR;
    db->magic = SQLITE_MAGIC_CLOSED;
    sqlite3Error(db, rc, "no such vfs: %s", (zVfs?zVfs:"(null)"));
    goto opendb_out;
  }

  /* Add the default collation sequence BINARY. BINARY works for both UTF-8
  ** and UTF-16, so add a version for each to avoid any unnecessary
  ** conversions. The only error that can occur here is a malloc() failure.
  */
  if( createCollation(db, "BINARY", SQLITE_UTF8, 0, binCollFunc, 0) ||
      createCollation(db, "BINARY", SQLITE_UTF16BE, 0, binCollFunc, 0) ||
      createCollation(db, "BINARY", SQLITE_UTF16LE, 0, binCollFunc, 0) ||
      (db->pDfltColl = sqlite3FindCollSeq(db, SQLITE_UTF8, "BINARY", 6, 0))==0 
  ){
    assert( db->mallocFailed );
    db->magic = SQLITE_MAGIC_CLOSED;
    goto opendb_out;
  }

  /* Also add a UTF-8 case-insensitive collation sequence. */
  createCollation(db, "NOCASE", SQLITE_UTF8, 0, nocaseCollatingFunc, 0);

  /* Set flags on the built-in collating sequences */
  db->pDfltColl->type = SQLITE_COLL_BINARY;
  pColl = sqlite3FindCollSeq(db, SQLITE_UTF8, "NOCASE", 6, 0);
  if( pColl ){
    pColl->type = SQLITE_COLL_NOCASE;
  }

  /* Open the backend database driver */
  db->openFlags = flags;
  rc = sqlite3BtreeFactory(db, zFilename, 0, SQLITE_DEFAULT_CACHE_SIZE, 
                           flags | SQLITE_OPEN_MAIN_DB,
                           &db->aDb[0].pBt);
  if( rc!=SQLITE_OK ){
    sqlite3Error(db, rc, 0);
    db->magic = SQLITE_MAGIC_CLOSED;
    goto opendb_out;
  }
  db->aDb[0].pSchema = sqlite3SchemaGet(db, db->aDb[0].pBt);
  db->aDb[1].pSchema = sqlite3SchemaGet(db, 0);


  /* The default safety_level for the main database is 'full'; for the temp
  ** database it is 'NONE'. This matches the pager layer defaults.  
  */
  db->aDb[0].zName = "main";
  db->aDb[0].safety_level = 3;
#ifndef SQLITE_OMIT_TEMPDB
  db->aDb[1].zName = "temp";
  db->aDb[1].safety_level = 1;
#endif

  db->magic = SQLITE_MAGIC_OPEN;
  if( db->mallocFailed ){
    goto opendb_out;
  }

  /* Register all built-in functions, but do not attempt to read the
  ** database schema yet. This is delayed until the first time the database
  ** is accessed.
  */
  sqlite3Error(db, SQLITE_OK, 0);
  sqlite3RegisterBuiltinFunctions(db);

  /* Load automatic extensions - extensions that have been registered
  ** using the sqlite3_automatic_extension() API.
  */
  (void)sqlite3AutoLoadExtensions(db);
  if( sqlite3_errcode(db)!=SQLITE_OK ){
    goto opendb_out;
  }

#ifdef SQLITE_ENABLE_FTS1
  if( !db->mallocFailed ){
    extern int sqlite3Fts1Init(sqlite3*);
    rc = sqlite3Fts1Init(db);
  }
#endif

#ifdef SQLITE_ENABLE_FTS2
  if( !db->mallocFailed && rc==SQLITE_OK ){
    extern int sqlite3Fts2Init(sqlite3*);
    rc = sqlite3Fts2Init(db);
  }
#endif

#ifdef SQLITE_ENABLE_FTS3
  if( !db->mallocFailed && rc==SQLITE_OK ){
    extern int sqlite3Fts3Init(sqlite3*);
    rc = sqlite3Fts3Init(db);
  }
#endif

#ifdef SQLITE_ENABLE_ICU
  if( !db->mallocFailed && rc==SQLITE_OK ){
    extern int sqlite3IcuInit(sqlite3*);
    rc = sqlite3IcuInit(db);
  }
#endif
  sqlite3Error(db, rc, 0);

  /* -DSQLITE_DEFAULT_LOCKING_MODE=1 makes EXCLUSIVE the default locking
  ** mode.  -DSQLITE_DEFAULT_LOCKING_MODE=0 make NORMAL the default locking
  ** mode.  Doing nothing at all also makes NORMAL the default.
  */
#ifdef SQLITE_DEFAULT_LOCKING_MODE
  db->dfltLockMode = SQLITE_DEFAULT_LOCKING_MODE;
  sqlite3PagerLockingMode(sqlite3BtreePager(db->aDb[0].pBt),
                          SQLITE_DEFAULT_LOCKING_MODE);
#endif

opendb_out:
  if( db && db->mutex ){
    sqlite3_mutex_leave(db->mutex);
  }
  if( SQLITE_NOMEM==(rc = sqlite3_errcode(db)) ){
    sqlite3_close(db);
    db = 0;
  }
  *ppDb = db;
  return sqlite3ApiExit(0, rc);
}