diff options
author | danielk1977 <danielk1977@noemail.net> | 2008-06-18 09:45:56 +0000 |
---|---|---|
committer | danielk1977 <danielk1977@noemail.net> | 2008-06-18 09:45:56 +0000 |
commit | 1a9ed0b27a97371d3db4d381f3258071ff5c71e8 (patch) | |
tree | f69687413d11a768ebfa587f43759117e396c5f9 /src | |
parent | 5f09d3e611f2b88f168d1ce6631d4e4d83a6115c (diff) | |
download | sqlite-1a9ed0b27a97371d3db4d381f3258071ff5c71e8.tar.gz sqlite-1a9ed0b27a97371d3db4d381f3258071ff5c71e8.zip |
Add some test infrastructure and cases for the new mutex api. (CVS 5230)
FossilOrigin-Name: 262baee9952b28afe5dc77eb7365ebb11a480906
Diffstat (limited to 'src')
-rw-r--r-- | src/main.c | 7 | ||||
-rw-r--r-- | src/mutex.c | 6 | ||||
-rw-r--r-- | src/mutex_unix.c | 4 | ||||
-rw-r--r-- | src/sqlite.h.in | 5 | ||||
-rw-r--r-- | src/tclsqlite.c | 4 | ||||
-rw-r--r-- | src/test_mutex.c | 269 |
6 files changed, 286 insertions, 9 deletions
diff --git a/src/main.c b/src/main.c index af2576e45..54b13fa8b 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.446 2008/06/17 18:57:49 danielk1977 Exp $ +** $Id: main.c,v 1.447 2008/06/18 09:45:56 danielk1977 Exp $ */ #include "sqliteInt.h" #include <ctype.h> @@ -156,6 +156,11 @@ int sqlite3_config(int op, ...){ sqlite3Config.mutex = *va_arg(ap, sqlite3_mutex_methods*); break; } + case SQLITE_CONFIG_GETMUTEX: { + /* Retrieve the current mutex implementation */ + *va_arg(ap, sqlite3_mutex_methods*) = sqlite3Config.mutex; + break; + } case SQLITE_CONFIG_MEMSTATUS: { /* Enable or disable the malloc status collection */ sqlite3Config.bMemstat = va_arg(ap, int); diff --git a/src/mutex.c b/src/mutex.c index 46bb82d71..a9fe68fa7 100644 --- a/src/mutex.c +++ b/src/mutex.c @@ -19,7 +19,7 @@ ** implementation is suitable for testing. ** debugging purposes ** -** $Id: mutex.c,v 1.22 2008/06/17 18:57:49 danielk1977 Exp $ +** $Id: mutex.c,v 1.23 2008/06/18 09:45:56 danielk1977 Exp $ */ #include "sqliteInt.h" @@ -237,9 +237,9 @@ static int noopMutexTry(sqlite3_mutex *p){ ** is not currently allocated. SQLite will never do either. */ static void noopMutexLeave(sqlite3_mutex *p){ - assert( sqlite3_mutex_held(p) ); + assert( noopMutexHeld(p) ); p->cnt--; - assert( p->id==SQLITE_MUTEX_RECURSIVE || sqlite3_mutex_notheld(p) ); + assert( p->id==SQLITE_MUTEX_RECURSIVE || noopMutexNotheld(p) ); } sqlite3_mutex_methods *sqlite3DefaultMutex(void){ diff --git a/src/mutex_unix.c b/src/mutex_unix.c index 2ec52a1a9..7b5ca7616 100644 --- a/src/mutex_unix.c +++ b/src/mutex_unix.c @@ -11,7 +11,7 @@ ************************************************************************* ** This file contains the C functions that implement mutexes for pthreads ** -** $Id: mutex_unix.c,v 1.9 2008/06/17 17:21:18 danielk1977 Exp $ +** $Id: mutex_unix.c,v 1.10 2008/06/18 09:45:56 danielk1977 Exp $ */ #include "sqliteInt.h" @@ -285,7 +285,7 @@ static int pthreadMutexTry(sqlite3_mutex *p){ ** is not currently allocated. SQLite will never do either. */ static void pthreadMutexLeave(sqlite3_mutex *p){ - assert( sqlite3_mutex_held(p) ); + assert( pthreadMutexHeld(p) ); p->nRef--; assert( p->nRef==0 || p->id==SQLITE_MUTEX_RECURSIVE ); diff --git a/src/sqlite.h.in b/src/sqlite.h.in index d9b8921aa..352fceafe 100644 --- a/src/sqlite.h.in +++ b/src/sqlite.h.in @@ -30,7 +30,7 @@ ** the version number) and changes its name to "sqlite3.h" as ** part of the build process. ** -** @(#) $Id: sqlite.h.in,v 1.331 2008/06/17 18:57:49 danielk1977 Exp $ +** @(#) $Id: sqlite.h.in,v 1.332 2008/06/18 09:45:56 danielk1977 Exp $ */ #ifndef _SQLITE3_H_ #define _SQLITE3_H_ @@ -1051,9 +1051,10 @@ struct sqlite3_mem_methods { #define SQLITE_CONFIG_MALLOC 4 /* sqlite3_mem_methods* */ #define SQLITE_CONFIG_MEMSTATUS 5 /* boolean */ #define SQLITE_CONFIG_MUTEX 6 /* sqlite3_mutex_methods* */ +#define SQLITE_CONFIG_GETMUTEX 7 /* sqlite3_mutex_methods* */ /* These options are to be added later. Currently unused and undocumented. */ -#define SQLITE_CONFIG_HEAP 6 /* void*, int64, min, max, tmp */ +#define SQLITE_CONFIG_HEAP 8 /* void*, int64, min, max, tmp */ /* diff --git a/src/tclsqlite.c b/src/tclsqlite.c index 0fd4602e3..ab00763db 100644 --- a/src/tclsqlite.c +++ b/src/tclsqlite.c @@ -12,7 +12,7 @@ ** A TCL Interface to SQLite. Append this file to sqlite3.c and ** compile the whole thing to build a TCL-enabled version of SQLite. ** -** $Id: tclsqlite.c,v 1.217 2008/05/01 17:16:53 drh Exp $ +** $Id: tclsqlite.c,v 1.218 2008/06/18 09:45:56 danielk1977 Exp $ */ #include "tcl.h" #include <errno.h> @@ -2528,6 +2528,7 @@ int TCLSH_MAIN(int argc, char **argv){ extern int Sqlitetest_func_Init(Tcl_Interp*); extern int Sqlitetest_hexio_Init(Tcl_Interp*); extern int Sqlitetest_malloc_Init(Tcl_Interp*); + extern int Sqlitetest_mutex_Init(Tcl_Interp*); extern int Sqlitetestschema_Init(Tcl_Interp*); extern int Sqlitetestsse_Init(Tcl_Interp*); extern int Sqlitetesttclvar_Init(Tcl_Interp*); @@ -2551,6 +2552,7 @@ int TCLSH_MAIN(int argc, char **argv){ Sqlitetest_func_Init(interp); Sqlitetest_hexio_Init(interp); Sqlitetest_malloc_Init(interp); + Sqlitetest_mutex_Init(interp); Sqlitetestschema_Init(interp); Sqlitetesttclvar_Init(interp); SqlitetestThread_Init(interp); diff --git a/src/test_mutex.c b/src/test_mutex.c new file mode 100644 index 000000000..fac9f4129 --- /dev/null +++ b/src/test_mutex.c @@ -0,0 +1,269 @@ +/* +** 2008 June 18 +** +** 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. +** +************************************************************************* +** +** $Id: test_mutex.c,v 1.1 2008/06/18 09:45:56 danielk1977 Exp $ +*/ + +#include "tcl.h" +#include "sqlite3.h" +#include <stdlib.h> +#include <assert.h> +#include <string.h> + +const char *sqlite3TestErrorName(int); + +struct sqlite3_mutex { + sqlite3_mutex *pReal; + int eType; +}; + +static struct test_mutex_globals { + int isInstalled; + sqlite3_mutex_methods m; /* Interface to "real" mutex system */ + int aCounter[8]; /* Number of grabs of each type of mutex */ + sqlite3_mutex aStatic[6]; /* The six static mutexes */ +} g; + +static int counterMutexHeld(sqlite3_mutex *p){ + return g.m.xMutexHeld(p->pReal); +} + +static int counterMutexNotheld(sqlite3_mutex *p){ + return g.m.xMutexNotheld(p->pReal); +} + +static int counterMutexInit(void){ + return g.m.xMutexInit(); +} + +static int counterMutexEnd(void){ + return g.m.xMutexEnd(); +} + +static sqlite3_mutex *counterMutexAlloc(int eType){ + sqlite3_mutex *pReal; + sqlite3_mutex *pRet = 0; + + assert(eType<8 && eType>=0); + + pReal = g.m.xMutexAlloc(eType); + if( !pReal ) return 0; + + if( eType==0 || eType==1 ){ + pRet = (sqlite3_mutex *)malloc(sizeof(sqlite3_mutex)); + }else{ + pRet = &g.aStatic[eType-2]; + } + + pRet->eType = eType; + pRet->pReal = pReal; + return pRet; +} + +static void counterMutexFree(sqlite3_mutex *p){ + g.m.xMutexFree(p->pReal); + if( p->eType==0 || p->eType==1 ){ + free(p); + } +} + +static void counterMutexEnter(sqlite3_mutex *p){ + g.aCounter[p->eType]++; + g.m.xMutexEnter(p->pReal); +} + +static int counterMutexTry(sqlite3_mutex *p){ + g.aCounter[p->eType]++; + return g.m.xMutexTry(p->pReal); +} + +static void counterMutexLeave(sqlite3_mutex *p){ + g.m.xMutexLeave(p->pReal); +} + +/* +** sqlite3_shutdown +*/ +static int test_shutdown( + void * clientData, + Tcl_Interp *interp, + int objc, + Tcl_Obj *CONST objv[] +){ + int rc; + + if( objc!=1 ){ + Tcl_WrongNumArgs(interp, 1, objv, ""); + return TCL_ERROR; + } + + rc = sqlite3_shutdown(); + Tcl_SetResult(interp, (char *)sqlite3TestErrorName(rc), TCL_VOLATILE); + return TCL_OK; +} + +/* +** sqlite3_initialize +*/ +static int test_initialize( + void * clientData, + Tcl_Interp *interp, + int objc, + Tcl_Obj *CONST objv[] +){ + int rc; + + if( objc!=1 ){ + Tcl_WrongNumArgs(interp, 1, objv, ""); + return TCL_ERROR; + } + + rc = sqlite3_initialize(); + Tcl_SetResult(interp, (char *)sqlite3TestErrorName(rc), TCL_VOLATILE); + return TCL_OK; +} + +/* +** install_mutex_counters BOOLEAN +*/ +static int test_install_mutex_counters( + void * clientData, + Tcl_Interp *interp, + int objc, + Tcl_Obj *CONST objv[] +){ + int rc = SQLITE_OK; + int isInstall; + + sqlite3_mutex_methods counter_methods = { + counterMutexInit, + counterMutexAlloc, + counterMutexFree, + counterMutexEnter, + counterMutexTry, + counterMutexLeave, + counterMutexEnd, + counterMutexHeld, + counterMutexNotheld + }; + + if( objc!=2 ){ + Tcl_WrongNumArgs(interp, 1, objv, "BOOLEAN"); + return TCL_ERROR; + } + if( TCL_OK!=Tcl_GetBooleanFromObj(interp, objv[1], &isInstall) ){ + return TCL_ERROR; + } + + assert(isInstall==0 || isInstall==1); + assert(g.isInstalled==0 || g.isInstalled==1); + if( isInstall==g.isInstalled ){ + Tcl_AppendResult(interp, "mutex counters are ", 0); + Tcl_AppendResult(interp, isInstall?"already installed":"not installed", 0); + return TCL_ERROR; + } + + if( isInstall ){ + assert( g.m.xMutexAlloc==0 ); + rc = sqlite3_config(SQLITE_CONFIG_GETMUTEX, &g.m); + if( rc==SQLITE_OK ){ + sqlite3_config(SQLITE_CONFIG_MUTEX, &counter_methods); + } + }else{ + assert( g.m.xMutexAlloc ); + rc = sqlite3_config(SQLITE_CONFIG_MUTEX, &g.m); + memset(&g.m, 0, sizeof(sqlite3_mutex_methods)); + } + + if( rc==SQLITE_OK ){ + g.isInstalled = isInstall; + } + + Tcl_SetResult(interp, (char *)sqlite3TestErrorName(rc), TCL_VOLATILE); + return TCL_OK; +} + +/* +** read_mutex_counters +*/ +static int test_read_mutex_counters( + void * clientData, + Tcl_Interp *interp, + int objc, + Tcl_Obj *CONST objv[] +){ + Tcl_Obj *pRet; + int ii; + char *aName[8] = { + "fast", "recursive", "static_master", "static_mem", + "static_mem2", "static_prng", "static_lru", "static_lru2" + }; + + if( objc!=1 ){ + Tcl_WrongNumArgs(interp, 1, objv, ""); + return TCL_ERROR; + } + + pRet = Tcl_NewObj(); + Tcl_IncrRefCount(pRet); + for(ii=0; ii<8; ii++){ + Tcl_ListObjAppendElement(interp, pRet, Tcl_NewStringObj(aName[ii], -1)); + Tcl_ListObjAppendElement(interp, pRet, Tcl_NewIntObj(g.aCounter[ii])); + } + Tcl_SetObjResult(interp, pRet); + Tcl_DecrRefCount(pRet); + + return TCL_OK; +} + +/* +** clear_mutex_counters +*/ +static int test_clear_mutex_counters( + void * clientData, + Tcl_Interp *interp, + int objc, + Tcl_Obj *CONST objv[] +){ + int ii; + + if( objc!=1 ){ + Tcl_WrongNumArgs(interp, 1, objv, ""); + return TCL_ERROR; + } + + for(ii=0; ii<8; ii++){ + g.aCounter[ii] = 0; + } + return TCL_OK; +} + +int Sqlitetest_mutex_Init(Tcl_Interp *interp){ + static struct { + char *zName; + Tcl_ObjCmdProc *xProc; + } aCmd[] = { + { "sqlite3_shutdown", (Tcl_ObjCmdProc*)test_shutdown }, + { "sqlite3_initialize", (Tcl_ObjCmdProc*)test_initialize }, + + { "install_mutex_counters", (Tcl_ObjCmdProc*)test_install_mutex_counters }, + { "read_mutex_counters", (Tcl_ObjCmdProc*)test_read_mutex_counters }, + { "clear_mutex_counters", (Tcl_ObjCmdProc*)test_clear_mutex_counters }, + }; + int i; + for(i=0; i<sizeof(aCmd)/sizeof(aCmd[0]); i++){ + Tcl_CreateObjCommand(interp, aCmd[i].zName, aCmd[i].xProc, 0, 0); + } + memset(&g, 0, sizeof(g)); + return SQLITE_OK; +} + |