4 ** The author disclaims copyright to this source code. In place of
5 ** a legal notice, here is a blessing:
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.
11 *************************************************************************
12 ** This file contains the C functions that implement mutexes.
14 ** This implementation in this file does not provide any mutual
15 ** exclusion and is thus suitable for use only in applications
16 ** that use SQLite in a single thread. The routines defined
17 ** here are place-holders. Applications can substitute working
18 ** mutex routines at start-time using the
20 ** sqlite3_config(SQLITE_CONFIG_MUTEX,...)
24 ** If compiled with SQLITE_DEBUG, then additional logic is inserted
25 ** that does error checking on mutexes to make sure they are being
28 #include "sqliteInt.h"
30 #ifndef SQLITE_MUTEX_OMIT
34 ** Stub routines for all mutex methods.
36 ** This routines provide no mutual exclusion or error checking.
38 static int noopMutexInit(void){ return SQLITE_OK
; }
39 static int noopMutexEnd(void){ return SQLITE_OK
; }
40 static sqlite3_mutex
*noopMutexAlloc(int id
){
42 return (sqlite3_mutex
*)8;
44 static void noopMutexFree(sqlite3_mutex
*p
){ UNUSED_PARAMETER(p
); return; }
45 static void noopMutexEnter(sqlite3_mutex
*p
){ UNUSED_PARAMETER(p
); return; }
46 static int noopMutexTry(sqlite3_mutex
*p
){
50 static void noopMutexLeave(sqlite3_mutex
*p
){ UNUSED_PARAMETER(p
); return; }
52 sqlite3_mutex_methods
const *sqlite3NoopMutex(void){
53 static const sqlite3_mutex_methods sMutex
= {
68 #endif /* !SQLITE_DEBUG */
72 ** In this implementation, error checking is provided for testing
73 ** and debugging purposes. The mutexes still do not provide any
80 typedef struct sqlite3_debug_mutex
{
81 int id
; /* The mutex type */
82 int cnt
; /* Number of entries without a matching leave */
83 } sqlite3_debug_mutex
;
86 ** The sqlite3_mutex_held() and sqlite3_mutex_notheld() routine are
87 ** intended for use inside assert() statements.
89 static int debugMutexHeld(sqlite3_mutex
*pX
){
90 sqlite3_debug_mutex
*p
= (sqlite3_debug_mutex
*)pX
;
91 return p
==0 || p
->cnt
>0;
93 static int debugMutexNotheld(sqlite3_mutex
*pX
){
94 sqlite3_debug_mutex
*p
= (sqlite3_debug_mutex
*)pX
;
95 return p
==0 || p
->cnt
==0;
99 ** Initialize and deinitialize the mutex subsystem.
101 static int debugMutexInit(void){ return SQLITE_OK
; }
102 static int debugMutexEnd(void){ return SQLITE_OK
; }
105 ** The sqlite3_mutex_alloc() routine allocates a new
106 ** mutex and returns a pointer to it. If it returns NULL
107 ** that means that a mutex could not be allocated.
109 static sqlite3_mutex
*debugMutexAlloc(int id
){
110 static sqlite3_debug_mutex aStatic
[SQLITE_MUTEX_STATIC_VFS3
- 1];
111 sqlite3_debug_mutex
*pNew
= 0;
113 case SQLITE_MUTEX_FAST
:
114 case SQLITE_MUTEX_RECURSIVE
: {
115 pNew
= sqlite3Malloc(sizeof(*pNew
));
123 #ifdef SQLITE_ENABLE_API_ARMOR
124 if( id
-2<0 || id
-2>=ArraySize(aStatic
) ){
125 (void)SQLITE_MISUSE_BKPT
;
129 pNew
= &aStatic
[id
-2];
134 return (sqlite3_mutex
*)pNew
;
138 ** This routine deallocates a previously allocated mutex.
140 static void debugMutexFree(sqlite3_mutex
*pX
){
141 sqlite3_debug_mutex
*p
= (sqlite3_debug_mutex
*)pX
;
143 if( p
->id
==SQLITE_MUTEX_RECURSIVE
|| p
->id
==SQLITE_MUTEX_FAST
){
146 #ifdef SQLITE_ENABLE_API_ARMOR
147 (void)SQLITE_MISUSE_BKPT
;
153 ** The sqlite3_mutex_enter() and sqlite3_mutex_try() routines attempt
154 ** to enter a mutex. If another thread is already within the mutex,
155 ** sqlite3_mutex_enter() will block and sqlite3_mutex_try() will return
156 ** SQLITE_BUSY. The sqlite3_mutex_try() interface returns SQLITE_OK
157 ** upon successful entry. Mutexes created using SQLITE_MUTEX_RECURSIVE can
158 ** be entered multiple times by the same thread. In such cases the,
159 ** mutex must be exited an equal number of times before another thread
160 ** can enter. If the same thread tries to enter any other kind of mutex
161 ** more than once, the behavior is undefined.
163 static void debugMutexEnter(sqlite3_mutex
*pX
){
164 sqlite3_debug_mutex
*p
= (sqlite3_debug_mutex
*)pX
;
165 assert( p
->id
==SQLITE_MUTEX_RECURSIVE
|| debugMutexNotheld(pX
) );
168 static int debugMutexTry(sqlite3_mutex
*pX
){
169 sqlite3_debug_mutex
*p
= (sqlite3_debug_mutex
*)pX
;
170 assert( p
->id
==SQLITE_MUTEX_RECURSIVE
|| debugMutexNotheld(pX
) );
176 ** The sqlite3_mutex_leave() routine exits a mutex that was
177 ** previously entered by the same thread. The behavior
178 ** is undefined if the mutex is not currently entered or
179 ** is not currently allocated. SQLite will never do either.
181 static void debugMutexLeave(sqlite3_mutex
*pX
){
182 sqlite3_debug_mutex
*p
= (sqlite3_debug_mutex
*)pX
;
183 assert( debugMutexHeld(pX
) );
185 assert( p
->id
==SQLITE_MUTEX_RECURSIVE
|| debugMutexNotheld(pX
) );
188 sqlite3_mutex_methods
const *sqlite3NoopMutex(void){
189 static const sqlite3_mutex_methods sMutex
= {
204 #endif /* SQLITE_DEBUG */
207 ** If compiled with SQLITE_MUTEX_NOOP, then the no-op mutex implementation
208 ** is used regardless of the run-time threadsafety setting.
210 #ifdef SQLITE_MUTEX_NOOP
211 sqlite3_mutex_methods
const *sqlite3DefaultMutex(void){
212 return sqlite3NoopMutex();
214 #endif /* defined(SQLITE_MUTEX_NOOP) */
215 #endif /* !defined(SQLITE_MUTEX_OMIT) */