/ Check-in [ffd3312b]
Login
SQLite training in Houston TX on 2019-11-05 (details)
Part of the 2019 Tcl Conference

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

Overview
Comment:Bug-fixes to get the two threadtest C programs working again. (CVS 1756)
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA1: ffd3312b66e2657c3431eab814aadec254af2403
User & Date: danielk1977 2004-06-29 07:45:33
Context
2004-06-29
08:59
Fix error reporting path for errors that occur while reading the database schema. (CVS 1757) check-in: 157db33e user: danielk1977 tags: trunk
07:45
Bug-fixes to get the two threadtest C programs working again. (CVS 1756) check-in: ffd3312b user: danielk1977 tags: trunk
03:29
Try to get threads working again on Linux. (CVS 1755) check-in: a8417cb8 user: drh tags: trunk
Changes
Hide Diffs Side-by-Side Diffs Ignore Whitespace Patch

Changes to src/build.c.

    19     19   **     DROP INDEX
    20     20   **     creating ID lists
    21     21   **     BEGIN TRANSACTION
    22     22   **     COMMIT
    23     23   **     ROLLBACK
    24     24   **     PRAGMA
    25     25   **
    26         -** $Id: build.c,v 1.235 2004/06/28 01:11:47 danielk1977 Exp $
           26  +** $Id: build.c,v 1.236 2004/06/29 07:45:33 danielk1977 Exp $
    27     27   */
    28     28   #include "sqliteInt.h"
    29     29   #include <ctype.h>
    30     30   
    31     31   /*
    32     32   ** This routine is called when a new SQL statement is beginning to
    33     33   ** be parsed.  Check to see if the schema for the database needs
................................................................................
   143    143   ** where sqlite3FindTable() does not.
   144    144   */
   145    145   Table *sqlite3LocateTable(Parse *pParse, const char *zName, const char *zDbase){
   146    146     Table *p;
   147    147   
   148    148     p = sqlite3FindTable(pParse->db, zName, zDbase);
   149    149     if( p==0 ){
   150         -    if( zDbase ){
          150  +    if( !(pParse->db->flags & SQLITE_Initialized) ){
          151  +      /* If the schema is not initialised at this point, it must be because
          152  +      ** the database is locked. */
          153  +      pParse->nErr++;
          154  +      pParse->rc = SQLITE_BUSY;
          155  +    }else if( zDbase ){
   151    156         sqlite3ErrorMsg(pParse, "no such table: %s.%s", zDbase, zName);
   152    157       }else if( sqlite3FindTable(pParse->db, zName, 0)!=0 ){
   153    158         sqlite3ErrorMsg(pParse, "table \"%s\" is not in database \"%s\"",
   154    159            zName, zDbase);
   155    160       }else{
   156    161         sqlite3ErrorMsg(pParse, "no such table: %s", zName);
   157    162       }
................................................................................
   613    618     */
   614    619     if( isTemp && db->aDb[1].pBt==0 && !pParse->explain ){
   615    620       int rc = sqlite3BtreeFactory(db, 0, 0, MAX_PAGES, &db->aDb[1].pBt);
   616    621       if( rc!=SQLITE_OK ){
   617    622         sqlite3ErrorMsg(pParse, "unable to open a temporary database "
   618    623           "file for storing temporary tables");
   619    624         pParse->nErr++;
          625  +      pParse->rc = rc;
   620    626         sqliteFree(zName);
   621    627         return;
   622    628       }
   623    629       if( db->flags & !db->autoCommit ){
   624    630         rc = sqlite3BtreeBeginTrans(db->aDb[1].pBt, 1);
   625    631         if( rc!=SQLITE_OK ){
   626    632           sqlite3ErrorMsg(pParse, "unable to get a write lock on "
   627    633             "the temporary database file");
   628    634           sqliteFree(zName);
          635  +        pParse->rc = rc;
   629    636           return;
   630    637         }
   631    638       }
   632    639     }
   633    640   
   634    641     /* Make sure the new table name does not collide with an existing
   635    642     ** index or table name in the same database.  Issue an error message if

Changes to src/main.c.

    10     10   **
    11     11   *************************************************************************
    12     12   ** Main file for the SQLite library.  The routines in this file
    13     13   ** implement the programmer interface to the library.  Routines in
    14     14   ** other files are for internal use by SQLite and should not be
    15     15   ** accessed by users of the library.
    16     16   **
    17         -** $Id: main.c,v 1.237 2004/06/28 01:11:47 danielk1977 Exp $
           17  +** $Id: main.c,v 1.238 2004/06/29 07:45:34 danielk1977 Exp $
    18     18   */
    19     19   #include "sqliteInt.h"
    20     20   #include "os.h"
    21     21   #include <ctype.h>
    22     22   
    23     23   /*
    24     24   ** A pointer to this structure is used to communicate information
................................................................................
    81     81         if( argv[3] && argv[3][0] ){
    82     82           /* Call the parser to process a CREATE TABLE, INDEX or VIEW.
    83     83           ** But because db->init.busy is set to 1, no VDBE code is generated
    84     84           ** or executed.  All the parser does is build the internal data
    85     85           ** structures that describe the table, index, or view.
    86     86           */
    87     87           char *zErr;
           88  +        int rc;
    88     89           assert( db->init.busy );
    89     90           db->init.iDb = atoi(argv[4]);
    90     91           assert( db->init.iDb>=0 && db->init.iDb<db->nDb );
    91     92           db->init.newTnum = atoi(argv[2]);
    92         -        if( sqlite3_exec(db, argv[3], 0, 0, &zErr) ){
           93  +        rc = sqlite3_exec(db, argv[3], 0, 0, &zErr);
           94  +        db->init.iDb = 0;
           95  +        if( SQLITE_OK!=rc ){
    93     96             corruptSchema(pData, zErr);
    94     97             sqlite3_free(zErr);
           98  +          return rc;
    95     99           }
    96         -        db->init.iDb = 0;
    97    100         }else{
    98    101           /* If the SQL column is blank it means this is an index that
    99    102           ** was created to be the PRIMARY KEY or to fulfill a UNIQUE
   100    103           ** constraint for a CREATE TABLE.  The index should have already
   101    104           ** been created when we processed the CREATE TABLE.  All we have
   102    105           ** to do here is record the root page number for that index.
   103    106           */
................................................................................
   114    117             ** safely ignore the index on the permanent table.
   115    118             */
   116    119             /* Do Nothing */;
   117    120           }else{
   118    121             pIndex->tnum = atoi(argv[2]);
   119    122           }
   120    123         }
   121         -      break;
   122    124       }
          125  +    break;
   123    126       default: {
   124    127         /* This can not happen! */
   125    128         nErr = 1;
   126    129         assert( nErr==0 );
   127    130       }
   128    131     }
   129    132     return nErr;
................................................................................
   192    195     azArg[2] = "1";
   193    196     azArg[3] = zMasterSchema;
   194    197     sprintf(zDbNum, "%d", iDb);
   195    198     azArg[4] = zDbNum;
   196    199     azArg[5] = 0;
   197    200     initData.db = db;
   198    201     initData.pzErrMsg = pzErrMsg;
   199         -  sqlite3InitCallback(&initData, 5, (char **)azArg, 0);
          202  +  rc = sqlite3InitCallback(&initData, 5, (char **)azArg, 0);
          203  +  if( rc!=SQLITE_OK ){
          204  +    sqlite3SafetyOn(db);
          205  +    return rc;
          206  +  }
   200    207     pTab = sqlite3FindTable(db, zMasterName, db->aDb[iDb].zName);
   201    208     if( pTab ){
   202    209       pTab->readOnly = 1;
   203    210     }
   204    211     sqlite3SafetyOn(db);
   205    212   
   206    213     /* Create a cursor to hold the database open

Changes to src/os_common.h.

    40     40   #define SEEK(X)           last_page=(X)
    41     41   #define TRACE1(X)         if( sqlite3_os_trace ) sqlite3DebugPrintf(X)
    42     42   #define TRACE2(X,Y)       if( sqlite3_os_trace ) sqlite3DebugPrintf(X,Y)
    43     43   #define TRACE3(X,Y,Z)     if( sqlite3_os_trace ) sqlite3DebugPrintf(X,Y,Z)
    44     44   #define TRACE4(X,Y,Z,A)   if( sqlite3_os_trace ) sqlite3DebugPrintf(X,Y,Z,A)
    45     45   #define TRACE5(X,Y,Z,A,B) if( sqlite3_os_trace ) sqlite3DebugPrintf(X,Y,Z,A,B)
    46     46   #define TRACE6(X,Y,Z,A,B,C) if(sqlite3_os_trace) sqlite3DebugPrintf(X,Y,Z,A,B,C)
           47  +#define TRACE7(X,Y,Z,A,B,C,D) \
           48  +    if(sqlite3_os_trace) sqlite3DebugPrintf(X,Y,Z,A,B,C,D)
    47     49   #else
    48     50   #define TIMER_START
    49     51   #define TIMER_END
    50     52   #define SEEK(X)
    51     53   #define TRACE1(X)
    52     54   #define TRACE2(X,Y)
    53     55   #define TRACE3(X,Y,Z)

Changes to src/os_unix.c.

   755    755     
   756    756     sqlite3OsLeaveMutex();
   757    757     TRACE3("TEST WR-LOCK %d %d\n", id->h, r);
   758    758   
   759    759     return r;
   760    760   }
   761    761   
          762  +#ifdef SQLITE_DEBUG
          763  +/*
          764  +** Helper function for printing out trace information from debugging
          765  +** binaries. This returns the string represetation of the supplied
          766  +** integer lock-type.
          767  +*/
          768  +static const char * locktypeName(int locktype){
          769  +  switch( locktype ){
          770  +  case NO_LOCK: return "NONE";
          771  +  case SHARED_LOCK: return "SHARED";
          772  +  case RESERVED_LOCK: return "RESERVED";
          773  +  case PENDING_LOCK: return "PENDING";
          774  +  case EXCLUSIVE_LOCK: return "EXCLUSIVE";
          775  +  }
          776  +  return "ERROR";
          777  +}
          778  +#endif
          779  +
   762    780   /*
   763    781   ** Lock the file with the lock specified by parameter locktype - one
   764    782   ** of the following:
   765    783   **
   766    784   **     (1) SHARED_LOCK
   767    785   **     (2) RESERVED_LOCK
   768    786   **     (3) PENDING_LOCK
................................................................................
   824    842     */
   825    843     int rc = SQLITE_OK;
   826    844     struct lockInfo *pLock = id->pLock;
   827    845     struct flock lock;
   828    846     int s;
   829    847   
   830    848     assert( id->isOpen );
   831         -  TRACE6("LOCK %d %d was %d(%d,%d)\n",
   832         -          id->h, locktype, id->locktype, pLock->locktype, pLock->cnt);
          849  +  TRACE7("LOCK %d %s was %s(%s,%d) pid=%d\n", id->h, locktypeName(locktype), 
          850  +      locktypeName(id->locktype), locktypeName(pLock->locktype), pLock->cnt
          851  +      ,getpid() );
   833    852   
   834    853     /* If there is already a lock of this type or more restrictive on the
   835    854     ** OsFile, do nothing. Don't use the end_lock: exit path, as
   836    855     ** sqlite3OsEnterMutex() hasn't been called yet.
   837    856     */
   838    857     if( id->locktype>=locktype ){
          858  +    TRACE3("LOCK %d %s ok (already held)\n", id->h, locktypeName(locktype));
   839    859       return SQLITE_OK;
   840    860     }
   841    861   
   842    862     /* Make sure the locking sequence is correct
   843    863     */
   844    864     assert( id->locktype!=NO_LOCK || locktype==SHARED_LOCK );
   845    865     assert( locktype!=PENDING_LOCK );
................................................................................
   952    972     }else if( locktype==EXCLUSIVE_LOCK ){
   953    973       id->locktype = PENDING_LOCK;
   954    974       pLock->locktype = PENDING_LOCK;
   955    975     }
   956    976   
   957    977   end_lock:
   958    978     sqlite3OsLeaveMutex();
   959         -  TRACE4("LOCK %d %d %s\n", id->h, locktype, rc==SQLITE_OK ? "ok" : "failed");
          979  +  TRACE4("LOCK %d %s %s\n", id->h, locktypeName(locktype), 
          980  +      rc==SQLITE_OK ? "ok" : "failed");
   960    981     return rc;
   961    982   }
   962    983   
   963    984   /*
   964    985   ** Lower the locking level on file descriptor id to locktype.  locktype
   965    986   ** must be either NO_LOCK or SHARED_LOCK.
   966    987   **
................................................................................
   970    991   ** It is not possible for this routine to fail.
   971    992   */
   972    993   int sqlite3OsUnlock(OsFile *id, int locktype){
   973    994     struct lockInfo *pLock;
   974    995     struct flock lock;
   975    996   
   976    997     assert( id->isOpen );
   977         -  TRACE6("UNLOCK %d %d was %d(%d,%d)\n",
   978         -          id->h, locktype, id->locktype, id->pLock->locktype, id->pLock->cnt);
          998  +  TRACE7("UNLOCK %d %d was %d(%d,%d) pid=%d\n", id->h, locktype, id->locktype, 
          999  +      id->pLock->locktype, id->pLock->cnt, getpid());
   979   1000   
   980   1001     assert( locktype<=SHARED_LOCK );
   981   1002     if( id->locktype<=locktype ){
   982   1003       return SQLITE_OK;
   983   1004     }
   984   1005     sqlite3OsEnterMutex();
   985   1006     pLock = id->pLock;

Changes to src/pragma.c.

     7      7   **    May you do good and not evil.
     8      8   **    May you find forgiveness for yourself and forgive others.
     9      9   **    May you share freely, never taking more than you give.
    10     10   **
    11     11   *************************************************************************
    12     12   ** This file contains code used to implement the PRAGMA command.
    13     13   **
    14         -** $Id: pragma.c,v 1.54 2004/06/26 19:35:30 drh Exp $
           14  +** $Id: pragma.c,v 1.55 2004/06/29 07:45:34 danielk1977 Exp $
    15     15   */
    16     16   #include "sqliteInt.h"
    17     17   #include <ctype.h>
    18     18   
    19     19   #if defined(SQLITE_DEBUG) || defined(SQLITE_TEST)
    20     20   # include "pager.h"
    21     21   # include "btree.h"
................................................................................
   115    115     return 0;
   116    116   }
   117    117   
   118    118   /*
   119    119   ** Check to make sure the schema is loaded.  Return 1 if it is not.
   120    120   */
   121    121   static int checkSchema(Parse *pParse){
   122         -  if( SQLITE_OK!=sqlite3ReadSchema(pParse->db, &pParse->zErrMsg) ){
          122  +  int rc = sqlite3ReadSchema(pParse->db, &pParse->zErrMsg);
          123  +  if( SQLITE_OK!=rc ){
   123    124       pParse->nErr++;
          125  +    pParse->rc = rc;
   124    126       return 1;
   125    127     }
   126    128     return 0;
   127    129   }
   128    130   
   129    131   /*
   130    132   ** Process a pragma statement.  
................................................................................
   496    498           cnt++;
   497    499           for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){
   498    500             if( sqlite3CheckIndexCollSeq(pParse, pIdx) ) goto pragma_out;
   499    501             sqlite3VdbeAddOp(v, OP_Integer, pIdx->tnum, 0);
   500    502             cnt++;
   501    503           }
   502    504         }
          505  +      assert( cnt>0 );
   503    506         sqlite3VdbeAddOp(v, OP_IntegrityCk, cnt, i);
   504    507         sqlite3VdbeAddOp(v, OP_Dup, 0, 1);
   505    508         addr = sqlite3VdbeOp3(v, OP_String8, 0, 0, "ok", P3_STATIC);
   506    509         sqlite3VdbeAddOp(v, OP_Eq, 0, addr+6);
   507    510         sqlite3VdbeOp3(v, OP_String8, 0, 0,
   508    511            sqlite3MPrintf("*** in database %s ***\n", db->aDb[i].zName),
   509    512            P3_DYNAMIC);

Changes to test/threadtest1.c.

   258    258     for(i=0; i<n; i++){
   259    259       char zBuf[200];
   260    260       sprintf(zBuf, "testdb-%d", (i+1)/2);
   261    261       unlink(zBuf);
   262    262     }
   263    263     for(i=0; i<n; i++){
   264    264       zFile = sqlite3_mprintf("%d.testdb-%d", i%2+1, (i+2)/2);
   265         -    unlink(zFile);
          265  +    if( (i%2)==0 ){
          266  +      /* Remove both the database file and any old journal for the file
          267  +      ** being used by this thread and the next one. */
          268  +      char *zDb = &zFile[2];
          269  +      char *zJournal = sqlite3_mprintf("%s-journal", zDb);
          270  +      unlink(zDb);
          271  +      unlink(zJournal);
          272  +      free(zJournal);
          273  +    }
          274  +      
   266    275       pthread_create(&id, 0, worker_bee, (void*)zFile);
   267    276       pthread_detach(id);
   268    277     }
   269    278     pthread_mutex_lock(&lock);
   270    279     while( thread_cnt>0 ){
   271    280       pthread_cond_wait(&sig, &lock);
   272    281     }

Changes to test/threadtest2.c.

    92     92   ** Initialize the database and start the threads
    93     93   */
    94     94   int main(int argc, char **argv){
    95     95     sqlite *db;
    96     96     int i, rc;
    97     97     pthread_t aThread[5];
    98     98   
    99         -  if( strcmp(DB_FILE,":memory:") ) unlink(DB_FILE);
           99  +  if( strcmp(DB_FILE,":memory:") ){
          100  +    char *zJournal = sqlite3_mprintf("%s-journal", DB_FILE);
          101  +    unlink(DB_FILE);
          102  +    unlink(zJournal);
          103  +    free(zJournal);
          104  +  }  
   100    105     sqlite3_open(DB_FILE, &db);
   101    106     if( db==0 ){
   102    107       fprintf(stderr,"unable to initialize database\n");
   103    108       exit(1);
   104    109     }
   105    110     rc = sqlite3_exec(db, "CREATE TABLE t1(x);", 0,0,0);
   106    111     if( rc ){