aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/main.c65
-rw-r--r--src/os.c10
-rw-r--r--src/sqliteInt.h12
3 files changed, 55 insertions, 32 deletions
diff --git a/src/main.c b/src/main.c
index 520c16a4f..b2cfa119b 100644
--- a/src/main.c
+++ b/src/main.c
@@ -14,7 +14,7 @@
** other files are for internal use by SQLite and should not be
** accessed by users of the library.
**
-** $Id: main.c,v 1.462 2008/06/25 17:19:01 danielk1977 Exp $
+** $Id: main.c,v 1.463 2008/06/26 08:29:34 danielk1977 Exp $
*/
#include "sqliteInt.h"
#include <ctype.h>
@@ -66,26 +66,56 @@ char *sqlite3_temp_directory = 0;
** or for the first call after a call to sqlite3_shutdown.
*/
int sqlite3_initialize(void){
+ static int inProgress = 0;
int rc;
+
+ /* If SQLite is already initialized, this call is a no-op. */
if( sqlite3Config.isInit ) return SQLITE_OK;
+
+ /* Make sure the mutex system is initialized. */
rc = sqlite3MutexInit();
+
if( rc==SQLITE_OK ){
-#ifndef SQLITE_MUTEX_NOOP
- sqlite3_mutex *pMutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER);
-#endif
- sqlite3_mutex_enter(pMutex);
- if( sqlite3Config.isInit==0 ){
- sqlite3Config.isInit = 1;
- sqlite3StatusReset();
- if( rc==SQLITE_OK ) rc = sqlite3MallocInit();
- if( rc==SQLITE_OK ) rc = sqlite3_os_init();
- if( rc!=SQLITE_OK ){
- sqlite3Config.isInit = 0;
- }else{
- sqlite3Config.isInit = 2;
+
+ /* Initialize the malloc() system and the recursive pInitMutex mutex.
+ ** This operation is protected by the STATIC_MASTER mutex.
+ */
+ sqlite3_mutex *pMaster = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER);
+ sqlite3_mutex_enter(pMaster);
+ if( !sqlite3Config.isMallocInit ){
+ rc = sqlite3MallocInit();
+ }
+ if( rc==SQLITE_OK ){
+ sqlite3Config.isMallocInit = 1;
+ if( !sqlite3Config.pInitMutex ){
+ sqlite3Config.pInitMutex = sqlite3MutexAlloc(SQLITE_MUTEX_RECURSIVE);
+ if( sqlite3Config.bCoreMutex && !sqlite3Config.pInitMutex ){
+ rc = SQLITE_NOMEM;
+ }
}
}
- sqlite3_mutex_leave(pMutex);
+ sqlite3_mutex_leave(pMaster);
+ if( rc!=SQLITE_OK ){
+ return rc;
+ }
+
+ /* Enter the recursive pInitMutex mutex. After doing so, if the
+ ** sqlite3Config.isInit flag is true, then some other thread has
+ ** finished doing the initialization. If the inProgress flag is
+ ** true, then this function is being called recursively from within
+ ** the sqlite3_os_init() call below. In either case, exit early.
+ */
+ sqlite3_mutex_enter(sqlite3Config.pInitMutex);
+ if( sqlite3Config.isInit || inProgress ){
+ sqlite3_mutex_leave(sqlite3Config.pInitMutex);
+ return SQLITE_OK;
+ }
+ sqlite3StatusReset();
+ inProgress = 1;
+ rc = sqlite3_os_init();
+ inProgress = 0;
+ sqlite3Config.isInit = (rc==SQLITE_OK ? 1 : 0);
+ sqlite3_mutex_leave(sqlite3Config.pInitMutex);
}
return rc;
}
@@ -97,6 +127,9 @@ int sqlite3_initialize(void){
** routine is not threadsafe. Not by a long shot.
*/
int sqlite3_shutdown(void){
+ sqlite3_mutex_free(sqlite3Config.pInitMutex);
+ sqlite3Config.pInitMutex = 0;
+ sqlite3Config.isMallocInit = 0;
sqlite3_os_end();
sqlite3MallocEnd();
sqlite3MutexEnd();
@@ -119,7 +152,7 @@ int sqlite3_config(int op, ...){
/* sqlite3_config() shall return SQLITE_MISUSE if it is invoked while
** the SQLite library is in use. */
- if( sqlite3Config.isInit==2 ) return SQLITE_MISUSE;
+ if( sqlite3Config.isInit ) return SQLITE_MISUSE;
va_start(ap, op);
switch( op ){
diff --git a/src/os.c b/src/os.c
index a746cd726..3a58e77f0 100644
--- a/src/os.c
+++ b/src/os.c
@@ -13,7 +13,7 @@
** This file contains OS interface code that is common to all
** architectures.
**
-** $Id: os.c,v 1.116 2008/06/25 17:19:01 danielk1977 Exp $
+** $Id: os.c,v 1.117 2008/06/26 08:29:34 danielk1977 Exp $
*/
#define _SQLITE_OS_C_ 1
#include "sqliteInt.h"
@@ -243,18 +243,12 @@ static void vfsUnlink(sqlite3_vfs *pVfs){
** true.
*/
int sqlite3_vfs_register(sqlite3_vfs *pVfs, int makeDflt){
-#ifndef SQLITE_MUTEX_NOOP
sqlite3_mutex *mutex = 0;
-#endif
#ifndef SQLITE_OMIT_AUTOINIT
int rc = sqlite3_initialize();
if( rc ) return rc;
#endif
-#ifndef SQLITE_MUTEX_NOOP
- if( sqlite3Config.isInit!=1 ){
- mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER);
- }
-#endif
+ mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER);
sqlite3_mutex_enter(mutex);
vfsUnlink(pVfs);
if( makeDflt || vfsList==0 ){
diff --git a/src/sqliteInt.h b/src/sqliteInt.h
index 65c374d40..942396a6f 100644
--- a/src/sqliteInt.h
+++ b/src/sqliteInt.h
@@ -11,7 +11,7 @@
*************************************************************************
** Internal interface definitions for SQLite.
**
-** @(#) $Id: sqliteInt.h,v 1.729 2008/06/25 17:19:01 danielk1977 Exp $
+** @(#) $Id: sqliteInt.h,v 1.730 2008/06/26 08:29:34 danielk1977 Exp $
*/
#ifndef _SQLITEINT_H_
#define _SQLITEINT_H_
@@ -1734,12 +1734,6 @@ typedef struct {
** Structure containing global configuration data for the SQLite library.
**
** This structure also contains some state information.
-**
-** The Sqlite3Config.isInit variable indicates whether or not
-** sqlite3_initialize() has already been called or not. Initially, isInit
-** is 0. While sqlite3_initialize() is running, it is set to 1. After
-** sqlite3_initialize has successfully run, the Sqlite3Config.isInit variable
-** is set to 2. Calling sqlite3_shutdown() resets the value to 0.
*/
struct Sqlite3Config {
int bMemstat; /* True to enable memory status */
@@ -1756,7 +1750,9 @@ struct Sqlite3Config {
void *pPage; /* Page cache memory */
int szPage; /* Size of each page in pPage[] */
int nPage; /* Number of pages in pPage[] */
- int isInit; /* Initialization state */
+ int isInit; /* True after initialization has finished */
+ int isMallocInit; /* True after malloc is initialized */
+ sqlite3_mutex *pInitMutex; /* Mutex used by sqlite3_initialize() */
};
/*