/ Hex Artifact Content
Login

Artifact afdab9acbda8b96dd0e55052de59b87d972cadc1:


0000: 2f 2a 0a 2a 2a 20 32 30 31 32 20 4a 75 6c 79 20  /*.** 2012 July 
0010: 32 31 0a 2a 2a 0a 2a 2a 20 54 68 65 20 61 75 74  21.**.** The aut
0020: 68 6f 72 20 64 69 73 63 6c 61 69 6d 73 20 63 6f  hor disclaims co
0030: 70 79 72 69 67 68 74 20 74 6f 20 74 68 69 73 20  pyright to this 
0040: 73 6f 75 72 63 65 20 63 6f 64 65 2e 20 20 49 6e  source code.  In
0050: 20 70 6c 61 63 65 20 6f 66 0a 2a 2a 20 61 20 6c   place of.** a l
0060: 65 67 61 6c 20 6e 6f 74 69 63 65 2c 20 68 65 72  egal notice, her
0070: 65 20 69 73 20 61 20 62 6c 65 73 73 69 6e 67 3a  e is a blessing:
0080: 0a 2a 2a 0a 2a 2a 20 20 20 20 4d 61 79 20 79 6f  .**.**    May yo
0090: 75 20 64 6f 20 67 6f 6f 64 20 61 6e 64 20 6e 6f  u do good and no
00a0: 74 20 65 76 69 6c 2e 0a 2a 2a 20 20 20 20 4d 61  t evil..**    Ma
00b0: 79 20 79 6f 75 20 66 69 6e 64 20 66 6f 72 67 69  y you find forgi
00c0: 76 65 6e 65 73 73 20 66 6f 72 20 79 6f 75 72 73  veness for yours
00d0: 65 6c 66 20 61 6e 64 20 66 6f 72 67 69 76 65 20  elf and forgive 
00e0: 6f 74 68 65 72 73 2e 0a 2a 2a 20 20 20 20 4d 61  others..**    Ma
00f0: 79 20 79 6f 75 20 73 68 61 72 65 20 66 72 65 65  y you share free
0100: 6c 79 2c 20 6e 65 76 65 72 20 74 61 6b 69 6e 67  ly, never taking
0110: 20 6d 6f 72 65 20 74 68 61 6e 20 79 6f 75 20 67   more than you g
0120: 69 76 65 2e 0a 2a 2a 0a 2a 2a 2a 2a 2a 2a 2a 2a  ive..**.********
0130: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0140: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0150: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0160: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0170: 2a 2a 2a 2a 2a 2a 0a 2a 2a 0a 2a 2a 20 54 68 69  ******.**.** Thi
0180: 73 20 66 69 6c 65 20 70 72 65 73 65 6e 74 73 20  s file presents 
0190: 61 20 73 69 6d 70 6c 65 20 63 72 6f 73 73 2d 70  a simple cross-p
01a0: 6c 61 74 66 6f 72 6d 20 74 68 72 65 61 64 69 6e  latform threadin
01b0: 67 20 69 6e 74 65 72 66 61 63 65 20 66 6f 72 0a  g interface for.
01c0: 2a 2a 20 75 73 65 20 69 6e 74 65 72 6e 61 6c 6c  ** use internall
01d0: 79 20 62 79 20 53 51 4c 69 74 65 2e 0a 2a 2a 0a  y by SQLite..**.
01e0: 2a 2a 20 41 20 22 74 68 72 65 61 64 22 20 63 61  ** A "thread" ca
01f0: 6e 20 62 65 20 63 72 65 61 74 65 64 20 75 73 69  n be created usi
0200: 6e 67 20 73 71 6c 69 74 65 33 54 68 72 65 61 64  ng sqlite3Thread
0210: 43 72 65 61 74 65 28 29 2e 20 20 54 68 69 73 20  Create().  This 
0220: 74 68 72 65 61 64 0a 2a 2a 20 72 75 6e 73 20 69  thread.** runs i
0230: 6e 64 65 70 65 6e 64 65 6e 74 6c 79 20 6f 66 20  ndependently of 
0240: 69 74 73 20 63 72 65 61 74 6f 72 20 75 6e 74 69  its creator unti
0250: 6c 20 69 74 20 69 73 20 6a 6f 69 6e 65 64 20 75  l it is joined u
0260: 73 69 6e 67 0a 2a 2a 20 73 71 6c 69 74 65 33 54  sing.** sqlite3T
0270: 68 72 65 61 64 4a 6f 69 6e 28 29 2c 20 61 74 20  hreadJoin(), at 
0280: 77 68 69 63 68 20 70 6f 69 6e 74 20 69 74 20 74  which point it t
0290: 65 72 6d 69 6e 61 74 65 73 2e 0a 2a 2a 0a 2a 2a  erminates..**.**
02a0: 20 54 68 72 65 61 64 73 20 64 6f 20 6e 6f 74 20   Threads do not 
02b0: 68 61 76 65 20 74 6f 20 62 65 20 72 65 61 6c 2e  have to be real.
02c0: 20 20 49 74 20 63 6f 75 6c 64 20 62 65 20 74 68    It could be th
02d0: 61 74 20 74 68 65 20 77 6f 72 6b 20 6f 66 20 74  at the work of t
02e0: 68 65 0a 2a 2a 20 22 74 68 72 65 61 64 22 20 69  he.** "thread" i
02f0: 73 20 64 6f 6e 65 20 62 79 20 74 68 65 20 6d 61  s done by the ma
0300: 69 6e 20 74 68 72 65 61 64 20 61 74 20 65 69 74  in thread at eit
0310: 68 65 72 20 74 68 65 20 73 71 6c 69 74 65 33 54  her the sqlite3T
0320: 68 72 65 61 64 43 72 65 61 74 65 28 29 0a 2a 2a  hreadCreate().**
0330: 20 6f 72 20 73 71 6c 69 74 65 33 54 68 72 65 61   or sqlite3Threa
0340: 64 4a 6f 69 6e 28 29 20 63 61 6c 6c 2e 20 20 54  dJoin() call.  T
0350: 68 69 73 20 69 73 2c 20 69 6e 20 66 61 63 74 2c  his is, in fact,
0360: 20 77 68 61 74 20 68 61 70 70 65 6e 73 20 69 6e   what happens in
0370: 0a 2a 2a 20 73 69 6e 67 6c 65 20 74 68 72 65 61  .** single threa
0380: 64 65 64 20 73 79 73 74 65 6d 73 2e 20 20 4e 6f  ded systems.  No
0390: 74 68 69 6e 67 20 69 6e 20 53 51 4c 69 74 65 20  thing in SQLite 
03a0: 72 65 71 75 69 72 65 73 20 6d 75 6c 74 69 70 6c  requires multipl
03b0: 65 20 74 68 72 65 61 64 73 2e 0a 2a 2a 20 54 68  e threads..** Th
03c0: 69 73 20 69 6e 74 65 72 66 61 63 65 20 65 78 69  is interface exi
03d0: 73 74 73 20 73 6f 20 74 68 61 74 20 61 70 70 6c  sts so that appl
03e0: 69 63 61 74 69 6f 6e 73 20 74 68 61 74 20 77 61  ications that wa
03f0: 6e 74 20 74 6f 20 74 61 6b 65 20 61 64 76 61 6e  nt to take advan
0400: 74 61 67 65 0a 2a 2a 20 6f 66 20 6d 75 6c 74 69  tage.** of multi
0410: 70 6c 65 20 63 6f 72 65 73 20 63 61 6e 20 64 6f  ple cores can do
0420: 20 73 6f 2c 20 77 68 69 6c 65 20 61 6c 73 6f 20   so, while also 
0430: 61 6c 6c 6f 77 69 6e 67 20 61 70 70 6c 69 63 61  allowing applica
0440: 74 69 6f 6e 73 20 74 6f 20 73 74 61 79 0a 2a 2a  tions to stay.**
0450: 20 73 69 6e 67 6c 65 2d 74 68 72 65 61 64 65 64   single-threaded
0460: 20 69 66 20 64 65 73 69 72 65 64 2e 0a 2a 2f 0a   if desired..*/.
0470: 23 69 6e 63 6c 75 64 65 20 22 73 71 6c 69 74 65  #include "sqlite
0480: 49 6e 74 2e 68 22 0a 0a 23 69 66 20 53 51 4c 49  Int.h"..#if SQLI
0490: 54 45 5f 4d 41 58 5f 57 4f 52 4b 45 52 5f 54 48  TE_MAX_WORKER_TH
04a0: 52 45 41 44 53 3e 30 0a 0a 2f 2a 2a 2a 2a 2a 2a  READS>0../******
04b0: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
04c0: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 20 55 6e 69 78  *********** Unix
04d0: 20 50 74 68 72 65 61 64 73 20 2a 2a 2a 2a 2a 2a   Pthreads ******
04e0: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
04f0: 2a 2a 2a 2a 2a 2a 2f 0a 23 69 66 20 53 51 4c 49  ******/.#if SQLI
0500: 54 45 5f 4f 53 5f 55 4e 49 58 20 26 26 20 64 65  TE_OS_UNIX && de
0510: 66 69 6e 65 64 28 53 51 4c 49 54 45 5f 4d 55 54  fined(SQLITE_MUT
0520: 45 58 5f 50 54 48 52 45 41 44 53 29 20 26 26 20  EX_PTHREADS) && 
0530: 53 51 4c 49 54 45 5f 54 48 52 45 41 44 53 41 46  SQLITE_THREADSAF
0540: 45 3e 30 0a 0a 23 64 65 66 69 6e 65 20 53 51 4c  E>0..#define SQL
0550: 49 54 45 5f 54 48 52 45 41 44 53 5f 49 4d 50 4c  ITE_THREADS_IMPL
0560: 45 4d 45 4e 54 45 44 20 31 20 20 2f 2a 20 50 72  EMENTED 1  /* Pr
0570: 65 76 65 6e 74 20 74 68 65 20 73 69 6e 67 6c 65  event the single
0580: 2d 74 68 72 65 61 64 20 63 6f 64 65 20 62 65 6c  -thread code bel
0590: 6f 77 20 2a 2f 0a 23 69 6e 63 6c 75 64 65 20 3c  ow */.#include <
05a0: 70 74 68 72 65 61 64 2e 68 3e 0a 0a 2f 2a 20 41  pthread.h>../* A
05b0: 20 72 75 6e 6e 69 6e 67 20 74 68 72 65 61 64 20   running thread 
05c0: 2a 2f 0a 73 74 72 75 63 74 20 53 51 4c 69 74 65  */.struct SQLite
05d0: 54 68 72 65 61 64 20 7b 0a 20 20 70 74 68 72 65  Thread {.  pthre
05e0: 61 64 5f 74 20 74 69 64 3b 20 20 20 20 20 20 20  ad_t tid;       
05f0: 20 20 20 20 20 20 20 20 20 20 2f 2a 20 54 68 72            /* Thr
0600: 65 61 64 20 49 44 20 2a 2f 0a 20 20 69 6e 74 20  ead ID */.  int 
0610: 64 6f 6e 65 3b 20 20 20 20 20 20 20 20 20 20 20  done;           
0620: 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 53 65             /* Se
0630: 74 20 74 6f 20 74 72 75 65 20 77 68 65 6e 20 74  t to true when t
0640: 68 72 65 61 64 20 66 69 6e 69 73 68 65 73 20 2a  hread finishes *
0650: 2f 0a 20 20 76 6f 69 64 20 2a 70 4f 75 74 3b 20  /.  void *pOut; 
0660: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0670: 20 20 20 2f 2a 20 52 65 73 75 6c 74 20 72 65 74     /* Result ret
0680: 75 72 6e 65 64 20 62 79 20 74 68 65 20 74 68 72  urned by the thr
0690: 65 61 64 20 2a 2f 0a 20 20 76 6f 69 64 20 2a 28  ead */.  void *(
06a0: 2a 78 54 61 73 6b 29 28 76 6f 69 64 2a 29 3b 20  *xTask)(void*); 
06b0: 20 20 20 20 20 20 20 20 2f 2a 20 54 68 65 20 74          /* The t
06c0: 68 72 65 61 64 20 72 6f 75 74 69 6e 65 20 2a 2f  hread routine */
06d0: 0a 20 20 76 6f 69 64 20 2a 70 49 6e 3b 20 20 20  .  void *pIn;   
06e0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
06f0: 20 20 2f 2a 20 41 72 67 75 6d 65 6e 74 20 74 6f    /* Argument to
0700: 20 74 68 65 20 74 68 72 65 61 64 20 2a 2f 0a 7d   the thread */.}
0710: 3b 0a 0a 2f 2a 20 43 72 65 61 74 65 20 61 20 6e  ;../* Create a n
0720: 65 77 20 74 68 72 65 61 64 20 2a 2f 0a 69 6e 74  ew thread */.int
0730: 20 73 71 6c 69 74 65 33 54 68 72 65 61 64 43 72   sqlite3ThreadCr
0740: 65 61 74 65 28 0a 20 20 53 51 4c 69 74 65 54 68  eate(.  SQLiteTh
0750: 72 65 61 64 20 2a 2a 70 70 54 68 72 65 61 64 2c  read **ppThread,
0760: 20 20 2f 2a 20 4f 55 54 3a 20 57 72 69 74 65 20    /* OUT: Write 
0770: 74 68 65 20 74 68 72 65 61 64 20 6f 62 6a 65 63  the thread objec
0780: 74 20 68 65 72 65 20 2a 2f 0a 20 20 76 6f 69 64  t here */.  void
0790: 20 2a 28 2a 78 54 61 73 6b 29 28 76 6f 69 64 2a   *(*xTask)(void*
07a0: 29 2c 20 20 20 20 2f 2a 20 52 6f 75 74 69 6e 65  ),    /* Routine
07b0: 20 74 6f 20 72 75 6e 20 69 6e 20 61 20 73 65 70   to run in a sep
07c0: 61 72 61 74 65 20 74 68 72 65 61 64 20 2a 2f 0a  arate thread */.
07d0: 20 20 76 6f 69 64 20 2a 70 49 6e 20 20 20 20 20    void *pIn     
07e0: 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 41              /* A
07f0: 72 67 75 6d 65 6e 74 20 70 61 73 73 65 64 20 69  rgument passed i
0800: 6e 74 6f 20 78 54 61 73 6b 28 29 20 2a 2f 0a 29  nto xTask() */.)
0810: 7b 0a 20 20 53 51 4c 69 74 65 54 68 72 65 61 64  {.  SQLiteThread
0820: 20 2a 70 3b 0a 0a 20 20 61 73 73 65 72 74 28 20   *p;..  assert( 
0830: 70 70 54 68 72 65 61 64 21 3d 30 20 29 3b 0a 20  ppThread!=0 );. 
0840: 20 61 73 73 65 72 74 28 20 78 54 61 73 6b 21 3d   assert( xTask!=
0850: 30 20 29 3b 0a 20 20 2f 2a 20 54 68 69 73 20 72  0 );.  /* This r
0860: 6f 75 74 69 6e 65 20 69 73 20 6e 65 76 65 72 20  outine is never 
0870: 75 73 65 64 20 69 6e 20 73 69 6e 67 6c 65 2d 74  used in single-t
0880: 68 72 65 61 64 65 64 20 6d 6f 64 65 20 2a 2f 0a  hreaded mode */.
0890: 20 20 61 73 73 65 72 74 28 20 73 71 6c 69 74 65    assert( sqlite
08a0: 33 47 6c 6f 62 61 6c 43 6f 6e 66 69 67 2e 62 43  3GlobalConfig.bC
08b0: 6f 72 65 4d 75 74 65 78 21 3d 30 20 29 3b 0a 0a  oreMutex!=0 );..
08c0: 20 20 2a 70 70 54 68 72 65 61 64 20 3d 20 30 3b    *ppThread = 0;
08d0: 0a 20 20 70 20 3d 20 73 71 6c 69 74 65 33 4d 61  .  p = sqlite3Ma
08e0: 6c 6c 6f 63 28 73 69 7a 65 6f 66 28 2a 70 29 29  lloc(sizeof(*p))
08f0: 3b 0a 20 20 69 66 28 20 70 3d 3d 30 20 29 20 72  ;.  if( p==0 ) r
0900: 65 74 75 72 6e 20 53 51 4c 49 54 45 5f 4e 4f 4d  eturn SQLITE_NOM
0910: 45 4d 3b 0a 20 20 6d 65 6d 73 65 74 28 70 2c 20  EM;.  memset(p, 
0920: 30 2c 20 73 69 7a 65 6f 66 28 2a 70 29 29 3b 0a  0, sizeof(*p));.
0930: 20 20 70 2d 3e 78 54 61 73 6b 20 3d 20 78 54 61    p->xTask = xTa
0940: 73 6b 3b 0a 20 20 70 2d 3e 70 49 6e 20 3d 20 70  sk;.  p->pIn = p
0950: 49 6e 3b 0a 20 20 69 66 28 20 73 71 6c 69 74 65  In;.  if( sqlite
0960: 33 46 61 75 6c 74 53 69 6d 28 32 30 30 29 20 3f  3FaultSim(200) ?
0970: 20 31 20 3a 20 70 74 68 72 65 61 64 5f 63 72 65   1 : pthread_cre
0980: 61 74 65 28 26 70 2d 3e 74 69 64 2c 20 30 2c 20  ate(&p->tid, 0, 
0990: 78 54 61 73 6b 2c 20 70 49 6e 29 20 29 7b 0a 20  xTask, pIn) ){. 
09a0: 20 20 20 70 2d 3e 64 6f 6e 65 20 3d 20 31 3b 0a     p->done = 1;.
09b0: 20 20 20 20 70 2d 3e 70 4f 75 74 20 3d 20 78 54      p->pOut = xT
09c0: 61 73 6b 28 70 49 6e 29 3b 0a 20 20 7d 0a 20 20  ask(pIn);.  }.  
09d0: 2a 70 70 54 68 72 65 61 64 20 3d 20 70 3b 0a 20  *ppThread = p;. 
09e0: 20 72 65 74 75 72 6e 20 53 51 4c 49 54 45 5f 4f   return SQLITE_O
09f0: 4b 3b 0a 7d 0a 0a 2f 2a 20 47 65 74 20 74 68 65  K;.}../* Get the
0a00: 20 72 65 73 75 6c 74 73 20 6f 66 20 74 68 65 20   results of the 
0a10: 74 68 72 65 61 64 20 2a 2f 0a 69 6e 74 20 73 71  thread */.int sq
0a20: 6c 69 74 65 33 54 68 72 65 61 64 4a 6f 69 6e 28  lite3ThreadJoin(
0a30: 53 51 4c 69 74 65 54 68 72 65 61 64 20 2a 70 2c  SQLiteThread *p,
0a40: 20 76 6f 69 64 20 2a 2a 70 70 4f 75 74 29 7b 0a   void **ppOut){.
0a50: 20 20 69 6e 74 20 72 63 3b 0a 0a 20 20 61 73 73    int rc;..  ass
0a60: 65 72 74 28 20 70 70 4f 75 74 21 3d 30 20 29 3b  ert( ppOut!=0 );
0a70: 0a 20 20 69 66 28 20 70 3d 3d 30 20 29 20 72 65  .  if( p==0 ) re
0a80: 74 75 72 6e 20 53 51 4c 49 54 45 5f 4e 4f 4d 45  turn SQLITE_NOME
0a90: 4d 3b 0a 20 20 69 66 28 20 70 2d 3e 64 6f 6e 65  M;.  if( p->done
0aa0: 20 29 7b 0a 20 20 20 20 2a 70 70 4f 75 74 20 3d   ){.    *ppOut =
0ab0: 20 70 2d 3e 70 4f 75 74 3b 0a 20 20 20 20 72 63   p->pOut;.    rc
0ac0: 20 3d 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a 20 20   = SQLITE_OK;.  
0ad0: 7d 65 6c 73 65 7b 0a 20 20 20 20 72 63 20 3d 20  }else{.    rc = 
0ae0: 70 74 68 72 65 61 64 5f 6a 6f 69 6e 28 70 2d 3e  pthread_join(p->
0af0: 74 69 64 2c 20 70 70 4f 75 74 29 20 3f 20 53 51  tid, ppOut) ? SQ
0b00: 4c 49 54 45 5f 45 52 52 4f 52 20 3a 20 53 51 4c  LITE_ERROR : SQL
0b10: 49 54 45 5f 4f 4b 3b 0a 20 20 7d 0a 20 20 73 71  ITE_OK;.  }.  sq
0b20: 6c 69 74 65 33 5f 66 72 65 65 28 70 29 3b 0a 20  lite3_free(p);. 
0b30: 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 23   return rc;.}..#
0b40: 65 6e 64 69 66 20 2f 2a 20 53 51 4c 49 54 45 5f  endif /* SQLITE_
0b50: 4f 53 5f 55 4e 49 58 20 26 26 20 64 65 66 69 6e  OS_UNIX && defin
0b60: 65 64 28 53 51 4c 49 54 45 5f 4d 55 54 45 58 5f  ed(SQLITE_MUTEX_
0b70: 50 54 48 52 45 41 44 53 29 20 2a 2f 0a 2f 2a 2a  PTHREADS) */./**
0b80: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0b90: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 20 45  ************** E
0ba0: 6e 64 20 55 6e 69 78 20 50 74 68 72 65 61 64 73  nd Unix Pthreads
0bb0: 20 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a   ***************
0bc0: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2f 0a 0a 0a 2f 2a  **********/.../*
0bd0: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0be0: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0bf0: 20 57 69 6e 33 32 20 54 68 72 65 61 64 73 20 2a   Win32 Threads *
0c00: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0c10: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2f 0a 23 69 66  ***********/.#if
0c20: 20 53 51 4c 49 54 45 5f 4f 53 5f 57 49 4e 20 26   SQLITE_OS_WIN &
0c30: 26 20 21 53 51 4c 49 54 45 5f 4f 53 5f 57 49 4e  & !SQLITE_OS_WIN
0c40: 52 54 20 26 26 20 53 51 4c 49 54 45 5f 54 48 52  RT && SQLITE_THR
0c50: 45 41 44 53 41 46 45 3e 30 0a 0a 23 64 65 66 69  EADSAFE>0..#defi
0c60: 6e 65 20 53 51 4c 49 54 45 5f 54 48 52 45 41 44  ne SQLITE_THREAD
0c70: 53 5f 49 4d 50 4c 45 4d 45 4e 54 45 44 20 31 20  S_IMPLEMENTED 1 
0c80: 20 2f 2a 20 50 72 65 76 65 6e 74 20 74 68 65 20   /* Prevent the 
0c90: 73 69 6e 67 6c 65 2d 74 68 72 65 61 64 20 63 6f  single-thread co
0ca0: 64 65 20 62 65 6c 6f 77 20 2a 2f 0a 23 69 6e 63  de below */.#inc
0cb0: 6c 75 64 65 20 3c 70 72 6f 63 65 73 73 2e 68 3e  lude <process.h>
0cc0: 0a 0a 2f 2a 20 41 20 72 75 6e 6e 69 6e 67 20 74  ../* A running t
0cd0: 68 72 65 61 64 20 2a 2f 0a 73 74 72 75 63 74 20  hread */.struct 
0ce0: 53 51 4c 69 74 65 54 68 72 65 61 64 20 7b 0a 20  SQLiteThread {. 
0cf0: 20 75 69 6e 74 70 74 72 5f 74 20 74 69 64 3b 20   uintptr_t tid; 
0d00: 20 20 20 20 20 20 20 20 20 20 2f 2a 20 54 68 65            /* The
0d10: 20 74 68 72 65 61 64 20 68 61 6e 64 6c 65 20 2a   thread handle *
0d20: 2f 0a 20 20 76 6f 69 64 20 2a 28 2a 78 54 61 73  /.  void *(*xTas
0d30: 6b 29 28 76 6f 69 64 2a 29 3b 20 20 20 2f 2a 20  k)(void*);   /* 
0d40: 54 68 65 20 72 6f 75 74 69 6e 65 20 74 6f 20 72  The routine to r
0d50: 75 6e 20 61 73 20 61 20 74 68 72 65 61 64 20 2a  un as a thread *
0d60: 2f 0a 20 20 76 6f 69 64 20 2a 70 49 6e 3b 20 20  /.  void *pIn;  
0d70: 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
0d80: 41 72 67 75 6d 65 6e 74 20 74 6f 20 78 54 61 73  Argument to xTas
0d90: 6b 20 2a 2f 0a 20 20 76 6f 69 64 20 2a 70 52 65  k */.  void *pRe
0da0: 73 75 6c 74 3b 20 20 20 20 20 20 20 20 20 20 20  sult;           
0db0: 2f 2a 20 52 65 73 75 6c 74 20 6f 66 20 78 54 61  /* Result of xTa
0dc0: 73 6b 20 2a 2f 0a 7d 3b 0a 0a 2f 2a 20 54 68 72  sk */.};../* Thr
0dd0: 65 61 64 20 70 72 6f 63 65 64 75 72 65 20 57 69  ead procedure Wi
0de0: 6e 33 32 20 63 6f 6d 70 61 74 69 62 69 6c 69 74  n32 compatibilit
0df0: 79 20 73 68 69 6d 20 2a 2f 0a 73 74 61 74 69 63  y shim */.static
0e00: 20 76 6f 69 64 20 73 71 6c 69 74 65 33 54 68 72   void sqlite3Thr
0e10: 65 61 64 50 72 6f 63 28 0a 20 20 76 6f 69 64 20  eadProc(.  void 
0e20: 2a 70 41 72 67 20 20 2f 2a 20 49 4e 3a 20 50 6f  *pArg  /* IN: Po
0e30: 69 6e 74 65 72 20 74 6f 20 74 68 65 20 53 51 4c  inter to the SQL
0e40: 69 74 65 54 68 72 65 61 64 20 73 74 72 75 63 74  iteThread struct
0e50: 75 72 65 20 2a 2f 0a 29 7b 0a 20 20 53 51 4c 69  ure */.){.  SQLi
0e60: 74 65 54 68 72 65 61 64 20 2a 70 20 3d 20 28 53  teThread *p = (S
0e70: 51 4c 69 74 65 54 68 72 65 61 64 20 2a 29 70 41  QLiteThread *)pA
0e80: 72 67 3b 0a 0a 20 20 61 73 73 65 72 74 28 20 70  rg;..  assert( p
0e90: 21 3d 30 20 29 3b 0a 20 20 61 73 73 65 72 74 28  !=0 );.  assert(
0ea0: 20 70 2d 3e 78 54 61 73 6b 21 3d 30 20 29 3b 0a   p->xTask!=0 );.
0eb0: 20 20 70 2d 3e 70 52 65 73 75 6c 74 20 3d 20 70    p->pResult = p
0ec0: 2d 3e 78 54 61 73 6b 28 70 2d 3e 70 49 6e 29 3b  ->xTask(p->pIn);
0ed0: 0a 20 20 5f 65 6e 64 74 68 72 65 61 64 28 29 3b  .  _endthread();
0ee0: 0a 7d 0a 0a 2f 2a 20 43 72 65 61 74 65 20 61 20  .}../* Create a 
0ef0: 6e 65 77 20 74 68 72 65 61 64 20 2a 2f 0a 69 6e  new thread */.in
0f00: 74 20 73 71 6c 69 74 65 33 54 68 72 65 61 64 43  t sqlite3ThreadC
0f10: 72 65 61 74 65 28 0a 20 20 53 51 4c 69 74 65 54  reate(.  SQLiteT
0f20: 68 72 65 61 64 20 2a 2a 70 70 54 68 72 65 61 64  hread **ppThread
0f30: 2c 20 20 2f 2a 20 4f 55 54 3a 20 57 72 69 74 65  ,  /* OUT: Write
0f40: 20 74 68 65 20 74 68 72 65 61 64 20 6f 62 6a 65   the thread obje
0f50: 63 74 20 68 65 72 65 20 2a 2f 0a 20 20 76 6f 69  ct here */.  voi
0f60: 64 20 2a 28 2a 78 54 61 73 6b 29 28 76 6f 69 64  d *(*xTask)(void
0f70: 2a 29 2c 20 20 20 20 2f 2a 20 52 6f 75 74 69 6e  *),    /* Routin
0f80: 65 20 74 6f 20 72 75 6e 20 69 6e 20 61 20 73 65  e to run in a se
0f90: 70 61 72 61 74 65 20 74 68 72 65 61 64 20 2a 2f  parate thread */
0fa0: 0a 20 20 76 6f 69 64 20 2a 70 49 6e 20 20 20 20  .  void *pIn    
0fb0: 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
0fc0: 41 72 67 75 6d 65 6e 74 20 70 61 73 73 65 64 20  Argument passed 
0fd0: 69 6e 74 6f 20 78 54 61 73 6b 28 29 20 2a 2f 0a  into xTask() */.
0fe0: 29 7b 0a 20 20 53 51 4c 69 74 65 54 68 72 65 61  ){.  SQLiteThrea
0ff0: 64 20 2a 70 3b 0a 0a 20 20 61 73 73 65 72 74 28  d *p;..  assert(
1000: 20 70 70 54 68 72 65 61 64 21 3d 30 20 29 3b 0a   ppThread!=0 );.
1010: 20 20 61 73 73 65 72 74 28 20 78 54 61 73 6b 21    assert( xTask!
1020: 3d 30 20 29 3b 0a 20 20 2a 70 70 54 68 72 65 61  =0 );.  *ppThrea
1030: 64 20 3d 20 30 3b 0a 20 20 70 20 3d 20 73 71 6c  d = 0;.  p = sql
1040: 69 74 65 33 4d 61 6c 6c 6f 63 28 73 69 7a 65 6f  ite3Malloc(sizeo
1050: 66 28 2a 70 29 29 3b 0a 20 20 69 66 28 20 70 3d  f(*p));.  if( p=
1060: 3d 30 20 29 20 72 65 74 75 72 6e 20 53 51 4c 49  =0 ) return SQLI
1070: 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 69 66 28 20  TE_NOMEM;.  if( 
1080: 73 71 6c 69 74 65 33 47 6c 6f 62 61 6c 43 6f 6e  sqlite3GlobalCon
1090: 66 69 67 2e 62 43 6f 72 65 4d 75 74 65 78 3d 3d  fig.bCoreMutex==
10a0: 30 20 29 7b 0a 20 20 20 20 6d 65 6d 73 65 74 28  0 ){.    memset(
10b0: 70 2c 20 30 2c 20 73 69 7a 65 6f 66 28 2a 70 29  p, 0, sizeof(*p)
10c0: 29 3b 0a 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20  );.  }else{.    
10d0: 70 2d 3e 78 54 61 73 6b 20 3d 20 78 54 61 73 6b  p->xTask = xTask
10e0: 3b 0a 20 20 20 20 70 2d 3e 70 49 6e 20 3d 20 70  ;.    p->pIn = p
10f0: 49 6e 3b 0a 20 20 20 20 70 2d 3e 74 69 64 20 3d  In;.    p->tid =
1100: 20 5f 62 65 67 69 6e 74 68 72 65 61 64 28 73 71   _beginthread(sq
1110: 6c 69 74 65 33 54 68 72 65 61 64 50 72 6f 63 2c  lite3ThreadProc,
1120: 20 30 2c 20 70 29 3b 0a 20 20 20 20 69 66 28 20   0, p);.    if( 
1130: 70 2d 3e 74 69 64 3d 3d 28 75 69 6e 74 70 74 72  p->tid==(uintptr
1140: 5f 74 29 2d 31 20 29 7b 0a 20 20 20 20 20 20 6d  _t)-1 ){.      m
1150: 65 6d 73 65 74 28 70 2c 20 30 2c 20 73 69 7a 65  emset(p, 0, size
1160: 6f 66 28 2a 70 29 29 3b 0a 20 20 20 20 7d 0a 20  of(*p));.    }. 
1170: 20 7d 0a 20 20 69 66 28 20 70 2d 3e 78 54 61 73   }.  if( p->xTas
1180: 6b 3d 3d 30 20 29 7b 0a 20 20 20 20 70 2d 3e 70  k==0 ){.    p->p
1190: 52 65 73 75 6c 74 20 3d 20 78 54 61 73 6b 28 70  Result = xTask(p
11a0: 49 6e 29 3b 0a 20 20 7d 0a 20 20 2a 70 70 54 68  In);.  }.  *ppTh
11b0: 72 65 61 64 20 3d 20 70 3b 0a 20 20 72 65 74 75  read = p;.  retu
11c0: 72 6e 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a 7d 0a  rn SQLITE_OK;.}.
11d0: 0a 2f 2a 20 57 61 69 74 20 6f 6e 20 61 6e 20 6f  ./* Wait on an o
11e0: 62 6a 65 63 74 20 2a 2f 0a 44 57 4f 52 44 20 73  bject */.DWORD s
11f0: 71 6c 69 74 65 33 57 69 6e 33 32 57 61 69 74 28  qlite3Win32Wait(
1200: 48 41 4e 44 4c 45 20 68 4f 62 6a 65 63 74 29 7b  HANDLE hObject){
1210: 0a 20 20 44 57 4f 52 44 20 72 63 3b 0a 20 20 77  .  DWORD rc;.  w
1220: 68 69 6c 65 28 20 28 72 63 20 3d 20 6f 73 57 61  hile( (rc = osWa
1230: 69 74 46 6f 72 53 69 6e 67 6c 65 4f 62 6a 65 63  itForSingleObjec
1240: 74 45 78 28 68 4f 62 6a 65 63 74 2c 20 49 4e 46  tEx(hObject, INF
1250: 49 4e 49 54 45 2c 0a 20 20 20 20 20 20 20 20 20  INITE,.         
1260: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1270: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 54 52                TR
1280: 55 45 29 29 3d 3d 57 41 49 54 5f 49 4f 5f 43 4f  UE))==WAIT_IO_CO
1290: 4d 50 4c 45 54 49 4f 4e 20 29 7b 7d 0a 20 20 72  MPLETION ){}.  r
12a0: 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 20  eturn rc;.}../* 
12b0: 47 65 74 20 74 68 65 20 72 65 73 75 6c 74 73 20  Get the results 
12c0: 6f 66 20 74 68 65 20 74 68 72 65 61 64 20 2a 2f  of the thread */
12d0: 0a 69 6e 74 20 73 71 6c 69 74 65 33 54 68 72 65  .int sqlite3Thre
12e0: 61 64 4a 6f 69 6e 28 53 51 4c 69 74 65 54 68 72  adJoin(SQLiteThr
12f0: 65 61 64 20 2a 70 2c 20 76 6f 69 64 20 2a 2a 70  ead *p, void **p
1300: 70 4f 75 74 29 7b 0a 20 20 44 57 4f 52 44 20 72  pOut){.  DWORD r
1310: 63 3b 0a 0a 20 20 61 73 73 65 72 74 28 20 70 70  c;..  assert( pp
1320: 4f 75 74 21 3d 30 20 29 3b 0a 20 20 69 66 28 20  Out!=0 );.  if( 
1330: 70 3d 3d 30 20 29 20 72 65 74 75 72 6e 20 53 51  p==0 ) return SQ
1340: 4c 49 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 69 66  LITE_NOMEM;.  if
1350: 28 20 70 2d 3e 78 54 61 73 6b 3d 3d 30 20 29 7b  ( p->xTask==0 ){
1360: 0a 20 20 20 20 72 63 20 3d 20 57 41 49 54 5f 4f  .    rc = WAIT_O
1370: 42 4a 45 43 54 5f 30 3b 0a 20 20 7d 65 6c 73 65  BJECT_0;.  }else
1380: 7b 0a 20 20 20 20 72 63 20 3d 20 73 71 6c 69 74  {.    rc = sqlit
1390: 65 33 57 69 6e 33 32 57 61 69 74 28 28 48 41 4e  e3Win32Wait((HAN
13a0: 44 4c 45 29 70 2d 3e 74 69 64 29 3b 0a 20 20 20  DLE)p->tid);.   
13b0: 20 61 73 73 65 72 74 28 20 72 63 21 3d 57 41 49   assert( rc!=WAI
13c0: 54 5f 49 4f 5f 43 4f 4d 50 4c 45 54 49 4f 4e 20  T_IO_COMPLETION 
13d0: 29 3b 0a 20 20 7d 0a 20 20 69 66 28 20 72 63 3d  );.  }.  if( rc=
13e0: 3d 57 41 49 54 5f 4f 42 4a 45 43 54 5f 30 20 29  =WAIT_OBJECT_0 )
13f0: 20 2a 70 70 4f 75 74 20 3d 20 70 2d 3e 70 52 65   *ppOut = p->pRe
1400: 73 75 6c 74 3b 0a 20 20 73 71 6c 69 74 65 33 5f  sult;.  sqlite3_
1410: 66 72 65 65 28 70 29 3b 0a 20 20 72 65 74 75 72  free(p);.  retur
1420: 6e 20 28 72 63 3d 3d 57 41 49 54 5f 4f 42 4a 45  n (rc==WAIT_OBJE
1430: 43 54 5f 30 29 20 3f 20 53 51 4c 49 54 45 5f 4f  CT_0) ? SQLITE_O
1440: 4b 20 3a 20 53 51 4c 49 54 45 5f 45 52 52 4f 52  K : SQLITE_ERROR
1450: 3b 0a 7d 0a 0a 23 65 6e 64 69 66 20 2f 2a 20 53  ;.}..#endif /* S
1460: 51 4c 49 54 45 5f 4f 53 5f 57 49 4e 20 26 26 20  QLITE_OS_WIN && 
1470: 21 53 51 4c 49 54 45 5f 4f 53 5f 57 49 4e 52 54  !SQLITE_OS_WINRT
1480: 20 2a 2f 0a 2f 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a   */./***********
1490: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
14a0: 2a 2a 2a 2a 2a 20 45 6e 64 20 57 69 6e 33 32 20  ***** End Win32 
14b0: 54 68 72 65 61 64 73 20 2a 2a 2a 2a 2a 2a 2a 2a  Threads ********
14c0: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
14d0: 2a 2f 0a 0a 0a 2f 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  */.../**********
14e0: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
14f0: 2a 2a 2a 2a 2a 2a 2a 20 53 69 6e 67 6c 65 2d 54  ******* Single-T
1500: 68 72 65 61 64 65 64 20 2a 2a 2a 2a 2a 2a 2a 2a  hreaded ********
1510: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
1520: 2a 2a 2f 0a 23 69 66 6e 64 65 66 20 53 51 4c 49  **/.#ifndef SQLI
1530: 54 45 5f 54 48 52 45 41 44 53 5f 49 4d 50 4c 45  TE_THREADS_IMPLE
1540: 4d 45 4e 54 45 44 0a 2f 2a 0a 2a 2a 20 54 68 69  MENTED./*.** Thi
1550: 73 20 69 6d 70 6c 65 6d 65 6e 74 61 74 69 6f 6e  s implementation
1560: 20 64 6f 65 73 20 6e 6f 74 20 61 63 74 75 61 6c   does not actual
1570: 6c 79 20 63 72 65 61 74 65 20 61 20 6e 65 77 20  ly create a new 
1580: 74 68 72 65 61 64 2e 20 20 49 74 20 64 6f 65 73  thread.  It does
1590: 20 74 68 65 0a 2a 2a 20 77 6f 72 6b 20 6f 66 20   the.** work of 
15a0: 74 68 65 20 74 68 72 65 61 64 20 69 6e 20 74 68  the thread in th
15b0: 65 20 6d 61 69 6e 20 74 68 72 65 61 64 2c 20 77  e main thread, w
15c0: 68 65 6e 20 65 69 74 68 65 72 20 74 68 65 20 74  hen either the t
15d0: 68 72 65 61 64 20 69 73 20 63 72 65 61 74 65 64  hread is created
15e0: 0a 2a 2a 20 6f 72 20 77 68 65 6e 20 69 74 20 69  .** or when it i
15f0: 73 20 6a 6f 69 6e 65 64 0a 2a 2f 0a 0a 2f 2a 20  s joined.*/../* 
1600: 41 20 72 75 6e 6e 69 6e 67 20 74 68 72 65 61 64  A running thread
1610: 20 2a 2f 0a 73 74 72 75 63 74 20 53 51 4c 69 74   */.struct SQLit
1620: 65 54 68 72 65 61 64 20 7b 0a 20 20 76 6f 69 64  eThread {.  void
1630: 20 2a 28 2a 78 54 61 73 6b 29 28 76 6f 69 64 2a   *(*xTask)(void*
1640: 29 3b 20 20 20 2f 2a 20 54 68 65 20 72 6f 75 74  );   /* The rout
1650: 69 6e 65 20 74 6f 20 72 75 6e 20 61 73 20 61 20  ine to run as a 
1660: 74 68 72 65 61 64 20 2a 2f 0a 20 20 76 6f 69 64  thread */.  void
1670: 20 2a 70 49 6e 3b 20 20 20 20 20 20 20 20 20 20   *pIn;          
1680: 20 20 20 20 20 2f 2a 20 41 72 67 75 6d 65 6e 74       /* Argument
1690: 20 74 6f 20 78 54 61 73 6b 20 2a 2f 0a 20 20 76   to xTask */.  v
16a0: 6f 69 64 20 2a 70 52 65 73 75 6c 74 3b 20 20 20  oid *pResult;   
16b0: 20 20 20 20 20 20 20 20 2f 2a 20 52 65 73 75 6c          /* Resul
16c0: 74 20 6f 66 20 78 54 61 73 6b 20 2a 2f 0a 7d 3b  t of xTask */.};
16d0: 0a 0a 2f 2a 20 43 72 65 61 74 65 20 61 20 6e 65  ../* Create a ne
16e0: 77 20 74 68 72 65 61 64 20 2a 2f 0a 69 6e 74 20  w thread */.int 
16f0: 73 71 6c 69 74 65 33 54 68 72 65 61 64 43 72 65  sqlite3ThreadCre
1700: 61 74 65 28 0a 20 20 53 51 4c 69 74 65 54 68 72  ate(.  SQLiteThr
1710: 65 61 64 20 2a 2a 70 70 54 68 72 65 61 64 2c 20  ead **ppThread, 
1720: 20 2f 2a 20 4f 55 54 3a 20 57 72 69 74 65 20 74   /* OUT: Write t
1730: 68 65 20 74 68 72 65 61 64 20 6f 62 6a 65 63 74  he thread object
1740: 20 68 65 72 65 20 2a 2f 0a 20 20 76 6f 69 64 20   here */.  void 
1750: 2a 28 2a 78 54 61 73 6b 29 28 76 6f 69 64 2a 29  *(*xTask)(void*)
1760: 2c 20 20 20 20 2f 2a 20 52 6f 75 74 69 6e 65 20  ,    /* Routine 
1770: 74 6f 20 72 75 6e 20 69 6e 20 61 20 73 65 70 61  to run in a sepa
1780: 72 61 74 65 20 74 68 72 65 61 64 20 2a 2f 0a 20  rate thread */. 
1790: 20 76 6f 69 64 20 2a 70 49 6e 20 20 20 20 20 20   void *pIn      
17a0: 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 41 72             /* Ar
17b0: 67 75 6d 65 6e 74 20 70 61 73 73 65 64 20 69 6e  gument passed in
17c0: 74 6f 20 78 54 61 73 6b 28 29 20 2a 2f 0a 29 7b  to xTask() */.){
17d0: 0a 20 20 53 51 4c 69 74 65 54 68 72 65 61 64 20  .  SQLiteThread 
17e0: 2a 70 3b 0a 0a 20 20 61 73 73 65 72 74 28 20 70  *p;..  assert( p
17f0: 70 54 68 72 65 61 64 21 3d 30 20 29 3b 0a 20 20  pThread!=0 );.  
1800: 61 73 73 65 72 74 28 20 78 54 61 73 6b 21 3d 30  assert( xTask!=0
1810: 20 29 3b 0a 20 20 2a 70 70 54 68 72 65 61 64 20   );.  *ppThread 
1820: 3d 20 30 3b 0a 20 20 70 20 3d 20 73 71 6c 69 74  = 0;.  p = sqlit
1830: 65 33 4d 61 6c 6c 6f 63 28 73 69 7a 65 6f 66 28  e3Malloc(sizeof(
1840: 2a 70 29 29 3b 0a 20 20 69 66 28 20 70 3d 3d 30  *p));.  if( p==0
1850: 20 29 20 72 65 74 75 72 6e 20 53 51 4c 49 54 45   ) return SQLITE
1860: 5f 4e 4f 4d 45 4d 3b 0a 20 20 69 66 28 20 28 53  _NOMEM;.  if( (S
1870: 51 4c 49 54 45 5f 50 54 52 5f 54 4f 5f 49 4e 54  QLITE_PTR_TO_INT
1880: 28 70 29 2f 31 37 29 26 31 20 29 7b 0a 20 20 20  (p)/17)&1 ){.   
1890: 20 70 2d 3e 78 54 61 73 6b 20 3d 20 78 54 61 73   p->xTask = xTas
18a0: 6b 3b 0a 20 20 20 20 70 2d 3e 70 49 6e 20 3d 20  k;.    p->pIn = 
18b0: 70 49 6e 3b 0a 20 20 7d 65 6c 73 65 7b 0a 20 20  pIn;.  }else{.  
18c0: 20 20 70 2d 3e 78 54 61 73 6b 20 3d 20 30 3b 0a    p->xTask = 0;.
18d0: 20 20 20 20 70 2d 3e 70 52 65 73 75 6c 74 20 3d      p->pResult =
18e0: 20 78 54 61 73 6b 28 70 49 6e 29 3b 0a 20 20 7d   xTask(pIn);.  }
18f0: 0a 20 20 2a 70 70 54 68 72 65 61 64 20 3d 20 70  .  *ppThread = p
1900: 3b 0a 20 20 72 65 74 75 72 6e 20 53 51 4c 49 54  ;.  return SQLIT
1910: 45 5f 4f 4b 3b 0a 7d 0a 0a 2f 2a 20 47 65 74 20  E_OK;.}../* Get 
1920: 74 68 65 20 72 65 73 75 6c 74 73 20 6f 66 20 74  the results of t
1930: 68 65 20 74 68 72 65 61 64 20 2a 2f 0a 69 6e 74  he thread */.int
1940: 20 73 71 6c 69 74 65 33 54 68 72 65 61 64 4a 6f   sqlite3ThreadJo
1950: 69 6e 28 53 51 4c 69 74 65 54 68 72 65 61 64 20  in(SQLiteThread 
1960: 2a 70 2c 20 76 6f 69 64 20 2a 2a 70 70 4f 75 74  *p, void **ppOut
1970: 29 7b 0a 0a 20 20 61 73 73 65 72 74 28 20 70 70  ){..  assert( pp
1980: 4f 75 74 21 3d 30 20 29 3b 0a 20 20 69 66 28 20  Out!=0 );.  if( 
1990: 70 3d 3d 30 20 29 20 72 65 74 75 72 6e 20 53 51  p==0 ) return SQ
19a0: 4c 49 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 69 66  LITE_NOMEM;.  if
19b0: 28 20 70 2d 3e 78 54 61 73 6b 20 29 7b 0a 20 20  ( p->xTask ){.  
19c0: 20 20 2a 70 70 4f 75 74 20 3d 20 70 2d 3e 78 54    *ppOut = p->xT
19d0: 61 73 6b 28 70 2d 3e 70 49 6e 29 3b 0a 20 20 7d  ask(p->pIn);.  }
19e0: 65 6c 73 65 7b 0a 20 20 20 20 2a 70 70 4f 75 74  else{.    *ppOut
19f0: 20 3d 20 70 2d 3e 70 52 65 73 75 6c 74 3b 0a 20   = p->pResult;. 
1a00: 20 7d 0a 20 20 73 71 6c 69 74 65 33 5f 66 72 65   }.  sqlite3_fre
1a10: 65 28 70 29 3b 0a 0a 23 69 66 20 64 65 66 69 6e  e(p);..#if defin
1a20: 65 64 28 53 51 4c 49 54 45 5f 54 45 53 54 29 0a  ed(SQLITE_TEST).
1a30: 20 20 7b 0a 20 20 20 20 76 6f 69 64 20 2a 70 54    {.    void *pT
1a40: 73 74 41 6c 6c 6f 63 20 3d 20 73 71 6c 69 74 65  stAlloc = sqlite
1a50: 33 4d 61 6c 6c 6f 63 28 31 30 29 3b 0a 20 20 20  3Malloc(10);.   
1a60: 20 69 66 20 28 21 70 54 73 74 41 6c 6c 6f 63 29   if (!pTstAlloc)
1a70: 20 72 65 74 75 72 6e 20 53 51 4c 49 54 45 5f 4e   return SQLITE_N
1a80: 4f 4d 45 4d 3b 0a 20 20 20 20 73 71 6c 69 74 65  OMEM;.    sqlite
1a90: 33 5f 66 72 65 65 28 70 54 73 74 41 6c 6c 6f 63  3_free(pTstAlloc
1aa0: 29 3b 0a 20 20 7d 0a 23 65 6e 64 69 66 0a 0a 20  );.  }.#endif.. 
1ab0: 20 72 65 74 75 72 6e 20 53 51 4c 49 54 45 5f 4f   return SQLITE_O
1ac0: 4b 3b 0a 7d 0a 0a 23 65 6e 64 69 66 20 2f 2a 20  K;.}..#endif /* 
1ad0: 21 64 65 66 69 6e 65 64 28 53 51 4c 49 54 45 5f  !defined(SQLITE_
1ae0: 54 48 52 45 41 44 53 5f 49 4d 50 4c 45 4d 45 4e  THREADS_IMPLEMEN
1af0: 54 45 44 29 20 2a 2f 0a 2f 2a 2a 2a 2a 2a 2a 2a  TED) */./*******
1b00: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
1b10: 2a 2a 2a 2a 2a 2a 2a 20 45 6e 64 20 53 69 6e 67  ******* End Sing
1b20: 6c 65 2d 54 68 72 65 61 64 65 64 20 2a 2a 2a 2a  le-Threaded ****
1b30: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
1b40: 2a 2a 2a 2a 2a 2f 0a 23 65 6e 64 69 66 20 2f 2a  *****/.#endif /*
1b50: 20 53 51 4c 49 54 45 5f 4d 41 58 5f 57 4f 52 4b   SQLITE_MAX_WORK
1b60: 45 52 5f 54 48 52 45 41 44 53 3e 30 20 2a 2f 0a  ER_THREADS>0 */.