SQLite

Check-in [05afd86e2d]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:fix broken OS/2 mutex implementation (Ticket #2905) (CVS 4770)
Downloads: Tarball | ZIP archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA1: 05afd86e2d25a219843be48c21c212e84f94e7ef
User & Date: pweilbacher 2008-02-01 19:42:38.000
Context
2008-02-01
19:44
Use the buffer size as limit for temp file names. This is done for windows too, see check-in (4595). (CVS 4771) (check-in: 99275bcd62 user: pweilbacher tags: trunk)
19:42
fix broken OS/2 mutex implementation (Ticket #2905) (CVS 4770) (check-in: 05afd86e2d user: pweilbacher tags: trunk)
15:34
Minor fixes to FTS3 so that it works better when appended to the end of the amalgamation. (CVS 4769) (check-in: 62ede6699d user: drh tags: trunk)
Changes
Unified Diff Ignore Whitespace Patch
Changes to src/mutex_os2.c.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39


40
41
42
43
44
45
46
/*
** 2007 August 28
**
** 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.
**
*************************************************************************
** This file contains the C functions that implement mutexes for OS/2
**
** $Id: mutex_os2.c,v 1.4 2007/12/30 23:29:07 pweilbacher Exp $
*/
#include "sqliteInt.h"

/*
** The code in this file is only used if SQLITE_MUTEX_OS2 is defined.
** See the mutex.h file for details.
*/
#ifdef SQLITE_MUTEX_OS2

/********************** OS/2 Mutex Implementation **********************
**
** This implementation of mutexes is built using the OS/2 API.
*/

/*
** The mutex object
** Each recursive mutex is an instance of the following structure.
*/
struct sqlite3_mutex {
  PSZ  mutexName;   /* Mutex name controlling the lock */
  HMTX mutex;       /* Mutex controlling the lock */
  int  id;          /* Mutex type */
  int  nRef;        /* Number of references */
  TID  owner;       /* Thread holding this mutex */
};



/*
** The sqlite3_mutex_alloc() routine allocates a new
** mutex and returns a pointer to it.  If it returns NULL
** that means that a mutex could not be allocated. 
** SQLite will unwind its stack and return an error.  The argument
** to sqlite3_mutex_alloc() is one of these integer constants:













|



















<





>
>







1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33

34
35
36
37
38
39
40
41
42
43
44
45
46
47
/*
** 2007 August 28
**
** 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.
**
*************************************************************************
** This file contains the C functions that implement mutexes for OS/2
**
** $Id: mutex_os2.c,v 1.5 2008/02/01 19:42:38 pweilbacher Exp $
*/
#include "sqliteInt.h"

/*
** The code in this file is only used if SQLITE_MUTEX_OS2 is defined.
** See the mutex.h file for details.
*/
#ifdef SQLITE_MUTEX_OS2

/********************** OS/2 Mutex Implementation **********************
**
** This implementation of mutexes is built using the OS/2 API.
*/

/*
** The mutex object
** Each recursive mutex is an instance of the following structure.
*/
struct sqlite3_mutex {

  HMTX mutex;       /* Mutex controlling the lock */
  int  id;          /* Mutex type */
  int  nRef;        /* Number of references */
  TID  owner;       /* Thread holding this mutex */
};

#define OS2_MUTEX_INITIALIZER   0,0,0,0

/*
** The sqlite3_mutex_alloc() routine allocates a new
** mutex and returns a pointer to it.  If it returns NULL
** that means that a mutex could not be allocated. 
** SQLite will unwind its stack and return an error.  The argument
** to sqlite3_mutex_alloc() is one of these integer constants:
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94



95
96
97
98

99






100








101
102
103
104

105
106
107
108
109
110
111
112
113
114
115
116
117


118
119
120



121
122
123
124
125
126
127
** Note that if one of the dynamic mutex parameters (SQLITE_MUTEX_FAST
** or SQLITE_MUTEX_RECURSIVE) is used then sqlite3_mutex_alloc()
** returns a different mutex on every call.  But for the static
** mutex types, the same mutex is returned on every call that has
** the same type number.
*/
sqlite3_mutex *sqlite3_mutex_alloc(int iType){
  PSZ mutex_name = "\\SEM32\\SQLITE\\MUTEX";
  int mutex_name_len = strlen(mutex_name) + 1; /* name length + null byte */
  sqlite3_mutex *p;

  switch( iType ){
    case SQLITE_MUTEX_FAST:
    case SQLITE_MUTEX_RECURSIVE: {
      p = sqlite3MallocZero( sizeof(*p) );
      if( p ){
        p->mutexName = (PSZ)malloc(mutex_name_len);
        sqlite3_snprintf(mutex_name_len, p->mutexName, "%s", mutex_name);
        p->id = iType;
        DosCreateMutexSem(p->mutexName, &p->mutex, 0, FALSE);
        DosOpenMutexSem(p->mutexName, &p->mutex);



      }
      break;
    }
    default: {

      static sqlite3_mutex staticMutexes[5];






      static int isInit = 0;








      while( !isInit ) {
        static long lock = 0;
        DosEnterCritSec();
        lock++;

        if( lock == 1 ) {
          int i;
          DosExitCritSec();
          for(i = 0; i < sizeof(staticMutexes)/sizeof(staticMutexes[0]); i++) {
            staticMutexes[i].mutexName = (PSZ)malloc(mutex_name_len + 1);
            sqlite3_snprintf(mutex_name_len + 1, /* one more for the number */
                             staticMutexes[i].mutexName, "%s%1d", mutex_name, i);
            DosCreateMutexSem(staticMutexes[i].mutexName,
                              &staticMutexes[i].mutex, 0, FALSE);
            DosOpenMutexSem(staticMutexes[i].mutexName,
                            &staticMutexes[i].mutex);
          }
          isInit = 1;


        } else {
          DosExitCritSec();
          DosSleep(1);



        }
      }
      assert( iType-2 >= 0 );
      assert( iType-2 < sizeof(staticMutexes)/sizeof(staticMutexes[0]) );
      p = &staticMutexes[iType-2];
      p->id = iType;
      break;







<
<
|
<





<
<

|
<
>
>
>




>
|
>
>
>
>
>
>
|
>
>
>
>
>
>
>
>
|
|
<
<
>
|
|
|
|
<
<
<
<
|
<
<
|
|
>
>
|
<
|
>
>
>







75
76
77
78
79
80
81


82

83
84
85
86
87


88
89

90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115


116
117
118
119
120




121


122
123
124
125
126

127
128
129
130
131
132
133
134
135
136
137
** Note that if one of the dynamic mutex parameters (SQLITE_MUTEX_FAST
** or SQLITE_MUTEX_RECURSIVE) is used then sqlite3_mutex_alloc()
** returns a different mutex on every call.  But for the static
** mutex types, the same mutex is returned on every call that has
** the same type number.
*/
sqlite3_mutex *sqlite3_mutex_alloc(int iType){


  sqlite3_mutex *p = NULL;

  switch( iType ){
    case SQLITE_MUTEX_FAST:
    case SQLITE_MUTEX_RECURSIVE: {
      p = sqlite3MallocZero( sizeof(*p) );
      if( p ){


        p->id = iType;
        if( DosCreateMutexSem( 0, &p->mutex, 0, FALSE ) != NO_ERROR ){

          sqlite3_free( p );
          p = NULL;
        }
      }
      break;
    }
    default: {
      static volatile int isInit = 0;
      static sqlite3_mutex staticMutexes[] = {
        { OS2_MUTEX_INITIALIZER, },
        { OS2_MUTEX_INITIALIZER, },
        { OS2_MUTEX_INITIALIZER, },
        { OS2_MUTEX_INITIALIZER, },
        { OS2_MUTEX_INITIALIZER, },
      };
      if ( !isInit ){
        APIRET rc;
        PTIB ptib;
        PPIB ppib;
        HMTX mutex;
        char name[32];
        DosGetInfoBlocks( &ptib, &ppib );
        sqlite3_snprintf( sizeof(name), name, "\\SEM32\\SQLITE%04x",
                          ppib->pib_ulpid );
        while( !isInit ){
          mutex = 0;


          rc = DosCreateMutexSem( name, &mutex, 0, FALSE);
          if( rc == NO_ERROR ){
            int i;
            if( !isInit ){
              for( i = 0; i < sizeof(staticMutexes)/sizeof(staticMutexes[0]); i++ ){




                DosCreateMutexSem( 0, &staticMutexes[i].mutex, 0, FALSE );


              }
              isInit = 1;
            }
            DosCloseMutexSem( mutex );
          }else if( rc == ERROR_DUPLICATE_NAME ){

            DosSleep( 1 );
          }else{
            return p;
          }
        }
      }
      assert( iType-2 >= 0 );
      assert( iType-2 < sizeof(staticMutexes)/sizeof(staticMutexes[0]) );
      p = &staticMutexes[iType-2];
      p->id = iType;
      break;
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
** This routine deallocates a previously allocated mutex.
** SQLite is careful to deallocate every mutex that it allocates.
*/
void sqlite3_mutex_free(sqlite3_mutex *p){
  assert( p );
  assert( p->nRef==0 );
  assert( p->id==SQLITE_MUTEX_FAST || p->id==SQLITE_MUTEX_RECURSIVE );
  DosCloseMutexSem(p->mutex);
  free(p->mutexName);
  sqlite3_free(p);
}

/*
** The sqlite3_mutex_enter() and sqlite3_mutex_try() routines attempt
** to enter a mutex.  If another thread is already within the mutex,
** sqlite3_mutex_enter() will block and sqlite3_mutex_try() will return
** SQLITE_BUSY.  The sqlite3_mutex_try() interface returns SQLITE_OK







|
<
|







145
146
147
148
149
150
151
152

153
154
155
156
157
158
159
160
** This routine deallocates a previously allocated mutex.
** SQLite is careful to deallocate every mutex that it allocates.
*/
void sqlite3_mutex_free(sqlite3_mutex *p){
  assert( p );
  assert( p->nRef==0 );
  assert( p->id==SQLITE_MUTEX_FAST || p->id==SQLITE_MUTEX_RECURSIVE );
  DosCloseMutexSem( p->mutex );

  sqlite3_free( p );
}

/*
** The sqlite3_mutex_enter() and sqlite3_mutex_try() routines attempt
** to enter a mutex.  If another thread is already within the mutex,
** sqlite3_mutex_enter() will block and sqlite3_mutex_try() will return
** SQLITE_BUSY.  The sqlite3_mutex_try() interface returns SQLITE_OK