/ Hex Artifact Content
Login

Artifact 13642d9c754cc18f17e141f82860d269e2adf920:


0000: 0a 23 69 66 20 64 65 66 69 6e 65 64 28 53 51 4c  .#if defined(SQL
0010: 49 54 45 5f 45 4e 41 42 4c 45 5f 53 45 53 53 49  ITE_ENABLE_SESSI
0020: 4f 4e 29 20 26 26 20 64 65 66 69 6e 65 64 28 53  ON) && defined(S
0030: 51 4c 49 54 45 5f 45 4e 41 42 4c 45 5f 50 52 45  QLITE_ENABLE_PRE
0040: 55 50 44 41 54 45 5f 48 4f 4f 4b 29 0a 23 69 6e  UPDATE_HOOK).#in
0050: 63 6c 75 64 65 20 22 73 71 6c 69 74 65 33 73 65  clude "sqlite3se
0060: 73 73 69 6f 6e 2e 68 22 0a 23 69 6e 63 6c 75 64  ssion.h".#includ
0070: 65 20 3c 61 73 73 65 72 74 2e 68 3e 0a 23 69 6e  e <assert.h>.#in
0080: 63 6c 75 64 65 20 3c 73 74 72 69 6e 67 2e 68 3e  clude <string.h>
0090: 0a 0a 23 69 66 6e 64 65 66 20 53 51 4c 49 54 45  ..#ifndef SQLITE
00a0: 5f 41 4d 41 4c 47 41 4d 41 54 49 4f 4e 0a 23 20  _AMALGAMATION.# 
00b0: 69 6e 63 6c 75 64 65 20 22 73 71 6c 69 74 65 49  include "sqliteI
00c0: 6e 74 2e 68 22 0a 23 20 69 6e 63 6c 75 64 65 20  nt.h".# include 
00d0: 22 76 64 62 65 49 6e 74 2e 68 22 0a 23 65 6e 64  "vdbeInt.h".#end
00e0: 69 66 0a 0a 74 79 70 65 64 65 66 20 73 74 72 75  if..typedef stru
00f0: 63 74 20 53 65 73 73 69 6f 6e 54 61 62 6c 65 20  ct SessionTable 
0100: 53 65 73 73 69 6f 6e 54 61 62 6c 65 3b 0a 74 79  SessionTable;.ty
0110: 70 65 64 65 66 20 73 74 72 75 63 74 20 53 65 73  pedef struct Ses
0120: 73 69 6f 6e 43 68 61 6e 67 65 20 53 65 73 73 69  sionChange Sessi
0130: 6f 6e 43 68 61 6e 67 65 3b 0a 74 79 70 65 64 65  onChange;.typede
0140: 66 20 73 74 72 75 63 74 20 53 65 73 73 69 6f 6e  f struct Session
0150: 42 75 66 66 65 72 20 53 65 73 73 69 6f 6e 42 75  Buffer SessionBu
0160: 66 66 65 72 3b 0a 74 79 70 65 64 65 66 20 73 74  ffer;.typedef st
0170: 72 75 63 74 20 53 65 73 73 69 6f 6e 49 6e 70 75  ruct SessionInpu
0180: 74 20 53 65 73 73 69 6f 6e 49 6e 70 75 74 3b 0a  t SessionInput;.
0190: 0a 2f 2a 0a 2a 2a 20 4d 69 6e 69 6d 75 6d 20 63  ./*.** Minimum c
01a0: 68 75 6e 6b 20 73 69 7a 65 20 75 73 65 64 20 62  hunk size used b
01b0: 79 20 73 74 72 65 61 6d 69 6e 67 20 76 65 72 73  y streaming vers
01c0: 69 6f 6e 73 20 6f 66 20 66 75 6e 63 74 69 6f 6e  ions of function
01d0: 73 2e 0a 2a 2f 0a 23 69 66 6e 64 65 66 20 53 45  s..*/.#ifndef SE
01e0: 53 53 49 4f 4e 53 5f 53 54 52 4d 5f 43 48 55 4e  SSIONS_STRM_CHUN
01f0: 4b 5f 53 49 5a 45 0a 23 20 69 66 64 65 66 20 53  K_SIZE.# ifdef S
0200: 51 4c 49 54 45 5f 54 45 53 54 0a 23 20 20 20 64  QLITE_TEST.#   d
0210: 65 66 69 6e 65 20 53 45 53 53 49 4f 4e 53 5f 53  efine SESSIONS_S
0220: 54 52 4d 5f 43 48 55 4e 4b 5f 53 49 5a 45 20 36  TRM_CHUNK_SIZE 6
0230: 34 0a 23 20 65 6c 73 65 0a 23 20 20 20 64 65 66  4.# else.#   def
0240: 69 6e 65 20 53 45 53 53 49 4f 4e 53 5f 53 54 52  ine SESSIONS_STR
0250: 4d 5f 43 48 55 4e 4b 5f 53 49 5a 45 20 31 30 32  M_CHUNK_SIZE 102
0260: 34 0a 23 20 65 6e 64 69 66 0a 23 65 6e 64 69 66  4.# endif.#endif
0270: 0a 0a 74 79 70 65 64 65 66 20 73 74 72 75 63 74  ..typedef struct
0280: 20 53 65 73 73 69 6f 6e 48 6f 6f 6b 20 53 65 73   SessionHook Ses
0290: 73 69 6f 6e 48 6f 6f 6b 3b 0a 73 74 72 75 63 74  sionHook;.struct
02a0: 20 53 65 73 73 69 6f 6e 48 6f 6f 6b 20 7b 0a 20   SessionHook {. 
02b0: 20 76 6f 69 64 20 2a 70 43 74 78 3b 0a 20 20 69   void *pCtx;.  i
02c0: 6e 74 20 28 2a 78 4f 6c 64 29 28 76 6f 69 64 2a  nt (*xOld)(void*
02d0: 2c 69 6e 74 2c 73 71 6c 69 74 65 33 5f 76 61 6c  ,int,sqlite3_val
02e0: 75 65 2a 2a 29 3b 0a 20 20 69 6e 74 20 28 2a 78  ue**);.  int (*x
02f0: 4e 65 77 29 28 76 6f 69 64 2a 2c 69 6e 74 2c 73  New)(void*,int,s
0300: 71 6c 69 74 65 33 5f 76 61 6c 75 65 2a 2a 29 3b  qlite3_value**);
0310: 0a 20 20 69 6e 74 20 28 2a 78 43 6f 75 6e 74 29  .  int (*xCount)
0320: 28 76 6f 69 64 2a 29 3b 0a 20 20 69 6e 74 20 28  (void*);.  int (
0330: 2a 78 44 65 70 74 68 29 28 76 6f 69 64 2a 29 3b  *xDepth)(void*);
0340: 0a 7d 3b 0a 0a 2f 2a 0a 2a 2a 20 53 65 73 73 69  .};../*.** Sessi
0350: 6f 6e 20 68 61 6e 64 6c 65 20 73 74 72 75 63 74  on handle struct
0360: 75 72 65 2e 0a 2a 2f 0a 73 74 72 75 63 74 20 73  ure..*/.struct s
0370: 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20 7b  qlite3_session {
0380: 0a 20 20 73 71 6c 69 74 65 33 20 2a 64 62 3b 20  .  sqlite3 *db; 
0390: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
03a0: 20 20 20 2f 2a 20 44 61 74 61 62 61 73 65 20 68     /* Database h
03b0: 61 6e 64 6c 65 20 73 65 73 73 69 6f 6e 20 69 73  andle session is
03c0: 20 61 74 74 61 63 68 65 64 20 74 6f 20 2a 2f 0a   attached to */.
03d0: 20 20 63 68 61 72 20 2a 7a 44 62 3b 20 20 20 20    char *zDb;    
03e0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
03f0: 20 20 2f 2a 20 4e 61 6d 65 20 6f 66 20 64 61 74    /* Name of dat
0400: 61 62 61 73 65 20 73 65 73 73 69 6f 6e 20 69 73  abase session is
0410: 20 61 74 74 61 63 68 65 64 20 74 6f 20 2a 2f 0a   attached to */.
0420: 20 20 69 6e 74 20 62 45 6e 61 62 6c 65 3b 20 20    int bEnable;  
0430: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0440: 20 20 2f 2a 20 54 72 75 65 20 69 66 20 63 75 72    /* True if cur
0450: 72 65 6e 74 6c 79 20 72 65 63 6f 72 64 69 6e 67  rently recording
0460: 20 2a 2f 0a 20 20 69 6e 74 20 62 49 6e 64 69 72   */.  int bIndir
0470: 65 63 74 3b 20 20 20 20 20 20 20 20 20 20 20 20  ect;            
0480: 20 20 20 20 20 20 2f 2a 20 54 72 75 65 20 69 66        /* True if
0490: 20 61 6c 6c 20 63 68 61 6e 67 65 73 20 61 72 65   all changes are
04a0: 20 69 6e 64 69 72 65 63 74 20 2a 2f 0a 20 20 69   indirect */.  i
04b0: 6e 74 20 62 41 75 74 6f 41 74 74 61 63 68 3b 20  nt bAutoAttach; 
04c0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
04d0: 2a 20 54 72 75 65 20 74 6f 20 61 75 74 6f 2d 61  * True to auto-a
04e0: 74 74 61 63 68 20 74 61 62 6c 65 73 20 2a 2f 0a  ttach tables */.
04f0: 20 20 69 6e 74 20 72 63 3b 20 20 20 20 20 20 20    int rc;       
0500: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0510: 20 20 2f 2a 20 4e 6f 6e 2d 7a 65 72 6f 20 69 66    /* Non-zero if
0520: 20 61 6e 20 65 72 72 6f 72 20 68 61 73 20 6f 63   an error has oc
0530: 63 75 72 72 65 64 20 2a 2f 0a 20 20 76 6f 69 64  curred */.  void
0540: 20 2a 70 46 69 6c 74 65 72 43 74 78 3b 20 20 20   *pFilterCtx;   
0550: 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 46              /* F
0560: 69 72 73 74 20 61 72 67 75 6d 65 6e 74 20 74 6f  irst argument to
0570: 20 70 61 73 73 20 74 6f 20 78 54 61 62 6c 65 46   pass to xTableF
0580: 69 6c 74 65 72 20 2a 2f 0a 20 20 69 6e 74 20 28  ilter */.  int (
0590: 2a 78 54 61 62 6c 65 46 69 6c 74 65 72 29 28 76  *xTableFilter)(v
05a0: 6f 69 64 20 2a 70 43 74 78 2c 20 63 6f 6e 73 74  oid *pCtx, const
05b0: 20 63 68 61 72 20 2a 7a 54 61 62 29 3b 0a 20 20   char *zTab);.  
05c0: 73 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20  sqlite3_session 
05d0: 2a 70 4e 65 78 74 3b 20 20 20 20 20 20 20 20 20  *pNext;         
05e0: 2f 2a 20 4e 65 78 74 20 73 65 73 73 69 6f 6e 20  /* Next session 
05f0: 6f 62 6a 65 63 74 20 6f 6e 20 73 61 6d 65 20 64  object on same d
0600: 62 2e 20 2a 2f 0a 20 20 53 65 73 73 69 6f 6e 54  b. */.  SessionT
0610: 61 62 6c 65 20 2a 70 54 61 62 6c 65 3b 20 20 20  able *pTable;   
0620: 20 20 20 20 20 20 20 20 2f 2a 20 4c 69 73 74 20          /* List 
0630: 6f 66 20 61 74 74 61 63 68 65 64 20 74 61 62 6c  of attached tabl
0640: 65 73 20 2a 2f 0a 20 20 53 65 73 73 69 6f 6e 48  es */.  SessionH
0650: 6f 6f 6b 20 68 6f 6f 6b 3b 20 20 20 20 20 20 20  ook hook;       
0660: 20 20 20 20 20 20 20 20 2f 2a 20 41 50 49 73 20          /* APIs 
0670: 74 6f 20 67 72 61 62 20 6e 65 77 20 61 6e 64 20  to grab new and 
0680: 6f 6c 64 20 64 61 74 61 20 77 69 74 68 20 2a 2f  old data with */
0690: 0a 7d 3b 0a 0a 2f 2a 0a 2a 2a 20 49 6e 73 74 61  .};../*.** Insta
06a0: 6e 63 65 73 20 6f 66 20 74 68 69 73 20 73 74 72  nces of this str
06b0: 75 63 74 75 72 65 20 61 72 65 20 75 73 65 64 20  ucture are used 
06c0: 74 6f 20 62 75 69 6c 64 20 73 74 72 69 6e 67 73  to build strings
06d0: 20 6f 72 20 62 69 6e 61 72 79 20 72 65 63 6f 72   or binary recor
06e0: 64 73 2e 0a 2a 2f 0a 73 74 72 75 63 74 20 53 65  ds..*/.struct Se
06f0: 73 73 69 6f 6e 42 75 66 66 65 72 20 7b 0a 20 20  ssionBuffer {.  
0700: 75 38 20 2a 61 42 75 66 3b 20 20 20 20 20 20 20  u8 *aBuf;       
0710: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0720: 2f 2a 20 50 6f 69 6e 74 65 72 20 74 6f 20 63 68  /* Pointer to ch
0730: 61 6e 67 65 73 65 74 20 62 75 66 66 65 72 20 2a  angeset buffer *
0740: 2f 0a 20 20 69 6e 74 20 6e 42 75 66 3b 20 20 20  /.  int nBuf;   
0750: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0760: 20 20 20 20 2f 2a 20 53 69 7a 65 20 6f 66 20 62      /* Size of b
0770: 75 66 66 65 72 20 61 42 75 66 20 2a 2f 0a 20 20  uffer aBuf */.  
0780: 69 6e 74 20 6e 41 6c 6c 6f 63 3b 20 20 20 20 20  int nAlloc;     
0790: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
07a0: 2f 2a 20 53 69 7a 65 20 6f 66 20 61 6c 6c 6f 63  /* Size of alloc
07b0: 61 74 69 6f 6e 20 63 6f 6e 74 61 69 6e 69 6e 67  ation containing
07c0: 20 61 42 75 66 20 2a 2f 0a 7d 3b 0a 0a 2f 2a 0a   aBuf */.};../*.
07d0: 2a 2a 20 41 6e 20 6f 62 6a 65 63 74 20 6f 66 20  ** An object of 
07e0: 74 68 69 73 20 74 79 70 65 20 69 73 20 75 73 65  this type is use
07f0: 64 20 69 6e 74 65 72 6e 61 6c 6c 79 20 61 73 20  d internally as 
0800: 61 6e 20 61 62 73 74 72 61 63 74 69 6f 6e 20 66  an abstraction f
0810: 6f 72 20 0a 2a 2a 20 69 6e 70 75 74 20 64 61 74  or .** input dat
0820: 61 2e 20 49 6e 70 75 74 20 64 61 74 61 20 6d 61  a. Input data ma
0830: 79 20 62 65 20 73 75 70 70 6c 69 65 64 20 65 69  y be supplied ei
0840: 74 68 65 72 20 61 73 20 61 20 73 69 6e 67 6c 65  ther as a single
0850: 20 6c 61 72 67 65 20 62 75 66 66 65 72 0a 2a 2a   large buffer.**
0860: 20 28 65 2e 67 2e 20 73 71 6c 69 74 65 33 63 68   (e.g. sqlite3ch
0870: 61 6e 67 65 73 65 74 5f 73 74 61 72 74 28 29 29  angeset_start())
0880: 20 6f 72 20 75 73 69 6e 67 20 61 20 73 74 72 65   or using a stre
0890: 61 6d 20 66 75 6e 63 74 69 6f 6e 20 28 65 2e 67  am function (e.g
08a0: 2e 0a 2a 2a 20 20 73 71 6c 69 74 65 33 63 68 61  ..**  sqlite3cha
08b0: 6e 67 65 73 65 74 5f 73 74 61 72 74 5f 73 74 72  ngeset_start_str
08c0: 6d 28 29 29 2e 0a 2a 2f 0a 73 74 72 75 63 74 20  m())..*/.struct 
08d0: 53 65 73 73 69 6f 6e 49 6e 70 75 74 20 7b 0a 20  SessionInput {. 
08e0: 20 69 6e 74 20 62 4e 6f 44 69 73 63 61 72 64 3b   int bNoDiscard;
08f0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0900: 20 2f 2a 20 49 66 20 74 72 75 65 2c 20 64 69 73   /* If true, dis
0910: 63 61 72 64 20 6e 6f 20 64 61 74 61 20 2a 2f 0a  card no data */.
0920: 20 20 69 6e 74 20 69 43 75 72 72 65 6e 74 3b 20    int iCurrent; 
0930: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0940: 20 20 2f 2a 20 4f 66 66 73 65 74 20 69 6e 20 61    /* Offset in a
0950: 44 61 74 61 5b 5d 20 6f 66 20 63 75 72 72 65 6e  Data[] of curren
0960: 74 20 63 68 61 6e 67 65 20 2a 2f 0a 20 20 69 6e  t change */.  in
0970: 74 20 69 4e 65 78 74 3b 20 20 20 20 20 20 20 20  t iNext;        
0980: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
0990: 20 4f 66 66 73 65 74 20 69 6e 20 61 44 61 74 61   Offset in aData
09a0: 5b 5d 20 6f 66 20 6e 65 78 74 20 63 68 61 6e 67  [] of next chang
09b0: 65 20 2a 2f 0a 20 20 75 38 20 2a 61 44 61 74 61  e */.  u8 *aData
09c0: 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  ;               
09d0: 20 20 20 20 20 20 20 2f 2a 20 50 6f 69 6e 74 65         /* Pointe
09e0: 72 20 74 6f 20 62 75 66 66 65 72 20 63 6f 6e 74  r to buffer cont
09f0: 61 69 6e 69 6e 67 20 63 68 61 6e 67 65 73 65 74  aining changeset
0a00: 20 2a 2f 0a 20 20 69 6e 74 20 6e 44 61 74 61 3b   */.  int nData;
0a10: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0a20: 20 20 20 20 20 20 2f 2a 20 4e 75 6d 62 65 72 20        /* Number 
0a30: 6f 66 20 62 79 74 65 73 20 69 6e 20 61 44 61 74  of bytes in aDat
0a40: 61 20 2a 2f 0a 0a 20 20 53 65 73 73 69 6f 6e 42  a */..  SessionB
0a50: 75 66 66 65 72 20 62 75 66 3b 20 20 20 20 20 20  uffer buf;      
0a60: 20 20 20 20 20 20 20 20 2f 2a 20 43 75 72 72 65          /* Curre
0a70: 6e 74 20 72 65 61 64 20 62 75 66 66 65 72 20 2a  nt read buffer *
0a80: 2f 0a 20 20 69 6e 74 20 28 2a 78 49 6e 70 75 74  /.  int (*xInput
0a90: 29 28 76 6f 69 64 2a 2c 20 76 6f 69 64 2a 2c 20  )(void*, void*, 
0aa0: 69 6e 74 2a 29 3b 20 20 20 20 20 20 20 20 2f 2a  int*);        /*
0ab0: 20 49 6e 70 75 74 20 73 74 72 65 61 6d 20 63 61   Input stream ca
0ac0: 6c 6c 20 28 6f 72 20 4e 55 4c 4c 29 20 2a 2f 0a  ll (or NULL) */.
0ad0: 20 20 76 6f 69 64 20 2a 70 49 6e 3b 20 20 20 20    void *pIn;    
0ae0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0af0: 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 46              /* F
0b00: 69 72 73 74 20 61 72 67 75 6d 65 6e 74 20 74 6f  irst argument to
0b10: 20 78 49 6e 70 75 74 20 2a 2f 0a 20 20 69 6e 74   xInput */.  int
0b20: 20 62 45 6f 66 3b 20 20 20 20 20 20 20 20 20 20   bEof;          
0b30: 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
0b40: 53 65 74 20 74 6f 20 74 72 75 65 20 61 66 74 65  Set to true afte
0b50: 72 20 78 49 6e 70 75 74 20 66 69 6e 69 73 68 65  r xInput finishe
0b60: 64 20 2a 2f 0a 7d 3b 0a 0a 2f 2a 0a 2a 2a 20 53  d */.};../*.** S
0b70: 74 72 75 63 74 75 72 65 20 66 6f 72 20 63 68 61  tructure for cha
0b80: 6e 67 65 73 65 74 20 69 74 65 72 61 74 6f 72 73  ngeset iterators
0b90: 2e 0a 2a 2f 0a 73 74 72 75 63 74 20 73 71 6c 69  ..*/.struct sqli
0ba0: 74 65 33 5f 63 68 61 6e 67 65 73 65 74 5f 69 74  te3_changeset_it
0bb0: 65 72 20 7b 0a 20 20 53 65 73 73 69 6f 6e 49 6e  er {.  SessionIn
0bc0: 70 75 74 20 69 6e 3b 20 20 20 20 20 20 20 20 20  put in;         
0bd0: 20 20 20 20 20 20 20 2f 2a 20 49 6e 70 75 74 20         /* Input 
0be0: 62 75 66 66 65 72 20 6f 72 20 73 74 72 65 61 6d  buffer or stream
0bf0: 20 2a 2f 0a 20 20 53 65 73 73 69 6f 6e 42 75 66   */.  SessionBuf
0c00: 66 65 72 20 74 62 6c 68 64 72 3b 20 20 20 20 20  fer tblhdr;     
0c10: 20 20 20 20 20 20 2f 2a 20 42 75 66 66 65 72 20        /* Buffer 
0c20: 74 6f 20 68 6f 6c 64 20 61 70 56 61 6c 75 65 2f  to hold apValue/
0c30: 7a 54 61 62 2f 61 62 50 4b 2f 20 2a 2f 0a 20 20  zTab/abPK/ */.  
0c40: 69 6e 74 20 62 50 61 74 63 68 73 65 74 3b 20 20  int bPatchset;  
0c50: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0c60: 2f 2a 20 54 72 75 65 20 69 66 20 74 68 69 73 20  /* True if this 
0c70: 69 73 20 61 20 70 61 74 63 68 73 65 74 20 2a 2f  is a patchset */
0c80: 0a 20 20 69 6e 74 20 72 63 3b 20 20 20 20 20 20  .  int rc;      
0c90: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0ca0: 20 20 20 2f 2a 20 49 74 65 72 61 74 6f 72 20 65     /* Iterator e
0cb0: 72 72 6f 72 20 63 6f 64 65 20 2a 2f 0a 20 20 73  rror code */.  s
0cc0: 71 6c 69 74 65 33 5f 73 74 6d 74 20 2a 70 43 6f  qlite3_stmt *pCo
0cd0: 6e 66 6c 69 63 74 3b 20 20 20 20 20 20 20 20 2f  nflict;        /
0ce0: 2a 20 50 6f 69 6e 74 73 20 74 6f 20 63 6f 6e 66  * Points to conf
0cf0: 6c 69 63 74 69 6e 67 20 72 6f 77 2c 20 69 66 20  licting row, if 
0d00: 61 6e 79 20 2a 2f 0a 20 20 63 68 61 72 20 2a 7a  any */.  char *z
0d10: 54 61 62 3b 20 20 20 20 20 20 20 20 20 20 20 20  Tab;            
0d20: 20 20 20 20 20 20 20 20 20 2f 2a 20 43 75 72 72           /* Curr
0d30: 65 6e 74 20 74 61 62 6c 65 20 2a 2f 0a 20 20 69  ent table */.  i
0d40: 6e 74 20 6e 43 6f 6c 3b 20 20 20 20 20 20 20 20  nt nCol;        
0d50: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
0d60: 2a 20 4e 75 6d 62 65 72 20 6f 66 20 63 6f 6c 75  * Number of colu
0d70: 6d 6e 73 20 69 6e 20 7a 54 61 62 20 2a 2f 0a 20  mns in zTab */. 
0d80: 20 69 6e 74 20 6f 70 3b 20 20 20 20 20 20 20 20   int op;        
0d90: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0da0: 20 2f 2a 20 43 75 72 72 65 6e 74 20 6f 70 65 72   /* Current oper
0db0: 61 74 69 6f 6e 20 2a 2f 0a 20 20 69 6e 74 20 62  ation */.  int b
0dc0: 49 6e 64 69 72 65 63 74 3b 20 20 20 20 20 20 20  Indirect;       
0dd0: 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 54 72             /* Tr
0de0: 75 65 20 69 66 20 63 75 72 72 65 6e 74 20 63 68  ue if current ch
0df0: 61 6e 67 65 20 77 61 73 20 69 6e 64 69 72 65 63  ange was indirec
0e00: 74 20 2a 2f 0a 20 20 75 38 20 2a 61 62 50 4b 3b  t */.  u8 *abPK;
0e10: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
0e20: 20 20 20 20 20 20 20 2f 2a 20 50 72 69 6d 61 72         /* Primar
0e30: 79 20 6b 65 79 20 61 72 72 61 79 20 2a 2f 0a 20  y key array */. 
0e40: 20 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 20 2a   sqlite3_value *
0e50: 2a 61 70 56 61 6c 75 65 3b 20 20 20 20 20 20 20  *apValue;       
0e60: 20 2f 2a 20 6f 6c 64 2e 2a 20 61 6e 64 20 6e 65   /* old.* and ne
0e70: 77 2e 2a 20 76 61 6c 75 65 73 20 2a 2f 0a 7d 3b  w.* values */.};
0e80: 0a 0a 2f 2a 0a 2a 2a 20 45 61 63 68 20 73 65 73  ../*.** Each ses
0e90: 73 69 6f 6e 20 6f 62 6a 65 63 74 20 6d 61 69 6e  sion object main
0ea0: 74 61 69 6e 73 20 61 20 73 65 74 20 6f 66 20 74  tains a set of t
0eb0: 68 65 20 66 6f 6c 6c 6f 77 69 6e 67 20 73 74 72  he following str
0ec0: 75 63 74 75 72 65 73 2c 20 6f 6e 65 0a 2a 2a 20  uctures, one.** 
0ed0: 66 6f 72 20 65 61 63 68 20 74 61 62 6c 65 20 74  for each table t
0ee0: 68 65 20 73 65 73 73 69 6f 6e 20 6f 62 6a 65 63  he session objec
0ef0: 74 20 69 73 20 6d 6f 6e 69 74 6f 72 69 6e 67 2e  t is monitoring.
0f00: 20 54 68 65 20 73 74 72 75 63 74 75 72 65 73 20   The structures 
0f10: 61 72 65 0a 2a 2a 20 73 74 6f 72 65 64 20 69 6e  are.** stored in
0f20: 20 61 20 6c 69 6e 6b 65 64 20 6c 69 73 74 20 73   a linked list s
0f30: 74 61 72 74 69 6e 67 20 61 74 20 73 71 6c 69 74  tarting at sqlit
0f40: 65 33 5f 73 65 73 73 69 6f 6e 2e 70 54 61 62 6c  e3_session.pTabl
0f50: 65 2e 0a 2a 2a 0a 2a 2a 20 54 68 65 20 6b 65 79  e..**.** The key
0f60: 73 20 6f 66 20 74 68 65 20 53 65 73 73 69 6f 6e  s of the Session
0f70: 54 61 62 6c 65 2e 61 43 68 61 6e 67 65 5b 5d 20  Table.aChange[] 
0f80: 68 61 73 68 20 74 61 62 6c 65 20 61 72 65 20 61  hash table are a
0f90: 6c 6c 20 72 6f 77 73 20 74 68 61 74 20 68 61 76  ll rows that hav
0fa0: 65 0a 2a 2a 20 62 65 65 6e 20 6d 6f 64 69 66 69  e.** been modifi
0fb0: 65 64 20 69 6e 20 61 6e 79 20 77 61 79 20 73 69  ed in any way si
0fc0: 6e 63 65 20 74 68 65 20 73 65 73 73 69 6f 6e 20  nce the session 
0fd0: 6f 62 6a 65 63 74 20 77 61 73 20 61 74 74 61 63  object was attac
0fe0: 68 65 64 20 74 6f 20 74 68 65 0a 2a 2a 20 74 61  hed to the.** ta
0ff0: 62 6c 65 2e 0a 2a 2a 0a 2a 2a 20 54 68 65 20 64  ble..**.** The d
1000: 61 74 61 20 61 73 73 6f 63 69 61 74 65 64 20 77  ata associated w
1010: 69 74 68 20 65 61 63 68 20 68 61 73 68 2d 74 61  ith each hash-ta
1020: 62 6c 65 20 65 6e 74 72 79 20 69 73 20 61 20 73  ble entry is a s
1030: 74 72 75 63 74 75 72 65 20 63 6f 6e 74 61 69 6e  tructure contain
1040: 69 6e 67 0a 2a 2a 20 61 20 73 75 62 73 65 74 20  ing.** a subset 
1050: 6f 66 20 74 68 65 20 69 6e 69 74 69 61 6c 20 76  of the initial v
1060: 61 6c 75 65 73 20 74 68 61 74 20 74 68 65 20 6d  alues that the m
1070: 6f 64 69 66 69 65 64 20 72 6f 77 20 63 6f 6e 74  odified row cont
1080: 61 69 6e 65 64 20 61 74 20 74 68 65 0a 2a 2a 20  ained at the.** 
1090: 73 74 61 72 74 20 6f 66 20 74 68 65 20 73 65 73  start of the ses
10a0: 73 69 6f 6e 2e 20 4f 72 20 6e 6f 20 69 6e 69 74  sion. Or no init
10b0: 69 61 6c 20 76 61 6c 75 65 73 20 69 66 20 74 68  ial values if th
10c0: 65 20 72 6f 77 20 77 61 73 20 69 6e 73 65 72 74  e row was insert
10d0: 65 64 2e 0a 2a 2f 0a 73 74 72 75 63 74 20 53 65  ed..*/.struct Se
10e0: 73 73 69 6f 6e 54 61 62 6c 65 20 7b 0a 20 20 53  ssionTable {.  S
10f0: 65 73 73 69 6f 6e 54 61 62 6c 65 20 2a 70 4e 65  essionTable *pNe
1100: 78 74 3b 0a 20 20 63 68 61 72 20 2a 7a 4e 61 6d  xt;.  char *zNam
1110: 65 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 20  e;              
1120: 20 20 20 20 20 20 2f 2a 20 4c 6f 63 61 6c 20 6e        /* Local n
1130: 61 6d 65 20 6f 66 20 74 61 62 6c 65 20 2a 2f 0a  ame of table */.
1140: 20 20 69 6e 74 20 6e 43 6f 6c 3b 20 20 20 20 20    int nCol;     
1150: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1160: 20 20 2f 2a 20 4e 75 6d 62 65 72 20 6f 66 20 63    /* Number of c
1170: 6f 6c 75 6d 6e 73 20 69 6e 20 74 61 62 6c 65 20  olumns in table 
1180: 7a 4e 61 6d 65 20 2a 2f 0a 20 20 63 6f 6e 73 74  zName */.  const
1190: 20 63 68 61 72 20 2a 2a 61 7a 43 6f 6c 3b 20 20   char **azCol;  
11a0: 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 43 6f             /* Co
11b0: 6c 75 6d 6e 20 6e 61 6d 65 73 20 2a 2f 0a 20 20  lumn names */.  
11c0: 75 38 20 2a 61 62 50 4b 3b 20 20 20 20 20 20 20  u8 *abPK;       
11d0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
11e0: 2f 2a 20 41 72 72 61 79 20 6f 66 20 70 72 69 6d  /* Array of prim
11f0: 61 72 79 20 6b 65 79 20 66 6c 61 67 73 20 2a 2f  ary key flags */
1200: 0a 20 20 69 6e 74 20 6e 45 6e 74 72 79 3b 20 20  .  int nEntry;  
1210: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1220: 20 20 20 2f 2a 20 54 6f 74 61 6c 20 6e 75 6d 62     /* Total numb
1230: 65 72 20 6f 66 20 65 6e 74 72 69 65 73 20 69 6e  er of entries in
1240: 20 68 61 73 68 20 74 61 62 6c 65 20 2a 2f 0a 20   hash table */. 
1250: 20 69 6e 74 20 6e 43 68 61 6e 67 65 3b 20 20 20   int nChange;   
1260: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1270: 20 2f 2a 20 53 69 7a 65 20 6f 66 20 61 70 43 68   /* Size of apCh
1280: 61 6e 67 65 5b 5d 20 61 72 72 61 79 20 2a 2f 0a  ange[] array */.
1290: 20 20 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 20    SessionChange 
12a0: 2a 2a 61 70 43 68 61 6e 67 65 3b 20 20 20 20 20  **apChange;     
12b0: 20 20 2f 2a 20 48 61 73 68 20 74 61 62 6c 65 20    /* Hash table 
12c0: 62 75 63 6b 65 74 73 20 2a 2f 0a 7d 3b 0a 0a 2f  buckets */.};../
12d0: 2a 20 0a 2a 2a 20 52 45 43 4f 52 44 20 46 4f 52  * .** RECORD FOR
12e0: 4d 41 54 3a 0a 2a 2a 0a 2a 2a 20 54 68 65 20 66  MAT:.**.** The f
12f0: 6f 6c 6c 6f 77 69 6e 67 20 72 65 63 6f 72 64 20  ollowing record 
1300: 66 6f 72 6d 61 74 20 69 73 20 73 69 6d 69 6c 61  format is simila
1310: 72 20 74 6f 20 28 62 75 74 20 6e 6f 74 20 63 6f  r to (but not co
1320: 6d 70 61 74 69 62 6c 65 20 77 69 74 68 29 20 74  mpatible with) t
1330: 68 61 74 20 0a 2a 2a 20 75 73 65 64 20 69 6e 20  hat .** used in 
1340: 53 51 4c 69 74 65 20 64 61 74 61 62 61 73 65 20  SQLite database 
1350: 66 69 6c 65 73 2e 20 54 68 69 73 20 66 6f 72 6d  files. This form
1360: 61 74 20 69 73 20 75 73 65 64 20 61 73 20 70 61  at is used as pa
1370: 72 74 20 6f 66 20 74 68 65 20 0a 2a 2a 20 63 68  rt of the .** ch
1380: 61 6e 67 65 2d 73 65 74 20 62 69 6e 61 72 79 20  ange-set binary 
1390: 66 6f 72 6d 61 74 2c 20 61 6e 64 20 73 6f 20 6d  format, and so m
13a0: 75 73 74 20 62 65 20 61 72 63 68 69 74 65 63 74  ust be architect
13b0: 75 72 65 20 69 6e 64 65 70 65 6e 64 65 6e 74 2e  ure independent.
13c0: 0a 2a 2a 0a 2a 2a 20 55 6e 6c 69 6b 65 20 74 68  .**.** Unlike th
13d0: 65 20 53 51 4c 69 74 65 20 64 61 74 61 62 61 73  e SQLite databas
13e0: 65 20 72 65 63 6f 72 64 20 66 6f 72 6d 61 74 2c  e record format,
13f0: 20 65 61 63 68 20 66 69 65 6c 64 20 69 73 20 73   each field is s
1400: 65 6c 66 2d 63 6f 6e 74 61 69 6e 65 64 20 2d 0a  elf-contained -.
1410: 2a 2a 20 74 68 65 72 65 20 69 73 20 6e 6f 20 73  ** there is no s
1420: 65 70 61 72 61 74 69 6f 6e 20 6f 66 20 68 65 61  eparation of hea
1430: 64 65 72 20 61 6e 64 20 64 61 74 61 2e 20 45 61  der and data. Ea
1440: 63 68 20 66 69 65 6c 64 20 62 65 67 69 6e 73 20  ch field begins 
1450: 77 69 74 68 20 61 0a 2a 2a 20 73 69 6e 67 6c 65  with a.** single
1460: 20 62 79 74 65 20 64 65 73 63 72 69 62 69 6e 67   byte describing
1470: 20 69 74 73 20 74 79 70 65 2c 20 61 73 20 66 6f   its type, as fo
1480: 6c 6c 6f 77 73 3a 0a 2a 2a 0a 2a 2a 20 20 20 20  llows:.**.**    
1490: 20 20 20 30 78 30 30 3a 20 55 6e 64 65 66 69 6e     0x00: Undefin
14a0: 65 64 20 76 61 6c 75 65 2e 0a 2a 2a 20 20 20 20  ed value..**    
14b0: 20 20 20 30 78 30 31 3a 20 49 6e 74 65 67 65 72     0x01: Integer
14c0: 20 76 61 6c 75 65 2e 0a 2a 2a 20 20 20 20 20 20   value..**      
14d0: 20 30 78 30 32 3a 20 52 65 61 6c 20 76 61 6c 75   0x02: Real valu
14e0: 65 2e 0a 2a 2a 20 20 20 20 20 20 20 30 78 30 33  e..**       0x03
14f0: 3a 20 54 65 78 74 20 76 61 6c 75 65 2e 0a 2a 2a  : Text value..**
1500: 20 20 20 20 20 20 20 30 78 30 34 3a 20 42 6c 6f         0x04: Blo
1510: 62 20 76 61 6c 75 65 2e 0a 2a 2a 20 20 20 20 20  b value..**     
1520: 20 20 30 78 30 35 3a 20 53 51 4c 20 4e 55 4c 4c    0x05: SQL NULL
1530: 20 76 61 6c 75 65 2e 0a 2a 2a 0a 2a 2a 20 4e 6f   value..**.** No
1540: 74 65 20 74 68 61 74 20 74 68 65 20 61 62 6f 76  te that the abov
1550: 65 20 6d 61 74 63 68 20 74 68 65 20 64 65 66 69  e match the defi
1560: 6e 69 74 69 6f 6e 73 20 6f 66 20 53 51 4c 49 54  nitions of SQLIT
1570: 45 5f 49 4e 54 45 47 45 52 2c 20 53 51 4c 49 54  E_INTEGER, SQLIT
1580: 45 5f 54 45 58 54 0a 2a 2a 20 61 6e 64 20 73 6f  E_TEXT.** and so
1590: 20 6f 6e 20 69 6e 20 73 71 6c 69 74 65 33 2e 68   on in sqlite3.h
15a0: 2e 20 46 6f 72 20 75 6e 64 65 66 69 6e 65 64 20  . For undefined 
15b0: 61 6e 64 20 4e 55 4c 4c 20 76 61 6c 75 65 73 2c  and NULL values,
15c0: 20 74 68 65 20 66 69 65 6c 64 20 63 6f 6e 73 69   the field consi
15d0: 73 74 73 0a 2a 2a 20 6f 6e 6c 79 20 6f 66 20 74  sts.** only of t
15e0: 68 65 20 73 69 6e 67 6c 65 20 74 79 70 65 20 62  he single type b
15f0: 79 74 65 2e 20 46 6f 72 20 6f 74 68 65 72 20 74  yte. For other t
1600: 79 70 65 73 20 6f 66 20 76 61 6c 75 65 73 2c 20  ypes of values, 
1610: 74 68 65 20 74 79 70 65 20 62 79 74 65 0a 2a 2a  the type byte.**
1620: 20 69 73 20 66 6f 6c 6c 6f 77 65 64 20 62 79 3a   is followed by:
1630: 0a 2a 2a 0a 2a 2a 20 20 20 54 65 78 74 20 76 61  .**.**   Text va
1640: 6c 75 65 73 3a 0a 2a 2a 20 20 20 20 20 41 20 76  lues:.**     A v
1650: 61 72 69 6e 74 20 63 6f 6e 74 61 69 6e 69 6e 67  arint containing
1660: 20 74 68 65 20 6e 75 6d 62 65 72 20 6f 66 20 62   the number of b
1670: 79 74 65 73 20 69 6e 20 74 68 65 20 76 61 6c 75  ytes in the valu
1680: 65 20 28 65 6e 63 6f 64 65 64 20 75 73 69 6e 67  e (encoded using
1690: 0a 2a 2a 20 20 20 20 20 55 54 46 2d 38 29 2e 20  .**     UTF-8). 
16a0: 46 6f 6c 6c 6f 77 65 64 20 62 79 20 61 20 62 75  Followed by a bu
16b0: 66 66 65 72 20 63 6f 6e 74 61 69 6e 69 6e 67 20  ffer containing 
16c0: 74 68 65 20 55 54 46 2d 38 20 72 65 70 72 65 73  the UTF-8 repres
16d0: 65 6e 74 61 74 69 6f 6e 0a 2a 2a 20 20 20 20 20  entation.**     
16e0: 6f 66 20 74 68 65 20 74 65 78 74 20 76 61 6c 75  of the text valu
16f0: 65 2e 20 54 68 65 72 65 20 69 73 20 6e 6f 20 6e  e. There is no n
1700: 75 6c 20 74 65 72 6d 69 6e 61 74 6f 72 2e 0a 2a  ul terminator..*
1710: 2a 0a 2a 2a 20 20 20 42 6c 6f 62 20 76 61 6c 75  *.**   Blob valu
1720: 65 73 3a 0a 2a 2a 20 20 20 20 20 41 20 76 61 72  es:.**     A var
1730: 69 6e 74 20 63 6f 6e 74 61 69 6e 69 6e 67 20 74  int containing t
1740: 68 65 20 6e 75 6d 62 65 72 20 6f 66 20 62 79 74  he number of byt
1750: 65 73 20 69 6e 20 74 68 65 20 76 61 6c 75 65 2c  es in the value,
1760: 20 66 6f 6c 6c 6f 77 65 64 20 62 79 0a 2a 2a 20   followed by.** 
1770: 20 20 20 20 61 20 62 75 66 66 65 72 20 63 6f 6e      a buffer con
1780: 74 61 69 6e 69 6e 67 20 74 68 65 20 76 61 6c 75  taining the valu
1790: 65 20 69 74 73 65 6c 66 2e 0a 2a 2a 0a 2a 2a 20  e itself..**.** 
17a0: 20 20 49 6e 74 65 67 65 72 20 76 61 6c 75 65 73    Integer values
17b0: 3a 0a 2a 2a 20 20 20 20 20 41 6e 20 38 2d 62 79  :.**     An 8-by
17c0: 74 65 20 62 69 67 2d 65 6e 64 69 61 6e 20 69 6e  te big-endian in
17d0: 74 65 67 65 72 20 76 61 6c 75 65 2e 0a 2a 2a 0a  teger value..**.
17e0: 2a 2a 20 20 20 52 65 61 6c 20 76 61 6c 75 65 73  **   Real values
17f0: 3a 0a 2a 2a 20 20 20 20 20 41 6e 20 38 2d 62 79  :.**     An 8-by
1800: 74 65 20 62 69 67 2d 65 6e 64 69 61 6e 20 49 45  te big-endian IE
1810: 45 45 20 37 35 34 2d 32 30 30 38 20 72 65 61 6c  EE 754-2008 real
1820: 20 76 61 6c 75 65 2e 0a 2a 2a 0a 2a 2a 20 56 61   value..**.** Va
1830: 72 69 6e 74 20 76 61 6c 75 65 73 20 61 72 65 20  rint values are 
1840: 65 6e 63 6f 64 65 64 20 69 6e 20 74 68 65 20 73  encoded in the s
1850: 61 6d 65 20 77 61 79 20 61 73 20 76 61 72 69 6e  ame way as varin
1860: 74 73 20 69 6e 20 74 68 65 20 53 51 4c 69 74 65  ts in the SQLite
1870: 20 0a 2a 2a 20 72 65 63 6f 72 64 20 66 6f 72 6d   .** record form
1880: 61 74 2e 0a 2a 2a 0a 2a 2a 20 43 48 41 4e 47 45  at..**.** CHANGE
1890: 53 45 54 20 46 4f 52 4d 41 54 3a 0a 2a 2a 0a 2a  SET FORMAT:.**.*
18a0: 2a 20 41 20 63 68 61 6e 67 65 73 65 74 20 69 73  * A changeset is
18b0: 20 61 20 63 6f 6c 6c 65 63 74 69 6f 6e 20 6f 66   a collection of
18c0: 20 44 45 4c 45 54 45 2c 20 55 50 44 41 54 45 20   DELETE, UPDATE 
18d0: 61 6e 64 20 49 4e 53 45 52 54 20 6f 70 65 72 61  and INSERT opera
18e0: 74 69 6f 6e 73 20 6f 6e 0a 2a 2a 20 6f 6e 65 20  tions on.** one 
18f0: 6f 72 20 6d 6f 72 65 20 74 61 62 6c 65 73 2e 20  or more tables. 
1900: 4f 70 65 72 61 74 69 6f 6e 73 20 6f 6e 20 61 20  Operations on a 
1910: 73 69 6e 67 6c 65 20 74 61 62 6c 65 20 61 72 65  single table are
1920: 20 67 72 6f 75 70 65 64 20 74 6f 67 65 74 68 65   grouped togethe
1930: 72 2c 0a 2a 2a 20 62 75 74 20 6d 61 79 20 6f 63  r,.** but may oc
1940: 63 75 72 20 69 6e 20 61 6e 79 20 6f 72 64 65 72  cur in any order
1950: 20 28 69 2e 65 2e 20 64 65 6c 65 74 65 73 2c 20   (i.e. deletes, 
1960: 75 70 64 61 74 65 73 20 61 6e 64 20 69 6e 73 65  updates and inse
1970: 72 74 73 20 61 72 65 20 61 6c 6c 0a 2a 2a 20 6d  rts are all.** m
1980: 69 78 65 64 20 74 6f 67 65 74 68 65 72 29 2e 0a  ixed together)..
1990: 2a 2a 0a 2a 2a 20 45 61 63 68 20 67 72 6f 75 70  **.** Each group
19a0: 20 6f 66 20 63 68 61 6e 67 65 73 20 62 65 67 69   of changes begi
19b0: 6e 73 20 77 69 74 68 20 61 20 74 61 62 6c 65 20  ns with a table 
19c0: 68 65 61 64 65 72 3a 0a 2a 2a 0a 2a 2a 20 20 20  header:.**.**   
19d0: 31 20 62 79 74 65 3a 20 43 6f 6e 73 74 61 6e 74  1 byte: Constant
19e0: 20 30 78 35 34 20 28 63 61 70 69 74 61 6c 20 27   0x54 (capital '
19f0: 54 27 29 0a 2a 2a 20 20 20 56 61 72 69 6e 74 3a  T').**   Varint:
1a00: 20 4e 75 6d 62 65 72 20 6f 66 20 63 6f 6c 75 6d   Number of colum
1a10: 6e 73 20 69 6e 20 74 68 65 20 74 61 62 6c 65 2e  ns in the table.
1a20: 0a 2a 2a 20 20 20 6e 43 6f 6c 20 62 79 74 65 73  .**   nCol bytes
1a30: 3a 20 30 78 30 31 20 66 6f 72 20 50 4b 20 63 6f  : 0x01 for PK co
1a40: 6c 75 6d 6e 73 2c 20 30 78 30 30 20 6f 74 68 65  lumns, 0x00 othe
1a50: 72 77 69 73 65 2e 0a 2a 2a 20 20 20 4e 20 62 79  rwise..**   N by
1a60: 74 65 73 3a 20 55 6e 71 75 61 6c 69 66 69 65 64  tes: Unqualified
1a70: 20 74 61 62 6c 65 20 6e 61 6d 65 20 28 65 6e 63   table name (enc
1a80: 6f 64 65 64 20 75 73 69 6e 67 20 55 54 46 2d 38  oded using UTF-8
1a90: 29 2e 20 4e 75 6c 2d 74 65 72 6d 69 6e 61 74 65  ). Nul-terminate
1aa0: 64 2e 0a 2a 2a 0a 2a 2a 20 46 6f 6c 6c 6f 77 65  d..**.** Followe
1ab0: 64 20 62 79 20 6f 6e 65 20 6f 72 20 6d 6f 72 65  d by one or more
1ac0: 20 63 68 61 6e 67 65 73 20 74 6f 20 74 68 65 20   changes to the 
1ad0: 74 61 62 6c 65 2e 0a 2a 2a 0a 2a 2a 20 20 20 31  table..**.**   1
1ae0: 20 62 79 74 65 3a 20 45 69 74 68 65 72 20 53 51   byte: Either SQ
1af0: 4c 49 54 45 5f 49 4e 53 45 52 54 20 28 30 78 31  LITE_INSERT (0x1
1b00: 32 29 2c 20 55 50 44 41 54 45 20 28 30 78 31 37  2), UPDATE (0x17
1b10: 29 20 6f 72 20 44 45 4c 45 54 45 20 28 30 78 30  ) or DELETE (0x0
1b20: 39 29 2e 0a 2a 2a 20 20 20 31 20 62 79 74 65 3a  9)..**   1 byte:
1b30: 20 54 68 65 20 22 69 6e 64 69 72 65 63 74 2d 63   The "indirect-c
1b40: 68 61 6e 67 65 22 20 66 6c 61 67 2e 0a 2a 2a 20  hange" flag..** 
1b50: 20 20 6f 6c 64 2e 2a 20 72 65 63 6f 72 64 3a 20    old.* record: 
1b60: 28 64 65 6c 65 74 65 20 61 6e 64 20 75 70 64 61  (delete and upda
1b70: 74 65 20 6f 6e 6c 79 29 0a 2a 2a 20 20 20 6e 65  te only).**   ne
1b80: 77 2e 2a 20 72 65 63 6f 72 64 3a 20 28 69 6e 73  w.* record: (ins
1b90: 65 72 74 20 61 6e 64 20 75 70 64 61 74 65 20 6f  ert and update o
1ba0: 6e 6c 79 29 0a 2a 2a 0a 2a 2a 20 54 68 65 20 22  nly).**.** The "
1bb0: 6f 6c 64 2e 2a 22 20 61 6e 64 20 22 6e 65 77 2e  old.*" and "new.
1bc0: 2a 22 20 72 65 63 6f 72 64 73 2c 20 69 66 20 70  *" records, if p
1bd0: 72 65 73 65 6e 74 2c 20 61 72 65 20 4e 20 66 69  resent, are N fi
1be0: 65 6c 64 20 72 65 63 6f 72 64 73 20 69 6e 20 74  eld records in t
1bf0: 68 65 0a 2a 2a 20 66 6f 72 6d 61 74 20 64 65 73  he.** format des
1c00: 63 72 69 62 65 64 20 61 62 6f 76 65 20 75 6e 64  cribed above und
1c10: 65 72 20 22 52 45 43 4f 52 44 20 46 4f 52 4d 41  er "RECORD FORMA
1c20: 54 22 2c 20 77 68 65 72 65 20 4e 20 69 73 20 74  T", where N is t
1c30: 68 65 20 6e 75 6d 62 65 72 20 6f 66 0a 2a 2a 20  he number of.** 
1c40: 63 6f 6c 75 6d 6e 73 20 69 6e 20 74 68 65 20 74  columns in the t
1c50: 61 62 6c 65 2e 20 54 68 65 20 69 27 74 68 20 66  able. The i'th f
1c60: 69 65 6c 64 20 6f 66 20 65 61 63 68 20 72 65 63  ield of each rec
1c70: 6f 72 64 20 69 73 20 61 73 73 6f 63 69 61 74 65  ord is associate
1c80: 64 20 77 69 74 68 0a 2a 2a 20 74 68 65 20 69 27  d with.** the i'
1c90: 74 68 20 63 6f 6c 75 6d 6e 20 6f 66 20 74 68 65  th column of the
1ca0: 20 74 61 62 6c 65 2c 20 63 6f 75 6e 74 69 6e 67   table, counting
1cb0: 20 66 72 6f 6d 20 6c 65 66 74 20 74 6f 20 72 69   from left to ri
1cc0: 67 68 74 20 69 6e 20 74 68 65 20 6f 72 64 65 72  ght in the order
1cd0: 0a 2a 2a 20 69 6e 20 77 68 69 63 68 20 63 6f 6c  .** in which col
1ce0: 75 6d 6e 73 20 77 65 72 65 20 64 65 63 6c 61 72  umns were declar
1cf0: 65 64 20 69 6e 20 74 68 65 20 43 52 45 41 54 45  ed in the CREATE
1d00: 20 54 41 42 4c 45 20 73 74 61 74 65 6d 65 6e 74   TABLE statement
1d10: 2e 0a 2a 2a 0a 2a 2a 20 54 68 65 20 6e 65 77 2e  ..**.** The new.
1d20: 2a 20 72 65 63 6f 72 64 20 74 68 61 74 20 69 73  * record that is
1d30: 20 70 61 72 74 20 6f 66 20 65 61 63 68 20 49 4e   part of each IN
1d40: 53 45 52 54 20 63 68 61 6e 67 65 20 63 6f 6e 74  SERT change cont
1d50: 61 69 6e 73 20 74 68 65 20 76 61 6c 75 65 73 0a  ains the values.
1d60: 2a 2a 20 74 68 61 74 20 6d 61 6b 65 20 75 70 20  ** that make up 
1d70: 74 68 65 20 6e 65 77 20 72 6f 77 2e 20 53 69 6d  the new row. Sim
1d80: 69 6c 61 72 6c 79 2c 20 74 68 65 20 6f 6c 64 2e  ilarly, the old.
1d90: 2a 20 72 65 63 6f 72 64 20 74 68 61 74 20 69 73  * record that is
1da0: 20 70 61 72 74 20 6f 66 20 65 61 63 68 0a 2a 2a   part of each.**
1db0: 20 44 45 4c 45 54 45 20 63 68 61 6e 67 65 20 63   DELETE change c
1dc0: 6f 6e 74 61 69 6e 73 20 74 68 65 20 76 61 6c 75  ontains the valu
1dd0: 65 73 20 74 68 61 74 20 6d 61 64 65 20 75 70 20  es that made up 
1de0: 74 68 65 20 72 6f 77 20 74 68 61 74 20 77 61 73  the row that was
1df0: 20 64 65 6c 65 74 65 64 20 0a 2a 2a 20 66 72 6f   deleted .** fro
1e00: 6d 20 74 68 65 20 64 61 74 61 62 61 73 65 2e 20  m the database. 
1e10: 49 6e 20 74 68 65 20 63 68 61 6e 67 65 73 65 74  In the changeset
1e20: 20 66 6f 72 6d 61 74 2c 20 74 68 65 20 72 65 63   format, the rec
1e30: 6f 72 64 73 20 74 68 61 74 20 61 72 65 20 70 61  ords that are pa
1e40: 72 74 0a 2a 2a 20 6f 66 20 49 4e 53 45 52 54 20  rt.** of INSERT 
1e50: 6f 72 20 44 45 4c 45 54 45 20 63 68 61 6e 67 65  or DELETE change
1e60: 73 20 6e 65 76 65 72 20 63 6f 6e 74 61 69 6e 20  s never contain 
1e70: 61 6e 79 20 75 6e 64 65 66 69 6e 65 64 20 28 74  any undefined (t
1e80: 79 70 65 20 62 79 74 65 20 30 78 30 30 29 0a 2a  ype byte 0x00).*
1e90: 2a 20 66 69 65 6c 64 73 2e 0a 2a 2a 0a 2a 2a 20  * fields..**.** 
1ea0: 57 69 74 68 69 6e 20 74 68 65 20 6f 6c 64 2e 2a  Within the old.*
1eb0: 20 72 65 63 6f 72 64 20 61 73 73 6f 63 69 61 74   record associat
1ec0: 65 64 20 77 69 74 68 20 61 6e 20 55 50 44 41 54  ed with an UPDAT
1ed0: 45 20 63 68 61 6e 67 65 2c 20 61 6c 6c 20 66 69  E change, all fi
1ee0: 65 6c 64 73 0a 2a 2a 20 61 73 73 6f 63 69 61 74  elds.** associat
1ef0: 65 64 20 77 69 74 68 20 74 61 62 6c 65 20 63 6f  ed with table co
1f00: 6c 75 6d 6e 73 20 74 68 61 74 20 61 72 65 20 6e  lumns that are n
1f10: 6f 74 20 50 52 49 4d 41 52 59 20 4b 45 59 20 63  ot PRIMARY KEY c
1f20: 6f 6c 75 6d 6e 73 20 61 6e 64 20 61 72 65 0a 2a  olumns and are.*
1f30: 2a 20 6e 6f 74 20 6d 6f 64 69 66 69 65 64 20 62  * not modified b
1f40: 79 20 74 68 65 20 55 50 44 41 54 45 20 63 68 61  y the UPDATE cha
1f50: 6e 67 65 20 61 72 65 20 73 65 74 20 74 6f 20 22  nge are set to "
1f60: 75 6e 64 65 66 69 6e 65 64 22 2e 20 4f 74 68 65  undefined". Othe
1f70: 72 20 66 69 65 6c 64 73 0a 2a 2a 20 61 72 65 20  r fields.** are 
1f80: 73 65 74 20 74 6f 20 74 68 65 20 76 61 6c 75 65  set to the value
1f90: 73 20 74 68 61 74 20 6d 61 64 65 20 75 70 20 74  s that made up t
1fa0: 68 65 20 72 6f 77 20 62 65 66 6f 72 65 20 74 68  he row before th
1fb0: 65 20 55 50 44 41 54 45 20 74 68 61 74 20 74 68  e UPDATE that th
1fc0: 65 0a 2a 2a 20 63 68 61 6e 67 65 20 72 65 63 6f  e.** change reco
1fd0: 72 64 73 20 74 6f 6f 6b 20 70 6c 61 63 65 2e 20  rds took place. 
1fe0: 57 69 74 68 69 6e 20 74 68 65 20 6e 65 77 2e 2a  Within the new.*
1ff0: 20 72 65 63 6f 72 64 2c 20 66 69 65 6c 64 73 20   record, fields 
2000: 61 73 73 6f 63 69 61 74 65 64 20 0a 2a 2a 20 77  associated .** w
2010: 69 74 68 20 74 61 62 6c 65 20 63 6f 6c 75 6d 6e  ith table column
2020: 73 20 6d 6f 64 69 66 69 65 64 20 62 79 20 74 68  s modified by th
2030: 65 20 55 50 44 41 54 45 20 63 68 61 6e 67 65 20  e UPDATE change 
2040: 63 6f 6e 74 61 69 6e 20 74 68 65 20 6e 65 77 20  contain the new 
2050: 0a 2a 2a 20 76 61 6c 75 65 73 2e 20 46 69 65 6c  .** values. Fiel
2060: 64 73 20 61 73 73 6f 63 69 61 74 65 64 20 77 69  ds associated wi
2070: 74 68 20 74 61 62 6c 65 20 63 6f 6c 75 6d 6e 73  th table columns
2080: 20 74 68 61 74 20 61 72 65 20 6e 6f 74 20 6d 6f   that are not mo
2090: 64 69 66 69 65 64 0a 2a 2a 20 61 72 65 20 73 65  dified.** are se
20a0: 74 20 74 6f 20 22 75 6e 64 65 66 69 6e 65 64 22  t to "undefined"
20b0: 2e 0a 2a 2a 0a 2a 2a 20 50 41 54 43 48 53 45 54  ..**.** PATCHSET
20c0: 20 46 4f 52 4d 41 54 3a 0a 2a 2a 0a 2a 2a 20 41   FORMAT:.**.** A
20d0: 20 70 61 74 63 68 73 65 74 20 69 73 20 61 6c 73   patchset is als
20e0: 6f 20 61 20 63 6f 6c 6c 65 63 74 69 6f 6e 20 6f  o a collection o
20f0: 66 20 63 68 61 6e 67 65 73 2e 20 49 74 20 69 73  f changes. It is
2100: 20 73 69 6d 69 6c 61 72 20 74 6f 20 61 20 63 68   similar to a ch
2110: 61 6e 67 65 73 65 74 2c 0a 2a 2a 20 62 75 74 20  angeset,.** but 
2120: 6c 65 61 76 65 73 20 75 6e 64 65 66 69 6e 65 64  leaves undefined
2130: 20 74 68 6f 73 65 20 66 69 65 6c 64 73 20 74 68   those fields th
2140: 61 74 20 61 72 65 20 6e 6f 74 20 75 73 65 66 75  at are not usefu
2150: 6c 20 69 66 20 6e 6f 20 63 6f 6e 66 6c 69 63 74  l if no conflict
2160: 0a 2a 2a 20 72 65 73 6f 6c 75 74 69 6f 6e 20 69  .** resolution i
2170: 73 20 72 65 71 75 69 72 65 64 20 77 68 65 6e 20  s required when 
2180: 61 70 70 6c 79 69 6e 67 20 74 68 65 20 63 68 61  applying the cha
2190: 6e 67 65 73 65 74 2e 0a 2a 2a 0a 2a 2a 20 45 61  ngeset..**.** Ea
21a0: 63 68 20 67 72 6f 75 70 20 6f 66 20 63 68 61 6e  ch group of chan
21b0: 67 65 73 20 62 65 67 69 6e 73 20 77 69 74 68 20  ges begins with 
21c0: 61 20 74 61 62 6c 65 20 68 65 61 64 65 72 3a 0a  a table header:.
21d0: 2a 2a 0a 2a 2a 20 20 20 31 20 62 79 74 65 3a 20  **.**   1 byte: 
21e0: 43 6f 6e 73 74 61 6e 74 20 30 78 35 30 20 28 63  Constant 0x50 (c
21f0: 61 70 69 74 61 6c 20 27 50 27 29 0a 2a 2a 20 20  apital 'P').**  
2200: 20 56 61 72 69 6e 74 3a 20 4e 75 6d 62 65 72 20   Varint: Number 
2210: 6f 66 20 63 6f 6c 75 6d 6e 73 20 69 6e 20 74 68  of columns in th
2220: 65 20 74 61 62 6c 65 2e 0a 2a 2a 20 20 20 6e 43  e table..**   nC
2230: 6f 6c 20 62 79 74 65 73 3a 20 30 78 30 31 20 66  ol bytes: 0x01 f
2240: 6f 72 20 50 4b 20 63 6f 6c 75 6d 6e 73 2c 20 30  or PK columns, 0
2250: 78 30 30 20 6f 74 68 65 72 77 69 73 65 2e 0a 2a  x00 otherwise..*
2260: 2a 20 20 20 4e 20 62 79 74 65 73 3a 20 55 6e 71  *   N bytes: Unq
2270: 75 61 6c 69 66 69 65 64 20 74 61 62 6c 65 20 6e  ualified table n
2280: 61 6d 65 20 28 65 6e 63 6f 64 65 64 20 75 73 69  ame (encoded usi
2290: 6e 67 20 55 54 46 2d 38 29 2e 20 4e 75 6c 2d 74  ng UTF-8). Nul-t
22a0: 65 72 6d 69 6e 61 74 65 64 2e 0a 2a 2a 0a 2a 2a  erminated..**.**
22b0: 20 46 6f 6c 6c 6f 77 65 64 20 62 79 20 6f 6e 65   Followed by one
22c0: 20 6f 72 20 6d 6f 72 65 20 63 68 61 6e 67 65 73   or more changes
22d0: 20 74 6f 20 74 68 65 20 74 61 62 6c 65 2e 0a 2a   to the table..*
22e0: 2a 0a 2a 2a 20 20 20 31 20 62 79 74 65 3a 20 45  *.**   1 byte: E
22f0: 69 74 68 65 72 20 53 51 4c 49 54 45 5f 49 4e 53  ither SQLITE_INS
2300: 45 52 54 20 28 30 78 31 32 29 2c 20 55 50 44 41  ERT (0x12), UPDA
2310: 54 45 20 28 30 78 31 37 29 20 6f 72 20 44 45 4c  TE (0x17) or DEL
2320: 45 54 45 20 28 30 78 30 39 29 2e 0a 2a 2a 20 20  ETE (0x09)..**  
2330: 20 31 20 62 79 74 65 3a 20 54 68 65 20 22 69 6e   1 byte: The "in
2340: 64 69 72 65 63 74 2d 63 68 61 6e 67 65 22 20 66  direct-change" f
2350: 6c 61 67 2e 0a 2a 2a 20 20 20 73 69 6e 67 6c 65  lag..**   single
2360: 20 72 65 63 6f 72 64 3a 20 28 50 4b 20 66 69 65   record: (PK fie
2370: 6c 64 73 20 66 6f 72 20 44 45 4c 45 54 45 2c 20  lds for DELETE, 
2380: 50 4b 20 61 6e 64 20 6d 6f 64 69 66 69 65 64 20  PK and modified 
2390: 66 69 65 6c 64 73 20 66 6f 72 20 55 50 44 41 54  fields for UPDAT
23a0: 45 2c 0a 2a 2a 20 20 20 20 20 20 20 20 20 20 20  E,.**           
23b0: 20 20 20 20 20 20 20 20 66 75 6c 6c 20 72 65 63          full rec
23c0: 6f 72 64 20 66 6f 72 20 49 4e 53 45 52 54 29 2e  ord for INSERT).
23d0: 0a 2a 2a 0a 2a 2a 20 41 73 20 69 6e 20 74 68 65  .**.** As in the
23e0: 20 63 68 61 6e 67 65 73 65 74 20 66 6f 72 6d 61   changeset forma
23f0: 74 2c 20 65 61 63 68 20 66 69 65 6c 64 20 6f 66  t, each field of
2400: 20 74 68 65 20 73 69 6e 67 6c 65 20 72 65 63 6f   the single reco
2410: 72 64 20 74 68 61 74 20 69 73 20 70 61 72 74 0a  rd that is part.
2420: 2a 2a 20 6f 66 20 61 20 70 61 74 63 68 73 65 74  ** of a patchset
2430: 20 63 68 61 6e 67 65 20 69 73 20 61 73 73 6f 63   change is assoc
2440: 69 61 74 65 64 20 77 69 74 68 20 74 68 65 20 63  iated with the c
2450: 6f 72 72 65 73 70 6f 6e 64 69 6e 67 6c 79 20 70  orrespondingly p
2460: 6f 73 69 74 69 6f 6e 65 64 0a 2a 2a 20 74 61 62  ositioned.** tab
2470: 6c 65 20 63 6f 6c 75 6d 6e 2c 20 63 6f 75 6e 74  le column, count
2480: 69 6e 67 20 66 72 6f 6d 20 6c 65 66 74 20 74 6f  ing from left to
2490: 20 72 69 67 68 74 20 77 69 74 68 69 6e 20 74 68   right within th
24a0: 65 20 43 52 45 41 54 45 20 54 41 42 4c 45 20 0a  e CREATE TABLE .
24b0: 2a 2a 20 73 74 61 74 65 6d 65 6e 74 2e 0a 2a 2a  ** statement..**
24c0: 0a 2a 2a 20 46 6f 72 20 61 20 44 45 4c 45 54 45  .** For a DELETE
24d0: 20 63 68 61 6e 67 65 2c 20 61 6c 6c 20 66 69 65   change, all fie
24e0: 6c 64 73 20 77 69 74 68 69 6e 20 74 68 65 20 72  lds within the r
24f0: 65 63 6f 72 64 20 65 78 63 65 70 74 20 74 68 6f  ecord except tho
2500: 73 65 20 61 73 73 6f 63 69 61 74 65 64 0a 2a 2a  se associated.**
2510: 20 77 69 74 68 20 50 52 49 4d 41 52 59 20 4b 45   with PRIMARY KE
2520: 59 20 63 6f 6c 75 6d 6e 73 20 61 72 65 20 73 65  Y columns are se
2530: 74 20 74 6f 20 22 75 6e 64 65 66 69 6e 65 64 22  t to "undefined"
2540: 2e 20 54 68 65 20 50 52 49 4d 41 52 59 20 4b 45  . The PRIMARY KE
2550: 59 20 66 69 65 6c 64 73 0a 2a 2a 20 63 6f 6e 74  Y fields.** cont
2560: 61 69 6e 20 74 68 65 20 76 61 6c 75 65 73 20 69  ain the values i
2570: 64 65 6e 74 69 66 79 69 6e 67 20 74 68 65 20 72  dentifying the r
2580: 6f 77 20 74 6f 20 64 65 6c 65 74 65 2e 0a 2a 2a  ow to delete..**
2590: 0a 2a 2a 20 46 6f 72 20 61 6e 20 55 50 44 41 54  .** For an UPDAT
25a0: 45 20 63 68 61 6e 67 65 2c 20 61 6c 6c 20 66 69  E change, all fi
25b0: 65 6c 64 73 20 65 78 63 65 70 74 20 74 68 6f 73  elds except thos
25c0: 65 20 61 73 73 6f 63 69 61 74 65 64 20 77 69 74  e associated wit
25d0: 68 20 50 52 49 4d 41 52 59 20 4b 45 59 0a 2a 2a  h PRIMARY KEY.**
25e0: 20 63 6f 6c 75 6d 6e 73 20 61 6e 64 20 63 6f 6c   columns and col
25f0: 75 6d 6e 73 20 74 68 61 74 20 61 72 65 20 6d 6f  umns that are mo
2600: 64 69 66 69 65 64 20 62 79 20 74 68 65 20 55 50  dified by the UP
2610: 44 41 54 45 20 61 72 65 20 73 65 74 20 74 6f 20  DATE are set to 
2620: 22 75 6e 64 65 66 69 6e 65 64 22 2e 0a 2a 2a 20  "undefined"..** 
2630: 50 52 49 4d 41 52 59 20 4b 45 59 20 66 69 65 6c  PRIMARY KEY fiel
2640: 64 73 20 63 6f 6e 74 61 69 6e 20 74 68 65 20 76  ds contain the v
2650: 61 6c 75 65 73 20 69 64 65 6e 74 69 66 79 69 6e  alues identifyin
2660: 67 20 74 68 65 20 74 61 62 6c 65 20 72 6f 77 20  g the table row 
2670: 74 6f 20 75 70 64 61 74 65 2c 0a 2a 2a 20 61 6e  to update,.** an
2680: 64 20 66 69 65 6c 64 73 20 61 73 73 6f 63 69 61  d fields associa
2690: 74 65 64 20 77 69 74 68 20 6d 6f 64 69 66 69 65  ted with modifie
26a0: 64 20 63 6f 6c 75 6d 6e 73 20 63 6f 6e 74 61 69  d columns contai
26b0: 6e 20 74 68 65 20 6e 65 77 20 63 6f 6c 75 6d 6e  n the new column
26c0: 20 76 61 6c 75 65 73 2e 0a 2a 2a 0a 2a 2a 20 54   values..**.** T
26d0: 68 65 20 72 65 63 6f 72 64 73 20 61 73 73 6f 63  he records assoc
26e0: 69 61 74 65 64 20 77 69 74 68 20 49 4e 53 45 52  iated with INSER
26f0: 54 20 63 68 61 6e 67 65 73 20 61 72 65 20 69 6e  T changes are in
2700: 20 74 68 65 20 73 61 6d 65 20 66 6f 72 6d 61 74   the same format
2710: 20 61 73 20 66 6f 72 0a 2a 2a 20 63 68 61 6e 67   as for.** chang
2720: 65 73 65 74 73 2e 20 49 74 20 69 73 20 6e 6f 74  esets. It is not
2730: 20 70 6f 73 73 69 62 6c 65 20 66 6f 72 20 61 20   possible for a 
2740: 72 65 63 6f 72 64 20 61 73 73 6f 63 69 61 74 65  record associate
2750: 64 20 77 69 74 68 20 61 6e 20 49 4e 53 45 52 54  d with an INSERT
2760: 0a 2a 2a 20 63 68 61 6e 67 65 20 74 6f 20 63 6f  .** change to co
2770: 6e 74 61 69 6e 20 61 20 66 69 65 6c 64 20 73 65  ntain a field se
2780: 74 20 74 6f 20 22 75 6e 64 65 66 69 6e 65 64 22  t to "undefined"
2790: 2e 0a 2a 2f 0a 0a 2f 2a 0a 2a 2a 20 46 6f 72 20  ..*/../*.** For 
27a0: 65 61 63 68 20 72 6f 77 20 6d 6f 64 69 66 69 65  each row modifie
27b0: 64 20 64 75 72 69 6e 67 20 61 20 73 65 73 73 69  d during a sessi
27c0: 6f 6e 2c 20 74 68 65 72 65 20 65 78 69 73 74 73  on, there exists
27d0: 20 61 20 73 69 6e 67 6c 65 20 69 6e 73 74 61 6e   a single instan
27e0: 63 65 20 6f 66 0a 2a 2a 20 74 68 69 73 20 73 74  ce of.** this st
27f0: 72 75 63 74 75 72 65 20 73 74 6f 72 65 64 20 69  ructure stored i
2800: 6e 20 61 20 53 65 73 73 69 6f 6e 54 61 62 6c 65  n a SessionTable
2810: 2e 61 43 68 61 6e 67 65 5b 5d 20 68 61 73 68 20  .aChange[] hash 
2820: 74 61 62 6c 65 2e 0a 2a 2f 0a 73 74 72 75 63 74  table..*/.struct
2830: 20 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 20 7b   SessionChange {
2840: 0a 20 20 69 6e 74 20 6f 70 3b 20 20 20 20 20 20  .  int op;      
2850: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
2860: 20 20 20 2f 2a 20 4f 6e 65 20 6f 66 20 55 50 44     /* One of UPD
2870: 41 54 45 2c 20 44 45 4c 45 54 45 2c 20 49 4e 53  ATE, DELETE, INS
2880: 45 52 54 20 2a 2f 0a 20 20 69 6e 74 20 62 49 6e  ERT */.  int bIn
2890: 64 69 72 65 63 74 3b 20 20 20 20 20 20 20 20 20  direct;         
28a0: 20 20 20 20 20 20 20 20 20 2f 2a 20 54 72 75 65           /* True
28b0: 20 69 66 20 74 68 69 73 20 63 68 61 6e 67 65 20   if this change 
28c0: 69 73 20 22 69 6e 64 69 72 65 63 74 22 20 2a 2f  is "indirect" */
28d0: 0a 20 20 69 6e 74 20 6e 52 65 63 6f 72 64 3b 20  .  int nRecord; 
28e0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
28f0: 20 20 20 2f 2a 20 4e 75 6d 62 65 72 20 6f 66 20     /* Number of 
2900: 62 79 74 65 73 20 69 6e 20 62 75 66 66 65 72 20  bytes in buffer 
2910: 61 52 65 63 6f 72 64 5b 5d 20 2a 2f 0a 20 20 75  aRecord[] */.  u
2920: 38 20 2a 61 52 65 63 6f 72 64 3b 20 20 20 20 20  8 *aRecord;     
2930: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
2940: 2a 20 42 75 66 66 65 72 20 63 6f 6e 74 61 69 6e  * Buffer contain
2950: 69 6e 67 20 6f 6c 64 2e 2a 20 72 65 63 6f 72 64  ing old.* record
2960: 20 2a 2f 0a 20 20 53 65 73 73 69 6f 6e 43 68 61   */.  SessionCha
2970: 6e 67 65 20 2a 70 4e 65 78 74 3b 20 20 20 20 20  nge *pNext;     
2980: 20 20 20 20 20 20 2f 2a 20 46 6f 72 20 68 61 73        /* For has
2990: 68 2d 74 61 62 6c 65 20 63 6f 6c 6c 69 73 69 6f  h-table collisio
29a0: 6e 73 20 2a 2f 0a 7d 3b 0a 0a 2f 2a 0a 2a 2a 20  ns */.};../*.** 
29b0: 57 72 69 74 65 20 61 20 76 61 72 69 6e 74 20 77  Write a varint w
29c0: 69 74 68 20 76 61 6c 75 65 20 69 56 61 6c 20 69  ith value iVal i
29d0: 6e 74 6f 20 74 68 65 20 62 75 66 66 65 72 20 61  nto the buffer a
29e0: 74 20 61 42 75 66 2e 20 52 65 74 75 72 6e 20 74  t aBuf. Return t
29f0: 68 65 20 0a 2a 2a 20 6e 75 6d 62 65 72 20 6f 66  he .** number of
2a00: 20 62 79 74 65 73 20 77 72 69 74 74 65 6e 2e 0a   bytes written..
2a10: 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65  */.static int se
2a20: 73 73 69 6f 6e 56 61 72 69 6e 74 50 75 74 28 75  ssionVarintPut(u
2a30: 38 20 2a 61 42 75 66 2c 20 69 6e 74 20 69 56 61  8 *aBuf, int iVa
2a40: 6c 29 7b 0a 20 20 72 65 74 75 72 6e 20 70 75 74  l){.  return put
2a50: 56 61 72 69 6e 74 33 32 28 61 42 75 66 2c 20 69  Varint32(aBuf, i
2a60: 56 61 6c 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 52  Val);.}../*.** R
2a70: 65 74 75 72 6e 20 74 68 65 20 6e 75 6d 62 65 72  eturn the number
2a80: 20 6f 66 20 62 79 74 65 73 20 72 65 71 75 69 72   of bytes requir
2a90: 65 64 20 74 6f 20 73 74 6f 72 65 20 76 61 6c 75  ed to store valu
2aa0: 65 20 69 56 61 6c 20 61 73 20 61 20 76 61 72 69  e iVal as a vari
2ab0: 6e 74 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e  nt..*/.static in
2ac0: 74 20 73 65 73 73 69 6f 6e 56 61 72 69 6e 74 4c  t sessionVarintL
2ad0: 65 6e 28 69 6e 74 20 69 56 61 6c 29 7b 0a 20 20  en(int iVal){.  
2ae0: 72 65 74 75 72 6e 20 73 71 6c 69 74 65 33 56 61  return sqlite3Va
2af0: 72 69 6e 74 4c 65 6e 28 69 56 61 6c 29 3b 0a 7d  rintLen(iVal);.}
2b00: 0a 0a 2f 2a 0a 2a 2a 20 52 65 61 64 20 61 20 76  ../*.** Read a v
2b10: 61 72 69 6e 74 20 76 61 6c 75 65 20 66 72 6f 6d  arint value from
2b20: 20 61 42 75 66 5b 5d 20 69 6e 74 6f 20 2a 70 69   aBuf[] into *pi
2b30: 56 61 6c 2e 20 52 65 74 75 72 6e 20 74 68 65 20  Val. Return the 
2b40: 6e 75 6d 62 65 72 20 6f 66 20 0a 2a 2a 20 62 79  number of .** by
2b50: 74 65 73 20 72 65 61 64 2e 0a 2a 2f 0a 73 74 61  tes read..*/.sta
2b60: 74 69 63 20 69 6e 74 20 73 65 73 73 69 6f 6e 56  tic int sessionV
2b70: 61 72 69 6e 74 47 65 74 28 75 38 20 2a 61 42 75  arintGet(u8 *aBu
2b80: 66 2c 20 69 6e 74 20 2a 70 69 56 61 6c 29 7b 0a  f, int *piVal){.
2b90: 20 20 72 65 74 75 72 6e 20 67 65 74 56 61 72 69    return getVari
2ba0: 6e 74 33 32 28 61 42 75 66 2c 20 2a 70 69 56 61  nt32(aBuf, *piVa
2bb0: 6c 29 3b 0a 7d 0a 0a 2f 2a 20 4c 6f 61 64 20 61  l);.}../* Load a
2bc0: 6e 20 75 6e 61 6c 69 67 6e 65 64 20 61 6e 64 20  n unaligned and 
2bd0: 75 6e 73 69 67 6e 65 64 20 33 32 2d 62 69 74 20  unsigned 32-bit 
2be0: 69 6e 74 65 67 65 72 20 2a 2f 0a 23 64 65 66 69  integer */.#defi
2bf0: 6e 65 20 53 45 53 53 49 4f 4e 5f 55 49 4e 54 33  ne SESSION_UINT3
2c00: 32 28 78 29 20 28 28 28 75 33 32 29 28 78 29 5b  2(x) (((u32)(x)[
2c10: 30 5d 3c 3c 32 34 29 7c 28 28 78 29 5b 31 5d 3c  0]<<24)|((x)[1]<
2c20: 3c 31 36 29 7c 28 28 78 29 5b 32 5d 3c 3c 38 29  <16)|((x)[2]<<8)
2c30: 7c 28 78 29 5b 33 5d 29 0a 0a 2f 2a 0a 2a 2a 20  |(x)[3])../*.** 
2c40: 52 65 61 64 20 61 20 36 34 2d 62 69 74 20 62 69  Read a 64-bit bi
2c50: 67 2d 65 6e 64 69 61 6e 20 69 6e 74 65 67 65 72  g-endian integer
2c60: 20 76 61 6c 75 65 20 66 72 6f 6d 20 62 75 66 66   value from buff
2c70: 65 72 20 61 52 65 63 5b 5d 2e 20 52 65 74 75 72  er aRec[]. Retur
2c80: 6e 0a 2a 2a 20 74 68 65 20 76 61 6c 75 65 20 72  n.** the value r
2c90: 65 61 64 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 73  ead..*/.static s
2ca0: 71 6c 69 74 65 33 5f 69 6e 74 36 34 20 73 65 73  qlite3_int64 ses
2cb0: 73 69 6f 6e 47 65 74 49 36 34 28 75 38 20 2a 61  sionGetI64(u8 *a
2cc0: 52 65 63 29 7b 0a 20 20 75 36 34 20 78 20 3d 20  Rec){.  u64 x = 
2cd0: 53 45 53 53 49 4f 4e 5f 55 49 4e 54 33 32 28 61  SESSION_UINT32(a
2ce0: 52 65 63 29 3b 0a 20 20 75 33 32 20 79 20 3d 20  Rec);.  u32 y = 
2cf0: 53 45 53 53 49 4f 4e 5f 55 49 4e 54 33 32 28 61  SESSION_UINT32(a
2d00: 52 65 63 2b 34 29 3b 0a 20 20 78 20 3d 20 28 78  Rec+4);.  x = (x
2d10: 3c 3c 33 32 29 20 2b 20 79 3b 0a 20 20 72 65 74  <<32) + y;.  ret
2d20: 75 72 6e 20 28 73 71 6c 69 74 65 33 5f 69 6e 74  urn (sqlite3_int
2d30: 36 34 29 78 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 57  64)x;.}../*.** W
2d40: 72 69 74 65 20 61 20 36 34 2d 62 69 74 20 62 69  rite a 64-bit bi
2d50: 67 2d 65 6e 64 69 61 6e 20 69 6e 74 65 67 65 72  g-endian integer
2d60: 20 76 61 6c 75 65 20 74 6f 20 74 68 65 20 62 75   value to the bu
2d70: 66 66 65 72 20 61 42 75 66 5b 5d 2e 0a 2a 2f 0a  ffer aBuf[]..*/.
2d80: 73 74 61 74 69 63 20 76 6f 69 64 20 73 65 73 73  static void sess
2d90: 69 6f 6e 50 75 74 49 36 34 28 75 38 20 2a 61 42  ionPutI64(u8 *aB
2da0: 75 66 2c 20 73 71 6c 69 74 65 33 5f 69 6e 74 36  uf, sqlite3_int6
2db0: 34 20 69 29 7b 0a 20 20 61 42 75 66 5b 30 5d 20  4 i){.  aBuf[0] 
2dc0: 3d 20 28 69 3e 3e 35 36 29 20 26 20 30 78 46 46  = (i>>56) & 0xFF
2dd0: 3b 0a 20 20 61 42 75 66 5b 31 5d 20 3d 20 28 69  ;.  aBuf[1] = (i
2de0: 3e 3e 34 38 29 20 26 20 30 78 46 46 3b 0a 20 20  >>48) & 0xFF;.  
2df0: 61 42 75 66 5b 32 5d 20 3d 20 28 69 3e 3e 34 30  aBuf[2] = (i>>40
2e00: 29 20 26 20 30 78 46 46 3b 0a 20 20 61 42 75 66  ) & 0xFF;.  aBuf
2e10: 5b 33 5d 20 3d 20 28 69 3e 3e 33 32 29 20 26 20  [3] = (i>>32) & 
2e20: 30 78 46 46 3b 0a 20 20 61 42 75 66 5b 34 5d 20  0xFF;.  aBuf[4] 
2e30: 3d 20 28 69 3e 3e 32 34 29 20 26 20 30 78 46 46  = (i>>24) & 0xFF
2e40: 3b 0a 20 20 61 42 75 66 5b 35 5d 20 3d 20 28 69  ;.  aBuf[5] = (i
2e50: 3e 3e 31 36 29 20 26 20 30 78 46 46 3b 0a 20 20  >>16) & 0xFF;.  
2e60: 61 42 75 66 5b 36 5d 20 3d 20 28 69 3e 3e 20 38  aBuf[6] = (i>> 8
2e70: 29 20 26 20 30 78 46 46 3b 0a 20 20 61 42 75 66  ) & 0xFF;.  aBuf
2e80: 5b 37 5d 20 3d 20 28 69 3e 3e 20 30 29 20 26 20  [7] = (i>> 0) & 
2e90: 30 78 46 46 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54  0xFF;.}../*.** T
2ea0: 68 69 73 20 66 75 6e 63 74 69 6f 6e 20 69 73 20  his function is 
2eb0: 75 73 65 64 20 74 6f 20 73 65 72 69 61 6c 69 7a  used to serializ
2ec0: 65 20 74 68 65 20 63 6f 6e 74 65 6e 74 73 20 6f  e the contents o
2ed0: 66 20 76 61 6c 75 65 20 70 56 61 6c 75 65 20 28  f value pValue (
2ee0: 73 65 65 0a 2a 2a 20 63 6f 6d 6d 65 6e 74 20 74  see.** comment t
2ef0: 69 74 6c 65 64 20 22 52 45 43 4f 52 44 20 46 4f  itled "RECORD FO
2f00: 52 4d 41 54 22 20 61 62 6f 76 65 29 2e 0a 2a 2a  RMAT" above)..**
2f10: 0a 2a 2a 20 49 66 20 69 74 20 69 73 20 6e 6f 6e  .** If it is non
2f20: 2d 4e 55 4c 4c 2c 20 74 68 65 20 73 65 72 69 61  -NULL, the seria
2f30: 6c 69 7a 65 64 20 66 6f 72 6d 20 6f 66 20 74 68  lized form of th
2f40: 65 20 76 61 6c 75 65 20 69 73 20 77 72 69 74 74  e value is writt
2f50: 65 6e 20 74 6f 20 0a 2a 2a 20 62 75 66 66 65 72  en to .** buffer
2f60: 20 61 42 75 66 2e 20 2a 70 6e 57 72 69 74 65 20   aBuf. *pnWrite 
2f70: 69 73 20 73 65 74 20 74 6f 20 74 68 65 20 6e 75  is set to the nu
2f80: 6d 62 65 72 20 6f 66 20 62 79 74 65 73 20 77 72  mber of bytes wr
2f90: 69 74 74 65 6e 20 62 65 66 6f 72 65 0a 2a 2a 20  itten before.** 
2fa0: 72 65 74 75 72 6e 69 6e 67 2e 20 4f 72 2c 20 69  returning. Or, i
2fb0: 66 20 61 42 75 66 20 69 73 20 4e 55 4c 4c 2c 20  f aBuf is NULL, 
2fc0: 74 68 65 20 6f 6e 6c 79 20 74 68 69 6e 67 20 74  the only thing t
2fd0: 68 69 73 20 66 75 6e 63 74 69 6f 6e 20 64 6f 65  his function doe
2fe0: 73 20 69 73 0a 2a 2a 20 73 65 74 20 2a 70 6e 57  s is.** set *pnW
2ff0: 72 69 74 65 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 6e  rite..**.** If n
3000: 6f 20 65 72 72 6f 72 20 6f 63 63 75 72 73 2c 20  o error occurs, 
3010: 53 51 4c 49 54 45 5f 4f 4b 20 69 73 20 72 65 74  SQLITE_OK is ret
3020: 75 72 6e 65 64 2e 20 4f 72 2c 20 69 66 20 61 6e  urned. Or, if an
3030: 20 4f 4f 4d 20 65 72 72 6f 72 20 6f 63 63 75 72   OOM error occur
3040: 73 0a 2a 2a 20 77 69 74 68 69 6e 20 61 20 63 61  s.** within a ca
3050: 6c 6c 20 74 6f 20 73 71 6c 69 74 65 33 5f 76 61  ll to sqlite3_va
3060: 6c 75 65 5f 74 65 78 74 28 29 20 28 6d 61 79 20  lue_text() (may 
3070: 66 61 69 6c 20 69 66 20 74 68 65 20 64 62 20 69  fail if the db i
3080: 73 20 75 74 66 2d 31 36 29 29 20 0a 2a 2a 20 53  s utf-16)) .** S
3090: 51 4c 49 54 45 5f 4e 4f 4d 45 4d 20 69 73 20 72  QLITE_NOMEM is r
30a0: 65 74 75 72 6e 65 64 2e 0a 2a 2f 0a 73 74 61 74  eturned..*/.stat
30b0: 69 63 20 69 6e 74 20 73 65 73 73 69 6f 6e 53 65  ic int sessionSe
30c0: 72 69 61 6c 69 7a 65 56 61 6c 75 65 28 0a 20 20  rializeValue(.  
30d0: 75 38 20 2a 61 42 75 66 2c 20 20 20 20 20 20 20  u8 *aBuf,       
30e0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
30f0: 2f 2a 20 49 66 20 6e 6f 6e 2d 4e 55 4c 4c 2c 20  /* If non-NULL, 
3100: 77 72 69 74 65 20 73 65 72 69 61 6c 69 7a 65 64  write serialized
3110: 20 76 61 6c 75 65 20 68 65 72 65 20 2a 2f 0a 20   value here */. 
3120: 20 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 20 2a   sqlite3_value *
3130: 70 56 61 6c 75 65 2c 20 20 20 20 20 20 20 20 20  pValue,         
3140: 20 2f 2a 20 56 61 6c 75 65 20 74 6f 20 73 65 72   /* Value to ser
3150: 69 61 6c 69 7a 65 20 2a 2f 0a 20 20 69 6e 74 20  ialize */.  int 
3160: 2a 70 6e 57 72 69 74 65 20 20 20 20 20 20 20 20  *pnWrite        
3170: 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 49              /* I
3180: 4e 2f 4f 55 54 3a 20 49 6e 63 72 65 6d 65 6e 74  N/OUT: Increment
3190: 20 62 79 20 62 79 74 65 73 20 77 72 69 74 74 65   by bytes writte
31a0: 6e 20 2a 2f 0a 29 7b 0a 20 20 69 6e 74 20 6e 42  n */.){.  int nB
31b0: 79 74 65 3b 20 20 20 20 20 20 20 20 20 20 20 20  yte;            
31c0: 20 20 20 20 20 20 20 20 20 20 2f 2a 20 53 69 7a            /* Siz
31d0: 65 20 6f 66 20 73 65 72 69 61 6c 69 7a 65 64 20  e of serialized 
31e0: 76 61 6c 75 65 20 69 6e 20 62 79 74 65 73 20 2a  value in bytes *
31f0: 2f 0a 0a 20 20 69 66 28 20 70 56 61 6c 75 65 20  /..  if( pValue 
3200: 29 7b 0a 20 20 20 20 69 6e 74 20 65 54 79 70 65  ){.    int eType
3210: 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  ;               
3220: 20 20 20 20 20 2f 2a 20 56 61 6c 75 65 20 74 79       /* Value ty
3230: 70 65 20 28 53 51 4c 49 54 45 5f 4e 55 4c 4c 2c  pe (SQLITE_NULL,
3240: 20 54 45 58 54 20 65 74 63 2e 29 20 2a 2f 0a 20   TEXT etc.) */. 
3250: 20 0a 20 20 20 20 65 54 79 70 65 20 3d 20 73 71   .    eType = sq
3260: 6c 69 74 65 33 5f 76 61 6c 75 65 5f 74 79 70 65  lite3_value_type
3270: 28 70 56 61 6c 75 65 29 3b 0a 20 20 20 20 69 66  (pValue);.    if
3280: 28 20 61 42 75 66 20 29 20 61 42 75 66 5b 30 5d  ( aBuf ) aBuf[0]
3290: 20 3d 20 65 54 79 70 65 3b 0a 20 20 0a 20 20 20   = eType;.  .   
32a0: 20 73 77 69 74 63 68 28 20 65 54 79 70 65 20 29   switch( eType )
32b0: 7b 0a 20 20 20 20 20 20 63 61 73 65 20 53 51 4c  {.      case SQL
32c0: 49 54 45 5f 4e 55 4c 4c 3a 20 0a 20 20 20 20 20  ITE_NULL: .     
32d0: 20 20 20 6e 42 79 74 65 20 3d 20 31 3b 0a 20 20     nByte = 1;.  
32e0: 20 20 20 20 20 20 62 72 65 61 6b 3b 0a 20 20 0a        break;.  .
32f0: 20 20 20 20 20 20 63 61 73 65 20 53 51 4c 49 54        case SQLIT
3300: 45 5f 49 4e 54 45 47 45 52 3a 20 0a 20 20 20 20  E_INTEGER: .    
3310: 20 20 63 61 73 65 20 53 51 4c 49 54 45 5f 46 4c    case SQLITE_FL
3320: 4f 41 54 3a 0a 20 20 20 20 20 20 20 20 69 66 28  OAT:.        if(
3330: 20 61 42 75 66 20 29 7b 0a 20 20 20 20 20 20 20   aBuf ){.       
3340: 20 20 20 2f 2a 20 54 4f 44 4f 3a 20 53 51 4c 69     /* TODO: SQLi
3350: 74 65 20 64 6f 65 73 20 73 6f 6d 65 74 68 69 6e  te does somethin
3360: 67 20 73 70 65 63 69 61 6c 20 74 6f 20 64 65 61  g special to dea
3370: 6c 20 77 69 74 68 20 6d 69 78 65 64 2d 65 6e 64  l with mixed-end
3380: 69 61 6e 0a 20 20 20 20 20 20 20 20 20 20 2a 2a  ian.          **
3390: 20 66 6c 6f 61 74 69 6e 67 20 70 6f 69 6e 74 20   floating point 
33a0: 76 61 6c 75 65 73 20 28 65 2e 67 2e 20 41 52 4d  values (e.g. ARM
33b0: 37 29 2e 20 54 68 69 73 20 63 6f 64 65 20 70 72  7). This code pr
33c0: 6f 62 61 62 6c 79 20 73 68 6f 75 6c 64 0a 20 20  obably should.  
33d0: 20 20 20 20 20 20 20 20 2a 2a 20 74 6f 6f 2e 20          ** too. 
33e0: 20 2a 2f 0a 20 20 20 20 20 20 20 20 20 20 75 36   */.          u6
33f0: 34 20 69 3b 0a 20 20 20 20 20 20 20 20 20 20 69  4 i;.          i
3400: 66 28 20 65 54 79 70 65 3d 3d 53 51 4c 49 54 45  f( eType==SQLITE
3410: 5f 49 4e 54 45 47 45 52 20 29 7b 0a 20 20 20 20  _INTEGER ){.    
3420: 20 20 20 20 20 20 20 20 69 20 3d 20 28 75 36 34          i = (u64
3430: 29 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 5f 69  )sqlite3_value_i
3440: 6e 74 36 34 28 70 56 61 6c 75 65 29 3b 0a 20 20  nt64(pValue);.  
3450: 20 20 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a 20          }else{. 
3460: 20 20 20 20 20 20 20 20 20 20 20 64 6f 75 62 6c             doubl
3470: 65 20 72 3b 0a 20 20 20 20 20 20 20 20 20 20 20  e r;.           
3480: 20 61 73 73 65 72 74 28 20 73 69 7a 65 6f 66 28   assert( sizeof(
3490: 64 6f 75 62 6c 65 29 3d 3d 38 20 26 26 20 73 69  double)==8 && si
34a0: 7a 65 6f 66 28 75 36 34 29 3d 3d 38 20 29 3b 0a  zeof(u64)==8 );.
34b0: 20 20 20 20 20 20 20 20 20 20 20 20 72 20 3d 20              r = 
34c0: 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 5f 64 6f  sqlite3_value_do
34d0: 75 62 6c 65 28 70 56 61 6c 75 65 29 3b 0a 20 20  uble(pValue);.  
34e0: 20 20 20 20 20 20 20 20 20 20 6d 65 6d 63 70 79            memcpy
34f0: 28 26 69 2c 20 26 72 2c 20 38 29 3b 0a 20 20 20  (&i, &r, 8);.   
3500: 20 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 20         }.       
3510: 20 20 20 73 65 73 73 69 6f 6e 50 75 74 49 36 34     sessionPutI64
3520: 28 26 61 42 75 66 5b 31 5d 2c 20 69 29 3b 0a 20  (&aBuf[1], i);. 
3530: 20 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 20         }.       
3540: 20 6e 42 79 74 65 20 3d 20 39 3b 20 0a 20 20 20   nByte = 9; .   
3550: 20 20 20 20 20 62 72 65 61 6b 3b 0a 20 20 0a 20       break;.  . 
3560: 20 20 20 20 20 64 65 66 61 75 6c 74 3a 20 7b 0a       default: {.
3570: 20 20 20 20 20 20 20 20 75 38 20 2a 7a 3b 0a 20          u8 *z;. 
3580: 20 20 20 20 20 20 20 69 6e 74 20 6e 3b 0a 20 20         int n;.  
3590: 20 20 20 20 20 20 69 6e 74 20 6e 56 61 72 69 6e        int nVarin
35a0: 74 3b 0a 20 20 0a 20 20 20 20 20 20 20 20 61 73  t;.  .        as
35b0: 73 65 72 74 28 20 65 54 79 70 65 3d 3d 53 51 4c  sert( eType==SQL
35c0: 49 54 45 5f 54 45 58 54 20 7c 7c 20 65 54 79 70  ITE_TEXT || eTyp
35d0: 65 3d 3d 53 51 4c 49 54 45 5f 42 4c 4f 42 20 29  e==SQLITE_BLOB )
35e0: 3b 0a 20 20 20 20 20 20 20 20 69 66 28 20 65 54  ;.        if( eT
35f0: 79 70 65 3d 3d 53 51 4c 49 54 45 5f 54 45 58 54  ype==SQLITE_TEXT
3600: 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 7a 20   ){.          z 
3610: 3d 20 28 75 38 20 2a 29 73 71 6c 69 74 65 33 5f  = (u8 *)sqlite3_
3620: 76 61 6c 75 65 5f 74 65 78 74 28 70 56 61 6c 75  value_text(pValu
3630: 65 29 3b 0a 20 20 20 20 20 20 20 20 7d 65 6c 73  e);.        }els
3640: 65 7b 0a 20 20 20 20 20 20 20 20 20 20 7a 20 3d  e{.          z =
3650: 20 28 75 38 20 2a 29 73 71 6c 69 74 65 33 5f 76   (u8 *)sqlite3_v
3660: 61 6c 75 65 5f 62 6c 6f 62 28 70 56 61 6c 75 65  alue_blob(pValue
3670: 29 3b 0a 20 20 20 20 20 20 20 20 7d 0a 20 20 20  );.        }.   
3680: 20 20 20 20 20 6e 20 3d 20 73 71 6c 69 74 65 33       n = sqlite3
3690: 5f 76 61 6c 75 65 5f 62 79 74 65 73 28 70 56 61  _value_bytes(pVa
36a0: 6c 75 65 29 3b 0a 20 20 20 20 20 20 20 20 69 66  lue);.        if
36b0: 28 20 7a 3d 3d 30 20 26 26 20 28 65 54 79 70 65  ( z==0 && (eType
36c0: 21 3d 53 51 4c 49 54 45 5f 42 4c 4f 42 20 7c 7c  !=SQLITE_BLOB ||
36d0: 20 6e 3e 30 29 20 29 20 72 65 74 75 72 6e 20 53   n>0) ) return S
36e0: 51 4c 49 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 20  QLITE_NOMEM;.   
36f0: 20 20 20 20 20 6e 56 61 72 69 6e 74 20 3d 20 73       nVarint = s
3700: 65 73 73 69 6f 6e 56 61 72 69 6e 74 4c 65 6e 28  essionVarintLen(
3710: 6e 29 3b 0a 20 20 0a 20 20 20 20 20 20 20 20 69  n);.  .        i
3720: 66 28 20 61 42 75 66 20 29 7b 0a 20 20 20 20 20  f( aBuf ){.     
3730: 20 20 20 20 20 73 65 73 73 69 6f 6e 56 61 72 69       sessionVari
3740: 6e 74 50 75 74 28 26 61 42 75 66 5b 31 5d 2c 20  ntPut(&aBuf[1], 
3750: 6e 29 3b 0a 20 20 20 20 20 20 20 20 20 20 69 66  n);.          if
3760: 28 20 6e 20 29 20 6d 65 6d 63 70 79 28 26 61 42  ( n ) memcpy(&aB
3770: 75 66 5b 6e 56 61 72 69 6e 74 20 2b 20 31 5d 2c  uf[nVarint + 1],
3780: 20 7a 2c 20 6e 29 3b 0a 20 20 20 20 20 20 20 20   z, n);.        
3790: 7d 0a 20 20 0a 20 20 20 20 20 20 20 20 6e 42 79  }.  .        nBy
37a0: 74 65 20 3d 20 31 20 2b 20 6e 56 61 72 69 6e 74  te = 1 + nVarint
37b0: 20 2b 20 6e 3b 0a 20 20 20 20 20 20 20 20 62 72   + n;.        br
37c0: 65 61 6b 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20  eak;.      }.   
37d0: 20 7d 0a 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20   }.  }else{.    
37e0: 6e 42 79 74 65 20 3d 20 31 3b 0a 20 20 20 20 69  nByte = 1;.    i
37f0: 66 28 20 61 42 75 66 20 29 20 61 42 75 66 5b 30  f( aBuf ) aBuf[0
3800: 5d 20 3d 20 27 5c 30 27 3b 0a 20 20 7d 0a 0a 20  ] = '\0';.  }.. 
3810: 20 69 66 28 20 70 6e 57 72 69 74 65 20 29 20 2a   if( pnWrite ) *
3820: 70 6e 57 72 69 74 65 20 2b 3d 20 6e 42 79 74 65  pnWrite += nByte
3830: 3b 0a 20 20 72 65 74 75 72 6e 20 53 51 4c 49 54  ;.  return SQLIT
3840: 45 5f 4f 4b 3b 0a 7d 0a 0a 0a 2f 2a 0a 2a 2a 20  E_OK;.}.../*.** 
3850: 54 68 69 73 20 6d 61 63 72 6f 20 69 73 20 75 73  This macro is us
3860: 65 64 20 74 6f 20 63 61 6c 63 75 6c 61 74 65 20  ed to calculate 
3870: 68 61 73 68 20 6b 65 79 20 76 61 6c 75 65 73 20  hash key values 
3880: 66 6f 72 20 64 61 74 61 20 73 74 72 75 63 74 75  for data structu
3890: 72 65 73 2e 20 49 6e 0a 2a 2a 20 6f 72 64 65 72  res. In.** order
38a0: 20 74 6f 20 75 73 65 20 74 68 69 73 20 6d 61 63   to use this mac
38b0: 72 6f 2c 20 74 68 65 20 65 6e 74 69 72 65 20 64  ro, the entire d
38c0: 61 74 61 20 73 74 72 75 63 74 75 72 65 20 6d 75  ata structure mu
38d0: 73 74 20 62 65 20 72 65 70 72 65 73 65 6e 74 65  st be represente
38e0: 64 0a 2a 2a 20 61 73 20 61 20 73 65 72 69 65 73  d.** as a series
38f0: 20 6f 66 20 75 6e 73 69 67 6e 65 64 20 69 6e 74   of unsigned int
3900: 65 67 65 72 73 2e 20 49 6e 20 6f 72 64 65 72 20  egers. In order 
3910: 74 6f 20 63 61 6c 63 75 6c 61 74 65 20 61 20 68  to calculate a h
3920: 61 73 68 2d 6b 65 79 20 76 61 6c 75 65 0a 2a 2a  ash-key value.**
3930: 20 66 6f 72 20 61 20 64 61 74 61 20 73 74 72 75   for a data stru
3940: 63 74 75 72 65 20 72 65 70 72 65 73 65 6e 74 65  cture represente
3950: 64 20 61 73 20 74 68 72 65 65 20 73 75 63 68 20  d as three such 
3960: 69 6e 74 65 67 65 72 73 2c 20 74 68 65 20 6d 61  integers, the ma
3970: 63 72 6f 20 6d 61 79 0a 2a 2a 20 74 68 65 6e 20  cro may.** then 
3980: 62 65 20 75 73 65 64 20 61 73 20 66 6f 6c 6c 6f  be used as follo
3990: 77 73 3a 0a 2a 2a 0a 2a 2a 20 20 20 20 69 6e 74  ws:.**.**    int
39a0: 20 68 61 73 68 5f 6b 65 79 5f 76 61 6c 75 65 3b   hash_key_value;
39b0: 0a 2a 2a 20 20 20 20 68 61 73 68 5f 6b 65 79 5f  .**    hash_key_
39c0: 76 61 6c 75 65 20 3d 20 48 41 53 48 5f 41 50 50  value = HASH_APP
39d0: 45 4e 44 28 30 2c 20 3c 76 61 6c 75 65 20 31 3e  END(0, <value 1>
39e0: 29 3b 0a 2a 2a 20 20 20 20 68 61 73 68 5f 6b 65  );.**    hash_ke
39f0: 79 5f 76 61 6c 75 65 20 3d 20 48 41 53 48 5f 41  y_value = HASH_A
3a00: 50 50 45 4e 44 28 68 61 73 68 5f 6b 65 79 5f 76  PPEND(hash_key_v
3a10: 61 6c 75 65 2c 20 3c 76 61 6c 75 65 20 32 3e 29  alue, <value 2>)
3a20: 3b 0a 2a 2a 20 20 20 20 68 61 73 68 5f 6b 65 79  ;.**    hash_key
3a30: 5f 76 61 6c 75 65 20 3d 20 48 41 53 48 5f 41 50  _value = HASH_AP
3a40: 50 45 4e 44 28 68 61 73 68 5f 6b 65 79 5f 76 61  PEND(hash_key_va
3a50: 6c 75 65 2c 20 3c 76 61 6c 75 65 20 33 3e 29 3b  lue, <value 3>);
3a60: 0a 2a 2a 0a 2a 2a 20 49 6e 20 70 72 61 63 74 69  .**.** In practi
3a70: 63 65 2c 20 74 68 65 20 64 61 74 61 20 73 74 72  ce, the data str
3a80: 75 63 74 75 72 65 73 20 74 68 69 73 20 6d 61 63  uctures this mac
3a90: 72 6f 20 69 73 20 75 73 65 64 20 66 6f 72 20 61  ro is used for a
3aa0: 72 65 20 74 68 65 20 70 72 69 6d 61 72 79 0a 2a  re the primary.*
3ab0: 2a 20 6b 65 79 20 76 61 6c 75 65 73 20 6f 66 20  * key values of 
3ac0: 6d 6f 64 69 66 69 65 64 20 72 6f 77 73 2e 0a 2a  modified rows..*
3ad0: 2f 0a 23 64 65 66 69 6e 65 20 48 41 53 48 5f 41  /.#define HASH_A
3ae0: 50 50 45 4e 44 28 68 61 73 68 2c 20 61 64 64 29  PPEND(hash, add)
3af0: 20 28 28 68 61 73 68 29 20 3c 3c 20 33 29 20 5e   ((hash) << 3) ^
3b00: 20 28 68 61 73 68 29 20 5e 20 28 75 6e 73 69 67   (hash) ^ (unsig
3b10: 6e 65 64 20 69 6e 74 29 28 61 64 64 29 0a 0a 2f  ned int)(add)../
3b20: 2a 0a 2a 2a 20 41 70 70 65 6e 64 20 74 68 65 20  *.** Append the 
3b30: 68 61 73 68 20 6f 66 20 74 68 65 20 36 34 2d 62  hash of the 64-b
3b40: 69 74 20 69 6e 74 65 67 65 72 20 70 61 73 73 65  it integer passe
3b50: 64 20 61 73 20 74 68 65 20 73 65 63 6f 6e 64 20  d as the second 
3b60: 61 72 67 75 6d 65 6e 74 20 74 6f 20 74 68 65 0a  argument to the.
3b70: 2a 2a 20 68 61 73 68 2d 6b 65 79 20 76 61 6c 75  ** hash-key valu
3b80: 65 20 70 61 73 73 65 64 20 61 73 20 74 68 65 20  e passed as the 
3b90: 66 69 72 73 74 2e 20 52 65 74 75 72 6e 20 74 68  first. Return th
3ba0: 65 20 6e 65 77 20 68 61 73 68 2d 6b 65 79 20 76  e new hash-key v
3bb0: 61 6c 75 65 2e 0a 2a 2f 0a 73 74 61 74 69 63 20  alue..*/.static 
3bc0: 75 6e 73 69 67 6e 65 64 20 69 6e 74 20 73 65 73  unsigned int ses
3bd0: 73 69 6f 6e 48 61 73 68 41 70 70 65 6e 64 49 36  sionHashAppendI6
3be0: 34 28 75 6e 73 69 67 6e 65 64 20 69 6e 74 20 68  4(unsigned int h
3bf0: 2c 20 69 36 34 20 69 29 7b 0a 20 20 68 20 3d 20  , i64 i){.  h = 
3c00: 48 41 53 48 5f 41 50 50 45 4e 44 28 68 2c 20 69  HASH_APPEND(h, i
3c10: 20 26 20 30 78 46 46 46 46 46 46 46 46 29 3b 0a   & 0xFFFFFFFF);.
3c20: 20 20 72 65 74 75 72 6e 20 48 41 53 48 5f 41 50    return HASH_AP
3c30: 50 45 4e 44 28 68 2c 20 28 69 3e 3e 33 32 29 26  PEND(h, (i>>32)&
3c40: 30 78 46 46 46 46 46 46 46 46 29 3b 0a 7d 0a 0a  0xFFFFFFFF);.}..
3c50: 2f 2a 0a 2a 2a 20 41 70 70 65 6e 64 20 74 68 65  /*.** Append the
3c60: 20 68 61 73 68 20 6f 66 20 74 68 65 20 62 6c 6f   hash of the blo
3c70: 62 20 70 61 73 73 65 64 20 76 69 61 20 74 68 65  b passed via the
3c80: 20 73 65 63 6f 6e 64 20 61 6e 64 20 74 68 69 72   second and thir
3c90: 64 20 61 72 67 75 6d 65 6e 74 73 20 74 6f 20 0a  d arguments to .
3ca0: 2a 2a 20 74 68 65 20 68 61 73 68 2d 6b 65 79 20  ** the hash-key 
3cb0: 76 61 6c 75 65 20 70 61 73 73 65 64 20 61 73 20  value passed as 
3cc0: 74 68 65 20 66 69 72 73 74 2e 20 52 65 74 75 72  the first. Retur
3cd0: 6e 20 74 68 65 20 6e 65 77 20 68 61 73 68 2d 6b  n the new hash-k
3ce0: 65 79 20 76 61 6c 75 65 2e 0a 2a 2f 0a 73 74 61  ey value..*/.sta
3cf0: 74 69 63 20 75 6e 73 69 67 6e 65 64 20 69 6e 74  tic unsigned int
3d00: 20 73 65 73 73 69 6f 6e 48 61 73 68 41 70 70 65   sessionHashAppe
3d10: 6e 64 42 6c 6f 62 28 75 6e 73 69 67 6e 65 64 20  ndBlob(unsigned 
3d20: 69 6e 74 20 68 2c 20 69 6e 74 20 6e 2c 20 63 6f  int h, int n, co
3d30: 6e 73 74 20 75 38 20 2a 7a 29 7b 0a 20 20 69 6e  nst u8 *z){.  in
3d40: 74 20 69 3b 0a 20 20 66 6f 72 28 69 3d 30 3b 20  t i;.  for(i=0; 
3d50: 69 3c 6e 3b 20 69 2b 2b 29 20 68 20 3d 20 48 41  i<n; i++) h = HA
3d60: 53 48 5f 41 50 50 45 4e 44 28 68 2c 20 7a 5b 69  SH_APPEND(h, z[i
3d70: 5d 29 3b 0a 20 20 72 65 74 75 72 6e 20 68 3b 0a  ]);.  return h;.
3d80: 7d 0a 0a 2f 2a 0a 2a 2a 20 41 70 70 65 6e 64 20  }../*.** Append 
3d90: 74 68 65 20 68 61 73 68 20 6f 66 20 74 68 65 20  the hash of the 
3da0: 64 61 74 61 20 74 79 70 65 20 70 61 73 73 65 64  data type passed
3db0: 20 61 73 20 74 68 65 20 73 65 63 6f 6e 64 20 61   as the second a
3dc0: 72 67 75 6d 65 6e 74 20 74 6f 20 74 68 65 0a 2a  rgument to the.*
3dd0: 2a 20 68 61 73 68 2d 6b 65 79 20 76 61 6c 75 65  * hash-key value
3de0: 20 70 61 73 73 65 64 20 61 73 20 74 68 65 20 66   passed as the f
3df0: 69 72 73 74 2e 20 52 65 74 75 72 6e 20 74 68 65  irst. Return the
3e00: 20 6e 65 77 20 68 61 73 68 2d 6b 65 79 20 76 61   new hash-key va
3e10: 6c 75 65 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 75  lue..*/.static u
3e20: 6e 73 69 67 6e 65 64 20 69 6e 74 20 73 65 73 73  nsigned int sess
3e30: 69 6f 6e 48 61 73 68 41 70 70 65 6e 64 54 79 70  ionHashAppendTyp
3e40: 65 28 75 6e 73 69 67 6e 65 64 20 69 6e 74 20 68  e(unsigned int h
3e50: 2c 20 69 6e 74 20 65 54 79 70 65 29 7b 0a 20 20  , int eType){.  
3e60: 72 65 74 75 72 6e 20 48 41 53 48 5f 41 50 50 45  return HASH_APPE
3e70: 4e 44 28 68 2c 20 65 54 79 70 65 29 3b 0a 7d 0a  ND(h, eType);.}.
3e80: 0a 2f 2a 0a 2a 2a 20 54 68 69 73 20 66 75 6e 63  ./*.** This func
3e90: 74 69 6f 6e 20 6d 61 79 20 6f 6e 6c 79 20 62 65  tion may only be
3ea0: 20 63 61 6c 6c 65 64 20 66 72 6f 6d 20 77 69 74   called from wit
3eb0: 68 69 6e 20 61 20 70 72 65 2d 75 70 64 61 74 65  hin a pre-update
3ec0: 20 63 61 6c 6c 62 61 63 6b 2e 0a 2a 2a 20 49 74   callback..** It
3ed0: 20 63 61 6c 63 75 6c 61 74 65 73 20 61 20 68 61   calculates a ha
3ee0: 73 68 20 62 61 73 65 64 20 6f 6e 20 74 68 65 20  sh based on the 
3ef0: 70 72 69 6d 61 72 79 20 6b 65 79 20 76 61 6c 75  primary key valu
3f00: 65 73 20 6f 66 20 74 68 65 20 6f 6c 64 2e 2a 20  es of the old.* 
3f10: 6f 72 20 0a 2a 2a 20 6e 65 77 2e 2a 20 72 6f 77  or .** new.* row
3f20: 20 63 75 72 72 65 6e 74 6c 79 20 61 76 61 69 6c   currently avail
3f30: 61 62 6c 65 20 61 6e 64 2c 20 61 73 73 75 6d 69  able and, assumi
3f40: 6e 67 20 6e 6f 20 65 72 72 6f 72 20 6f 63 63 75  ng no error occu
3f50: 72 73 2c 20 77 72 69 74 65 73 20 69 74 20 74 6f  rs, writes it to
3f60: 0a 2a 2a 20 2a 70 69 48 61 73 68 20 62 65 66 6f  .** *piHash befo
3f70: 72 65 20 72 65 74 75 72 6e 69 6e 67 2e 20 49 66  re returning. If
3f80: 20 74 68 65 20 70 72 69 6d 61 72 79 20 6b 65 79   the primary key
3f90: 20 63 6f 6e 74 61 69 6e 73 20 6f 6e 65 20 6f 72   contains one or
3fa0: 20 6d 6f 72 65 20 4e 55 4c 4c 0a 2a 2a 20 76 61   more NULL.** va
3fb0: 6c 75 65 73 2c 20 2a 70 62 4e 75 6c 6c 50 4b 20  lues, *pbNullPK 
3fc0: 69 73 20 73 65 74 20 74 6f 20 74 72 75 65 20 62  is set to true b
3fd0: 65 66 6f 72 65 20 72 65 74 75 72 6e 69 6e 67 2e  efore returning.
3fe0: 0a 2a 2a 0a 2a 2a 20 49 66 20 61 6e 20 65 72 72  .**.** If an err
3ff0: 6f 72 20 6f 63 63 75 72 73 2c 20 61 6e 20 53 51  or occurs, an SQ
4000: 4c 69 74 65 20 65 72 72 6f 72 20 63 6f 64 65 20  Lite error code 
4010: 69 73 20 72 65 74 75 72 6e 65 64 20 61 6e 64 20  is returned and 
4020: 74 68 65 20 66 69 6e 61 6c 20 76 61 6c 75 65 73  the final values
4030: 0a 2a 2a 20 6f 66 20 2a 70 69 48 61 73 68 20 61  .** of *piHash a
4040: 73 6e 20 2a 70 62 4e 75 6c 6c 50 4b 20 61 72 65  sn *pbNullPK are
4050: 20 75 6e 64 65 66 69 6e 65 64 2e 20 4f 74 68 65   undefined. Othe
4060: 72 77 69 73 65 2c 20 53 51 4c 49 54 45 5f 4f 4b  rwise, SQLITE_OK
4070: 20 69 73 20 72 65 74 75 72 6e 65 64 0a 2a 2a 20   is returned.** 
4080: 61 6e 64 20 74 68 65 20 6f 75 74 70 75 74 20 76  and the output v
4090: 61 72 69 61 62 6c 65 73 20 61 72 65 20 73 65 74  ariables are set
40a0: 20 61 73 20 64 65 73 63 72 69 62 65 64 20 61 62   as described ab
40b0: 6f 76 65 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69  ove..*/.static i
40c0: 6e 74 20 73 65 73 73 69 6f 6e 50 72 65 75 70 64  nt sessionPreupd
40d0: 61 74 65 48 61 73 68 28 0a 20 20 73 71 6c 69 74  ateHash(.  sqlit
40e0: 65 33 5f 73 65 73 73 69 6f 6e 20 2a 70 53 65 73  e3_session *pSes
40f0: 73 69 6f 6e 2c 20 20 20 20 20 20 2f 2a 20 53 65  sion,      /* Se
4100: 73 73 69 6f 6e 20 6f 62 6a 65 63 74 20 74 68 61  ssion object tha
4110: 74 20 6f 77 6e 73 20 70 54 61 62 20 2a 2f 0a 20  t owns pTab */. 
4120: 20 53 65 73 73 69 6f 6e 54 61 62 6c 65 20 2a 70   SessionTable *p
4130: 54 61 62 2c 20 20 20 20 20 20 20 20 20 20 20 20  Tab,            
4140: 20 2f 2a 20 53 65 73 73 69 6f 6e 20 74 61 62 6c   /* Session tabl
4150: 65 20 68 61 6e 64 6c 65 20 2a 2f 0a 20 20 69 6e  e handle */.  in
4160: 74 20 62 4e 65 77 2c 20 20 20 20 20 20 20 20 20  t bNew,         
4170: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
4180: 20 54 72 75 65 20 74 6f 20 68 61 73 68 20 74 68   True to hash th
4190: 65 20 6e 65 77 2e 2a 20 50 4b 20 2a 2f 0a 20 20  e new.* PK */.  
41a0: 69 6e 74 20 2a 70 69 48 61 73 68 2c 20 20 20 20  int *piHash,    
41b0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
41c0: 2f 2a 20 4f 55 54 3a 20 48 61 73 68 20 76 61 6c  /* OUT: Hash val
41d0: 75 65 20 2a 2f 0a 20 20 69 6e 74 20 2a 70 62 4e  ue */.  int *pbN
41e0: 75 6c 6c 50 4b 20 20 20 20 20 20 20 20 20 20 20  ullPK           
41f0: 20 20 20 20 20 20 20 20 2f 2a 20 4f 55 54 3a 20          /* OUT: 
4200: 54 72 75 65 20 69 66 20 74 68 65 72 65 20 61 72  True if there ar
4210: 65 20 4e 55 4c 4c 20 76 61 6c 75 65 73 20 69 6e  e NULL values in
4220: 20 50 4b 20 2a 2f 0a 29 7b 0a 20 20 75 6e 73 69   PK */.){.  unsi
4230: 67 6e 65 64 20 69 6e 74 20 68 20 3d 20 30 3b 20  gned int h = 0; 
4240: 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 48              /* H
4250: 61 73 68 20 76 61 6c 75 65 20 74 6f 20 72 65 74  ash value to ret
4260: 75 72 6e 20 2a 2f 0a 20 20 69 6e 74 20 69 3b 20  urn */.  int i; 
4270: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
4280: 20 20 20 20 20 20 20 20 20 2f 2a 20 55 73 65 64           /* Used
4290: 20 74 6f 20 69 74 65 72 61 74 65 20 74 68 72 6f   to iterate thro
42a0: 75 67 68 20 63 6f 6c 75 6d 6e 73 20 2a 2f 0a 0a  ugh columns */..
42b0: 20 20 61 73 73 65 72 74 28 20 2a 70 62 4e 75 6c    assert( *pbNul
42c0: 6c 50 4b 3d 3d 30 20 29 3b 0a 20 20 61 73 73 65  lPK==0 );.  asse
42d0: 72 74 28 20 70 54 61 62 2d 3e 6e 43 6f 6c 3d 3d  rt( pTab->nCol==
42e0: 70 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 78  pSession->hook.x
42f0: 43 6f 75 6e 74 28 70 53 65 73 73 69 6f 6e 2d 3e  Count(pSession->
4300: 68 6f 6f 6b 2e 70 43 74 78 29 20 29 3b 0a 20 20  hook.pCtx) );.  
4310: 66 6f 72 28 69 3d 30 3b 20 69 3c 70 54 61 62 2d  for(i=0; i<pTab-
4320: 3e 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a 20 20 20  >nCol; i++){.   
4330: 20 69 66 28 20 70 54 61 62 2d 3e 61 62 50 4b 5b   if( pTab->abPK[
4340: 69 5d 20 29 7b 0a 20 20 20 20 20 20 69 6e 74 20  i] ){.      int 
4350: 72 63 3b 0a 20 20 20 20 20 20 69 6e 74 20 65 54  rc;.      int eT
4360: 79 70 65 3b 0a 20 20 20 20 20 20 73 71 6c 69 74  ype;.      sqlit
4370: 65 33 5f 76 61 6c 75 65 20 2a 70 56 61 6c 3b 0a  e3_value *pVal;.
4380: 0a 20 20 20 20 20 20 69 66 28 20 62 4e 65 77 20  .      if( bNew 
4390: 29 7b 0a 20 20 20 20 20 20 20 20 72 63 20 3d 20  ){.        rc = 
43a0: 70 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 78  pSession->hook.x
43b0: 4e 65 77 28 70 53 65 73 73 69 6f 6e 2d 3e 68 6f  New(pSession->ho
43c0: 6f 6b 2e 70 43 74 78 2c 20 69 2c 20 26 70 56 61  ok.pCtx, i, &pVa
43d0: 6c 29 3b 0a 20 20 20 20 20 20 7d 65 6c 73 65 7b  l);.      }else{
43e0: 0a 20 20 20 20 20 20 20 20 72 63 20 3d 20 70 53  .        rc = pS
43f0: 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 78 4f 6c  ession->hook.xOl
4400: 64 28 70 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b  d(pSession->hook
4410: 2e 70 43 74 78 2c 20 69 2c 20 26 70 56 61 6c 29  .pCtx, i, &pVal)
4420: 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20  ;.      }.      
4430: 69 66 28 20 72 63 21 3d 53 51 4c 49 54 45 5f 4f  if( rc!=SQLITE_O
4440: 4b 20 29 20 72 65 74 75 72 6e 20 72 63 3b 0a 0a  K ) return rc;..
4450: 20 20 20 20 20 20 65 54 79 70 65 20 3d 20 73 71        eType = sq
4460: 6c 69 74 65 33 5f 76 61 6c 75 65 5f 74 79 70 65  lite3_value_type
4470: 28 70 56 61 6c 29 3b 0a 20 20 20 20 20 20 68 20  (pVal);.      h 
4480: 3d 20 73 65 73 73 69 6f 6e 48 61 73 68 41 70 70  = sessionHashApp
4490: 65 6e 64 54 79 70 65 28 68 2c 20 65 54 79 70 65  endType(h, eType
44a0: 29 3b 0a 20 20 20 20 20 20 69 66 28 20 65 54 79  );.      if( eTy
44b0: 70 65 3d 3d 53 51 4c 49 54 45 5f 49 4e 54 45 47  pe==SQLITE_INTEG
44c0: 45 52 20 7c 7c 20 65 54 79 70 65 3d 3d 53 51 4c  ER || eType==SQL
44d0: 49 54 45 5f 46 4c 4f 41 54 20 29 7b 0a 20 20 20  ITE_FLOAT ){.   
44e0: 20 20 20 20 20 69 36 34 20 69 56 61 6c 3b 0a 20       i64 iVal;. 
44f0: 20 20 20 20 20 20 20 69 66 28 20 65 54 79 70 65         if( eType
4500: 3d 3d 53 51 4c 49 54 45 5f 49 4e 54 45 47 45 52  ==SQLITE_INTEGER
4510: 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 69 56   ){.          iV
4520: 61 6c 20 3d 20 73 71 6c 69 74 65 33 5f 76 61 6c  al = sqlite3_val
4530: 75 65 5f 69 6e 74 36 34 28 70 56 61 6c 29 3b 0a  ue_int64(pVal);.
4540: 20 20 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a 20          }else{. 
4550: 20 20 20 20 20 20 20 20 20 64 6f 75 62 6c 65 20           double 
4560: 72 56 61 6c 20 3d 20 73 71 6c 69 74 65 33 5f 76  rVal = sqlite3_v
4570: 61 6c 75 65 5f 64 6f 75 62 6c 65 28 70 56 61 6c  alue_double(pVal
4580: 29 3b 0a 20 20 20 20 20 20 20 20 20 20 61 73 73  );.          ass
4590: 65 72 74 28 20 73 69 7a 65 6f 66 28 69 56 61 6c  ert( sizeof(iVal
45a0: 29 3d 3d 38 20 26 26 20 73 69 7a 65 6f 66 28 72  )==8 && sizeof(r
45b0: 56 61 6c 29 3d 3d 38 20 29 3b 0a 20 20 20 20 20  Val)==8 );.     
45c0: 20 20 20 20 20 6d 65 6d 63 70 79 28 26 69 56 61       memcpy(&iVa
45d0: 6c 2c 20 26 72 56 61 6c 2c 20 38 29 3b 0a 20 20  l, &rVal, 8);.  
45e0: 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 20 20        }.        
45f0: 68 20 3d 20 73 65 73 73 69 6f 6e 48 61 73 68 41  h = sessionHashA
4600: 70 70 65 6e 64 49 36 34 28 68 2c 20 69 56 61 6c  ppendI64(h, iVal
4610: 29 3b 0a 20 20 20 20 20 20 7d 65 6c 73 65 20 69  );.      }else i
4620: 66 28 20 65 54 79 70 65 3d 3d 53 51 4c 49 54 45  f( eType==SQLITE
4630: 5f 54 45 58 54 20 7c 7c 20 65 54 79 70 65 3d 3d  _TEXT || eType==
4640: 53 51 4c 49 54 45 5f 42 4c 4f 42 20 29 7b 0a 20  SQLITE_BLOB ){. 
4650: 20 20 20 20 20 20 20 63 6f 6e 73 74 20 75 38 20         const u8 
4660: 2a 7a 3b 0a 20 20 20 20 20 20 20 20 69 6e 74 20  *z;.        int 
4670: 6e 3b 0a 20 20 20 20 20 20 20 20 69 66 28 20 65  n;.        if( e
4680: 54 79 70 65 3d 3d 53 51 4c 49 54 45 5f 54 45 58  Type==SQLITE_TEX
4690: 54 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 7a  T ){.          z
46a0: 20 3d 20 28 63 6f 6e 73 74 20 75 38 20 2a 29 73   = (const u8 *)s
46b0: 71 6c 69 74 65 33 5f 76 61 6c 75 65 5f 74 65 78  qlite3_value_tex
46c0: 74 28 70 56 61 6c 29 3b 0a 20 20 20 20 20 20 20  t(pVal);.       
46d0: 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 20 20   }else{.        
46e0: 20 20 7a 20 3d 20 28 63 6f 6e 73 74 20 75 38 20    z = (const u8 
46f0: 2a 29 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 5f  *)sqlite3_value_
4700: 62 6c 6f 62 28 70 56 61 6c 29 3b 0a 20 20 20 20  blob(pVal);.    
4710: 20 20 20 20 7d 0a 20 20 20 20 20 20 20 20 6e 20      }.        n 
4720: 3d 20 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 5f  = sqlite3_value_
4730: 62 79 74 65 73 28 70 56 61 6c 29 3b 0a 20 20 20  bytes(pVal);.   
4740: 20 20 20 20 20 69 66 28 20 21 7a 20 26 26 20 28       if( !z && (
4750: 65 54 79 70 65 21 3d 53 51 4c 49 54 45 5f 42 4c  eType!=SQLITE_BL
4760: 4f 42 20 7c 7c 20 6e 3e 30 29 20 29 20 72 65 74  OB || n>0) ) ret
4770: 75 72 6e 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d  urn SQLITE_NOMEM
4780: 3b 0a 20 20 20 20 20 20 20 20 68 20 3d 20 73 65  ;.        h = se
4790: 73 73 69 6f 6e 48 61 73 68 41 70 70 65 6e 64 42  ssionHashAppendB
47a0: 6c 6f 62 28 68 2c 20 6e 2c 20 7a 29 3b 0a 20 20  lob(h, n, z);.  
47b0: 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20      }else{.     
47c0: 20 20 20 61 73 73 65 72 74 28 20 65 54 79 70 65     assert( eType
47d0: 3d 3d 53 51 4c 49 54 45 5f 4e 55 4c 4c 20 29 3b  ==SQLITE_NULL );
47e0: 0a 20 20 20 20 20 20 20 20 2a 70 62 4e 75 6c 6c  .        *pbNull
47f0: 50 4b 20 3d 20 31 3b 0a 20 20 20 20 20 20 7d 0a  PK = 1;.      }.
4800: 20 20 20 20 7d 0a 20 20 7d 0a 0a 20 20 2a 70 69      }.  }..  *pi
4810: 48 61 73 68 20 3d 20 28 68 20 25 20 70 54 61 62  Hash = (h % pTab
4820: 2d 3e 6e 43 68 61 6e 67 65 29 3b 0a 20 20 72 65  ->nChange);.  re
4830: 74 75 72 6e 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a  turn SQLITE_OK;.
4840: 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68 65 20 62 75 66  }../*.** The buf
4850: 66 65 72 20 74 68 61 74 20 74 68 65 20 61 72 67  fer that the arg
4860: 75 6d 65 6e 74 20 70 6f 69 6e 74 73 20 74 6f 20  ument points to 
4870: 63 6f 6e 74 61 69 6e 73 20 61 20 73 65 72 69 61  contains a seria
4880: 6c 69 7a 65 64 20 53 51 4c 20 76 61 6c 75 65 2e  lized SQL value.
4890: 0a 2a 2a 20 52 65 74 75 72 6e 20 74 68 65 20 6e  .** Return the n
48a0: 75 6d 62 65 72 20 6f 66 20 62 79 74 65 73 20 6f  umber of bytes o
48b0: 66 20 73 70 61 63 65 20 6f 63 63 75 70 69 65 64  f space occupied
48c0: 20 62 79 20 74 68 65 20 76 61 6c 75 65 20 28 69   by the value (i
48d0: 6e 63 6c 75 64 69 6e 67 0a 2a 2a 20 74 68 65 20  ncluding.** the 
48e0: 74 79 70 65 20 62 79 74 65 29 2e 0a 2a 2f 0a 73  type byte)..*/.s
48f0: 74 61 74 69 63 20 69 6e 74 20 73 65 73 73 69 6f  tatic int sessio
4900: 6e 53 65 72 69 61 6c 4c 65 6e 28 75 38 20 2a 61  nSerialLen(u8 *a
4910: 29 7b 0a 20 20 69 6e 74 20 65 20 3d 20 2a 61 3b  ){.  int e = *a;
4920: 0a 20 20 69 6e 74 20 6e 3b 0a 20 20 69 66 28 20  .  int n;.  if( 
4930: 65 3d 3d 30 20 29 20 72 65 74 75 72 6e 20 31 3b  e==0 ) return 1;
4940: 0a 20 20 69 66 28 20 65 3d 3d 53 51 4c 49 54 45  .  if( e==SQLITE
4950: 5f 4e 55 4c 4c 20 29 20 72 65 74 75 72 6e 20 31  _NULL ) return 1
4960: 3b 0a 20 20 69 66 28 20 65 3d 3d 53 51 4c 49 54  ;.  if( e==SQLIT
4970: 45 5f 49 4e 54 45 47 45 52 20 7c 7c 20 65 3d 3d  E_INTEGER || e==
4980: 53 51 4c 49 54 45 5f 46 4c 4f 41 54 20 29 20 72  SQLITE_FLOAT ) r
4990: 65 74 75 72 6e 20 39 3b 0a 20 20 72 65 74 75 72  eturn 9;.  retur
49a0: 6e 20 73 65 73 73 69 6f 6e 56 61 72 69 6e 74 47  n sessionVarintG
49b0: 65 74 28 26 61 5b 31 5d 2c 20 26 6e 29 20 2b 20  et(&a[1], &n) + 
49c0: 31 20 2b 20 6e 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20  1 + n;.}../*.** 
49d0: 42 61 73 65 64 20 6f 6e 20 74 68 65 20 70 72 69  Based on the pri
49e0: 6d 61 72 79 20 6b 65 79 20 76 61 6c 75 65 73 20  mary key values 
49f0: 73 74 6f 72 65 64 20 69 6e 20 63 68 61 6e 67 65  stored in change
4a00: 20 61 52 65 63 6f 72 64 2c 20 63 61 6c 63 75 6c   aRecord, calcul
4a10: 61 74 65 20 61 0a 2a 2a 20 68 61 73 68 20 6b 65  ate a.** hash ke
4a20: 79 2e 20 41 73 73 75 6d 65 20 74 68 65 20 68 61  y. Assume the ha
4a30: 73 20 74 61 62 6c 65 20 68 61 73 20 6e 42 75 63  s table has nBuc
4a40: 6b 65 74 20 62 75 63 6b 65 74 73 2e 20 54 68 65  ket buckets. The
4a50: 20 68 61 73 68 20 6b 65 79 73 0a 2a 2a 20 63 61   hash keys.** ca
4a60: 6c 63 75 6c 61 74 65 64 20 62 79 20 74 68 69 73  lculated by this
4a70: 20 66 75 6e 63 74 69 6f 6e 20 61 72 65 20 63 6f   function are co
4a80: 6d 70 61 74 69 62 6c 65 20 77 69 74 68 20 74 68  mpatible with th
4a90: 6f 73 65 20 63 61 6c 63 75 6c 61 74 65 64 20 62  ose calculated b
4aa0: 79 0a 2a 2a 20 73 65 73 73 69 6f 6e 50 72 65 75  y.** sessionPreu
4ab0: 70 64 61 74 65 48 61 73 68 28 29 2e 0a 2a 2a 0a  pdateHash()..**.
4ac0: 2a 2a 20 54 68 65 20 62 50 6b 4f 6e 6c 79 20 61  ** The bPkOnly a
4ad0: 72 67 75 6d 65 6e 74 20 69 73 20 6e 6f 6e 2d 7a  rgument is non-z
4ae0: 65 72 6f 20 69 66 20 74 68 65 20 72 65 63 6f 72  ero if the recor
4af0: 64 20 61 74 20 61 52 65 63 6f 72 64 5b 5d 20 69  d at aRecord[] i
4b00: 73 20 66 72 6f 6d 0a 2a 2a 20 61 20 70 61 74 63  s from.** a patc
4b10: 68 73 65 74 20 44 45 4c 45 54 45 2e 20 49 6e 20  hset DELETE. In 
4b20: 74 68 69 73 20 63 61 73 65 20 74 68 65 20 6e 6f  this case the no
4b30: 6e 2d 50 4b 20 66 69 65 6c 64 73 20 61 72 65 20  n-PK fields are 
4b40: 6f 6d 69 74 74 65 64 20 65 6e 74 69 72 65 6c 79  omitted entirely
4b50: 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 75 6e 73 69  ..*/.static unsi
4b60: 67 6e 65 64 20 69 6e 74 20 73 65 73 73 69 6f 6e  gned int session
4b70: 43 68 61 6e 67 65 48 61 73 68 28 0a 20 20 53 65  ChangeHash(.  Se
4b80: 73 73 69 6f 6e 54 61 62 6c 65 20 2a 70 54 61 62  ssionTable *pTab
4b90: 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a  ,             /*
4ba0: 20 54 61 62 6c 65 20 68 61 6e 64 6c 65 20 2a 2f   Table handle */
4bb0: 0a 20 20 69 6e 74 20 62 50 6b 4f 6e 6c 79 2c 20  .  int bPkOnly, 
4bc0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
4bd0: 20 20 20 2f 2a 20 52 65 63 6f 72 64 20 63 6f 6e     /* Record con
4be0: 73 69 73 74 73 20 6f 66 20 50 4b 20 66 69 65 6c  sists of PK fiel
4bf0: 64 73 20 6f 6e 6c 79 20 2a 2f 0a 20 20 75 38 20  ds only */.  u8 
4c00: 2a 61 52 65 63 6f 72 64 2c 20 20 20 20 20 20 20  *aRecord,       
4c10: 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
4c20: 43 68 61 6e 67 65 20 72 65 63 6f 72 64 20 2a 2f  Change record */
4c30: 0a 20 20 69 6e 74 20 6e 42 75 63 6b 65 74 20 20  .  int nBucket  
4c40: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
4c50: 20 20 20 2f 2a 20 41 73 73 75 6d 65 20 74 68 69     /* Assume thi
4c60: 73 20 6d 61 6e 79 20 62 75 63 6b 65 74 73 20 69  s many buckets i
4c70: 6e 20 68 61 73 68 20 74 61 62 6c 65 20 2a 2f 0a  n hash table */.
4c80: 29 7b 0a 20 20 75 6e 73 69 67 6e 65 64 20 69 6e  ){.  unsigned in
4c90: 74 20 68 20 3d 20 30 3b 20 20 20 20 20 20 20 20  t h = 0;        
4ca0: 20 20 20 20 20 2f 2a 20 56 61 6c 75 65 20 74 6f       /* Value to
4cb0: 20 72 65 74 75 72 6e 20 2a 2f 0a 20 20 69 6e 74   return */.  int
4cc0: 20 69 3b 20 20 20 20 20 20 20 20 20 20 20 20 20   i;             
4cd0: 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
4ce0: 55 73 65 64 20 74 6f 20 69 74 65 72 61 74 65 20  Used to iterate 
4cf0: 74 68 72 6f 75 67 68 20 63 6f 6c 75 6d 6e 73 20  through columns 
4d00: 2a 2f 0a 20 20 75 38 20 2a 61 20 3d 20 61 52 65  */.  u8 *a = aRe
4d10: 63 6f 72 64 3b 20 20 20 20 20 20 20 20 20 20 20  cord;           
4d20: 20 20 20 20 20 2f 2a 20 55 73 65 64 20 74 6f 20       /* Used to 
4d30: 69 74 65 72 61 74 65 20 74 68 72 6f 75 67 68 20  iterate through 
4d40: 63 68 61 6e 67 65 20 72 65 63 6f 72 64 20 2a 2f  change record */
4d50: 0a 0a 20 20 66 6f 72 28 69 3d 30 3b 20 69 3c 70  ..  for(i=0; i<p
4d60: 54 61 62 2d 3e 6e 43 6f 6c 3b 20 69 2b 2b 29 7b  Tab->nCol; i++){
4d70: 0a 20 20 20 20 69 6e 74 20 65 54 79 70 65 20 3d  .    int eType =
4d80: 20 2a 61 3b 0a 20 20 20 20 69 6e 74 20 69 73 50   *a;.    int isP
4d90: 4b 20 3d 20 70 54 61 62 2d 3e 61 62 50 4b 5b 69  K = pTab->abPK[i
4da0: 5d 3b 0a 20 20 20 20 69 66 28 20 62 50 6b 4f 6e  ];.    if( bPkOn
4db0: 6c 79 20 26 26 20 69 73 50 4b 3d 3d 30 20 29 20  ly && isPK==0 ) 
4dc0: 63 6f 6e 74 69 6e 75 65 3b 0a 0a 20 20 20 20 2f  continue;..    /
4dd0: 2a 20 49 74 20 69 73 20 6e 6f 74 20 70 6f 73 73  * It is not poss
4de0: 69 62 6c 65 20 66 6f 72 20 65 54 79 70 65 20 74  ible for eType t
4df0: 6f 20 62 65 20 53 51 4c 49 54 45 5f 4e 55 4c 4c  o be SQLITE_NULL
4e00: 20 68 65 72 65 2e 20 54 68 65 20 73 65 73 73 69   here. The sessi
4e10: 6f 6e 20 0a 20 20 20 20 2a 2a 20 6d 6f 64 75 6c  on .    ** modul
4e20: 65 20 64 6f 65 73 20 6e 6f 74 20 72 65 63 6f 72  e does not recor
4e30: 64 20 63 68 61 6e 67 65 73 20 66 6f 72 20 72 6f  d changes for ro
4e40: 77 73 20 77 69 74 68 20 4e 55 4c 4c 20 76 61 6c  ws with NULL val
4e50: 75 65 73 20 73 74 6f 72 65 64 20 69 6e 0a 20 20  ues stored in.  
4e60: 20 20 2a 2a 20 70 72 69 6d 61 72 79 20 6b 65 79    ** primary key
4e70: 20 63 6f 6c 75 6d 6e 73 2e 20 2a 2f 0a 20 20 20   columns. */.   
4e80: 20 61 73 73 65 72 74 28 20 65 54 79 70 65 3d 3d   assert( eType==
4e90: 53 51 4c 49 54 45 5f 49 4e 54 45 47 45 52 20 7c  SQLITE_INTEGER |
4ea0: 7c 20 65 54 79 70 65 3d 3d 53 51 4c 49 54 45 5f  | eType==SQLITE_
4eb0: 46 4c 4f 41 54 20 0a 20 20 20 20 20 20 20 20 20  FLOAT .         
4ec0: 7c 7c 20 65 54 79 70 65 3d 3d 53 51 4c 49 54 45  || eType==SQLITE
4ed0: 5f 54 45 58 54 20 7c 7c 20 65 54 79 70 65 3d 3d  _TEXT || eType==
4ee0: 53 51 4c 49 54 45 5f 42 4c 4f 42 20 0a 20 20 20  SQLITE_BLOB .   
4ef0: 20 20 20 20 20 20 7c 7c 20 65 54 79 70 65 3d 3d        || eType==
4f00: 53 51 4c 49 54 45 5f 4e 55 4c 4c 20 7c 7c 20 65  SQLITE_NULL || e
4f10: 54 79 70 65 3d 3d 30 20 0a 20 20 20 20 29 3b 0a  Type==0 .    );.
4f20: 20 20 20 20 61 73 73 65 72 74 28 20 21 69 73 50      assert( !isP
4f30: 4b 20 7c 7c 20 28 65 54 79 70 65 21 3d 30 20 26  K || (eType!=0 &
4f40: 26 20 65 54 79 70 65 21 3d 53 51 4c 49 54 45 5f  & eType!=SQLITE_
4f50: 4e 55 4c 4c 29 20 29 3b 0a 0a 20 20 20 20 69 66  NULL) );..    if
4f60: 28 20 69 73 50 4b 20 29 7b 0a 20 20 20 20 20 20  ( isPK ){.      
4f70: 61 2b 2b 3b 0a 20 20 20 20 20 20 68 20 3d 20 73  a++;.      h = s
4f80: 65 73 73 69 6f 6e 48 61 73 68 41 70 70 65 6e 64  essionHashAppend
4f90: 54 79 70 65 28 68 2c 20 65 54 79 70 65 29 3b 0a  Type(h, eType);.
4fa0: 20 20 20 20 20 20 69 66 28 20 65 54 79 70 65 3d        if( eType=
4fb0: 3d 53 51 4c 49 54 45 5f 49 4e 54 45 47 45 52 20  =SQLITE_INTEGER 
4fc0: 7c 7c 20 65 54 79 70 65 3d 3d 53 51 4c 49 54 45  || eType==SQLITE
4fd0: 5f 46 4c 4f 41 54 20 29 7b 0a 20 20 20 20 20 20  _FLOAT ){.      
4fe0: 20 20 68 20 3d 20 73 65 73 73 69 6f 6e 48 61 73    h = sessionHas
4ff0: 68 41 70 70 65 6e 64 49 36 34 28 68 2c 20 73 65  hAppendI64(h, se
5000: 73 73 69 6f 6e 47 65 74 49 36 34 28 61 29 29 3b  ssionGetI64(a));
5010: 0a 20 20 20 20 20 20 20 20 61 20 2b 3d 20 38 3b  .        a += 8;
5020: 0a 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20  .      }else{.  
5030: 20 20 20 20 20 20 69 6e 74 20 6e 3b 20 0a 20 20        int n; .  
5040: 20 20 20 20 20 20 61 20 2b 3d 20 73 65 73 73 69        a += sessi
5050: 6f 6e 56 61 72 69 6e 74 47 65 74 28 61 2c 20 26  onVarintGet(a, &
5060: 6e 29 3b 0a 20 20 20 20 20 20 20 20 68 20 3d 20  n);.        h = 
5070: 73 65 73 73 69 6f 6e 48 61 73 68 41 70 70 65 6e  sessionHashAppen
5080: 64 42 6c 6f 62 28 68 2c 20 6e 2c 20 61 29 3b 0a  dBlob(h, n, a);.
5090: 20 20 20 20 20 20 20 20 61 20 2b 3d 20 6e 3b 0a          a += n;.
50a0: 20 20 20 20 20 20 7d 0a 20 20 20 20 7d 65 6c 73        }.    }els
50b0: 65 7b 0a 20 20 20 20 20 20 61 20 2b 3d 20 73 65  e{.      a += se
50c0: 73 73 69 6f 6e 53 65 72 69 61 6c 4c 65 6e 28 61  ssionSerialLen(a
50d0: 29 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a 20 20 72  );.    }.  }.  r
50e0: 65 74 75 72 6e 20 28 68 20 25 20 6e 42 75 63 6b  eturn (h % nBuck
50f0: 65 74 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 41 72  et);.}../*.** Ar
5100: 67 75 6d 65 6e 74 73 20 61 4c 65 66 74 20 61 6e  guments aLeft an
5110: 64 20 61 52 69 67 68 74 20 61 72 65 20 70 6f 69  d aRight are poi
5120: 6e 74 65 72 73 20 74 6f 20 63 68 61 6e 67 65 20  nters to change 
5130: 72 65 63 6f 72 64 73 20 66 6f 72 20 74 61 62 6c  records for tabl
5140: 65 20 70 54 61 62 2e 0a 2a 2a 20 54 68 69 73 20  e pTab..** This 
5150: 66 75 6e 63 74 69 6f 6e 20 72 65 74 75 72 6e 73  function returns
5160: 20 74 72 75 65 20 69 66 20 74 68 65 20 74 77 6f   true if the two
5170: 20 72 65 63 6f 72 64 73 20 61 70 70 6c 79 20 74   records apply t
5180: 6f 20 74 68 65 20 73 61 6d 65 20 72 6f 77 20 28  o the same row (
5190: 69 2e 65 2e 0a 2a 2a 20 68 61 76 65 20 74 68 65  i.e..** have the
51a0: 20 73 61 6d 65 20 76 61 6c 75 65 73 20 73 74 6f   same values sto
51b0: 72 65 64 20 69 6e 20 74 68 65 20 70 72 69 6d 61  red in the prima
51c0: 72 79 20 6b 65 79 20 63 6f 6c 75 6d 6e 73 29 2c  ry key columns),
51d0: 20 6f 72 20 66 61 6c 73 65 20 0a 2a 2a 20 6f 74   or false .** ot
51e0: 68 65 72 77 69 73 65 2e 0a 2a 2f 0a 73 74 61 74  herwise..*/.stat
51f0: 69 63 20 69 6e 74 20 73 65 73 73 69 6f 6e 43 68  ic int sessionCh
5200: 61 6e 67 65 45 71 75 61 6c 28 0a 20 20 53 65 73  angeEqual(.  Ses
5210: 73 69 6f 6e 54 61 62 6c 65 20 2a 70 54 61 62 2c  sionTable *pTab,
5220: 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
5230: 54 61 62 6c 65 20 75 73 65 64 20 66 6f 72 20 50  Table used for P
5240: 4b 20 64 65 66 69 6e 69 74 69 6f 6e 20 2a 2f 0a  K definition */.
5250: 20 20 69 6e 74 20 62 4c 65 66 74 50 6b 4f 6e 6c    int bLeftPkOnl
5260: 79 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20  y,              
5270: 20 20 2f 2a 20 54 72 75 65 20 69 66 20 61 4c 65    /* True if aLe
5280: 66 74 5b 5d 20 63 6f 6e 74 61 69 6e 73 20 50 4b  ft[] contains PK
5290: 20 66 69 65 6c 64 73 20 6f 6e 6c 79 20 2a 2f 0a   fields only */.
52a0: 20 20 75 38 20 2a 61 4c 65 66 74 2c 20 20 20 20    u8 *aLeft,    
52b0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
52c0: 20 20 2f 2a 20 43 68 61 6e 67 65 20 72 65 63 6f    /* Change reco
52d0: 72 64 20 2a 2f 0a 20 20 69 6e 74 20 62 52 69 67  rd */.  int bRig
52e0: 68 74 50 6b 4f 6e 6c 79 2c 20 20 20 20 20 20 20  htPkOnly,       
52f0: 20 20 20 20 20 20 20 20 2f 2a 20 54 72 75 65 20          /* True 
5300: 69 66 20 61 52 69 67 68 74 5b 5d 20 63 6f 6e 74  if aRight[] cont
5310: 61 69 6e 73 20 50 4b 20 66 69 65 6c 64 73 20 6f  ains PK fields o
5320: 6e 6c 79 20 2a 2f 0a 20 20 75 38 20 2a 61 52 69  nly */.  u8 *aRi
5330: 67 68 74 20 20 20 20 20 20 20 20 20 20 20 20 20  ght             
5340: 20 20 20 20 20 20 20 20 20 2f 2a 20 43 68 61 6e           /* Chan
5350: 67 65 20 72 65 63 6f 72 64 20 2a 2f 0a 29 7b 0a  ge record */.){.
5360: 20 20 75 38 20 2a 61 31 20 3d 20 61 4c 65 66 74    u8 *a1 = aLeft
5370: 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  ;               
5380: 20 20 2f 2a 20 43 75 72 73 6f 72 20 74 6f 20 69    /* Cursor to i
5390: 74 65 72 61 74 65 20 74 68 72 6f 75 67 68 20 61  terate through a
53a0: 4c 65 66 74 20 2a 2f 0a 20 20 75 38 20 2a 61 32  Left */.  u8 *a2
53b0: 20 3d 20 61 52 69 67 68 74 3b 20 20 20 20 20 20   = aRight;      
53c0: 20 20 20 20 20 20 20 20 20 20 2f 2a 20 43 75 72            /* Cur
53d0: 73 6f 72 20 74 6f 20 69 74 65 72 61 74 65 20 74  sor to iterate t
53e0: 68 72 6f 75 67 68 20 61 52 69 67 68 74 20 2a 2f  hrough aRight */
53f0: 0a 20 20 69 6e 74 20 69 43 6f 6c 3b 20 20 20 20  .  int iCol;    
5400: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
5410: 20 20 20 2f 2a 20 55 73 65 64 20 74 6f 20 69 74     /* Used to it
5420: 65 72 61 74 65 20 74 68 72 6f 75 67 68 20 74 61  erate through ta
5430: 62 6c 65 20 63 6f 6c 75 6d 6e 73 20 2a 2f 0a 0a  ble columns */..
5440: 20 20 66 6f 72 28 69 43 6f 6c 3d 30 3b 20 69 43    for(iCol=0; iC
5450: 6f 6c 3c 70 54 61 62 2d 3e 6e 43 6f 6c 3b 20 69  ol<pTab->nCol; i
5460: 43 6f 6c 2b 2b 29 7b 0a 20 20 20 20 69 66 28 20  Col++){.    if( 
5470: 70 54 61 62 2d 3e 61 62 50 4b 5b 69 43 6f 6c 5d  pTab->abPK[iCol]
5480: 20 29 7b 0a 20 20 20 20 20 20 69 6e 74 20 6e 31   ){.      int n1
5490: 20 3d 20 73 65 73 73 69 6f 6e 53 65 72 69 61 6c   = sessionSerial
54a0: 4c 65 6e 28 61 31 29 3b 0a 20 20 20 20 20 20 69  Len(a1);.      i
54b0: 6e 74 20 6e 32 20 3d 20 73 65 73 73 69 6f 6e 53  nt n2 = sessionS
54c0: 65 72 69 61 6c 4c 65 6e 28 61 32 29 3b 0a 0a 20  erialLen(a2);.. 
54d0: 20 20 20 20 20 69 66 28 20 70 54 61 62 2d 3e 61       if( pTab->a
54e0: 62 50 4b 5b 69 43 6f 6c 5d 20 26 26 20 28 6e 31  bPK[iCol] && (n1
54f0: 21 3d 6e 32 20 7c 7c 20 6d 65 6d 63 6d 70 28 61  !=n2 || memcmp(a
5500: 31 2c 20 61 32 2c 20 6e 31 29 29 20 29 7b 0a 20  1, a2, n1)) ){. 
5510: 20 20 20 20 20 20 20 72 65 74 75 72 6e 20 30 3b         return 0;
5520: 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 61  .      }.      a
5530: 31 20 2b 3d 20 6e 31 3b 0a 20 20 20 20 20 20 61  1 += n1;.      a
5540: 32 20 2b 3d 20 6e 32 3b 0a 20 20 20 20 7d 65 6c  2 += n2;.    }el
5550: 73 65 7b 0a 20 20 20 20 20 20 69 66 28 20 62 4c  se{.      if( bL
5560: 65 66 74 50 6b 4f 6e 6c 79 3d 3d 30 20 29 20 61  eftPkOnly==0 ) a
5570: 31 20 2b 3d 20 73 65 73 73 69 6f 6e 53 65 72 69  1 += sessionSeri
5580: 61 6c 4c 65 6e 28 61 31 29 3b 0a 20 20 20 20 20  alLen(a1);.     
5590: 20 69 66 28 20 62 52 69 67 68 74 50 6b 4f 6e 6c   if( bRightPkOnl
55a0: 79 3d 3d 30 20 29 20 61 32 20 2b 3d 20 73 65 73  y==0 ) a2 += ses
55b0: 73 69 6f 6e 53 65 72 69 61 6c 4c 65 6e 28 61 32  sionSerialLen(a2
55c0: 29 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a 0a 20 20  );.    }.  }..  
55d0: 72 65 74 75 72 6e 20 31 3b 0a 7d 0a 0a 2f 2a 0a  return 1;.}../*.
55e0: 2a 2a 20 41 72 67 75 6d 65 6e 74 73 20 61 4c 65  ** Arguments aLe
55f0: 66 74 20 61 6e 64 20 61 52 69 67 68 74 20 62 6f  ft and aRight bo
5600: 74 68 20 70 6f 69 6e 74 20 74 6f 20 62 75 66 66  th point to buff
5610: 65 72 73 20 63 6f 6e 74 61 69 6e 69 6e 67 20 63  ers containing c
5620: 68 61 6e 67 65 0a 2a 2a 20 72 65 63 6f 72 64 73  hange.** records
5630: 20 77 69 74 68 20 6e 43 6f 6c 20 63 6f 6c 75 6d   with nCol colum
5640: 6e 73 2e 20 54 68 69 73 20 66 75 6e 63 74 69 6f  ns. This functio
5650: 6e 20 22 6d 65 72 67 65 73 22 20 74 68 65 20 74  n "merges" the t
5660: 77 6f 20 72 65 63 6f 72 64 73 20 69 6e 74 6f 0a  wo records into.
5670: 2a 2a 20 61 20 73 69 6e 67 6c 65 20 72 65 63 6f  ** a single reco
5680: 72 64 73 20 77 68 69 63 68 20 69 73 20 77 72 69  rds which is wri
5690: 74 74 65 6e 20 74 6f 20 74 68 65 20 62 75 66 66  tten to the buff
56a0: 65 72 20 61 74 20 2a 70 61 4f 75 74 2e 20 2a 70  er at *paOut. *p
56b0: 61 4f 75 74 20 69 73 0a 2a 2a 20 74 68 65 6e 20  aOut is.** then 
56c0: 73 65 74 20 74 6f 20 70 6f 69 6e 74 20 74 6f 20  set to point to 
56d0: 6f 6e 65 20 62 79 74 65 20 61 66 74 65 72 20 74  one byte after t
56e0: 68 65 20 6c 61 73 74 20 62 79 74 65 20 77 72 69  he last byte wri
56f0: 74 74 65 6e 20 62 65 66 6f 72 65 20 0a 2a 2a 20  tten before .** 
5700: 72 65 74 75 72 6e 69 6e 67 2e 0a 2a 2a 0a 2a 2a  returning..**.**
5710: 20 54 68 65 20 6d 65 72 67 69 6e 67 20 6f 66 20   The merging of 
5720: 72 65 63 6f 72 64 73 20 69 73 20 64 6f 6e 65 20  records is done 
5730: 61 73 20 66 6f 6c 6c 6f 77 73 3a 20 46 6f 72 20  as follows: For 
5740: 65 61 63 68 20 63 6f 6c 75 6d 6e 2c 20 69 66 20  each column, if 
5750: 74 68 65 20 0a 2a 2a 20 61 52 69 67 68 74 20 72  the .** aRight r
5760: 65 63 6f 72 64 20 63 6f 6e 74 61 69 6e 73 20 61  ecord contains a
5770: 20 76 61 6c 75 65 20 66 6f 72 20 74 68 65 20 63   value for the c
5780: 6f 6c 75 6d 6e 2c 20 63 6f 70 79 20 74 68 65 20  olumn, copy the 
5790: 76 61 6c 75 65 20 66 72 6f 6d 0a 2a 2a 20 74 68  value from.** th
57a0: 65 69 72 2e 20 4f 74 68 65 72 77 69 73 65 2c 20  eir. Otherwise, 
57b0: 69 66 20 61 4c 65 66 74 20 63 6f 6e 74 61 69 6e  if aLeft contain
57c0: 73 20 61 20 76 61 6c 75 65 2c 20 63 6f 70 79 20  s a value, copy 
57d0: 69 74 2e 20 49 66 20 6e 65 69 74 68 65 72 0a 2a  it. If neither.*
57e0: 2a 20 72 65 63 6f 72 64 20 63 6f 6e 74 61 69 6e  * record contain
57f0: 73 20 61 20 76 61 6c 75 65 20 66 6f 72 20 61 20  s a value for a 
5800: 67 69 76 65 6e 20 63 6f 6c 75 6d 6e 2c 20 74 68  given column, th
5810: 65 6e 20 6e 65 69 74 68 65 72 20 64 6f 65 73 20  en neither does 
5820: 74 68 65 0a 2a 2a 20 6f 75 74 70 75 74 20 72 65  the.** output re
5830: 63 6f 72 64 2e 0a 2a 2f 0a 73 74 61 74 69 63 20  cord..*/.static 
5840: 76 6f 69 64 20 73 65 73 73 69 6f 6e 4d 65 72 67  void sessionMerg
5850: 65 52 65 63 6f 72 64 28 0a 20 20 75 38 20 2a 2a  eRecord(.  u8 **
5860: 70 61 4f 75 74 2c 20 0a 20 20 69 6e 74 20 6e 43  paOut, .  int nC
5870: 6f 6c 2c 0a 20 20 75 38 20 2a 61 4c 65 66 74 2c  ol,.  u8 *aLeft,
5880: 0a 20 20 75 38 20 2a 61 52 69 67 68 74 0a 29 7b  .  u8 *aRight.){
5890: 0a 20 20 75 38 20 2a 61 31 20 3d 20 61 4c 65 66  .  u8 *a1 = aLef
58a0: 74 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 20  t;              
58b0: 20 20 20 2f 2a 20 43 75 72 73 6f 72 20 75 73 65     /* Cursor use
58c0: 64 20 74 6f 20 69 74 65 72 61 74 65 20 74 68 72  d to iterate thr
58d0: 6f 75 67 68 20 61 4c 65 66 74 20 2a 2f 0a 20 20  ough aLeft */.  
58e0: 75 38 20 2a 61 32 20 3d 20 61 52 69 67 68 74 3b  u8 *a2 = aRight;
58f0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
5900: 2f 2a 20 43 75 72 73 6f 72 20 75 73 65 64 20 74  /* Cursor used t
5910: 6f 20 69 74 65 72 61 74 65 20 74 68 72 6f 75 67  o iterate throug
5920: 68 20 61 52 69 67 68 74 20 2a 2f 0a 20 20 75 38  h aRight */.  u8
5930: 20 2a 61 4f 75 74 20 3d 20 2a 70 61 4f 75 74 3b   *aOut = *paOut;
5940: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
5950: 20 4f 75 74 70 75 74 20 63 75 72 73 6f 72 20 2a   Output cursor *
5960: 2f 0a 20 20 69 6e 74 20 69 43 6f 6c 3b 20 20 20  /.  int iCol;   
5970: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
5980: 20 20 20 20 2f 2a 20 55 73 65 64 20 74 6f 20 69      /* Used to i
5990: 74 65 72 61 74 65 20 66 72 6f 6d 20 30 20 74 6f  terate from 0 to
59a0: 20 6e 43 6f 6c 20 2a 2f 0a 0a 20 20 66 6f 72 28   nCol */..  for(
59b0: 69 43 6f 6c 3d 30 3b 20 69 43 6f 6c 3c 6e 43 6f  iCol=0; iCol<nCo
59c0: 6c 3b 20 69 43 6f 6c 2b 2b 29 7b 0a 20 20 20 20  l; iCol++){.    
59d0: 69 6e 74 20 6e 31 20 3d 20 73 65 73 73 69 6f 6e  int n1 = session
59e0: 53 65 72 69 61 6c 4c 65 6e 28 61 31 29 3b 0a 20  SerialLen(a1);. 
59f0: 20 20 20 69 6e 74 20 6e 32 20 3d 20 73 65 73 73     int n2 = sess
5a00: 69 6f 6e 53 65 72 69 61 6c 4c 65 6e 28 61 32 29  ionSerialLen(a2)
5a10: 3b 0a 20 20 20 20 69 66 28 20 2a 61 32 20 29 7b  ;.    if( *a2 ){
5a20: 0a 20 20 20 20 20 20 6d 65 6d 63 70 79 28 61 4f  .      memcpy(aO
5a30: 75 74 2c 20 61 32 2c 20 6e 32 29 3b 0a 20 20 20  ut, a2, n2);.   
5a40: 20 20 20 61 4f 75 74 20 2b 3d 20 6e 32 3b 0a 20     aOut += n2;. 
5a50: 20 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20     }else{.      
5a60: 6d 65 6d 63 70 79 28 61 4f 75 74 2c 20 61 31 2c  memcpy(aOut, a1,
5a70: 20 6e 31 29 3b 0a 20 20 20 20 20 20 61 4f 75 74   n1);.      aOut
5a80: 20 2b 3d 20 6e 31 3b 0a 20 20 20 20 7d 0a 20 20   += n1;.    }.  
5a90: 20 20 61 31 20 2b 3d 20 6e 31 3b 0a 20 20 20 20    a1 += n1;.    
5aa0: 61 32 20 2b 3d 20 6e 32 3b 0a 20 20 7d 0a 0a 20  a2 += n2;.  }.. 
5ab0: 20 2a 70 61 4f 75 74 20 3d 20 61 4f 75 74 3b 0a   *paOut = aOut;.
5ac0: 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68 69 73 20 69 73  }../*.** This is
5ad0: 20 61 20 68 65 6c 70 65 72 20 66 75 6e 63 74 69   a helper functi
5ae0: 6f 6e 20 75 73 65 64 20 62 79 20 73 65 73 73 69  on used by sessi
5af0: 6f 6e 4d 65 72 67 65 55 70 64 61 74 65 28 29 2e  onMergeUpdate().
5b00: 0a 2a 2a 0a 2a 2a 20 57 68 65 6e 20 74 68 69 73  .**.** When this
5b10: 20 66 75 6e 63 74 69 6f 6e 20 69 73 20 63 61 6c   function is cal
5b20: 6c 65 64 2c 20 62 6f 74 68 20 2a 70 61 4f 6e 65  led, both *paOne
5b30: 20 61 6e 64 20 2a 70 61 54 77 6f 20 70 6f 69 6e   and *paTwo poin
5b40: 74 20 74 6f 20 61 20 76 61 6c 75 65 20 0a 2a 2a  t to a value .**
5b50: 20 77 69 74 68 69 6e 20 61 20 63 68 61 6e 67 65   within a change
5b60: 20 72 65 63 6f 72 64 2e 20 42 65 66 6f 72 65 20   record. Before 
5b70: 69 74 20 72 65 74 75 72 6e 73 2c 20 62 6f 74 68  it returns, both
5b80: 20 68 61 76 65 20 62 65 65 6e 20 61 64 76 61 6e   have been advan
5b90: 63 65 64 20 73 6f 20 0a 2a 2a 20 61 73 20 74 6f  ced so .** as to
5ba0: 20 70 6f 69 6e 74 20 74 6f 20 74 68 65 20 6e 65   point to the ne
5bb0: 78 74 20 76 61 6c 75 65 20 69 6e 20 74 68 65 20  xt value in the 
5bc0: 72 65 63 6f 72 64 2e 0a 2a 2a 0a 2a 2a 20 49 66  record..**.** If
5bd0: 2c 20 77 68 65 6e 20 74 68 69 73 20 66 75 6e 63  , when this func
5be0: 74 69 6f 6e 20 69 73 20 63 61 6c 6c 65 64 2c 20  tion is called, 
5bf0: 2a 70 61 54 77 6f 20 70 6f 69 6e 74 73 20 74 6f  *paTwo points to
5c00: 20 61 20 76 61 6c 69 64 20 76 61 6c 75 65 20 28   a valid value (
5c10: 69 2e 65 2e 0a 2a 2a 20 2a 70 61 54 77 6f 5b 30  i.e..** *paTwo[0
5c20: 5d 20 69 73 20 6e 6f 74 20 30 78 30 30 20 2d 20  ] is not 0x00 - 
5c30: 74 68 65 20 22 6e 6f 20 76 61 6c 75 65 22 20 70  the "no value" p
5c40: 6c 61 63 65 68 6f 6c 64 65 72 29 2c 20 61 20 63  laceholder), a c
5c50: 6f 70 79 20 6f 66 20 74 68 65 20 2a 70 61 54 77  opy of the *paTw
5c60: 6f 0a 2a 2a 20 70 6f 69 6e 74 65 72 20 69 73 20  o.** pointer is 
5c70: 72 65 74 75 72 6e 65 64 20 61 6e 64 20 2a 70 6e  returned and *pn
5c80: 56 61 6c 20 69 73 20 73 65 74 20 74 6f 20 74 68  Val is set to th
5c90: 65 20 6e 75 6d 62 65 72 20 6f 66 20 62 79 74 65  e number of byte
5ca0: 73 20 69 6e 20 74 68 65 20 0a 2a 2a 20 73 65 72  s in the .** ser
5cb0: 69 61 6c 69 7a 65 64 20 76 61 6c 75 65 2e 20 4f  ialized value. O
5cc0: 74 68 65 72 77 69 73 65 2c 20 61 20 63 6f 70 79  therwise, a copy
5cd0: 20 6f 66 20 2a 70 61 4f 6e 65 20 69 73 20 72 65   of *paOne is re
5ce0: 74 75 72 6e 65 64 20 61 6e 64 20 2a 70 6e 56 61  turned and *pnVa
5cf0: 6c 0a 2a 2a 20 73 65 74 20 74 6f 20 74 68 65 20  l.** set to the 
5d00: 6e 75 6d 62 65 72 20 6f 66 20 62 79 74 65 73 20  number of bytes 
5d10: 69 6e 20 74 68 65 20 76 61 6c 75 65 20 61 74 20  in the value at 
5d20: 2a 70 61 4f 6e 65 2e 20 49 66 20 2a 70 61 4f 6e  *paOne. If *paOn
5d30: 65 20 70 6f 69 6e 74 73 0a 2a 2a 20 74 6f 20 74  e points.** to t
5d40: 68 65 20 22 6e 6f 20 76 61 6c 75 65 22 20 70 6c  he "no value" pl
5d50: 61 63 65 68 6f 6c 64 65 72 2c 20 2a 70 6e 56 61  aceholder, *pnVa
5d60: 6c 20 69 73 20 73 65 74 20 74 6f 20 31 2e 20 49  l is set to 1. I
5d70: 6e 20 6f 74 68 65 72 20 77 6f 72 64 73 3a 0a 2a  n other words:.*
5d80: 2a 0a 2a 2a 20 20 20 69 66 28 20 2a 70 61 54 77  *.**   if( *paTw
5d90: 6f 20 69 73 20 76 61 6c 69 64 20 29 20 72 65 74  o is valid ) ret
5da0: 75 72 6e 20 2a 70 61 54 77 6f 3b 0a 2a 2a 20 20  urn *paTwo;.**  
5db0: 20 72 65 74 75 72 6e 20 2a 70 61 4f 6e 65 3b 0a   return *paOne;.
5dc0: 2a 2a 0a 2a 2f 0a 73 74 61 74 69 63 20 75 38 20  **.*/.static u8 
5dd0: 2a 73 65 73 73 69 6f 6e 4d 65 72 67 65 56 61 6c  *sessionMergeVal
5de0: 75 65 28 0a 20 20 75 38 20 2a 2a 70 61 4f 6e 65  ue(.  u8 **paOne
5df0: 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  ,               
5e00: 20 20 20 20 20 20 2f 2a 20 49 4e 2f 4f 55 54 3a        /* IN/OUT:
5e10: 20 4c 65 66 74 2d 68 61 6e 64 20 62 75 66 66 65   Left-hand buffe
5e20: 72 20 70 6f 69 6e 74 65 72 20 2a 2f 0a 20 20 75  r pointer */.  u
5e30: 38 20 2a 2a 70 61 54 77 6f 2c 20 20 20 20 20 20  8 **paTwo,      
5e40: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
5e50: 2a 20 49 4e 2f 4f 55 54 3a 20 52 69 67 68 74 2d  * IN/OUT: Right-
5e60: 68 61 6e 64 20 62 75 66 66 65 72 20 70 6f 69 6e  hand buffer poin
5e70: 74 65 72 20 2a 2f 0a 20 20 69 6e 74 20 2a 70 6e  ter */.  int *pn
5e80: 56 61 6c 20 20 20 20 20 20 20 20 20 20 20 20 20  Val             
5e90: 20 20 20 20 20 20 20 20 20 2f 2a 20 4f 55 54 3a           /* OUT:
5ea0: 20 42 79 74 65 73 20 69 6e 20 72 65 74 75 72 6e   Bytes in return
5eb0: 65 64 20 76 61 6c 75 65 20 2a 2f 0a 29 7b 0a 20  ed value */.){. 
5ec0: 20 75 38 20 2a 61 31 20 3d 20 2a 70 61 4f 6e 65   u8 *a1 = *paOne
5ed0: 3b 0a 20 20 75 38 20 2a 61 32 20 3d 20 2a 70 61  ;.  u8 *a2 = *pa
5ee0: 54 77 6f 3b 0a 20 20 75 38 20 2a 70 52 65 74 20  Two;.  u8 *pRet 
5ef0: 3d 20 30 3b 0a 20 20 69 6e 74 20 6e 31 3b 0a 0a  = 0;.  int n1;..
5f00: 20 20 61 73 73 65 72 74 28 20 61 31 20 29 3b 0a    assert( a1 );.
5f10: 20 20 69 66 28 20 61 32 20 29 7b 0a 20 20 20 20    if( a2 ){.    
5f20: 69 6e 74 20 6e 32 20 3d 20 73 65 73 73 69 6f 6e  int n2 = session
5f30: 53 65 72 69 61 6c 4c 65 6e 28 61 32 29 3b 0a 20  SerialLen(a2);. 
5f40: 20 20 20 69 66 28 20 2a 61 32 20 29 7b 0a 20 20     if( *a2 ){.  
5f50: 20 20 20 20 2a 70 6e 56 61 6c 20 3d 20 6e 32 3b      *pnVal = n2;
5f60: 0a 20 20 20 20 20 20 70 52 65 74 20 3d 20 61 32  .      pRet = a2
5f70: 3b 0a 20 20 20 20 7d 0a 20 20 20 20 2a 70 61 54  ;.    }.    *paT
5f80: 77 6f 20 3d 20 26 61 32 5b 6e 32 5d 3b 0a 20 20  wo = &a2[n2];.  
5f90: 7d 0a 0a 20 20 6e 31 20 3d 20 73 65 73 73 69 6f  }..  n1 = sessio
5fa0: 6e 53 65 72 69 61 6c 4c 65 6e 28 61 31 29 3b 0a  nSerialLen(a1);.
5fb0: 20 20 69 66 28 20 70 52 65 74 3d 3d 30 20 29 7b    if( pRet==0 ){
5fc0: 0a 20 20 20 20 2a 70 6e 56 61 6c 20 3d 20 6e 31  .    *pnVal = n1
5fd0: 3b 0a 20 20 20 20 70 52 65 74 20 3d 20 61 31 3b  ;.    pRet = a1;
5fe0: 0a 20 20 7d 0a 20 20 2a 70 61 4f 6e 65 20 3d 20  .  }.  *paOne = 
5ff0: 26 61 31 5b 6e 31 5d 3b 0a 0a 20 20 72 65 74 75  &a1[n1];..  retu
6000: 72 6e 20 70 52 65 74 3b 0a 7d 0a 0a 2f 2a 0a 2a  rn pRet;.}../*.*
6010: 2a 20 54 68 69 73 20 66 75 6e 63 74 69 6f 6e 20  * This function 
6020: 69 73 20 75 73 65 64 20 62 79 20 63 68 61 6e 67  is used by chang
6030: 65 73 65 74 5f 63 6f 6e 63 61 74 28 29 20 74 6f  eset_concat() to
6040: 20 6d 65 72 67 65 20 74 77 6f 20 55 50 44 41 54   merge two UPDAT
6050: 45 20 63 68 61 6e 67 65 73 0a 2a 2a 20 6f 6e 20  E changes.** on 
6060: 74 68 65 20 73 61 6d 65 20 72 6f 77 2e 0a 2a 2f  the same row..*/
6070: 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73 73  .static int sess
6080: 69 6f 6e 4d 65 72 67 65 55 70 64 61 74 65 28 0a  ionMergeUpdate(.
6090: 20 20 75 38 20 2a 2a 70 61 4f 75 74 2c 20 20 20    u8 **paOut,   
60a0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
60b0: 20 20 2f 2a 20 49 4e 2f 4f 55 54 3a 20 50 6f 69    /* IN/OUT: Poi
60c0: 6e 74 65 72 20 74 6f 20 6f 75 74 70 75 74 20 62  nter to output b
60d0: 75 66 66 65 72 20 2a 2f 0a 20 20 53 65 73 73 69  uffer */.  Sessi
60e0: 6f 6e 54 61 62 6c 65 20 2a 70 54 61 62 2c 20 20  onTable *pTab,  
60f0: 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 54 61             /* Ta
6100: 62 6c 65 20 63 68 61 6e 67 65 20 70 65 72 74 61  ble change perta
6110: 69 6e 73 20 74 6f 20 2a 2f 0a 20 20 69 6e 74 20  ins to */.  int 
6120: 62 50 61 74 63 68 73 65 74 2c 20 20 20 20 20 20  bPatchset,      
6130: 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 54              /* T
6140: 72 75 65 20 69 66 20 72 65 63 6f 72 64 73 20 61  rue if records a
6150: 72 65 20 70 61 74 63 68 73 65 74 20 72 65 63 6f  re patchset reco
6160: 72 64 73 20 2a 2f 0a 20 20 75 38 20 2a 61 4f 6c  rds */.  u8 *aOl
6170: 64 52 65 63 6f 72 64 31 2c 20 20 20 20 20 20 20  dRecord1,       
6180: 20 20 20 20 20 20 20 20 20 2f 2a 20 6f 6c 64 2e           /* old.
6190: 2a 20 72 65 63 6f 72 64 20 66 6f 72 20 66 69 72  * record for fir
61a0: 73 74 20 63 68 61 6e 67 65 20 2a 2f 0a 20 20 75  st change */.  u
61b0: 38 20 2a 61 4f 6c 64 52 65 63 6f 72 64 32 2c 20  8 *aOldRecord2, 
61c0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
61d0: 2a 20 6f 6c 64 2e 2a 20 72 65 63 6f 72 64 20 66  * old.* record f
61e0: 6f 72 20 73 65 63 6f 6e 64 20 63 68 61 6e 67 65  or second change
61f0: 20 2a 2f 0a 20 20 75 38 20 2a 61 4e 65 77 52 65   */.  u8 *aNewRe
6200: 63 6f 72 64 31 2c 20 20 20 20 20 20 20 20 20 20  cord1,          
6210: 20 20 20 20 20 20 2f 2a 20 6e 65 77 2e 2a 20 72        /* new.* r
6220: 65 63 6f 72 64 20 66 6f 72 20 66 69 72 73 74 20  ecord for first 
6230: 63 68 61 6e 67 65 20 2a 2f 0a 20 20 75 38 20 2a  change */.  u8 *
6240: 61 4e 65 77 52 65 63 6f 72 64 32 20 20 20 20 20  aNewRecord2     
6250: 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 6e              /* n
6260: 65 77 2e 2a 20 72 65 63 6f 72 64 20 66 6f 72 20  ew.* record for 
6270: 73 65 63 6f 6e 64 20 63 68 61 6e 67 65 20 2a 2f  second change */
6280: 0a 29 7b 0a 20 20 75 38 20 2a 61 4f 6c 64 31 20  .){.  u8 *aOld1 
6290: 3d 20 61 4f 6c 64 52 65 63 6f 72 64 31 3b 0a 20  = aOldRecord1;. 
62a0: 20 75 38 20 2a 61 4f 6c 64 32 20 3d 20 61 4f 6c   u8 *aOld2 = aOl
62b0: 64 52 65 63 6f 72 64 32 3b 0a 20 20 75 38 20 2a  dRecord2;.  u8 *
62c0: 61 4e 65 77 31 20 3d 20 61 4e 65 77 52 65 63 6f  aNew1 = aNewReco
62d0: 72 64 31 3b 0a 20 20 75 38 20 2a 61 4e 65 77 32  rd1;.  u8 *aNew2
62e0: 20 3d 20 61 4e 65 77 52 65 63 6f 72 64 32 3b 0a   = aNewRecord2;.
62f0: 0a 20 20 75 38 20 2a 61 4f 75 74 20 3d 20 2a 70  .  u8 *aOut = *p
6300: 61 4f 75 74 3b 0a 20 20 69 6e 74 20 69 3b 0a 0a  aOut;.  int i;..
6310: 20 20 69 66 28 20 62 50 61 74 63 68 73 65 74 3d    if( bPatchset=
6320: 3d 30 20 29 7b 0a 20 20 20 20 69 6e 74 20 62 52  =0 ){.    int bR
6330: 65 71 75 69 72 65 64 20 3d 20 30 3b 0a 0a 20 20  equired = 0;..  
6340: 20 20 61 73 73 65 72 74 28 20 61 4f 6c 64 52 65    assert( aOldRe
6350: 63 6f 72 64 31 20 26 26 20 61 4e 65 77 52 65 63  cord1 && aNewRec
6360: 6f 72 64 31 20 29 3b 0a 0a 20 20 20 20 2f 2a 20  ord1 );..    /* 
6370: 57 72 69 74 65 20 74 68 65 20 6f 6c 64 2e 2a 20  Write the old.* 
6380: 76 65 63 74 6f 72 20 66 69 72 73 74 2e 20 2a 2f  vector first. */
6390: 0a 20 20 20 20 66 6f 72 28 69 3d 30 3b 20 69 3c  .    for(i=0; i<
63a0: 70 54 61 62 2d 3e 6e 43 6f 6c 3b 20 69 2b 2b 29  pTab->nCol; i++)
63b0: 7b 0a 20 20 20 20 20 20 69 6e 74 20 6e 4f 6c 64  {.      int nOld
63c0: 3b 0a 20 20 20 20 20 20 75 38 20 2a 61 4f 6c 64  ;.      u8 *aOld
63d0: 3b 0a 20 20 20 20 20 20 69 6e 74 20 6e 4e 65 77  ;.      int nNew
63e0: 3b 0a 20 20 20 20 20 20 75 38 20 2a 61 4e 65 77  ;.      u8 *aNew
63f0: 3b 0a 0a 20 20 20 20 20 20 61 4f 6c 64 20 3d 20  ;..      aOld = 
6400: 73 65 73 73 69 6f 6e 4d 65 72 67 65 56 61 6c 75  sessionMergeValu
6410: 65 28 26 61 4f 6c 64 31 2c 20 26 61 4f 6c 64 32  e(&aOld1, &aOld2
6420: 2c 20 26 6e 4f 6c 64 29 3b 0a 20 20 20 20 20 20  , &nOld);.      
6430: 61 4e 65 77 20 3d 20 73 65 73 73 69 6f 6e 4d 65  aNew = sessionMe
6440: 72 67 65 56 61 6c 75 65 28 26 61 4e 65 77 31 2c  rgeValue(&aNew1,
6450: 20 26 61 4e 65 77 32 2c 20 26 6e 4e 65 77 29 3b   &aNew2, &nNew);
6460: 0a 20 20 20 20 20 20 69 66 28 20 70 54 61 62 2d  .      if( pTab-
6470: 3e 61 62 50 4b 5b 69 5d 20 7c 7c 20 6e 4f 6c 64  >abPK[i] || nOld
6480: 21 3d 6e 4e 65 77 20 7c 7c 20 6d 65 6d 63 6d 70  !=nNew || memcmp
6490: 28 61 4f 6c 64 2c 20 61 4e 65 77 2c 20 6e 4e 65  (aOld, aNew, nNe
64a0: 77 29 20 29 7b 0a 20 20 20 20 20 20 20 20 69 66  w) ){.        if
64b0: 28 20 70 54 61 62 2d 3e 61 62 50 4b 5b 69 5d 3d  ( pTab->abPK[i]=
64c0: 3d 30 20 29 20 62 52 65 71 75 69 72 65 64 20 3d  =0 ) bRequired =
64d0: 20 31 3b 0a 20 20 20 20 20 20 20 20 6d 65 6d 63   1;.        memc
64e0: 70 79 28 61 4f 75 74 2c 20 61 4f 6c 64 2c 20 6e  py(aOut, aOld, n
64f0: 4f 6c 64 29 3b 0a 20 20 20 20 20 20 20 20 61 4f  Old);.        aO
6500: 75 74 20 2b 3d 20 6e 4f 6c 64 3b 0a 20 20 20 20  ut += nOld;.    
6510: 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 20    }else{.       
6520: 20 2a 28 61 4f 75 74 2b 2b 29 20 3d 20 27 5c 30   *(aOut++) = '\0
6530: 27 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 7d  ';.      }.    }
6540: 0a 0a 20 20 20 20 69 66 28 20 21 62 52 65 71 75  ..    if( !bRequ
6550: 69 72 65 64 20 29 20 72 65 74 75 72 6e 20 30 3b  ired ) return 0;
6560: 0a 20 20 7d 0a 0a 20 20 2f 2a 20 57 72 69 74 65  .  }..  /* Write
6570: 20 74 68 65 20 6e 65 77 2e 2a 20 76 65 63 74 6f   the new.* vecto
6580: 72 20 2a 2f 0a 20 20 61 4f 6c 64 31 20 3d 20 61  r */.  aOld1 = a
6590: 4f 6c 64 52 65 63 6f 72 64 31 3b 0a 20 20 61 4f  OldRecord1;.  aO
65a0: 6c 64 32 20 3d 20 61 4f 6c 64 52 65 63 6f 72 64  ld2 = aOldRecord
65b0: 32 3b 0a 20 20 61 4e 65 77 31 20 3d 20 61 4e 65  2;.  aNew1 = aNe
65c0: 77 52 65 63 6f 72 64 31 3b 0a 20 20 61 4e 65 77  wRecord1;.  aNew
65d0: 32 20 3d 20 61 4e 65 77 52 65 63 6f 72 64 32 3b  2 = aNewRecord2;
65e0: 0a 20 20 66 6f 72 28 69 3d 30 3b 20 69 3c 70 54  .  for(i=0; i<pT
65f0: 61 62 2d 3e 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a  ab->nCol; i++){.
6600: 20 20 20 20 69 6e 74 20 6e 4f 6c 64 3b 0a 20 20      int nOld;.  
6610: 20 20 75 38 20 2a 61 4f 6c 64 3b 0a 20 20 20 20    u8 *aOld;.    
6620: 69 6e 74 20 6e 4e 65 77 3b 0a 20 20 20 20 75 38  int nNew;.    u8
6630: 20 2a 61 4e 65 77 3b 0a 0a 20 20 20 20 61 4f 6c   *aNew;..    aOl
6640: 64 20 3d 20 73 65 73 73 69 6f 6e 4d 65 72 67 65  d = sessionMerge
6650: 56 61 6c 75 65 28 26 61 4f 6c 64 31 2c 20 26 61  Value(&aOld1, &a
6660: 4f 6c 64 32 2c 20 26 6e 4f 6c 64 29 3b 0a 20 20  Old2, &nOld);.  
6670: 20 20 61 4e 65 77 20 3d 20 73 65 73 73 69 6f 6e    aNew = session
6680: 4d 65 72 67 65 56 61 6c 75 65 28 26 61 4e 65 77  MergeValue(&aNew
6690: 31 2c 20 26 61 4e 65 77 32 2c 20 26 6e 4e 65 77  1, &aNew2, &nNew
66a0: 29 3b 0a 20 20 20 20 69 66 28 20 62 50 61 74 63  );.    if( bPatc
66b0: 68 73 65 74 3d 3d 30 20 0a 20 20 20 20 20 26 26  hset==0 .     &&
66c0: 20 28 70 54 61 62 2d 3e 61 62 50 4b 5b 69 5d 20   (pTab->abPK[i] 
66d0: 7c 7c 20 28 6e 4f 6c 64 3d 3d 6e 4e 65 77 20 26  || (nOld==nNew &
66e0: 26 20 30 3d 3d 6d 65 6d 63 6d 70 28 61 4f 6c 64  & 0==memcmp(aOld
66f0: 2c 20 61 4e 65 77 2c 20 6e 4e 65 77 29 29 29 20  , aNew, nNew))) 
6700: 0a 20 20 20 20 29 7b 0a 20 20 20 20 20 20 2a 28  .    ){.      *(
6710: 61 4f 75 74 2b 2b 29 20 3d 20 27 5c 30 27 3b 0a  aOut++) = '\0';.
6720: 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20      }else{.     
6730: 20 6d 65 6d 63 70 79 28 61 4f 75 74 2c 20 61 4e   memcpy(aOut, aN
6740: 65 77 2c 20 6e 4e 65 77 29 3b 0a 20 20 20 20 20  ew, nNew);.     
6750: 20 61 4f 75 74 20 2b 3d 20 6e 4e 65 77 3b 0a 20   aOut += nNew;. 
6760: 20 20 20 7d 0a 20 20 7d 0a 0a 20 20 2a 70 61 4f     }.  }..  *paO
6770: 75 74 20 3d 20 61 4f 75 74 3b 0a 20 20 72 65 74  ut = aOut;.  ret
6780: 75 72 6e 20 31 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20  urn 1;.}../*.** 
6790: 54 68 69 73 20 66 75 6e 63 74 69 6f 6e 20 69 73  This function is
67a0: 20 6f 6e 6c 79 20 63 61 6c 6c 65 64 20 66 72 6f   only called fro
67b0: 6d 20 77 69 74 68 69 6e 20 61 20 70 72 65 2d 75  m within a pre-u
67c0: 70 64 61 74 65 2d 68 6f 6f 6b 20 63 61 6c 6c 62  pdate-hook callb
67d0: 61 63 6b 2e 0a 2a 2a 20 49 74 20 64 65 74 65 72  ack..** It deter
67e0: 6d 69 6e 65 73 20 69 66 20 74 68 65 20 63 75 72  mines if the cur
67f0: 72 65 6e 74 20 70 72 65 2d 75 70 64 61 74 65 2d  rent pre-update-
6800: 68 6f 6f 6b 20 63 68 61 6e 67 65 20 61 66 66 65  hook change affe
6810: 63 74 73 20 74 68 65 20 73 61 6d 65 20 72 6f 77  cts the same row
6820: 0a 2a 2a 20 61 73 20 74 68 65 20 63 68 61 6e 67  .** as the chang
6830: 65 20 73 74 6f 72 65 64 20 69 6e 20 61 72 67 75  e stored in argu
6840: 6d 65 6e 74 20 70 43 68 61 6e 67 65 2e 20 49 66  ment pChange. If
6850: 20 73 6f 2c 20 69 74 20 72 65 74 75 72 6e 73 20   so, it returns 
6860: 74 72 75 65 2e 20 4f 74 68 65 72 77 69 73 65 0a  true. Otherwise.
6870: 2a 2a 20 69 66 20 74 68 65 20 70 72 65 2d 75 70  ** if the pre-up
6880: 64 61 74 65 2d 68 6f 6f 6b 20 64 6f 65 73 20 6e  date-hook does n
6890: 6f 74 20 61 66 66 65 63 74 20 74 68 65 20 73 61  ot affect the sa
68a0: 6d 65 20 72 6f 77 20 61 73 20 70 43 68 61 6e 67  me row as pChang
68b0: 65 2c 20 69 74 20 72 65 74 75 72 6e 73 0a 2a 2a  e, it returns.**
68c0: 20 66 61 6c 73 65 2e 0a 2a 2f 0a 73 74 61 74 69   false..*/.stati
68d0: 63 20 69 6e 74 20 73 65 73 73 69 6f 6e 50 72 65  c int sessionPre
68e0: 75 70 64 61 74 65 45 71 75 61 6c 28 0a 20 20 73  updateEqual(.  s
68f0: 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a  qlite3_session *
6900: 70 53 65 73 73 69 6f 6e 2c 20 20 20 20 20 20 2f  pSession,      /
6910: 2a 20 53 65 73 73 69 6f 6e 20 6f 62 6a 65 63 74  * Session object
6920: 20 74 68 61 74 20 6f 77 6e 73 20 53 65 73 73 69   that owns Sessi
6930: 6f 6e 54 61 62 6c 65 20 2a 2f 0a 20 20 53 65 73  onTable */.  Ses
6940: 73 69 6f 6e 54 61 62 6c 65 20 2a 70 54 61 62 2c  sionTable *pTab,
6950: 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
6960: 54 61 62 6c 65 20 61 73 73 6f 63 69 61 74 65 64  Table associated
6970: 20 77 69 74 68 20 63 68 61 6e 67 65 20 2a 2f 0a   with change */.
6980: 20 20 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 20    SessionChange 
6990: 2a 70 43 68 61 6e 67 65 2c 20 20 20 20 20 20 20  *pChange,       
69a0: 20 20 2f 2a 20 43 68 61 6e 67 65 20 74 6f 20 63    /* Change to c
69b0: 6f 6d 70 61 72 65 20 74 6f 20 2a 2f 0a 20 20 69  ompare to */.  i
69c0: 6e 74 20 6f 70 20 20 20 20 20 20 20 20 20 20 20  nt op           
69d0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
69e0: 2a 20 43 75 72 72 65 6e 74 20 70 72 65 2d 75 70  * Current pre-up
69f0: 64 61 74 65 20 6f 70 65 72 61 74 69 6f 6e 20 2a  date operation *
6a00: 2f 0a 29 7b 0a 20 20 69 6e 74 20 69 43 6f 6c 3b  /.){.  int iCol;
6a10: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
6a20: 20 20 20 20 20 20 20 2f 2a 20 55 73 65 64 20 74         /* Used t
6a30: 6f 20 69 74 65 72 61 74 65 20 74 68 72 6f 75 67  o iterate throug
6a40: 68 20 63 6f 6c 75 6d 6e 73 20 2a 2f 0a 20 20 75  h columns */.  u
6a50: 38 20 2a 61 20 3d 20 70 43 68 61 6e 67 65 2d 3e  8 *a = pChange->
6a60: 61 52 65 63 6f 72 64 3b 20 20 20 20 20 20 20 2f  aRecord;       /
6a70: 2a 20 43 75 72 73 6f 72 20 75 73 65 64 20 74 6f  * Cursor used to
6a80: 20 73 63 61 6e 20 63 68 61 6e 67 65 20 72 65 63   scan change rec
6a90: 6f 72 64 20 2a 2f 0a 0a 20 20 61 73 73 65 72 74  ord */..  assert
6aa0: 28 20 6f 70 3d 3d 53 51 4c 49 54 45 5f 49 4e 53  ( op==SQLITE_INS
6ab0: 45 52 54 20 7c 7c 20 6f 70 3d 3d 53 51 4c 49 54  ERT || op==SQLIT
6ac0: 45 5f 55 50 44 41 54 45 20 7c 7c 20 6f 70 3d 3d  E_UPDATE || op==
6ad0: 53 51 4c 49 54 45 5f 44 45 4c 45 54 45 20 29 3b  SQLITE_DELETE );
6ae0: 0a 20 20 66 6f 72 28 69 43 6f 6c 3d 30 3b 20 69  .  for(iCol=0; i
6af0: 43 6f 6c 3c 70 54 61 62 2d 3e 6e 43 6f 6c 3b 20  Col<pTab->nCol; 
6b00: 69 43 6f 6c 2b 2b 29 7b 0a 20 20 20 20 69 66 28  iCol++){.    if(
6b10: 20 21 70 54 61 62 2d 3e 61 62 50 4b 5b 69 43 6f   !pTab->abPK[iCo
6b20: 6c 5d 20 29 7b 0a 20 20 20 20 20 20 61 20 2b 3d  l] ){.      a +=
6b30: 20 73 65 73 73 69 6f 6e 53 65 72 69 61 6c 4c 65   sessionSerialLe
6b40: 6e 28 61 29 3b 0a 20 20 20 20 7d 65 6c 73 65 7b  n(a);.    }else{
6b50: 0a 20 20 20 20 20 20 73 71 6c 69 74 65 33 5f 76  .      sqlite3_v
6b60: 61 6c 75 65 20 2a 70 56 61 6c 3b 20 20 20 20 20  alue *pVal;     
6b70: 20 20 20 2f 2a 20 56 61 6c 75 65 20 72 65 74 75     /* Value retu
6b80: 72 6e 65 64 20 62 79 20 70 72 65 75 70 64 61 74  rned by preupdat
6b90: 65 5f 6e 65 77 2f 6f 6c 64 20 2a 2f 0a 20 20 20  e_new/old */.   
6ba0: 20 20 20 69 6e 74 20 72 63 3b 20 20 20 20 20 20     int rc;      
6bb0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
6bc0: 2a 20 45 72 72 6f 72 20 63 6f 64 65 20 66 72 6f  * Error code fro
6bd0: 6d 20 70 72 65 75 70 64 61 74 65 5f 6e 65 77 2f  m preupdate_new/
6be0: 6f 6c 64 20 2a 2f 0a 20 20 20 20 20 20 69 6e 74  old */.      int
6bf0: 20 65 54 79 70 65 20 3d 20 2a 61 2b 2b 3b 20 20   eType = *a++;  
6c00: 20 20 20 20 20 20 20 20 20 2f 2a 20 54 79 70 65           /* Type
6c10: 20 6f 66 20 76 61 6c 75 65 20 66 72 6f 6d 20 63   of value from c
6c20: 68 61 6e 67 65 20 72 65 63 6f 72 64 20 2a 2f 0a  hange record */.
6c30: 0a 20 20 20 20 20 20 2f 2a 20 54 68 65 20 66 6f  .      /* The fo
6c40: 6c 6c 6f 77 69 6e 67 20 63 61 6c 6c 73 20 74 6f  llowing calls to
6c50: 20 70 72 65 75 70 64 61 74 65 5f 6e 65 77 28 29   preupdate_new()
6c60: 20 61 6e 64 20 70 72 65 75 70 64 61 74 65 5f 6f   and preupdate_o
6c70: 6c 64 28 29 20 63 61 6e 20 6e 6f 74 0a 20 20 20  ld() can not.   
6c80: 20 20 20 2a 2a 20 66 61 69 6c 2e 20 54 68 69 73     ** fail. This
6c90: 20 69 73 20 62 65 63 61 75 73 65 20 74 68 65 79   is because they
6ca0: 20 63 61 63 68 65 20 74 68 65 69 72 20 72 65 74   cache their ret
6cb0: 75 72 6e 20 76 61 6c 75 65 73 2c 20 61 6e 64 20  urn values, and 
6cc0: 62 79 20 74 68 65 0a 20 20 20 20 20 20 2a 2a 20  by the.      ** 
6cd0: 74 69 6d 65 20 63 6f 6e 74 72 6f 6c 20 66 6c 6f  time control flo
6ce0: 77 73 20 74 6f 20 68 65 72 65 20 74 68 65 79 20  ws to here they 
6cf0: 68 61 76 65 20 61 6c 72 65 61 64 79 20 62 65 65  have already bee
6d00: 6e 20 63 61 6c 6c 65 64 20 6f 6e 63 65 20 66 72  n called once fr
6d10: 6f 6d 0a 20 20 20 20 20 20 2a 2a 20 77 69 74 68  om.      ** with
6d20: 69 6e 20 73 65 73 73 69 6f 6e 50 72 65 75 70 64  in sessionPreupd
6d30: 61 74 65 48 61 73 68 28 29 2e 20 54 68 65 20 66  ateHash(). The f
6d40: 69 72 73 74 20 74 77 6f 20 61 73 73 65 72 74 73  irst two asserts
6d50: 20 62 65 6c 6f 77 20 76 65 72 69 66 79 0a 20 20   below verify.  
6d60: 20 20 20 20 2a 2a 20 74 68 69 73 20 28 74 68 61      ** this (tha
6d70: 74 20 74 68 65 20 6d 65 74 68 6f 64 20 68 61 73  t the method has
6d80: 20 61 6c 72 65 61 64 79 20 62 65 65 6e 20 63 61   already been ca
6d90: 6c 6c 65 64 29 2e 20 2a 2f 0a 20 20 20 20 20 20  lled). */.      
6da0: 69 66 28 20 6f 70 3d 3d 53 51 4c 49 54 45 5f 49  if( op==SQLITE_I
6db0: 4e 53 45 52 54 20 29 7b 0a 20 20 20 20 20 20 20  NSERT ){.       
6dc0: 20 2f 2a 20 61 73 73 65 72 74 28 20 64 62 2d 3e   /* assert( db->
6dd0: 70 50 72 65 55 70 64 61 74 65 2d 3e 70 4e 65 77  pPreUpdate->pNew
6de0: 55 6e 70 61 63 6b 65 64 20 7c 7c 20 64 62 2d 3e  Unpacked || db->
6df0: 70 50 72 65 55 70 64 61 74 65 2d 3e 61 4e 65 77  pPreUpdate->aNew
6e00: 20 29 3b 20 2a 2f 0a 20 20 20 20 20 20 20 20 72   ); */.        r
6e10: 63 20 3d 20 70 53 65 73 73 69 6f 6e 2d 3e 68 6f  c = pSession->ho
6e20: 6f 6b 2e 78 4e 65 77 28 70 53 65 73 73 69 6f 6e  ok.xNew(pSession
6e30: 2d 3e 68 6f 6f 6b 2e 70 43 74 78 2c 20 69 43 6f  ->hook.pCtx, iCo
6e40: 6c 2c 20 26 70 56 61 6c 29 3b 0a 20 20 20 20 20  l, &pVal);.     
6e50: 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 20 20   }else{.        
6e60: 2f 2a 20 61 73 73 65 72 74 28 20 64 62 2d 3e 70  /* assert( db->p
6e70: 50 72 65 55 70 64 61 74 65 2d 3e 70 55 6e 70 61  PreUpdate->pUnpa
6e80: 63 6b 65 64 20 29 3b 20 2a 2f 0a 20 20 20 20 20  cked ); */.     
6e90: 20 20 20 72 63 20 3d 20 70 53 65 73 73 69 6f 6e     rc = pSession
6ea0: 2d 3e 68 6f 6f 6b 2e 78 4f 6c 64 28 70 53 65 73  ->hook.xOld(pSes
6eb0: 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 70 43 74 78 2c  sion->hook.pCtx,
6ec0: 20 69 43 6f 6c 2c 20 26 70 56 61 6c 29 3b 0a 20   iCol, &pVal);. 
6ed0: 20 20 20 20 20 7d 0a 20 20 20 20 20 20 61 73 73       }.      ass
6ee0: 65 72 74 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f  ert( rc==SQLITE_
6ef0: 4f 4b 20 29 3b 0a 20 20 20 20 20 20 69 66 28 20  OK );.      if( 
6f00: 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 5f 74 79  sqlite3_value_ty
6f10: 70 65 28 70 56 61 6c 29 21 3d 65 54 79 70 65 20  pe(pVal)!=eType 
6f20: 29 20 72 65 74 75 72 6e 20 30 3b 0a 0a 20 20 20  ) return 0;..   
6f30: 20 20 20 2f 2a 20 41 20 53 65 73 73 69 6f 6e 43     /* A SessionC
6f40: 68 61 6e 67 65 20 6f 62 6a 65 63 74 20 6e 65 76  hange object nev
6f50: 65 72 20 68 61 73 20 61 20 4e 55 4c 4c 20 76 61  er has a NULL va
6f60: 6c 75 65 20 69 6e 20 61 20 50 4b 20 63 6f 6c 75  lue in a PK colu
6f70: 6d 6e 20 2a 2f 0a 20 20 20 20 20 20 61 73 73 65  mn */.      asse
6f80: 72 74 28 20 65 54 79 70 65 3d 3d 53 51 4c 49 54  rt( eType==SQLIT
6f90: 45 5f 49 4e 54 45 47 45 52 20 7c 7c 20 65 54 79  E_INTEGER || eTy
6fa0: 70 65 3d 3d 53 51 4c 49 54 45 5f 46 4c 4f 41 54  pe==SQLITE_FLOAT
6fb0: 0a 20 20 20 20 20 20 20 20 20 20 20 7c 7c 20 65  .           || e
6fc0: 54 79 70 65 3d 3d 53 51 4c 49 54 45 5f 42 4c 4f  Type==SQLITE_BLO
6fd0: 42 20 20 20 20 7c 7c 20 65 54 79 70 65 3d 3d 53  B    || eType==S
6fe0: 51 4c 49 54 45 5f 54 45 58 54 0a 20 20 20 20 20  QLITE_TEXT.     
6ff0: 20 29 3b 0a 0a 20 20 20 20 20 20 69 66 28 20 65   );..      if( e
7000: 54 79 70 65 3d 3d 53 51 4c 49 54 45 5f 49 4e 54  Type==SQLITE_INT
7010: 45 47 45 52 20 7c 7c 20 65 54 79 70 65 3d 3d 53  EGER || eType==S
7020: 51 4c 49 54 45 5f 46 4c 4f 41 54 20 29 7b 0a 20  QLITE_FLOAT ){. 
7030: 20 20 20 20 20 20 20 69 36 34 20 69 56 61 6c 20         i64 iVal 
7040: 3d 20 73 65 73 73 69 6f 6e 47 65 74 49 36 34 28  = sessionGetI64(
7050: 61 29 3b 0a 20 20 20 20 20 20 20 20 61 20 2b 3d  a);.        a +=
7060: 20 38 3b 0a 20 20 20 20 20 20 20 20 69 66 28 20   8;.        if( 
7070: 65 54 79 70 65 3d 3d 53 51 4c 49 54 45 5f 49 4e  eType==SQLITE_IN
7080: 54 45 47 45 52 20 29 7b 0a 20 20 20 20 20 20 20  TEGER ){.       
7090: 20 20 20 69 66 28 20 73 71 6c 69 74 65 33 5f 76     if( sqlite3_v
70a0: 61 6c 75 65 5f 69 6e 74 36 34 28 70 56 61 6c 29  alue_int64(pVal)
70b0: 21 3d 69 56 61 6c 20 29 20 72 65 74 75 72 6e 20  !=iVal ) return 
70c0: 30 3b 0a 20 20 20 20 20 20 20 20 7d 65 6c 73 65  0;.        }else
70d0: 7b 0a 20 20 20 20 20 20 20 20 20 20 64 6f 75 62  {.          doub
70e0: 6c 65 20 72 56 61 6c 3b 0a 20 20 20 20 20 20 20  le rVal;.       
70f0: 20 20 20 61 73 73 65 72 74 28 20 73 69 7a 65 6f     assert( sizeo
7100: 66 28 69 56 61 6c 29 3d 3d 38 20 26 26 20 73 69  f(iVal)==8 && si
7110: 7a 65 6f 66 28 72 56 61 6c 29 3d 3d 38 20 29 3b  zeof(rVal)==8 );
7120: 0a 20 20 20 20 20 20 20 20 20 20 6d 65 6d 63 70  .          memcp
7130: 79 28 26 72 56 61 6c 2c 20 26 69 56 61 6c 2c 20  y(&rVal, &iVal, 
7140: 38 29 3b 0a 20 20 20 20 20 20 20 20 20 20 69 66  8);.          if
7150: 28 20 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 5f  ( sqlite3_value_
7160: 64 6f 75 62 6c 65 28 70 56 61 6c 29 21 3d 72 56  double(pVal)!=rV
7170: 61 6c 20 29 20 72 65 74 75 72 6e 20 30 3b 0a 20  al ) return 0;. 
7180: 20 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 7d         }.      }
7190: 65 6c 73 65 7b 0a 20 20 20 20 20 20 20 20 69 6e  else{.        in
71a0: 74 20 6e 3b 0a 20 20 20 20 20 20 20 20 63 6f 6e  t n;.        con
71b0: 73 74 20 75 38 20 2a 7a 3b 0a 20 20 20 20 20 20  st u8 *z;.      
71c0: 20 20 61 20 2b 3d 20 73 65 73 73 69 6f 6e 56 61    a += sessionVa
71d0: 72 69 6e 74 47 65 74 28 61 2c 20 26 6e 29 3b 0a  rintGet(a, &n);.
71e0: 20 20 20 20 20 20 20 20 69 66 28 20 73 71 6c 69          if( sqli
71f0: 74 65 33 5f 76 61 6c 75 65 5f 62 79 74 65 73 28  te3_value_bytes(
7200: 70 56 61 6c 29 21 3d 6e 20 29 20 72 65 74 75 72  pVal)!=n ) retur
7210: 6e 20 30 3b 0a 20 20 20 20 20 20 20 20 69 66 28  n 0;.        if(
7220: 20 65 54 79 70 65 3d 3d 53 51 4c 49 54 45 5f 54   eType==SQLITE_T
7230: 45 58 54 20 29 7b 0a 20 20 20 20 20 20 20 20 20  EXT ){.         
7240: 20 7a 20 3d 20 73 71 6c 69 74 65 33 5f 76 61 6c   z = sqlite3_val
7250: 75 65 5f 74 65 78 74 28 70 56 61 6c 29 3b 0a 20  ue_text(pVal);. 
7260: 20 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20         }else{.  
7270: 20 20 20 20 20 20 20 20 7a 20 3d 20 73 71 6c 69          z = sqli
7280: 74 65 33 5f 76 61 6c 75 65 5f 62 6c 6f 62 28 70  te3_value_blob(p
7290: 56 61 6c 29 3b 0a 20 20 20 20 20 20 20 20 7d 0a  Val);.        }.
72a0: 20 20 20 20 20 20 20 20 69 66 28 20 6d 65 6d 63          if( memc
72b0: 6d 70 28 61 2c 20 7a 2c 20 6e 29 20 29 20 72 65  mp(a, z, n) ) re
72c0: 74 75 72 6e 20 30 3b 0a 20 20 20 20 20 20 20 20  turn 0;.        
72d0: 61 20 2b 3d 20 6e 3b 0a 20 20 20 20 20 20 20 20  a += n;.        
72e0: 62 72 65 61 6b 3b 0a 20 20 20 20 20 20 7d 0a 20  break;.      }. 
72f0: 20 20 20 7d 0a 20 20 7d 0a 0a 20 20 72 65 74 75     }.  }..  retu
7300: 72 6e 20 31 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 49  rn 1;.}../*.** I
7310: 66 20 72 65 71 75 69 72 65 64 2c 20 67 72 6f 77  f required, grow
7320: 20 74 68 65 20 68 61 73 68 20 74 61 62 6c 65 20   the hash table 
7330: 75 73 65 64 20 74 6f 20 73 74 6f 72 65 20 63 68  used to store ch
7340: 61 6e 67 65 73 20 6f 6e 20 74 61 62 6c 65 20 70  anges on table p
7350: 54 61 62 20 0a 2a 2a 20 28 70 61 72 74 20 6f 66  Tab .** (part of
7360: 20 74 68 65 20 73 65 73 73 69 6f 6e 20 70 53 65   the session pSe
7370: 73 73 69 6f 6e 29 2e 20 49 66 20 61 20 66 61 74  ssion). If a fat
7380: 61 6c 20 4f 4f 4d 20 65 72 72 6f 72 20 6f 63 63  al OOM error occ
7390: 75 72 73 2c 20 73 65 74 20 74 68 65 0a 2a 2a 20  urs, set the.** 
73a0: 73 65 73 73 69 6f 6e 20 6f 62 6a 65 63 74 20 74  session object t
73b0: 6f 20 66 61 69 6c 65 64 20 61 6e 64 20 72 65 74  o failed and ret
73c0: 75 72 6e 20 53 51 4c 49 54 45 5f 45 52 52 4f 52  urn SQLITE_ERROR
73d0: 2e 20 4f 74 68 65 72 77 69 73 65 2c 20 72 65 74  . Otherwise, ret
73e0: 75 72 6e 0a 2a 2a 20 53 51 4c 49 54 45 5f 4f 4b  urn.** SQLITE_OK
73f0: 2e 0a 2a 2a 0a 2a 2a 20 49 74 20 69 73 20 70 6f  ..**.** It is po
7400: 73 73 69 62 6c 65 20 74 68 61 74 20 61 20 6e 6f  ssible that a no
7410: 6e 2d 66 61 74 61 6c 20 4f 4f 4d 20 65 72 72 6f  n-fatal OOM erro
7420: 72 20 6f 63 63 75 72 73 20 69 6e 20 74 68 69 73  r occurs in this
7430: 20 66 75 6e 63 74 69 6f 6e 2e 20 49 6e 0a 2a 2a   function. In.**
7440: 20 74 68 61 74 20 63 61 73 65 20 74 68 65 20 68   that case the h
7450: 61 73 68 2d 74 61 62 6c 65 20 64 6f 65 73 20 6e  ash-table does n
7460: 6f 74 20 67 72 6f 77 2c 20 62 75 74 20 53 51 4c  ot grow, but SQL
7470: 49 54 45 5f 4f 4b 20 69 73 20 72 65 74 75 72 6e  ITE_OK is return
7480: 65 64 20 61 6e 79 77 61 79 2e 0a 2a 2a 20 47 72  ed anyway..** Gr
7490: 6f 77 69 6e 67 20 74 68 65 20 68 61 73 68 20 74  owing the hash t
74a0: 61 62 6c 65 20 69 6e 20 74 68 69 73 20 63 61 73  able in this cas
74b0: 65 20 69 73 20 61 20 70 65 72 66 6f 72 6d 61 6e  e is a performan
74c0: 63 65 20 6f 70 74 69 6d 69 7a 61 74 69 6f 6e 20  ce optimization 
74d0: 6f 6e 6c 79 2c 0a 2a 2a 20 69 74 20 69 73 20 6e  only,.** it is n
74e0: 6f 74 20 72 65 71 75 69 72 65 64 20 66 6f 72 20  ot required for 
74f0: 63 6f 72 72 65 63 74 20 6f 70 65 72 61 74 69 6f  correct operatio
7500: 6e 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74  n..*/.static int
7510: 20 73 65 73 73 69 6f 6e 47 72 6f 77 48 61 73 68   sessionGrowHash
7520: 28 69 6e 74 20 62 50 61 74 63 68 73 65 74 2c 20  (int bPatchset, 
7530: 53 65 73 73 69 6f 6e 54 61 62 6c 65 20 2a 70 54  SessionTable *pT
7540: 61 62 29 7b 0a 20 20 69 66 28 20 70 54 61 62 2d  ab){.  if( pTab-
7550: 3e 6e 43 68 61 6e 67 65 3d 3d 30 20 7c 7c 20 70  >nChange==0 || p
7560: 54 61 62 2d 3e 6e 45 6e 74 72 79 3e 3d 28 70 54  Tab->nEntry>=(pT
7570: 61 62 2d 3e 6e 43 68 61 6e 67 65 2f 32 29 20 29  ab->nChange/2) )
7580: 7b 0a 20 20 20 20 69 6e 74 20 69 3b 0a 20 20 20  {.    int i;.   
7590: 20 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 20 2a   SessionChange *
75a0: 2a 61 70 4e 65 77 3b 0a 20 20 20 20 69 6e 74 20  *apNew;.    int 
75b0: 6e 4e 65 77 20 3d 20 28 70 54 61 62 2d 3e 6e 43  nNew = (pTab->nC
75c0: 68 61 6e 67 65 20 3f 20 70 54 61 62 2d 3e 6e 43  hange ? pTab->nC
75d0: 68 61 6e 67 65 20 3a 20 31 32 38 29 20 2a 20 32  hange : 128) * 2
75e0: 3b 0a 0a 20 20 20 20 61 70 4e 65 77 20 3d 20 28  ;..    apNew = (
75f0: 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 20 2a 2a  SessionChange **
7600: 29 73 71 6c 69 74 65 33 5f 6d 61 6c 6c 6f 63 28  )sqlite3_malloc(
7610: 73 69 7a 65 6f 66 28 53 65 73 73 69 6f 6e 43 68  sizeof(SessionCh
7620: 61 6e 67 65 20 2a 29 20 2a 20 6e 4e 65 77 29 3b  ange *) * nNew);
7630: 0a 20 20 20 20 69 66 28 20 61 70 4e 65 77 3d 3d  .    if( apNew==
7640: 30 20 29 7b 0a 20 20 20 20 20 20 69 66 28 20 70  0 ){.      if( p
7650: 54 61 62 2d 3e 6e 43 68 61 6e 67 65 3d 3d 30 20  Tab->nChange==0 
7660: 29 7b 0a 20 20 20 20 20 20 20 20 72 65 74 75 72  ){.        retur
7670: 6e 20 53 51 4c 49 54 45 5f 45 52 52 4f 52 3b 0a  n SQLITE_ERROR;.
7680: 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 72 65        }.      re
7690: 74 75 72 6e 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a  turn SQLITE_OK;.
76a0: 20 20 20 20 7d 0a 20 20 20 20 6d 65 6d 73 65 74      }.    memset
76b0: 28 61 70 4e 65 77 2c 20 30 2c 20 73 69 7a 65 6f  (apNew, 0, sizeo
76c0: 66 28 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 20  f(SessionChange 
76d0: 2a 29 20 2a 20 6e 4e 65 77 29 3b 0a 0a 20 20 20  *) * nNew);..   
76e0: 20 66 6f 72 28 69 3d 30 3b 20 69 3c 70 54 61 62   for(i=0; i<pTab
76f0: 2d 3e 6e 43 68 61 6e 67 65 3b 20 69 2b 2b 29 7b  ->nChange; i++){
7700: 0a 20 20 20 20 20 20 53 65 73 73 69 6f 6e 43 68  .      SessionCh
7710: 61 6e 67 65 20 2a 70 3b 0a 20 20 20 20 20 20 53  ange *p;.      S
7720: 65 73 73 69 6f 6e 43 68 61 6e 67 65 20 2a 70 4e  essionChange *pN
7730: 65 78 74 3b 0a 20 20 20 20 20 20 66 6f 72 28 70  ext;.      for(p
7740: 3d 70 54 61 62 2d 3e 61 70 43 68 61 6e 67 65 5b  =pTab->apChange[
7750: 69 5d 3b 20 70 3b 20 70 3d 70 4e 65 78 74 29 7b  i]; p; p=pNext){
7760: 0a 20 20 20 20 20 20 20 20 69 6e 74 20 62 50 6b  .        int bPk
7770: 4f 6e 6c 79 20 3d 20 28 70 2d 3e 6f 70 3d 3d 53  Only = (p->op==S
7780: 51 4c 49 54 45 5f 44 45 4c 45 54 45 20 26 26 20  QLITE_DELETE && 
7790: 62 50 61 74 63 68 73 65 74 29 3b 0a 20 20 20 20  bPatchset);.    
77a0: 20 20 20 20 69 6e 74 20 69 48 61 73 68 20 3d 20      int iHash = 
77b0: 73 65 73 73 69 6f 6e 43 68 61 6e 67 65 48 61 73  sessionChangeHas
77c0: 68 28 70 54 61 62 2c 20 62 50 6b 4f 6e 6c 79 2c  h(pTab, bPkOnly,
77d0: 20 70 2d 3e 61 52 65 63 6f 72 64 2c 20 6e 4e 65   p->aRecord, nNe
77e0: 77 29 3b 0a 20 20 20 20 20 20 20 20 70 4e 65 78  w);.        pNex
77f0: 74 20 3d 20 70 2d 3e 70 4e 65 78 74 3b 0a 20 20  t = p->pNext;.  
7800: 20 20 20 20 20 20 70 2d 3e 70 4e 65 78 74 20 3d        p->pNext =
7810: 20 61 70 4e 65 77 5b 69 48 61 73 68 5d 3b 0a 20   apNew[iHash];. 
7820: 20 20 20 20 20 20 20 61 70 4e 65 77 5b 69 48 61         apNew[iHa
7830: 73 68 5d 20 3d 20 70 3b 0a 20 20 20 20 20 20 7d  sh] = p;.      }
7840: 0a 20 20 20 20 7d 0a 0a 20 20 20 20 73 71 6c 69  .    }..    sqli
7850: 74 65 33 5f 66 72 65 65 28 70 54 61 62 2d 3e 61  te3_free(pTab->a
7860: 70 43 68 61 6e 67 65 29 3b 0a 20 20 20 20 70 54  pChange);.    pT
7870: 61 62 2d 3e 6e 43 68 61 6e 67 65 20 3d 20 6e 4e  ab->nChange = nN
7880: 65 77 3b 0a 20 20 20 20 70 54 61 62 2d 3e 61 70  ew;.    pTab->ap
7890: 43 68 61 6e 67 65 20 3d 20 61 70 4e 65 77 3b 0a  Change = apNew;.
78a0: 20 20 7d 0a 0a 20 20 72 65 74 75 72 6e 20 53 51    }..  return SQ
78b0: 4c 49 54 45 5f 4f 4b 3b 0a 7d 0a 0a 2f 2a 0a 2a  LITE_OK;.}../*.*
78c0: 2a 20 54 68 69 73 20 66 75 6e 63 74 69 6f 6e 20  * This function 
78d0: 71 75 65 72 69 65 73 20 74 68 65 20 64 61 74 61  queries the data
78e0: 62 61 73 65 20 66 6f 72 20 74 68 65 20 6e 61 6d  base for the nam
78f0: 65 73 20 6f 66 20 74 68 65 20 63 6f 6c 75 6d 6e  es of the column
7900: 73 20 6f 66 20 74 61 62 6c 65 0a 2a 2a 20 7a 54  s of table.** zT
7910: 68 69 73 2c 20 69 6e 20 73 63 68 65 6d 61 20 7a  his, in schema z
7920: 44 62 2e 20 49 74 20 69 73 20 65 78 70 65 63 74  Db. It is expect
7930: 65 64 20 74 68 61 74 20 74 68 65 20 74 61 62 6c  ed that the tabl
7940: 65 20 68 61 73 20 6e 43 6f 6c 20 63 6f 6c 75 6d  e has nCol colum
7950: 6e 73 2e 20 49 66 0a 2a 2a 20 6e 6f 74 2c 20 53  ns. If.** not, S
7960: 51 4c 49 54 45 5f 53 43 48 45 4d 41 20 69 73 20  QLITE_SCHEMA is 
7970: 72 65 74 75 72 6e 65 64 20 61 6e 64 20 6e 6f 6e  returned and non
7980: 65 20 6f 66 20 74 68 65 20 6f 75 74 70 75 74 20  e of the output 
7990: 76 61 72 69 61 62 6c 65 73 20 61 72 65 0a 2a 2a  variables are.**
79a0: 20 70 6f 70 75 6c 61 74 65 64 2e 0a 2a 2a 0a 2a   populated..**.*
79b0: 2a 20 4f 74 68 65 72 77 69 73 65 2c 20 69 66 20  * Otherwise, if 
79c0: 74 68 65 79 20 61 72 65 20 6e 6f 74 20 4e 55 4c  they are not NUL
79d0: 4c 2c 20 76 61 72 69 61 62 6c 65 20 2a 70 6e 43  L, variable *pnC
79e0: 6f 6c 20 69 73 20 73 65 74 20 74 6f 20 74 68 65  ol is set to the
79f0: 20 6e 75 6d 62 65 72 0a 2a 2a 20 6f 66 20 63 6f   number.** of co
7a00: 6c 75 6d 6e 73 20 69 6e 20 74 68 65 20 64 61 74  lumns in the dat
7a10: 61 62 61 73 65 20 74 61 62 6c 65 20 61 6e 64 20  abase table and 
7a20: 76 61 72 69 61 62 6c 65 20 2a 70 7a 54 61 62 20  variable *pzTab 
7a30: 69 73 20 73 65 74 20 74 6f 20 70 6f 69 6e 74 20  is set to point 
7a40: 74 6f 20 61 0a 2a 2a 20 6e 75 6c 2d 74 65 72 6d  to a.** nul-term
7a50: 69 6e 61 74 65 64 20 63 6f 70 79 20 6f 66 20 74  inated copy of t
7a60: 68 65 20 74 61 62 6c 65 20 6e 61 6d 65 2e 20 2a  he table name. *
7a70: 70 61 7a 43 6f 6c 20 28 69 66 20 6e 6f 74 20 4e  pazCol (if not N
7a80: 55 4c 4c 29 20 69 73 20 73 65 74 20 74 6f 0a 2a  ULL) is set to.*
7a90: 2a 20 70 6f 69 6e 74 20 74 6f 20 61 6e 20 61 72  * point to an ar
7aa0: 72 61 79 20 6f 66 20 70 6f 69 6e 74 65 72 73 20  ray of pointers 
7ab0: 74 6f 20 63 6f 6c 75 6d 6e 20 6e 61 6d 65 73 2e  to column names.
7ac0: 20 41 6e 64 20 2a 70 61 62 50 4b 20 28 61 67 61   And *pabPK (aga
7ad0: 69 6e 2c 20 69 66 20 6e 6f 74 0a 2a 2a 20 4e 55  in, if not.** NU
7ae0: 4c 4c 29 20 69 73 20 73 65 74 20 74 6f 20 70 6f  LL) is set to po
7af0: 69 6e 74 20 74 6f 20 61 6e 20 61 72 72 61 79 20  int to an array 
7b00: 6f 66 20 62 6f 6f 6c 65 61 6e 73 20 2d 20 74 72  of booleans - tr
7b10: 75 65 20 69 66 20 74 68 65 20 63 6f 72 72 65 73  ue if the corres
7b20: 70 6f 6e 64 69 6e 67 0a 2a 2a 20 63 6f 6c 75 6d  ponding.** colum
7b30: 6e 20 69 73 20 70 61 72 74 20 6f 66 20 74 68 65  n is part of the
7b40: 20 70 72 69 6d 61 72 79 20 6b 65 79 2e 0a 2a 2a   primary key..**
7b50: 0a 2a 2a 20 46 6f 72 20 65 78 61 6d 70 6c 65 2c  .** For example,
7b60: 20 69 66 20 74 68 65 20 74 61 62 6c 65 20 69 73   if the table is
7b70: 20 64 65 63 6c 61 72 65 64 20 61 73 3a 0a 2a 2a   declared as:.**
7b80: 0a 2a 2a 20 20 20 20 20 43 52 45 41 54 45 20 54  .**     CREATE T
7b90: 41 42 4c 45 20 74 62 6c 31 28 77 2c 20 78 2c 20  ABLE tbl1(w, x, 
7ba0: 79 2c 20 7a 2c 20 50 52 49 4d 41 52 59 20 4b 45  y, z, PRIMARY KE
7bb0: 59 28 77 2c 20 7a 29 29 3b 0a 2a 2a 0a 2a 2a 20  Y(w, z));.**.** 
7bc0: 54 68 65 6e 20 74 68 65 20 66 6f 75 72 20 6f 75  Then the four ou
7bd0: 74 70 75 74 20 76 61 72 69 61 62 6c 65 73 20 61  tput variables a
7be0: 72 65 20 70 6f 70 75 6c 61 74 65 64 20 61 73 20  re populated as 
7bf0: 66 6f 6c 6c 6f 77 73 3a 0a 2a 2a 0a 2a 2a 20 20  follows:.**.**  
7c00: 20 20 20 2a 70 6e 43 6f 6c 20 20 3d 20 34 0a 2a     *pnCol  = 4.*
7c10: 2a 20 20 20 20 20 2a 70 7a 54 61 62 20 20 3d 20  *     *pzTab  = 
7c20: 22 74 62 6c 31 22 0a 2a 2a 20 20 20 20 20 2a 70  "tbl1".**     *p
7c30: 61 7a 43 6f 6c 20 3d 20 7b 22 77 22 2c 20 22 78  azCol = {"w", "x
7c40: 22 2c 20 22 79 22 2c 20 22 7a 22 7d 0a 2a 2a 20  ", "y", "z"}.** 
7c50: 20 20 20 20 2a 70 61 62 50 4b 20 20 3d 20 7b 31      *pabPK  = {1
7c60: 2c 20 30 2c 20 30 2c 20 31 7d 0a 2a 2a 0a 2a 2a  , 0, 0, 1}.**.**
7c70: 20 41 6c 6c 20 72 65 74 75 72 6e 65 64 20 62 75   All returned bu
7c80: 66 66 65 72 73 20 61 72 65 20 70 61 72 74 20 6f  ffers are part o
7c90: 66 20 74 68 65 20 73 61 6d 65 20 73 69 6e 67 6c  f the same singl
7ca0: 65 20 61 6c 6c 6f 63 61 74 69 6f 6e 2c 20 77 68  e allocation, wh
7cb0: 69 63 68 20 6d 75 73 74 0a 2a 2a 20 62 65 20 66  ich must.** be f
7cc0: 72 65 65 64 20 75 73 69 6e 67 20 73 71 6c 69 74  reed using sqlit
7cd0: 65 33 5f 66 72 65 65 28 29 20 62 79 20 74 68 65  e3_free() by the
7ce0: 20 63 61 6c 6c 65 72 2e 20 49 66 20 70 61 7a 43   caller. If pazC
7cf0: 6f 6c 20 77 61 73 20 6e 6f 74 20 4e 55 4c 4c 2c  ol was not NULL,
7d00: 20 74 68 65 6e 0a 2a 2a 20 70 6f 69 6e 74 65 72   then.** pointer
7d10: 20 2a 70 61 7a 43 6f 6c 20 73 68 6f 75 6c 64 20   *pazCol should 
7d20: 62 65 20 66 72 65 65 64 20 74 6f 20 72 65 6c 65  be freed to rele
7d30: 61 73 65 20 61 6c 6c 20 6d 65 6d 6f 72 79 2e 20  ase all memory. 
7d40: 4f 74 68 65 72 77 69 73 65 2c 20 70 6f 69 6e 74  Otherwise, point
7d50: 65 72 0a 2a 2a 20 2a 70 61 62 50 4b 2e 20 49 74  er.** *pabPK. It
7d60: 20 69 73 20 69 6c 6c 65 67 61 6c 20 66 6f 72 20   is illegal for 
7d70: 62 6f 74 68 20 70 61 7a 43 6f 6c 20 61 6e 64 20  both pazCol and 
7d80: 70 61 62 50 4b 20 74 6f 20 62 65 20 4e 55 4c 4c  pabPK to be NULL
7d90: 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20  ..*/.static int 
7da0: 73 65 73 73 69 6f 6e 54 61 62 6c 65 49 6e 66 6f  sessionTableInfo
7db0: 28 0a 20 20 73 71 6c 69 74 65 33 20 2a 64 62 2c  (.  sqlite3 *db,
7dc0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
7dd0: 20 20 20 20 2f 2a 20 44 61 74 61 62 61 73 65 20      /* Database 
7de0: 63 6f 6e 6e 65 63 74 69 6f 6e 20 2a 2f 0a 20 20  connection */.  
7df0: 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 44 62 2c  const char *zDb,
7e00: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
7e10: 2f 2a 20 4e 61 6d 65 20 6f 66 20 61 74 74 61 63  /* Name of attac
7e20: 68 65 64 20 64 61 74 61 62 61 73 65 20 28 65 2e  hed database (e.
7e30: 67 2e 20 22 6d 61 69 6e 22 29 20 2a 2f 0a 20 20  g. "main") */.  
7e40: 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 54 68 69  const char *zThi
7e50: 73 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20  s,              
7e60: 2f 2a 20 54 61 62 6c 65 20 6e 61 6d 65 20 2a 2f  /* Table name */
7e70: 0a 20 20 69 6e 74 20 2a 70 6e 43 6f 6c 2c 20 20  .  int *pnCol,  
7e80: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
7e90: 20 20 20 2f 2a 20 4f 55 54 3a 20 6e 75 6d 62 65     /* OUT: numbe
7ea0: 72 20 6f 66 20 63 6f 6c 75 6d 6e 73 20 2a 2f 0a  r of columns */.
7eb0: 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 2a 70    const char **p
7ec0: 7a 54 61 62 2c 20 20 20 20 20 20 20 20 20 20 20  zTab,           
7ed0: 20 20 2f 2a 20 4f 55 54 3a 20 43 6f 70 79 20 6f    /* OUT: Copy o
7ee0: 66 20 7a 54 68 69 73 20 2a 2f 0a 20 20 63 6f 6e  f zThis */.  con
7ef0: 73 74 20 63 68 61 72 20 2a 2a 2a 70 61 7a 43 6f  st char ***pazCo
7f00: 6c 2c 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20  l,           /* 
7f10: 4f 55 54 3a 20 41 72 72 61 79 20 6f 66 20 63 6f  OUT: Array of co
7f20: 6c 75 6d 6e 20 6e 61 6d 65 73 20 66 6f 72 20 74  lumn names for t
7f30: 61 62 6c 65 20 2a 2f 0a 20 20 75 38 20 2a 2a 70  able */.  u8 **p
7f40: 61 62 50 4b 20 20 20 20 20 20 20 20 20 20 20 20  abPK            
7f50: 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4f 55 54            /* OUT
7f60: 3a 20 41 72 72 61 79 20 6f 66 20 62 6f 6f 6c 65  : Array of boole
7f70: 61 6e 73 20 2d 20 74 72 75 65 20 66 6f 72 20 50  ans - true for P
7f80: 4b 20 63 6f 6c 20 2a 2f 0a 29 7b 0a 20 20 63 68  K col */.){.  ch
7f90: 61 72 20 2a 7a 50 72 61 67 6d 61 3b 0a 20 20 73  ar *zPragma;.  s
7fa0: 71 6c 69 74 65 33 5f 73 74 6d 74 20 2a 70 53 74  qlite3_stmt *pSt
7fb0: 6d 74 3b 0a 20 20 69 6e 74 20 72 63 3b 0a 20 20  mt;.  int rc;.  
7fc0: 69 6e 74 20 6e 42 79 74 65 3b 0a 20 20 69 6e 74  int nByte;.  int
7fd0: 20 6e 44 62 43 6f 6c 20 3d 20 30 3b 0a 20 20 69   nDbCol = 0;.  i
7fe0: 6e 74 20 6e 54 68 69 73 3b 0a 20 20 69 6e 74 20  nt nThis;.  int 
7ff0: 69 3b 0a 20 20 75 38 20 2a 70 41 6c 6c 6f 63 20  i;.  u8 *pAlloc 
8000: 3d 20 30 3b 0a 20 20 63 68 61 72 20 2a 2a 61 7a  = 0;.  char **az
8010: 43 6f 6c 20 3d 20 30 3b 0a 20 20 75 38 20 2a 61  Col = 0;.  u8 *a
8020: 62 50 4b 20 3d 20 30 3b 0a 0a 20 20 61 73 73 65  bPK = 0;..  asse
8030: 72 74 28 20 70 61 7a 43 6f 6c 20 26 26 20 70 61  rt( pazCol && pa
8040: 62 50 4b 20 29 3b 0a 0a 20 20 6e 54 68 69 73 20  bPK );..  nThis 
8050: 3d 20 73 71 6c 69 74 65 33 53 74 72 6c 65 6e 33  = sqlite3Strlen3
8060: 30 28 7a 54 68 69 73 29 3b 0a 20 20 7a 50 72 61  0(zThis);.  zPra
8070: 67 6d 61 20 3d 20 73 71 6c 69 74 65 33 5f 6d 70  gma = sqlite3_mp
8080: 72 69 6e 74 66 28 22 50 52 41 47 4d 41 20 27 25  rintf("PRAGMA '%
8090: 71 27 2e 74 61 62 6c 65 5f 69 6e 66 6f 28 27 25  q'.table_info('%
80a0: 71 27 29 22 2c 20 7a 44 62 2c 20 7a 54 68 69 73  q')", zDb, zThis
80b0: 29 3b 0a 20 20 69 66 28 20 21 7a 50 72 61 67 6d  );.  if( !zPragm
80c0: 61 20 29 20 72 65 74 75 72 6e 20 53 51 4c 49 54  a ) return SQLIT
80d0: 45 5f 4e 4f 4d 45 4d 3b 0a 0a 20 20 72 63 20 3d  E_NOMEM;..  rc =
80e0: 20 73 71 6c 69 74 65 33 5f 70 72 65 70 61 72 65   sqlite3_prepare
80f0: 5f 76 32 28 64 62 2c 20 7a 50 72 61 67 6d 61 2c  _v2(db, zPragma,
8100: 20 2d 31 2c 20 26 70 53 74 6d 74 2c 20 30 29 3b   -1, &pStmt, 0);
8110: 0a 20 20 73 71 6c 69 74 65 33 5f 66 72 65 65 28  .  sqlite3_free(
8120: 7a 50 72 61 67 6d 61 29 3b 0a 20 20 69 66 28 20  zPragma);.  if( 
8130: 72 63 21 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 20  rc!=SQLITE_OK ) 
8140: 72 65 74 75 72 6e 20 72 63 3b 0a 0a 20 20 6e 42  return rc;..  nB
8150: 79 74 65 20 3d 20 6e 54 68 69 73 20 2b 20 31 3b  yte = nThis + 1;
8160: 0a 20 20 77 68 69 6c 65 28 20 53 51 4c 49 54 45  .  while( SQLITE
8170: 5f 52 4f 57 3d 3d 73 71 6c 69 74 65 33 5f 73 74  _ROW==sqlite3_st
8180: 65 70 28 70 53 74 6d 74 29 20 29 7b 0a 20 20 20  ep(pStmt) ){.   
8190: 20 6e 42 79 74 65 20 2b 3d 20 73 71 6c 69 74 65   nByte += sqlite
81a0: 33 5f 63 6f 6c 75 6d 6e 5f 62 79 74 65 73 28 70  3_column_bytes(p
81b0: 53 74 6d 74 2c 20 31 29 3b 0a 20 20 20 20 6e 44  Stmt, 1);.    nD
81c0: 62 43 6f 6c 2b 2b 3b 0a 20 20 7d 0a 20 20 72 63  bCol++;.  }.  rc
81d0: 20 3d 20 73 71 6c 69 74 65 33 5f 72 65 73 65 74   = sqlite3_reset
81e0: 28 70 53 74 6d 74 29 3b 0a 0a 20 20 69 66 28 20  (pStmt);..  if( 
81f0: 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b  rc==SQLITE_OK ){
8200: 0a 20 20 20 20 6e 42 79 74 65 20 2b 3d 20 6e 44  .    nByte += nD
8210: 62 43 6f 6c 20 2a 20 28 73 69 7a 65 6f 66 28 63  bCol * (sizeof(c
8220: 6f 6e 73 74 20 63 68 61 72 20 2a 29 20 2b 20 73  onst char *) + s
8230: 69 7a 65 6f 66 28 75 38 29 20 2b 20 31 29 3b 0a  izeof(u8) + 1);.
8240: 20 20 20 20 70 41 6c 6c 6f 63 20 3d 20 73 71 6c      pAlloc = sql
8250: 69 74 65 33 5f 6d 61 6c 6c 6f 63 28 6e 42 79 74  ite3_malloc(nByt
8260: 65 29 3b 0a 20 20 20 20 69 66 28 20 70 41 6c 6c  e);.    if( pAll
8270: 6f 63 3d 3d 30 20 29 7b 0a 20 20 20 20 20 20 72  oc==0 ){.      r
8280: 63 20 3d 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d  c = SQLITE_NOMEM
8290: 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a 20 20 69 66  ;.    }.  }.  if
82a0: 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20  ( rc==SQLITE_OK 
82b0: 29 7b 0a 20 20 20 20 61 7a 43 6f 6c 20 3d 20 28  ){.    azCol = (
82c0: 63 68 61 72 20 2a 2a 29 70 41 6c 6c 6f 63 3b 0a  char **)pAlloc;.
82d0: 20 20 20 20 70 41 6c 6c 6f 63 20 3d 20 28 75 38      pAlloc = (u8
82e0: 20 2a 29 26 61 7a 43 6f 6c 5b 6e 44 62 43 6f 6c   *)&azCol[nDbCol
82f0: 5d 3b 0a 20 20 20 20 61 62 50 4b 20 3d 20 28 75  ];.    abPK = (u
8300: 38 20 2a 29 70 41 6c 6c 6f 63 3b 0a 20 20 20 20  8 *)pAlloc;.    
8310: 70 41 6c 6c 6f 63 20 3d 20 26 61 62 50 4b 5b 6e  pAlloc = &abPK[n
8320: 44 62 43 6f 6c 5d 3b 0a 20 20 20 20 69 66 28 20  DbCol];.    if( 
8330: 70 7a 54 61 62 20 29 7b 0a 20 20 20 20 20 20 6d  pzTab ){.      m
8340: 65 6d 63 70 79 28 70 41 6c 6c 6f 63 2c 20 7a 54  emcpy(pAlloc, zT
8350: 68 69 73 2c 20 6e 54 68 69 73 2b 31 29 3b 0a 20  his, nThis+1);. 
8360: 20 20 20 20 20 2a 70 7a 54 61 62 20 3d 20 28 63       *pzTab = (c
8370: 68 61 72 20 2a 29 70 41 6c 6c 6f 63 3b 0a 20 20  har *)pAlloc;.  
8380: 20 20 20 20 70 41 6c 6c 6f 63 20 2b 3d 20 6e 54      pAlloc += nT
8390: 68 69 73 2b 31 3b 0a 20 20 20 20 7d 0a 20 20 0a  his+1;.    }.  .
83a0: 20 20 20 20 69 20 3d 20 30 3b 0a 20 20 20 20 77      i = 0;.    w
83b0: 68 69 6c 65 28 20 53 51 4c 49 54 45 5f 52 4f 57  hile( SQLITE_ROW
83c0: 3d 3d 73 71 6c 69 74 65 33 5f 73 74 65 70 28 70  ==sqlite3_step(p
83d0: 53 74 6d 74 29 20 29 7b 0a 20 20 20 20 20 20 69  Stmt) ){.      i
83e0: 6e 74 20 6e 4e 61 6d 65 20 3d 20 73 71 6c 69 74  nt nName = sqlit
83f0: 65 33 5f 63 6f 6c 75 6d 6e 5f 62 79 74 65 73 28  e3_column_bytes(
8400: 70 53 74 6d 74 2c 20 31 29 3b 0a 20 20 20 20 20  pStmt, 1);.     
8410: 20 63 6f 6e 73 74 20 75 6e 73 69 67 6e 65 64 20   const unsigned 
8420: 63 68 61 72 20 2a 7a 4e 61 6d 65 20 3d 20 73 71  char *zName = sq
8430: 6c 69 74 65 33 5f 63 6f 6c 75 6d 6e 5f 74 65 78  lite3_column_tex
8440: 74 28 70 53 74 6d 74 2c 20 31 29 3b 0a 20 20 20  t(pStmt, 1);.   
8450: 20 20 20 69 66 28 20 7a 4e 61 6d 65 3d 3d 30 20     if( zName==0 
8460: 29 20 62 72 65 61 6b 3b 0a 20 20 20 20 20 20 6d  ) break;.      m
8470: 65 6d 63 70 79 28 70 41 6c 6c 6f 63 2c 20 7a 4e  emcpy(pAlloc, zN
8480: 61 6d 65 2c 20 6e 4e 61 6d 65 2b 31 29 3b 0a 20  ame, nName+1);. 
8490: 20 20 20 20 20 61 7a 43 6f 6c 5b 69 5d 20 3d 20       azCol[i] = 
84a0: 28 63 68 61 72 20 2a 29 70 41 6c 6c 6f 63 3b 0a  (char *)pAlloc;.
84b0: 20 20 20 20 20 20 70 41 6c 6c 6f 63 20 2b 3d 20        pAlloc += 
84c0: 6e 4e 61 6d 65 2b 31 3b 0a 20 20 20 20 20 20 61  nName+1;.      a
84d0: 62 50 4b 5b 69 5d 20 3d 20 73 71 6c 69 74 65 33  bPK[i] = sqlite3
84e0: 5f 63 6f 6c 75 6d 6e 5f 69 6e 74 28 70 53 74 6d  _column_int(pStm
84f0: 74 2c 20 35 29 3b 0a 20 20 20 20 20 20 69 2b 2b  t, 5);.      i++
8500: 3b 0a 20 20 20 20 7d 0a 20 20 20 20 72 63 20 3d  ;.    }.    rc =
8510: 20 73 71 6c 69 74 65 33 5f 72 65 73 65 74 28 70   sqlite3_reset(p
8520: 53 74 6d 74 29 3b 0a 20 20 0a 20 20 7d 0a 0a 20  Stmt);.  .  }.. 
8530: 20 2f 2a 20 49 66 20 73 75 63 63 65 73 73 66 75   /* If successfu
8540: 6c 2c 20 70 6f 70 75 6c 61 74 65 20 74 68 65 20  l, populate the 
8550: 6f 75 74 70 75 74 20 76 61 72 69 61 62 6c 65 73  output variables
8560: 2e 20 4f 74 68 65 72 77 69 73 65 2c 20 7a 65 72  . Otherwise, zer
8570: 6f 20 74 68 65 6d 20 61 6e 64 0a 20 20 2a 2a 20  o them and.  ** 
8580: 66 72 65 65 20 61 6e 79 20 61 6c 6c 6f 63 61 74  free any allocat
8590: 69 6f 6e 20 6d 61 64 65 2e 20 41 6e 20 65 72 72  ion made. An err
85a0: 6f 72 20 63 6f 64 65 20 77 69 6c 6c 20 62 65 20  or code will be 
85b0: 72 65 74 75 72 6e 65 64 20 69 6e 20 74 68 69 73  returned in this
85c0: 20 63 61 73 65 2e 0a 20 20 2a 2f 0a 20 20 69 66   case..  */.  if
85d0: 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20  ( rc==SQLITE_OK 
85e0: 29 7b 0a 20 20 20 20 2a 70 61 7a 43 6f 6c 20 3d  ){.    *pazCol =
85f0: 20 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 2a 29   (const char **)
8600: 61 7a 43 6f 6c 3b 0a 20 20 20 20 2a 70 61 62 50  azCol;.    *pabP
8610: 4b 20 3d 20 61 62 50 4b 3b 0a 20 20 20 20 2a 70  K = abPK;.    *p
8620: 6e 43 6f 6c 20 3d 20 6e 44 62 43 6f 6c 3b 0a 20  nCol = nDbCol;. 
8630: 20 7d 65 6c 73 65 7b 0a 20 20 20 20 2a 70 61 7a   }else{.    *paz
8640: 43 6f 6c 20 3d 20 30 3b 0a 20 20 20 20 2a 70 61  Col = 0;.    *pa
8650: 62 50 4b 20 3d 20 30 3b 0a 20 20 20 20 2a 70 6e  bPK = 0;.    *pn
8660: 43 6f 6c 20 3d 20 30 3b 0a 20 20 20 20 69 66 28  Col = 0;.    if(
8670: 20 70 7a 54 61 62 20 29 20 2a 70 7a 54 61 62 20   pzTab ) *pzTab 
8680: 3d 20 30 3b 0a 20 20 20 20 73 71 6c 69 74 65 33  = 0;.    sqlite3
8690: 5f 66 72 65 65 28 61 7a 43 6f 6c 29 3b 0a 20 20  _free(azCol);.  
86a0: 7d 0a 20 20 73 71 6c 69 74 65 33 5f 66 69 6e 61  }.  sqlite3_fina
86b0: 6c 69 7a 65 28 70 53 74 6d 74 29 3b 0a 20 20 72  lize(pStmt);.  r
86c0: 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a  eturn rc;.}../*.
86d0: 2a 2a 20 54 68 69 73 20 66 75 6e 63 74 69 6f 6e  ** This function
86e0: 20 69 73 20 6f 6e 6c 79 20 63 61 6c 6c 65 64 20   is only called 
86f0: 66 72 6f 6d 20 77 69 74 68 69 6e 20 61 20 70 72  from within a pr
8700: 65 2d 75 70 64 61 74 65 20 68 61 6e 64 6c 65 72  e-update handler
8710: 20 66 6f 72 20 61 0a 2a 2a 20 77 72 69 74 65 20   for a.** write 
8720: 74 6f 20 74 61 62 6c 65 20 70 54 61 62 2c 20 70  to table pTab, p
8730: 61 72 74 20 6f 66 20 73 65 73 73 69 6f 6e 20 70  art of session p
8740: 53 65 73 73 69 6f 6e 2e 20 49 66 20 74 68 69 73  Session. If this
8750: 20 69 73 20 74 68 65 20 66 69 72 73 74 0a 2a 2a   is the first.**
8760: 20 77 72 69 74 65 20 74 6f 20 74 68 69 73 20 74   write to this t
8770: 61 62 6c 65 2c 20 69 6e 69 74 61 6c 69 7a 65 20  able, initalize 
8780: 74 68 65 20 53 65 73 73 69 6f 6e 54 61 62 6c 65  the SessionTable
8790: 2e 6e 43 6f 6c 2c 20 61 7a 43 6f 6c 5b 5d 20 61  .nCol, azCol[] a
87a0: 6e 64 0a 2a 2a 20 61 62 50 4b 5b 5d 20 61 72 72  nd.** abPK[] arr
87b0: 61 79 73 20 61 63 63 6f 72 64 69 6e 67 6c 79 2e  ays accordingly.
87c0: 0a 2a 2a 0a 2a 2a 20 49 66 20 61 6e 20 65 72 72  .**.** If an err
87d0: 6f 72 20 6f 63 63 75 72 73 2c 20 61 6e 20 65 72  or occurs, an er
87e0: 72 6f 72 20 63 6f 64 65 20 69 73 20 73 74 6f 72  ror code is stor
87f0: 65 64 20 69 6e 20 73 71 6c 69 74 65 33 5f 73 65  ed in sqlite3_se
8800: 73 73 69 6f 6e 2e 72 63 20 61 6e 64 0a 2a 2a 20  ssion.rc and.** 
8810: 6e 6f 6e 2d 7a 65 72 6f 20 72 65 74 75 72 6e 65  non-zero returne
8820: 64 2e 20 4f 72 2c 20 69 66 20 6e 6f 20 65 72 72  d. Or, if no err
8830: 6f 72 20 6f 63 63 75 72 73 20 62 75 74 20 74 68  or occurs but th
8840: 65 20 74 61 62 6c 65 20 68 61 73 20 6e 6f 20 70  e table has no p
8850: 72 69 6d 61 72 79 0a 2a 2a 20 6b 65 79 2c 20 73  rimary.** key, s
8860: 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 2e 72  qlite3_session.r
8870: 63 20 69 73 20 6c 65 66 74 20 73 65 74 20 74 6f  c is left set to
8880: 20 53 51 4c 49 54 45 5f 4f 4b 20 61 6e 64 20 6e   SQLITE_OK and n
8890: 6f 6e 2d 7a 65 72 6f 20 72 65 74 75 72 6e 65 64  on-zero returned
88a0: 20 74 6f 0a 2a 2a 20 69 6e 64 69 63 61 74 65 20   to.** indicate 
88b0: 74 68 61 74 20 75 70 64 61 74 65 73 20 6f 6e 20  that updates on 
88c0: 74 68 69 73 20 74 61 62 6c 65 20 73 68 6f 75 6c  this table shoul
88d0: 64 20 62 65 20 69 67 6e 6f 72 65 64 2e 20 53 65  d be ignored. Se
88e0: 73 73 69 6f 6e 54 61 62 6c 65 2e 61 62 50 4b 20  ssionTable.abPK 
88f0: 0a 2a 2a 20 69 73 20 73 65 74 20 74 6f 20 4e 55  .** is set to NU
8900: 4c 4c 20 69 6e 20 74 68 69 73 20 63 61 73 65 2e  LL in this case.
8910: 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73  .*/.static int s
8920: 65 73 73 69 6f 6e 49 6e 69 74 54 61 62 6c 65 28  essionInitTable(
8930: 73 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20  sqlite3_session 
8940: 2a 70 53 65 73 73 69 6f 6e 2c 20 53 65 73 73 69  *pSession, Sessi
8950: 6f 6e 54 61 62 6c 65 20 2a 70 54 61 62 29 7b 0a  onTable *pTab){.
8960: 20 20 69 66 28 20 70 54 61 62 2d 3e 6e 43 6f 6c    if( pTab->nCol
8970: 3d 3d 30 20 29 7b 0a 20 20 20 20 75 38 20 2a 61  ==0 ){.    u8 *a
8980: 62 50 4b 3b 0a 20 20 20 20 61 73 73 65 72 74 28  bPK;.    assert(
8990: 20 70 54 61 62 2d 3e 61 7a 43 6f 6c 3d 3d 30 20   pTab->azCol==0 
89a0: 7c 7c 20 70 54 61 62 2d 3e 61 62 50 4b 3d 3d 30  || pTab->abPK==0
89b0: 20 29 3b 0a 20 20 20 20 70 53 65 73 73 69 6f 6e   );.    pSession
89c0: 2d 3e 72 63 20 3d 20 73 65 73 73 69 6f 6e 54 61  ->rc = sessionTa
89d0: 62 6c 65 49 6e 66 6f 28 70 53 65 73 73 69 6f 6e  bleInfo(pSession
89e0: 2d 3e 64 62 2c 20 70 53 65 73 73 69 6f 6e 2d 3e  ->db, pSession->
89f0: 7a 44 62 2c 20 0a 20 20 20 20 20 20 20 20 70 54  zDb, .        pT
8a00: 61 62 2d 3e 7a 4e 61 6d 65 2c 20 26 70 54 61 62  ab->zName, &pTab
8a10: 2d 3e 6e 43 6f 6c 2c 20 30 2c 20 26 70 54 61 62  ->nCol, 0, &pTab
8a20: 2d 3e 61 7a 43 6f 6c 2c 20 26 61 62 50 4b 0a 20  ->azCol, &abPK. 
8a30: 20 20 20 29 3b 0a 20 20 20 20 69 66 28 20 70 53     );.    if( pS
8a40: 65 73 73 69 6f 6e 2d 3e 72 63 3d 3d 53 51 4c 49  ession->rc==SQLI
8a50: 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 20 20 69  TE_OK ){.      i
8a60: 6e 74 20 69 3b 0a 20 20 20 20 20 20 66 6f 72 28  nt i;.      for(
8a70: 69 3d 30 3b 20 69 3c 70 54 61 62 2d 3e 6e 43 6f  i=0; i<pTab->nCo
8a80: 6c 3b 20 69 2b 2b 29 7b 0a 20 20 20 20 20 20 20  l; i++){.       
8a90: 20 69 66 28 20 61 62 50 4b 5b 69 5d 20 29 7b 0a   if( abPK[i] ){.
8aa0: 20 20 20 20 20 20 20 20 20 20 70 54 61 62 2d 3e            pTab->
8ab0: 61 62 50 4b 20 3d 20 61 62 50 4b 3b 0a 20 20 20  abPK = abPK;.   
8ac0: 20 20 20 20 20 20 20 62 72 65 61 6b 3b 0a 20 20         break;.  
8ad0: 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 7d 0a        }.      }.
8ae0: 20 20 20 20 7d 0a 20 20 7d 0a 20 20 72 65 74 75      }.  }.  retu
8af0: 72 6e 20 28 70 53 65 73 73 69 6f 6e 2d 3e 72 63  rn (pSession->rc
8b00: 20 7c 7c 20 70 54 61 62 2d 3e 61 62 50 4b 3d 3d   || pTab->abPK==
8b10: 30 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68 69  0);.}../*.** Thi
8b20: 73 20 66 75 6e 63 74 69 6f 6e 20 69 73 20 6f 6e  s function is on
8b30: 6c 79 20 63 61 6c 6c 65 64 20 66 72 6f 6d 20 77  ly called from w
8b40: 69 74 68 20 61 20 70 72 65 2d 75 70 64 61 74 65  ith a pre-update
8b50: 2d 68 6f 6f 6b 20 72 65 70 6f 72 74 69 6e 67 20  -hook reporting 
8b60: 61 20 0a 2a 2a 20 63 68 61 6e 67 65 20 6f 6e 20  a .** change on 
8b70: 74 61 62 6c 65 20 70 54 61 62 20 28 61 74 74 61  table pTab (atta
8b80: 63 68 65 64 20 74 6f 20 73 65 73 73 69 6f 6e 20  ched to session 
8b90: 70 53 65 73 73 69 6f 6e 29 2e 20 54 68 65 20 74  pSession). The t
8ba0: 79 70 65 20 6f 66 20 63 68 61 6e 67 65 0a 2a 2a  ype of change.**
8bb0: 20 28 55 50 44 41 54 45 2c 20 49 4e 53 45 52 54   (UPDATE, INSERT
8bc0: 2c 20 44 45 4c 45 54 45 29 20 69 73 20 73 70 65  , DELETE) is spe
8bd0: 63 69 66 69 65 64 20 62 79 20 74 68 65 20 66 69  cified by the fi
8be0: 72 73 74 20 61 72 67 75 6d 65 6e 74 2e 0a 2a 2a  rst argument..**
8bf0: 0a 2a 2a 20 55 6e 6c 65 73 73 20 6f 6e 65 20 69  .** Unless one i
8c00: 73 20 61 6c 72 65 61 64 79 20 70 72 65 73 65 6e  s already presen
8c10: 74 20 6f 72 20 61 6e 20 65 72 72 6f 72 20 6f 63  t or an error oc
8c20: 63 75 72 73 2c 20 61 6e 20 65 6e 74 72 79 20 69  curs, an entry i
8c30: 73 20 61 64 64 65 64 0a 2a 2a 20 74 6f 20 74 68  s added.** to th
8c40: 65 20 63 68 61 6e 67 65 64 2d 72 6f 77 73 20 68  e changed-rows h
8c50: 61 73 68 20 74 61 62 6c 65 20 61 73 73 6f 63 69  ash table associ
8c60: 61 74 65 64 20 77 69 74 68 20 74 61 62 6c 65 20  ated with table 
8c70: 70 54 61 62 2e 0a 2a 2f 0a 73 74 61 74 69 63 20  pTab..*/.static 
8c80: 76 6f 69 64 20 73 65 73 73 69 6f 6e 50 72 65 75  void sessionPreu
8c90: 70 64 61 74 65 4f 6e 65 43 68 61 6e 67 65 28 0a  pdateOneChange(.
8ca0: 20 20 69 6e 74 20 6f 70 2c 20 20 20 20 20 20 20    int op,       
8cb0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
8cc0: 20 20 2f 2a 20 4f 6e 65 20 6f 66 20 53 51 4c 49    /* One of SQLI
8cd0: 54 45 5f 55 50 44 41 54 45 2c 20 49 4e 53 45 52  TE_UPDATE, INSER
8ce0: 54 2c 20 44 45 4c 45 54 45 20 2a 2f 0a 20 20 73  T, DELETE */.  s
8cf0: 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a  qlite3_session *
8d00: 70 53 65 73 73 69 6f 6e 2c 20 20 20 20 20 20 2f  pSession,      /
8d10: 2a 20 53 65 73 73 69 6f 6e 20 6f 62 6a 65 63 74  * Session object
8d20: 20 70 54 61 62 20 69 73 20 61 74 74 61 63 68 65   pTab is attache
8d30: 64 20 74 6f 20 2a 2f 0a 20 20 53 65 73 73 69 6f  d to */.  Sessio
8d40: 6e 54 61 62 6c 65 20 2a 70 54 61 62 20 20 20 20  nTable *pTab    
8d50: 20 20 20 20 20 20 20 20 20 20 2f 2a 20 54 61 62            /* Tab
8d60: 6c 65 20 74 68 61 74 20 63 68 61 6e 67 65 20 61  le that change a
8d70: 70 70 6c 69 65 73 20 74 6f 20 2a 2f 0a 29 7b 0a  pplies to */.){.
8d80: 20 20 69 6e 74 20 69 48 61 73 68 3b 20 0a 20 20    int iHash; .  
8d90: 69 6e 74 20 62 4e 75 6c 6c 20 3d 20 30 3b 20 0a  int bNull = 0; .
8da0: 20 20 69 6e 74 20 72 63 20 3d 20 53 51 4c 49 54    int rc = SQLIT
8db0: 45 5f 4f 4b 3b 0a 0a 20 20 69 66 28 20 70 53 65  E_OK;..  if( pSe
8dc0: 73 73 69 6f 6e 2d 3e 72 63 20 29 20 72 65 74 75  ssion->rc ) retu
8dd0: 72 6e 3b 0a 0a 20 20 2f 2a 20 4c 6f 61 64 20 74  rn;..  /* Load t
8de0: 61 62 6c 65 20 64 65 74 61 69 6c 73 20 69 66 20  able details if 
8df0: 72 65 71 75 69 72 65 64 20 2a 2f 0a 20 20 69 66  required */.  if
8e00: 28 20 73 65 73 73 69 6f 6e 49 6e 69 74 54 61 62  ( sessionInitTab
8e10: 6c 65 28 70 53 65 73 73 69 6f 6e 2c 20 70 54 61  le(pSession, pTa
8e20: 62 29 20 29 20 72 65 74 75 72 6e 3b 0a 0a 20 20  b) ) return;..  
8e30: 2f 2a 20 43 68 65 63 6b 20 74 68 65 20 6e 75 6d  /* Check the num
8e40: 62 65 72 20 6f 66 20 63 6f 6c 75 6d 6e 73 20 69  ber of columns i
8e50: 6e 20 74 68 69 73 20 78 50 72 65 55 70 64 61 74  n this xPreUpdat
8e60: 65 20 63 61 6c 6c 20 6d 61 74 63 68 65 73 20 74  e call matches t
8e70: 68 65 20 0a 20 20 2a 2a 20 6e 75 6d 62 65 72 20  he .  ** number 
8e80: 6f 66 20 63 6f 6c 75 6d 6e 73 20 69 6e 20 74 68  of columns in th
8e90: 65 20 74 61 62 6c 65 2e 20 20 2a 2f 0a 20 20 69  e table.  */.  i
8ea0: 66 28 20 70 54 61 62 2d 3e 6e 43 6f 6c 21 3d 70  f( pTab->nCol!=p
8eb0: 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 78 43  Session->hook.xC
8ec0: 6f 75 6e 74 28 70 53 65 73 73 69 6f 6e 2d 3e 68  ount(pSession->h
8ed0: 6f 6f 6b 2e 70 43 74 78 29 20 29 7b 0a 20 20 20  ook.pCtx) ){.   
8ee0: 20 70 53 65 73 73 69 6f 6e 2d 3e 72 63 20 3d 20   pSession->rc = 
8ef0: 53 51 4c 49 54 45 5f 53 43 48 45 4d 41 3b 0a 20  SQLITE_SCHEMA;. 
8f00: 20 20 20 72 65 74 75 72 6e 3b 0a 20 20 7d 0a 0a     return;.  }..
8f10: 20 20 2f 2a 20 47 72 6f 77 20 74 68 65 20 68 61    /* Grow the ha
8f20: 73 68 20 74 61 62 6c 65 20 69 66 20 72 65 71 75  sh table if requ
8f30: 69 72 65 64 20 2a 2f 0a 20 20 69 66 28 20 73 65  ired */.  if( se
8f40: 73 73 69 6f 6e 47 72 6f 77 48 61 73 68 28 30 2c  ssionGrowHash(0,
8f50: 20 70 54 61 62 29 20 29 7b 0a 20 20 20 20 70 53   pTab) ){.    pS
8f60: 65 73 73 69 6f 6e 2d 3e 72 63 20 3d 20 53 51 4c  ession->rc = SQL
8f70: 49 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 20 20 72  ITE_NOMEM;.    r
8f80: 65 74 75 72 6e 3b 0a 20 20 7d 0a 0a 20 20 2f 2a  eturn;.  }..  /*
8f90: 20 43 61 6c 63 75 6c 61 74 65 20 74 68 65 20 68   Calculate the h
8fa0: 61 73 68 2d 6b 65 79 20 66 6f 72 20 74 68 69 73  ash-key for this
8fb0: 20 63 68 61 6e 67 65 2e 20 49 66 20 74 68 65 20   change. If the 
8fc0: 70 72 69 6d 61 72 79 20 6b 65 79 20 6f 66 20 74  primary key of t
8fd0: 68 65 20 72 6f 77 0a 20 20 2a 2a 20 69 6e 63 6c  he row.  ** incl
8fe0: 75 64 65 73 20 61 20 4e 55 4c 4c 20 76 61 6c 75  udes a NULL valu
8ff0: 65 2c 20 65 78 69 74 20 65 61 72 6c 79 2e 20 53  e, exit early. S
9000: 75 63 68 20 63 68 61 6e 67 65 73 20 61 72 65 20  uch changes are 
9010: 69 67 6e 6f 72 65 64 20 62 79 20 74 68 65 0a 20  ignored by the. 
9020: 20 2a 2a 20 73 65 73 73 69 6f 6e 20 6d 6f 64 75   ** session modu
9030: 6c 65 2e 20 2a 2f 0a 20 20 72 63 20 3d 20 73 65  le. */.  rc = se
9040: 73 73 69 6f 6e 50 72 65 75 70 64 61 74 65 48 61  ssionPreupdateHa
9050: 73 68 28 70 53 65 73 73 69 6f 6e 2c 20 70 54 61  sh(pSession, pTa
9060: 62 2c 20 6f 70 3d 3d 53 51 4c 49 54 45 5f 49 4e  b, op==SQLITE_IN
9070: 53 45 52 54 2c 20 26 69 48 61 73 68 2c 20 26 62  SERT, &iHash, &b
9080: 4e 75 6c 6c 29 3b 0a 20 20 69 66 28 20 72 63 21  Null);.  if( rc!
9090: 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 20 67 6f 74  =SQLITE_OK ) got
90a0: 6f 20 65 72 72 6f 72 5f 6f 75 74 3b 0a 0a 20 20  o error_out;..  
90b0: 69 66 28 20 62 4e 75 6c 6c 3d 3d 30 20 29 7b 0a  if( bNull==0 ){.
90c0: 20 20 20 20 2f 2a 20 53 65 61 72 63 68 20 74 68      /* Search th
90d0: 65 20 68 61 73 68 20 74 61 62 6c 65 20 66 6f 72  e hash table for
90e0: 20 61 6e 20 65 78 69 73 74 69 6e 67 20 72 65 63   an existing rec
90f0: 6f 72 64 20 66 6f 72 20 74 68 69 73 20 72 6f 77  ord for this row
9100: 2e 20 2a 2f 0a 20 20 20 20 53 65 73 73 69 6f 6e  . */.    Session
9110: 43 68 61 6e 67 65 20 2a 70 43 3b 0a 20 20 20 20  Change *pC;.    
9120: 66 6f 72 28 70 43 3d 70 54 61 62 2d 3e 61 70 43  for(pC=pTab->apC
9130: 68 61 6e 67 65 5b 69 48 61 73 68 5d 3b 20 70 43  hange[iHash]; pC
9140: 3b 20 70 43 3d 70 43 2d 3e 70 4e 65 78 74 29 7b  ; pC=pC->pNext){
9150: 0a 20 20 20 20 20 20 69 66 28 20 73 65 73 73 69  .      if( sessi
9160: 6f 6e 50 72 65 75 70 64 61 74 65 45 71 75 61 6c  onPreupdateEqual
9170: 28 70 53 65 73 73 69 6f 6e 2c 20 70 54 61 62 2c  (pSession, pTab,
9180: 20 70 43 2c 20 6f 70 29 20 29 20 62 72 65 61 6b   pC, op) ) break
9190: 3b 0a 20 20 20 20 7d 0a 0a 20 20 20 20 69 66 28  ;.    }..    if(
91a0: 20 70 43 3d 3d 30 20 29 7b 0a 20 20 20 20 20 20   pC==0 ){.      
91b0: 2f 2a 20 43 72 65 61 74 65 20 61 20 6e 65 77 20  /* Create a new 
91c0: 63 68 61 6e 67 65 20 6f 62 6a 65 63 74 20 63 6f  change object co
91d0: 6e 74 61 69 6e 69 6e 67 20 61 6c 6c 20 74 68 65  ntaining all the
91e0: 20 6f 6c 64 20 76 61 6c 75 65 73 20 28 69 66 0a   old values (if.
91f0: 20 20 20 20 20 20 2a 2a 20 74 68 69 73 20 69 73        ** this is
9200: 20 61 6e 20 53 51 4c 49 54 45 5f 55 50 44 41 54   an SQLITE_UPDAT
9210: 45 20 6f 72 20 53 51 4c 49 54 45 5f 44 45 4c 45  E or SQLITE_DELE
9220: 54 45 29 2c 20 6f 72 20 6a 75 73 74 20 74 68 65  TE), or just the
9230: 20 50 4b 0a 20 20 20 20 20 20 2a 2a 20 76 61 6c   PK.      ** val
9240: 75 65 73 20 28 69 66 20 74 68 69 73 20 69 73 20  ues (if this is 
9250: 61 6e 20 49 4e 53 45 52 54 29 2e 20 2a 2f 0a 20  an INSERT). */. 
9260: 20 20 20 20 20 53 65 73 73 69 6f 6e 43 68 61 6e       SessionChan
9270: 67 65 20 2a 70 43 68 61 6e 67 65 3b 20 2f 2a 20  ge *pChange; /* 
9280: 4e 65 77 20 63 68 61 6e 67 65 20 6f 62 6a 65 63  New change objec
9290: 74 20 2a 2f 0a 20 20 20 20 20 20 69 6e 74 20 6e  t */.      int n
92a0: 42 79 74 65 3b 20 20 20 20 20 20 20 20 20 20 20  Byte;           
92b0: 20 20 20 2f 2a 20 4e 75 6d 62 65 72 20 6f 66 20     /* Number of 
92c0: 62 79 74 65 73 20 74 6f 20 61 6c 6c 6f 63 61 74  bytes to allocat
92d0: 65 20 2a 2f 0a 20 20 20 20 20 20 69 6e 74 20 69  e */.      int i
92e0: 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  ;               
92f0: 20 20 20 2f 2a 20 55 73 65 64 20 74 6f 20 69 74     /* Used to it
9300: 65 72 61 74 65 20 74 68 72 6f 75 67 68 20 63 6f  erate through co
9310: 6c 75 6d 6e 73 20 2a 2f 0a 20 20 0a 20 20 20 20  lumns */.  .    
9320: 20 20 61 73 73 65 72 74 28 20 72 63 3d 3d 53 51    assert( rc==SQ
9330: 4c 49 54 45 5f 4f 4b 20 29 3b 0a 20 20 20 20 20  LITE_OK );.     
9340: 20 70 54 61 62 2d 3e 6e 45 6e 74 72 79 2b 2b 3b   pTab->nEntry++;
9350: 0a 20 20 0a 20 20 20 20 20 20 2f 2a 20 46 69 67  .  .      /* Fig
9360: 75 72 65 20 6f 75 74 20 68 6f 77 20 6c 61 72 67  ure out how larg
9370: 65 20 61 6e 20 61 6c 6c 6f 63 61 74 69 6f 6e 20  e an allocation 
9380: 69 73 20 72 65 71 75 69 72 65 64 20 2a 2f 0a 20  is required */. 
9390: 20 20 20 20 20 6e 42 79 74 65 20 3d 20 73 69 7a       nByte = siz
93a0: 65 6f 66 28 53 65 73 73 69 6f 6e 43 68 61 6e 67  eof(SessionChang
93b0: 65 29 3b 0a 20 20 20 20 20 20 66 6f 72 28 69 3d  e);.      for(i=
93c0: 30 3b 20 69 3c 70 54 61 62 2d 3e 6e 43 6f 6c 3b  0; i<pTab->nCol;
93d0: 20 69 2b 2b 29 7b 0a 20 20 20 20 20 20 20 20 73   i++){.        s
93e0: 71 6c 69 74 65 33 5f 76 61 6c 75 65 20 2a 70 20  qlite3_value *p 
93f0: 3d 20 30 3b 0a 20 20 20 20 20 20 20 20 69 66 28  = 0;.        if(
9400: 20 6f 70 21 3d 53 51 4c 49 54 45 5f 49 4e 53 45   op!=SQLITE_INSE
9410: 52 54 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20  RT ){.          
9420: 54 45 53 54 4f 4e 4c 59 28 69 6e 74 20 74 72 63  TESTONLY(int trc
9430: 20 3d 20 29 20 70 53 65 73 73 69 6f 6e 2d 3e 68   = ) pSession->h
9440: 6f 6f 6b 2e 78 4f 6c 64 28 70 53 65 73 73 69 6f  ook.xOld(pSessio
9450: 6e 2d 3e 68 6f 6f 6b 2e 70 43 74 78 2c 20 69 2c  n->hook.pCtx, i,
9460: 20 26 70 29 3b 0a 20 20 20 20 20 20 20 20 20 20   &p);.          
9470: 61 73 73 65 72 74 28 20 74 72 63 3d 3d 53 51 4c  assert( trc==SQL
9480: 49 54 45 5f 4f 4b 20 29 3b 0a 20 20 20 20 20 20  ITE_OK );.      
9490: 20 20 7d 65 6c 73 65 20 69 66 28 20 70 54 61 62    }else if( pTab
94a0: 2d 3e 61 62 50 4b 5b 69 5d 20 29 7b 0a 20 20 20  ->abPK[i] ){.   
94b0: 20 20 20 20 20 20 20 54 45 53 54 4f 4e 4c 59 28         TESTONLY(
94c0: 69 6e 74 20 74 72 63 20 3d 20 29 20 70 53 65 73  int trc = ) pSes
94d0: 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 78 4e 65 77 28  sion->hook.xNew(
94e0: 70 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 70  pSession->hook.p
94f0: 43 74 78 2c 20 69 2c 20 26 70 29 3b 0a 20 20 20  Ctx, i, &p);.   
9500: 20 20 20 20 20 20 20 61 73 73 65 72 74 28 20 74         assert( t
9510: 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 3b  rc==SQLITE_OK );
9520: 0a 20 20 20 20 20 20 20 20 7d 0a 0a 20 20 20 20  .        }..    
9530: 20 20 20 20 2f 2a 20 54 68 69 73 20 6d 61 79 20      /* This may 
9540: 66 61 69 6c 20 69 66 20 53 51 4c 69 74 65 20 76  fail if SQLite v
9550: 61 6c 75 65 20 70 20 63 6f 6e 74 61 69 6e 73 20  alue p contains 
9560: 61 20 75 74 66 2d 31 36 20 73 74 72 69 6e 67 20  a utf-16 string 
9570: 74 68 61 74 20 6d 75 73 74 0a 20 20 20 20 20 20  that must.      
9580: 20 20 2a 2a 20 62 65 20 63 6f 6e 76 65 72 74 65    ** be converte
9590: 64 20 74 6f 20 75 74 66 2d 38 20 61 6e 64 20 61  d to utf-8 and a
95a0: 6e 20 4f 4f 4d 20 65 72 72 6f 72 20 6f 63 63 75  n OOM error occu
95b0: 72 73 20 77 68 69 6c 65 20 64 6f 69 6e 67 20 73  rs while doing s
95c0: 6f 2e 20 2a 2f 0a 20 20 20 20 20 20 20 20 72 63  o. */.        rc
95d0: 20 3d 20 73 65 73 73 69 6f 6e 53 65 72 69 61 6c   = sessionSerial
95e0: 69 7a 65 56 61 6c 75 65 28 30 2c 20 70 2c 20 26  izeValue(0, p, &
95f0: 6e 42 79 74 65 29 3b 0a 20 20 20 20 20 20 20 20  nByte);.        
9600: 69 66 28 20 72 63 21 3d 53 51 4c 49 54 45 5f 4f  if( rc!=SQLITE_O
9610: 4b 20 29 20 67 6f 74 6f 20 65 72 72 6f 72 5f 6f  K ) goto error_o
9620: 75 74 3b 0a 20 20 20 20 20 20 7d 0a 20 20 0a 20  ut;.      }.  . 
9630: 20 20 20 20 20 2f 2a 20 41 6c 6c 6f 63 61 74 65       /* Allocate
9640: 20 74 68 65 20 63 68 61 6e 67 65 20 6f 62 6a 65   the change obje
9650: 63 74 20 2a 2f 0a 20 20 20 20 20 20 70 43 68 61  ct */.      pCha
9660: 6e 67 65 20 3d 20 28 53 65 73 73 69 6f 6e 43 68  nge = (SessionCh
9670: 61 6e 67 65 20 2a 29 73 71 6c 69 74 65 33 5f 6d  ange *)sqlite3_m
9680: 61 6c 6c 6f 63 28 6e 42 79 74 65 29 3b 0a 20 20  alloc(nByte);.  
9690: 20 20 20 20 69 66 28 20 21 70 43 68 61 6e 67 65      if( !pChange
96a0: 20 29 7b 0a 20 20 20 20 20 20 20 20 72 63 20 3d   ){.        rc =
96b0: 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 3b 0a 20   SQLITE_NOMEM;. 
96c0: 20 20 20 20 20 20 20 67 6f 74 6f 20 65 72 72 6f         goto erro
96d0: 72 5f 6f 75 74 3b 0a 20 20 20 20 20 20 7d 65 6c  r_out;.      }el
96e0: 73 65 7b 0a 20 20 20 20 20 20 20 20 6d 65 6d 73  se{.        mems
96f0: 65 74 28 70 43 68 61 6e 67 65 2c 20 30 2c 20 73  et(pChange, 0, s
9700: 69 7a 65 6f 66 28 53 65 73 73 69 6f 6e 43 68 61  izeof(SessionCha
9710: 6e 67 65 29 29 3b 0a 20 20 20 20 20 20 20 20 70  nge));.        p
9720: 43 68 61 6e 67 65 2d 3e 61 52 65 63 6f 72 64 20  Change->aRecord 
9730: 3d 20 28 75 38 20 2a 29 26 70 43 68 61 6e 67 65  = (u8 *)&pChange
9740: 5b 31 5d 3b 0a 20 20 20 20 20 20 7d 0a 20 20 0a  [1];.      }.  .
9750: 20 20 20 20 20 20 2f 2a 20 50 6f 70 75 6c 61 74        /* Populat
9760: 65 20 74 68 65 20 63 68 61 6e 67 65 20 6f 62 6a  e the change obj
9770: 65 63 74 2e 20 4e 6f 6e 65 20 6f 66 20 74 68 65  ect. None of the
9780: 20 70 72 65 75 70 64 61 74 65 5f 6f 6c 64 28 29   preupdate_old()
9790: 2c 0a 20 20 20 20 20 20 2a 2a 20 70 72 65 75 70  ,.      ** preup
97a0: 64 61 74 65 5f 6e 65 77 28 29 20 6f 72 20 53 65  date_new() or Se
97b0: 72 69 61 6c 69 7a 65 56 61 6c 75 65 28 29 20 63  rializeValue() c
97c0: 61 6c 6c 73 20 62 65 6c 6f 77 20 6d 61 79 20 66  alls below may f
97d0: 61 69 6c 20 61 73 20 61 6c 6c 0a 20 20 20 20 20  ail as all.     
97e0: 20 2a 2a 20 72 65 71 75 69 72 65 64 20 76 61 6c   ** required val
97f0: 75 65 73 20 61 6e 64 20 65 6e 63 6f 64 69 6e 67  ues and encoding
9800: 73 20 68 61 76 65 20 61 6c 72 65 61 64 79 20 62  s have already b
9810: 65 65 6e 20 63 61 63 68 65 64 20 69 6e 20 6d 65  een cached in me
9820: 6d 6f 72 79 2e 0a 20 20 20 20 20 20 2a 2a 20 49  mory..      ** I
9830: 74 20 69 73 20 6e 6f 74 20 70 6f 73 73 69 62 6c  t is not possibl
9840: 65 20 66 6f 72 20 61 6e 20 4f 4f 4d 20 74 6f 20  e for an OOM to 
9850: 6f 63 63 75 72 20 69 6e 20 74 68 69 73 20 62 6c  occur in this bl
9860: 6f 63 6b 2e 20 2a 2f 0a 20 20 20 20 20 20 6e 42  ock. */.      nB
9870: 79 74 65 20 3d 20 30 3b 0a 20 20 20 20 20 20 66  yte = 0;.      f
9880: 6f 72 28 69 3d 30 3b 20 69 3c 70 54 61 62 2d 3e  or(i=0; i<pTab->
9890: 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a 20 20 20 20  nCol; i++){.    
98a0: 20 20 20 20 73 71 6c 69 74 65 33 5f 76 61 6c 75      sqlite3_valu
98b0: 65 20 2a 70 20 3d 20 30 3b 0a 20 20 20 20 20 20  e *p = 0;.      
98c0: 20 20 69 66 28 20 6f 70 21 3d 53 51 4c 49 54 45    if( op!=SQLITE
98d0: 5f 49 4e 53 45 52 54 20 29 7b 0a 20 20 20 20 20  _INSERT ){.     
98e0: 20 20 20 20 20 70 53 65 73 73 69 6f 6e 2d 3e 68       pSession->h
98f0: 6f 6f 6b 2e 78 4f 6c 64 28 70 53 65 73 73 69 6f  ook.xOld(pSessio
9900: 6e 2d 3e 68 6f 6f 6b 2e 70 43 74 78 2c 20 69 2c  n->hook.pCtx, i,
9910: 20 26 70 29 3b 0a 20 20 20 20 20 20 20 20 7d 65   &p);.        }e
9920: 6c 73 65 20 69 66 28 20 70 54 61 62 2d 3e 61 62  lse if( pTab->ab
9930: 50 4b 5b 69 5d 20 29 7b 0a 20 20 20 20 20 20 20  PK[i] ){.       
9940: 20 20 20 70 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f     pSession->hoo
9950: 6b 2e 78 4e 65 77 28 70 53 65 73 73 69 6f 6e 2d  k.xNew(pSession-
9960: 3e 68 6f 6f 6b 2e 70 43 74 78 2c 20 69 2c 20 26  >hook.pCtx, i, &
9970: 70 29 3b 0a 20 20 20 20 20 20 20 20 7d 0a 20 20  p);.        }.  
9980: 20 20 20 20 20 20 73 65 73 73 69 6f 6e 53 65 72        sessionSer
9990: 69 61 6c 69 7a 65 56 61 6c 75 65 28 26 70 43 68  ializeValue(&pCh
99a0: 61 6e 67 65 2d 3e 61 52 65 63 6f 72 64 5b 6e 42  ange->aRecord[nB
99b0: 79 74 65 5d 2c 20 70 2c 20 26 6e 42 79 74 65 29  yte], p, &nByte)
99c0: 3b 0a 20 20 20 20 20 20 7d 0a 0a 20 20 20 20 20  ;.      }..     
99d0: 20 2f 2a 20 41 64 64 20 74 68 65 20 63 68 61 6e   /* Add the chan
99e0: 67 65 20 74 6f 20 74 68 65 20 68 61 73 68 2d 74  ge to the hash-t
99f0: 61 62 6c 65 20 2a 2f 0a 20 20 20 20 20 20 69 66  able */.      if
9a00: 28 20 70 53 65 73 73 69 6f 6e 2d 3e 62 49 6e 64  ( pSession->bInd
9a10: 69 72 65 63 74 20 7c 7c 20 70 53 65 73 73 69 6f  irect || pSessio
9a20: 6e 2d 3e 68 6f 6f 6b 2e 78 44 65 70 74 68 28 70  n->hook.xDepth(p
9a30: 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 70 43  Session->hook.pC
9a40: 74 78 29 20 29 7b 0a 20 20 20 20 20 20 20 20 70  tx) ){.        p
9a50: 43 68 61 6e 67 65 2d 3e 62 49 6e 64 69 72 65 63  Change->bIndirec
9a60: 74 20 3d 20 31 3b 0a 20 20 20 20 20 20 7d 0a 20  t = 1;.      }. 
9a70: 20 20 20 20 20 70 43 68 61 6e 67 65 2d 3e 6e 52       pChange->nR
9a80: 65 63 6f 72 64 20 3d 20 6e 42 79 74 65 3b 0a 20  ecord = nByte;. 
9a90: 20 20 20 20 20 70 43 68 61 6e 67 65 2d 3e 6f 70       pChange->op
9aa0: 20 3d 20 6f 70 3b 0a 20 20 20 20 20 20 70 43 68   = op;.      pCh
9ab0: 61 6e 67 65 2d 3e 70 4e 65 78 74 20 3d 20 70 54  ange->pNext = pT
9ac0: 61 62 2d 3e 61 70 43 68 61 6e 67 65 5b 69 48 61  ab->apChange[iHa
9ad0: 73 68 5d 3b 0a 20 20 20 20 20 20 70 54 61 62 2d  sh];.      pTab-
9ae0: 3e 61 70 43 68 61 6e 67 65 5b 69 48 61 73 68 5d  >apChange[iHash]
9af0: 20 3d 20 70 43 68 61 6e 67 65 3b 0a 0a 20 20 20   = pChange;..   
9b00: 20 7d 65 6c 73 65 20 69 66 28 20 70 43 2d 3e 62   }else if( pC->b
9b10: 49 6e 64 69 72 65 63 74 20 29 7b 0a 20 20 20 20  Indirect ){.    
9b20: 20 20 2f 2a 20 49 66 20 74 68 65 20 65 78 69 73    /* If the exis
9b30: 74 69 6e 67 20 63 68 61 6e 67 65 20 69 73 20 63  ting change is c
9b40: 6f 6e 73 69 64 65 72 65 64 20 22 69 6e 64 69 72  onsidered "indir
9b50: 65 63 74 22 2c 20 62 75 74 20 74 68 69 73 20 63  ect", but this c
9b60: 75 72 72 65 6e 74 0a 20 20 20 20 20 20 2a 2a 20  urrent.      ** 
9b70: 63 68 61 6e 67 65 20 69 73 20 22 64 69 72 65 63  change is "direc
9b80: 74 22 2c 20 6d 61 72 6b 20 74 68 65 20 63 68 61  t", mark the cha
9b90: 6e 67 65 20 6f 62 6a 65 63 74 20 61 73 20 64 69  nge object as di
9ba0: 72 65 63 74 2e 20 2a 2f 0a 20 20 20 20 20 20 69  rect. */.      i
9bb0: 66 28 20 70 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f  f( pSession->hoo
9bc0: 6b 2e 78 44 65 70 74 68 28 70 53 65 73 73 69 6f  k.xDepth(pSessio
9bd0: 6e 2d 3e 68 6f 6f 6b 2e 70 43 74 78 29 3d 3d 30  n->hook.pCtx)==0
9be0: 20 0a 20 20 20 20 20 20 20 26 26 20 70 53 65 73   .       && pSes
9bf0: 73 69 6f 6e 2d 3e 62 49 6e 64 69 72 65 63 74 3d  sion->bIndirect=
9c00: 3d 30 20 0a 20 20 20 20 20 20 29 7b 0a 20 20 20  =0 .      ){.   
9c10: 20 20 20 20 20 70 43 2d 3e 62 49 6e 64 69 72 65       pC->bIndire
9c20: 63 74 20 3d 20 30 3b 0a 20 20 20 20 20 20 7d 0a  ct = 0;.      }.
9c30: 20 20 20 20 7d 0a 20 20 7d 0a 0a 20 20 2f 2a 20      }.  }..  /* 
9c40: 49 66 20 61 6e 20 65 72 72 6f 72 20 68 61 73 20  If an error has 
9c50: 6f 63 63 75 72 72 65 64 2c 20 6d 61 72 6b 20 74  occurred, mark t
9c60: 68 65 20 73 65 73 73 69 6f 6e 20 6f 62 6a 65 63  he session objec
9c70: 74 20 61 73 20 66 61 69 6c 65 64 2e 20 2a 2f 0a  t as failed. */.
9c80: 20 65 72 72 6f 72 5f 6f 75 74 3a 0a 20 20 69 66   error_out:.  if
9c90: 28 20 72 63 21 3d 53 51 4c 49 54 45 5f 4f 4b 20  ( rc!=SQLITE_OK 
9ca0: 29 7b 0a 20 20 20 20 70 53 65 73 73 69 6f 6e 2d  ){.    pSession-
9cb0: 3e 72 63 20 3d 20 72 63 3b 0a 20 20 7d 0a 7d 0a  >rc = rc;.  }.}.
9cc0: 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73 73  .static int sess
9cd0: 69 6f 6e 46 69 6e 64 54 61 62 6c 65 28 0a 20 20  ionFindTable(.  
9ce0: 73 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20  sqlite3_session 
9cf0: 2a 70 53 65 73 73 69 6f 6e 2c 20 0a 20 20 63 6f  *pSession, .  co
9d00: 6e 73 74 20 63 68 61 72 20 2a 7a 4e 61 6d 65 2c  nst char *zName,
9d10: 0a 20 20 53 65 73 73 69 6f 6e 54 61 62 6c 65 20  .  SessionTable 
9d20: 2a 2a 70 70 54 61 62 0a 29 7b 0a 20 20 69 6e 74  **ppTab.){.  int
9d30: 20 72 63 20 3d 20 53 51 4c 49 54 45 5f 4f 4b 3b   rc = SQLITE_OK;
9d40: 0a 20 20 69 6e 74 20 6e 4e 61 6d 65 20 3d 20 73  .  int nName = s
9d50: 71 6c 69 74 65 33 53 74 72 6c 65 6e 33 30 28 7a  qlite3Strlen30(z
9d60: 4e 61 6d 65 29 3b 0a 20 20 53 65 73 73 69 6f 6e  Name);.  Session
9d70: 54 61 62 6c 65 20 2a 70 52 65 74 3b 0a 0a 20 20  Table *pRet;..  
9d80: 2f 2a 20 53 65 61 72 63 68 20 66 6f 72 20 61 6e  /* Search for an
9d90: 20 65 78 69 73 74 69 6e 67 20 74 61 62 6c 65 20   existing table 
9da0: 2a 2f 0a 20 20 66 6f 72 28 70 52 65 74 3d 70 53  */.  for(pRet=pS
9db0: 65 73 73 69 6f 6e 2d 3e 70 54 61 62 6c 65 3b 20  ession->pTable; 
9dc0: 70 52 65 74 3b 20 70 52 65 74 3d 70 52 65 74 2d  pRet; pRet=pRet-
9dd0: 3e 70 4e 65 78 74 29 7b 0a 20 20 20 20 69 66 28  >pNext){.    if(
9de0: 20 30 3d 3d 73 71 6c 69 74 65 33 5f 73 74 72 6e   0==sqlite3_strn
9df0: 69 63 6d 70 28 70 52 65 74 2d 3e 7a 4e 61 6d 65  icmp(pRet->zName
9e00: 2c 20 7a 4e 61 6d 65 2c 20 6e 4e 61 6d 65 2b 31  , zName, nName+1
9e10: 29 20 29 20 62 72 65 61 6b 3b 0a 20 20 7d 0a 0a  ) ) break;.  }..
9e20: 20 20 69 66 28 20 70 52 65 74 3d 3d 30 20 26 26    if( pRet==0 &&
9e30: 20 70 53 65 73 73 69 6f 6e 2d 3e 62 41 75 74 6f   pSession->bAuto
9e40: 41 74 74 61 63 68 20 29 7b 0a 20 20 20 20 2f 2a  Attach ){.    /*
9e50: 20 49 66 20 74 68 65 72 65 20 69 73 20 61 20 74   If there is a t
9e60: 61 62 6c 65 2d 66 69 6c 74 65 72 20 63 6f 6e 66  able-filter conf
9e70: 69 67 75 72 65 64 2c 20 69 6e 76 6f 6b 65 20 69  igured, invoke i
9e80: 74 2e 20 49 66 20 69 74 20 72 65 74 75 72 6e 73  t. If it returns
9e90: 20 30 2c 0a 20 20 20 20 2a 2a 20 64 6f 20 6e 6f   0,.    ** do no
9ea0: 74 20 61 75 74 6f 6d 61 74 69 63 61 6c 6c 79 20  t automatically 
9eb0: 61 64 64 20 74 68 65 20 6e 65 77 20 74 61 62 6c  add the new tabl
9ec0: 65 2e 20 2a 2f 0a 20 20 20 20 69 66 28 20 70 53  e. */.    if( pS
9ed0: 65 73 73 69 6f 6e 2d 3e 78 54 61 62 6c 65 46 69  ession->xTableFi
9ee0: 6c 74 65 72 3d 3d 30 0a 20 20 20 20 20 7c 7c 20  lter==0.     || 
9ef0: 70 53 65 73 73 69 6f 6e 2d 3e 78 54 61 62 6c 65  pSession->xTable
9f00: 46 69 6c 74 65 72 28 70 53 65 73 73 69 6f 6e 2d  Filter(pSession-
9f10: 3e 70 46 69 6c 74 65 72 43 74 78 2c 20 7a 4e 61  >pFilterCtx, zNa
9f20: 6d 65 29 20 0a 20 20 20 20 29 7b 0a 20 20 20 20  me) .    ){.    
9f30: 20 20 72 63 20 3d 20 73 71 6c 69 74 65 33 73 65    rc = sqlite3se
9f40: 73 73 69 6f 6e 5f 61 74 74 61 63 68 28 70 53 65  ssion_attach(pSe
9f50: 73 73 69 6f 6e 2c 20 7a 4e 61 6d 65 29 3b 0a 20  ssion, zName);. 
9f60: 20 20 20 20 20 69 66 28 20 72 63 3d 3d 53 51 4c       if( rc==SQL
9f70: 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 20 20  ITE_OK ){.      
9f80: 20 20 66 6f 72 28 70 52 65 74 3d 70 53 65 73 73    for(pRet=pSess
9f90: 69 6f 6e 2d 3e 70 54 61 62 6c 65 3b 20 70 52 65  ion->pTable; pRe
9fa0: 74 2d 3e 70 4e 65 78 74 3b 20 70 52 65 74 3d 70  t->pNext; pRet=p
9fb0: 52 65 74 2d 3e 70 4e 65 78 74 29 3b 0a 20 20 20  Ret->pNext);.   
9fc0: 20 20 20 20 20 61 73 73 65 72 74 28 20 30 3d 3d       assert( 0==
9fd0: 73 71 6c 69 74 65 33 5f 73 74 72 6e 69 63 6d 70  sqlite3_strnicmp
9fe0: 28 70 52 65 74 2d 3e 7a 4e 61 6d 65 2c 20 7a 4e  (pRet->zName, zN
9ff0: 61 6d 65 2c 20 6e 4e 61 6d 65 2b 31 29 20 29 3b  ame, nName+1) );
a000: 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 7d 0a 20  .      }.    }. 
a010: 20 7d 0a 0a 20 20 61 73 73 65 72 74 28 20 72 63   }..  assert( rc
a020: 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 7c 7c 20 70  ==SQLITE_OK || p
a030: 52 65 74 3d 3d 30 20 29 3b 0a 20 20 2a 70 70 54  Ret==0 );.  *ppT
a040: 61 62 20 3d 20 70 52 65 74 3b 0a 20 20 72 65 74  ab = pRet;.  ret
a050: 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a  urn rc;.}../*.**
a060: 20 54 68 65 20 27 70 72 65 2d 75 70 64 61 74 65   The 'pre-update
a070: 27 20 68 6f 6f 6b 20 72 65 67 69 73 74 65 72 65  ' hook registere
a080: 64 20 62 79 20 74 68 69 73 20 6d 6f 64 75 6c 65  d by this module
a090: 20 77 69 74 68 20 53 51 4c 69 74 65 20 64 61 74   with SQLite dat
a0a0: 61 62 61 73 65 73 2e 0a 2a 2f 0a 73 74 61 74 69  abases..*/.stati
a0b0: 63 20 76 6f 69 64 20 78 50 72 65 55 70 64 61 74  c void xPreUpdat
a0c0: 65 28 0a 20 20 76 6f 69 64 20 2a 70 43 74 78 2c  e(.  void *pCtx,
a0d0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
a0e0: 20 20 20 20 20 2f 2a 20 43 6f 70 79 20 6f 66 20       /* Copy of 
a0f0: 74 68 69 72 64 20 61 72 67 20 74 6f 20 70 72 65  third arg to pre
a100: 75 70 64 61 74 65 5f 68 6f 6f 6b 28 29 20 2a 2f  update_hook() */
a110: 0a 20 20 73 71 6c 69 74 65 33 20 2a 64 62 2c 20  .  sqlite3 *db, 
a120: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
a130: 20 20 20 2f 2a 20 44 61 74 61 62 61 73 65 20 68     /* Database h
a140: 61 6e 64 6c 65 20 2a 2f 0a 20 20 69 6e 74 20 6f  andle */.  int o
a150: 70 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20  p,              
a160: 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 53 51             /* SQ
a170: 4c 49 54 45 5f 55 50 44 41 54 45 2c 20 44 45 4c  LITE_UPDATE, DEL
a180: 45 54 45 20 6f 72 20 49 4e 53 45 52 54 20 2a 2f  ETE or INSERT */
a190: 0a 20 20 63 68 61 72 20 63 6f 6e 73 74 20 2a 7a  .  char const *z
a1a0: 44 62 2c 20 20 20 20 20 20 20 20 20 20 20 20 20  Db,             
a1b0: 20 20 20 2f 2a 20 44 61 74 61 62 61 73 65 20 6e     /* Database n
a1c0: 61 6d 65 20 2a 2f 0a 20 20 63 68 61 72 20 63 6f  ame */.  char co
a1d0: 6e 73 74 20 2a 7a 4e 61 6d 65 2c 20 20 20 20 20  nst *zName,     
a1e0: 20 20 20 20 20 20 20 20 20 2f 2a 20 54 61 62 6c           /* Tabl
a1f0: 65 20 6e 61 6d 65 20 2a 2f 0a 20 20 73 71 6c 69  e name */.  sqli
a200: 74 65 33 5f 69 6e 74 36 34 20 69 4b 65 79 31 2c  te3_int64 iKey1,
a210: 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 52              /* R
a220: 6f 77 69 64 20 6f 66 20 72 6f 77 20 61 62 6f 75  owid of row abou
a230: 74 20 74 6f 20 62 65 20 64 65 6c 65 74 65 64 2f  t to be deleted/
a240: 75 70 64 61 74 65 64 20 2a 2f 0a 20 20 73 71 6c  updated */.  sql
a250: 69 74 65 33 5f 69 6e 74 36 34 20 69 4b 65 79 32  ite3_int64 iKey2
a260: 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
a270: 4e 65 77 20 72 6f 77 69 64 20 76 61 6c 75 65 20  New rowid value 
a280: 28 66 6f 72 20 61 20 72 6f 77 69 64 20 55 50 44  (for a rowid UPD
a290: 41 54 45 29 20 2a 2f 0a 29 7b 0a 20 20 73 71 6c  ATE) */.){.  sql
a2a0: 69 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a 70 53  ite3_session *pS
a2b0: 65 73 73 69 6f 6e 3b 0a 20 20 69 6e 74 20 6e 44  ession;.  int nD
a2c0: 62 20 3d 20 73 71 6c 69 74 65 33 53 74 72 6c 65  b = sqlite3Strle
a2d0: 6e 33 30 28 7a 44 62 29 3b 0a 0a 20 20 61 73 73  n30(zDb);..  ass
a2e0: 65 72 74 28 20 73 71 6c 69 74 65 33 5f 6d 75 74  ert( sqlite3_mut
a2f0: 65 78 5f 68 65 6c 64 28 64 62 2d 3e 6d 75 74 65  ex_held(db->mute
a300: 78 29 20 29 3b 0a 0a 20 20 66 6f 72 28 70 53 65  x) );..  for(pSe
a310: 73 73 69 6f 6e 3d 28 73 71 6c 69 74 65 33 5f 73  ssion=(sqlite3_s
a320: 65 73 73 69 6f 6e 20 2a 29 70 43 74 78 3b 20 70  ession *)pCtx; p
a330: 53 65 73 73 69 6f 6e 3b 20 70 53 65 73 73 69 6f  Session; pSessio
a340: 6e 3d 70 53 65 73 73 69 6f 6e 2d 3e 70 4e 65 78  n=pSession->pNex
a350: 74 29 7b 0a 20 20 20 20 53 65 73 73 69 6f 6e 54  t){.    SessionT
a360: 61 62 6c 65 20 2a 70 54 61 62 3b 0a 0a 20 20 20  able *pTab;..   
a370: 20 2f 2a 20 49 66 20 74 68 69 73 20 73 65 73 73   /* If this sess
a380: 69 6f 6e 20 69 73 20 61 74 74 61 63 68 65 64 20  ion is attached 
a390: 74 6f 20 61 20 64 69 66 66 65 72 65 6e 74 20 64  to a different d
a3a0: 61 74 61 62 61 73 65 20 28 22 6d 61 69 6e 22 2c  atabase ("main",
a3b0: 20 22 74 65 6d 70 22 20 0a 20 20 20 20 2a 2a 20   "temp" .    ** 
a3c0: 65 74 63 2e 29 2c 20 6f 72 20 69 66 20 69 74 20  etc.), or if it 
a3d0: 69 73 20 6e 6f 74 20 63 75 72 72 65 6e 74 6c 79  is not currently
a3e0: 20 65 6e 61 62 6c 65 64 2c 20 74 68 65 72 65 20   enabled, there 
a3f0: 69 73 20 6e 6f 74 68 69 6e 67 20 74 6f 20 64 6f  is nothing to do
a400: 2e 20 53 6b 69 70 20 0a 20 20 20 20 2a 2a 20 74  . Skip .    ** t
a410: 6f 20 74 68 65 20 6e 65 78 74 20 73 65 73 73 69  o the next sessi
a420: 6f 6e 20 6f 62 6a 65 63 74 20 61 74 74 61 63 68  on object attach
a430: 65 64 20 74 6f 20 74 68 69 73 20 64 61 74 61 62  ed to this datab
a440: 61 73 65 2e 20 2a 2f 0a 20 20 20 20 69 66 28 20  ase. */.    if( 
a450: 70 53 65 73 73 69 6f 6e 2d 3e 62 45 6e 61 62 6c  pSession->bEnabl
a460: 65 3d 3d 30 20 29 20 63 6f 6e 74 69 6e 75 65 3b  e==0 ) continue;
a470: 0a 20 20 20 20 69 66 28 20 70 53 65 73 73 69 6f  .    if( pSessio
a480: 6e 2d 3e 72 63 20 29 20 63 6f 6e 74 69 6e 75 65  n->rc ) continue
a490: 3b 0a 20 20 20 20 69 66 28 20 73 71 6c 69 74 65  ;.    if( sqlite
a4a0: 33 5f 73 74 72 6e 69 63 6d 70 28 7a 44 62 2c 20  3_strnicmp(zDb, 
a4b0: 70 53 65 73 73 69 6f 6e 2d 3e 7a 44 62 2c 20 6e  pSession->zDb, n
a4c0: 44 62 2b 31 29 20 29 20 63 6f 6e 74 69 6e 75 65  Db+1) ) continue
a4d0: 3b 0a 0a 20 20 20 20 70 53 65 73 73 69 6f 6e 2d  ;..    pSession-
a4e0: 3e 72 63 20 3d 20 73 65 73 73 69 6f 6e 46 69 6e  >rc = sessionFin
a4f0: 64 54 61 62 6c 65 28 70 53 65 73 73 69 6f 6e 2c  dTable(pSession,
a500: 20 7a 4e 61 6d 65 2c 20 26 70 54 61 62 29 3b 0a   zName, &pTab);.
a510: 20 20 20 20 69 66 28 20 70 54 61 62 20 29 7b 0a      if( pTab ){.
a520: 20 20 20 20 20 20 61 73 73 65 72 74 28 20 70 53        assert( pS
a530: 65 73 73 69 6f 6e 2d 3e 72 63 3d 3d 53 51 4c 49  ession->rc==SQLI
a540: 54 45 5f 4f 4b 20 29 3b 0a 20 20 20 20 20 20 73  TE_OK );.      s
a550: 65 73 73 69 6f 6e 50 72 65 75 70 64 61 74 65 4f  essionPreupdateO
a560: 6e 65 43 68 61 6e 67 65 28 6f 70 2c 20 70 53 65  neChange(op, pSe
a570: 73 73 69 6f 6e 2c 20 70 54 61 62 29 3b 0a 20 20  ssion, pTab);.  
a580: 20 20 20 20 69 66 28 20 6f 70 3d 3d 53 51 4c 49      if( op==SQLI
a590: 54 45 5f 55 50 44 41 54 45 20 29 7b 0a 20 20 20  TE_UPDATE ){.   
a5a0: 20 20 20 20 20 73 65 73 73 69 6f 6e 50 72 65 75       sessionPreu
a5b0: 70 64 61 74 65 4f 6e 65 43 68 61 6e 67 65 28 53  pdateOneChange(S
a5c0: 51 4c 49 54 45 5f 49 4e 53 45 52 54 2c 20 70 53  QLITE_INSERT, pS
a5d0: 65 73 73 69 6f 6e 2c 20 70 54 61 62 29 3b 0a 20  ession, pTab);. 
a5e0: 20 20 20 20 20 7d 0a 20 20 20 20 7d 0a 20 20 7d       }.    }.  }
a5f0: 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68 65 20 70 72  .}../*.** The pr
a600: 65 2d 75 70 64 61 74 65 20 68 6f 6f 6b 20 69 6d  e-update hook im
a610: 70 6c 65 6d 65 6e 74 61 74 69 6f 6e 73 2e 0a 2a  plementations..*
a620: 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73  /.static int ses
a630: 73 69 6f 6e 50 72 65 75 70 64 61 74 65 4f 6c 64  sionPreupdateOld
a640: 28 76 6f 69 64 20 2a 70 43 74 78 2c 20 69 6e 74  (void *pCtx, int
a650: 20 69 56 61 6c 2c 20 73 71 6c 69 74 65 33 5f 76   iVal, sqlite3_v
a660: 61 6c 75 65 20 2a 2a 70 70 56 61 6c 29 7b 0a 20  alue **ppVal){. 
a670: 20 72 65 74 75 72 6e 20 73 71 6c 69 74 65 33 5f   return sqlite3_
a680: 70 72 65 75 70 64 61 74 65 5f 6f 6c 64 28 28 73  preupdate_old((s
a690: 71 6c 69 74 65 33 2a 29 70 43 74 78 2c 20 69 56  qlite3*)pCtx, iV
a6a0: 61 6c 2c 20 70 70 56 61 6c 29 3b 0a 7d 0a 73 74  al, ppVal);.}.st
a6b0: 61 74 69 63 20 69 6e 74 20 73 65 73 73 69 6f 6e  atic int session
a6c0: 50 72 65 75 70 64 61 74 65 4e 65 77 28 76 6f 69  PreupdateNew(voi
a6d0: 64 20 2a 70 43 74 78 2c 20 69 6e 74 20 69 56 61  d *pCtx, int iVa
a6e0: 6c 2c 20 73 71 6c 69 74 65 33 5f 76 61 6c 75 65  l, sqlite3_value
a6f0: 20 2a 2a 70 70 56 61 6c 29 7b 0a 20 20 72 65 74   **ppVal){.  ret
a700: 75 72 6e 20 73 71 6c 69 74 65 33 5f 70 72 65 75  urn sqlite3_preu
a710: 70 64 61 74 65 5f 6e 65 77 28 28 73 71 6c 69 74  pdate_new((sqlit
a720: 65 33 2a 29 70 43 74 78 2c 20 69 56 61 6c 2c 20  e3*)pCtx, iVal, 
a730: 70 70 56 61 6c 29 3b 0a 7d 0a 73 74 61 74 69 63  ppVal);.}.static
a740: 20 69 6e 74 20 73 65 73 73 69 6f 6e 50 72 65 75   int sessionPreu
a750: 70 64 61 74 65 43 6f 75 6e 74 28 76 6f 69 64 20  pdateCount(void 
a760: 2a 70 43 74 78 29 7b 0a 20 20 72 65 74 75 72 6e  *pCtx){.  return
a770: 20 73 71 6c 69 74 65 33 5f 70 72 65 75 70 64 61   sqlite3_preupda
a780: 74 65 5f 63 6f 75 6e 74 28 28 73 71 6c 69 74 65  te_count((sqlite
a790: 33 2a 29 70 43 74 78 29 3b 0a 7d 0a 73 74 61 74  3*)pCtx);.}.stat
a7a0: 69 63 20 69 6e 74 20 73 65 73 73 69 6f 6e 50 72  ic int sessionPr
a7b0: 65 75 70 64 61 74 65 44 65 70 74 68 28 76 6f 69  eupdateDepth(voi
a7c0: 64 20 2a 70 43 74 78 29 7b 0a 20 20 72 65 74 75  d *pCtx){.  retu
a7d0: 72 6e 20 73 71 6c 69 74 65 33 5f 70 72 65 75 70  rn sqlite3_preup
a7e0: 64 61 74 65 5f 64 65 70 74 68 28 28 73 71 6c 69  date_depth((sqli
a7f0: 74 65 33 2a 29 70 43 74 78 29 3b 0a 7d 0a 0a 2f  te3*)pCtx);.}../
a800: 2a 0a 2a 2a 20 49 6e 73 74 61 6c 6c 20 74 68 65  *.** Install the
a810: 20 70 72 65 2d 75 70 64 61 74 65 20 68 6f 6f 6b   pre-update hook
a820: 73 20 6f 6e 20 74 68 65 20 73 65 73 73 69 6f 6e  s on the session
a830: 20 6f 62 6a 65 63 74 20 70 61 73 73 65 64 20 61   object passed a
a840: 73 20 74 68 65 20 6f 6e 6c 79 0a 2a 2a 20 61 72  s the only.** ar
a850: 67 75 6d 65 6e 74 2e 0a 2a 2f 0a 73 74 61 74 69  gument..*/.stati
a860: 63 20 76 6f 69 64 20 73 65 73 73 69 6f 6e 50 72  c void sessionPr
a870: 65 75 70 64 61 74 65 48 6f 6f 6b 73 28 0a 20 20  eupdateHooks(.  
a880: 73 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20  sqlite3_session 
a890: 2a 70 53 65 73 73 69 6f 6e 0a 29 7b 0a 20 20 70  *pSession.){.  p
a8a0: 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 70 43  Session->hook.pC
a8b0: 74 78 20 3d 20 28 76 6f 69 64 2a 29 70 53 65 73  tx = (void*)pSes
a8c0: 73 69 6f 6e 2d 3e 64 62 3b 0a 20 20 70 53 65 73  sion->db;.  pSes
a8d0: 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 78 4f 6c 64 20  sion->hook.xOld 
a8e0: 3d 20 73 65 73 73 69 6f 6e 50 72 65 75 70 64 61  = sessionPreupda
a8f0: 74 65 4f 6c 64 3b 0a 20 20 70 53 65 73 73 69 6f  teOld;.  pSessio
a900: 6e 2d 3e 68 6f 6f 6b 2e 78 4e 65 77 20 3d 20 73  n->hook.xNew = s
a910: 65 73 73 69 6f 6e 50 72 65 75 70 64 61 74 65 4e  essionPreupdateN
a920: 65 77 3b 0a 20 20 70 53 65 73 73 69 6f 6e 2d 3e  ew;.  pSession->
a930: 68 6f 6f 6b 2e 78 43 6f 75 6e 74 20 3d 20 73 65  hook.xCount = se
a940: 73 73 69 6f 6e 50 72 65 75 70 64 61 74 65 43 6f  ssionPreupdateCo
a950: 75 6e 74 3b 0a 20 20 70 53 65 73 73 69 6f 6e 2d  unt;.  pSession-
a960: 3e 68 6f 6f 6b 2e 78 44 65 70 74 68 20 3d 20 73  >hook.xDepth = s
a970: 65 73 73 69 6f 6e 50 72 65 75 70 64 61 74 65 44  essionPreupdateD
a980: 65 70 74 68 3b 0a 7d 0a 0a 74 79 70 65 64 65 66  epth;.}..typedef
a990: 20 73 74 72 75 63 74 20 53 65 73 73 69 6f 6e 44   struct SessionD
a9a0: 69 66 66 43 74 78 20 53 65 73 73 69 6f 6e 44 69  iffCtx SessionDi
a9b0: 66 66 43 74 78 3b 0a 73 74 72 75 63 74 20 53 65  ffCtx;.struct Se
a9c0: 73 73 69 6f 6e 44 69 66 66 43 74 78 20 7b 0a 20  ssionDiffCtx {. 
a9d0: 20 73 71 6c 69 74 65 33 5f 73 74 6d 74 20 2a 70   sqlite3_stmt *p
a9e0: 53 74 6d 74 3b 0a 20 20 69 6e 74 20 6e 4f 6c 64  Stmt;.  int nOld
a9f0: 4f 66 66 3b 0a 7d 3b 0a 0a 2f 2a 0a 2a 2a 20 54  Off;.};../*.** T
aa00: 68 65 20 64 69 66 66 20 68 6f 6f 6b 20 69 6d 70  he diff hook imp
aa10: 6c 65 6d 65 6e 74 61 74 69 6f 6e 73 2e 0a 2a 2f  lementations..*/
aa20: 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73 73  .static int sess
aa30: 69 6f 6e 44 69 66 66 4f 6c 64 28 76 6f 69 64 20  ionDiffOld(void 
aa40: 2a 70 43 74 78 2c 20 69 6e 74 20 69 56 61 6c 2c  *pCtx, int iVal,
aa50: 20 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 20 2a   sqlite3_value *
aa60: 2a 70 70 56 61 6c 29 7b 0a 20 20 53 65 73 73 69  *ppVal){.  Sessi
aa70: 6f 6e 44 69 66 66 43 74 78 20 2a 70 20 3d 20 28  onDiffCtx *p = (
aa80: 53 65 73 73 69 6f 6e 44 69 66 66 43 74 78 2a 29  SessionDiffCtx*)
aa90: 70 43 74 78 3b 0a 20 20 2a 70 70 56 61 6c 20 3d  pCtx;.  *ppVal =
aaa0: 20 73 71 6c 69 74 65 33 5f 63 6f 6c 75 6d 6e 5f   sqlite3_column_
aab0: 76 61 6c 75 65 28 70 2d 3e 70 53 74 6d 74 2c 20  value(p->pStmt, 
aac0: 69 56 61 6c 2b 70 2d 3e 6e 4f 6c 64 4f 66 66 29  iVal+p->nOldOff)
aad0: 3b 0a 20 20 72 65 74 75 72 6e 20 53 51 4c 49 54  ;.  return SQLIT
aae0: 45 5f 4f 4b 3b 0a 7d 0a 73 74 61 74 69 63 20 69  E_OK;.}.static i
aaf0: 6e 74 20 73 65 73 73 69 6f 6e 44 69 66 66 4e 65  nt sessionDiffNe
ab00: 77 28 76 6f 69 64 20 2a 70 43 74 78 2c 20 69 6e  w(void *pCtx, in
ab10: 74 20 69 56 61 6c 2c 20 73 71 6c 69 74 65 33 5f  t iVal, sqlite3_
ab20: 76 61 6c 75 65 20 2a 2a 70 70 56 61 6c 29 7b 0a  value **ppVal){.
ab30: 20 20 53 65 73 73 69 6f 6e 44 69 66 66 43 74 78    SessionDiffCtx
ab40: 20 2a 70 20 3d 20 28 53 65 73 73 69 6f 6e 44 69   *p = (SessionDi
ab50: 66 66 43 74 78 2a 29 70 43 74 78 3b 0a 20 20 2a  ffCtx*)pCtx;.  *
ab60: 70 70 56 61 6c 20 3d 20 73 71 6c 69 74 65 33 5f  ppVal = sqlite3_
ab70: 63 6f 6c 75 6d 6e 5f 76 61 6c 75 65 28 70 2d 3e  column_value(p->
ab80: 70 53 74 6d 74 2c 20 69 56 61 6c 29 3b 0a 20 20  pStmt, iVal);.  
ab90: 20 72 65 74 75 72 6e 20 53 51 4c 49 54 45 5f 4f   return SQLITE_O
aba0: 4b 3b 0a 7d 0a 73 74 61 74 69 63 20 69 6e 74 20  K;.}.static int 
abb0: 73 65 73 73 69 6f 6e 44 69 66 66 43 6f 75 6e 74  sessionDiffCount
abc0: 28 76 6f 69 64 20 2a 70 43 74 78 29 7b 0a 20 20  (void *pCtx){.  
abd0: 53 65 73 73 69 6f 6e 44 69 66 66 43 74 78 20 2a  SessionDiffCtx *
abe0: 70 20 3d 20 28 53 65 73 73 69 6f 6e 44 69 66 66  p = (SessionDiff
abf0: 43 74 78 2a 29 70 43 74 78 3b 0a 20 20 72 65 74  Ctx*)pCtx;.  ret
ac00: 75 72 6e 20 70 2d 3e 6e 4f 6c 64 4f 66 66 20 3f  urn p->nOldOff ?
ac10: 20 70 2d 3e 6e 4f 6c 64 4f 66 66 20 3a 20 73 71   p->nOldOff : sq
ac20: 6c 69 74 65 33 5f 63 6f 6c 75 6d 6e 5f 63 6f 75  lite3_column_cou
ac30: 6e 74 28 70 2d 3e 70 53 74 6d 74 29 3b 0a 7d 0a  nt(p->pStmt);.}.
ac40: 73 74 61 74 69 63 20 69 6e 74 20 73 65 73 73 69  static int sessi
ac50: 6f 6e 44 69 66 66 44 65 70 74 68 28 76 6f 69 64  onDiffDepth(void
ac60: 20 2a 70 43 74 78 29 7b 0a 20 20 72 65 74 75 72   *pCtx){.  retur
ac70: 6e 20 30 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 49 6e  n 0;.}../*.** In
ac80: 73 74 61 6c 6c 20 74 68 65 20 64 69 66 66 20 68  stall the diff h
ac90: 6f 6f 6b 73 20 6f 6e 20 74 68 65 20 73 65 73 73  ooks on the sess
aca0: 69 6f 6e 20 6f 62 6a 65 63 74 20 70 61 73 73 65  ion object passe
acb0: 64 20 61 73 20 74 68 65 20 6f 6e 6c 79 0a 2a 2a  d as the only.**
acc0: 20 61 72 67 75 6d 65 6e 74 2e 0a 2a 2f 0a 73 74   argument..*/.st
acd0: 61 74 69 63 20 76 6f 69 64 20 73 65 73 73 69 6f  atic void sessio
ace0: 6e 44 69 66 66 48 6f 6f 6b 73 28 0a 20 20 73 71  nDiffHooks(.  sq
acf0: 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a 70  lite3_session *p
ad00: 53 65 73 73 69 6f 6e 2c 0a 20 20 53 65 73 73 69  Session,.  Sessi
ad10: 6f 6e 44 69 66 66 43 74 78 20 2a 70 44 69 66 66  onDiffCtx *pDiff
ad20: 43 74 78 0a 29 7b 0a 20 20 70 53 65 73 73 69 6f  Ctx.){.  pSessio
ad30: 6e 2d 3e 68 6f 6f 6b 2e 70 43 74 78 20 3d 20 28  n->hook.pCtx = (
ad40: 76 6f 69 64 2a 29 70 44 69 66 66 43 74 78 3b 0a  void*)pDiffCtx;.
ad50: 20 20 70 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b    pSession->hook
ad60: 2e 78 4f 6c 64 20 3d 20 73 65 73 73 69 6f 6e 44  .xOld = sessionD
ad70: 69 66 66 4f 6c 64 3b 0a 20 20 70 53 65 73 73 69  iffOld;.  pSessi
ad80: 6f 6e 2d 3e 68 6f 6f 6b 2e 78 4e 65 77 20 3d 20  on->hook.xNew = 
ad90: 73 65 73 73 69 6f 6e 44 69 66 66 4e 65 77 3b 0a  sessionDiffNew;.
ada0: 20 20 70 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b    pSession->hook
adb0: 2e 78 43 6f 75 6e 74 20 3d 20 73 65 73 73 69 6f  .xCount = sessio
adc0: 6e 44 69 66 66 43 6f 75 6e 74 3b 0a 20 20 70 53  nDiffCount;.  pS
add0: 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 78 44 65  ession->hook.xDe
ade0: 70 74 68 20 3d 20 73 65 73 73 69 6f 6e 44 69 66  pth = sessionDif
adf0: 66 44 65 70 74 68 3b 0a 7d 0a 0a 73 74 61 74 69  fDepth;.}..stati
ae00: 63 20 63 68 61 72 20 2a 73 65 73 73 69 6f 6e 45  c char *sessionE
ae10: 78 70 72 43 6f 6d 70 61 72 65 50 4b 28 0a 20 20  xprComparePK(.  
ae20: 69 6e 74 20 6e 43 6f 6c 2c 0a 20 20 63 6f 6e 73  int nCol,.  cons
ae30: 74 20 63 68 61 72 20 2a 7a 44 62 31 2c 20 63 6f  t char *zDb1, co
ae40: 6e 73 74 20 63 68 61 72 20 2a 7a 44 62 32 2c 20  nst char *zDb2, 
ae50: 0a 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a  .  const char *z
ae60: 54 61 62 2c 0a 20 20 63 6f 6e 73 74 20 63 68 61  Tab,.  const cha
ae70: 72 20 2a 2a 61 7a 43 6f 6c 2c 20 75 38 20 2a 61  r **azCol, u8 *a
ae80: 62 50 4b 0a 29 7b 0a 20 20 69 6e 74 20 69 3b 0a  bPK.){.  int i;.
ae90: 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 53    const char *zS
aea0: 65 70 20 3d 20 22 22 3b 0a 20 20 63 68 61 72 20  ep = "";.  char 
aeb0: 2a 7a 52 65 74 20 3d 20 30 3b 0a 0a 20 20 66 6f  *zRet = 0;..  fo
aec0: 72 28 69 3d 30 3b 20 69 3c 6e 43 6f 6c 3b 20 69  r(i=0; i<nCol; i
aed0: 2b 2b 29 7b 0a 20 20 20 20 69 66 28 20 61 62 50  ++){.    if( abP
aee0: 4b 5b 69 5d 20 29 7b 0a 20 20 20 20 20 20 7a 52  K[i] ){.      zR
aef0: 65 74 20 3d 20 73 71 6c 69 74 65 33 5f 6d 70 72  et = sqlite3_mpr
af00: 69 6e 74 66 28 22 25 7a 25 73 5c 22 25 77 5c 22  intf("%z%s\"%w\"
af10: 2e 5c 22 25 77 5c 22 2e 5c 22 25 77 5c 22 3d 5c  .\"%w\".\"%w\"=\
af20: 22 25 77 5c 22 2e 5c 22 25 77 5c 22 2e 5c 22 25  "%w\".\"%w\".\"%
af30: 77 5c 22 22 2c 0a 20 20 20 20 20 20 20 20 20 20  w\"",.          
af40: 7a 52 65 74 2c 20 7a 53 65 70 2c 20 7a 44 62 31  zRet, zSep, zDb1
af50: 2c 20 7a 54 61 62 2c 20 61 7a 43 6f 6c 5b 69 5d  , zTab, azCol[i]
af60: 2c 20 7a 44 62 32 2c 20 7a 54 61 62 2c 20 61 7a  , zDb2, zTab, az
af70: 43 6f 6c 5b 69 5d 0a 20 20 20 20 20 20 29 3b 0a  Col[i].      );.
af80: 20 20 20 20 20 20 7a 53 65 70 20 3d 20 22 20 41        zSep = " A
af90: 4e 44 20 22 3b 0a 20 20 20 20 20 20 69 66 28 20  ND ";.      if( 
afa0: 7a 52 65 74 3d 3d 30 20 29 20 62 72 65 61 6b 3b  zRet==0 ) break;
afb0: 0a 20 20 20 20 7d 0a 20 20 7d 0a 0a 20 20 72 65  .    }.  }..  re
afc0: 74 75 72 6e 20 7a 52 65 74 3b 0a 7d 0a 0a 73 74  turn zRet;.}..st
afd0: 61 74 69 63 20 63 68 61 72 20 2a 73 65 73 73 69  atic char *sessi
afe0: 6f 6e 45 78 70 72 43 6f 6d 70 61 72 65 4f 74 68  onExprCompareOth
aff0: 65 72 28 0a 20 20 69 6e 74 20 6e 43 6f 6c 2c 0a  er(.  int nCol,.
b000: 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 44    const char *zD
b010: 62 31 2c 20 63 6f 6e 73 74 20 63 68 61 72 20 2a  b1, const char *
b020: 7a 44 62 32 2c 20 0a 20 20 63 6f 6e 73 74 20 63  zDb2, .  const c
b030: 68 61 72 20 2a 7a 54 61 62 2c 0a 20 20 63 6f 6e  har *zTab,.  con
b040: 73 74 20 63 68 61 72 20 2a 2a 61 7a 43 6f 6c 2c  st char **azCol,
b050: 20 75 38 20 2a 61 62 50 4b 0a 29 7b 0a 20 20 69   u8 *abPK.){.  i
b060: 6e 74 20 69 3b 0a 20 20 63 6f 6e 73 74 20 63 68  nt i;.  const ch
b070: 61 72 20 2a 7a 53 65 70 20 3d 20 22 22 3b 0a 20  ar *zSep = "";. 
b080: 20 63 68 61 72 20 2a 7a 52 65 74 20 3d 20 30 3b   char *zRet = 0;
b090: 0a 20 20 69 6e 74 20 62 48 61 76 65 20 3d 20 30  .  int bHave = 0
b0a0: 3b 0a 0a 20 20 66 6f 72 28 69 3d 30 3b 20 69 3c  ;..  for(i=0; i<
b0b0: 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a 20 20 20 20  nCol; i++){.    
b0c0: 69 66 28 20 61 62 50 4b 5b 69 5d 3d 3d 30 20 29  if( abPK[i]==0 )
b0d0: 7b 0a 20 20 20 20 20 20 62 48 61 76 65 20 3d 20  {.      bHave = 
b0e0: 31 3b 0a 20 20 20 20 20 20 7a 52 65 74 20 3d 20  1;.      zRet = 
b0f0: 73 71 6c 69 74 65 33 5f 6d 70 72 69 6e 74 66 28  sqlite3_mprintf(
b100: 0a 20 20 20 20 20 20 20 20 20 20 22 25 7a 25 73  .          "%z%s
b110: 5c 22 25 77 5c 22 2e 5c 22 25 77 5c 22 2e 5c 22  \"%w\".\"%w\".\"
b120: 25 77 5c 22 20 49 53 20 4e 4f 54 20 5c 22 25 77  %w\" IS NOT \"%w
b130: 5c 22 2e 5c 22 25 77 5c 22 2e 5c 22 25 77 5c 22  \".\"%w\".\"%w\"
b140: 22 2c 0a 20 20 20 20 20 20 20 20 20 20 7a 52 65  ",.          zRe
b150: 74 2c 20 7a 53 65 70 2c 20 7a 44 62 31 2c 20 7a  t, zSep, zDb1, z
b160: 54 61 62 2c 20 61 7a 43 6f 6c 5b 69 5d 2c 20 7a  Tab, azCol[i], z
b170: 44 62 32 2c 20 7a 54 61 62 2c 20 61 7a 43 6f 6c  Db2, zTab, azCol
b180: 5b 69 5d 0a 20 20 20 20 20 20 29 3b 0a 20 20 20  [i].      );.   
b190: 20 20 20 7a 53 65 70 20 3d 20 22 20 4f 52 20 22     zSep = " OR "
b1a0: 3b 0a 20 20 20 20 20 20 69 66 28 20 7a 52 65 74  ;.      if( zRet
b1b0: 3d 3d 30 20 29 20 62 72 65 61 6b 3b 0a 20 20 20  ==0 ) break;.   
b1c0: 20 7d 0a 20 20 7d 0a 0a 20 20 69 66 28 20 62 48   }.  }..  if( bH
b1d0: 61 76 65 3d 3d 30 20 29 7b 0a 20 20 20 20 61 73  ave==0 ){.    as
b1e0: 73 65 72 74 28 20 7a 52 65 74 3d 3d 30 20 29 3b  sert( zRet==0 );
b1f0: 0a 20 20 20 20 7a 52 65 74 20 3d 20 73 71 6c 69  .    zRet = sqli
b200: 74 65 33 5f 6d 70 72 69 6e 74 66 28 22 30 22 29  te3_mprintf("0")
b210: 3b 0a 20 20 7d 0a 0a 20 20 72 65 74 75 72 6e 20  ;.  }..  return 
b220: 7a 52 65 74 3b 0a 7d 0a 0a 73 74 61 74 69 63 20  zRet;.}..static 
b230: 63 68 61 72 20 2a 73 65 73 73 69 6f 6e 53 65 6c  char *sessionSel
b240: 65 63 74 46 69 6e 64 4e 65 77 28 0a 20 20 69 6e  ectFindNew(.  in
b250: 74 20 6e 43 6f 6c 2c 0a 20 20 63 6f 6e 73 74 20  t nCol,.  const 
b260: 63 68 61 72 20 2a 7a 44 62 31 2c 20 20 20 20 20  char *zDb1,     
b270: 20 2f 2a 20 50 69 63 6b 20 72 6f 77 73 20 69 6e   /* Pick rows in
b280: 20 74 68 69 73 20 64 62 20 6f 6e 6c 79 20 2a 2f   this db only */
b290: 0a 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a  .  const char *z
b2a0: 44 62 32 2c 20 20 20 20 20 20 2f 2a 20 42 75 74  Db2,      /* But
b2b0: 20 6e 6f 74 20 69 6e 20 74 68 69 73 20 6f 6e 65   not in this one
b2c0: 20 2a 2f 0a 20 20 63 6f 6e 73 74 20 63 68 61 72   */.  const char
b2d0: 20 2a 7a 54 62 6c 2c 20 20 20 20 20 20 2f 2a 20   *zTbl,      /* 
b2e0: 54 61 62 6c 65 20 6e 61 6d 65 20 2a 2f 0a 20 20  Table name */.  
b2f0: 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 45 78 70  const char *zExp
b300: 72 0a 29 7b 0a 20 20 63 68 61 72 20 2a 7a 52 65  r.){.  char *zRe
b310: 74 20 3d 20 73 71 6c 69 74 65 33 5f 6d 70 72 69  t = sqlite3_mpri
b320: 6e 74 66 28 0a 20 20 20 20 20 20 22 53 45 4c 45  ntf(.      "SELE
b330: 43 54 20 2a 20 46 52 4f 4d 20 5c 22 25 77 5c 22  CT * FROM \"%w\"
b340: 2e 5c 22 25 77 5c 22 20 57 48 45 52 45 20 4e 4f  .\"%w\" WHERE NO
b350: 54 20 45 58 49 53 54 53 20 28 22 0a 20 20 20 20  T EXISTS (".    
b360: 20 20 22 20 20 53 45 4c 45 43 54 20 31 20 46 52    "  SELECT 1 FR
b370: 4f 4d 20 5c 22 25 77 5c 22 2e 5c 22 25 77 5c 22  OM \"%w\".\"%w\"
b380: 20 57 48 45 52 45 20 25 73 22 0a 20 20 20 20 20   WHERE %s".     
b390: 20 22 29 22 2c 0a 20 20 20 20 20 20 7a 44 62 31   ")",.      zDb1
b3a0: 2c 20 7a 54 62 6c 2c 20 7a 44 62 32 2c 20 7a 54  , zTbl, zDb2, zT
b3b0: 62 6c 2c 20 7a 45 78 70 72 0a 20 20 29 3b 0a 20  bl, zExpr.  );. 
b3c0: 20 72 65 74 75 72 6e 20 7a 52 65 74 3b 0a 7d 0a   return zRet;.}.
b3d0: 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73 73  .static int sess
b3e0: 69 6f 6e 44 69 66 66 46 69 6e 64 4e 65 77 28 0a  ionDiffFindNew(.
b3f0: 20 20 69 6e 74 20 6f 70 2c 0a 20 20 73 71 6c 69    int op,.  sqli
b400: 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a 70 53 65  te3_session *pSe
b410: 73 73 69 6f 6e 2c 0a 20 20 53 65 73 73 69 6f 6e  ssion,.  Session
b420: 54 61 62 6c 65 20 2a 70 54 61 62 2c 0a 20 20 63  Table *pTab,.  c
b430: 6f 6e 73 74 20 63 68 61 72 20 2a 7a 44 62 31 2c  onst char *zDb1,
b440: 0a 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a  .  const char *z
b450: 44 62 32 2c 0a 20 20 63 68 61 72 20 2a 7a 45 78  Db2,.  char *zEx
b460: 70 72 0a 29 7b 0a 20 20 69 6e 74 20 72 63 20 3d  pr.){.  int rc =
b470: 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a 20 20 63 68   SQLITE_OK;.  ch
b480: 61 72 20 2a 7a 53 74 6d 74 20 3d 20 73 65 73 73  ar *zStmt = sess
b490: 69 6f 6e 53 65 6c 65 63 74 46 69 6e 64 4e 65 77  ionSelectFindNew
b4a0: 28 70 54 61 62 2d 3e 6e 43 6f 6c 2c 20 7a 44 62  (pTab->nCol, zDb
b4b0: 31 2c 20 7a 44 62 32 2c 20 70 54 61 62 2d 3e 7a  1, zDb2, pTab->z
b4c0: 4e 61 6d 65 2c 7a 45 78 70 72 29 3b 0a 0a 20 20  Name,zExpr);..  
b4d0: 69 66 28 20 7a 53 74 6d 74 3d 3d 30 20 29 7b 0a  if( zStmt==0 ){.
b4e0: 20 20 20 20 72 63 20 3d 20 53 51 4c 49 54 45 5f      rc = SQLITE_
b4f0: 4e 4f 4d 45 4d 3b 0a 20 20 7d 65 6c 73 65 7b 0a  NOMEM;.  }else{.
b500: 20 20 20 20 73 71 6c 69 74 65 33 5f 73 74 6d 74      sqlite3_stmt
b510: 20 2a 70 53 74 6d 74 3b 0a 20 20 20 20 72 63 20   *pStmt;.    rc 
b520: 3d 20 73 71 6c 69 74 65 33 5f 70 72 65 70 61 72  = sqlite3_prepar
b530: 65 28 70 53 65 73 73 69 6f 6e 2d 3e 64 62 2c 20  e(pSession->db, 
b540: 7a 53 74 6d 74 2c 20 2d 31 2c 20 26 70 53 74 6d  zStmt, -1, &pStm
b550: 74 2c 20 30 29 3b 0a 20 20 20 20 69 66 28 20 72  t, 0);.    if( r
b560: 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a  c==SQLITE_OK ){.
b570: 20 20 20 20 20 20 53 65 73 73 69 6f 6e 44 69 66        SessionDif
b580: 66 43 74 78 20 2a 70 44 69 66 66 43 74 78 20 3d  fCtx *pDiffCtx =
b590: 20 28 53 65 73 73 69 6f 6e 44 69 66 66 43 74 78   (SessionDiffCtx
b5a0: 2a 29 70 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b  *)pSession->hook
b5b0: 2e 70 43 74 78 3b 0a 20 20 20 20 20 20 70 44 69  .pCtx;.      pDi
b5c0: 66 66 43 74 78 2d 3e 70 53 74 6d 74 20 3d 20 70  ffCtx->pStmt = p
b5d0: 53 74 6d 74 3b 0a 20 20 20 20 20 20 70 44 69 66  Stmt;.      pDif
b5e0: 66 43 74 78 2d 3e 6e 4f 6c 64 4f 66 66 20 3d 20  fCtx->nOldOff = 
b5f0: 30 3b 0a 20 20 20 20 20 20 77 68 69 6c 65 28 20  0;.      while( 
b600: 53 51 4c 49 54 45 5f 52 4f 57 3d 3d 73 71 6c 69  SQLITE_ROW==sqli
b610: 74 65 33 5f 73 74 65 70 28 70 53 74 6d 74 29 20  te3_step(pStmt) 
b620: 29 7b 0a 20 20 20 20 20 20 20 20 73 65 73 73 69  ){.        sessi
b630: 6f 6e 50 72 65 75 70 64 61 74 65 4f 6e 65 43 68  onPreupdateOneCh
b640: 61 6e 67 65 28 6f 70 2c 20 70 53 65 73 73 69 6f  ange(op, pSessio
b650: 6e 2c 20 70 54 61 62 29 3b 0a 20 20 20 20 20 20  n, pTab);.      
b660: 7d 0a 20 20 20 20 20 20 72 63 20 3d 20 73 71 6c  }.      rc = sql
b670: 69 74 65 33 5f 66 69 6e 61 6c 69 7a 65 28 70 53  ite3_finalize(pS
b680: 74 6d 74 29 3b 0a 20 20 20 20 7d 0a 20 20 20 20  tmt);.    }.    
b690: 73 71 6c 69 74 65 33 5f 66 72 65 65 28 7a 53 74  sqlite3_free(zSt
b6a0: 6d 74 29 3b 0a 20 20 7d 0a 0a 20 20 72 65 74 75  mt);.  }..  retu
b6b0: 72 6e 20 72 63 3b 0a 7d 0a 0a 73 74 61 74 69 63  rn rc;.}..static
b6c0: 20 69 6e 74 20 73 65 73 73 69 6f 6e 44 69 66 66   int sessionDiff
b6d0: 46 69 6e 64 4d 6f 64 69 66 69 65 64 28 0a 20 20  FindModified(.  
b6e0: 73 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20  sqlite3_session 
b6f0: 2a 70 53 65 73 73 69 6f 6e 2c 20 0a 20 20 53 65  *pSession, .  Se
b700: 73 73 69 6f 6e 54 61 62 6c 65 20 2a 70 54 61 62  ssionTable *pTab
b710: 2c 20 0a 20 20 63 6f 6e 73 74 20 63 68 61 72 20  , .  const char 
b720: 2a 7a 46 72 6f 6d 2c 20 0a 20 20 63 6f 6e 73 74  *zFrom, .  const
b730: 20 63 68 61 72 20 2a 7a 45 78 70 72 0a 29 7b 0a   char *zExpr.){.
b740: 20 20 69 6e 74 20 72 63 20 3d 20 53 51 4c 49 54    int rc = SQLIT
b750: 45 5f 4f 4b 3b 0a 0a 20 20 63 68 61 72 20 2a 7a  E_OK;..  char *z
b760: 45 78 70 72 32 20 3d 20 73 65 73 73 69 6f 6e 45  Expr2 = sessionE
b770: 78 70 72 43 6f 6d 70 61 72 65 4f 74 68 65 72 28  xprCompareOther(
b780: 70 54 61 62 2d 3e 6e 43 6f 6c 2c 0a 20 20 20 20  pTab->nCol,.    
b790: 20 20 70 53 65 73 73 69 6f 6e 2d 3e 7a 44 62 2c    pSession->zDb,
b7a0: 20 7a 46 72 6f 6d 2c 20 70 54 61 62 2d 3e 7a 4e   zFrom, pTab->zN
b7b0: 61 6d 65 2c 20 70 54 61 62 2d 3e 61 7a 43 6f 6c  ame, pTab->azCol
b7c0: 2c 20 70 54 61 62 2d 3e 61 62 50 4b 0a 20 20 29  , pTab->abPK.  )
b7d0: 3b 0a 20 20 69 66 28 20 7a 45 78 70 72 32 3d 3d  ;.  if( zExpr2==
b7e0: 30 20 29 7b 0a 20 20 20 20 72 63 20 3d 20 53 51  0 ){.    rc = SQ
b7f0: 4c 49 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 7d 65  LITE_NOMEM;.  }e
b800: 6c 73 65 7b 0a 20 20 20 20 63 68 61 72 20 2a 7a  lse{.    char *z
b810: 53 74 6d 74 20 3d 20 73 71 6c 69 74 65 33 5f 6d  Stmt = sqlite3_m
b820: 70 72 69 6e 74 66 28 0a 20 20 20 20 20 20 20 20  printf(.        
b830: 22 53 45 4c 45 43 54 20 2a 20 46 52 4f 4d 20 5c  "SELECT * FROM \
b840: 22 25 77 5c 22 2e 5c 22 25 77 5c 22 2c 20 5c 22  "%w\".\"%w\", \"
b850: 25 77 5c 22 2e 5c 22 25 77 5c 22 20 57 48 45 52  %w\".\"%w\" WHER
b860: 45 20 25 73 20 41 4e 44 20 28 25 7a 29 22 2c 0a  E %s AND (%z)",.
b870: 20 20 20 20 20 20 20 20 70 53 65 73 73 69 6f 6e          pSession
b880: 2d 3e 7a 44 62 2c 20 70 54 61 62 2d 3e 7a 4e 61  ->zDb, pTab->zNa
b890: 6d 65 2c 20 7a 46 72 6f 6d 2c 20 70 54 61 62 2d  me, zFrom, pTab-
b8a0: 3e 7a 4e 61 6d 65 2c 20 7a 45 78 70 72 2c 20 7a  >zName, zExpr, z
b8b0: 45 78 70 72 32 0a 20 20 20 20 29 3b 0a 20 20 20  Expr2.    );.   
b8c0: 20 69 66 28 20 7a 53 74 6d 74 3d 3d 30 20 29 7b   if( zStmt==0 ){
b8d0: 0a 20 20 20 20 20 20 72 63 20 3d 20 53 51 4c 49  .      rc = SQLI
b8e0: 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 20 20 7d 65  TE_NOMEM;.    }e
b8f0: 6c 73 65 7b 0a 20 20 20 20 20 20 73 71 6c 69 74  lse{.      sqlit
b900: 65 33 5f 73 74 6d 74 20 2a 70 53 74 6d 74 3b 0a  e3_stmt *pStmt;.
b910: 20 20 20 20 20 20 72 63 20 3d 20 73 71 6c 69 74        rc = sqlit
b920: 65 33 5f 70 72 65 70 61 72 65 28 70 53 65 73 73  e3_prepare(pSess
b930: 69 6f 6e 2d 3e 64 62 2c 20 7a 53 74 6d 74 2c 20  ion->db, zStmt, 
b940: 2d 31 2c 20 26 70 53 74 6d 74 2c 20 30 29 3b 0a  -1, &pStmt, 0);.
b950: 0a 20 20 20 20 20 20 69 66 28 20 72 63 3d 3d 53  .      if( rc==S
b960: 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20  QLITE_OK ){.    
b970: 20 20 20 20 53 65 73 73 69 6f 6e 44 69 66 66 43      SessionDiffC
b980: 74 78 20 2a 70 44 69 66 66 43 74 78 20 3d 20 28  tx *pDiffCtx = (
b990: 53 65 73 73 69 6f 6e 44 69 66 66 43 74 78 2a 29  SessionDiffCtx*)
b9a0: 70 53 65 73 73 69 6f 6e 2d 3e 68 6f 6f 6b 2e 70  pSession->hook.p
b9b0: 43 74 78 3b 0a 20 20 20 20 20 20 20 20 70 44 69  Ctx;.        pDi
b9c0: 66 66 43 74 78 2d 3e 70 53 74 6d 74 20 3d 20 70  ffCtx->pStmt = p
b9d0: 53 74 6d 74 3b 0a 20 20 20 20 20 20 20 20 70 44  Stmt;.        pD
b9e0: 69 66 66 43 74 78 2d 3e 6e 4f 6c 64 4f 66 66 20  iffCtx->nOldOff 
b9f0: 3d 20 70 54 61 62 2d 3e 6e 43 6f 6c 3b 0a 20 20  = pTab->nCol;.  
ba00: 20 20 20 20 20 20 77 68 69 6c 65 28 20 53 51 4c        while( SQL
ba10: 49 54 45 5f 52 4f 57 3d 3d 73 71 6c 69 74 65 33  ITE_ROW==sqlite3
ba20: 5f 73 74 65 70 28 70 53 74 6d 74 29 20 29 7b 0a  _step(pStmt) ){.
ba30: 20 20 20 20 20 20 20 20 20 20 73 65 73 73 69 6f            sessio
ba40: 6e 50 72 65 75 70 64 61 74 65 4f 6e 65 43 68 61  nPreupdateOneCha
ba50: 6e 67 65 28 53 51 4c 49 54 45 5f 55 50 44 41 54  nge(SQLITE_UPDAT
ba60: 45 2c 20 70 53 65 73 73 69 6f 6e 2c 20 70 54 61  E, pSession, pTa
ba70: 62 29 3b 0a 20 20 20 20 20 20 20 20 7d 0a 20 20  b);.        }.  
ba80: 20 20 20 20 20 20 72 63 20 3d 20 73 71 6c 69 74        rc = sqlit
ba90: 65 33 5f 66 69 6e 61 6c 69 7a 65 28 70 53 74 6d  e3_finalize(pStm
baa0: 74 29 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20 20  t);.      }.    
bab0: 20 20 73 71 6c 69 74 65 33 5f 66 72 65 65 28 7a    sqlite3_free(z
bac0: 53 74 6d 74 29 3b 0a 20 20 20 20 7d 0a 20 20 7d  Stmt);.    }.  }
bad0: 0a 0a 20 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d  ..  return rc;.}
bae0: 0a 0a 69 6e 74 20 73 71 6c 69 74 65 33 73 65 73  ..int sqlite3ses
baf0: 73 69 6f 6e 5f 64 69 66 66 28 0a 20 20 73 71 6c  sion_diff(.  sql
bb00: 69 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a 70 53  ite3_session *pS
bb10: 65 73 73 69 6f 6e 2c 0a 20 20 63 6f 6e 73 74 20  ession,.  const 
bb20: 63 68 61 72 20 2a 7a 46 72 6f 6d 2c 0a 20 20 63  char *zFrom,.  c
bb30: 6f 6e 73 74 20 63 68 61 72 20 2a 7a 54 62 6c 2c  onst char *zTbl,
bb40: 0a 20 20 63 68 61 72 20 2a 2a 70 7a 45 72 72 4d  .  char **pzErrM
bb50: 73 67 0a 29 7b 0a 20 20 63 6f 6e 73 74 20 63 68  sg.){.  const ch
bb60: 61 72 20 2a 7a 44 62 20 3d 20 70 53 65 73 73 69  ar *zDb = pSessi
bb70: 6f 6e 2d 3e 7a 44 62 3b 0a 20 20 69 6e 74 20 72  on->zDb;.  int r
bb80: 63 20 3d 20 70 53 65 73 73 69 6f 6e 2d 3e 72 63  c = pSession->rc
bb90: 3b 0a 20 20 53 65 73 73 69 6f 6e 44 69 66 66 43  ;.  SessionDiffC
bba0: 74 78 20 64 3b 0a 0a 20 20 6d 65 6d 73 65 74 28  tx d;..  memset(
bbb0: 26 64 2c 20 30 2c 20 73 69 7a 65 6f 66 28 64 29  &d, 0, sizeof(d)
bbc0: 29 3b 0a 20 20 73 65 73 73 69 6f 6e 44 69 66 66  );.  sessionDiff
bbd0: 48 6f 6f 6b 73 28 70 53 65 73 73 69 6f 6e 2c 20  Hooks(pSession, 
bbe0: 26 64 29 3b 0a 0a 20 20 73 71 6c 69 74 65 33 5f  &d);..  sqlite3_
bbf0: 6d 75 74 65 78 5f 65 6e 74 65 72 28 73 71 6c 69  mutex_enter(sqli
bc00: 74 65 33 5f 64 62 5f 6d 75 74 65 78 28 70 53 65  te3_db_mutex(pSe
bc10: 73 73 69 6f 6e 2d 3e 64 62 29 29 3b 0a 20 20 69  ssion->db));.  i
bc20: 66 28 20 70 7a 45 72 72 4d 73 67 20 29 20 2a 70  f( pzErrMsg ) *p
bc30: 7a 45 72 72 4d 73 67 20 3d 20 30 3b 0a 20 20 69  zErrMsg = 0;.  i
bc40: 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b  f( rc==SQLITE_OK
bc50: 20 29 7b 0a 20 20 20 20 63 68 61 72 20 2a 7a 45   ){.    char *zE
bc60: 78 70 72 20 3d 20 30 3b 0a 20 20 20 20 73 71 6c  xpr = 0;.    sql
bc70: 69 74 65 33 20 2a 64 62 20 3d 20 70 53 65 73 73  ite3 *db = pSess
bc80: 69 6f 6e 2d 3e 64 62 3b 0a 20 20 20 20 53 65 73  ion->db;.    Ses
bc90: 73 69 6f 6e 54 61 62 6c 65 20 2a 70 54 6f 3b 20  sionTable *pTo; 
bca0: 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 54 61             /* Ta
bcb0: 62 6c 65 20 7a 54 62 6c 20 2a 2f 0a 0a 20 20 20  ble zTbl */..   
bcc0: 20 2f 2a 20 4c 6f 63 61 74 65 20 61 6e 64 20 69   /* Locate and i
bcd0: 66 20 6e 65 63 65 73 73 61 72 79 20 69 6e 69 74  f necessary init
bce0: 69 61 6c 69 7a 65 20 74 68 65 20 74 61 72 67 65  ialize the targe
bcf0: 74 20 74 61 62 6c 65 20 6f 62 6a 65 63 74 20 2a  t table object *
bd00: 2f 0a 20 20 20 20 72 63 20 3d 20 73 65 73 73 69  /.    rc = sessi
bd10: 6f 6e 46 69 6e 64 54 61 62 6c 65 28 70 53 65 73  onFindTable(pSes
bd20: 73 69 6f 6e 2c 20 7a 54 62 6c 2c 20 26 70 54 6f  sion, zTbl, &pTo
bd30: 29 3b 0a 20 20 20 20 69 66 28 20 70 54 6f 3d 3d  );.    if( pTo==
bd40: 30 20 29 20 67 6f 74 6f 20 64 69 66 66 5f 6f 75  0 ) goto diff_ou
bd50: 74 3b 0a 20 20 20 20 69 66 28 20 73 65 73 73 69  t;.    if( sessi
bd60: 6f 6e 49 6e 69 74 54 61 62 6c 65 28 70 53 65 73  onInitTable(pSes
bd70: 73 69 6f 6e 2c 20 70 54 6f 29 20 29 7b 0a 20 20  sion, pTo) ){.  
bd80: 20 20 20 20 72 63 20 3d 20 70 53 65 73 73 69 6f      rc = pSessio
bd90: 6e 2d 3e 72 63 3b 0a 20 20 20 20 20 20 67 6f 74  n->rc;.      got
bda0: 6f 20 64 69 66 66 5f 6f 75 74 3b 0a 20 20 20 20  o diff_out;.    
bdb0: 7d 0a 0a 20 20 20 20 2f 2a 20 43 68 65 63 6b 20  }..    /* Check 
bdc0: 74 68 65 20 74 61 62 6c 65 20 73 63 68 65 6d 61  the table schema
bdd0: 73 20 6d 61 74 63 68 20 2a 2f 0a 20 20 20 20 69  s match */.    i
bde0: 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b  f( rc==SQLITE_OK
bdf0: 20 29 7b 0a 20 20 20 20 20 20 69 6e 74 20 62 48   ){.      int bH
be00: 61 73 50 6b 20 3d 20 30 3b 0a 20 20 20 20 20 20  asPk = 0;.      
be10: 69 6e 74 20 62 4d 69 73 6d 61 74 63 68 20 3d 20  int bMismatch = 
be20: 30 3b 0a 20 20 20 20 20 20 69 6e 74 20 6e 43 6f  0;.      int nCo
be30: 6c 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 20  l;              
be40: 20 20 20 20 20 2f 2a 20 43 6f 6c 75 6d 6e 73 20       /* Columns 
be50: 69 6e 20 7a 46 72 6f 6d 2e 7a 54 62 6c 20 2a 2f  in zFrom.zTbl */
be60: 0a 20 20 20 20 20 20 75 38 20 2a 61 62 50 4b 3b  .      u8 *abPK;
be70: 0a 20 20 20 20 20 20 63 6f 6e 73 74 20 63 68 61  .      const cha
be80: 72 20 2a 2a 61 7a 43 6f 6c 20 3d 20 30 3b 0a 20  r **azCol = 0;. 
be90: 20 20 20 20 20 72 63 20 3d 20 73 65 73 73 69 6f       rc = sessio
bea0: 6e 54 61 62 6c 65 49 6e 66 6f 28 64 62 2c 20 7a  nTableInfo(db, z
beb0: 46 72 6f 6d 2c 20 7a 54 62 6c 2c 20 26 6e 43 6f  From, zTbl, &nCo
bec0: 6c 2c 20 30 2c 20 26 61 7a 43 6f 6c 2c 20 26 61  l, 0, &azCol, &a
bed0: 62 50 4b 29 3b 0a 20 20 20 20 20 20 69 66 28 20  bPK);.      if( 
bee0: 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b  rc==SQLITE_OK ){
bef0: 0a 20 20 20 20 20 20 20 20 69 66 28 20 70 54 6f  .        if( pTo
bf00: 2d 3e 6e 43 6f 6c 21 3d 6e 43 6f 6c 20 29 7b 0a  ->nCol!=nCol ){.
bf10: 20 20 20 20 20 20 20 20 20 20 62 4d 69 73 6d 61            bMisma
bf20: 74 63 68 20 3d 20 31 3b 0a 20 20 20 20 20 20 20  tch = 1;.       
bf30: 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 20 20   }else{.        
bf40: 20 20 69 6e 74 20 69 3b 0a 20 20 20 20 20 20 20    int i;.       
bf50: 20 20 20 66 6f 72 28 69 3d 30 3b 20 69 3c 6e 43     for(i=0; i<nC
bf60: 6f 6c 3b 20 69 2b 2b 29 7b 0a 20 20 20 20 20 20  ol; i++){.      
bf70: 20 20 20 20 20 20 69 66 28 20 70 54 6f 2d 3e 61        if( pTo->a
bf80: 62 50 4b 5b 69 5d 21 3d 61 62 50 4b 5b 69 5d 20  bPK[i]!=abPK[i] 
bf90: 29 20 62 4d 69 73 6d 61 74 63 68 20 3d 20 31 3b  ) bMismatch = 1;
bfa0: 0a 20 20 20 20 20 20 20 20 20 20 20 20 69 66 28  .            if(
bfb0: 20 73 71 6c 69 74 65 33 5f 73 74 72 69 63 6d 70   sqlite3_stricmp
bfc0: 28 61 7a 43 6f 6c 5b 69 5d 2c 20 70 54 6f 2d 3e  (azCol[i], pTo->
bfd0: 61 7a 43 6f 6c 5b 69 5d 29 20 29 20 62 4d 69 73  azCol[i]) ) bMis
bfe0: 6d 61 74 63 68 20 3d 20 31 3b 0a 20 20 20 20 20  match = 1;.     
bff0: 20 20 20 20 20 20 20 69 66 28 20 61 62 50 4b 5b         if( abPK[
c000: 69 5d 20 29 20 62 48 61 73 50 6b 20 3d 20 31 3b  i] ) bHasPk = 1;
c010: 0a 20 20 20 20 20 20 20 20 20 20 7d 0a 20 20 20  .          }.   
c020: 20 20 20 20 20 7d 0a 0a 20 20 20 20 20 20 7d 0a       }..      }.
c030: 20 20 20 20 20 20 73 71 6c 69 74 65 33 5f 66 72        sqlite3_fr
c040: 65 65 28 28 63 68 61 72 2a 29 61 7a 43 6f 6c 29  ee((char*)azCol)
c050: 3b 0a 20 20 20 20 20 20 69 66 28 20 62 4d 69 73  ;.      if( bMis
c060: 6d 61 74 63 68 20 29 7b 0a 20 20 20 20 20 20 20  match ){.       
c070: 20 2a 70 7a 45 72 72 4d 73 67 20 3d 20 73 71 6c   *pzErrMsg = sql
c080: 69 74 65 33 5f 6d 70 72 69 6e 74 66 28 22 74 61  ite3_mprintf("ta
c090: 62 6c 65 20 73 63 68 65 6d 61 73 20 64 6f 20 6e  ble schemas do n
c0a0: 6f 74 20 6d 61 74 63 68 22 29 3b 0a 20 20 20 20  ot match");.    
c0b0: 20 20 20 20 72 63 20 3d 20 53 51 4c 49 54 45 5f      rc = SQLITE_
c0c0: 53 43 48 45 4d 41 3b 0a 20 20 20 20 20 20 7d 0a  SCHEMA;.      }.
c0d0: 20 20 20 20 20 20 69 66 28 20 62 48 61 73 50 6b        if( bHasPk
c0e0: 3d 3d 30 20 29 7b 0a 20 20 20 20 20 20 20 20 2f  ==0 ){.        /
c0f0: 2a 20 49 67 6e 6f 72 65 20 74 61 62 6c 65 73 20  * Ignore tables 
c100: 77 69 74 68 20 6e 6f 20 70 72 69 6d 61 72 79 20  with no primary 
c110: 6b 65 79 73 20 2a 2f 0a 20 20 20 20 20 20 20 20  keys */.        
c120: 67 6f 74 6f 20 64 69 66 66 5f 6f 75 74 3b 0a 20  goto diff_out;. 
c130: 20 20 20 20 20 7d 0a 20 20 20 20 7d 0a 0a 20 20       }.    }..  
c140: 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54 45    if( rc==SQLITE
c150: 5f 4f 4b 20 29 7b 0a 20 20 20 20 20 20 7a 45 78  _OK ){.      zEx
c160: 70 72 20 3d 20 73 65 73 73 69 6f 6e 45 78 70 72  pr = sessionExpr
c170: 43 6f 6d 70 61 72 65 50 4b 28 70 54 6f 2d 3e 6e  ComparePK(pTo->n
c180: 43 6f 6c 2c 20 0a 20 20 20 20 20 20 20 20 20 20  Col, .          
c190: 7a 44 62 2c 20 7a 46 72 6f 6d 2c 20 70 54 6f 2d  zDb, zFrom, pTo-
c1a0: 3e 7a 4e 61 6d 65 2c 20 70 54 6f 2d 3e 61 7a 43  >zName, pTo->azC
c1b0: 6f 6c 2c 20 70 54 6f 2d 3e 61 62 50 4b 0a 20 20  ol, pTo->abPK.  
c1c0: 20 20 20 20 29 3b 0a 20 20 20 20 7d 0a 0a 20 20      );.    }..  
c1d0: 20 20 2f 2a 20 46 69 6e 64 20 6e 65 77 20 72 6f    /* Find new ro
c1e0: 77 73 20 2a 2f 0a 20 20 20 20 69 66 28 20 72 63  ws */.    if( rc
c1f0: 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20  ==SQLITE_OK ){. 
c200: 20 20 20 20 20 72 63 20 3d 20 73 65 73 73 69 6f       rc = sessio
c210: 6e 44 69 66 66 46 69 6e 64 4e 65 77 28 53 51 4c  nDiffFindNew(SQL
c220: 49 54 45 5f 49 4e 53 45 52 54 2c 20 70 53 65 73  ITE_INSERT, pSes
c230: 73 69 6f 6e 2c 20 70 54 6f 2c 20 7a 44 62 2c 20  sion, pTo, zDb, 
c240: 7a 46 72 6f 6d 2c 20 7a 45 78 70 72 29 3b 0a 20  zFrom, zExpr);. 
c250: 20 20 20 7d 0a 0a 20 20 20 20 2f 2a 20 46 69 6e     }..    /* Fin
c260: 64 20 6f 6c 64 20 72 6f 77 73 20 2a 2f 0a 20 20  d old rows */.  
c270: 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54 45    if( rc==SQLITE
c280: 5f 4f 4b 20 29 7b 0a 20 20 20 20 20 20 72 63 20  _OK ){.      rc 
c290: 3d 20 73 65 73 73 69 6f 6e 44 69 66 66 46 69 6e  = sessionDiffFin
c2a0: 64 4e 65 77 28 53 51 4c 49 54 45 5f 44 45 4c 45  dNew(SQLITE_DELE
c2b0: 54 45 2c 20 70 53 65 73 73 69 6f 6e 2c 20 70 54  TE, pSession, pT
c2c0: 6f 2c 20 7a 46 72 6f 6d 2c 20 7a 44 62 2c 20 7a  o, zFrom, zDb, z
c2d0: 45 78 70 72 29 3b 0a 20 20 20 20 7d 0a 0a 20 20  Expr);.    }..  
c2e0: 20 20 2f 2a 20 46 69 6e 64 20 6d 6f 64 69 66 69    /* Find modifi
c2f0: 65 64 20 72 6f 77 73 20 2a 2f 0a 20 20 20 20 69  ed rows */.    i
c300: 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b  f( rc==SQLITE_OK
c310: 20 29 7b 0a 20 20 20 20 20 20 72 63 20 3d 20 73   ){.      rc = s
c320: 65 73 73 69 6f 6e 44 69 66 66 46 69 6e 64 4d 6f  essionDiffFindMo
c330: 64 69 66 69 65 64 28 70 53 65 73 73 69 6f 6e 2c  dified(pSession,
c340: 20 70 54 6f 2c 20 7a 46 72 6f 6d 2c 20 7a 45 78   pTo, zFrom, zEx
c350: 70 72 29 3b 0a 20 20 20 20 7d 0a 0a 20 20 20 20  pr);.    }..    
c360: 73 71 6c 69 74 65 33 5f 66 72 65 65 28 7a 45 78  sqlite3_free(zEx
c370: 70 72 29 3b 0a 20 20 7d 0a 0a 20 64 69 66 66 5f  pr);.  }.. diff_
c380: 6f 75 74 3a 0a 20 20 73 65 73 73 69 6f 6e 50 72  out:.  sessionPr
c390: 65 75 70 64 61 74 65 48 6f 6f 6b 73 28 70 53 65  eupdateHooks(pSe
c3a0: 73 73 69 6f 6e 29 3b 0a 20 20 73 71 6c 69 74 65  ssion);.  sqlite
c3b0: 33 5f 6d 75 74 65 78 5f 6c 65 61 76 65 28 73 71  3_mutex_leave(sq
c3c0: 6c 69 74 65 33 5f 64 62 5f 6d 75 74 65 78 28 70  lite3_db_mutex(p
c3d0: 53 65 73 73 69 6f 6e 2d 3e 64 62 29 29 3b 0a 20  Session->db));. 
c3e0: 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f   return rc;.}../
c3f0: 2a 0a 2a 2a 20 43 72 65 61 74 65 20 61 20 73 65  *.** Create a se
c400: 73 73 69 6f 6e 20 6f 62 6a 65 63 74 2e 20 54 68  ssion object. Th
c410: 69 73 20 73 65 73 73 69 6f 6e 20 6f 62 6a 65 63  is session objec
c420: 74 20 77 69 6c 6c 20 72 65 63 6f 72 64 20 63 68  t will record ch
c430: 61 6e 67 65 73 20 74 6f 0a 2a 2a 20 64 61 74 61  anges to.** data
c440: 62 61 73 65 20 7a 44 62 20 61 74 74 61 63 68 65  base zDb attache
c450: 64 20 74 6f 20 63 6f 6e 6e 65 63 74 69 6f 6e 20  d to connection 
c460: 64 62 2e 0a 2a 2f 0a 69 6e 74 20 73 71 6c 69 74  db..*/.int sqlit
c470: 65 33 73 65 73 73 69 6f 6e 5f 63 72 65 61 74 65  e3session_create
c480: 28 0a 20 20 73 71 6c 69 74 65 33 20 2a 64 62 2c  (.  sqlite3 *db,
c490: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
c4a0: 20 20 20 20 2f 2a 20 44 61 74 61 62 61 73 65 20      /* Database 
c4b0: 68 61 6e 64 6c 65 20 2a 2f 0a 20 20 63 6f 6e 73  handle */.  cons
c4c0: 74 20 63 68 61 72 20 2a 7a 44 62 2c 20 20 20 20  t char *zDb,    
c4d0: 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4e              /* N
c4e0: 61 6d 65 20 6f 66 20 64 62 20 28 65 2e 67 2e 20  ame of db (e.g. 
c4f0: 22 6d 61 69 6e 22 29 20 2a 2f 0a 20 20 73 71 6c  "main") */.  sql
c500: 69 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a 2a 70  ite3_session **p
c510: 70 53 65 73 73 69 6f 6e 20 20 20 20 20 2f 2a 20  pSession     /* 
c520: 4f 55 54 3a 20 4e 65 77 20 73 65 73 73 69 6f 6e  OUT: New session
c530: 20 6f 62 6a 65 63 74 20 2a 2f 0a 29 7b 0a 20 20   object */.){.  
c540: 73 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20  sqlite3_session 
c550: 2a 70 4e 65 77 3b 20 20 20 20 20 20 20 20 20 20  *pNew;          
c560: 2f 2a 20 4e 65 77 6c 79 20 61 6c 6c 6f 63 61 74  /* Newly allocat
c570: 65 64 20 73 65 73 73 69 6f 6e 20 6f 62 6a 65 63  ed session objec
c580: 74 20 2a 2f 0a 20 20 73 71 6c 69 74 65 33 5f 73  t */.  sqlite3_s
c590: 65 73 73 69 6f 6e 20 2a 70 4f 6c 64 3b 20 20 20  ession *pOld;   
c5a0: 20 20 20 20 20 20 20 2f 2a 20 53 65 73 73 69 6f         /* Sessio
c5b0: 6e 20 6f 62 6a 65 63 74 20 61 6c 72 65 61 64 79  n object already
c5c0: 20 61 74 74 61 63 68 65 64 20 74 6f 20 64 62 20   attached to db 
c5d0: 2a 2f 0a 20 20 69 6e 74 20 6e 44 62 20 3d 20 73  */.  int nDb = s
c5e0: 71 6c 69 74 65 33 53 74 72 6c 65 6e 33 30 28 7a  qlite3Strlen30(z
c5f0: 44 62 29 3b 20 2f 2a 20 4c 65 6e 67 74 68 20 6f  Db); /* Length o
c600: 66 20 7a 44 62 20 69 6e 20 62 79 74 65 73 20 2a  f zDb in bytes *
c610: 2f 0a 0a 20 20 2f 2a 20 5a 65 72 6f 20 74 68 65  /..  /* Zero the
c620: 20 6f 75 74 70 75 74 20 76 61 6c 75 65 20 69 6e   output value in
c630: 20 63 61 73 65 20 61 6e 20 65 72 72 6f 72 20 6f   case an error o
c640: 63 63 75 72 73 2e 20 2a 2f 0a 20 20 2a 70 70 53  ccurs. */.  *ppS
c650: 65 73 73 69 6f 6e 20 3d 20 30 3b 0a 0a 20 20 2f  ession = 0;..  /
c660: 2a 20 41 6c 6c 6f 63 61 74 65 20 61 6e 64 20 70  * Allocate and p
c670: 6f 70 75 6c 61 74 65 20 74 68 65 20 6e 65 77 20  opulate the new 
c680: 73 65 73 73 69 6f 6e 20 6f 62 6a 65 63 74 2e 20  session object. 
c690: 2a 2f 0a 20 20 70 4e 65 77 20 3d 20 28 73 71 6c  */.  pNew = (sql
c6a0: 69 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a 29 73  ite3_session *)s
c6b0: 71 6c 69 74 65 33 5f 6d 61 6c 6c 6f 63 28 73 69  qlite3_malloc(si
c6c0: 7a 65 6f 66 28 73 71 6c 69 74 65 33 5f 73 65 73  zeof(sqlite3_ses
c6d0: 73 69 6f 6e 29 20 2b 20 6e 44 62 20 2b 20 31 29  sion) + nDb + 1)
c6e0: 3b 0a 20 20 69 66 28 20 21 70 4e 65 77 20 29 20  ;.  if( !pNew ) 
c6f0: 72 65 74 75 72 6e 20 53 51 4c 49 54 45 5f 4e 4f  return SQLITE_NO
c700: 4d 45 4d 3b 0a 20 20 6d 65 6d 73 65 74 28 70 4e  MEM;.  memset(pN
c710: 65 77 2c 20 30 2c 20 73 69 7a 65 6f 66 28 73 71  ew, 0, sizeof(sq
c720: 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 29 29 3b  lite3_session));
c730: 0a 20 20 70 4e 65 77 2d 3e 64 62 20 3d 20 64 62  .  pNew->db = db
c740: 3b 0a 20 20 70 4e 65 77 2d 3e 7a 44 62 20 3d 20  ;.  pNew->zDb = 
c750: 28 63 68 61 72 20 2a 29 26 70 4e 65 77 5b 31 5d  (char *)&pNew[1]
c760: 3b 0a 20 20 70 4e 65 77 2d 3e 62 45 6e 61 62 6c  ;.  pNew->bEnabl
c770: 65 20 3d 20 31 3b 0a 20 20 6d 65 6d 63 70 79 28  e = 1;.  memcpy(
c780: 70 4e 65 77 2d 3e 7a 44 62 2c 20 7a 44 62 2c 20  pNew->zDb, zDb, 
c790: 6e 44 62 2b 31 29 3b 0a 20 20 73 65 73 73 69 6f  nDb+1);.  sessio
c7a0: 6e 50 72 65 75 70 64 61 74 65 48 6f 6f 6b 73 28  nPreupdateHooks(
c7b0: 70 4e 65 77 29 3b 0a 0a 20 20 2f 2a 20 41 64 64  pNew);..  /* Add
c7c0: 20 74 68 65 20 6e 65 77 20 73 65 73 73 69 6f 6e   the new session
c7d0: 20 6f 62 6a 65 63 74 20 74 6f 20 74 68 65 20 6c   object to the l
c7e0: 69 6e 6b 65 64 20 6c 69 73 74 20 6f 66 20 73 65  inked list of se
c7f0: 73 73 69 6f 6e 20 6f 62 6a 65 63 74 73 20 0a 20  ssion objects . 
c800: 20 2a 2a 20 61 74 74 61 63 68 65 64 20 74 6f 20   ** attached to 
c810: 64 61 74 61 62 61 73 65 20 68 61 6e 64 6c 65 20  database handle 
c820: 24 64 62 2e 20 44 6f 20 74 68 69 73 20 75 6e 64  $db. Do this und
c830: 65 72 20 74 68 65 20 63 6f 76 65 72 20 6f 66 20  er the cover of 
c840: 74 68 65 20 64 62 0a 20 20 2a 2a 20 68 61 6e 64  the db.  ** hand
c850: 6c 65 20 6d 75 74 65 78 2e 20 20 2a 2f 0a 20 20  le mutex.  */.  
c860: 73 71 6c 69 74 65 33 5f 6d 75 74 65 78 5f 65 6e  sqlite3_mutex_en
c870: 74 65 72 28 73 71 6c 69 74 65 33 5f 64 62 5f 6d  ter(sqlite3_db_m
c880: 75 74 65 78 28 64 62 29 29 3b 0a 20 20 70 4f 6c  utex(db));.  pOl
c890: 64 20 3d 20 28 73 71 6c 69 74 65 33 5f 73 65 73  d = (sqlite3_ses
c8a0: 73 69 6f 6e 2a 29 73 71 6c 69 74 65 33 5f 70 72  sion*)sqlite3_pr
c8b0: 65 75 70 64 61 74 65 5f 68 6f 6f 6b 28 64 62 2c  eupdate_hook(db,
c8c0: 20 78 50 72 65 55 70 64 61 74 65 2c 20 28 76 6f   xPreUpdate, (vo
c8d0: 69 64 2a 29 70 4e 65 77 29 3b 0a 20 20 70 4e 65  id*)pNew);.  pNe
c8e0: 77 2d 3e 70 4e 65 78 74 20 3d 20 70 4f 6c 64 3b  w->pNext = pOld;
c8f0: 0a 20 20 73 71 6c 69 74 65 33 5f 6d 75 74 65 78  .  sqlite3_mutex
c900: 5f 6c 65 61 76 65 28 73 71 6c 69 74 65 33 5f 64  _leave(sqlite3_d
c910: 62 5f 6d 75 74 65 78 28 64 62 29 29 3b 0a 0a 20  b_mutex(db));.. 
c920: 20 2a 70 70 53 65 73 73 69 6f 6e 20 3d 20 70 4e   *ppSession = pN
c930: 65 77 3b 0a 20 20 72 65 74 75 72 6e 20 53 51 4c  ew;.  return SQL
c940: 49 54 45 5f 4f 4b 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a  ITE_OK;.}../*.**
c950: 20 46 72 65 65 20 74 68 65 20 6c 69 73 74 20 6f   Free the list o
c960: 66 20 74 61 62 6c 65 20 6f 62 6a 65 63 74 73 20  f table objects 
c970: 70 61 73 73 65 64 20 61 73 20 74 68 65 20 66 69  passed as the fi
c980: 72 73 74 20 61 72 67 75 6d 65 6e 74 2e 20 54 68  rst argument. Th
c990: 65 20 63 6f 6e 74 65 6e 74 73 0a 2a 2a 20 6f 66  e contents.** of
c9a0: 20 74 68 65 20 63 68 61 6e 67 65 64 2d 72 6f 77   the changed-row
c9b0: 73 20 68 61 73 68 20 74 61 62 6c 65 73 20 61 72  s hash tables ar
c9c0: 65 20 61 6c 73 6f 20 64 65 6c 65 74 65 64 2e 0a  e also deleted..
c9d0: 2a 2f 0a 73 74 61 74 69 63 20 76 6f 69 64 20 73  */.static void s
c9e0: 65 73 73 69 6f 6e 44 65 6c 65 74 65 54 61 62 6c  essionDeleteTabl
c9f0: 65 28 53 65 73 73 69 6f 6e 54 61 62 6c 65 20 2a  e(SessionTable *
ca00: 70 4c 69 73 74 29 7b 0a 20 20 53 65 73 73 69 6f  pList){.  Sessio
ca10: 6e 54 61 62 6c 65 20 2a 70 4e 65 78 74 3b 0a 20  nTable *pNext;. 
ca20: 20 53 65 73 73 69 6f 6e 54 61 62 6c 65 20 2a 70   SessionTable *p
ca30: 54 61 62 3b 0a 0a 20 20 66 6f 72 28 70 54 61 62  Tab;..  for(pTab
ca40: 3d 70 4c 69 73 74 3b 20 70 54 61 62 3b 20 70 54  =pList; pTab; pT
ca50: 61 62 3d 70 4e 65 78 74 29 7b 0a 20 20 20 20 69  ab=pNext){.    i
ca60: 6e 74 20 69 3b 0a 20 20 20 20 70 4e 65 78 74 20  nt i;.    pNext 
ca70: 3d 20 70 54 61 62 2d 3e 70 4e 65 78 74 3b 0a 20  = pTab->pNext;. 
ca80: 20 20 20 66 6f 72 28 69 3d 30 3b 20 69 3c 70 54     for(i=0; i<pT
ca90: 61 62 2d 3e 6e 43 68 61 6e 67 65 3b 20 69 2b 2b  ab->nChange; i++
caa0: 29 7b 0a 20 20 20 20 20 20 53 65 73 73 69 6f 6e  ){.      Session
cab0: 43 68 61 6e 67 65 20 2a 70 3b 0a 20 20 20 20 20  Change *p;.     
cac0: 20 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 20 2a   SessionChange *
cad0: 70 4e 65 78 74 43 68 61 6e 67 65 3b 0a 20 20 20  pNextChange;.   
cae0: 20 20 20 66 6f 72 28 70 3d 70 54 61 62 2d 3e 61     for(p=pTab->a
caf0: 70 43 68 61 6e 67 65 5b 69 5d 3b 20 70 3b 20 70  pChange[i]; p; p
cb00: 3d 70 4e 65 78 74 43 68 61 6e 67 65 29 7b 0a 20  =pNextChange){. 
cb10: 20 20 20 20 20 20 20 70 4e 65 78 74 43 68 61 6e         pNextChan
cb20: 67 65 20 3d 20 70 2d 3e 70 4e 65 78 74 3b 0a 20  ge = p->pNext;. 
cb30: 20 20 20 20 20 20 20 73 71 6c 69 74 65 33 5f 66         sqlite3_f
cb40: 72 65 65 28 70 29 3b 0a 20 20 20 20 20 20 7d 0a  ree(p);.      }.
cb50: 20 20 20 20 7d 0a 20 20 20 20 73 71 6c 69 74 65      }.    sqlite
cb60: 33 5f 66 72 65 65 28 28 63 68 61 72 2a 29 70 54  3_free((char*)pT
cb70: 61 62 2d 3e 61 7a 43 6f 6c 29 3b 20 20 2f 2a 20  ab->azCol);  /* 
cb80: 63 61 73 74 20 77 6f 72 6b 73 20 61 72 6f 75 6e  cast works aroun
cb90: 64 20 56 43 2b 2b 20 62 75 67 20 2a 2f 0a 20 20  d VC++ bug */.  
cba0: 20 20 73 71 6c 69 74 65 33 5f 66 72 65 65 28 70    sqlite3_free(p
cbb0: 54 61 62 2d 3e 61 70 43 68 61 6e 67 65 29 3b 0a  Tab->apChange);.
cbc0: 20 20 20 20 73 71 6c 69 74 65 33 5f 66 72 65 65      sqlite3_free
cbd0: 28 70 54 61 62 29 3b 0a 20 20 7d 0a 7d 0a 0a 2f  (pTab);.  }.}../
cbe0: 2a 0a 2a 2a 20 44 65 6c 65 74 65 20 61 20 73 65  *.** Delete a se
cbf0: 73 73 69 6f 6e 20 6f 62 6a 65 63 74 20 70 72 65  ssion object pre
cc00: 76 69 6f 75 73 6c 79 20 61 6c 6c 6f 63 61 74 65  viously allocate
cc10: 64 20 75 73 69 6e 67 20 73 71 6c 69 74 65 33 73  d using sqlite3s
cc20: 65 73 73 69 6f 6e 5f 63 72 65 61 74 65 28 29 2e  ession_create().
cc30: 0a 2a 2f 0a 76 6f 69 64 20 73 71 6c 69 74 65 33  .*/.void sqlite3
cc40: 73 65 73 73 69 6f 6e 5f 64 65 6c 65 74 65 28 73  session_delete(s
cc50: 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a  qlite3_session *
cc60: 70 53 65 73 73 69 6f 6e 29 7b 0a 20 20 73 71 6c  pSession){.  sql
cc70: 69 74 65 33 20 2a 64 62 20 3d 20 70 53 65 73 73  ite3 *db = pSess
cc80: 69 6f 6e 2d 3e 64 62 3b 0a 20 20 73 71 6c 69 74  ion->db;.  sqlit
cc90: 65 33 5f 73 65 73 73 69 6f 6e 20 2a 70 48 65 61  e3_session *pHea
cca0: 64 3b 0a 20 20 73 71 6c 69 74 65 33 5f 73 65 73  d;.  sqlite3_ses
ccb0: 73 69 6f 6e 20 2a 2a 70 70 3b 0a 0a 20 20 2f 2a  sion **pp;..  /*
ccc0: 20 55 6e 6c 69 6e 6b 20 74 68 65 20 73 65 73 73   Unlink the sess
ccd0: 69 6f 6e 20 66 72 6f 6d 20 74 68 65 20 6c 69 6e  ion from the lin
cce0: 6b 65 64 20 6c 69 73 74 20 6f 66 20 73 65 73 73  ked list of sess
ccf0: 69 6f 6e 73 20 61 74 74 61 63 68 65 64 20 74 6f  ions attached to
cd00: 20 74 68 65 0a 20 20 2a 2a 20 64 61 74 61 62 61   the.  ** databa
cd10: 73 65 20 68 61 6e 64 6c 65 2e 20 48 6f 6c 64 20  se handle. Hold 
cd20: 74 68 65 20 64 62 20 6d 75 74 65 78 20 77 68 69  the db mutex whi
cd30: 6c 65 20 64 6f 69 6e 67 20 73 6f 2e 20 20 2a 2f  le doing so.  */
cd40: 0a 20 20 73 71 6c 69 74 65 33 5f 6d 75 74 65 78  .  sqlite3_mutex
cd50: 5f 65 6e 74 65 72 28 73 71 6c 69 74 65 33 5f 64  _enter(sqlite3_d
cd60: 62 5f 6d 75 74 65 78 28 64 62 29 29 3b 0a 20 20  b_mutex(db));.  
cd70: 70 48 65 61 64 20 3d 20 28 73 71 6c 69 74 65 33  pHead = (sqlite3
cd80: 5f 73 65 73 73 69 6f 6e 2a 29 73 71 6c 69 74 65  _session*)sqlite
cd90: 33 5f 70 72 65 75 70 64 61 74 65 5f 68 6f 6f 6b  3_preupdate_hook
cda0: 28 64 62 2c 20 30 2c 20 30 29 3b 0a 20 20 66 6f  (db, 0, 0);.  fo
cdb0: 72 28 70 70 3d 26 70 48 65 61 64 3b 20 41 4c 57  r(pp=&pHead; ALW
cdc0: 41 59 53 28 28 2a 70 70 29 21 3d 30 29 3b 20 70  AYS((*pp)!=0); p
cdd0: 70 3d 26 28 28 2a 70 70 29 2d 3e 70 4e 65 78 74  p=&((*pp)->pNext
cde0: 29 29 7b 0a 20 20 20 20 69 66 28 20 28 2a 70 70  )){.    if( (*pp
cdf0: 29 3d 3d 70 53 65 73 73 69 6f 6e 20 29 7b 0a 20  )==pSession ){. 
ce00: 20 20 20 20 20 2a 70 70 20 3d 20 28 2a 70 70 29       *pp = (*pp)
ce10: 2d 3e 70 4e 65 78 74 3b 0a 20 20 20 20 20 20 69  ->pNext;.      i
ce20: 66 28 20 70 48 65 61 64 20 29 20 73 71 6c 69 74  f( pHead ) sqlit
ce30: 65 33 5f 70 72 65 75 70 64 61 74 65 5f 68 6f 6f  e3_preupdate_hoo
ce40: 6b 28 64 62 2c 20 78 50 72 65 55 70 64 61 74 65  k(db, xPreUpdate
ce50: 2c 20 28 76 6f 69 64 2a 29 70 48 65 61 64 29 3b  , (void*)pHead);
ce60: 0a 20 20 20 20 20 20 62 72 65 61 6b 3b 0a 20 20  .      break;.  
ce70: 20 20 7d 0a 20 20 7d 0a 20 20 73 71 6c 69 74 65    }.  }.  sqlite
ce80: 33 5f 6d 75 74 65 78 5f 6c 65 61 76 65 28 73 71  3_mutex_leave(sq
ce90: 6c 69 74 65 33 5f 64 62 5f 6d 75 74 65 78 28 64  lite3_db_mutex(d
cea0: 62 29 29 3b 0a 0a 20 20 2f 2a 20 44 65 6c 65 74  b));..  /* Delet
ceb0: 65 20 61 6c 6c 20 61 74 74 61 63 68 65 64 20 74  e all attached t
cec0: 61 62 6c 65 20 6f 62 6a 65 63 74 73 2e 20 41 6e  able objects. An
ced0: 64 20 74 68 65 20 63 6f 6e 74 65 6e 74 73 20 6f  d the contents o
cee0: 66 20 74 68 65 69 72 20 0a 20 20 2a 2a 20 61 73  f their .  ** as
cef0: 73 6f 63 69 61 74 65 64 20 68 61 73 68 2d 74 61  sociated hash-ta
cf00: 62 6c 65 73 2e 20 2a 2f 0a 20 20 73 65 73 73 69  bles. */.  sessi
cf10: 6f 6e 44 65 6c 65 74 65 54 61 62 6c 65 28 70 53  onDeleteTable(pS
cf20: 65 73 73 69 6f 6e 2d 3e 70 54 61 62 6c 65 29 3b  ession->pTable);
cf30: 0a 0a 20 20 2f 2a 20 46 72 65 65 20 74 68 65 20  ..  /* Free the 
cf40: 73 65 73 73 69 6f 6e 20 6f 62 6a 65 63 74 20 69  session object i
cf50: 74 73 65 6c 66 2e 20 2a 2f 0a 20 20 73 71 6c 69  tself. */.  sqli
cf60: 74 65 33 5f 66 72 65 65 28 70 53 65 73 73 69 6f  te3_free(pSessio
cf70: 6e 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 53 65 74  n);.}../*.** Set
cf80: 20 61 20 74 61 62 6c 65 20 66 69 6c 74 65 72 20   a table filter 
cf90: 6f 6e 20 61 20 53 65 73 73 69 6f 6e 20 4f 62 6a  on a Session Obj
cfa0: 65 63 74 2e 0a 2a 2f 0a 76 6f 69 64 20 73 71 6c  ect..*/.void sql
cfb0: 69 74 65 33 73 65 73 73 69 6f 6e 5f 74 61 62 6c  ite3session_tabl
cfc0: 65 5f 66 69 6c 74 65 72 28 0a 20 20 73 71 6c 69  e_filter(.  sqli
cfd0: 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a 70 53 65  te3_session *pSe
cfe0: 73 73 69 6f 6e 2c 20 0a 20 20 69 6e 74 28 2a 78  ssion, .  int(*x
cff0: 46 69 6c 74 65 72 29 28 76 6f 69 64 2a 2c 20 63  Filter)(void*, c
d000: 6f 6e 73 74 20 63 68 61 72 2a 29 2c 0a 20 20 76  onst char*),.  v
d010: 6f 69 64 20 2a 70 43 74 78 20 20 20 20 20 20 20  oid *pCtx       
d020: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
d030: 2a 20 46 69 72 73 74 20 61 72 67 75 6d 65 6e 74  * First argument
d040: 20 70 61 73 73 65 64 20 74 6f 20 78 46 69 6c 74   passed to xFilt
d050: 65 72 20 2a 2f 0a 29 7b 0a 20 20 70 53 65 73 73  er */.){.  pSess
d060: 69 6f 6e 2d 3e 62 41 75 74 6f 41 74 74 61 63 68  ion->bAutoAttach
d070: 20 3d 20 31 3b 0a 20 20 70 53 65 73 73 69 6f 6e   = 1;.  pSession
d080: 2d 3e 70 46 69 6c 74 65 72 43 74 78 20 3d 20 70  ->pFilterCtx = p
d090: 43 74 78 3b 0a 20 20 70 53 65 73 73 69 6f 6e 2d  Ctx;.  pSession-
d0a0: 3e 78 54 61 62 6c 65 46 69 6c 74 65 72 20 3d 20  >xTableFilter = 
d0b0: 78 46 69 6c 74 65 72 3b 0a 7d 0a 0a 2f 2a 0a 2a  xFilter;.}../*.*
d0c0: 2a 20 41 74 74 61 63 68 20 61 20 74 61 62 6c 65  * Attach a table
d0d0: 20 74 6f 20 61 20 73 65 73 73 69 6f 6e 2e 20 41   to a session. A
d0e0: 6c 6c 20 73 75 62 73 65 71 75 65 6e 74 20 63 68  ll subsequent ch
d0f0: 61 6e 67 65 73 20 6d 61 64 65 20 74 6f 20 74 68  anges made to th
d100: 65 20 74 61 62 6c 65 0a 2a 2a 20 77 68 69 6c 65  e table.** while
d110: 20 74 68 65 20 73 65 73 73 69 6f 6e 20 6f 62 6a   the session obj
d120: 65 63 74 20 69 73 20 65 6e 61 62 6c 65 64 20 77  ect is enabled w
d130: 69 6c 6c 20 62 65 20 72 65 63 6f 72 64 65 64 2e  ill be recorded.
d140: 0a 2a 2a 0a 2a 2a 20 4f 6e 6c 79 20 74 61 62 6c  .**.** Only tabl
d150: 65 73 20 74 68 61 74 20 68 61 76 65 20 61 20 50  es that have a P
d160: 52 49 4d 41 52 59 20 4b 45 59 20 64 65 66 69 6e  RIMARY KEY defin
d170: 65 64 20 6d 61 79 20 62 65 20 61 74 74 61 63 68  ed may be attach
d180: 65 64 2e 20 49 74 20 64 6f 65 73 0a 2a 2a 20 6e  ed. It does.** n
d190: 6f 74 20 6d 61 74 74 65 72 20 69 66 20 74 68 65  ot matter if the
d1a0: 20 50 52 49 4d 41 52 59 20 4b 45 59 20 69 73 20   PRIMARY KEY is 
d1b0: 61 6e 20 22 49 4e 54 45 47 45 52 20 50 52 49 4d  an "INTEGER PRIM
d1c0: 41 52 59 20 4b 45 59 22 20 28 72 6f 77 69 64 20  ARY KEY" (rowid 
d1d0: 61 6c 69 61 73 29 0a 2a 2a 20 6f 72 20 6e 6f 74  alias).** or not
d1e0: 2e 0a 2a 2f 0a 69 6e 74 20 73 71 6c 69 74 65 33  ..*/.int sqlite3
d1f0: 73 65 73 73 69 6f 6e 5f 61 74 74 61 63 68 28 0a  session_attach(.
d200: 20 20 73 71 6c 69 74 65 33 5f 73 65 73 73 69 6f    sqlite3_sessio
d210: 6e 20 2a 70 53 65 73 73 69 6f 6e 2c 20 20 20 20  n *pSession,    
d220: 20 20 2f 2a 20 53 65 73 73 69 6f 6e 20 6f 62 6a    /* Session obj
d230: 65 63 74 20 2a 2f 0a 20 20 63 6f 6e 73 74 20 63  ect */.  const c
d240: 68 61 72 20 2a 7a 4e 61 6d 65 20 20 20 20 20 20  har *zName      
d250: 20 20 20 20 20 20 20 20 20 2f 2a 20 54 61 62 6c           /* Tabl
d260: 65 20 6e 61 6d 65 20 2a 2f 0a 29 7b 0a 20 20 69  e name */.){.  i
d270: 6e 74 20 72 63 20 3d 20 53 51 4c 49 54 45 5f 4f  nt rc = SQLITE_O
d280: 4b 3b 0a 20 20 73 71 6c 69 74 65 33 5f 6d 75 74  K;.  sqlite3_mut
d290: 65 78 5f 65 6e 74 65 72 28 73 71 6c 69 74 65 33  ex_enter(sqlite3
d2a0: 5f 64 62 5f 6d 75 74 65 78 28 70 53 65 73 73 69  _db_mutex(pSessi
d2b0: 6f 6e 2d 3e 64 62 29 29 3b 0a 0a 20 20 69 66 28  on->db));..  if(
d2c0: 20 21 7a 4e 61 6d 65 20 29 7b 0a 20 20 20 20 70   !zName ){.    p
d2d0: 53 65 73 73 69 6f 6e 2d 3e 62 41 75 74 6f 41 74  Session->bAutoAt
d2e0: 74 61 63 68 20 3d 20 31 3b 0a 20 20 7d 65 6c 73  tach = 1;.  }els
d2f0: 65 7b 0a 20 20 20 20 53 65 73 73 69 6f 6e 54 61  e{.    SessionTa
d300: 62 6c 65 20 2a 70 54 61 62 3b 20 20 20 20 20 20  ble *pTab;      
d310: 20 20 20 20 20 2f 2a 20 4e 65 77 20 74 61 62 6c       /* New tabl
d320: 65 20 6f 62 6a 65 63 74 20 28 69 66 20 72 65 71  e object (if req
d330: 75 69 72 65 64 29 20 2a 2f 0a 20 20 20 20 69 6e  uired) */.    in
d340: 74 20 6e 4e 61 6d 65 3b 20 20 20 20 20 20 20 20  t nName;        
d350: 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4e              /* N
d360: 75 6d 62 65 72 20 6f 66 20 62 79 74 65 73 20 69  umber of bytes i
d370: 6e 20 73 74 72 69 6e 67 20 7a 4e 61 6d 65 20 2a  n string zName *
d380: 2f 0a 0a 20 20 20 20 2f 2a 20 46 69 72 73 74 20  /..    /* First 
d390: 73 65 61 72 63 68 20 66 6f 72 20 61 6e 20 65 78  search for an ex
d3a0: 69 73 74 69 6e 67 20 65 6e 74 72 79 2e 20 49 66  isting entry. If
d3b0: 20 6f 6e 65 20 69 73 20 66 6f 75 6e 64 2c 20 74   one is found, t
d3c0: 68 69 73 20 63 61 6c 6c 20 69 73 0a 20 20 20 20  his call is.    
d3d0: 2a 2a 20 61 20 6e 6f 2d 6f 70 2e 20 52 65 74 75  ** a no-op. Retu
d3e0: 72 6e 20 65 61 72 6c 79 2e 20 2a 2f 0a 20 20 20  rn early. */.   
d3f0: 20 6e 4e 61 6d 65 20 3d 20 73 71 6c 69 74 65 33   nName = sqlite3
d400: 53 74 72 6c 65 6e 33 30 28 7a 4e 61 6d 65 29 3b  Strlen30(zName);
d410: 0a 20 20 20 20 66 6f 72 28 70 54 61 62 3d 70 53  .    for(pTab=pS
d420: 65 73 73 69 6f 6e 2d 3e 70 54 61 62 6c 65 3b 20  ession->pTable; 
d430: 70 54 61 62 3b 20 70 54 61 62 3d 70 54 61 62 2d  pTab; pTab=pTab-
d440: 3e 70 4e 65 78 74 29 7b 0a 20 20 20 20 20 20 69  >pNext){.      i
d450: 66 28 20 30 3d 3d 73 71 6c 69 74 65 33 5f 73 74  f( 0==sqlite3_st
d460: 72 6e 69 63 6d 70 28 70 54 61 62 2d 3e 7a 4e 61  rnicmp(pTab->zNa
d470: 6d 65 2c 20 7a 4e 61 6d 65 2c 20 6e 4e 61 6d 65  me, zName, nName
d480: 2b 31 29 20 29 20 62 72 65 61 6b 3b 0a 20 20 20  +1) ) break;.   
d490: 20 7d 0a 0a 20 20 20 20 69 66 28 20 21 70 54 61   }..    if( !pTa
d4a0: 62 20 29 7b 0a 20 20 20 20 20 20 2f 2a 20 41 6c  b ){.      /* Al
d4b0: 6c 6f 63 61 74 65 20 6e 65 77 20 53 65 73 73 69  locate new Sessi
d4c0: 6f 6e 54 61 62 6c 65 20 6f 62 6a 65 63 74 2e 20  onTable object. 
d4d0: 2a 2f 0a 20 20 20 20 20 20 70 54 61 62 20 3d 20  */.      pTab = 
d4e0: 28 53 65 73 73 69 6f 6e 54 61 62 6c 65 20 2a 29  (SessionTable *)
d4f0: 73 71 6c 69 74 65 33 5f 6d 61 6c 6c 6f 63 28 73  sqlite3_malloc(s
d500: 69 7a 65 6f 66 28 53 65 73 73 69 6f 6e 54 61 62  izeof(SessionTab
d510: 6c 65 29 20 2b 20 6e 4e 61 6d 65 20 2b 20 31 29  le) + nName + 1)
d520: 3b 0a 20 20 20 20 20 20 69 66 28 20 21 70 54 61  ;.      if( !pTa
d530: 62 20 29 7b 0a 20 20 20 20 20 20 20 20 72 63 20  b ){.        rc 
d540: 3d 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 3b 0a  = SQLITE_NOMEM;.
d550: 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20 20        }else{.   
d560: 20 20 20 20 20 2f 2a 20 50 6f 70 75 6c 61 74 65       /* Populate
d570: 20 74 68 65 20 6e 65 77 20 53 65 73 73 69 6f 6e   the new Session
d580: 54 61 62 6c 65 20 6f 62 6a 65 63 74 20 61 6e 64  Table object and
d590: 20 6c 69 6e 6b 20 69 74 20 69 6e 74 6f 20 74 68   link it into th
d5a0: 65 20 6c 69 73 74 2e 0a 20 20 20 20 20 20 20 20  e list..        
d5b0: 2a 2a 20 54 68 65 20 6e 65 77 20 6f 62 6a 65 63  ** The new objec
d5c0: 74 20 6d 75 73 74 20 62 65 20 6c 69 6e 6b 65 64  t must be linked
d5d0: 20 6f 6e 74 6f 20 74 68 65 20 65 6e 64 20 6f 66   onto the end of
d5e0: 20 74 68 65 20 6c 69 73 74 2c 20 6e 6f 74 20 0a   the list, not .
d5f0: 20 20 20 20 20 20 20 20 2a 2a 20 73 69 6d 70 6c          ** simpl
d600: 79 20 61 64 64 65 64 20 74 6f 20 74 68 65 20 73  y added to the s
d610: 74 61 72 74 20 6f 66 20 69 74 20 69 6e 20 6f 72  tart of it in or
d620: 64 65 72 20 74 6f 20 65 6e 73 75 72 65 20 74 68  der to ensure th
d630: 61 74 20 74 61 62 6c 65 73 0a 20 20 20 20 20 20  at tables.      
d640: 20 20 2a 2a 20 61 70 70 65 61 72 20 69 6e 20 74    ** appear in t
d650: 68 65 20 63 6f 72 72 65 63 74 20 6f 72 64 65 72  he correct order
d660: 20 77 68 65 6e 20 61 20 63 68 61 6e 67 65 73 65   when a changese
d670: 74 20 6f 72 20 70 61 74 63 68 73 65 74 20 69 73  t or patchset is
d680: 0a 20 20 20 20 20 20 20 20 2a 2a 20 65 76 65 6e  .        ** even
d690: 74 75 61 6c 6c 79 20 67 65 6e 65 72 61 74 65 64  tually generated
d6a0: 2e 20 2a 2f 0a 20 20 20 20 20 20 20 20 53 65 73  . */.        Ses
d6b0: 73 69 6f 6e 54 61 62 6c 65 20 2a 2a 70 70 54 61  sionTable **ppTa
d6c0: 62 3b 0a 20 20 20 20 20 20 20 20 6d 65 6d 73 65  b;.        memse
d6d0: 74 28 70 54 61 62 2c 20 30 2c 20 73 69 7a 65 6f  t(pTab, 0, sizeo
d6e0: 66 28 53 65 73 73 69 6f 6e 54 61 62 6c 65 29 29  f(SessionTable))
d6f0: 3b 0a 20 20 20 20 20 20 20 20 70 54 61 62 2d 3e  ;.        pTab->
d700: 7a 4e 61 6d 65 20 3d 20 28 63 68 61 72 20 2a 29  zName = (char *)
d710: 26 70 54 61 62 5b 31 5d 3b 0a 20 20 20 20 20 20  &pTab[1];.      
d720: 20 20 6d 65 6d 63 70 79 28 70 54 61 62 2d 3e 7a    memcpy(pTab->z
d730: 4e 61 6d 65 2c 20 7a 4e 61 6d 65 2c 20 6e 4e 61  Name, zName, nNa
d740: 6d 65 2b 31 29 3b 0a 20 20 20 20 20 20 20 20 66  me+1);.        f
d750: 6f 72 28 70 70 54 61 62 3d 26 70 53 65 73 73 69  or(ppTab=&pSessi
d760: 6f 6e 2d 3e 70 54 61 62 6c 65 3b 20 2a 70 70 54  on->pTable; *ppT
d770: 61 62 3b 20 70 70 54 61 62 3d 26 28 2a 70 70 54  ab; ppTab=&(*ppT
d780: 61 62 29 2d 3e 70 4e 65 78 74 29 3b 0a 20 20 20  ab)->pNext);.   
d790: 20 20 20 20 20 2a 70 70 54 61 62 20 3d 20 70 54       *ppTab = pT
d7a0: 61 62 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20 20  ab;.      }.    
d7b0: 7d 0a 20 20 7d 0a 0a 20 20 73 71 6c 69 74 65 33  }.  }..  sqlite3
d7c0: 5f 6d 75 74 65 78 5f 6c 65 61 76 65 28 73 71 6c  _mutex_leave(sql
d7d0: 69 74 65 33 5f 64 62 5f 6d 75 74 65 78 28 70 53  ite3_db_mutex(pS
d7e0: 65 73 73 69 6f 6e 2d 3e 64 62 29 29 3b 0a 20 20  ession->db));.  
d7f0: 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a  return rc;.}../*
d800: 0a 2a 2a 20 45 6e 73 75 72 65 20 74 68 61 74 20  .** Ensure that 
d810: 74 68 65 72 65 20 69 73 20 72 6f 6f 6d 20 69 6e  there is room in
d820: 20 74 68 65 20 62 75 66 66 65 72 20 74 6f 20 61   the buffer to a
d830: 70 70 65 6e 64 20 6e 42 79 74 65 20 62 79 74 65  ppend nByte byte
d840: 73 20 6f 66 20 64 61 74 61 2e 0a 2a 2a 20 49 66  s of data..** If
d850: 20 6e 6f 74 2c 20 75 73 65 20 73 71 6c 69 74 65   not, use sqlite
d860: 33 5f 72 65 61 6c 6c 6f 63 28 29 20 74 6f 20 67  3_realloc() to g
d870: 72 6f 77 20 74 68 65 20 62 75 66 66 65 72 20 73  row the buffer s
d880: 6f 20 74 68 61 74 20 74 68 65 72 65 20 69 73 2e  o that there is.
d890: 0a 2a 2a 0a 2a 2a 20 49 66 20 73 75 63 63 65 73  .**.** If succes
d8a0: 73 66 75 6c 2c 20 72 65 74 75 72 6e 20 7a 65 72  sful, return zer
d8b0: 6f 2e 20 4f 74 68 65 72 77 69 73 65 2c 20 69 66  o. Otherwise, if
d8c0: 20 61 6e 20 4f 4f 4d 20 63 6f 6e 64 69 74 69 6f   an OOM conditio
d8d0: 6e 20 69 73 20 65 6e 63 6f 75 6e 74 65 72 65 64  n is encountered
d8e0: 2c 0a 2a 2a 20 73 65 74 20 2a 70 52 63 20 74 6f  ,.** set *pRc to
d8f0: 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 20 61 6e   SQLITE_NOMEM an
d900: 64 20 72 65 74 75 72 6e 20 6e 6f 6e 2d 7a 65 72  d return non-zer
d910: 6f 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74  o..*/.static int
d920: 20 73 65 73 73 69 6f 6e 42 75 66 66 65 72 47 72   sessionBufferGr
d930: 6f 77 28 53 65 73 73 69 6f 6e 42 75 66 66 65 72  ow(SessionBuffer
d940: 20 2a 70 2c 20 69 6e 74 20 6e 42 79 74 65 2c 20   *p, int nByte, 
d950: 69 6e 74 20 2a 70 52 63 29 7b 0a 20 20 69 66 28  int *pRc){.  if(
d960: 20 2a 70 52 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b   *pRc==SQLITE_OK
d970: 20 26 26 20 70 2d 3e 6e 41 6c 6c 6f 63 2d 70 2d   && p->nAlloc-p-
d980: 3e 6e 42 75 66 3c 6e 42 79 74 65 20 29 7b 0a 20  >nBuf<nByte ){. 
d990: 20 20 20 75 38 20 2a 61 4e 65 77 3b 0a 20 20 20     u8 *aNew;.   
d9a0: 20 69 6e 74 20 6e 4e 65 77 20 3d 20 70 2d 3e 6e   int nNew = p->n
d9b0: 41 6c 6c 6f 63 20 3f 20 70 2d 3e 6e 41 6c 6c 6f  Alloc ? p->nAllo
d9c0: 63 20 3a 20 31 32 38 3b 0a 20 20 20 20 64 6f 20  c : 128;.    do 
d9d0: 7b 0a 20 20 20 20 20 20 6e 4e 65 77 20 3d 20 6e  {.      nNew = n
d9e0: 4e 65 77 2a 32 3b 0a 20 20 20 20 7d 77 68 69 6c  New*2;.    }whil
d9f0: 65 28 20 6e 4e 65 77 3c 28 70 2d 3e 6e 42 75 66  e( nNew<(p->nBuf
da00: 2b 6e 42 79 74 65 29 20 29 3b 0a 0a 20 20 20 20  +nByte) );..    
da10: 61 4e 65 77 20 3d 20 28 75 38 20 2a 29 73 71 6c  aNew = (u8 *)sql
da20: 69 74 65 33 5f 72 65 61 6c 6c 6f 63 28 70 2d 3e  ite3_realloc(p->
da30: 61 42 75 66 2c 20 6e 4e 65 77 29 3b 0a 20 20 20  aBuf, nNew);.   
da40: 20 69 66 28 20 30 3d 3d 61 4e 65 77 20 29 7b 0a   if( 0==aNew ){.
da50: 20 20 20 20 20 20 2a 70 52 63 20 3d 20 53 51 4c        *pRc = SQL
da60: 49 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 20 20 7d  ITE_NOMEM;.    }
da70: 65 6c 73 65 7b 0a 20 20 20 20 20 20 70 2d 3e 61  else{.      p->a
da80: 42 75 66 20 3d 20 61 4e 65 77 3b 0a 20 20 20 20  Buf = aNew;.    
da90: 20 20 70 2d 3e 6e 41 6c 6c 6f 63 20 3d 20 6e 4e    p->nAlloc = nN
daa0: 65 77 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a 20 20  ew;.    }.  }.  
dab0: 72 65 74 75 72 6e 20 28 2a 70 52 63 21 3d 53 51  return (*pRc!=SQ
dac0: 4c 49 54 45 5f 4f 4b 29 3b 0a 7d 0a 0a 2f 2a 0a  LITE_OK);.}../*.
dad0: 2a 2a 20 41 70 70 65 6e 64 20 74 68 65 20 76 61  ** Append the va
dae0: 6c 75 65 20 70 61 73 73 65 64 20 61 73 20 74 68  lue passed as th
daf0: 65 20 73 65 63 6f 6e 64 20 61 72 67 75 6d 65 6e  e second argumen
db00: 74 20 74 6f 20 74 68 65 20 62 75 66 66 65 72 20  t to the buffer 
db10: 70 61 73 73 65 64 0a 2a 2a 20 61 73 20 74 68 65  passed.** as the
db20: 20 66 69 72 73 74 2e 0a 2a 2a 0a 2a 2a 20 54 68   first..**.** Th
db30: 69 73 20 66 75 6e 63 74 69 6f 6e 20 69 73 20 61  is function is a
db40: 20 6e 6f 2d 6f 70 20 69 66 20 2a 70 52 63 20 69   no-op if *pRc i
db50: 73 20 6e 6f 6e 2d 7a 65 72 6f 20 77 68 65 6e 20  s non-zero when 
db60: 69 74 20 69 73 20 63 61 6c 6c 65 64 2e 0a 2a 2a  it is called..**
db70: 20 4f 74 68 65 72 77 69 73 65 2c 20 69 66 20 61   Otherwise, if a
db80: 6e 20 65 72 72 6f 72 20 6f 63 63 75 72 73 2c 20  n error occurs, 
db90: 2a 70 52 63 20 69 73 20 73 65 74 20 74 6f 20 61  *pRc is set to a
dba0: 6e 20 53 51 4c 69 74 65 20 65 72 72 6f 72 20 63  n SQLite error c
dbb0: 6f 64 65 0a 2a 2a 20 62 65 66 6f 72 65 20 72 65  ode.** before re
dbc0: 74 75 72 6e 69 6e 67 2e 0a 2a 2f 0a 73 74 61 74  turning..*/.stat
dbd0: 69 63 20 76 6f 69 64 20 73 65 73 73 69 6f 6e 41  ic void sessionA
dbe0: 70 70 65 6e 64 56 61 6c 75 65 28 53 65 73 73 69  ppendValue(Sessi
dbf0: 6f 6e 42 75 66 66 65 72 20 2a 70 2c 20 73 71 6c  onBuffer *p, sql
dc00: 69 74 65 33 5f 76 61 6c 75 65 20 2a 70 56 61 6c  ite3_value *pVal
dc10: 2c 20 69 6e 74 20 2a 70 52 63 29 7b 0a 20 20 69  , int *pRc){.  i
dc20: 6e 74 20 72 63 20 3d 20 2a 70 52 63 3b 0a 20 20  nt rc = *pRc;.  
dc30: 69 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f  if( rc==SQLITE_O
dc40: 4b 20 29 7b 0a 20 20 20 20 69 6e 74 20 6e 42 79  K ){.    int nBy
dc50: 74 65 20 3d 20 30 3b 0a 20 20 20 20 72 63 20 3d  te = 0;.    rc =
dc60: 20 73 65 73 73 69 6f 6e 53 65 72 69 61 6c 69 7a   sessionSerializ
dc70: 65 56 61 6c 75 65 28 30 2c 20 70 56 61 6c 2c 20  eValue(0, pVal, 
dc80: 26 6e 42 79 74 65 29 3b 0a 20 20 20 20 73 65 73  &nByte);.    ses
dc90: 73 69 6f 6e 42 75 66 66 65 72 47 72 6f 77 28 70  sionBufferGrow(p
dca0: 2c 20 6e 42 79 74 65 2c 20 26 72 63 29 3b 0a 20  , nByte, &rc);. 
dcb0: 20 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54     if( rc==SQLIT
dcc0: 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 20 20 72 63  E_OK ){.      rc
dcd0: 20 3d 20 73 65 73 73 69 6f 6e 53 65 72 69 61 6c   = sessionSerial
dce0: 69 7a 65 56 61 6c 75 65 28 26 70 2d 3e 61 42 75  izeValue(&p->aBu
dcf0: 66 5b 70 2d 3e 6e 42 75 66 5d 2c 20 70 56 61 6c  f[p->nBuf], pVal
dd00: 2c 20 30 29 3b 0a 20 20 20 20 20 20 70 2d 3e 6e  , 0);.      p->n
dd10: 42 75 66 20 2b 3d 20 6e 42 79 74 65 3b 0a 20 20  Buf += nByte;.  
dd20: 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 2a    }else{.      *
dd30: 70 52 63 20 3d 20 72 63 3b 0a 20 20 20 20 7d 0a  pRc = rc;.    }.
dd40: 20 20 7d 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68 69    }.}../*.** Thi
dd50: 73 20 66 75 6e 63 74 69 6f 6e 20 69 73 20 61 20  s function is a 
dd60: 6e 6f 2d 6f 70 20 69 66 20 2a 70 52 63 20 69 73  no-op if *pRc is
dd70: 20 6f 74 68 65 72 20 74 68 61 6e 20 53 51 4c 49   other than SQLI
dd80: 54 45 5f 4f 4b 20 77 68 65 6e 20 69 74 20 69 73  TE_OK when it is
dd90: 20 0a 2a 2a 20 63 61 6c 6c 65 64 2e 20 4f 74 68   .** called. Oth
dda0: 65 72 77 69 73 65 2c 20 61 70 70 65 6e 64 20 61  erwise, append a
ddb0: 20 73 69 6e 67 6c 65 20 62 79 74 65 20 74 6f 20   single byte to 
ddc0: 74 68 65 20 62 75 66 66 65 72 2e 20 0a 2a 2a 0a  the buffer. .**.
ddd0: 2a 2a 20 49 66 20 61 6e 20 4f 4f 4d 20 63 6f 6e  ** If an OOM con
dde0: 64 69 74 69 6f 6e 20 69 73 20 65 6e 63 6f 75 6e  dition is encoun
ddf0: 74 65 72 65 64 2c 20 73 65 74 20 2a 70 52 63 20  tered, set *pRc 
de00: 74 6f 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 20  to SQLITE_NOMEM 
de10: 62 65 66 6f 72 65 0a 2a 2a 20 72 65 74 75 72 6e  before.** return
de20: 69 6e 67 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 76  ing..*/.static v
de30: 6f 69 64 20 73 65 73 73 69 6f 6e 41 70 70 65 6e  oid sessionAppen
de40: 64 42 79 74 65 28 53 65 73 73 69 6f 6e 42 75 66  dByte(SessionBuf
de50: 66 65 72 20 2a 70 2c 20 75 38 20 76 2c 20 69 6e  fer *p, u8 v, in
de60: 74 20 2a 70 52 63 29 7b 0a 20 20 69 66 28 20 30  t *pRc){.  if( 0
de70: 3d 3d 73 65 73 73 69 6f 6e 42 75 66 66 65 72 47  ==sessionBufferG
de80: 72 6f 77 28 70 2c 20 31 2c 20 70 52 63 29 20 29  row(p, 1, pRc) )
de90: 7b 0a 20 20 20 20 70 2d 3e 61 42 75 66 5b 70 2d  {.    p->aBuf[p-
dea0: 3e 6e 42 75 66 2b 2b 5d 20 3d 20 76 3b 0a 20 20  >nBuf++] = v;.  
deb0: 7d 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68 69 73 20  }.}../*.** This 
dec0: 66 75 6e 63 74 69 6f 6e 20 69 73 20 61 20 6e 6f  function is a no
ded0: 2d 6f 70 20 69 66 20 2a 70 52 63 20 69 73 20 6f  -op if *pRc is o
dee0: 74 68 65 72 20 74 68 61 6e 20 53 51 4c 49 54 45  ther than SQLITE
def0: 5f 4f 4b 20 77 68 65 6e 20 69 74 20 69 73 20 0a  _OK when it is .
df00: 2a 2a 20 63 61 6c 6c 65 64 2e 20 4f 74 68 65 72  ** called. Other
df10: 77 69 73 65 2c 20 61 70 70 65 6e 64 20 61 20 73  wise, append a s
df20: 69 6e 67 6c 65 20 76 61 72 69 6e 74 20 74 6f 20  ingle varint to 
df30: 74 68 65 20 62 75 66 66 65 72 2e 20 0a 2a 2a 0a  the buffer. .**.
df40: 2a 2a 20 49 66 20 61 6e 20 4f 4f 4d 20 63 6f 6e  ** If an OOM con
df50: 64 69 74 69 6f 6e 20 69 73 20 65 6e 63 6f 75 6e  dition is encoun
df60: 74 65 72 65 64 2c 20 73 65 74 20 2a 70 52 63 20  tered, set *pRc 
df70: 74 6f 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 20  to SQLITE_NOMEM 
df80: 62 65 66 6f 72 65 0a 2a 2a 20 72 65 74 75 72 6e  before.** return
df90: 69 6e 67 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 76  ing..*/.static v
dfa0: 6f 69 64 20 73 65 73 73 69 6f 6e 41 70 70 65 6e  oid sessionAppen
dfb0: 64 56 61 72 69 6e 74 28 53 65 73 73 69 6f 6e 42  dVarint(SessionB
dfc0: 75 66 66 65 72 20 2a 70 2c 20 69 6e 74 20 76 2c  uffer *p, int v,
dfd0: 20 69 6e 74 20 2a 70 52 63 29 7b 0a 20 20 69 66   int *pRc){.  if
dfe0: 28 20 30 3d 3d 73 65 73 73 69 6f 6e 42 75 66 66  ( 0==sessionBuff
dff0: 65 72 47 72 6f 77 28 70 2c 20 39 2c 20 70 52 63  erGrow(p, 9, pRc
e000: 29 20 29 7b 0a 20 20 20 20 70 2d 3e 6e 42 75 66  ) ){.    p->nBuf
e010: 20 2b 3d 20 73 65 73 73 69 6f 6e 56 61 72 69 6e   += sessionVarin
e020: 74 50 75 74 28 26 70 2d 3e 61 42 75 66 5b 70 2d  tPut(&p->aBuf[p-
e030: 3e 6e 42 75 66 5d 2c 20 76 29 3b 0a 20 20 7d 0a  >nBuf], v);.  }.
e040: 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68 69 73 20 66 75  }../*.** This fu
e050: 6e 63 74 69 6f 6e 20 69 73 20 61 20 6e 6f 2d 6f  nction is a no-o
e060: 70 20 69 66 20 2a 70 52 63 20 69 73 20 6f 74 68  p if *pRc is oth
e070: 65 72 20 74 68 61 6e 20 53 51 4c 49 54 45 5f 4f  er than SQLITE_O
e080: 4b 20 77 68 65 6e 20 69 74 20 69 73 20 0a 2a 2a  K when it is .**
e090: 20 63 61 6c 6c 65 64 2e 20 4f 74 68 65 72 77 69   called. Otherwi
e0a0: 73 65 2c 20 61 70 70 65 6e 64 20 61 20 62 6c 6f  se, append a blo
e0b0: 62 20 6f 66 20 64 61 74 61 20 74 6f 20 74 68 65  b of data to the
e0c0: 20 62 75 66 66 65 72 2e 20 0a 2a 2a 0a 2a 2a 20   buffer. .**.** 
e0d0: 49 66 20 61 6e 20 4f 4f 4d 20 63 6f 6e 64 69 74  If an OOM condit
e0e0: 69 6f 6e 20 69 73 20 65 6e 63 6f 75 6e 74 65 72  ion is encounter
e0f0: 65 64 2c 20 73 65 74 20 2a 70 52 63 20 74 6f 20  ed, set *pRc to 
e100: 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 20 62 65 66  SQLITE_NOMEM bef
e110: 6f 72 65 0a 2a 2a 20 72 65 74 75 72 6e 69 6e 67  ore.** returning
e120: 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 76 6f 69 64  ..*/.static void
e130: 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 42 6c   sessionAppendBl
e140: 6f 62 28 0a 20 20 53 65 73 73 69 6f 6e 42 75 66  ob(.  SessionBuf
e150: 66 65 72 20 2a 70 2c 20 0a 20 20 63 6f 6e 73 74  fer *p, .  const
e160: 20 75 38 20 2a 61 42 6c 6f 62 2c 20 0a 20 20 69   u8 *aBlob, .  i
e170: 6e 74 20 6e 42 6c 6f 62 2c 20 0a 20 20 69 6e 74  nt nBlob, .  int
e180: 20 2a 70 52 63 0a 29 7b 0a 20 20 69 66 28 20 6e   *pRc.){.  if( n
e190: 42 6c 6f 62 3e 30 20 26 26 20 30 3d 3d 73 65 73  Blob>0 && 0==ses
e1a0: 73 69 6f 6e 42 75 66 66 65 72 47 72 6f 77 28 70  sionBufferGrow(p
e1b0: 2c 20 6e 42 6c 6f 62 2c 20 70 52 63 29 20 29 7b  , nBlob, pRc) ){
e1c0: 0a 20 20 20 20 6d 65 6d 63 70 79 28 26 70 2d 3e  .    memcpy(&p->
e1d0: 61 42 75 66 5b 70 2d 3e 6e 42 75 66 5d 2c 20 61  aBuf[p->nBuf], a
e1e0: 42 6c 6f 62 2c 20 6e 42 6c 6f 62 29 3b 0a 20 20  Blob, nBlob);.  
e1f0: 20 20 70 2d 3e 6e 42 75 66 20 2b 3d 20 6e 42 6c    p->nBuf += nBl
e200: 6f 62 3b 0a 20 20 7d 0a 7d 0a 0a 2f 2a 0a 2a 2a  ob;.  }.}../*.**
e210: 20 54 68 69 73 20 66 75 6e 63 74 69 6f 6e 20 69   This function i
e220: 73 20 61 20 6e 6f 2d 6f 70 20 69 66 20 2a 70 52  s a no-op if *pR
e230: 63 20 69 73 20 6f 74 68 65 72 20 74 68 61 6e 20  c is other than 
e240: 53 51 4c 49 54 45 5f 4f 4b 20 77 68 65 6e 20 69  SQLITE_OK when i
e250: 74 20 69 73 20 0a 2a 2a 20 63 61 6c 6c 65 64 2e  t is .** called.
e260: 20 4f 74 68 65 72 77 69 73 65 2c 20 61 70 70 65   Otherwise, appe
e270: 6e 64 20 61 20 73 74 72 69 6e 67 20 74 6f 20 74  nd a string to t
e280: 68 65 20 62 75 66 66 65 72 2e 20 41 6c 6c 20 62  he buffer. All b
e290: 79 74 65 73 20 69 6e 20 74 68 65 20 73 74 72 69  ytes in the stri
e2a0: 6e 67 0a 2a 2a 20 75 70 20 74 6f 20 28 62 75 74  ng.** up to (but
e2b0: 20 6e 6f 74 20 69 6e 63 6c 75 64 69 6e 67 29 20   not including) 
e2c0: 74 68 65 20 6e 75 6c 2d 74 65 72 6d 69 6e 61 74  the nul-terminat
e2d0: 6f 72 20 61 72 65 20 77 72 69 74 74 65 6e 20 74  or are written t
e2e0: 6f 20 74 68 65 20 62 75 66 66 65 72 2e 0a 2a 2a  o the buffer..**
e2f0: 0a 2a 2a 20 49 66 20 61 6e 20 4f 4f 4d 20 63 6f  .** If an OOM co
e300: 6e 64 69 74 69 6f 6e 20 69 73 20 65 6e 63 6f 75  ndition is encou
e310: 6e 74 65 72 65 64 2c 20 73 65 74 20 2a 70 52 63  ntered, set *pRc
e320: 20 74 6f 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d   to SQLITE_NOMEM
e330: 20 62 65 66 6f 72 65 0a 2a 2a 20 72 65 74 75 72   before.** retur
e340: 6e 69 6e 67 2e 0a 2a 2f 0a 73 74 61 74 69 63 20  ning..*/.static 
e350: 76 6f 69 64 20 73 65 73 73 69 6f 6e 41 70 70 65  void sessionAppe
e360: 6e 64 53 74 72 28 0a 20 20 53 65 73 73 69 6f 6e  ndStr(.  Session
e370: 42 75 66 66 65 72 20 2a 70 2c 20 0a 20 20 63 6f  Buffer *p, .  co
e380: 6e 73 74 20 63 68 61 72 20 2a 7a 53 74 72 2c 20  nst char *zStr, 
e390: 0a 20 20 69 6e 74 20 2a 70 52 63 0a 29 7b 0a 20  .  int *pRc.){. 
e3a0: 20 69 6e 74 20 6e 53 74 72 20 3d 20 73 71 6c 69   int nStr = sqli
e3b0: 74 65 33 53 74 72 6c 65 6e 33 30 28 7a 53 74 72  te3Strlen30(zStr
e3c0: 29 3b 0a 20 20 69 66 28 20 30 3d 3d 73 65 73 73  );.  if( 0==sess
e3d0: 69 6f 6e 42 75 66 66 65 72 47 72 6f 77 28 70 2c  ionBufferGrow(p,
e3e0: 20 6e 53 74 72 2c 20 70 52 63 29 20 29 7b 0a 20   nStr, pRc) ){. 
e3f0: 20 20 20 6d 65 6d 63 70 79 28 26 70 2d 3e 61 42     memcpy(&p->aB
e400: 75 66 5b 70 2d 3e 6e 42 75 66 5d 2c 20 7a 53 74  uf[p->nBuf], zSt
e410: 72 2c 20 6e 53 74 72 29 3b 0a 20 20 20 20 70 2d  r, nStr);.    p-
e420: 3e 6e 42 75 66 20 2b 3d 20 6e 53 74 72 3b 0a 20  >nBuf += nStr;. 
e430: 20 7d 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68 69 73   }.}../*.** This
e440: 20 66 75 6e 63 74 69 6f 6e 20 69 73 20 61 20 6e   function is a n
e450: 6f 2d 6f 70 20 69 66 20 2a 70 52 63 20 69 73 20  o-op if *pRc is 
e460: 6f 74 68 65 72 20 74 68 61 6e 20 53 51 4c 49 54  other than SQLIT
e470: 45 5f 4f 4b 20 77 68 65 6e 20 69 74 20 69 73 20  E_OK when it is 
e480: 0a 2a 2a 20 63 61 6c 6c 65 64 2e 20 4f 74 68 65  .** called. Othe
e490: 72 77 69 73 65 2c 20 61 70 70 65 6e 64 20 74 68  rwise, append th
e4a0: 65 20 73 74 72 69 6e 67 20 72 65 70 72 65 73 65  e string represe
e4b0: 6e 74 61 74 69 6f 6e 20 6f 66 20 69 6e 74 65 67  ntation of integ
e4c0: 65 72 20 69 56 61 6c 0a 2a 2a 20 74 6f 20 74 68  er iVal.** to th
e4d0: 65 20 62 75 66 66 65 72 2e 20 4e 6f 20 6e 75 6c  e buffer. No nul
e4e0: 2d 74 65 72 6d 69 6e 61 74 6f 72 20 69 73 20 77  -terminator is w
e4f0: 72 69 74 74 65 6e 2e 0a 2a 2a 0a 2a 2a 20 49 66  ritten..**.** If
e500: 20 61 6e 20 4f 4f 4d 20 63 6f 6e 64 69 74 69 6f   an OOM conditio
e510: 6e 20 69 73 20 65 6e 63 6f 75 6e 74 65 72 65 64  n is encountered
e520: 2c 20 73 65 74 20 2a 70 52 63 20 74 6f 20 53 51  , set *pRc to SQ
e530: 4c 49 54 45 5f 4e 4f 4d 45 4d 20 62 65 66 6f 72  LITE_NOMEM befor
e540: 65 0a 2a 2a 20 72 65 74 75 72 6e 69 6e 67 2e 0a  e.** returning..
e550: 2a 2f 0a 73 74 61 74 69 63 20 76 6f 69 64 20 73  */.static void s
e560: 65 73 73 69 6f 6e 41 70 70 65 6e 64 49 6e 74 65  essionAppendInte
e570: 67 65 72 28 0a 20 20 53 65 73 73 69 6f 6e 42 75  ger(.  SessionBu
e580: 66 66 65 72 20 2a 70 2c 20 20 20 20 20 20 20 20  ffer *p,        
e590: 20 20 20 20 20 20 20 2f 2a 20 42 75 66 66 65 72         /* Buffer
e5a0: 20 74 6f 20 61 70 70 65 6e 64 20 74 6f 20 2a 2f   to append to */
e5b0: 0a 20 20 69 6e 74 20 69 56 61 6c 2c 20 20 20 20  .  int iVal,    
e5c0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
e5d0: 20 20 20 2f 2a 20 56 61 6c 75 65 20 74 6f 20 77     /* Value to w
e5e0: 72 69 74 65 20 74 68 65 20 73 74 72 69 6e 67 20  rite the string 
e5f0: 72 65 70 2e 20 6f 66 20 2a 2f 0a 20 20 69 6e 74  rep. of */.  int
e600: 20 2a 70 52 63 20 20 20 20 20 20 20 20 20 20 20   *pRc           
e610: 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
e620: 49 4e 2f 4f 55 54 3a 20 45 72 72 6f 72 20 63 6f  IN/OUT: Error co
e630: 64 65 20 2a 2f 0a 29 7b 0a 20 20 63 68 61 72 20  de */.){.  char 
e640: 61 42 75 66 5b 32 34 5d 3b 0a 20 20 73 71 6c 69  aBuf[24];.  sqli
e650: 74 65 33 5f 73 6e 70 72 69 6e 74 66 28 73 69 7a  te3_snprintf(siz
e660: 65 6f 66 28 61 42 75 66 29 2d 31 2c 20 61 42 75  eof(aBuf)-1, aBu
e670: 66 2c 20 22 25 64 22 2c 20 69 56 61 6c 29 3b 0a  f, "%d", iVal);.
e680: 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 53    sessionAppendS
e690: 74 72 28 70 2c 20 61 42 75 66 2c 20 70 52 63 29  tr(p, aBuf, pRc)
e6a0: 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68 69 73 20  ;.}../*.** This 
e6b0: 66 75 6e 63 74 69 6f 6e 20 69 73 20 61 20 6e 6f  function is a no
e6c0: 2d 6f 70 20 69 66 20 2a 70 52 63 20 69 73 20 6f  -op if *pRc is o
e6d0: 74 68 65 72 20 74 68 61 6e 20 53 51 4c 49 54 45  ther than SQLITE
e6e0: 5f 4f 4b 20 77 68 65 6e 20 69 74 20 69 73 20 0a  _OK when it is .
e6f0: 2a 2a 20 63 61 6c 6c 65 64 2e 20 4f 74 68 65 72  ** called. Other
e700: 77 69 73 65 2c 20 61 70 70 65 6e 64 20 74 68 65  wise, append the
e710: 20 73 74 72 69 6e 67 20 7a 53 74 72 20 65 6e 63   string zStr enc
e720: 6c 6f 73 65 64 20 69 6e 20 71 75 6f 74 65 73 20  losed in quotes 
e730: 28 22 29 20 61 6e 64 0a 2a 2a 20 77 69 74 68 20  (") and.** with 
e740: 61 6e 79 20 65 6d 62 65 64 64 65 64 20 71 75 6f  any embedded quo
e750: 74 65 20 63 68 61 72 61 63 74 65 72 73 20 65 73  te characters es
e760: 63 61 70 65 64 20 74 6f 20 74 68 65 20 62 75 66  caped to the buf
e770: 66 65 72 2e 20 4e 6f 20 0a 2a 2a 20 6e 75 6c 2d  fer. No .** nul-
e780: 74 65 72 6d 69 6e 61 74 6f 72 20 62 79 74 65 20  terminator byte 
e790: 69 73 20 77 72 69 74 74 65 6e 2e 0a 2a 2a 0a 2a  is written..**.*
e7a0: 2a 20 49 66 20 61 6e 20 4f 4f 4d 20 63 6f 6e 64  * If an OOM cond
e7b0: 69 74 69 6f 6e 20 69 73 20 65 6e 63 6f 75 6e 74  ition is encount
e7c0: 65 72 65 64 2c 20 73 65 74 20 2a 70 52 63 20 74  ered, set *pRc t
e7d0: 6f 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 20 62  o SQLITE_NOMEM b
e7e0: 65 66 6f 72 65 0a 2a 2a 20 72 65 74 75 72 6e 69  efore.** returni
e7f0: 6e 67 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 76 6f  ng..*/.static vo
e800: 69 64 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64  id sessionAppend
e810: 49 64 65 6e 74 28 0a 20 20 53 65 73 73 69 6f 6e  Ident(.  Session
e820: 42 75 66 66 65 72 20 2a 70 2c 20 20 20 20 20 20  Buffer *p,      
e830: 20 20 20 20 20 20 20 20 20 2f 2a 20 42 75 66 66           /* Buff
e840: 65 72 20 74 6f 20 61 20 61 70 70 65 6e 64 20 74  er to a append t
e850: 6f 20 2a 2f 0a 20 20 63 6f 6e 73 74 20 63 68 61  o */.  const cha
e860: 72 20 2a 7a 53 74 72 2c 20 20 20 20 20 20 20 20  r *zStr,        
e870: 20 20 20 20 20 20 20 2f 2a 20 53 74 72 69 6e 67         /* String
e880: 20 74 6f 20 71 75 6f 74 65 2c 20 65 73 63 61 70   to quote, escap
e890: 65 20 61 6e 64 20 61 70 70 65 6e 64 20 2a 2f 0a  e and append */.
e8a0: 20 20 69 6e 74 20 2a 70 52 63 20 20 20 20 20 20    int *pRc      
e8b0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
e8c0: 20 20 2f 2a 20 49 4e 2f 4f 55 54 3a 20 45 72 72    /* IN/OUT: Err
e8d0: 6f 72 20 63 6f 64 65 20 2a 2f 0a 29 7b 0a 20 20  or code */.){.  
e8e0: 69 6e 74 20 6e 53 74 72 20 3d 20 73 71 6c 69 74  int nStr = sqlit
e8f0: 65 33 53 74 72 6c 65 6e 33 30 28 7a 53 74 72 29  e3Strlen30(zStr)
e900: 2a 32 20 2b 20 32 20 2b 20 31 3b 0a 20 20 69 66  *2 + 2 + 1;.  if
e910: 28 20 30 3d 3d 73 65 73 73 69 6f 6e 42 75 66 66  ( 0==sessionBuff
e920: 65 72 47 72 6f 77 28 70 2c 20 6e 53 74 72 2c 20  erGrow(p, nStr, 
e930: 70 52 63 29 20 29 7b 0a 20 20 20 20 63 68 61 72  pRc) ){.    char
e940: 20 2a 7a 4f 75 74 20 3d 20 28 63 68 61 72 20 2a   *zOut = (char *
e950: 29 26 70 2d 3e 61 42 75 66 5b 70 2d 3e 6e 42 75  )&p->aBuf[p->nBu
e960: 66 5d 3b 0a 20 20 20 20 63 6f 6e 73 74 20 63 68  f];.    const ch
e970: 61 72 20 2a 7a 49 6e 20 3d 20 7a 53 74 72 3b 0a  ar *zIn = zStr;.
e980: 20 20 20 20 2a 7a 4f 75 74 2b 2b 20 3d 20 27 22      *zOut++ = '"
e990: 27 3b 0a 20 20 20 20 77 68 69 6c 65 28 20 2a 7a  ';.    while( *z
e9a0: 49 6e 20 29 7b 0a 20 20 20 20 20 20 69 66 28 20  In ){.      if( 
e9b0: 2a 7a 49 6e 3d 3d 27 22 27 20 29 20 2a 7a 4f 75  *zIn=='"' ) *zOu
e9c0: 74 2b 2b 20 3d 20 27 22 27 3b 0a 20 20 20 20 20  t++ = '"';.     
e9d0: 20 2a 7a 4f 75 74 2b 2b 20 3d 20 2a 28 7a 49 6e   *zOut++ = *(zIn
e9e0: 2b 2b 29 3b 0a 20 20 20 20 7d 0a 20 20 20 20 2a  ++);.    }.    *
e9f0: 7a 4f 75 74 2b 2b 20 3d 20 27 22 27 3b 0a 20 20  zOut++ = '"';.  
ea00: 20 20 70 2d 3e 6e 42 75 66 20 3d 20 28 69 6e 74    p->nBuf = (int
ea10: 29 28 28 75 38 20 2a 29 7a 4f 75 74 20 2d 20 70  )((u8 *)zOut - p
ea20: 2d 3e 61 42 75 66 29 3b 0a 20 20 7d 0a 7d 0a 0a  ->aBuf);.  }.}..
ea30: 2f 2a 0a 2a 2a 20 54 68 69 73 20 66 75 6e 63 74  /*.** This funct
ea40: 69 6f 6e 20 69 73 20 61 20 6e 6f 2d 6f 70 20 69  ion is a no-op i
ea50: 66 20 2a 70 52 63 20 69 73 20 6f 74 68 65 72 20  f *pRc is other 
ea60: 74 68 61 6e 20 53 51 4c 49 54 45 5f 4f 4b 20 77  than SQLITE_OK w
ea70: 68 65 6e 20 69 74 20 69 73 0a 2a 2a 20 63 61 6c  hen it is.** cal
ea80: 6c 65 64 2e 20 4f 74 68 65 72 77 73 65 2c 20 69  led. Otherwse, i
ea90: 74 20 61 70 70 65 6e 64 73 20 74 68 65 20 73 65  t appends the se
eaa0: 72 69 61 6c 69 7a 65 64 20 76 65 72 73 69 6f 6e  rialized version
eab0: 20 6f 66 20 74 68 65 20 76 61 6c 75 65 20 73 74   of the value st
eac0: 6f 72 65 64 0a 2a 2a 20 69 6e 20 63 6f 6c 75 6d  ored.** in colum
ead0: 6e 20 69 43 6f 6c 20 6f 66 20 74 68 65 20 72 6f  n iCol of the ro
eae0: 77 20 74 68 61 74 20 53 51 4c 20 73 74 61 74 65  w that SQL state
eaf0: 6d 65 6e 74 20 70 53 74 6d 74 20 63 75 72 72 65  ment pStmt curre
eb00: 6e 74 6c 79 20 70 6f 69 6e 74 73 0a 2a 2a 20 74  ntly points.** t
eb10: 6f 20 74 6f 20 74 68 65 20 62 75 66 66 65 72 2e  o to the buffer.
eb20: 0a 2a 2f 0a 73 74 61 74 69 63 20 76 6f 69 64 20  .*/.static void 
eb30: 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 43 6f 6c  sessionAppendCol
eb40: 28 0a 20 20 53 65 73 73 69 6f 6e 42 75 66 66 65  (.  SessionBuffe
eb50: 72 20 2a 70 2c 20 20 20 20 20 20 20 20 20 20 20  r *p,           
eb60: 20 20 20 20 2f 2a 20 42 75 66 66 65 72 20 74 6f      /* Buffer to
eb70: 20 61 70 70 65 6e 64 20 74 6f 20 2a 2f 0a 20 20   append to */.  
eb80: 73 71 6c 69 74 65 33 5f 73 74 6d 74 20 2a 70 53  sqlite3_stmt *pS
eb90: 74 6d 74 2c 20 20 20 20 20 20 20 20 20 20 20 20  tmt,            
eba0: 2f 2a 20 48 61 6e 64 6c 65 20 70 6f 69 6e 74 69  /* Handle pointi
ebb0: 6e 67 20 74 6f 20 72 6f 77 20 63 6f 6e 74 61 69  ng to row contai
ebc0: 6e 69 6e 67 20 76 61 6c 75 65 20 2a 2f 0a 20 20  ning value */.  
ebd0: 69 6e 74 20 69 43 6f 6c 2c 20 20 20 20 20 20 20  int iCol,       
ebe0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
ebf0: 2f 2a 20 43 6f 6c 75 6d 6e 20 74 6f 20 72 65 61  /* Column to rea
ec00: 64 20 76 61 6c 75 65 20 66 72 6f 6d 20 2a 2f 0a  d value from */.
ec10: 20 20 69 6e 74 20 2a 70 52 63 20 20 20 20 20 20    int *pRc      
ec20: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
ec30: 20 20 2f 2a 20 49 4e 2f 4f 55 54 3a 20 45 72 72    /* IN/OUT: Err
ec40: 6f 72 20 63 6f 64 65 20 2a 2f 0a 29 7b 0a 20 20  or code */.){.  
ec50: 69 66 28 20 2a 70 52 63 3d 3d 53 51 4c 49 54 45  if( *pRc==SQLITE
ec60: 5f 4f 4b 20 29 7b 0a 20 20 20 20 69 6e 74 20 65  _OK ){.    int e
ec70: 54 79 70 65 20 3d 20 73 71 6c 69 74 65 33 5f 63  Type = sqlite3_c
ec80: 6f 6c 75 6d 6e 5f 74 79 70 65 28 70 53 74 6d 74  olumn_type(pStmt
ec90: 2c 20 69 43 6f 6c 29 3b 0a 20 20 20 20 73 65 73  , iCol);.    ses
eca0: 73 69 6f 6e 41 70 70 65 6e 64 42 79 74 65 28 70  sionAppendByte(p
ecb0: 2c 20 28 75 38 29 65 54 79 70 65 2c 20 70 52 63  , (u8)eType, pRc
ecc0: 29 3b 0a 20 20 20 20 69 66 28 20 65 54 79 70 65  );.    if( eType
ecd0: 3d 3d 53 51 4c 49 54 45 5f 49 4e 54 45 47 45 52  ==SQLITE_INTEGER
ece0: 20 7c 7c 20 65 54 79 70 65 3d 3d 53 51 4c 49 54   || eType==SQLIT
ecf0: 45 5f 46 4c 4f 41 54 20 29 7b 0a 20 20 20 20 20  E_FLOAT ){.     
ed00: 20 73 71 6c 69 74 65 33 5f 69 6e 74 36 34 20 69   sqlite3_int64 i
ed10: 3b 0a 20 20 20 20 20 20 75 38 20 61 42 75 66 5b  ;.      u8 aBuf[
ed20: 38 5d 3b 0a 20 20 20 20 20 20 69 66 28 20 65 54  8];.      if( eT
ed30: 79 70 65 3d 3d 53 51 4c 49 54 45 5f 49 4e 54 45  ype==SQLITE_INTE
ed40: 47 45 52 20 29 7b 0a 20 20 20 20 20 20 20 20 69  GER ){.        i
ed50: 20 3d 20 73 71 6c 69 74 65 33 5f 63 6f 6c 75 6d   = sqlite3_colum
ed60: 6e 5f 69 6e 74 36 34 28 70 53 74 6d 74 2c 20 69  n_int64(pStmt, i
ed70: 43 6f 6c 29 3b 0a 20 20 20 20 20 20 7d 65 6c 73  Col);.      }els
ed80: 65 7b 0a 20 20 20 20 20 20 20 20 64 6f 75 62 6c  e{.        doubl
ed90: 65 20 72 20 3d 20 73 71 6c 69 74 65 33 5f 63 6f  e r = sqlite3_co
eda0: 6c 75 6d 6e 5f 64 6f 75 62 6c 65 28 70 53 74 6d  lumn_double(pStm
edb0: 74 2c 20 69 43 6f 6c 29 3b 0a 20 20 20 20 20 20  t, iCol);.      
edc0: 20 20 6d 65 6d 63 70 79 28 26 69 2c 20 26 72 2c    memcpy(&i, &r,
edd0: 20 38 29 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20   8);.      }.   
ede0: 20 20 20 73 65 73 73 69 6f 6e 50 75 74 49 36 34     sessionPutI64
edf0: 28 61 42 75 66 2c 20 69 29 3b 0a 20 20 20 20 20  (aBuf, i);.     
ee00: 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 42 6c   sessionAppendBl
ee10: 6f 62 28 70 2c 20 61 42 75 66 2c 20 38 2c 20 70  ob(p, aBuf, 8, p
ee20: 52 63 29 3b 0a 20 20 20 20 7d 0a 20 20 20 20 69  Rc);.    }.    i
ee30: 66 28 20 65 54 79 70 65 3d 3d 53 51 4c 49 54 45  f( eType==SQLITE
ee40: 5f 42 4c 4f 42 20 7c 7c 20 65 54 79 70 65 3d 3d  _BLOB || eType==
ee50: 53 51 4c 49 54 45 5f 54 45 58 54 20 29 7b 0a 20  SQLITE_TEXT ){. 
ee60: 20 20 20 20 20 75 38 20 2a 7a 3b 0a 20 20 20 20       u8 *z;.    
ee70: 20 20 69 6e 74 20 6e 42 79 74 65 3b 0a 20 20 20    int nByte;.   
ee80: 20 20 20 69 66 28 20 65 54 79 70 65 3d 3d 53 51     if( eType==SQ
ee90: 4c 49 54 45 5f 42 4c 4f 42 20 29 7b 0a 20 20 20  LITE_BLOB ){.   
eea0: 20 20 20 20 20 7a 20 3d 20 28 75 38 20 2a 29 73       z = (u8 *)s
eeb0: 71 6c 69 74 65 33 5f 63 6f 6c 75 6d 6e 5f 62 6c  qlite3_column_bl
eec0: 6f 62 28 70 53 74 6d 74 2c 20 69 43 6f 6c 29 3b  ob(pStmt, iCol);
eed0: 0a 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20  .      }else{.  
eee0: 20 20 20 20 20 20 7a 20 3d 20 28 75 38 20 2a 29        z = (u8 *)
eef0: 73 71 6c 69 74 65 33 5f 63 6f 6c 75 6d 6e 5f 74  sqlite3_column_t
ef00: 65 78 74 28 70 53 74 6d 74 2c 20 69 43 6f 6c 29  ext(pStmt, iCol)
ef10: 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20  ;.      }.      
ef20: 6e 42 79 74 65 20 3d 20 73 71 6c 69 74 65 33 5f  nByte = sqlite3_
ef30: 63 6f 6c 75 6d 6e 5f 62 79 74 65 73 28 70 53 74  column_bytes(pSt
ef40: 6d 74 2c 20 69 43 6f 6c 29 3b 0a 20 20 20 20 20  mt, iCol);.     
ef50: 20 69 66 28 20 7a 20 7c 7c 20 28 65 54 79 70 65   if( z || (eType
ef60: 3d 3d 53 51 4c 49 54 45 5f 42 4c 4f 42 20 26 26  ==SQLITE_BLOB &&
ef70: 20 6e 42 79 74 65 3d 3d 30 29 20 29 7b 0a 20 20   nByte==0) ){.  
ef80: 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70 70        sessionApp
ef90: 65 6e 64 56 61 72 69 6e 74 28 70 2c 20 6e 42 79  endVarint(p, nBy
efa0: 74 65 2c 20 70 52 63 29 3b 0a 20 20 20 20 20 20  te, pRc);.      
efb0: 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 42    sessionAppendB
efc0: 6c 6f 62 28 70 2c 20 7a 2c 20 6e 42 79 74 65 2c  lob(p, z, nByte,
efd0: 20 70 52 63 29 3b 0a 20 20 20 20 20 20 7d 65 6c   pRc);.      }el
efe0: 73 65 7b 0a 20 20 20 20 20 20 20 20 2a 70 52 63  se{.        *pRc
eff0: 20 3d 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 3b   = SQLITE_NOMEM;
f000: 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 7d 0a 20  .      }.    }. 
f010: 20 7d 0a 7d 0a 0a 2f 2a 0a 2a 2a 0a 2a 2a 20 54   }.}../*.**.** T
f020: 68 69 73 20 66 75 6e 63 74 69 6f 6e 20 61 70 70  his function app
f030: 65 6e 64 73 20 61 6e 20 75 70 64 61 74 65 20 63  ends an update c
f040: 68 61 6e 67 65 20 74 6f 20 74 68 65 20 62 75 66  hange to the buf
f050: 66 65 72 20 28 73 65 65 20 74 68 65 20 63 6f 6d  fer (see the com
f060: 6d 65 6e 74 73 20 0a 2a 2a 20 75 6e 64 65 72 20  ments .** under 
f070: 22 43 48 41 4e 47 45 53 45 54 20 46 4f 52 4d 41  "CHANGESET FORMA
f080: 54 22 20 61 74 20 74 68 65 20 74 6f 70 20 6f 66  T" at the top of
f090: 20 74 68 65 20 66 69 6c 65 29 2e 20 41 6e 20 75   the file). An u
f0a0: 70 64 61 74 65 20 63 68 61 6e 67 65 20 0a 2a 2a  pdate change .**
f0b0: 20 63 6f 6e 73 69 73 74 73 20 6f 66 3a 0a 2a 2a   consists of:.**
f0c0: 0a 2a 2a 20 20 20 31 20 62 79 74 65 3a 20 20 53  .**   1 byte:  S
f0d0: 51 4c 49 54 45 5f 55 50 44 41 54 45 20 28 30 78  QLITE_UPDATE (0x
f0e0: 31 37 29 0a 2a 2a 20 20 20 6e 20 62 79 74 65 73  17).**   n bytes
f0f0: 3a 20 6f 6c 64 2e 2a 20 72 65 63 6f 72 64 20 28  : old.* record (
f100: 73 65 65 20 52 45 43 4f 52 44 20 46 4f 52 4d 41  see RECORD FORMA
f110: 54 29 0a 2a 2a 20 20 20 6d 20 62 79 74 65 73 3a  T).**   m bytes:
f120: 20 6e 65 77 2e 2a 20 72 65 63 6f 72 64 20 28 73   new.* record (s
f130: 65 65 20 52 45 43 4f 52 44 20 46 4f 52 4d 41 54  ee RECORD FORMAT
f140: 29 0a 2a 2a 0a 2a 2a 20 54 68 65 20 53 65 73 73  ).**.** The Sess
f150: 69 6f 6e 43 68 61 6e 67 65 20 6f 62 6a 65 63 74  ionChange object
f160: 20 70 61 73 73 65 64 20 61 73 20 74 68 65 20 74   passed as the t
f170: 68 69 72 64 20 61 72 67 75 6d 65 6e 74 20 63 6f  hird argument co
f180: 6e 74 61 69 6e 73 20 74 68 65 0a 2a 2a 20 76 61  ntains the.** va
f190: 6c 75 65 73 20 74 68 61 74 20 77 65 72 65 20 73  lues that were s
f1a0: 74 6f 72 65 64 20 69 6e 20 74 68 65 20 72 6f 77  tored in the row
f1b0: 20 77 68 65 6e 20 74 68 65 20 73 65 73 73 69 6f   when the sessio
f1c0: 6e 20 62 65 67 61 6e 20 28 74 68 65 20 6f 6c 64  n began (the old
f1d0: 2e 2a 0a 2a 2a 20 76 61 6c 75 65 73 29 2e 20 54  .*.** values). T
f1e0: 68 65 20 73 74 61 74 65 6d 65 6e 74 20 68 61 6e  he statement han
f1f0: 64 6c 65 20 70 61 73 73 65 64 20 61 73 20 74 68  dle passed as th
f200: 65 20 73 65 63 6f 6e 64 20 61 72 67 75 6d 65 6e  e second argumen
f210: 74 20 70 6f 69 6e 74 73 0a 2a 2a 20 61 74 20 74  t points.** at t
f220: 68 65 20 63 75 72 72 65 6e 74 20 76 65 72 73 69  he current versi
f230: 6f 6e 20 6f 66 20 74 68 65 20 72 6f 77 20 28 74  on of the row (t
f240: 68 65 20 6e 65 77 2e 2a 20 76 61 6c 75 65 73 29  he new.* values)
f250: 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 61 6c 6c 20 6f  ..**.** If all o
f260: 66 20 74 68 65 20 6f 6c 64 2e 2a 20 76 61 6c 75  f the old.* valu
f270: 65 73 20 61 72 65 20 65 71 75 61 6c 20 74 6f 20  es are equal to 
f280: 74 68 65 69 72 20 63 6f 72 72 65 73 70 6f 6e 64  their correspond
f290: 69 6e 67 20 6e 65 77 2e 2a 20 76 61 6c 75 65 0a  ing new.* value.
f2a0: 2a 2a 20 28 69 2e 65 2e 20 6e 6f 74 68 69 6e 67  ** (i.e. nothing
f2b0: 20 68 61 73 20 63 68 61 6e 67 65 64 29 2c 20 74   has changed), t
f2c0: 68 65 6e 20 6e 6f 20 64 61 74 61 20 61 74 20 61  hen no data at a
f2d0: 6c 6c 20 69 73 20 61 70 70 65 6e 64 65 64 20 74  ll is appended t
f2e0: 6f 20 74 68 65 20 62 75 66 66 65 72 2e 0a 2a 2a  o the buffer..**
f2f0: 0a 2a 2a 20 4f 74 68 65 72 77 69 73 65 2c 20 74  .** Otherwise, t
f300: 68 65 20 6f 6c 64 2e 2a 20 72 65 63 6f 72 64 20  he old.* record 
f310: 63 6f 6e 74 61 69 6e 73 20 61 6c 6c 20 70 72 69  contains all pri
f320: 6d 61 72 79 20 6b 65 79 20 76 61 6c 75 65 73 20  mary key values 
f330: 61 6e 64 20 74 68 65 20 0a 2a 2a 20 6f 72 69 67  and the .** orig
f340: 69 6e 61 6c 20 76 61 6c 75 65 73 20 6f 66 20 61  inal values of a
f350: 6e 79 20 66 69 65 6c 64 73 20 74 68 61 74 20 68  ny fields that h
f360: 61 76 65 20 62 65 65 6e 20 6d 6f 64 69 66 69 65  ave been modifie
f370: 64 2e 20 54 68 65 20 6e 65 77 2e 2a 20 72 65 63  d. The new.* rec
f380: 6f 72 64 20 0a 2a 2a 20 63 6f 6e 74 61 69 6e 73  ord .** contains
f390: 20 74 68 65 20 6e 65 77 20 76 61 6c 75 65 73 20   the new values 
f3a0: 6f 66 20 6f 6e 6c 79 20 74 68 6f 73 65 20 66 69  of only those fi
f3b0: 65 6c 64 73 20 74 68 61 74 20 68 61 76 65 20 62  elds that have b
f3c0: 65 65 6e 20 6d 6f 64 69 66 69 65 64 2e 0a 2a 2f  een modified..*/
f3d0: 20 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73   .static int ses
f3e0: 73 69 6f 6e 41 70 70 65 6e 64 55 70 64 61 74 65  sionAppendUpdate
f3f0: 28 0a 20 20 53 65 73 73 69 6f 6e 42 75 66 66 65  (.  SessionBuffe
f400: 72 20 2a 70 42 75 66 2c 20 20 20 20 20 20 20 20  r *pBuf,        
f410: 20 20 20 20 2f 2a 20 42 75 66 66 65 72 20 74 6f      /* Buffer to
f420: 20 61 70 70 65 6e 64 20 74 6f 20 2a 2f 0a 20 20   append to */.  
f430: 69 6e 74 20 62 50 61 74 63 68 73 65 74 2c 20 20  int bPatchset,  
f440: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
f450: 2f 2a 20 54 72 75 65 20 66 6f 72 20 22 70 61 74  /* True for "pat
f460: 63 68 73 65 74 22 2c 20 30 20 66 6f 72 20 22 63  chset", 0 for "c
f470: 68 61 6e 67 65 73 65 74 22 20 2a 2f 0a 20 20 73  hangeset" */.  s
f480: 71 6c 69 74 65 33 5f 73 74 6d 74 20 2a 70 53 74  qlite3_stmt *pSt
f490: 6d 74 2c 20 20 20 20 20 20 20 20 20 20 20 20 2f  mt,            /
f4a0: 2a 20 53 74 61 74 65 6d 65 6e 74 20 68 61 6e 64  * Statement hand
f4b0: 6c 65 20 70 6f 69 6e 74 69 6e 67 20 61 74 20 6e  le pointing at n
f4c0: 65 77 20 72 6f 77 20 2a 2f 0a 20 20 53 65 73 73  ew row */.  Sess
f4d0: 69 6f 6e 43 68 61 6e 67 65 20 2a 70 2c 20 20 20  ionChange *p,   
f4e0: 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4f              /* O
f4f0: 62 6a 65 63 74 20 63 6f 6e 74 61 69 6e 69 6e 67  bject containing
f500: 20 6f 6c 64 20 76 61 6c 75 65 73 20 2a 2f 0a 20   old values */. 
f510: 20 75 38 20 2a 61 62 50 4b 20 20 20 20 20 20 20   u8 *abPK       
f520: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
f530: 20 2f 2a 20 42 6f 6f 6c 65 61 6e 20 61 72 72 61   /* Boolean arra
f540: 79 20 2d 20 74 72 75 65 20 66 6f 72 20 50 4b 20  y - true for PK 
f550: 63 6f 6c 75 6d 6e 73 20 2a 2f 0a 29 7b 0a 20 20  columns */.){.  
f560: 69 6e 74 20 72 63 20 3d 20 53 51 4c 49 54 45 5f  int rc = SQLITE_
f570: 4f 4b 3b 0a 20 20 53 65 73 73 69 6f 6e 42 75 66  OK;.  SessionBuf
f580: 66 65 72 20 62 75 66 32 20 3d 20 7b 30 2c 30 2c  fer buf2 = {0,0,
f590: 30 7d 3b 20 2f 2a 20 42 75 66 66 65 72 20 74 6f  0}; /* Buffer to
f5a0: 20 61 63 63 75 6d 75 6c 61 74 65 20 6e 65 77 2e   accumulate new.
f5b0: 2a 20 72 65 63 6f 72 64 20 69 6e 20 2a 2f 0a 20  * record in */. 
f5c0: 20 69 6e 74 20 62 4e 6f 6f 70 20 3d 20 31 3b 20   int bNoop = 1; 
f5d0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
f5e0: 2a 20 53 65 74 20 74 6f 20 7a 65 72 6f 20 69 66  * Set to zero if
f5f0: 20 61 6e 79 20 76 61 6c 75 65 73 20 61 72 65 20   any values are 
f600: 6d 6f 64 69 66 69 65 64 20 2a 2f 0a 20 20 69 6e  modified */.  in
f610: 74 20 6e 52 65 77 69 6e 64 20 3d 20 70 42 75 66  t nRewind = pBuf
f620: 2d 3e 6e 42 75 66 3b 20 20 20 20 20 2f 2a 20 53  ->nBuf;     /* S
f630: 65 74 20 74 6f 20 7a 65 72 6f 20 69 66 20 61 6e  et to zero if an
f640: 79 20 76 61 6c 75 65 73 20 61 72 65 20 6d 6f 64  y values are mod
f650: 69 66 69 65 64 20 2a 2f 0a 20 20 69 6e 74 20 69  ified */.  int i
f660: 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  ;               
f670: 20 20 20 20 20 20 20 20 20 2f 2a 20 55 73 65 64           /* Used
f680: 20 74 6f 20 69 74 65 72 61 74 65 20 74 68 72 6f   to iterate thro
f690: 75 67 68 20 63 6f 6c 75 6d 6e 73 20 2a 2f 0a 20  ugh columns */. 
f6a0: 20 75 38 20 2a 70 43 73 72 20 3d 20 70 2d 3e 61   u8 *pCsr = p->a
f6b0: 52 65 63 6f 72 64 3b 20 20 20 20 20 20 20 20 2f  Record;        /
f6c0: 2a 20 55 73 65 64 20 74 6f 20 69 74 65 72 61 74  * Used to iterat
f6d0: 65 20 74 68 72 6f 75 67 68 20 6f 6c 64 2e 2a 20  e through old.* 
f6e0: 76 61 6c 75 65 73 20 2a 2f 0a 0a 20 20 73 65 73  values */..  ses
f6f0: 73 69 6f 6e 41 70 70 65 6e 64 42 79 74 65 28 70  sionAppendByte(p
f700: 42 75 66 2c 20 53 51 4c 49 54 45 5f 55 50 44 41  Buf, SQLITE_UPDA
f710: 54 45 2c 20 26 72 63 29 3b 0a 20 20 73 65 73 73  TE, &rc);.  sess
f720: 69 6f 6e 41 70 70 65 6e 64 42 79 74 65 28 70 42  ionAppendByte(pB
f730: 75 66 2c 20 70 2d 3e 62 49 6e 64 69 72 65 63 74  uf, p->bIndirect
f740: 2c 20 26 72 63 29 3b 0a 20 20 66 6f 72 28 69 3d  , &rc);.  for(i=
f750: 30 3b 20 69 3c 73 71 6c 69 74 65 33 5f 63 6f 6c  0; i<sqlite3_col
f760: 75 6d 6e 5f 63 6f 75 6e 74 28 70 53 74 6d 74 29  umn_count(pStmt)
f770: 3b 20 69 2b 2b 29 7b 0a 20 20 20 20 69 6e 74 20  ; i++){.    int 
f780: 62 43 68 61 6e 67 65 64 20 3d 20 30 3b 0a 20 20  bChanged = 0;.  
f790: 20 20 69 6e 74 20 6e 41 64 76 61 6e 63 65 3b 0a    int nAdvance;.
f7a0: 20 20 20 20 69 6e 74 20 65 54 79 70 65 20 3d 20      int eType = 
f7b0: 2a 70 43 73 72 3b 0a 20 20 20 20 73 77 69 74 63  *pCsr;.    switc
f7c0: 68 28 20 65 54 79 70 65 20 29 7b 0a 20 20 20 20  h( eType ){.    
f7d0: 20 20 63 61 73 65 20 53 51 4c 49 54 45 5f 4e 55    case SQLITE_NU
f7e0: 4c 4c 3a 0a 20 20 20 20 20 20 20 20 6e 41 64 76  LL:.        nAdv
f7f0: 61 6e 63 65 20 3d 20 31 3b 0a 20 20 20 20 20 20  ance = 1;.      
f800: 20 20 69 66 28 20 73 71 6c 69 74 65 33 5f 63 6f    if( sqlite3_co
f810: 6c 75 6d 6e 5f 74 79 70 65 28 70 53 74 6d 74 2c  lumn_type(pStmt,
f820: 20 69 29 21 3d 53 51 4c 49 54 45 5f 4e 55 4c 4c   i)!=SQLITE_NULL
f830: 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 62 43   ){.          bC
f840: 68 61 6e 67 65 64 20 3d 20 31 3b 0a 20 20 20 20  hanged = 1;.    
f850: 20 20 20 20 7d 0a 20 20 20 20 20 20 20 20 62 72      }.        br
f860: 65 61 6b 3b 0a 0a 20 20 20 20 20 20 63 61 73 65  eak;..      case
f870: 20 53 51 4c 49 54 45 5f 46 4c 4f 41 54 3a 0a 20   SQLITE_FLOAT:. 
f880: 20 20 20 20 20 63 61 73 65 20 53 51 4c 49 54 45       case SQLITE
f890: 5f 49 4e 54 45 47 45 52 3a 20 7b 0a 20 20 20 20  _INTEGER: {.    
f8a0: 20 20 20 20 6e 41 64 76 61 6e 63 65 20 3d 20 39      nAdvance = 9
f8b0: 3b 0a 20 20 20 20 20 20 20 20 69 66 28 20 65 54  ;.        if( eT
f8c0: 79 70 65 3d 3d 73 71 6c 69 74 65 33 5f 63 6f 6c  ype==sqlite3_col
f8d0: 75 6d 6e 5f 74 79 70 65 28 70 53 74 6d 74 2c 20  umn_type(pStmt, 
f8e0: 69 29 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20  i) ){.          
f8f0: 73 71 6c 69 74 65 33 5f 69 6e 74 36 34 20 69 56  sqlite3_int64 iV
f900: 61 6c 20 3d 20 73 65 73 73 69 6f 6e 47 65 74 49  al = sessionGetI
f910: 36 34 28 26 70 43 73 72 5b 31 5d 29 3b 0a 20 20  64(&pCsr[1]);.  
f920: 20 20 20 20 20 20 20 20 69 66 28 20 65 54 79 70          if( eTyp
f930: 65 3d 3d 53 51 4c 49 54 45 5f 49 4e 54 45 47 45  e==SQLITE_INTEGE
f940: 52 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 20  R ){.           
f950: 20 69 66 28 20 69 56 61 6c 3d 3d 73 71 6c 69 74   if( iVal==sqlit
f960: 65 33 5f 63 6f 6c 75 6d 6e 5f 69 6e 74 36 34 28  e3_column_int64(
f970: 70 53 74 6d 74 2c 20 69 29 20 29 20 62 72 65 61  pStmt, i) ) brea
f980: 6b 3b 0a 20 20 20 20 20 20 20 20 20 20 7d 65 6c  k;.          }el
f990: 73 65 7b 0a 20 20 20 20 20 20 20 20 20 20 20 20  se{.            
f9a0: 64 6f 75 62 6c 65 20 64 56 61 6c 3b 0a 20 20 20  double dVal;.   
f9b0: 20 20 20 20 20 20 20 20 20 6d 65 6d 63 70 79 28           memcpy(
f9c0: 26 64 56 61 6c 2c 20 26 69 56 61 6c 2c 20 38 29  &dVal, &iVal, 8)
f9d0: 3b 0a 20 20 20 20 20 20 20 20 20 20 20 20 69 66  ;.            if
f9e0: 28 20 64 56 61 6c 3d 3d 73 71 6c 69 74 65 33 5f  ( dVal==sqlite3_
f9f0: 63 6f 6c 75 6d 6e 5f 64 6f 75 62 6c 65 28 70 53  column_double(pS
fa00: 74 6d 74 2c 20 69 29 20 29 20 62 72 65 61 6b 3b  tmt, i) ) break;
fa10: 0a 20 20 20 20 20 20 20 20 20 20 7d 0a 20 20 20  .          }.   
fa20: 20 20 20 20 20 7d 0a 20 20 20 20 20 20 20 20 62       }.        b
fa30: 43 68 61 6e 67 65 64 20 3d 20 31 3b 0a 20 20 20  Changed = 1;.   
fa40: 20 20 20 20 20 62 72 65 61 6b 3b 0a 20 20 20 20       break;.    
fa50: 20 20 7d 0a 0a 20 20 20 20 20 20 64 65 66 61 75    }..      defau
fa60: 6c 74 3a 20 7b 0a 20 20 20 20 20 20 20 20 69 6e  lt: {.        in
fa70: 74 20 6e 3b 0a 20 20 20 20 20 20 20 20 69 6e 74  t n;.        int
fa80: 20 6e 48 64 72 20 3d 20 31 20 2b 20 73 65 73 73   nHdr = 1 + sess
fa90: 69 6f 6e 56 61 72 69 6e 74 47 65 74 28 26 70 43  ionVarintGet(&pC
faa0: 73 72 5b 31 5d 2c 20 26 6e 29 3b 0a 20 20 20 20  sr[1], &n);.    
fab0: 20 20 20 20 61 73 73 65 72 74 28 20 65 54 79 70      assert( eTyp
fac0: 65 3d 3d 53 51 4c 49 54 45 5f 54 45 58 54 20 7c  e==SQLITE_TEXT |
fad0: 7c 20 65 54 79 70 65 3d 3d 53 51 4c 49 54 45 5f  | eType==SQLITE_
fae0: 42 4c 4f 42 20 29 3b 0a 20 20 20 20 20 20 20 20  BLOB );.        
faf0: 6e 41 64 76 61 6e 63 65 20 3d 20 6e 48 64 72 20  nAdvance = nHdr 
fb00: 2b 20 6e 3b 0a 20 20 20 20 20 20 20 20 69 66 28  + n;.        if(
fb10: 20 65 54 79 70 65 3d 3d 73 71 6c 69 74 65 33 5f   eType==sqlite3_
fb20: 63 6f 6c 75 6d 6e 5f 74 79 70 65 28 70 53 74 6d  column_type(pStm
fb30: 74 2c 20 69 29 20 0a 20 20 20 20 20 20 20 20 20  t, i) .         
fb40: 26 26 20 6e 3d 3d 73 71 6c 69 74 65 33 5f 63 6f  && n==sqlite3_co
fb50: 6c 75 6d 6e 5f 62 79 74 65 73 28 70 53 74 6d 74  lumn_bytes(pStmt
fb60: 2c 20 69 29 20 0a 20 20 20 20 20 20 20 20 20 26  , i) .         &
fb70: 26 20 28 6e 3d 3d 30 20 7c 7c 20 30 3d 3d 6d 65  & (n==0 || 0==me
fb80: 6d 63 6d 70 28 26 70 43 73 72 5b 6e 48 64 72 5d  mcmp(&pCsr[nHdr]
fb90: 2c 20 73 71 6c 69 74 65 33 5f 63 6f 6c 75 6d 6e  , sqlite3_column
fba0: 5f 62 6c 6f 62 28 70 53 74 6d 74 2c 20 69 29 2c  _blob(pStmt, i),
fbb0: 20 6e 29 29 0a 20 20 20 20 20 20 20 20 29 7b 0a   n)).        ){.
fbc0: 20 20 20 20 20 20 20 20 20 20 62 72 65 61 6b 3b            break;
fbd0: 0a 20 20 20 20 20 20 20 20 7d 0a 20 20 20 20 20  .        }.     
fbe0: 20 20 20 62 43 68 61 6e 67 65 64 20 3d 20 31 3b     bChanged = 1;
fbf0: 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 7d 0a 0a  .      }.    }..
fc00: 20 20 20 20 2f 2a 20 49 66 20 61 74 20 6c 65 61      /* If at lea
fc10: 73 74 20 6f 6e 65 20 66 69 65 6c 64 20 68 61 73  st one field has
fc20: 20 62 65 65 6e 20 6d 6f 64 69 66 69 65 64 2c 20   been modified, 
fc30: 74 68 69 73 20 69 73 20 6e 6f 74 20 61 20 6e 6f  this is not a no
fc40: 2d 6f 70 2e 20 2a 2f 0a 20 20 20 20 69 66 28 20  -op. */.    if( 
fc50: 62 43 68 61 6e 67 65 64 20 29 20 62 4e 6f 6f 70  bChanged ) bNoop
fc60: 20 3d 20 30 3b 0a 0a 20 20 20 20 2f 2a 20 41 64   = 0;..    /* Ad
fc70: 64 20 61 20 66 69 65 6c 64 20 74 6f 20 74 68 65  d a field to the
fc80: 20 6f 6c 64 2e 2a 20 72 65 63 6f 72 64 2e 20 54   old.* record. T
fc90: 68 69 73 20 69 73 20 6f 6d 69 74 74 65 64 20 69  his is omitted i
fca0: 66 20 74 68 69 73 20 6d 6f 64 75 6c 65 73 20 69  f this modules i
fcb0: 73 0a 20 20 20 20 2a 2a 20 63 75 72 72 65 6e 74  s.    ** current
fcc0: 6c 79 20 67 65 6e 65 72 61 74 69 6e 67 20 61 20  ly generating a 
fcd0: 70 61 74 63 68 73 65 74 2e 20 2a 2f 0a 20 20 20  patchset. */.   
fce0: 20 69 66 28 20 62 50 61 74 63 68 73 65 74 3d 3d   if( bPatchset==
fcf0: 30 20 29 7b 0a 20 20 20 20 20 20 69 66 28 20 62  0 ){.      if( b
fd00: 43 68 61 6e 67 65 64 20 7c 7c 20 61 62 50 4b 5b  Changed || abPK[
fd10: 69 5d 20 29 7b 0a 20 20 20 20 20 20 20 20 73 65  i] ){.        se
fd20: 73 73 69 6f 6e 41 70 70 65 6e 64 42 6c 6f 62 28  ssionAppendBlob(
fd30: 70 42 75 66 2c 20 70 43 73 72 2c 20 6e 41 64 76  pBuf, pCsr, nAdv
fd40: 61 6e 63 65 2c 20 26 72 63 29 3b 0a 20 20 20 20  ance, &rc);.    
fd50: 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 20    }else{.       
fd60: 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 42 79   sessionAppendBy
fd70: 74 65 28 70 42 75 66 2c 20 30 2c 20 26 72 63 29  te(pBuf, 0, &rc)
fd80: 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 7d 0a  ;.      }.    }.
fd90: 0a 20 20 20 20 2f 2a 20 41 64 64 20 61 20 66 69  .    /* Add a fi
fda0: 65 6c 64 20 74 6f 20 74 68 65 20 6e 65 77 2e 2a  eld to the new.*
fdb0: 20 72 65 63 6f 72 64 2e 20 4f 72 20 74 68 65 20   record. Or the 
fdc0: 6f 6e 6c 79 20 72 65 63 6f 72 64 20 69 66 20 63  only record if c
fdd0: 75 72 72 65 6e 74 6c 79 0a 20 20 20 20 2a 2a 20  urrently.    ** 
fde0: 67 65 6e 65 72 61 74 69 6e 67 20 61 20 70 61 74  generating a pat
fdf0: 63 68 73 65 74 2e 20 20 2a 2f 0a 20 20 20 20 69  chset.  */.    i
fe00: 66 28 20 62 43 68 61 6e 67 65 64 20 7c 7c 20 28  f( bChanged || (
fe10: 62 50 61 74 63 68 73 65 74 20 26 26 20 61 62 50  bPatchset && abP
fe20: 4b 5b 69 5d 29 20 29 7b 0a 20 20 20 20 20 20 73  K[i]) ){.      s
fe30: 65 73 73 69 6f 6e 41 70 70 65 6e 64 43 6f 6c 28  essionAppendCol(
fe40: 26 62 75 66 32 2c 20 70 53 74 6d 74 2c 20 69 2c  &buf2, pStmt, i,
fe50: 20 26 72 63 29 3b 0a 20 20 20 20 7d 65 6c 73 65   &rc);.    }else
fe60: 7b 0a 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41  {.      sessionA
fe70: 70 70 65 6e 64 42 79 74 65 28 26 62 75 66 32 2c  ppendByte(&buf2,
fe80: 20 30 2c 20 26 72 63 29 3b 0a 20 20 20 20 7d 0a   0, &rc);.    }.
fe90: 0a 20 20 20 20 70 43 73 72 20 2b 3d 20 6e 41 64  .    pCsr += nAd
fea0: 76 61 6e 63 65 3b 0a 20 20 7d 0a 0a 20 20 69 66  vance;.  }..  if
feb0: 28 20 62 4e 6f 6f 70 20 29 7b 0a 20 20 20 20 70  ( bNoop ){.    p
fec0: 42 75 66 2d 3e 6e 42 75 66 20 3d 20 6e 52 65 77  Buf->nBuf = nRew
fed0: 69 6e 64 3b 0a 20 20 7d 65 6c 73 65 7b 0a 20 20  ind;.  }else{.  
fee0: 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 42    sessionAppendB
fef0: 6c 6f 62 28 70 42 75 66 2c 20 62 75 66 32 2e 61  lob(pBuf, buf2.a
ff00: 42 75 66 2c 20 62 75 66 32 2e 6e 42 75 66 2c 20  Buf, buf2.nBuf, 
ff10: 26 72 63 29 3b 0a 20 20 7d 0a 20 20 73 71 6c 69  &rc);.  }.  sqli
ff20: 74 65 33 5f 66 72 65 65 28 62 75 66 32 2e 61 42  te3_free(buf2.aB
ff30: 75 66 29 3b 0a 0a 20 20 72 65 74 75 72 6e 20 72  uf);..  return r
ff40: 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 41 70 70 65  c;.}../*.** Appe
ff50: 6e 64 20 61 20 44 45 4c 45 54 45 20 63 68 61 6e  nd a DELETE chan
ff60: 67 65 20 74 6f 20 74 68 65 20 62 75 66 66 65 72  ge to the buffer
ff70: 20 70 61 73 73 65 64 20 61 73 20 74 68 65 20 66   passed as the f
ff80: 69 72 73 74 20 61 72 67 75 6d 65 6e 74 2e 20 55  irst argument. U
ff90: 73 65 0a 2a 2a 20 74 68 65 20 63 68 61 6e 67 65  se.** the change
ffa0: 73 65 74 20 66 6f 72 6d 61 74 20 69 66 20 61 72  set format if ar
ffb0: 67 75 6d 65 6e 74 20 62 50 61 74 63 68 73 65 74  gument bPatchset
ffc0: 20 69 73 20 7a 65 72 6f 2c 20 6f 72 20 74 68 65   is zero, or the
ffd0: 20 70 61 74 63 68 73 65 74 0a 2a 2a 20 66 6f 72   patchset.** for
ffe0: 6d 61 74 20 6f 74 68 65 72 77 69 73 65 2e 0a 2a  mat otherwise..*
fff0: 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73  /.static int ses
10000 73 69 6f 6e 41 70 70 65 6e 64 44 65 6c 65 74 65  sionAppendDelete
10010 28 0a 20 20 53 65 73 73 69 6f 6e 42 75 66 66 65  (.  SessionBuffe
10020 72 20 2a 70 42 75 66 2c 20 20 20 20 20 20 20 20  r *pBuf,        
10030 20 20 20 20 2f 2a 20 42 75 66 66 65 72 20 74 6f      /* Buffer to
10040 20 61 70 70 65 6e 64 20 74 6f 20 2a 2f 0a 20 20   append to */.  
10050 69 6e 74 20 62 50 61 74 63 68 73 65 74 2c 20 20  int bPatchset,  
10060 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
10070 2f 2a 20 54 72 75 65 20 66 6f 72 20 22 70 61 74  /* True for "pat
10080 63 68 73 65 74 22 2c 20 30 20 66 6f 72 20 22 63  chset", 0 for "c
10090 68 61 6e 67 65 73 65 74 22 20 2a 2f 0a 20 20 53  hangeset" */.  S
100a0 65 73 73 69 6f 6e 43 68 61 6e 67 65 20 2a 70 2c  essionChange *p,
100b0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
100c0 2a 20 4f 62 6a 65 63 74 20 63 6f 6e 74 61 69 6e  * Object contain
100d0 69 6e 67 20 6f 6c 64 20 76 61 6c 75 65 73 20 2a  ing old values *
100e0 2f 0a 20 20 69 6e 74 20 6e 43 6f 6c 2c 20 20 20  /.  int nCol,   
100f0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
10100 20 20 20 20 2f 2a 20 4e 75 6d 62 65 72 20 6f 66      /* Number of
10110 20 63 6f 6c 75 6d 6e 73 20 69 6e 20 74 61 62 6c   columns in tabl
10120 65 20 2a 2f 0a 20 20 75 38 20 2a 61 62 50 4b 20  e */.  u8 *abPK 
10130 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
10140 20 20 20 20 20 20 20 2f 2a 20 42 6f 6f 6c 65 61         /* Boolea
10150 6e 20 61 72 72 61 79 20 2d 20 74 72 75 65 20 66  n array - true f
10160 6f 72 20 50 4b 20 63 6f 6c 75 6d 6e 73 20 2a 2f  or PK columns */
10170 0a 29 7b 0a 20 20 69 6e 74 20 72 63 20 3d 20 53  .){.  int rc = S
10180 51 4c 49 54 45 5f 4f 4b 3b 0a 0a 20 20 73 65 73  QLITE_OK;..  ses
10190 73 69 6f 6e 41 70 70 65 6e 64 42 79 74 65 28 70  sionAppendByte(p
101a0 42 75 66 2c 20 53 51 4c 49 54 45 5f 44 45 4c 45  Buf, SQLITE_DELE
101b0 54 45 2c 20 26 72 63 29 3b 0a 20 20 73 65 73 73  TE, &rc);.  sess
101c0 69 6f 6e 41 70 70 65 6e 64 42 79 74 65 28 70 42  ionAppendByte(pB
101d0 75 66 2c 20 70 2d 3e 62 49 6e 64 69 72 65 63 74  uf, p->bIndirect
101e0 2c 20 26 72 63 29 3b 0a 0a 20 20 69 66 28 20 62  , &rc);..  if( b
101f0 50 61 74 63 68 73 65 74 3d 3d 30 20 29 7b 0a 20  Patchset==0 ){. 
10200 20 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64     sessionAppend
10210 42 6c 6f 62 28 70 42 75 66 2c 20 70 2d 3e 61 52  Blob(pBuf, p->aR
10220 65 63 6f 72 64 2c 20 70 2d 3e 6e 52 65 63 6f 72  ecord, p->nRecor
10230 64 2c 20 26 72 63 29 3b 0a 20 20 7d 65 6c 73 65  d, &rc);.  }else
10240 7b 0a 20 20 20 20 69 6e 74 20 69 3b 0a 20 20 20  {.    int i;.   
10250 20 75 38 20 2a 61 20 3d 20 70 2d 3e 61 52 65 63   u8 *a = p->aRec
10260 6f 72 64 3b 0a 20 20 20 20 66 6f 72 28 69 3d 30  ord;.    for(i=0
10270 3b 20 69 3c 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a  ; i<nCol; i++){.
10280 20 20 20 20 20 20 75 38 20 2a 70 53 74 61 72 74        u8 *pStart
10290 20 3d 20 61 3b 0a 20 20 20 20 20 20 69 6e 74 20   = a;.      int 
102a0 65 54 79 70 65 20 3d 20 2a 61 2b 2b 3b 0a 0a 20  eType = *a++;.. 
102b0 20 20 20 20 20 73 77 69 74 63 68 28 20 65 54 79       switch( eTy
102c0 70 65 20 29 7b 0a 20 20 20 20 20 20 20 20 63 61  pe ){.        ca
102d0 73 65 20 30 3a 0a 20 20 20 20 20 20 20 20 63 61  se 0:.        ca
102e0 73 65 20 53 51 4c 49 54 45 5f 4e 55 4c 4c 3a 0a  se SQLITE_NULL:.
102f0 20 20 20 20 20 20 20 20 20 20 61 73 73 65 72 74            assert
10300 28 20 61 62 50 4b 5b 69 5d 3d 3d 30 20 29 3b 0a  ( abPK[i]==0 );.
10310 20 20 20 20 20 20 20 20 20 20 62 72 65 61 6b 3b            break;
10320 0a 0a 20 20 20 20 20 20 20 20 63 61 73 65 20 53  ..        case S
10330 51 4c 49 54 45 5f 46 4c 4f 41 54 3a 0a 20 20 20  QLITE_FLOAT:.   
10340 20 20 20 20 20 63 61 73 65 20 53 51 4c 49 54 45       case SQLITE
10350 5f 49 4e 54 45 47 45 52 3a 0a 20 20 20 20 20 20  _INTEGER:.      
10360 20 20 20 20 61 20 2b 3d 20 38 3b 0a 20 20 20 20      a += 8;.    
10370 20 20 20 20 20 20 62 72 65 61 6b 3b 0a 0a 20 20        break;..  
10380 20 20 20 20 20 20 64 65 66 61 75 6c 74 3a 20 7b        default: {
10390 0a 20 20 20 20 20 20 20 20 20 20 69 6e 74 20 6e  .          int n
103a0 3b 0a 20 20 20 20 20 20 20 20 20 20 61 20 2b 3d  ;.          a +=
103b0 20 73 65 73 73 69 6f 6e 56 61 72 69 6e 74 47 65   sessionVarintGe
103c0 74 28 61 2c 20 26 6e 29 3b 0a 20 20 20 20 20 20  t(a, &n);.      
103d0 20 20 20 20 61 20 2b 3d 20 6e 3b 0a 20 20 20 20      a += n;.    
103e0 20 20 20 20 20 20 62 72 65 61 6b 3b 0a 20 20 20        break;.   
103f0 20 20 20 20 20 7d 0a 20 20 20 20 20 20 7d 0a 20       }.      }. 
10400 20 20 20 20 20 69 66 28 20 61 62 50 4b 5b 69 5d       if( abPK[i]
10410 20 29 7b 0a 20 20 20 20 20 20 20 20 73 65 73 73   ){.        sess
10420 69 6f 6e 41 70 70 65 6e 64 42 6c 6f 62 28 70 42  ionAppendBlob(pB
10430 75 66 2c 20 70 53 74 61 72 74 2c 20 28 69 6e 74  uf, pStart, (int
10440 29 28 61 2d 70 53 74 61 72 74 29 2c 20 26 72 63  )(a-pStart), &rc
10450 29 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 7d  );.      }.    }
10460 0a 20 20 20 20 61 73 73 65 72 74 28 20 28 61 20  .    assert( (a 
10470 2d 20 70 2d 3e 61 52 65 63 6f 72 64 29 3d 3d 70  - p->aRecord)==p
10480 2d 3e 6e 52 65 63 6f 72 64 20 29 3b 0a 20 20 7d  ->nRecord );.  }
10490 0a 0a 20 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d  ..  return rc;.}
104a0 0a 0a 2f 2a 0a 2a 2a 20 46 6f 72 6d 75 6c 61 74  ../*.** Formulat
104b0 65 20 61 6e 64 20 70 72 65 70 61 72 65 20 61 20  e and prepare a 
104c0 53 45 4c 45 43 54 20 73 74 61 74 65 6d 65 6e 74  SELECT statement
104d0 20 74 6f 20 72 65 74 72 69 65 76 65 20 61 20 72   to retrieve a r
104e0 6f 77 20 66 72 6f 6d 20 74 61 62 6c 65 0a 2a 2a  ow from table.**
104f0 20 7a 54 61 62 20 69 6e 20 64 61 74 61 62 61 73   zTab in databas
10500 65 20 7a 44 62 20 62 61 73 65 64 20 6f 6e 20 69  e zDb based on i
10510 74 73 20 70 72 69 6d 61 72 79 20 6b 65 79 2e 20  ts primary key. 
10520 69 2e 65 2e 0a 2a 2a 0a 2a 2a 20 20 20 53 45 4c  i.e..**.**   SEL
10530 45 43 54 20 2a 20 46 52 4f 4d 20 7a 44 62 2e 7a  ECT * FROM zDb.z
10540 54 61 62 20 57 48 45 52 45 20 70 6b 31 20 3d 20  Tab WHERE pk1 = 
10550 3f 20 41 4e 44 20 70 6b 32 20 3d 20 3f 20 41 4e  ? AND pk2 = ? AN
10560 44 20 2e 2e 2e 0a 2a 2f 0a 73 74 61 74 69 63 20  D ....*/.static 
10570 69 6e 74 20 73 65 73 73 69 6f 6e 53 65 6c 65 63  int sessionSelec
10580 74 53 74 6d 74 28 0a 20 20 73 71 6c 69 74 65 33  tStmt(.  sqlite3
10590 20 2a 64 62 2c 20 20 20 20 20 20 20 20 20 20 20   *db,           
105a0 20 20 20 20 20 20 20 20 20 2f 2a 20 44 61 74 61           /* Data
105b0 62 61 73 65 20 68 61 6e 64 6c 65 20 2a 2f 0a 20  base handle */. 
105c0 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 44 62   const char *zDb
105d0 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  ,               
105e0 20 2f 2a 20 44 61 74 61 62 61 73 65 20 6e 61 6d   /* Database nam
105f0 65 20 2a 2f 0a 20 20 63 6f 6e 73 74 20 63 68 61  e */.  const cha
10600 72 20 2a 7a 54 61 62 2c 20 20 20 20 20 20 20 20  r *zTab,        
10610 20 20 20 20 20 20 20 2f 2a 20 54 61 62 6c 65 20         /* Table 
10620 6e 61 6d 65 20 2a 2f 0a 20 20 69 6e 74 20 6e 43  name */.  int nC
10630 6f 6c 2c 20 20 20 20 20 20 20 20 20 20 20 20 20  ol,             
10640 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4e 75 6d            /* Num
10650 62 65 72 20 6f 66 20 63 6f 6c 75 6d 6e 73 20 69  ber of columns i
10660 6e 20 74 61 62 6c 65 20 2a 2f 0a 20 20 63 6f 6e  n table */.  con
10670 73 74 20 63 68 61 72 20 2a 2a 61 7a 43 6f 6c 2c  st char **azCol,
10680 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
10690 4e 61 6d 65 73 20 6f 66 20 74 61 62 6c 65 20 63  Names of table c
106a0 6f 6c 75 6d 6e 73 20 2a 2f 0a 20 20 75 38 20 2a  olumns */.  u8 *
106b0 61 62 50 4b 2c 20 20 20 20 20 20 20 20 20 20 20  abPK,           
106c0 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 50              /* P
106d0 52 49 4d 41 52 59 20 4b 45 59 20 20 61 72 72 61  RIMARY KEY  arra
106e0 79 20 2a 2f 0a 20 20 73 71 6c 69 74 65 33 5f 73  y */.  sqlite3_s
106f0 74 6d 74 20 2a 2a 70 70 53 74 6d 74 20 20 20 20  tmt **ppStmt    
10700 20 20 20 20 20 20 20 2f 2a 20 4f 55 54 3a 20 50         /* OUT: P
10710 72 65 70 61 72 65 64 20 53 45 4c 45 43 54 20 73  repared SELECT s
10720 74 61 74 65 6d 65 6e 74 20 2a 2f 0a 29 7b 0a 20  tatement */.){. 
10730 20 69 6e 74 20 72 63 20 3d 20 53 51 4c 49 54 45   int rc = SQLITE
10740 5f 4f 4b 3b 0a 20 20 69 6e 74 20 69 3b 0a 20 20  _OK;.  int i;.  
10750 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 53 65 70  const char *zSep
10760 20 3d 20 22 22 3b 0a 20 20 53 65 73 73 69 6f 6e   = "";.  Session
10770 42 75 66 66 65 72 20 62 75 66 20 3d 20 7b 30 2c  Buffer buf = {0,
10780 20 30 2c 20 30 7d 3b 0a 0a 20 20 73 65 73 73 69   0, 0};..  sessi
10790 6f 6e 41 70 70 65 6e 64 53 74 72 28 26 62 75 66  onAppendStr(&buf
107a0 2c 20 22 53 45 4c 45 43 54 20 2a 20 46 52 4f 4d  , "SELECT * FROM
107b0 20 22 2c 20 26 72 63 29 3b 0a 20 20 73 65 73 73   ", &rc);.  sess
107c0 69 6f 6e 41 70 70 65 6e 64 49 64 65 6e 74 28 26  ionAppendIdent(&
107d0 62 75 66 2c 20 7a 44 62 2c 20 26 72 63 29 3b 0a  buf, zDb, &rc);.
107e0 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 53    sessionAppendS
107f0 74 72 28 26 62 75 66 2c 20 22 2e 22 2c 20 26 72  tr(&buf, ".", &r
10800 63 29 3b 0a 20 20 73 65 73 73 69 6f 6e 41 70 70  c);.  sessionApp
10810 65 6e 64 49 64 65 6e 74 28 26 62 75 66 2c 20 7a  endIdent(&buf, z
10820 54 61 62 2c 20 26 72 63 29 3b 0a 20 20 73 65 73  Tab, &rc);.  ses
10830 73 69 6f 6e 41 70 70 65 6e 64 53 74 72 28 26 62  sionAppendStr(&b
10840 75 66 2c 20 22 20 57 48 45 52 45 20 22 2c 20 26  uf, " WHERE ", &
10850 72 63 29 3b 0a 20 20 66 6f 72 28 69 3d 30 3b 20  rc);.  for(i=0; 
10860 69 3c 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a 20 20  i<nCol; i++){.  
10870 20 20 69 66 28 20 61 62 50 4b 5b 69 5d 20 29 7b    if( abPK[i] ){
10880 0a 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70  .      sessionAp
10890 70 65 6e 64 53 74 72 28 26 62 75 66 2c 20 7a 53  pendStr(&buf, zS
108a0 65 70 2c 20 26 72 63 29 3b 0a 20 20 20 20 20 20  ep, &rc);.      
108b0 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 49 64 65  sessionAppendIde
108c0 6e 74 28 26 62 75 66 2c 20 61 7a 43 6f 6c 5b 69  nt(&buf, azCol[i
108d0 5d 2c 20 26 72 63 29 3b 0a 20 20 20 20 20 20 73  ], &rc);.      s
108e0 65 73 73 69 6f 6e 41 70 70 65 6e 64 53 74 72 28  essionAppendStr(
108f0 26 62 75 66 2c 20 22 20 3d 20 3f 22 2c 20 26 72  &buf, " = ?", &r
10900 63 29 3b 0a 20 20 20 20 20 20 73 65 73 73 69 6f  c);.      sessio
10910 6e 41 70 70 65 6e 64 49 6e 74 65 67 65 72 28 26  nAppendInteger(&
10920 62 75 66 2c 20 69 2b 31 2c 20 26 72 63 29 3b 0a  buf, i+1, &rc);.
10930 20 20 20 20 20 20 7a 53 65 70 20 3d 20 22 20 41        zSep = " A
10940 4e 44 20 22 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a  ND ";.    }.  }.
10950 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54 45    if( rc==SQLITE
10960 5f 4f 4b 20 29 7b 0a 20 20 20 20 72 63 20 3d 20  _OK ){.    rc = 
10970 73 71 6c 69 74 65 33 5f 70 72 65 70 61 72 65 5f  sqlite3_prepare_
10980 76 32 28 64 62 2c 20 28 63 68 61 72 20 2a 29 62  v2(db, (char *)b
10990 75 66 2e 61 42 75 66 2c 20 62 75 66 2e 6e 42 75  uf.aBuf, buf.nBu
109a0 66 2c 20 70 70 53 74 6d 74 2c 20 30 29 3b 0a 20  f, ppStmt, 0);. 
109b0 20 7d 0a 20 20 73 71 6c 69 74 65 33 5f 66 72 65   }.  sqlite3_fre
109c0 65 28 62 75 66 2e 61 42 75 66 29 3b 0a 20 20 72  e(buf.aBuf);.  r
109d0 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a  eturn rc;.}../*.
109e0 2a 2a 20 42 69 6e 64 20 74 68 65 20 50 52 49 4d  ** Bind the PRIM
109f0 41 52 59 20 4b 45 59 20 76 61 6c 75 65 73 20 66  ARY KEY values f
10a00 72 6f 6d 20 74 68 65 20 63 68 61 6e 67 65 20 70  rom the change p
10a10 61 73 73 65 64 20 69 6e 20 61 72 67 75 6d 65 6e  assed in argumen
10a20 74 20 70 43 68 61 6e 67 65 0a 2a 2a 20 74 6f 20  t pChange.** to 
10a30 74 68 65 20 53 45 4c 45 43 54 20 73 74 61 74 65  the SELECT state
10a40 6d 65 6e 74 20 70 61 73 73 65 64 20 61 73 20 74  ment passed as t
10a50 68 65 20 66 69 72 73 74 20 61 72 67 75 6d 65 6e  he first argumen
10a60 74 2e 20 54 68 65 20 53 45 4c 45 43 54 20 73 74  t. The SELECT st
10a70 61 74 65 6d 65 6e 74 0a 2a 2a 20 69 73 20 61 73  atement.** is as
10a80 20 70 72 65 70 61 72 65 64 20 62 79 20 66 75 6e   prepared by fun
10a90 63 74 69 6f 6e 20 73 65 73 73 69 6f 6e 53 65 6c  ction sessionSel
10aa0 65 63 74 53 74 6d 74 28 29 2e 0a 2a 2a 0a 2a 2a  ectStmt()..**.**
10ab0 20 52 65 74 75 72 6e 20 53 51 4c 49 54 45 5f 4f   Return SQLITE_O
10ac0 4b 20 69 66 20 61 6c 6c 20 50 4b 20 76 61 6c 75  K if all PK valu
10ad0 65 73 20 61 72 65 20 73 75 63 63 65 73 73 66 75  es are successfu
10ae0 6c 6c 79 20 62 6f 75 6e 64 2c 20 6f 72 20 61 6e  lly bound, or an
10af0 20 53 51 4c 69 74 65 0a 2a 2a 20 65 72 72 6f 72   SQLite.** error
10b00 20 63 6f 64 65 20 28 65 2e 67 2e 20 53 51 4c 49   code (e.g. SQLI
10b10 54 45 5f 4e 4f 4d 45 4d 29 20 6f 74 68 65 72 77  TE_NOMEM) otherw
10b20 69 73 65 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69  ise..*/.static i
10b30 6e 74 20 73 65 73 73 69 6f 6e 53 65 6c 65 63 74  nt sessionSelect
10b40 42 69 6e 64 28 0a 20 20 73 71 6c 69 74 65 33 5f  Bind(.  sqlite3_
10b50 73 74 6d 74 20 2a 70 53 65 6c 65 63 74 2c 20 20  stmt *pSelect,  
10b60 20 20 20 20 20 20 20 20 2f 2a 20 53 45 4c 45 43          /* SELEC
10b70 54 20 66 72 6f 6d 20 73 65 73 73 69 6f 6e 53 65  T from sessionSe
10b80 6c 65 63 74 53 74 6d 74 28 29 20 2a 2f 0a 20 20  lectStmt() */.  
10b90 69 6e 74 20 6e 43 6f 6c 2c 20 20 20 20 20 20 20  int nCol,       
10ba0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
10bb0 2f 2a 20 4e 75 6d 62 65 72 20 6f 66 20 63 6f 6c  /* Number of col
10bc0 75 6d 6e 73 20 69 6e 20 74 61 62 6c 65 20 2a 2f  umns in table */
10bd0 0a 20 20 75 38 20 2a 61 62 50 4b 2c 20 20 20 20  .  u8 *abPK,    
10be0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
10bf0 20 20 20 2f 2a 20 50 52 49 4d 41 52 59 20 4b 45     /* PRIMARY KE
10c00 59 20 61 72 72 61 79 20 2a 2f 0a 20 20 53 65 73  Y array */.  Ses
10c10 73 69 6f 6e 43 68 61 6e 67 65 20 2a 70 43 68 61  sionChange *pCha
10c20 6e 67 65 20 20 20 20 20 20 20 20 20 20 2f 2a 20  nge          /* 
10c30 43 68 61 6e 67 65 20 73 74 72 75 63 74 75 72 65  Change structure
10c40 20 2a 2f 0a 29 7b 0a 20 20 69 6e 74 20 69 3b 0a   */.){.  int i;.
10c50 20 20 69 6e 74 20 72 63 20 3d 20 53 51 4c 49 54    int rc = SQLIT
10c60 45 5f 4f 4b 3b 0a 20 20 75 38 20 2a 61 20 3d 20  E_OK;.  u8 *a = 
10c70 70 43 68 61 6e 67 65 2d 3e 61 52 65 63 6f 72 64  pChange->aRecord
10c80 3b 0a 0a 20 20 66 6f 72 28 69 3d 30 3b 20 69 3c  ;..  for(i=0; i<
10c90 6e 43 6f 6c 20 26 26 20 72 63 3d 3d 53 51 4c 49  nCol && rc==SQLI
10ca0 54 45 5f 4f 4b 3b 20 69 2b 2b 29 7b 0a 20 20 20  TE_OK; i++){.   
10cb0 20 69 6e 74 20 65 54 79 70 65 20 3d 20 2a 61 2b   int eType = *a+
10cc0 2b 3b 0a 0a 20 20 20 20 73 77 69 74 63 68 28 20  +;..    switch( 
10cd0 65 54 79 70 65 20 29 7b 0a 20 20 20 20 20 20 63  eType ){.      c
10ce0 61 73 65 20 30 3a 0a 20 20 20 20 20 20 63 61 73  ase 0:.      cas
10cf0 65 20 53 51 4c 49 54 45 5f 4e 55 4c 4c 3a 0a 20  e SQLITE_NULL:. 
10d00 20 20 20 20 20 20 20 61 73 73 65 72 74 28 20 61         assert( a
10d10 62 50 4b 5b 69 5d 3d 3d 30 20 29 3b 0a 20 20 20  bPK[i]==0 );.   
10d20 20 20 20 20 20 62 72 65 61 6b 3b 0a 0a 20 20 20       break;..   
10d30 20 20 20 63 61 73 65 20 53 51 4c 49 54 45 5f 49     case SQLITE_I
10d40 4e 54 45 47 45 52 3a 20 7b 0a 20 20 20 20 20 20  NTEGER: {.      
10d50 20 20 69 66 28 20 61 62 50 4b 5b 69 5d 20 29 7b    if( abPK[i] ){
10d60 0a 20 20 20 20 20 20 20 20 20 20 69 36 34 20 69  .          i64 i
10d70 56 61 6c 20 3d 20 73 65 73 73 69 6f 6e 47 65 74  Val = sessionGet
10d80 49 36 34 28 61 29 3b 0a 20 20 20 20 20 20 20 20  I64(a);.        
10d90 20 20 72 63 20 3d 20 73 71 6c 69 74 65 33 5f 62    rc = sqlite3_b
10da0 69 6e 64 5f 69 6e 74 36 34 28 70 53 65 6c 65 63  ind_int64(pSelec
10db0 74 2c 20 69 2b 31 2c 20 69 56 61 6c 29 3b 0a 20  t, i+1, iVal);. 
10dc0 20 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 20         }.       
10dd0 20 61 20 2b 3d 20 38 3b 0a 20 20 20 20 20 20 20   a += 8;.       
10de0 20 62 72 65 61 6b 3b 0a 20 20 20 20 20 20 7d 0a   break;.      }.
10df0 0a 20 20 20 20 20 20 63 61 73 65 20 53 51 4c 49  .      case SQLI
10e00 54 45 5f 46 4c 4f 41 54 3a 20 7b 0a 20 20 20 20  TE_FLOAT: {.    
10e10 20 20 20 20 69 66 28 20 61 62 50 4b 5b 69 5d 20      if( abPK[i] 
10e20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 64 6f 75  ){.          dou
10e30 62 6c 65 20 72 56 61 6c 3b 0a 20 20 20 20 20 20  ble rVal;.      
10e40 20 20 20 20 69 36 34 20 69 56 61 6c 20 3d 20 73      i64 iVal = s
10e50 65 73 73 69 6f 6e 47 65 74 49 36 34 28 61 29 3b  essionGetI64(a);
10e60 0a 20 20 20 20 20 20 20 20 20 20 6d 65 6d 63 70  .          memcp
10e70 79 28 26 72 56 61 6c 2c 20 26 69 56 61 6c 2c 20  y(&rVal, &iVal, 
10e80 38 29 3b 0a 20 20 20 20 20 20 20 20 20 20 72 63  8);.          rc
10e90 20 3d 20 73 71 6c 69 74 65 33 5f 62 69 6e 64 5f   = sqlite3_bind_
10ea0 64 6f 75 62 6c 65 28 70 53 65 6c 65 63 74 2c 20  double(pSelect, 
10eb0 69 2b 31 2c 20 72 56 61 6c 29 3b 0a 20 20 20 20  i+1, rVal);.    
10ec0 20 20 20 20 7d 0a 20 20 20 20 20 20 20 20 61 20      }.        a 
10ed0 2b 3d 20 38 3b 0a 20 20 20 20 20 20 20 20 62 72  += 8;.        br
10ee0 65 61 6b 3b 0a 20 20 20 20 20 20 7d 0a 0a 20 20  eak;.      }..  
10ef0 20 20 20 20 63 61 73 65 20 53 51 4c 49 54 45 5f      case SQLITE_
10f00 54 45 58 54 3a 20 7b 0a 20 20 20 20 20 20 20 20  TEXT: {.        
10f10 69 6e 74 20 6e 3b 0a 20 20 20 20 20 20 20 20 61  int n;.        a
10f20 20 2b 3d 20 73 65 73 73 69 6f 6e 56 61 72 69 6e   += sessionVarin
10f30 74 47 65 74 28 61 2c 20 26 6e 29 3b 0a 20 20 20  tGet(a, &n);.   
10f40 20 20 20 20 20 69 66 28 20 61 62 50 4b 5b 69 5d       if( abPK[i]
10f50 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 72 63   ){.          rc
10f60 20 3d 20 73 71 6c 69 74 65 33 5f 62 69 6e 64 5f   = sqlite3_bind_
10f70 74 65 78 74 28 70 53 65 6c 65 63 74 2c 20 69 2b  text(pSelect, i+
10f80 31 2c 20 28 63 68 61 72 20 2a 29 61 2c 20 6e 2c  1, (char *)a, n,
10f90 20 53 51 4c 49 54 45 5f 54 52 41 4e 53 49 45 4e   SQLITE_TRANSIEN
10fa0 54 29 3b 0a 20 20 20 20 20 20 20 20 7d 0a 20 20  T);.        }.  
10fb0 20 20 20 20 20 20 61 20 2b 3d 20 6e 3b 0a 20 20        a += n;.  
10fc0 20 20 20 20 20 20 62 72 65 61 6b 3b 0a 20 20 20        break;.   
10fd0 20 20 20 7d 0a 0a 20 20 20 20 20 20 64 65 66 61     }..      defa
10fe0 75 6c 74 3a 20 7b 0a 20 20 20 20 20 20 20 20 69  ult: {.        i
10ff0 6e 74 20 6e 3b 0a 20 20 20 20 20 20 20 20 61 73  nt n;.        as
11000 73 65 72 74 28 20 65 54 79 70 65 3d 3d 53 51 4c  sert( eType==SQL
11010 49 54 45 5f 42 4c 4f 42 20 29 3b 0a 20 20 20 20  ITE_BLOB );.    
11020 20 20 20 20 61 20 2b 3d 20 73 65 73 73 69 6f 6e      a += session
11030 56 61 72 69 6e 74 47 65 74 28 61 2c 20 26 6e 29  VarintGet(a, &n)
11040 3b 0a 20 20 20 20 20 20 20 20 69 66 28 20 61 62  ;.        if( ab
11050 50 4b 5b 69 5d 20 29 7b 0a 20 20 20 20 20 20 20  PK[i] ){.       
11060 20 20 20 72 63 20 3d 20 73 71 6c 69 74 65 33 5f     rc = sqlite3_
11070 62 69 6e 64 5f 62 6c 6f 62 28 70 53 65 6c 65 63  bind_blob(pSelec
11080 74 2c 20 69 2b 31 2c 20 61 2c 20 6e 2c 20 53 51  t, i+1, a, n, SQ
11090 4c 49 54 45 5f 54 52 41 4e 53 49 45 4e 54 29 3b  LITE_TRANSIENT);
110a0 0a 20 20 20 20 20 20 20 20 7d 0a 20 20 20 20 20  .        }.     
110b0 20 20 20 61 20 2b 3d 20 6e 3b 0a 20 20 20 20 20     a += n;.     
110c0 20 20 20 62 72 65 61 6b 3b 0a 20 20 20 20 20 20     break;.      
110d0 7d 0a 20 20 20 20 7d 0a 20 20 7d 0a 0a 20 20 72  }.    }.  }..  r
110e0 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a  eturn rc;.}../*.
110f0 2a 2a 20 54 68 69 73 20 66 75 6e 63 74 69 6f 6e  ** This function
11100 20 69 73 20 61 20 6e 6f 2d 6f 70 20 69 66 20 2a   is a no-op if *
11110 70 52 63 20 69 73 20 73 65 74 20 74 6f 20 6f 74  pRc is set to ot
11120 68 65 72 20 74 68 61 6e 20 53 51 4c 49 54 45 5f  her than SQLITE_
11130 4f 4b 20 77 68 65 6e 20 69 74 0a 2a 2a 20 69 73  OK when it.** is
11140 20 63 61 6c 6c 65 64 2e 20 4f 74 68 65 72 77 69   called. Otherwi
11150 73 65 2c 20 61 70 70 65 6e 64 20 61 20 73 65 72  se, append a ser
11160 69 61 6c 69 7a 65 64 20 74 61 62 6c 65 20 68 65  ialized table he
11170 61 64 65 72 20 28 70 61 72 74 20 6f 66 20 74 68  ader (part of th
11180 65 20 62 69 6e 61 72 79 20 0a 2a 2a 20 63 68 61  e binary .** cha
11190 6e 67 65 73 65 74 20 66 6f 72 6d 61 74 29 20 74  ngeset format) t
111a0 6f 20 62 75 66 66 65 72 20 2a 70 42 75 66 2e 20  o buffer *pBuf. 
111b0 49 66 20 61 6e 20 65 72 72 6f 72 20 6f 63 63 75  If an error occu
111c0 72 73 2c 20 73 65 74 20 2a 70 52 63 20 74 6f 20  rs, set *pRc to 
111d0 61 6e 0a 2a 2a 20 53 51 4c 69 74 65 20 65 72 72  an.** SQLite err
111e0 6f 72 20 63 6f 64 65 20 62 65 66 6f 72 65 20 72  or code before r
111f0 65 74 75 72 6e 69 6e 67 2e 0a 2a 2f 0a 73 74 61  eturning..*/.sta
11200 74 69 63 20 76 6f 69 64 20 73 65 73 73 69 6f 6e  tic void session
11210 41 70 70 65 6e 64 54 61 62 6c 65 48 64 72 28 0a  AppendTableHdr(.
11220 20 20 53 65 73 73 69 6f 6e 42 75 66 66 65 72 20    SessionBuffer 
11230 2a 70 42 75 66 2c 20 20 20 20 20 20 20 20 20 20  *pBuf,          
11240 20 20 2f 2a 20 41 70 70 65 6e 64 20 68 65 61 64    /* Append head
11250 65 72 20 74 6f 20 74 68 69 73 20 62 75 66 66 65  er to this buffe
11260 72 20 2a 2f 0a 20 20 69 6e 74 20 62 50 61 74 63  r */.  int bPatc
11270 68 73 65 74 2c 20 20 20 20 20 20 20 20 20 20 20  hset,           
11280 20 20 20 20 20 20 20 2f 2a 20 55 73 65 20 74 68         /* Use th
11290 65 20 70 61 74 63 68 73 65 74 20 66 6f 72 6d 61  e patchset forma
112a0 74 20 69 66 20 74 72 75 65 20 2a 2f 0a 20 20 53  t if true */.  S
112b0 65 73 73 69 6f 6e 54 61 62 6c 65 20 2a 70 54 61  essionTable *pTa
112c0 62 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 2f  b,             /
112d0 2a 20 54 61 62 6c 65 20 6f 62 6a 65 63 74 20 74  * Table object t
112e0 6f 20 61 70 70 65 6e 64 20 68 65 61 64 65 72 20  o append header 
112f0 66 6f 72 20 2a 2f 0a 20 20 69 6e 74 20 2a 70 52  for */.  int *pR
11300 63 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  c               
11310 20 20 20 20 20 20 20 20 20 2f 2a 20 49 4e 2f 4f           /* IN/O
11320 55 54 3a 20 45 72 72 6f 72 20 63 6f 64 65 20 2a  UT: Error code *
11330 2f 0a 29 7b 0a 20 20 2f 2a 20 57 72 69 74 65 20  /.){.  /* Write 
11340 61 20 74 61 62 6c 65 20 68 65 61 64 65 72 20 2a  a table header *
11350 2f 0a 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e  /.  sessionAppen
11360 64 42 79 74 65 28 70 42 75 66 2c 20 28 62 50 61  dByte(pBuf, (bPa
11370 74 63 68 73 65 74 20 3f 20 27 50 27 20 3a 20 27  tchset ? 'P' : '
11380 54 27 29 2c 20 70 52 63 29 3b 0a 20 20 73 65 73  T'), pRc);.  ses
11390 73 69 6f 6e 41 70 70 65 6e 64 56 61 72 69 6e 74  sionAppendVarint
113a0 28 70 42 75 66 2c 20 70 54 61 62 2d 3e 6e 43 6f  (pBuf, pTab->nCo
113b0 6c 2c 20 70 52 63 29 3b 0a 20 20 73 65 73 73 69  l, pRc);.  sessi
113c0 6f 6e 41 70 70 65 6e 64 42 6c 6f 62 28 70 42 75  onAppendBlob(pBu
113d0 66 2c 20 70 54 61 62 2d 3e 61 62 50 4b 2c 20 70  f, pTab->abPK, p
113e0 54 61 62 2d 3e 6e 43 6f 6c 2c 20 70 52 63 29 3b  Tab->nCol, pRc);
113f0 0a 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64  .  sessionAppend
11400 42 6c 6f 62 28 70 42 75 66 2c 20 28 75 38 20 2a  Blob(pBuf, (u8 *
11410 29 70 54 61 62 2d 3e 7a 4e 61 6d 65 2c 20 28 69  )pTab->zName, (i
11420 6e 74 29 73 74 72 6c 65 6e 28 70 54 61 62 2d 3e  nt)strlen(pTab->
11430 7a 4e 61 6d 65 29 2b 31 2c 20 70 52 63 29 3b 0a  zName)+1, pRc);.
11440 7d 0a 0a 2f 2a 0a 2a 2a 20 47 65 6e 65 72 61 74  }../*.** Generat
11450 65 20 65 69 74 68 65 72 20 61 20 63 68 61 6e 67  e either a chang
11460 65 73 65 74 20 28 69 66 20 61 72 67 75 6d 65 6e  eset (if argumen
11470 74 20 62 50 61 74 63 68 73 65 74 20 69 73 20 7a  t bPatchset is z
11480 65 72 6f 29 20 6f 72 20 61 20 70 61 74 63 68 73  ero) or a patchs
11490 65 74 0a 2a 2a 20 28 69 66 20 69 74 20 69 73 20  et.** (if it is 
114a0 6e 6f 6e 2d 7a 65 72 6f 29 20 62 61 73 65 64 20  non-zero) based 
114b0 6f 6e 20 74 68 65 20 63 75 72 72 65 6e 74 20 63  on the current c
114c0 6f 6e 74 65 6e 74 73 20 6f 66 20 74 68 65 20 73  ontents of the s
114d0 65 73 73 69 6f 6e 20 6f 62 6a 65 63 74 0a 2a 2a  ession object.**
114e0 20 70 61 73 73 65 64 20 61 73 20 74 68 65 20 66   passed as the f
114f0 69 72 73 74 20 61 72 67 75 6d 65 6e 74 2e 0a 2a  irst argument..*
11500 2a 0a 2a 2a 20 49 66 20 6e 6f 20 65 72 72 6f 72  *.** If no error
11510 20 6f 63 63 75 72 73 2c 20 53 51 4c 49 54 45 5f   occurs, SQLITE_
11520 4f 4b 20 69 73 20 72 65 74 75 72 6e 65 64 20 61  OK is returned a
11530 6e 64 20 74 68 65 20 6e 65 77 20 63 68 61 6e 67  nd the new chang
11540 65 73 65 74 2f 70 61 74 63 68 73 65 74 0a 2a 2a  eset/patchset.**
11550 20 73 74 6f 72 65 64 20 69 6e 20 6f 75 74 70 75   stored in outpu
11560 74 20 76 61 72 69 61 62 6c 65 73 20 2a 70 6e 43  t variables *pnC
11570 68 61 6e 67 65 73 65 74 20 61 6e 64 20 2a 70 70  hangeset and *pp
11580 43 68 61 6e 67 65 73 65 74 2e 20 4f 72 2c 20 69  Changeset. Or, i
11590 66 20 61 6e 20 65 72 72 6f 72 0a 2a 2a 20 6f 63  f an error.** oc
115a0 63 75 72 73 2c 20 61 6e 20 53 51 4c 69 74 65 20  curs, an SQLite 
115b0 65 72 72 6f 72 20 63 6f 64 65 20 69 73 20 72 65  error code is re
115c0 74 75 72 6e 65 64 20 61 6e 64 20 62 6f 74 68 20  turned and both 
115d0 6f 75 74 70 75 74 20 76 61 72 69 61 62 6c 65 73  output variables
115e0 20 73 65 74 20 0a 2a 2a 20 74 6f 20 30 2e 0a 2a   set .** to 0..*
115f0 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73  /.static int ses
11600 73 69 6f 6e 47 65 6e 65 72 61 74 65 43 68 61 6e  sionGenerateChan
11610 67 65 73 65 74 28 0a 20 20 73 71 6c 69 74 65 33  geset(.  sqlite3
11620 5f 73 65 73 73 69 6f 6e 20 2a 70 53 65 73 73 69  _session *pSessi
11630 6f 6e 2c 20 20 20 20 20 20 2f 2a 20 53 65 73 73  on,      /* Sess
11640 69 6f 6e 20 6f 62 6a 65 63 74 20 2a 2f 0a 20 20  ion object */.  
11650 69 6e 74 20 62 50 61 74 63 68 73 65 74 2c 20 20  int bPatchset,  
11660 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
11670 2f 2a 20 54 72 75 65 20 66 6f 72 20 70 61 74 63  /* True for patc
11680 68 73 65 74 2c 20 66 61 6c 73 65 20 66 6f 72 20  hset, false for 
11690 63 68 61 6e 67 65 73 65 74 20 2a 2f 0a 20 20 69  changeset */.  i
116a0 6e 74 20 28 2a 78 4f 75 74 70 75 74 29 28 76 6f  nt (*xOutput)(vo
116b0 69 64 20 2a 70 4f 75 74 2c 20 63 6f 6e 73 74 20  id *pOut, const 
116c0 76 6f 69 64 20 2a 70 44 61 74 61 2c 20 69 6e 74  void *pData, int
116d0 20 6e 44 61 74 61 29 2c 0a 20 20 76 6f 69 64 20   nData),.  void 
116e0 2a 70 4f 75 74 2c 20 20 20 20 20 20 20 20 20 20  *pOut,          
116f0 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 46 69             /* Fi
11700 72 73 74 20 61 72 67 75 6d 65 6e 74 20 66 6f 72  rst argument for
11710 20 78 4f 75 74 70 75 74 20 2a 2f 0a 20 20 69 6e   xOutput */.  in
11720 74 20 2a 70 6e 43 68 61 6e 67 65 73 65 74 2c 20  t *pnChangeset, 
11730 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
11740 20 4f 55 54 3a 20 53 69 7a 65 20 6f 66 20 62 75   OUT: Size of bu
11750 66 66 65 72 20 61 74 20 2a 70 70 43 68 61 6e 67  ffer at *ppChang
11760 65 73 65 74 20 2a 2f 0a 20 20 76 6f 69 64 20 2a  eset */.  void *
11770 2a 70 70 43 68 61 6e 67 65 73 65 74 20 20 20 20  *ppChangeset    
11780 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4f 55 54            /* OUT
11790 3a 20 42 75 66 66 65 72 20 63 6f 6e 74 61 69 6e  : Buffer contain
117a0 69 6e 67 20 63 68 61 6e 67 65 73 65 74 20 2a 2f  ing changeset */
117b0 0a 29 7b 0a 20 20 73 71 6c 69 74 65 33 20 2a 64  .){.  sqlite3 *d
117c0 62 20 3d 20 70 53 65 73 73 69 6f 6e 2d 3e 64 62  b = pSession->db
117d0 3b 20 20 20 20 20 2f 2a 20 53 6f 75 72 63 65 20  ;     /* Source 
117e0 64 61 74 61 62 61 73 65 20 68 61 6e 64 6c 65 20  database handle 
117f0 2a 2f 0a 20 20 53 65 73 73 69 6f 6e 54 61 62 6c  */.  SessionTabl
11800 65 20 2a 70 54 61 62 3b 20 20 20 20 20 20 20 20  e *pTab;        
11810 20 20 20 20 20 2f 2a 20 55 73 65 64 20 74 6f 20       /* Used to 
11820 69 74 65 72 61 74 65 20 74 68 72 6f 75 67 68 20  iterate through 
11830 61 74 74 61 63 68 65 64 20 74 61 62 6c 65 73 20  attached tables 
11840 2a 2f 0a 20 20 53 65 73 73 69 6f 6e 42 75 66 66  */.  SessionBuff
11850 65 72 20 62 75 66 20 3d 20 7b 30 2c 30 2c 30 7d  er buf = {0,0,0}
11860 3b 20 20 20 20 2f 2a 20 42 75 66 66 65 72 20 69  ;    /* Buffer i
11870 6e 20 77 68 69 63 68 20 74 6f 20 61 63 63 75 6d  n which to accum
11880 6c 61 74 65 20 63 68 61 6e 67 65 73 65 74 20 2a  late changeset *
11890 2f 0a 20 20 69 6e 74 20 72 63 3b 20 20 20 20 20  /.  int rc;     
118a0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
118b0 20 20 20 20 2f 2a 20 52 65 74 75 72 6e 20 63 6f      /* Return co
118c0 64 65 20 2a 2f 0a 0a 20 20 61 73 73 65 72 74 28  de */..  assert(
118d0 20 78 4f 75 74 70 75 74 3d 3d 30 20 7c 7c 20 28   xOutput==0 || (
118e0 70 6e 43 68 61 6e 67 65 73 65 74 3d 3d 30 20 26  pnChangeset==0 &
118f0 26 20 70 70 43 68 61 6e 67 65 73 65 74 3d 3d 30  & ppChangeset==0
11900 20 29 20 29 3b 0a 0a 20 20 2f 2a 20 5a 65 72 6f   ) );..  /* Zero
11910 20 74 68 65 20 6f 75 74 70 75 74 20 76 61 72 69   the output vari
11920 61 62 6c 65 73 20 69 6e 20 63 61 73 65 20 61 6e  ables in case an
11930 20 65 72 72 6f 72 20 6f 63 63 75 72 73 2e 20 49   error occurs. I
11940 66 20 74 68 69 73 20 73 65 73 73 69 6f 6e 0a 20  f this session. 
11950 20 2a 2a 20 6f 62 6a 65 63 74 20 69 73 20 61 6c   ** object is al
11960 72 65 61 64 79 20 69 6e 20 74 68 65 20 65 72 72  ready in the err
11970 6f 72 20 73 74 61 74 65 20 28 73 71 6c 69 74 65  or state (sqlite
11980 33 5f 73 65 73 73 69 6f 6e 2e 72 63 20 21 3d 20  3_session.rc != 
11990 53 51 4c 49 54 45 5f 4f 4b 29 2c 0a 20 20 2a 2a  SQLITE_OK),.  **
119a0 20 74 68 69 73 20 63 61 6c 6c 20 77 69 6c 6c 20   this call will 
119b0 62 65 20 61 20 6e 6f 2d 6f 70 2e 20 20 2a 2f 0a  be a no-op.  */.
119c0 20 20 69 66 28 20 78 4f 75 74 70 75 74 3d 3d 30    if( xOutput==0
119d0 20 29 7b 0a 20 20 20 20 2a 70 6e 43 68 61 6e 67   ){.    *pnChang
119e0 65 73 65 74 20 3d 20 30 3b 0a 20 20 20 20 2a 70  eset = 0;.    *p
119f0 70 43 68 61 6e 67 65 73 65 74 20 3d 20 30 3b 0a  pChangeset = 0;.
11a00 20 20 7d 0a 0a 20 20 69 66 28 20 70 53 65 73 73    }..  if( pSess
11a10 69 6f 6e 2d 3e 72 63 20 29 20 72 65 74 75 72 6e  ion->rc ) return
11a20 20 70 53 65 73 73 69 6f 6e 2d 3e 72 63 3b 0a 20   pSession->rc;. 
11a30 20 72 63 20 3d 20 73 71 6c 69 74 65 33 5f 65 78   rc = sqlite3_ex
11a40 65 63 28 70 53 65 73 73 69 6f 6e 2d 3e 64 62 2c  ec(pSession->db,
11a50 20 22 53 41 56 45 50 4f 49 4e 54 20 63 68 61 6e   "SAVEPOINT chan
11a60 67 65 73 65 74 22 2c 20 30 2c 20 30 2c 20 30 29  geset", 0, 0, 0)
11a70 3b 0a 20 20 69 66 28 20 72 63 21 3d 53 51 4c 49  ;.  if( rc!=SQLI
11a80 54 45 5f 4f 4b 20 29 20 72 65 74 75 72 6e 20 72  TE_OK ) return r
11a90 63 3b 0a 0a 20 20 73 71 6c 69 74 65 33 5f 6d 75  c;..  sqlite3_mu
11aa0 74 65 78 5f 65 6e 74 65 72 28 73 71 6c 69 74 65  tex_enter(sqlite
11ab0 33 5f 64 62 5f 6d 75 74 65 78 28 64 62 29 29 3b  3_db_mutex(db));
11ac0 0a 0a 20 20 66 6f 72 28 70 54 61 62 3d 70 53 65  ..  for(pTab=pSe
11ad0 73 73 69 6f 6e 2d 3e 70 54 61 62 6c 65 3b 20 72  ssion->pTable; r
11ae0 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 26 26 20  c==SQLITE_OK && 
11af0 70 54 61 62 3b 20 70 54 61 62 3d 70 54 61 62 2d  pTab; pTab=pTab-
11b00 3e 70 4e 65 78 74 29 7b 0a 20 20 20 20 69 66 28  >pNext){.    if(
11b10 20 70 54 61 62 2d 3e 6e 45 6e 74 72 79 20 29 7b   pTab->nEntry ){
11b20 0a 20 20 20 20 20 20 63 6f 6e 73 74 20 63 68 61  .      const cha
11b30 72 20 2a 7a 4e 61 6d 65 20 3d 20 70 54 61 62 2d  r *zName = pTab-
11b40 3e 7a 4e 61 6d 65 3b 0a 20 20 20 20 20 20 69 6e  >zName;.      in
11b50 74 20 6e 43 6f 6c 3b 20 20 20 20 20 20 20 20 20  t nCol;         
11b60 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4e 75 6d            /* Num
11b70 62 65 72 20 6f 66 20 63 6f 6c 75 6d 6e 73 20 69  ber of columns i
11b80 6e 20 74 61 62 6c 65 20 2a 2f 0a 20 20 20 20 20  n table */.     
11b90 20 75 38 20 2a 61 62 50 4b 3b 20 20 20 20 20 20   u8 *abPK;      
11ba0 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
11bb0 50 72 69 6d 61 72 79 20 6b 65 79 20 61 72 72 61  Primary key arra
11bc0 79 20 2a 2f 0a 20 20 20 20 20 20 63 6f 6e 73 74  y */.      const
11bd0 20 63 68 61 72 20 2a 2a 61 7a 43 6f 6c 20 3d 20   char **azCol = 
11be0 30 3b 20 20 20 20 20 2f 2a 20 54 61 62 6c 65 20  0;     /* Table 
11bf0 63 6f 6c 75 6d 6e 73 20 2a 2f 0a 20 20 20 20 20  columns */.     
11c00 20 69 6e 74 20 69 3b 20 20 20 20 20 20 20 20 20   int i;         
11c10 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
11c20 55 73 65 64 20 74 6f 20 69 74 65 72 61 74 65 20  Used to iterate 
11c30 74 68 72 6f 75 67 68 20 68 61 73 68 20 62 75 63  through hash buc
11c40 6b 65 74 73 20 2a 2f 0a 20 20 20 20 20 20 73 71  kets */.      sq
11c50 6c 69 74 65 33 5f 73 74 6d 74 20 2a 70 53 65 6c  lite3_stmt *pSel
11c60 20 3d 20 30 3b 20 20 20 20 20 2f 2a 20 53 45 4c   = 0;     /* SEL
11c70 45 43 54 20 73 74 61 74 65 6d 65 6e 74 20 74 6f  ECT statement to
11c80 20 71 75 65 72 79 20 74 61 62 6c 65 20 70 54 61   query table pTa
11c90 62 20 2a 2f 0a 20 20 20 20 20 20 69 6e 74 20 6e  b */.      int n
11ca0 52 65 77 69 6e 64 20 3d 20 62 75 66 2e 6e 42 75  Rewind = buf.nBu
11cb0 66 3b 20 20 20 20 20 2f 2a 20 49 6e 69 74 69 61  f;     /* Initia
11cc0 6c 20 73 69 7a 65 20 6f 66 20 77 72 69 74 65 20  l size of write 
11cd0 62 75 66 66 65 72 20 2a 2f 0a 20 20 20 20 20 20  buffer */.      
11ce0 69 6e 74 20 6e 4e 6f 6f 70 3b 20 20 20 20 20 20  int nNoop;      
11cf0 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 53              /* S
11d00 69 7a 65 20 6f 66 20 62 75 66 66 65 72 20 61 66  ize of buffer af
11d10 74 65 72 20 77 72 69 74 69 6e 67 20 74 62 6c 20  ter writing tbl 
11d20 68 65 61 64 65 72 20 2a 2f 0a 0a 20 20 20 20 20  header */..     
11d30 20 2f 2a 20 43 68 65 63 6b 20 74 68 65 20 74 61   /* Check the ta
11d40 62 6c 65 20 73 63 68 65 6d 61 20 69 73 20 73 74  ble schema is st
11d50 69 6c 6c 20 4f 6b 2e 20 2a 2f 0a 20 20 20 20 20  ill Ok. */.     
11d60 20 72 63 20 3d 20 73 65 73 73 69 6f 6e 54 61 62   rc = sessionTab
11d70 6c 65 49 6e 66 6f 28 64 62 2c 20 70 53 65 73 73  leInfo(db, pSess
11d80 69 6f 6e 2d 3e 7a 44 62 2c 20 7a 4e 61 6d 65 2c  ion->zDb, zName,
11d90 20 26 6e 43 6f 6c 2c 20 30 2c 20 26 61 7a 43 6f   &nCol, 0, &azCo
11da0 6c 2c 20 26 61 62 50 4b 29 3b 0a 20 20 20 20 20  l, &abPK);.     
11db0 20 69 66 28 20 21 72 63 20 26 26 20 28 70 54 61   if( !rc && (pTa
11dc0 62 2d 3e 6e 43 6f 6c 21 3d 6e 43 6f 6c 20 7c 7c  b->nCol!=nCol ||
11dd0 20 6d 65 6d 63 6d 70 28 61 62 50 4b 2c 20 70 54   memcmp(abPK, pT
11de0 61 62 2d 3e 61 62 50 4b 2c 20 6e 43 6f 6c 29 29  ab->abPK, nCol))
11df0 20 29 7b 0a 20 20 20 20 20 20 20 20 72 63 20 3d   ){.        rc =
11e00 20 53 51 4c 49 54 45 5f 53 43 48 45 4d 41 3b 0a   SQLITE_SCHEMA;.
11e10 20 20 20 20 20 20 7d 0a 0a 20 20 20 20 20 20 2f        }..      /
11e20 2a 20 57 72 69 74 65 20 61 20 74 61 62 6c 65 20  * Write a table 
11e30 68 65 61 64 65 72 20 2a 2f 0a 20 20 20 20 20 20  header */.      
11e40 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 54 61 62  sessionAppendTab
11e50 6c 65 48 64 72 28 26 62 75 66 2c 20 62 50 61 74  leHdr(&buf, bPat
11e60 63 68 73 65 74 2c 20 70 54 61 62 2c 20 26 72 63  chset, pTab, &rc
11e70 29 3b 0a 0a 20 20 20 20 20 20 2f 2a 20 42 75 69  );..      /* Bui
11e80 6c 64 20 61 6e 64 20 63 6f 6d 70 69 6c 65 20 61  ld and compile a
11e90 20 73 74 61 74 65 6d 65 6e 74 20 74 6f 20 65 78   statement to ex
11ea0 65 63 75 74 65 3a 20 2a 2f 0a 20 20 20 20 20 20  ecute: */.      
11eb0 69 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f  if( rc==SQLITE_O
11ec0 4b 20 29 7b 0a 20 20 20 20 20 20 20 20 72 63 20  K ){.        rc 
11ed0 3d 20 73 65 73 73 69 6f 6e 53 65 6c 65 63 74 53  = sessionSelectS
11ee0 74 6d 74 28 0a 20 20 20 20 20 20 20 20 20 20 20  tmt(.           
11ef0 20 64 62 2c 20 70 53 65 73 73 69 6f 6e 2d 3e 7a   db, pSession->z
11f00 44 62 2c 20 7a 4e 61 6d 65 2c 20 6e 43 6f 6c 2c  Db, zName, nCol,
11f10 20 61 7a 43 6f 6c 2c 20 61 62 50 4b 2c 20 26 70   azCol, abPK, &p
11f20 53 65 6c 29 3b 0a 20 20 20 20 20 20 7d 0a 0a 20  Sel);.      }.. 
11f30 20 20 20 20 20 6e 4e 6f 6f 70 20 3d 20 62 75 66       nNoop = buf
11f40 2e 6e 42 75 66 3b 0a 20 20 20 20 20 20 66 6f 72  .nBuf;.      for
11f50 28 69 3d 30 3b 20 69 3c 70 54 61 62 2d 3e 6e 43  (i=0; i<pTab->nC
11f60 68 61 6e 67 65 20 26 26 20 72 63 3d 3d 53 51 4c  hange && rc==SQL
11f70 49 54 45 5f 4f 4b 3b 20 69 2b 2b 29 7b 0a 20 20  ITE_OK; i++){.  
11f80 20 20 20 20 20 20 53 65 73 73 69 6f 6e 43 68 61        SessionCha
11f90 6e 67 65 20 2a 70 3b 20 20 20 20 20 20 20 20 20  nge *p;         
11fa0 2f 2a 20 55 73 65 64 20 74 6f 20 69 74 65 72 61  /* Used to itera
11fb0 74 65 20 74 68 72 6f 75 67 68 20 63 68 61 6e 67  te through chang
11fc0 65 73 20 2a 2f 0a 0a 20 20 20 20 20 20 20 20 66  es */..        f
11fd0 6f 72 28 70 3d 70 54 61 62 2d 3e 61 70 43 68 61  or(p=pTab->apCha
11fe0 6e 67 65 5b 69 5d 3b 20 72 63 3d 3d 53 51 4c 49  nge[i]; rc==SQLI
11ff0 54 45 5f 4f 4b 20 26 26 20 70 3b 20 70 3d 70 2d  TE_OK && p; p=p-
12000 3e 70 4e 65 78 74 29 7b 0a 20 20 20 20 20 20 20  >pNext){.       
12010 20 20 20 72 63 20 3d 20 73 65 73 73 69 6f 6e 53     rc = sessionS
12020 65 6c 65 63 74 42 69 6e 64 28 70 53 65 6c 2c 20  electBind(pSel, 
12030 6e 43 6f 6c 2c 20 61 62 50 4b 2c 20 70 29 3b 0a  nCol, abPK, p);.
12040 20 20 20 20 20 20 20 20 20 20 69 66 28 20 72 63            if( rc
12050 21 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 20 63 6f  !=SQLITE_OK ) co
12060 6e 74 69 6e 75 65 3b 0a 20 20 20 20 20 20 20 20  ntinue;.        
12070 20 20 69 66 28 20 73 71 6c 69 74 65 33 5f 73 74    if( sqlite3_st
12080 65 70 28 70 53 65 6c 29 3d 3d 53 51 4c 49 54 45  ep(pSel)==SQLITE
12090 5f 52 4f 57 20 29 7b 0a 20 20 20 20 20 20 20 20  _ROW ){.        
120a0 20 20 20 20 69 66 28 20 70 2d 3e 6f 70 3d 3d 53      if( p->op==S
120b0 51 4c 49 54 45 5f 49 4e 53 45 52 54 20 29 7b 0a  QLITE_INSERT ){.
120c0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 69 6e                in
120d0 74 20 69 43 6f 6c 3b 0a 20 20 20 20 20 20 20 20  t iCol;.        
120e0 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70 70        sessionApp
120f0 65 6e 64 42 79 74 65 28 26 62 75 66 2c 20 53 51  endByte(&buf, SQ
12100 4c 49 54 45 5f 49 4e 53 45 52 54 2c 20 26 72 63  LITE_INSERT, &rc
12110 29 3b 0a 20 20 20 20 20 20 20 20 20 20 20 20 20  );.             
12120 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 42 79   sessionAppendBy
12130 74 65 28 26 62 75 66 2c 20 70 2d 3e 62 49 6e 64  te(&buf, p->bInd
12140 69 72 65 63 74 2c 20 26 72 63 29 3b 0a 20 20 20  irect, &rc);.   
12150 20 20 20 20 20 20 20 20 20 20 20 66 6f 72 28 69             for(i
12160 43 6f 6c 3d 30 3b 20 69 43 6f 6c 3c 6e 43 6f 6c  Col=0; iCol<nCol
12170 3b 20 69 43 6f 6c 2b 2b 29 7b 0a 20 20 20 20 20  ; iCol++){.     
12180 20 20 20 20 20 20 20 20 20 20 20 73 65 73 73 69             sessi
12190 6f 6e 41 70 70 65 6e 64 43 6f 6c 28 26 62 75 66  onAppendCol(&buf
121a0 2c 20 70 53 65 6c 2c 20 69 43 6f 6c 2c 20 26 72  , pSel, iCol, &r
121b0 63 29 3b 0a 20 20 20 20 20 20 20 20 20 20 20 20  c);.            
121c0 20 20 7d 0a 20 20 20 20 20 20 20 20 20 20 20 20    }.            
121d0 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 20 20 20  }else{.         
121e0 20 20 20 20 20 72 63 20 3d 20 73 65 73 73 69 6f       rc = sessio
121f0 6e 41 70 70 65 6e 64 55 70 64 61 74 65 28 26 62  nAppendUpdate(&b
12200 75 66 2c 20 62 50 61 74 63 68 73 65 74 2c 20 70  uf, bPatchset, p
12210 53 65 6c 2c 20 70 2c 20 61 62 50 4b 29 3b 0a 20  Sel, p, abPK);. 
12220 20 20 20 20 20 20 20 20 20 20 20 7d 0a 20 20 20             }.   
12230 20 20 20 20 20 20 20 7d 65 6c 73 65 20 69 66 28         }else if(
12240 20 70 2d 3e 6f 70 21 3d 53 51 4c 49 54 45 5f 49   p->op!=SQLITE_I
12250 4e 53 45 52 54 20 29 7b 0a 20 20 20 20 20 20 20  NSERT ){.       
12260 20 20 20 20 20 72 63 20 3d 20 73 65 73 73 69 6f       rc = sessio
12270 6e 41 70 70 65 6e 64 44 65 6c 65 74 65 28 26 62  nAppendDelete(&b
12280 75 66 2c 20 62 50 61 74 63 68 73 65 74 2c 20 70  uf, bPatchset, p
12290 2c 20 6e 43 6f 6c 2c 20 61 62 50 4b 29 3b 0a 20  , nCol, abPK);. 
122a0 20 20 20 20 20 20 20 20 20 7d 0a 20 20 20 20 20           }.     
122b0 20 20 20 20 20 69 66 28 20 72 63 3d 3d 53 51 4c       if( rc==SQL
122c0 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 20 20  ITE_OK ){.      
122d0 20 20 20 20 20 20 72 63 20 3d 20 73 71 6c 69 74        rc = sqlit
122e0 65 33 5f 72 65 73 65 74 28 70 53 65 6c 29 3b 0a  e3_reset(pSel);.
122f0 20 20 20 20 20 20 20 20 20 20 7d 0a 0a 20 20 20            }..   
12300 20 20 20 20 20 20 20 2f 2a 20 49 66 20 74 68 65         /* If the
12310 20 62 75 66 66 65 72 20 69 73 20 6e 6f 77 20 6c   buffer is now l
12320 61 72 67 65 72 20 74 68 61 6e 20 53 45 53 53 49  arger than SESSI
12330 4f 4e 53 5f 53 54 52 4d 5f 43 48 55 4e 4b 5f 53  ONS_STRM_CHUNK_S
12340 49 5a 45 2c 20 70 61 73 73 0a 20 20 20 20 20 20  IZE, pass.      
12350 20 20 20 20 2a 2a 20 69 74 73 20 63 6f 6e 74 65      ** its conte
12360 6e 74 73 20 74 6f 20 74 68 65 20 78 4f 75 74 70  nts to the xOutp
12370 75 74 28 29 20 63 61 6c 6c 62 61 63 6b 2e 20 2a  ut() callback. *
12380 2f 0a 20 20 20 20 20 20 20 20 20 20 69 66 28 20  /.          if( 
12390 78 4f 75 74 70 75 74 20 0a 20 20 20 20 20 20 20  xOutput .       
123a0 20 20 20 20 26 26 20 72 63 3d 3d 53 51 4c 49 54      && rc==SQLIT
123b0 45 5f 4f 4b 20 0a 20 20 20 20 20 20 20 20 20 20  E_OK .          
123c0 20 26 26 20 62 75 66 2e 6e 42 75 66 3e 6e 4e 6f   && buf.nBuf>nNo
123d0 6f 70 20 0a 20 20 20 20 20 20 20 20 20 20 20 26  op .           &
123e0 26 20 62 75 66 2e 6e 42 75 66 3e 53 45 53 53 49  & buf.nBuf>SESSI
123f0 4f 4e 53 5f 53 54 52 4d 5f 43 48 55 4e 4b 5f 53  ONS_STRM_CHUNK_S
12400 49 5a 45 20 0a 20 20 20 20 20 20 20 20 20 20 29  IZE .          )
12410 7b 0a 20 20 20 20 20 20 20 20 20 20 20 20 72 63  {.            rc
12420 20 3d 20 78 4f 75 74 70 75 74 28 70 4f 75 74 2c   = xOutput(pOut,
12430 20 28 76 6f 69 64 2a 29 62 75 66 2e 61 42 75 66   (void*)buf.aBuf
12440 2c 20 62 75 66 2e 6e 42 75 66 29 3b 0a 20 20 20  , buf.nBuf);.   
12450 20 20 20 20 20 20 20 20 20 6e 4e 6f 6f 70 20 3d           nNoop =
12460 20 2d 31 3b 0a 20 20 20 20 20 20 20 20 20 20 20   -1;.           
12470 20 62 75 66 2e 6e 42 75 66 20 3d 20 30 3b 0a 20   buf.nBuf = 0;. 
12480 20 20 20 20 20 20 20 20 20 7d 0a 0a 20 20 20 20           }..    
12490 20 20 20 20 7d 0a 20 20 20 20 20 20 7d 0a 0a 20      }.      }.. 
124a0 20 20 20 20 20 73 71 6c 69 74 65 33 5f 66 69 6e       sqlite3_fin
124b0 61 6c 69 7a 65 28 70 53 65 6c 29 3b 0a 20 20 20  alize(pSel);.   
124c0 20 20 20 69 66 28 20 62 75 66 2e 6e 42 75 66 3d     if( buf.nBuf=
124d0 3d 6e 4e 6f 6f 70 20 29 7b 0a 20 20 20 20 20 20  =nNoop ){.      
124e0 20 20 62 75 66 2e 6e 42 75 66 20 3d 20 6e 52 65    buf.nBuf = nRe
124f0 77 69 6e 64 3b 0a 20 20 20 20 20 20 7d 0a 20 20  wind;.      }.  
12500 20 20 20 20 73 71 6c 69 74 65 33 5f 66 72 65 65      sqlite3_free
12510 28 28 63 68 61 72 2a 29 61 7a 43 6f 6c 29 3b 20  ((char*)azCol); 
12520 20 2f 2a 20 63 61 73 74 20 77 6f 72 6b 73 20 61   /* cast works a
12530 72 6f 75 6e 64 20 56 43 2b 2b 20 62 75 67 20 2a  round VC++ bug *
12540 2f 0a 20 20 20 20 7d 0a 20 20 7d 0a 0a 20 20 69  /.    }.  }..  i
12550 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b  f( rc==SQLITE_OK
12560 20 29 7b 0a 20 20 20 20 69 66 28 20 78 4f 75 74   ){.    if( xOut
12570 70 75 74 3d 3d 30 20 29 7b 0a 20 20 20 20 20 20  put==0 ){.      
12580 2a 70 6e 43 68 61 6e 67 65 73 65 74 20 3d 20 62  *pnChangeset = b
12590 75 66 2e 6e 42 75 66 3b 0a 20 20 20 20 20 20 2a  uf.nBuf;.      *
125a0 70 70 43 68 61 6e 67 65 73 65 74 20 3d 20 62 75  ppChangeset = bu
125b0 66 2e 61 42 75 66 3b 0a 20 20 20 20 20 20 62 75  f.aBuf;.      bu
125c0 66 2e 61 42 75 66 20 3d 20 30 3b 0a 20 20 20 20  f.aBuf = 0;.    
125d0 7d 65 6c 73 65 20 69 66 28 20 62 75 66 2e 6e 42  }else if( buf.nB
125e0 75 66 3e 30 20 29 7b 0a 20 20 20 20 20 20 72 63  uf>0 ){.      rc
125f0 20 3d 20 78 4f 75 74 70 75 74 28 70 4f 75 74 2c   = xOutput(pOut,
12600 20 28 76 6f 69 64 2a 29 62 75 66 2e 61 42 75 66   (void*)buf.aBuf
12610 2c 20 62 75 66 2e 6e 42 75 66 29 3b 0a 20 20 20  , buf.nBuf);.   
12620 20 7d 0a 20 20 7d 0a 0a 20 20 73 71 6c 69 74 65   }.  }..  sqlite
12630 33 5f 66 72 65 65 28 62 75 66 2e 61 42 75 66 29  3_free(buf.aBuf)
12640 3b 0a 20 20 73 71 6c 69 74 65 33 5f 65 78 65 63  ;.  sqlite3_exec
12650 28 64 62 2c 20 22 52 45 4c 45 41 53 45 20 63 68  (db, "RELEASE ch
12660 61 6e 67 65 73 65 74 22 2c 20 30 2c 20 30 2c 20  angeset", 0, 0, 
12670 30 29 3b 0a 20 20 73 71 6c 69 74 65 33 5f 6d 75  0);.  sqlite3_mu
12680 74 65 78 5f 6c 65 61 76 65 28 73 71 6c 69 74 65  tex_leave(sqlite
12690 33 5f 64 62 5f 6d 75 74 65 78 28 64 62 29 29 3b  3_db_mutex(db));
126a0 0a 20 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a  .  return rc;.}.
126b0 0a 2f 2a 0a 2a 2a 20 4f 62 74 61 69 6e 20 61 20  ./*.** Obtain a 
126c0 63 68 61 6e 67 65 73 65 74 20 6f 62 6a 65 63 74  changeset object
126d0 20 63 6f 6e 74 61 69 6e 69 6e 67 20 61 6c 6c 20   containing all 
126e0 63 68 61 6e 67 65 73 20 72 65 63 6f 72 64 65 64  changes recorded
126f0 20 62 79 20 74 68 65 20 0a 2a 2a 20 73 65 73 73   by the .** sess
12700 69 6f 6e 20 6f 62 6a 65 63 74 20 70 61 73 73 65  ion object passe
12710 64 20 61 73 20 74 68 65 20 66 69 72 73 74 20 61  d as the first a
12720 72 67 75 6d 65 6e 74 2e 0a 2a 2a 0a 2a 2a 20 49  rgument..**.** I
12730 74 20 69 73 20 74 68 65 20 72 65 73 70 6f 6e 73  t is the respons
12740 69 62 69 6c 69 74 79 20 6f 66 20 74 68 65 20 63  ibility of the c
12750 61 6c 6c 65 72 20 74 6f 20 65 76 65 6e 74 75 61  aller to eventua
12760 6c 6c 79 20 66 72 65 65 20 74 68 65 20 62 75 66  lly free the buf
12770 66 65 72 20 0a 2a 2a 20 75 73 69 6e 67 20 73 71  fer .** using sq
12780 6c 69 74 65 33 5f 66 72 65 65 28 29 2e 0a 2a 2f  lite3_free()..*/
12790 0a 69 6e 74 20 73 71 6c 69 74 65 33 73 65 73 73  .int sqlite3sess
127a0 69 6f 6e 5f 63 68 61 6e 67 65 73 65 74 28 0a 20  ion_changeset(. 
127b0 20 73 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e   sqlite3_session
127c0 20 2a 70 53 65 73 73 69 6f 6e 2c 20 20 20 20 20   *pSession,     
127d0 20 2f 2a 20 53 65 73 73 69 6f 6e 20 6f 62 6a 65   /* Session obje
127e0 63 74 20 2a 2f 0a 20 20 69 6e 74 20 2a 70 6e 43  ct */.  int *pnC
127f0 68 61 6e 67 65 73 65 74 2c 20 20 20 20 20 20 20  hangeset,       
12800 20 20 20 20 20 20 20 20 2f 2a 20 4f 55 54 3a 20          /* OUT: 
12810 53 69 7a 65 20 6f 66 20 62 75 66 66 65 72 20 61  Size of buffer a
12820 74 20 2a 70 70 43 68 61 6e 67 65 73 65 74 20 2a  t *ppChangeset *
12830 2f 0a 20 20 76 6f 69 64 20 2a 2a 70 70 43 68 61  /.  void **ppCha
12840 6e 67 65 73 65 74 20 20 20 20 20 20 20 20 20 20  ngeset          
12850 20 20 20 20 2f 2a 20 4f 55 54 3a 20 42 75 66 66      /* OUT: Buff
12860 65 72 20 63 6f 6e 74 61 69 6e 69 6e 67 20 63 68  er containing ch
12870 61 6e 67 65 73 65 74 20 2a 2f 0a 29 7b 0a 20 20  angeset */.){.  
12880 72 65 74 75 72 6e 20 73 65 73 73 69 6f 6e 47 65  return sessionGe
12890 6e 65 72 61 74 65 43 68 61 6e 67 65 73 65 74 28  nerateChangeset(
128a0 70 53 65 73 73 69 6f 6e 2c 20 30 2c 20 30 2c 20  pSession, 0, 0, 
128b0 30 2c 20 70 6e 43 68 61 6e 67 65 73 65 74 2c 20  0, pnChangeset, 
128c0 70 70 43 68 61 6e 67 65 73 65 74 29 3b 0a 7d 0a  ppChangeset);.}.
128d0 0a 2f 2a 0a 2a 2a 20 53 74 72 65 61 6d 69 6e 67  ./*.** Streaming
128e0 20 76 65 72 73 69 6f 6e 20 6f 66 20 73 71 6c 69   version of sqli
128f0 74 65 33 73 65 73 73 69 6f 6e 5f 63 68 61 6e 67  te3session_chang
12900 65 73 65 74 28 29 2e 0a 2a 2f 0a 69 6e 74 20 73  eset()..*/.int s
12910 71 6c 69 74 65 33 73 65 73 73 69 6f 6e 5f 63 68  qlite3session_ch
12920 61 6e 67 65 73 65 74 5f 73 74 72 6d 28 0a 20 20  angeset_strm(.  
12930 73 71 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20  sqlite3_session 
12940 2a 70 53 65 73 73 69 6f 6e 2c 0a 20 20 69 6e 74  *pSession,.  int
12950 20 28 2a 78 4f 75 74 70 75 74 29 28 76 6f 69 64   (*xOutput)(void
12960 20 2a 70 4f 75 74 2c 20 63 6f 6e 73 74 20 76 6f   *pOut, const vo
12970 69 64 20 2a 70 44 61 74 61 2c 20 69 6e 74 20 6e  id *pData, int n
12980 44 61 74 61 29 2c 0a 20 20 76 6f 69 64 20 2a 70  Data),.  void *p
12990 4f 75 74 0a 29 7b 0a 20 20 72 65 74 75 72 6e 20  Out.){.  return 
129a0 73 65 73 73 69 6f 6e 47 65 6e 65 72 61 74 65 43  sessionGenerateC
129b0 68 61 6e 67 65 73 65 74 28 70 53 65 73 73 69 6f  hangeset(pSessio
129c0 6e 2c 20 30 2c 20 78 4f 75 74 70 75 74 2c 20 70  n, 0, xOutput, p
129d0 4f 75 74 2c 20 30 2c 20 30 29 3b 0a 7d 0a 0a 2f  Out, 0, 0);.}../
129e0 2a 0a 2a 2a 20 53 74 72 65 61 6d 69 6e 67 20 76  *.** Streaming v
129f0 65 72 73 69 6f 6e 20 6f 66 20 73 71 6c 69 74 65  ersion of sqlite
12a00 33 73 65 73 73 69 6f 6e 5f 70 61 74 63 68 73 65  3session_patchse
12a10 74 28 29 2e 0a 2a 2f 0a 69 6e 74 20 73 71 6c 69  t()..*/.int sqli
12a20 74 65 33 73 65 73 73 69 6f 6e 5f 70 61 74 63 68  te3session_patch
12a30 73 65 74 5f 73 74 72 6d 28 0a 20 20 73 71 6c 69  set_strm(.  sqli
12a40 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a 70 53 65  te3_session *pSe
12a50 73 73 69 6f 6e 2c 0a 20 20 69 6e 74 20 28 2a 78  ssion,.  int (*x
12a60 4f 75 74 70 75 74 29 28 76 6f 69 64 20 2a 70 4f  Output)(void *pO
12a70 75 74 2c 20 63 6f 6e 73 74 20 76 6f 69 64 20 2a  ut, const void *
12a80 70 44 61 74 61 2c 20 69 6e 74 20 6e 44 61 74 61  pData, int nData
12a90 29 2c 0a 20 20 76 6f 69 64 20 2a 70 4f 75 74 0a  ),.  void *pOut.
12aa0 29 7b 0a 20 20 72 65 74 75 72 6e 20 73 65 73 73  ){.  return sess
12ab0 69 6f 6e 47 65 6e 65 72 61 74 65 43 68 61 6e 67  ionGenerateChang
12ac0 65 73 65 74 28 70 53 65 73 73 69 6f 6e 2c 20 31  eset(pSession, 1
12ad0 2c 20 78 4f 75 74 70 75 74 2c 20 70 4f 75 74 2c  , xOutput, pOut,
12ae0 20 30 2c 20 30 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a   0, 0);.}../*.**
12af0 20 4f 62 74 61 69 6e 20 61 20 70 61 74 63 68 73   Obtain a patchs
12b00 65 74 20 6f 62 6a 65 63 74 20 63 6f 6e 74 61 69  et object contai
12b10 6e 69 6e 67 20 61 6c 6c 20 63 68 61 6e 67 65 73  ning all changes
12b20 20 72 65 63 6f 72 64 65 64 20 62 79 20 74 68 65   recorded by the
12b30 20 0a 2a 2a 20 73 65 73 73 69 6f 6e 20 6f 62 6a   .** session obj
12b40 65 63 74 20 70 61 73 73 65 64 20 61 73 20 74 68  ect passed as th
12b50 65 20 66 69 72 73 74 20 61 72 67 75 6d 65 6e 74  e first argument
12b60 2e 0a 2a 2a 0a 2a 2a 20 49 74 20 69 73 20 74 68  ..**.** It is th
12b70 65 20 72 65 73 70 6f 6e 73 69 62 69 6c 69 74 79  e responsibility
12b80 20 6f 66 20 74 68 65 20 63 61 6c 6c 65 72 20 74   of the caller t
12b90 6f 20 65 76 65 6e 74 75 61 6c 6c 79 20 66 72 65  o eventually fre
12ba0 65 20 74 68 65 20 62 75 66 66 65 72 20 0a 2a 2a  e the buffer .**
12bb0 20 75 73 69 6e 67 20 73 71 6c 69 74 65 33 5f 66   using sqlite3_f
12bc0 72 65 65 28 29 2e 0a 2a 2f 0a 69 6e 74 20 73 71  ree()..*/.int sq
12bd0 6c 69 74 65 33 73 65 73 73 69 6f 6e 5f 70 61 74  lite3session_pat
12be0 63 68 73 65 74 28 0a 20 20 73 71 6c 69 74 65 33  chset(.  sqlite3
12bf0 5f 73 65 73 73 69 6f 6e 20 2a 70 53 65 73 73 69  _session *pSessi
12c00 6f 6e 2c 20 20 20 20 20 20 2f 2a 20 53 65 73 73  on,      /* Sess
12c10 69 6f 6e 20 6f 62 6a 65 63 74 20 2a 2f 0a 20 20  ion object */.  
12c20 69 6e 74 20 2a 70 6e 50 61 74 63 68 73 65 74 2c  int *pnPatchset,
12c30 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
12c40 2f 2a 20 4f 55 54 3a 20 53 69 7a 65 20 6f 66 20  /* OUT: Size of 
12c50 62 75 66 66 65 72 20 61 74 20 2a 70 70 43 68 61  buffer at *ppCha
12c60 6e 67 65 73 65 74 20 2a 2f 0a 20 20 76 6f 69 64  ngeset */.  void
12c70 20 2a 2a 70 70 50 61 74 63 68 73 65 74 20 20 20   **ppPatchset   
12c80 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4f              /* O
12c90 55 54 3a 20 42 75 66 66 65 72 20 63 6f 6e 74 61  UT: Buffer conta
12ca0 69 6e 69 6e 67 20 63 68 61 6e 67 65 73 65 74 20  ining changeset 
12cb0 2a 2f 0a 29 7b 0a 20 20 72 65 74 75 72 6e 20 73  */.){.  return s
12cc0 65 73 73 69 6f 6e 47 65 6e 65 72 61 74 65 43 68  essionGenerateCh
12cd0 61 6e 67 65 73 65 74 28 70 53 65 73 73 69 6f 6e  angeset(pSession
12ce0 2c 20 31 2c 20 30 2c 20 30 2c 20 70 6e 50 61 74  , 1, 0, 0, pnPat
12cf0 63 68 73 65 74 2c 20 70 70 50 61 74 63 68 73 65  chset, ppPatchse
12d00 74 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 45 6e 61  t);.}../*.** Ena
12d10 62 6c 65 20 6f 72 20 64 69 73 61 62 6c 65 20 74  ble or disable t
12d20 68 65 20 73 65 73 73 69 6f 6e 20 6f 62 6a 65 63  he session objec
12d30 74 20 70 61 73 73 65 64 20 61 73 20 74 68 65 20  t passed as the 
12d40 66 69 72 73 74 20 61 72 67 75 6d 65 6e 74 2e 0a  first argument..
12d50 2a 2f 0a 69 6e 74 20 73 71 6c 69 74 65 33 73 65  */.int sqlite3se
12d60 73 73 69 6f 6e 5f 65 6e 61 62 6c 65 28 73 71 6c  ssion_enable(sql
12d70 69 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a 70 53  ite3_session *pS
12d80 65 73 73 69 6f 6e 2c 20 69 6e 74 20 62 45 6e 61  ession, int bEna
12d90 62 6c 65 29 7b 0a 20 20 69 6e 74 20 72 65 74 3b  ble){.  int ret;
12da0 0a 20 20 73 71 6c 69 74 65 33 5f 6d 75 74 65 78  .  sqlite3_mutex
12db0 5f 65 6e 74 65 72 28 73 71 6c 69 74 65 33 5f 64  _enter(sqlite3_d
12dc0 62 5f 6d 75 74 65 78 28 70 53 65 73 73 69 6f 6e  b_mutex(pSession
12dd0 2d 3e 64 62 29 29 3b 0a 20 20 69 66 28 20 62 45  ->db));.  if( bE
12de0 6e 61 62 6c 65 3e 3d 30 20 29 7b 0a 20 20 20 20  nable>=0 ){.    
12df0 70 53 65 73 73 69 6f 6e 2d 3e 62 45 6e 61 62 6c  pSession->bEnabl
12e00 65 20 3d 20 62 45 6e 61 62 6c 65 3b 0a 20 20 7d  e = bEnable;.  }
12e10 0a 20 20 72 65 74 20 3d 20 70 53 65 73 73 69 6f  .  ret = pSessio
12e20 6e 2d 3e 62 45 6e 61 62 6c 65 3b 0a 20 20 73 71  n->bEnable;.  sq
12e30 6c 69 74 65 33 5f 6d 75 74 65 78 5f 6c 65 61 76  lite3_mutex_leav
12e40 65 28 73 71 6c 69 74 65 33 5f 64 62 5f 6d 75 74  e(sqlite3_db_mut
12e50 65 78 28 70 53 65 73 73 69 6f 6e 2d 3e 64 62 29  ex(pSession->db)
12e60 29 3b 0a 20 20 72 65 74 75 72 6e 20 72 65 74 3b  );.  return ret;
12e70 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 45 6e 61 62 6c 65  .}../*.** Enable
12e80 20 6f 72 20 64 69 73 61 62 6c 65 20 74 68 65 20   or disable the 
12e90 73 65 73 73 69 6f 6e 20 6f 62 6a 65 63 74 20 70  session object p
12ea0 61 73 73 65 64 20 61 73 20 74 68 65 20 66 69 72  assed as the fir
12eb0 73 74 20 61 72 67 75 6d 65 6e 74 2e 0a 2a 2f 0a  st argument..*/.
12ec0 69 6e 74 20 73 71 6c 69 74 65 33 73 65 73 73 69  int sqlite3sessi
12ed0 6f 6e 5f 69 6e 64 69 72 65 63 74 28 73 71 6c 69  on_indirect(sqli
12ee0 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a 70 53 65  te3_session *pSe
12ef0 73 73 69 6f 6e 2c 20 69 6e 74 20 62 49 6e 64 69  ssion, int bIndi
12f00 72 65 63 74 29 7b 0a 20 20 69 6e 74 20 72 65 74  rect){.  int ret
12f10 3b 0a 20 20 73 71 6c 69 74 65 33 5f 6d 75 74 65  ;.  sqlite3_mute
12f20 78 5f 65 6e 74 65 72 28 73 71 6c 69 74 65 33 5f  x_enter(sqlite3_
12f30 64 62 5f 6d 75 74 65 78 28 70 53 65 73 73 69 6f  db_mutex(pSessio
12f40 6e 2d 3e 64 62 29 29 3b 0a 20 20 69 66 28 20 62  n->db));.  if( b
12f50 49 6e 64 69 72 65 63 74 3e 3d 30 20 29 7b 0a 20  Indirect>=0 ){. 
12f60 20 20 20 70 53 65 73 73 69 6f 6e 2d 3e 62 49 6e     pSession->bIn
12f70 64 69 72 65 63 74 20 3d 20 62 49 6e 64 69 72 65  direct = bIndire
12f80 63 74 3b 0a 20 20 7d 0a 20 20 72 65 74 20 3d 20  ct;.  }.  ret = 
12f90 70 53 65 73 73 69 6f 6e 2d 3e 62 49 6e 64 69 72  pSession->bIndir
12fa0 65 63 74 3b 0a 20 20 73 71 6c 69 74 65 33 5f 6d  ect;.  sqlite3_m
12fb0 75 74 65 78 5f 6c 65 61 76 65 28 73 71 6c 69 74  utex_leave(sqlit
12fc0 65 33 5f 64 62 5f 6d 75 74 65 78 28 70 53 65 73  e3_db_mutex(pSes
12fd0 73 69 6f 6e 2d 3e 64 62 29 29 3b 0a 20 20 72 65  sion->db));.  re
12fe0 74 75 72 6e 20 72 65 74 3b 0a 7d 0a 0a 2f 2a 0a  turn ret;.}../*.
12ff0 2a 2a 20 52 65 74 75 72 6e 20 74 72 75 65 20 69  ** Return true i
13000 66 20 74 68 65 72 65 20 68 61 76 65 20 62 65 65  f there have bee
13010 6e 20 6e 6f 20 63 68 61 6e 67 65 73 20 74 6f 20  n no changes to 
13020 6d 6f 6e 69 74 6f 72 65 64 20 74 61 62 6c 65 73  monitored tables
13030 20 72 65 63 6f 72 64 65 64 0a 2a 2a 20 62 79 20   recorded.** by 
13040 74 68 65 20 73 65 73 73 69 6f 6e 20 6f 62 6a 65  the session obje
13050 63 74 20 70 61 73 73 65 64 20 61 73 20 74 68 65  ct passed as the
13060 20 6f 6e 6c 79 20 61 72 67 75 6d 65 6e 74 2e 0a   only argument..
13070 2a 2f 0a 69 6e 74 20 73 71 6c 69 74 65 33 73 65  */.int sqlite3se
13080 73 73 69 6f 6e 5f 69 73 65 6d 70 74 79 28 73 71  ssion_isempty(sq
13090 6c 69 74 65 33 5f 73 65 73 73 69 6f 6e 20 2a 70  lite3_session *p
130a0 53 65 73 73 69 6f 6e 29 7b 0a 20 20 69 6e 74 20  Session){.  int 
130b0 72 65 74 20 3d 20 30 3b 0a 20 20 53 65 73 73 69  ret = 0;.  Sessi
130c0 6f 6e 54 61 62 6c 65 20 2a 70 54 61 62 3b 0a 0a  onTable *pTab;..
130d0 20 20 73 71 6c 69 74 65 33 5f 6d 75 74 65 78 5f    sqlite3_mutex_
130e0 65 6e 74 65 72 28 73 71 6c 69 74 65 33 5f 64 62  enter(sqlite3_db
130f0 5f 6d 75 74 65 78 28 70 53 65 73 73 69 6f 6e 2d  _mutex(pSession-
13100 3e 64 62 29 29 3b 0a 20 20 66 6f 72 28 70 54 61  >db));.  for(pTa
13110 62 3d 70 53 65 73 73 69 6f 6e 2d 3e 70 54 61 62  b=pSession->pTab
13120 6c 65 3b 20 70 54 61 62 20 26 26 20 72 65 74 3d  le; pTab && ret=
13130 3d 30 3b 20 70 54 61 62 3d 70 54 61 62 2d 3e 70  =0; pTab=pTab->p
13140 4e 65 78 74 29 7b 0a 20 20 20 20 72 65 74 20 3d  Next){.    ret =
13150 20 28 70 54 61 62 2d 3e 6e 45 6e 74 72 79 3e 30   (pTab->nEntry>0
13160 29 3b 0a 20 20 7d 0a 20 20 73 71 6c 69 74 65 33  );.  }.  sqlite3
13170 5f 6d 75 74 65 78 5f 6c 65 61 76 65 28 73 71 6c  _mutex_leave(sql
13180 69 74 65 33 5f 64 62 5f 6d 75 74 65 78 28 70 53  ite3_db_mutex(pS
13190 65 73 73 69 6f 6e 2d 3e 64 62 29 29 3b 0a 0a 20  ession->db));.. 
131a0 20 72 65 74 75 72 6e 20 28 72 65 74 3d 3d 30 29   return (ret==0)
131b0 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 44 6f 20 74 68  ;.}../*.** Do th
131c0 65 20 77 6f 72 6b 20 66 6f 72 20 65 69 74 68 65  e work for eithe
131d0 72 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65 73  r sqlite3changes
131e0 65 74 5f 73 74 61 72 74 28 29 20 6f 72 20 73 74  et_start() or st
131f0 61 72 74 5f 73 74 72 6d 28 29 2e 0a 2a 2f 0a 73  art_strm()..*/.s
13200 74 61 74 69 63 20 69 6e 74 20 73 65 73 73 69 6f  tatic int sessio
13210 6e 43 68 61 6e 67 65 73 65 74 53 74 61 72 74 28  nChangesetStart(
13220 0a 20 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67  .  sqlite3_chang
13230 65 73 65 74 5f 69 74 65 72 20 2a 2a 70 70 2c 20  eset_iter **pp, 
13240 20 20 20 2f 2a 20 4f 55 54 3a 20 43 68 61 6e 67     /* OUT: Chang
13250 65 73 65 74 20 69 74 65 72 61 74 6f 72 20 68 61  eset iterator ha
13260 6e 64 6c 65 20 2a 2f 0a 20 20 69 6e 74 20 28 2a  ndle */.  int (*
13270 78 49 6e 70 75 74 29 28 76 6f 69 64 20 2a 70 49  xInput)(void *pI
13280 6e 2c 20 76 6f 69 64 20 2a 70 44 61 74 61 2c 20  n, void *pData, 
13290 69 6e 74 20 2a 70 6e 44 61 74 61 29 2c 0a 20 20  int *pnData),.  
132a0 76 6f 69 64 20 2a 70 49 6e 2c 0a 20 20 69 6e 74  void *pIn,.  int
132b0 20 6e 43 68 61 6e 67 65 73 65 74 2c 20 20 20 20   nChangeset,    
132c0 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
132d0 53 69 7a 65 20 6f 66 20 62 75 66 66 65 72 20 70  Size of buffer p
132e0 43 68 61 6e 67 65 73 65 74 20 69 6e 20 62 79 74  Changeset in byt
132f0 65 73 20 2a 2f 0a 20 20 76 6f 69 64 20 2a 70 43  es */.  void *pC
13300 68 61 6e 67 65 73 65 74 20 20 20 20 20 20 20 20  hangeset        
13310 20 20 20 20 20 20 20 20 2f 2a 20 50 6f 69 6e 74          /* Point
13320 65 72 20 74 6f 20 62 75 66 66 65 72 20 63 6f 6e  er to buffer con
13330 74 61 69 6e 69 6e 67 20 63 68 61 6e 67 65 73 65  taining changese
13340 74 20 2a 2f 0a 29 7b 0a 20 20 73 71 6c 69 74 65  t */.){.  sqlite
13350 33 5f 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72  3_changeset_iter
13360 20 2a 70 52 65 74 3b 20 20 20 2f 2a 20 49 74 65   *pRet;   /* Ite
13370 72 61 74 6f 72 20 74 6f 20 72 65 74 75 72 6e 20  rator to return 
13380 2a 2f 0a 20 20 69 6e 74 20 6e 42 79 74 65 3b 20  */.  int nByte; 
13390 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
133a0 20 20 20 20 20 2f 2a 20 4e 75 6d 62 65 72 20 6f       /* Number o
133b0 66 20 62 79 74 65 73 20 74 6f 20 61 6c 6c 6f 63  f bytes to alloc
133c0 61 74 65 20 66 6f 72 20 69 74 65 72 61 74 6f 72  ate for iterator
133d0 20 2a 2f 0a 0a 20 20 61 73 73 65 72 74 28 20 78   */..  assert( x
133e0 49 6e 70 75 74 3d 3d 30 20 7c 7c 20 28 70 43 68  Input==0 || (pCh
133f0 61 6e 67 65 73 65 74 3d 3d 30 20 26 26 20 6e 43  angeset==0 && nC
13400 68 61 6e 67 65 73 65 74 3d 3d 30 29 20 29 3b 0a  hangeset==0) );.
13410 0a 20 20 2f 2a 20 5a 65 72 6f 20 74 68 65 20 6f  .  /* Zero the o
13420 75 74 70 75 74 20 76 61 72 69 61 62 6c 65 20 69  utput variable i
13430 6e 20 63 61 73 65 20 61 6e 20 65 72 72 6f 72 20  n case an error 
13440 6f 63 63 75 72 73 2e 20 2a 2f 0a 20 20 2a 70 70  occurs. */.  *pp
13450 20 3d 20 30 3b 0a 0a 20 20 2f 2a 20 41 6c 6c 6f   = 0;..  /* Allo
13460 63 61 74 65 20 61 6e 64 20 69 6e 69 74 69 61 6c  cate and initial
13470 69 7a 65 20 74 68 65 20 69 74 65 72 61 74 6f 72  ize the iterator
13480 20 73 74 72 75 63 74 75 72 65 2e 20 2a 2f 0a 20   structure. */. 
13490 20 6e 42 79 74 65 20 3d 20 73 69 7a 65 6f 66 28   nByte = sizeof(
134a0 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 73 65  sqlite3_changese
134b0 74 5f 69 74 65 72 29 3b 0a 20 20 70 52 65 74 20  t_iter);.  pRet 
134c0 3d 20 28 73 71 6c 69 74 65 33 5f 63 68 61 6e 67  = (sqlite3_chang
134d0 65 73 65 74 5f 69 74 65 72 20 2a 29 73 71 6c 69  eset_iter *)sqli
134e0 74 65 33 5f 6d 61 6c 6c 6f 63 28 6e 42 79 74 65  te3_malloc(nByte
134f0 29 3b 0a 20 20 69 66 28 20 21 70 52 65 74 20 29  );.  if( !pRet )
13500 20 72 65 74 75 72 6e 20 53 51 4c 49 54 45 5f 4e   return SQLITE_N
13510 4f 4d 45 4d 3b 0a 20 20 6d 65 6d 73 65 74 28 70  OMEM;.  memset(p
13520 52 65 74 2c 20 30 2c 20 73 69 7a 65 6f 66 28 73  Ret, 0, sizeof(s
13530 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 73 65 74  qlite3_changeset
13540 5f 69 74 65 72 29 29 3b 0a 20 20 70 52 65 74 2d  _iter));.  pRet-
13550 3e 69 6e 2e 61 44 61 74 61 20 3d 20 28 75 38 20  >in.aData = (u8 
13560 2a 29 70 43 68 61 6e 67 65 73 65 74 3b 0a 20 20  *)pChangeset;.  
13570 70 52 65 74 2d 3e 69 6e 2e 6e 44 61 74 61 20 3d  pRet->in.nData =
13580 20 6e 43 68 61 6e 67 65 73 65 74 3b 0a 20 20 70   nChangeset;.  p
13590 52 65 74 2d 3e 69 6e 2e 78 49 6e 70 75 74 20 3d  Ret->in.xInput =
135a0 20 78 49 6e 70 75 74 3b 0a 20 20 70 52 65 74 2d   xInput;.  pRet-
135b0 3e 69 6e 2e 70 49 6e 20 3d 20 70 49 6e 3b 0a 20  >in.pIn = pIn;. 
135c0 20 70 52 65 74 2d 3e 69 6e 2e 62 45 6f 66 20 3d   pRet->in.bEof =
135d0 20 28 78 49 6e 70 75 74 20 3f 20 30 20 3a 20 31   (xInput ? 0 : 1
135e0 29 3b 0a 0a 20 20 2f 2a 20 50 6f 70 75 6c 61 74  );..  /* Populat
135f0 65 20 74 68 65 20 6f 75 74 70 75 74 20 76 61 72  e the output var
13600 69 61 62 6c 65 20 61 6e 64 20 72 65 74 75 72 6e  iable and return
13610 20 73 75 63 63 65 73 73 2e 20 2a 2f 0a 20 20 2a   success. */.  *
13620 70 70 20 3d 20 70 52 65 74 3b 0a 20 20 72 65 74  pp = pRet;.  ret
13630 75 72 6e 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a 7d  urn SQLITE_OK;.}
13640 0a 0a 2f 2a 0a 2a 2a 20 43 72 65 61 74 65 20 61  ../*.** Create a
13650 6e 20 69 74 65 72 61 74 6f 72 20 75 73 65 64 20  n iterator used 
13660 74 6f 20 69 74 65 72 61 74 65 20 74 68 72 6f 75  to iterate throu
13670 67 68 20 74 68 65 20 63 6f 6e 74 65 6e 74 73 20  gh the contents 
13680 6f 66 20 61 20 63 68 61 6e 67 65 73 65 74 2e 0a  of a changeset..
13690 2a 2f 0a 69 6e 74 20 73 71 6c 69 74 65 33 63 68  */.int sqlite3ch
136a0 61 6e 67 65 73 65 74 5f 73 74 61 72 74 28 0a 20  angeset_start(. 
136b0 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 73   sqlite3_changes
136c0 65 74 5f 69 74 65 72 20 2a 2a 70 70 2c 20 20 20  et_iter **pp,   
136d0 20 2f 2a 20 4f 55 54 3a 20 43 68 61 6e 67 65 73   /* OUT: Changes
136e0 65 74 20 69 74 65 72 61 74 6f 72 20 68 61 6e 64  et iterator hand
136f0 6c 65 20 2a 2f 0a 20 20 69 6e 74 20 6e 43 68 61  le */.  int nCha
13700 6e 67 65 73 65 74 2c 20 20 20 20 20 20 20 20 20  ngeset,         
13710 20 20 20 20 20 20 20 20 2f 2a 20 53 69 7a 65 20          /* Size 
13720 6f 66 20 62 75 66 66 65 72 20 70 43 68 61 6e 67  of buffer pChang
13730 65 73 65 74 20 69 6e 20 62 79 74 65 73 20 2a 2f  eset in bytes */
13740 0a 20 20 76 6f 69 64 20 2a 70 43 68 61 6e 67 65  .  void *pChange
13750 73 65 74 20 20 20 20 20 20 20 20 20 20 20 20 20  set             
13760 20 20 20 2f 2a 20 50 6f 69 6e 74 65 72 20 74 6f     /* Pointer to
13770 20 62 75 66 66 65 72 20 63 6f 6e 74 61 69 6e 69   buffer containi
13780 6e 67 20 63 68 61 6e 67 65 73 65 74 20 2a 2f 0a  ng changeset */.
13790 29 7b 0a 20 20 72 65 74 75 72 6e 20 73 65 73 73  ){.  return sess
137a0 69 6f 6e 43 68 61 6e 67 65 73 65 74 53 74 61 72  ionChangesetStar
137b0 74 28 70 70 2c 20 30 2c 20 30 2c 20 6e 43 68 61  t(pp, 0, 0, nCha
137c0 6e 67 65 73 65 74 2c 20 70 43 68 61 6e 67 65 73  ngeset, pChanges
137d0 65 74 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 53 74  et);.}../*.** St
137e0 72 65 61 6d 69 6e 67 20 76 65 72 73 69 6f 6e 20  reaming version 
137f0 6f 66 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65  of sqlite3change
13800 73 65 74 5f 73 74 61 72 74 28 29 2e 0a 2a 2f 0a  set_start()..*/.
13810 69 6e 74 20 73 71 6c 69 74 65 33 63 68 61 6e 67  int sqlite3chang
13820 65 73 65 74 5f 73 74 61 72 74 5f 73 74 72 6d 28  eset_start_strm(
13830 0a 20 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67  .  sqlite3_chang
13840 65 73 65 74 5f 69 74 65 72 20 2a 2a 70 70 2c 20  eset_iter **pp, 
13850 20 20 20 2f 2a 20 4f 55 54 3a 20 43 68 61 6e 67     /* OUT: Chang
13860 65 73 65 74 20 69 74 65 72 61 74 6f 72 20 68 61  eset iterator ha
13870 6e 64 6c 65 20 2a 2f 0a 20 20 69 6e 74 20 28 2a  ndle */.  int (*
13880 78 49 6e 70 75 74 29 28 76 6f 69 64 20 2a 70 49  xInput)(void *pI
13890 6e 2c 20 76 6f 69 64 20 2a 70 44 61 74 61 2c 20  n, void *pData, 
138a0 69 6e 74 20 2a 70 6e 44 61 74 61 29 2c 0a 20 20  int *pnData),.  
138b0 76 6f 69 64 20 2a 70 49 6e 0a 29 7b 0a 20 20 72  void *pIn.){.  r
138c0 65 74 75 72 6e 20 73 65 73 73 69 6f 6e 43 68 61  eturn sessionCha
138d0 6e 67 65 73 65 74 53 74 61 72 74 28 70 70 2c 20  ngesetStart(pp, 
138e0 78 49 6e 70 75 74 2c 20 70 49 6e 2c 20 30 2c 20  xInput, pIn, 0, 
138f0 30 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 49 66 20  0);.}../*.** If 
13900 74 68 65 20 53 65 73 73 69 6f 6e 49 6e 70 75 74  the SessionInput
13910 20 6f 62 6a 65 63 74 20 70 61 73 73 65 64 20 61   object passed a
13920 73 20 74 68 65 20 6f 6e 6c 79 20 61 72 67 75 6d  s the only argum
13930 65 6e 74 20 69 73 20 61 20 73 74 72 65 61 6d 69  ent is a streami
13940 6e 67 0a 2a 2a 20 6f 62 6a 65 63 74 20 61 6e 64  ng.** object and
13950 20 74 68 65 20 62 75 66 66 65 72 20 69 73 20 66   the buffer is f
13960 75 6c 6c 2c 20 64 69 73 63 61 72 64 20 73 6f 6d  ull, discard som
13970 65 20 64 61 74 61 20 74 6f 20 66 72 65 65 20 75  e data to free u
13980 70 20 73 70 61 63 65 2e 0a 2a 2f 0a 73 74 61 74  p space..*/.stat
13990 69 63 20 76 6f 69 64 20 73 65 73 73 69 6f 6e 44  ic void sessionD
139a0 69 73 63 61 72 64 44 61 74 61 28 53 65 73 73 69  iscardData(Sessi
139b0 6f 6e 49 6e 70 75 74 20 2a 70 49 6e 29 7b 0a 20  onInput *pIn){. 
139c0 20 69 66 28 20 70 49 6e 2d 3e 62 45 6f 66 20 26   if( pIn->bEof &
139d0 26 20 70 49 6e 2d 3e 78 49 6e 70 75 74 20 26 26  & pIn->xInput &&
139e0 20 70 49 6e 2d 3e 69 4e 65 78 74 3e 3d 53 45 53   pIn->iNext>=SES
139f0 53 49 4f 4e 53 5f 53 54 52 4d 5f 43 48 55 4e 4b  SIONS_STRM_CHUNK
13a00 5f 53 49 5a 45 20 29 7b 0a 20 20 20 20 69 6e 74  _SIZE ){.    int
13a10 20 6e 4d 6f 76 65 20 3d 20 70 49 6e 2d 3e 62 75   nMove = pIn->bu
13a20 66 2e 6e 42 75 66 20 2d 20 70 49 6e 2d 3e 69 4e  f.nBuf - pIn->iN
13a30 65 78 74 3b 0a 20 20 20 20 61 73 73 65 72 74 28  ext;.    assert(
13a40 20 6e 4d 6f 76 65 3e 3d 30 20 29 3b 0a 20 20 20   nMove>=0 );.   
13a50 20 69 66 28 20 6e 4d 6f 76 65 3e 30 20 29 7b 0a   if( nMove>0 ){.
13a60 20 20 20 20 20 20 6d 65 6d 6d 6f 76 65 28 70 49        memmove(pI
13a70 6e 2d 3e 62 75 66 2e 61 42 75 66 2c 20 26 70 49  n->buf.aBuf, &pI
13a80 6e 2d 3e 62 75 66 2e 61 42 75 66 5b 70 49 6e 2d  n->buf.aBuf[pIn-
13a90 3e 69 4e 65 78 74 5d 2c 20 6e 4d 6f 76 65 29 3b  >iNext], nMove);
13aa0 0a 20 20 20 20 7d 0a 20 20 20 20 70 49 6e 2d 3e  .    }.    pIn->
13ab0 62 75 66 2e 6e 42 75 66 20 2d 3d 20 70 49 6e 2d  buf.nBuf -= pIn-
13ac0 3e 69 4e 65 78 74 3b 0a 20 20 20 20 70 49 6e 2d  >iNext;.    pIn-
13ad0 3e 69 4e 65 78 74 20 3d 20 30 3b 0a 20 20 20 20  >iNext = 0;.    
13ae0 70 49 6e 2d 3e 6e 44 61 74 61 20 3d 20 70 49 6e  pIn->nData = pIn
13af0 2d 3e 62 75 66 2e 6e 42 75 66 3b 0a 20 20 7d 0a  ->buf.nBuf;.  }.
13b00 7d 0a 0a 2f 2a 0a 2a 2a 20 45 6e 73 75 72 65 20  }../*.** Ensure 
13b10 74 68 61 74 20 74 68 65 72 65 20 61 72 65 20 61  that there are a
13b20 74 20 6c 65 61 73 74 20 6e 42 79 74 65 20 62 79  t least nByte by
13b30 74 65 73 20 61 76 61 69 6c 61 62 6c 65 20 69 6e  tes available in
13b40 20 74 68 65 20 62 75 66 66 65 72 2e 20 4f 72 2c   the buffer. Or,
13b50 0a 2a 2a 20 69 66 20 74 68 65 72 65 20 61 72 65  .** if there are
13b60 20 6e 6f 74 20 6e 42 79 74 65 20 62 79 74 65 73   not nByte bytes
13b70 20 72 65 6d 61 69 6e 69 6e 67 20 69 6e 20 74 68   remaining in th
13b80 65 20 69 6e 70 75 74 2c 20 74 68 61 74 20 61 6c  e input, that al
13b90 6c 20 61 76 61 69 6c 61 62 6c 65 0a 2a 2a 20 64  l available.** d
13ba0 61 74 61 20 69 73 20 69 6e 20 74 68 65 20 62 75  ata is in the bu
13bb0 66 66 65 72 2e 0a 2a 2a 0a 2a 2a 20 52 65 74 75  ffer..**.** Retu
13bc0 72 6e 20 61 6e 20 53 51 4c 69 74 65 20 65 72 72  rn an SQLite err
13bd0 6f 72 20 63 6f 64 65 20 69 66 20 61 6e 20 65 72  or code if an er
13be0 72 6f 72 20 6f 63 63 75 72 73 2c 20 6f 72 20 53  ror occurs, or S
13bf0 51 4c 49 54 45 5f 4f 4b 20 6f 74 68 65 72 77 69  QLITE_OK otherwi
13c00 73 65 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e  se..*/.static in
13c10 74 20 73 65 73 73 69 6f 6e 49 6e 70 75 74 42 75  t sessionInputBu
13c20 66 66 65 72 28 53 65 73 73 69 6f 6e 49 6e 70 75  ffer(SessionInpu
13c30 74 20 2a 70 49 6e 2c 20 69 6e 74 20 6e 42 79 74  t *pIn, int nByt
13c40 65 29 7b 0a 20 20 69 6e 74 20 72 63 20 3d 20 53  e){.  int rc = S
13c50 51 4c 49 54 45 5f 4f 4b 3b 0a 20 20 69 66 28 20  QLITE_OK;.  if( 
13c60 70 49 6e 2d 3e 78 49 6e 70 75 74 20 29 7b 0a 20  pIn->xInput ){. 
13c70 20 20 20 77 68 69 6c 65 28 20 21 70 49 6e 2d 3e     while( !pIn->
13c80 62 45 6f 66 20 26 26 20 28 70 49 6e 2d 3e 69 4e  bEof && (pIn->iN
13c90 65 78 74 2b 6e 42 79 74 65 29 3e 3d 70 49 6e 2d  ext+nByte)>=pIn-
13ca0 3e 6e 44 61 74 61 20 26 26 20 72 63 3d 3d 53 51  >nData && rc==SQ
13cb0 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 20  LITE_OK ){.     
13cc0 20 69 6e 74 20 6e 4e 65 77 20 3d 20 53 45 53 53   int nNew = SESS
13cd0 49 4f 4e 53 5f 53 54 52 4d 5f 43 48 55 4e 4b 5f  IONS_STRM_CHUNK_
13ce0 53 49 5a 45 3b 0a 0a 20 20 20 20 20 20 69 66 28  SIZE;..      if(
13cf0 20 70 49 6e 2d 3e 62 4e 6f 44 69 73 63 61 72 64   pIn->bNoDiscard
13d00 3d 3d 30 20 29 20 73 65 73 73 69 6f 6e 44 69 73  ==0 ) sessionDis
13d10 63 61 72 64 44 61 74 61 28 70 49 6e 29 3b 0a 20  cardData(pIn);. 
13d20 20 20 20 20 20 69 66 28 20 53 51 4c 49 54 45 5f       if( SQLITE_
13d30 4f 4b 3d 3d 73 65 73 73 69 6f 6e 42 75 66 66 65  OK==sessionBuffe
13d40 72 47 72 6f 77 28 26 70 49 6e 2d 3e 62 75 66 2c  rGrow(&pIn->buf,
13d50 20 6e 4e 65 77 2c 20 26 72 63 29 20 29 7b 0a 20   nNew, &rc) ){. 
13d60 20 20 20 20 20 20 20 72 63 20 3d 20 70 49 6e 2d         rc = pIn-
13d70 3e 78 49 6e 70 75 74 28 70 49 6e 2d 3e 70 49 6e  >xInput(pIn->pIn
13d80 2c 20 26 70 49 6e 2d 3e 62 75 66 2e 61 42 75 66  , &pIn->buf.aBuf
13d90 5b 70 49 6e 2d 3e 62 75 66 2e 6e 42 75 66 5d 2c  [pIn->buf.nBuf],
13da0 20 26 6e 4e 65 77 29 3b 0a 20 20 20 20 20 20 20   &nNew);.       
13db0 20 69 66 28 20 6e 4e 65 77 3d 3d 30 20 29 7b 0a   if( nNew==0 ){.
13dc0 20 20 20 20 20 20 20 20 20 20 70 49 6e 2d 3e 62            pIn->b
13dd0 45 6f 66 20 3d 20 31 3b 0a 20 20 20 20 20 20 20  Eof = 1;.       
13de0 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 20 20   }else{.        
13df0 20 20 70 49 6e 2d 3e 62 75 66 2e 6e 42 75 66 20    pIn->buf.nBuf 
13e00 2b 3d 20 6e 4e 65 77 3b 0a 20 20 20 20 20 20 20  += nNew;.       
13e10 20 7d 0a 20 20 20 20 20 20 7d 0a 0a 20 20 20 20   }.      }..    
13e20 20 20 70 49 6e 2d 3e 61 44 61 74 61 20 3d 20 70    pIn->aData = p
13e30 49 6e 2d 3e 62 75 66 2e 61 42 75 66 3b 0a 20 20  In->buf.aBuf;.  
13e40 20 20 20 20 70 49 6e 2d 3e 6e 44 61 74 61 20 3d      pIn->nData =
13e50 20 70 49 6e 2d 3e 62 75 66 2e 6e 42 75 66 3b 0a   pIn->buf.nBuf;.
13e60 20 20 20 20 7d 0a 20 20 7d 0a 20 20 72 65 74 75      }.  }.  retu
13e70 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20  rn rc;.}../*.** 
13e80 57 68 65 6e 20 74 68 69 73 20 66 75 6e 63 74 69  When this functi
13e90 6f 6e 20 69 73 20 63 61 6c 6c 65 64 2c 20 2a 70  on is called, *p
13ea0 70 52 65 63 20 70 6f 69 6e 74 73 20 74 6f 20 74  pRec points to t
13eb0 68 65 20 73 74 61 72 74 20 6f 66 20 61 20 72 65  he start of a re
13ec0 63 6f 72 64 0a 2a 2a 20 74 68 61 74 20 63 6f 6e  cord.** that con
13ed0 74 61 69 6e 73 20 6e 43 6f 6c 20 76 61 6c 75 65  tains nCol value
13ee0 73 2e 20 54 68 69 73 20 66 75 6e 63 74 69 6f 6e  s. This function
13ef0 20 61 64 76 61 6e 63 65 73 20 74 68 65 20 70 6f   advances the po
13f00 69 6e 74 65 72 20 2a 70 70 52 65 63 0a 2a 2a 20  inter *ppRec.** 
13f10 75 6e 74 69 6c 20 69 74 20 70 6f 69 6e 74 73 20  until it points 
13f20 74 6f 20 74 68 65 20 62 79 74 65 20 69 6d 6d 65  to the byte imme
13f30 64 69 61 74 65 6c 79 20 66 6f 6c 6c 6f 77 69 6e  diately followin
13f40 67 20 74 68 61 74 20 72 65 63 6f 72 64 2e 0a 2a  g that record..*
13f50 2f 0a 73 74 61 74 69 63 20 76 6f 69 64 20 73 65  /.static void se
13f60 73 73 69 6f 6e 53 6b 69 70 52 65 63 6f 72 64 28  ssionSkipRecord(
13f70 0a 20 20 75 38 20 2a 2a 70 70 52 65 63 2c 20 20  .  u8 **ppRec,  
13f80 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
13f90 20 20 20 2f 2a 20 49 4e 2f 4f 55 54 3a 20 52 65     /* IN/OUT: Re
13fa0 63 6f 72 64 20 70 6f 69 6e 74 65 72 20 2a 2f 0a  cord pointer */.
13fb0 20 20 69 6e 74 20 6e 43 6f 6c 20 20 20 20 20 20    int nCol      
13fc0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
13fd0 20 20 2f 2a 20 4e 75 6d 62 65 72 20 6f 66 20 76    /* Number of v
13fe0 61 6c 75 65 73 20 69 6e 20 72 65 63 6f 72 64 20  alues in record 
13ff0 2a 2f 0a 29 7b 0a 20 20 75 38 20 2a 61 52 65 63  */.){.  u8 *aRec
14000 20 3d 20 2a 70 70 52 65 63 3b 0a 20 20 69 6e 74   = *ppRec;.  int
14010 20 69 3b 0a 20 20 66 6f 72 28 69 3d 30 3b 20 69   i;.  for(i=0; i
14020 3c 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a 20 20 20  <nCol; i++){.   
14030 20 69 6e 74 20 65 54 79 70 65 20 3d 20 2a 61 52   int eType = *aR
14040 65 63 2b 2b 3b 0a 20 20 20 20 69 66 28 20 65 54  ec++;.    if( eT
14050 79 70 65 3d 3d 53 51 4c 49 54 45 5f 54 45 58 54  ype==SQLITE_TEXT
14060 20 7c 7c 20 65 54 79 70 65 3d 3d 53 51 4c 49 54   || eType==SQLIT
14070 45 5f 42 4c 4f 42 20 29 7b 0a 20 20 20 20 20 20  E_BLOB ){.      
14080 69 6e 74 20 6e 42 79 74 65 3b 0a 20 20 20 20 20  int nByte;.     
14090 20 61 52 65 63 20 2b 3d 20 73 65 73 73 69 6f 6e   aRec += session
140a0 56 61 72 69 6e 74 47 65 74 28 28 75 38 2a 29 61  VarintGet((u8*)a
140b0 52 65 63 2c 20 26 6e 42 79 74 65 29 3b 0a 20 20  Rec, &nByte);.  
140c0 20 20 20 20 61 52 65 63 20 2b 3d 20 6e 42 79 74      aRec += nByt
140d0 65 3b 0a 20 20 20 20 7d 65 6c 73 65 20 69 66 28  e;.    }else if(
140e0 20 65 54 79 70 65 3d 3d 53 51 4c 49 54 45 5f 49   eType==SQLITE_I
140f0 4e 54 45 47 45 52 20 7c 7c 20 65 54 79 70 65 3d  NTEGER || eType=
14100 3d 53 51 4c 49 54 45 5f 46 4c 4f 41 54 20 29 7b  =SQLITE_FLOAT ){
14110 0a 20 20 20 20 20 20 61 52 65 63 20 2b 3d 20 38  .      aRec += 8
14120 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a 0a 20 20 2a  ;.    }.  }..  *
14130 70 70 52 65 63 20 3d 20 61 52 65 63 3b 0a 7d 0a  ppRec = aRec;.}.
14140 0a 2f 2a 0a 2a 2a 20 54 68 69 73 20 66 75 6e 63  ./*.** This func
14150 74 69 6f 6e 20 73 65 74 73 20 74 68 65 20 76 61  tion sets the va
14160 6c 75 65 20 6f 66 20 74 68 65 20 73 71 6c 69 74  lue of the sqlit
14170 65 33 5f 76 61 6c 75 65 20 6f 62 6a 65 63 74 20  e3_value object 
14180 70 61 73 73 65 64 20 61 73 20 74 68 65 0a 2a 2a  passed as the.**
14190 20 66 69 72 73 74 20 61 72 67 75 6d 65 6e 74 20   first argument 
141a0 74 6f 20 61 20 63 6f 70 79 20 6f 66 20 74 68 65  to a copy of the
141b0 20 73 74 72 69 6e 67 20 6f 72 20 62 6c 6f 62 20   string or blob 
141c0 68 65 6c 64 20 69 6e 20 74 68 65 20 61 44 61 74  held in the aDat
141d0 61 5b 5d 20 0a 2a 2a 20 62 75 66 66 65 72 2e 20  a[] .** buffer. 
141e0 53 51 4c 49 54 45 5f 4f 4b 20 69 73 20 72 65 74  SQLITE_OK is ret
141f0 75 72 6e 65 64 20 69 66 20 73 75 63 63 65 73 73  urned if success
14200 66 75 6c 2c 20 6f 72 20 53 51 4c 49 54 45 5f 4e  ful, or SQLITE_N
14210 4f 4d 45 4d 20 69 66 20 61 6e 20 4f 4f 4d 0a 2a  OMEM if an OOM.*
14220 2a 20 65 72 72 6f 72 20 6f 63 63 75 72 73 2e 0a  * error occurs..
14230 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65  */.static int se
14240 73 73 69 6f 6e 56 61 6c 75 65 53 65 74 53 74 72  ssionValueSetStr
14250 28 0a 20 20 73 71 6c 69 74 65 33 5f 76 61 6c 75  (.  sqlite3_valu
14260 65 20 2a 70 56 61 6c 2c 20 20 20 20 20 20 20 20  e *pVal,        
14270 20 20 20 20 2f 2a 20 53 65 74 20 74 68 65 20 76      /* Set the v
14280 61 6c 75 65 20 6f 66 20 74 68 69 73 20 6f 62 6a  alue of this obj
14290 65 63 74 20 2a 2f 0a 20 20 75 38 20 2a 61 44 61  ect */.  u8 *aDa
142a0 74 61 2c 20 20 20 20 20 20 20 20 20 20 20 20 20  ta,             
142b0 20 20 20 20 20 20 20 20 20 2f 2a 20 42 75 66 66           /* Buff
142c0 65 72 20 63 6f 6e 74 61 69 6e 69 6e 67 20 73 74  er containing st
142d0 72 69 6e 67 20 6f 72 20 62 6c 6f 62 20 64 61 74  ring or blob dat
142e0 61 20 2a 2f 0a 20 20 69 6e 74 20 6e 44 61 74 61  a */.  int nData
142f0 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  ,               
14300 20 20 20 20 20 20 20 2f 2a 20 53 69 7a 65 20 6f         /* Size o
14310 66 20 62 75 66 66 65 72 20 61 44 61 74 61 5b 5d  f buffer aData[]
14320 20 69 6e 20 62 79 74 65 73 20 2a 2f 0a 20 20 75   in bytes */.  u
14330 38 20 65 6e 63 20 20 20 20 20 20 20 20 20 20 20  8 enc           
14340 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
14350 2a 20 53 74 72 69 6e 67 20 65 6e 63 6f 64 69 6e  * String encodin
14360 67 20 28 30 20 66 6f 72 20 62 6c 6f 62 73 29 20  g (0 for blobs) 
14370 2a 2f 0a 29 7b 0a 20 20 2f 2a 20 49 6e 20 74 68  */.){.  /* In th
14380 65 6f 72 79 20 74 68 69 73 20 63 6f 64 65 20 63  eory this code c
14390 6f 75 6c 64 20 6a 75 73 74 20 70 61 73 73 20 53  ould just pass S
143a0 51 4c 49 54 45 5f 54 52 41 4e 53 49 45 4e 54 20  QLITE_TRANSIENT 
143b0 61 73 20 74 68 65 20 66 69 6e 61 6c 0a 20 20 2a  as the final.  *
143c0 2a 20 61 72 67 75 6d 65 6e 74 20 74 6f 20 73 71  * argument to sq
143d0 6c 69 74 65 33 56 61 6c 75 65 53 65 74 53 74 72  lite3ValueSetStr
143e0 28 29 20 61 6e 64 20 68 61 76 65 20 74 68 65 20  () and have the 
143f0 63 6f 70 79 20 63 72 65 61 74 65 64 20 0a 20 20  copy created .  
14400 2a 2a 20 61 75 74 6f 6d 61 74 69 63 61 6c 6c 79  ** automatically
14410 2e 20 42 75 74 20 64 6f 69 6e 67 20 73 6f 20 6d  . But doing so m
14420 61 6b 65 73 20 69 74 20 64 69 66 66 69 63 75 6c  akes it difficul
14430 74 20 74 6f 20 64 65 74 65 63 74 20 61 6e 79 20  t to detect any 
14440 4f 4f 4d 0a 20 20 2a 2a 20 65 72 72 6f 72 2e 20  OOM.  ** error. 
14450 48 65 6e 63 65 20 74 68 65 20 63 6f 64 65 20 74  Hence the code t
14460 6f 20 63 72 65 61 74 65 20 74 68 65 20 63 6f 70  o create the cop
14470 79 20 65 78 74 65 72 6e 61 6c 6c 79 2e 20 2a 2f  y externally. */
14480 0a 20 20 75 38 20 2a 61 43 6f 70 79 20 3d 20 73  .  u8 *aCopy = s
14490 71 6c 69 74 65 33 5f 6d 61 6c 6c 6f 63 28 6e 44  qlite3_malloc(nD
144a0 61 74 61 2b 31 29 3b 0a 20 20 69 66 28 20 61 43  ata+1);.  if( aC
144b0 6f 70 79 3d 3d 30 20 29 20 72 65 74 75 72 6e 20  opy==0 ) return 
144c0 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20  SQLITE_NOMEM;.  
144d0 6d 65 6d 63 70 79 28 61 43 6f 70 79 2c 20 61 44  memcpy(aCopy, aD
144e0 61 74 61 2c 20 6e 44 61 74 61 29 3b 0a 20 20 73  ata, nData);.  s
144f0 71 6c 69 74 65 33 56 61 6c 75 65 53 65 74 53 74  qlite3ValueSetSt
14500 72 28 70 56 61 6c 2c 20 6e 44 61 74 61 2c 20 28  r(pVal, nData, (
14510 63 68 61 72 2a 29 61 43 6f 70 79 2c 20 65 6e 63  char*)aCopy, enc
14520 2c 20 73 71 6c 69 74 65 33 5f 66 72 65 65 29 3b  , sqlite3_free);
14530 0a 20 20 72 65 74 75 72 6e 20 53 51 4c 49 54 45  .  return SQLITE
14540 5f 4f 4b 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 44 65  _OK;.}../*.** De
14550 73 65 72 69 61 6c 69 7a 65 20 61 20 73 69 6e 67  serialize a sing
14560 6c 65 20 72 65 63 6f 72 64 20 66 72 6f 6d 20 61  le record from a
14570 20 62 75 66 66 65 72 20 69 6e 20 6d 65 6d 6f 72   buffer in memor
14580 79 2e 20 53 65 65 20 22 52 45 43 4f 52 44 20 46  y. See "RECORD F
14590 4f 52 4d 41 54 22 0a 2a 2a 20 66 6f 72 20 64 65  ORMAT".** for de
145a0 74 61 69 6c 73 2e 0a 2a 2a 0a 2a 2a 20 57 68 65  tails..**.** Whe
145b0 6e 20 74 68 69 73 20 66 75 6e 63 74 69 6f 6e 20  n this function 
145c0 69 73 20 63 61 6c 6c 65 64 2c 20 2a 70 61 43 68  is called, *paCh
145d0 61 6e 67 65 20 70 6f 69 6e 74 73 20 74 6f 20 74  ange points to t
145e0 68 65 20 73 74 61 72 74 20 6f 66 20 74 68 65 20  he start of the 
145f0 72 65 63 6f 72 64 0a 2a 2a 20 74 6f 20 64 65 73  record.** to des
14600 65 72 69 61 6c 69 7a 65 2e 20 41 73 73 75 6d 69  erialize. Assumi
14610 6e 67 20 6e 6f 20 65 72 72 6f 72 20 6f 63 63 75  ng no error occu
14620 72 73 2c 20 2a 70 61 43 68 61 6e 67 65 20 69 73  rs, *paChange is
14630 20 73 65 74 20 74 6f 20 70 6f 69 6e 74 20 74 6f   set to point to
14640 0a 2a 2a 20 6f 6e 65 20 62 79 74 65 20 61 66 74  .** one byte aft
14650 65 72 20 74 68 65 20 65 6e 64 20 6f 66 20 74 68  er the end of th
14660 65 20 73 61 6d 65 20 72 65 63 6f 72 64 20 62 65  e same record be
14670 66 6f 72 65 20 74 68 69 73 20 66 75 6e 63 74 69  fore this functi
14680 6f 6e 20 72 65 74 75 72 6e 73 2e 0a 2a 2a 20 49  on returns..** I
14690 66 20 74 68 65 20 61 72 67 75 6d 65 6e 74 20 61  f the argument a
146a0 62 50 4b 20 69 73 20 4e 55 4c 4c 2c 20 74 68 65  bPK is NULL, the
146b0 6e 20 74 68 65 20 72 65 63 6f 72 64 20 63 6f 6e  n the record con
146c0 74 61 69 6e 73 20 6e 43 6f 6c 20 76 61 6c 75 65  tains nCol value
146d0 73 2e 20 4f 72 2c 0a 2a 2a 20 69 66 20 61 62 50  s. Or,.** if abP
146e0 4b 20 69 73 20 6f 74 68 65 72 20 74 68 61 6e 20  K is other than 
146f0 4e 55 4c 4c 2c 20 74 68 65 6e 20 74 68 65 20 72  NULL, then the r
14700 65 63 6f 72 64 20 63 6f 6e 74 61 69 6e 73 20 6f  ecord contains o
14710 6e 6c 79 20 74 68 65 20 50 4b 20 66 69 65 6c 64  nly the PK field
14720 73 0a 2a 2a 20 28 69 6e 20 6f 74 68 65 72 20 77  s.** (in other w
14730 6f 72 64 73 2c 20 69 74 20 69 73 20 61 20 70 61  ords, it is a pa
14740 74 63 68 73 65 74 20 44 45 4c 45 54 45 20 72 65  tchset DELETE re
14750 63 6f 72 64 29 2e 0a 2a 2a 0a 2a 2a 20 49 66 20  cord)..**.** If 
14760 73 75 63 63 65 73 73 66 75 6c 2c 20 65 61 63 68  successful, each
14770 20 65 6c 65 6d 65 6e 74 20 6f 66 20 74 68 65 20   element of the 
14780 61 70 4f 75 74 5b 5d 20 61 72 72 61 79 20 28 61  apOut[] array (a
14790 6c 6c 6f 63 61 74 65 64 20 62 79 20 74 68 65 20  llocated by the 
147a0 63 61 6c 6c 65 72 29 0a 2a 2a 20 69 73 20 73 65  caller).** is se
147b0 74 20 74 6f 20 70 6f 69 6e 74 20 74 6f 20 61 6e  t to point to an
147c0 20 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 20 6f   sqlite3_value o
147d0 62 6a 65 63 74 20 63 6f 6e 74 61 69 6e 69 6e 67  bject containing
147e0 20 74 68 65 20 76 61 6c 75 65 20 72 65 61 64 0a   the value read.
147f0 2a 2a 20 66 72 6f 6d 20 74 68 65 20 63 6f 72 72  ** from the corr
14800 65 73 70 6f 6e 64 69 6e 67 20 70 6f 73 69 74 69  esponding positi
14810 6f 6e 20 69 6e 20 74 68 65 20 72 65 63 6f 72 64  on in the record
14820 2e 20 49 66 20 74 68 61 74 20 76 61 6c 75 65 20  . If that value 
14830 69 73 20 6e 6f 74 0a 2a 2a 20 69 6e 63 6c 75 64  is not.** includ
14840 65 64 20 69 6e 20 74 68 65 20 72 65 63 6f 72 64  ed in the record
14850 20 28 69 2e 65 2e 20 62 65 63 61 75 73 65 20 74   (i.e. because t
14860 68 65 20 72 65 63 6f 72 64 20 69 73 20 70 61 72  he record is par
14870 74 20 6f 66 20 61 6e 20 55 50 44 41 54 45 20 63  t of an UPDATE c
14880 68 61 6e 67 65 0a 2a 2a 20 61 6e 64 20 74 68 65  hange.** and the
14890 20 66 69 65 6c 64 20 77 61 73 20 6e 6f 74 20 6d   field was not m
148a0 6f 64 69 66 69 65 64 29 2c 20 74 68 65 20 63 6f  odified), the co
148b0 72 72 65 73 70 6f 6e 64 69 6e 67 20 65 6c 65 6d  rresponding elem
148c0 65 6e 74 20 6f 66 20 61 70 4f 75 74 5b 5d 20 69  ent of apOut[] i
148d0 73 0a 2a 2a 20 73 65 74 20 74 6f 20 4e 55 4c 4c  s.** set to NULL
148e0 2e 0a 2a 2a 0a 2a 2a 20 49 74 20 69 73 20 74 68  ..**.** It is th
148f0 65 20 72 65 73 70 6f 6e 73 69 62 69 6c 69 74 79  e responsibility
14900 20 6f 66 20 74 68 65 20 63 61 6c 6c 65 72 20 74   of the caller t
14910 6f 20 66 72 65 65 20 61 6c 6c 20 73 71 6c 69 74  o free all sqlit
14920 65 5f 76 61 6c 75 65 20 73 74 72 75 63 74 75 72  e_value structur
14930 65 73 0a 2a 2a 20 75 73 69 6e 67 20 73 71 6c 69  es.** using sqli
14940 74 65 33 5f 66 72 65 65 28 29 2e 0a 2a 2a 0a 2a  te3_free()..**.*
14950 2a 20 49 66 20 61 6e 20 65 72 72 6f 72 20 6f 63  * If an error oc
14960 63 75 72 73 2c 20 61 6e 20 53 51 4c 69 74 65 20  curs, an SQLite 
14970 65 72 72 6f 72 20 63 6f 64 65 20 28 65 2e 67 2e  error code (e.g.
14980 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 29 20 69   SQLITE_NOMEM) i
14990 73 20 72 65 74 75 72 6e 65 64 2e 0a 2a 2a 20 54  s returned..** T
149a0 68 65 20 61 70 4f 75 74 5b 5d 20 61 72 72 61 79  he apOut[] array
149b0 20 6d 61 79 20 68 61 76 65 20 62 65 65 6e 20 70   may have been p
149c0 61 72 74 69 61 6c 6c 79 20 70 6f 70 75 6c 61 74  artially populat
149d0 65 64 20 69 6e 20 74 68 69 73 20 63 61 73 65 2e  ed in this case.
149e0 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73  .*/.static int s
149f0 65 73 73 69 6f 6e 52 65 61 64 52 65 63 6f 72 64  essionReadRecord
14a00 28 0a 20 20 53 65 73 73 69 6f 6e 49 6e 70 75 74  (.  SessionInput
14a10 20 2a 70 49 6e 2c 20 20 20 20 20 20 20 20 20 20   *pIn,          
14a20 20 20 20 20 2f 2a 20 49 6e 70 75 74 20 64 61 74      /* Input dat
14a30 61 20 2a 2f 0a 20 20 69 6e 74 20 6e 43 6f 6c 2c  a */.  int nCol,
14a40 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
14a50 20 20 20 20 20 20 20 2f 2a 20 4e 75 6d 62 65 72         /* Number
14a60 20 6f 66 20 76 61 6c 75 65 73 20 69 6e 20 72 65   of values in re
14a70 63 6f 72 64 20 2a 2f 0a 20 20 75 38 20 2a 61 62  cord */.  u8 *ab
14a80 50 4b 2c 20 20 20 20 20 20 20 20 20 20 20 20 20  PK,             
14a90 20 20 20 20 20 20 20 20 20 20 2f 2a 20 41 72 72            /* Arr
14aa0 61 79 20 6f 66 20 70 72 69 6d 61 72 79 20 6b 65  ay of primary ke
14ab0 79 20 66 6c 61 67 73 2c 20 6f 72 20 4e 55 4c 4c  y flags, or NULL
14ac0 20 2a 2f 0a 20 20 73 71 6c 69 74 65 33 5f 76 61   */.  sqlite3_va
14ad0 6c 75 65 20 2a 2a 61 70 4f 75 74 20 20 20 20 20  lue **apOut     
14ae0 20 20 20 20 20 20 2f 2a 20 57 72 69 74 65 20 76        /* Write v
14af0 61 6c 75 65 73 20 74 6f 20 74 68 69 73 20 61 72  alues to this ar
14b00 72 61 79 20 2a 2f 0a 29 7b 0a 20 20 69 6e 74 20  ray */.){.  int 
14b10 69 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 20  i;              
14b20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 55              /* U
14b30 73 65 64 20 74 6f 20 69 74 65 72 61 74 65 20 74  sed to iterate t
14b40 68 72 6f 75 67 68 20 63 6f 6c 75 6d 6e 73 20 2a  hrough columns *
14b50 2f 0a 20 20 69 6e 74 20 72 63 20 3d 20 53 51 4c  /.  int rc = SQL
14b60 49 54 45 5f 4f 4b 3b 0a 0a 20 20 66 6f 72 28 69  ITE_OK;..  for(i
14b70 3d 30 3b 20 69 3c 6e 43 6f 6c 20 26 26 20 72 63  =0; i<nCol && rc
14b80 3d 3d 53 51 4c 49 54 45 5f 4f 4b 3b 20 69 2b 2b  ==SQLITE_OK; i++
14b90 29 7b 0a 20 20 20 20 69 6e 74 20 65 54 79 70 65  ){.    int eType
14ba0 20 3d 20 30 3b 20 20 20 20 20 20 20 20 20 20 20   = 0;           
14bb0 20 20 20 20 20 2f 2a 20 54 79 70 65 20 6f 66 20       /* Type of 
14bc0 76 61 6c 75 65 20 28 53 51 4c 49 54 45 5f 4e 55  value (SQLITE_NU
14bd0 4c 4c 2c 20 54 45 58 54 20 65 74 63 2e 29 20 2a  LL, TEXT etc.) *
14be0 2f 0a 20 20 20 20 69 66 28 20 61 62 50 4b 20 26  /.    if( abPK &
14bf0 26 20 61 62 50 4b 5b 69 5d 3d 3d 30 20 29 20 63  & abPK[i]==0 ) c
14c00 6f 6e 74 69 6e 75 65 3b 0a 20 20 20 20 72 63 20  ontinue;.    rc 
14c10 3d 20 73 65 73 73 69 6f 6e 49 6e 70 75 74 42 75  = sessionInputBu
14c20 66 66 65 72 28 70 49 6e 2c 20 39 29 3b 0a 20 20  ffer(pIn, 9);.  
14c30 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54 45    if( rc==SQLITE
14c40 5f 4f 4b 20 29 7b 0a 20 20 20 20 20 20 65 54 79  _OK ){.      eTy
14c50 70 65 20 3d 20 70 49 6e 2d 3e 61 44 61 74 61 5b  pe = pIn->aData[
14c60 70 49 6e 2d 3e 69 4e 65 78 74 2b 2b 5d 3b 0a 20  pIn->iNext++];. 
14c70 20 20 20 7d 0a 0a 20 20 20 20 61 73 73 65 72 74     }..    assert
14c80 28 20 61 70 4f 75 74 5b 69 5d 3d 3d 30 20 29 3b  ( apOut[i]==0 );
14c90 0a 20 20 20 20 69 66 28 20 65 54 79 70 65 20 29  .    if( eType )
14ca0 7b 0a 20 20 20 20 20 20 61 70 4f 75 74 5b 69 5d  {.      apOut[i]
14cb0 20 3d 20 73 71 6c 69 74 65 33 56 61 6c 75 65 4e   = sqlite3ValueN
14cc0 65 77 28 30 29 3b 0a 20 20 20 20 20 20 69 66 28  ew(0);.      if(
14cd0 20 21 61 70 4f 75 74 5b 69 5d 20 29 20 72 63 20   !apOut[i] ) rc 
14ce0 3d 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 3b 0a  = SQLITE_NOMEM;.
14cf0 20 20 20 20 7d 0a 0a 20 20 20 20 69 66 28 20 72      }..    if( r
14d00 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a  c==SQLITE_OK ){.
14d10 20 20 20 20 20 20 75 38 20 2a 61 56 61 6c 20 3d        u8 *aVal =
14d20 20 26 70 49 6e 2d 3e 61 44 61 74 61 5b 70 49 6e   &pIn->aData[pIn
14d30 2d 3e 69 4e 65 78 74 5d 3b 0a 20 20 20 20 20 20  ->iNext];.      
14d40 69 66 28 20 65 54 79 70 65 3d 3d 53 51 4c 49 54  if( eType==SQLIT
14d50 45 5f 54 45 58 54 20 7c 7c 20 65 54 79 70 65 3d  E_TEXT || eType=
14d60 3d 53 51 4c 49 54 45 5f 42 4c 4f 42 20 29 7b 0a  =SQLITE_BLOB ){.
14d70 20 20 20 20 20 20 20 20 69 6e 74 20 6e 42 79 74          int nByt
14d80 65 3b 0a 20 20 20 20 20 20 20 20 70 49 6e 2d 3e  e;.        pIn->
14d90 69 4e 65 78 74 20 2b 3d 20 73 65 73 73 69 6f 6e  iNext += session
14da0 56 61 72 69 6e 74 47 65 74 28 61 56 61 6c 2c 20  VarintGet(aVal, 
14db0 26 6e 42 79 74 65 29 3b 0a 20 20 20 20 20 20 20  &nByte);.       
14dc0 20 72 63 20 3d 20 73 65 73 73 69 6f 6e 49 6e 70   rc = sessionInp
14dd0 75 74 42 75 66 66 65 72 28 70 49 6e 2c 20 6e 42  utBuffer(pIn, nB
14de0 79 74 65 29 3b 0a 20 20 20 20 20 20 20 20 69 66  yte);.        if
14df0 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20  ( rc==SQLITE_OK 
14e00 29 7b 0a 20 20 20 20 20 20 20 20 20 20 75 38 20  ){.          u8 
14e10 65 6e 63 20 3d 20 28 65 54 79 70 65 3d 3d 53 51  enc = (eType==SQ
14e20 4c 49 54 45 5f 54 45 58 54 20 3f 20 53 51 4c 49  LITE_TEXT ? SQLI
14e30 54 45 5f 55 54 46 38 20 3a 20 30 29 3b 0a 20 20  TE_UTF8 : 0);.  
14e40 20 20 20 20 20 20 20 20 72 63 20 3d 20 73 65 73          rc = ses
14e50 73 69 6f 6e 56 61 6c 75 65 53 65 74 53 74 72 28  sionValueSetStr(
14e60 61 70 4f 75 74 5b 69 5d 2c 26 70 49 6e 2d 3e 61  apOut[i],&pIn->a
14e70 44 61 74 61 5b 70 49 6e 2d 3e 69 4e 65 78 74 5d  Data[pIn->iNext]
14e80 2c 6e 42 79 74 65 2c 65 6e 63 29 3b 0a 20 20 20  ,nByte,enc);.   
14e90 20 20 20 20 20 7d 0a 20 20 20 20 20 20 20 20 70       }.        p
14ea0 49 6e 2d 3e 69 4e 65 78 74 20 2b 3d 20 6e 42 79  In->iNext += nBy
14eb0 74 65 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20 20  te;.      }.    
14ec0 20 20 69 66 28 20 65 54 79 70 65 3d 3d 53 51 4c    if( eType==SQL
14ed0 49 54 45 5f 49 4e 54 45 47 45 52 20 7c 7c 20 65  ITE_INTEGER || e
14ee0 54 79 70 65 3d 3d 53 51 4c 49 54 45 5f 46 4c 4f  Type==SQLITE_FLO
14ef0 41 54 20 29 7b 0a 20 20 20 20 20 20 20 20 73 71  AT ){.        sq
14f00 6c 69 74 65 33 5f 69 6e 74 36 34 20 76 20 3d 20  lite3_int64 v = 
14f10 73 65 73 73 69 6f 6e 47 65 74 49 36 34 28 61 56  sessionGetI64(aV
14f20 61 6c 29 3b 0a 20 20 20 20 20 20 20 20 69 66 28  al);.        if(
14f30 20 65 54 79 70 65 3d 3d 53 51 4c 49 54 45 5f 49   eType==SQLITE_I
14f40 4e 54 45 47 45 52 20 29 7b 0a 20 20 20 20 20 20  NTEGER ){.      
14f50 20 20 20 20 73 71 6c 69 74 65 33 56 64 62 65 4d      sqlite3VdbeM
14f60 65 6d 53 65 74 49 6e 74 36 34 28 61 70 4f 75 74  emSetInt64(apOut
14f70 5b 69 5d 2c 20 76 29 3b 0a 20 20 20 20 20 20 20  [i], v);.       
14f80 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 20 20   }else{.        
14f90 20 20 64 6f 75 62 6c 65 20 64 3b 0a 20 20 20 20    double d;.    
14fa0 20 20 20 20 20 20 6d 65 6d 63 70 79 28 26 64 2c        memcpy(&d,
14fb0 20 26 76 2c 20 38 29 3b 0a 20 20 20 20 20 20 20   &v, 8);.       
14fc0 20 20 20 73 71 6c 69 74 65 33 56 64 62 65 4d 65     sqlite3VdbeMe
14fd0 6d 53 65 74 44 6f 75 62 6c 65 28 61 70 4f 75 74  mSetDouble(apOut
14fe0 5b 69 5d 2c 20 64 29 3b 0a 20 20 20 20 20 20 20  [i], d);.       
14ff0 20 7d 0a 20 20 20 20 20 20 20 20 70 49 6e 2d 3e   }.        pIn->
15000 69 4e 65 78 74 20 2b 3d 20 38 3b 0a 20 20 20 20  iNext += 8;.    
15010 20 20 7d 0a 20 20 20 20 7d 0a 20 20 7d 0a 0a 20    }.    }.  }.. 
15020 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f   return rc;.}../
15030 2a 0a 2a 2a 20 54 68 65 20 69 6e 70 75 74 20 70  *.** The input p
15040 6f 69 6e 74 65 72 20 63 75 72 72 65 6e 74 6c 79  ointer currently
15050 20 70 6f 69 6e 74 73 20 74 6f 20 74 68 65 20 73   points to the s
15060 65 63 6f 6e 64 20 62 79 74 65 20 6f 66 20 61 20  econd byte of a 
15070 74 61 62 6c 65 2d 68 65 61 64 65 72 2e 0a 2a 2a  table-header..**
15080 20 53 70 65 63 69 66 69 63 61 6c 6c 79 2c 20 74   Specifically, t
15090 6f 20 74 68 65 20 66 6f 6c 6c 6f 77 69 6e 67 3a  o the following:
150a0 0a 2a 2a 0a 2a 2a 20 20 20 2b 20 6e 75 6d 62 65  .**.**   + numbe
150b0 72 20 6f 66 20 63 6f 6c 75 6d 6e 73 20 69 6e 20  r of columns in 
150c0 74 61 62 6c 65 20 28 76 61 72 69 6e 74 29 0a 2a  table (varint).*
150d0 2a 20 20 20 2b 20 61 72 72 61 79 20 6f 66 20 50  *   + array of P
150e0 4b 20 66 6c 61 67 73 20 28 31 20 62 79 74 65 20  K flags (1 byte 
150f0 70 65 72 20 63 6f 6c 75 6d 6e 29 2c 0a 2a 2a 20  per column),.** 
15100 20 20 2b 20 74 61 62 6c 65 20 6e 61 6d 65 20 28    + table name (
15110 6e 75 6c 20 74 65 72 6d 69 6e 61 74 65 64 29 2e  nul terminated).
15120 0a 2a 2a 0a 2a 2a 20 54 68 69 73 20 66 75 6e 63  .**.** This func
15130 74 69 6f 6e 20 65 6e 73 75 72 65 73 20 74 68 61  tion ensures tha
15140 74 20 61 6c 6c 20 6f 66 20 74 68 65 20 61 62 6f  t all of the abo
15150 76 65 20 69 73 20 70 72 65 73 65 6e 74 20 69 6e  ve is present in
15160 20 74 68 65 20 69 6e 70 75 74 20 0a 2a 2a 20 62   the input .** b
15170 75 66 66 65 72 20 28 69 2e 65 2e 20 74 68 61 74  uffer (i.e. that
15180 20 69 74 20 63 61 6e 20 62 65 20 61 63 63 65 73   it can be acces
15190 73 65 64 20 77 69 74 68 6f 75 74 20 61 6e 79 20  sed without any 
151a0 63 61 6c 6c 73 20 74 6f 20 78 49 6e 70 75 74 28  calls to xInput(
151b0 29 29 2e 0a 2a 2a 20 49 66 20 73 75 63 63 65 73  ))..** If succes
151c0 73 66 75 6c 2c 20 53 51 4c 49 54 45 5f 4f 4b 20  sful, SQLITE_OK 
151d0 69 73 20 72 65 74 75 72 6e 65 64 2e 20 4f 74 68  is returned. Oth
151e0 65 72 77 69 73 65 2c 20 61 6e 20 53 51 4c 69 74  erwise, an SQLit
151f0 65 20 65 72 72 6f 72 20 63 6f 64 65 2e 0a 2a 2a  e error code..**
15200 20 54 68 65 20 69 6e 70 75 74 20 70 6f 69 6e 74   The input point
15210 65 72 20 69 73 20 6e 6f 74 20 6d 6f 76 65 64 2e  er is not moved.
15220 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73  .*/.static int s
15230 65 73 73 69 6f 6e 43 68 61 6e 67 65 73 65 74 42  essionChangesetB
15240 75 66 66 65 72 54 62 6c 68 64 72 28 53 65 73 73  ufferTblhdr(Sess
15250 69 6f 6e 49 6e 70 75 74 20 2a 70 49 6e 2c 20 69  ionInput *pIn, i
15260 6e 74 20 2a 70 6e 42 79 74 65 29 7b 0a 20 20 69  nt *pnByte){.  i
15270 6e 74 20 72 63 20 3d 20 53 51 4c 49 54 45 5f 4f  nt rc = SQLITE_O
15280 4b 3b 0a 20 20 69 6e 74 20 6e 43 6f 6c 20 3d 20  K;.  int nCol = 
15290 30 3b 0a 20 20 69 6e 74 20 6e 52 65 61 64 20 3d  0;.  int nRead =
152a0 20 30 3b 0a 0a 20 20 72 63 20 3d 20 73 65 73 73   0;..  rc = sess
152b0 69 6f 6e 49 6e 70 75 74 42 75 66 66 65 72 28 70  ionInputBuffer(p
152c0 49 6e 2c 20 39 29 3b 0a 20 20 69 66 28 20 72 63  In, 9);.  if( rc
152d0 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20  ==SQLITE_OK ){. 
152e0 20 20 20 6e 52 65 61 64 20 2b 3d 20 73 65 73 73     nRead += sess
152f0 69 6f 6e 56 61 72 69 6e 74 47 65 74 28 26 70 49  ionVarintGet(&pI
15300 6e 2d 3e 61 44 61 74 61 5b 70 49 6e 2d 3e 69 4e  n->aData[pIn->iN
15310 65 78 74 20 2b 20 6e 52 65 61 64 5d 2c 20 26 6e  ext + nRead], &n
15320 43 6f 6c 29 3b 0a 20 20 20 20 72 63 20 3d 20 73  Col);.    rc = s
15330 65 73 73 69 6f 6e 49 6e 70 75 74 42 75 66 66 65  essionInputBuffe
15340 72 28 70 49 6e 2c 20 6e 52 65 61 64 2b 6e 43 6f  r(pIn, nRead+nCo
15350 6c 2b 31 30 30 29 3b 0a 20 20 20 20 6e 52 65 61  l+100);.    nRea
15360 64 20 2b 3d 20 6e 43 6f 6c 3b 0a 20 20 7d 0a 0a  d += nCol;.  }..
15370 20 20 77 68 69 6c 65 28 20 72 63 3d 3d 53 51 4c    while( rc==SQL
15380 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 77 68  ITE_OK ){.    wh
15390 69 6c 65 28 20 28 70 49 6e 2d 3e 69 4e 65 78 74  ile( (pIn->iNext
153a0 20 2b 20 6e 52 65 61 64 29 3c 70 49 6e 2d 3e 6e   + nRead)<pIn->n
153b0 44 61 74 61 20 26 26 20 70 49 6e 2d 3e 61 44 61  Data && pIn->aDa
153c0 74 61 5b 70 49 6e 2d 3e 69 4e 65 78 74 20 2b 20  ta[pIn->iNext + 
153d0 6e 52 65 61 64 5d 20 29 7b 0a 20 20 20 20 20 20  nRead] ){.      
153e0 6e 52 65 61 64 2b 2b 3b 0a 20 20 20 20 7d 0a 20  nRead++;.    }. 
153f0 20 20 20 69 66 28 20 28 70 49 6e 2d 3e 69 4e 65     if( (pIn->iNe
15400 78 74 20 2b 20 6e 52 65 61 64 29 3c 70 49 6e 2d  xt + nRead)<pIn-
15410 3e 6e 44 61 74 61 20 29 20 62 72 65 61 6b 3b 0a  >nData ) break;.
15420 20 20 20 20 72 63 20 3d 20 73 65 73 73 69 6f 6e      rc = session
15430 49 6e 70 75 74 42 75 66 66 65 72 28 70 49 6e 2c  InputBuffer(pIn,
15440 20 6e 52 65 61 64 20 2b 20 31 30 30 29 3b 0a 20   nRead + 100);. 
15450 20 7d 0a 20 20 2a 70 6e 42 79 74 65 20 3d 20 6e   }.  *pnByte = n
15460 52 65 61 64 2b 31 3b 0a 20 20 72 65 74 75 72 6e  Read+1;.  return
15470 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68   rc;.}../*.** Th
15480 65 20 69 6e 70 75 74 20 70 6f 69 6e 74 65 72 20  e input pointer 
15490 63 75 72 72 65 6e 74 6c 79 20 70 6f 69 6e 74 73  currently points
154a0 20 74 6f 20 74 68 65 20 66 69 72 73 74 20 62 79   to the first by
154b0 74 65 20 6f 66 20 74 68 65 20 66 69 72 73 74 20  te of the first 
154c0 66 69 65 6c 64 0a 2a 2a 20 6f 66 20 61 20 72 65  field.** of a re
154d0 63 6f 72 64 20 63 6f 6e 73 69 73 74 69 6e 67 20  cord consisting 
154e0 6f 66 20 6e 43 6f 6c 20 63 6f 6c 75 6d 6e 73 2e  of nCol columns.
154f0 20 54 68 69 73 20 66 75 6e 63 74 69 6f 6e 20 65   This function e
15500 6e 73 75 72 65 73 20 74 68 65 20 65 6e 74 69 72  nsures the entir
15510 65 0a 2a 2a 20 72 65 63 6f 72 64 20 69 73 20 62  e.** record is b
15520 75 66 66 65 72 65 64 2e 20 49 74 20 64 6f 65 73  uffered. It does
15530 20 6e 6f 74 20 6d 6f 76 65 20 74 68 65 20 69 6e   not move the in
15540 70 75 74 20 70 6f 69 6e 74 65 72 2e 0a 2a 2a 0a  put pointer..**.
15550 2a 2a 20 49 66 20 73 75 63 63 65 73 73 66 75 6c  ** If successful
15560 2c 20 53 51 4c 49 54 45 5f 4f 4b 20 69 73 20 72  , SQLITE_OK is r
15570 65 74 75 72 6e 65 64 20 61 6e 64 20 2a 70 6e 42  eturned and *pnB
15580 79 74 65 20 69 73 20 73 65 74 20 74 6f 20 74 68  yte is set to th
15590 65 20 73 69 7a 65 20 6f 66 0a 2a 2a 20 74 68 65  e size of.** the
155a0 20 72 65 63 6f 72 64 20 69 6e 20 62 79 74 65 73   record in bytes
155b0 2e 20 4f 74 68 65 72 77 69 73 65 2c 20 61 6e 20  . Otherwise, an 
155c0 53 51 4c 69 74 65 20 65 72 72 6f 72 20 63 6f 64  SQLite error cod
155d0 65 20 69 73 20 72 65 74 75 72 6e 65 64 2e 20 54  e is returned. T
155e0 68 65 0a 2a 2a 20 66 69 6e 61 6c 20 76 61 6c 75  he.** final valu
155f0 65 20 6f 66 20 2a 70 6e 42 79 74 65 20 69 73 20  e of *pnByte is 
15600 75 6e 64 65 66 69 6e 65 64 20 69 6e 20 74 68 69  undefined in thi
15610 73 20 63 61 73 65 2e 0a 2a 2f 0a 73 74 61 74 69  s case..*/.stati
15620 63 20 69 6e 74 20 73 65 73 73 69 6f 6e 43 68 61  c int sessionCha
15630 6e 67 65 73 65 74 42 75 66 66 65 72 52 65 63 6f  ngesetBufferReco
15640 72 64 28 0a 20 20 53 65 73 73 69 6f 6e 49 6e 70  rd(.  SessionInp
15650 75 74 20 2a 70 49 6e 2c 20 20 20 20 20 20 20 20  ut *pIn,        
15660 20 20 20 20 20 20 2f 2a 20 49 6e 70 75 74 20 64        /* Input d
15670 61 74 61 20 2a 2f 0a 20 20 69 6e 74 20 6e 43 6f  ata */.  int nCo
15680 6c 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20  l,              
15690 20 20 20 20 20 20 20 20 20 2f 2a 20 4e 75 6d 62           /* Numb
156a0 65 72 20 6f 66 20 63 6f 6c 75 6d 6e 73 20 69 6e  er of columns in
156b0 20 72 65 63 6f 72 64 20 2a 2f 0a 20 20 69 6e 74   record */.  int
156c0 20 2a 70 6e 42 79 74 65 20 20 20 20 20 20 20 20   *pnByte        
156d0 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
156e0 4f 55 54 3a 20 53 69 7a 65 20 6f 66 20 72 65 63  OUT: Size of rec
156f0 6f 72 64 20 69 6e 20 62 79 74 65 73 20 2a 2f 0a  ord in bytes */.
15700 29 7b 0a 20 20 69 6e 74 20 72 63 20 3d 20 53 51  ){.  int rc = SQ
15710 4c 49 54 45 5f 4f 4b 3b 0a 20 20 69 6e 74 20 6e  LITE_OK;.  int n
15720 42 79 74 65 20 3d 20 30 3b 0a 20 20 69 6e 74 20  Byte = 0;.  int 
15730 69 3b 0a 20 20 66 6f 72 28 69 3d 30 3b 20 72 63  i;.  for(i=0; rc
15740 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 26 26 20 69  ==SQLITE_OK && i
15750 3c 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a 20 20 20  <nCol; i++){.   
15760 20 69 6e 74 20 65 54 79 70 65 3b 0a 20 20 20 20   int eType;.    
15770 72 63 20 3d 20 73 65 73 73 69 6f 6e 49 6e 70 75  rc = sessionInpu
15780 74 42 75 66 66 65 72 28 70 49 6e 2c 20 6e 42 79  tBuffer(pIn, nBy
15790 74 65 20 2b 20 31 30 29 3b 0a 20 20 20 20 69 66  te + 10);.    if
157a0 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20  ( rc==SQLITE_OK 
157b0 29 7b 0a 20 20 20 20 20 20 65 54 79 70 65 20 3d  ){.      eType =
157c0 20 70 49 6e 2d 3e 61 44 61 74 61 5b 70 49 6e 2d   pIn->aData[pIn-
157d0 3e 69 4e 65 78 74 20 2b 20 6e 42 79 74 65 2b 2b  >iNext + nByte++
157e0 5d 3b 0a 20 20 20 20 20 20 69 66 28 20 65 54 79  ];.      if( eTy
157f0 70 65 3d 3d 53 51 4c 49 54 45 5f 54 45 58 54 20  pe==SQLITE_TEXT 
15800 7c 7c 20 65 54 79 70 65 3d 3d 53 51 4c 49 54 45  || eType==SQLITE
15810 5f 42 4c 4f 42 20 29 7b 0a 20 20 20 20 20 20 20  _BLOB ){.       
15820 20 69 6e 74 20 6e 3b 0a 20 20 20 20 20 20 20 20   int n;.        
15830 6e 42 79 74 65 20 2b 3d 20 73 65 73 73 69 6f 6e  nByte += session
15840 56 61 72 69 6e 74 47 65 74 28 26 70 49 6e 2d 3e  VarintGet(&pIn->
15850 61 44 61 74 61 5b 70 49 6e 2d 3e 69 4e 65 78 74  aData[pIn->iNext
15860 2b 6e 42 79 74 65 5d 2c 20 26 6e 29 3b 0a 20 20  +nByte], &n);.  
15870 20 20 20 20 20 20 6e 42 79 74 65 20 2b 3d 20 6e        nByte += n
15880 3b 0a 20 20 20 20 20 20 20 20 72 63 20 3d 20 73  ;.        rc = s
15890 65 73 73 69 6f 6e 49 6e 70 75 74 42 75 66 66 65  essionInputBuffe
158a0 72 28 70 49 6e 2c 20 6e 42 79 74 65 29 3b 0a 20  r(pIn, nByte);. 
158b0 20 20 20 20 20 7d 65 6c 73 65 20 69 66 28 20 65       }else if( e
158c0 54 79 70 65 3d 3d 53 51 4c 49 54 45 5f 49 4e 54  Type==SQLITE_INT
158d0 45 47 45 52 20 7c 7c 20 65 54 79 70 65 3d 3d 53  EGER || eType==S
158e0 51 4c 49 54 45 5f 46 4c 4f 41 54 20 29 7b 0a 20  QLITE_FLOAT ){. 
158f0 20 20 20 20 20 20 20 6e 42 79 74 65 20 2b 3d 20         nByte += 
15900 38 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 7d  8;.      }.    }
15910 0a 20 20 7d 0a 20 20 2a 70 6e 42 79 74 65 20 3d  .  }.  *pnByte =
15920 20 6e 42 79 74 65 3b 0a 20 20 72 65 74 75 72 6e   nByte;.  return
15930 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68   rc;.}../*.** Th
15940 65 20 69 6e 70 75 74 20 70 6f 69 6e 74 65 72 20  e input pointer 
15950 63 75 72 72 65 6e 74 6c 79 20 70 6f 69 6e 74 73  currently points
15960 20 74 6f 20 74 68 65 20 73 65 63 6f 6e 64 20 62   to the second b
15970 79 74 65 20 6f 66 20 61 20 74 61 62 6c 65 2d 68  yte of a table-h
15980 65 61 64 65 72 2e 0a 2a 2a 20 53 70 65 63 69 66  eader..** Specif
15990 69 63 61 6c 6c 79 2c 20 74 6f 20 74 68 65 20 66  ically, to the f
159a0 6f 6c 6c 6f 77 69 6e 67 3a 0a 2a 2a 0a 2a 2a 20  ollowing:.**.** 
159b0 20 20 2b 20 6e 75 6d 62 65 72 20 6f 66 20 63 6f    + number of co
159c0 6c 75 6d 6e 73 20 69 6e 20 74 61 62 6c 65 20 28  lumns in table (
159d0 76 61 72 69 6e 74 29 0a 2a 2a 20 20 20 2b 20 61  varint).**   + a
159e0 72 72 61 79 20 6f 66 20 50 4b 20 66 6c 61 67 73  rray of PK flags
159f0 20 28 31 20 62 79 74 65 20 70 65 72 20 63 6f 6c   (1 byte per col
15a00 75 6d 6e 29 2c 0a 2a 2a 20 20 20 2b 20 74 61 62  umn),.**   + tab
15a10 6c 65 20 6e 61 6d 65 20 28 6e 75 6c 20 74 65 72  le name (nul ter
15a20 6d 69 6e 61 74 65 64 29 2e 0a 2a 2a 0a 2a 2a 20  minated)..**.** 
15a30 54 68 69 73 20 66 75 6e 63 74 69 6f 6e 20 64 65  This function de
15a40 63 6f 64 65 73 20 74 68 65 20 74 61 62 6c 65 2d  codes the table-
15a50 68 65 61 64 65 72 20 61 6e 64 20 70 6f 70 75 6c  header and popul
15a60 61 74 65 73 20 74 68 65 20 70 2d 3e 6e 43 6f 6c  ates the p->nCol
15a70 2c 20 0a 2a 2a 20 70 2d 3e 7a 54 61 62 20 61 6e  , .** p->zTab an
15a80 64 20 70 2d 3e 61 62 50 4b 5b 5d 20 76 61 72 69  d p->abPK[] vari
15a90 61 62 6c 65 73 20 61 63 63 6f 72 64 69 6e 67 6c  ables accordingl
15aa0 79 2e 20 54 68 65 20 70 2d 3e 61 70 56 61 6c 75  y. The p->apValu
15ab0 65 5b 5d 20 61 72 72 61 79 20 69 73 20 0a 2a 2a  e[] array is .**
15ac0 20 61 6c 73 6f 20 61 6c 6c 6f 63 61 74 65 64 20   also allocated 
15ad0 6f 72 20 72 65 73 69 7a 65 64 20 61 63 63 6f 72  or resized accor
15ae0 64 69 6e 67 20 74 6f 20 74 68 65 20 6e 65 77 20  ding to the new 
15af0 76 61 6c 75 65 20 6f 66 20 70 2d 3e 6e 43 6f 6c  value of p->nCol
15b00 2e 20 54 68 65 0a 2a 2a 20 69 6e 70 75 74 20 70  . The.** input p
15b10 6f 69 6e 74 65 72 20 69 73 20 6c 65 66 74 20 70  ointer is left p
15b20 6f 69 6e 74 69 6e 67 20 74 6f 20 74 68 65 20 62  ointing to the b
15b30 79 74 65 20 66 6f 6c 6c 6f 77 69 6e 67 20 74 68  yte following th
15b40 65 20 74 61 62 6c 65 20 68 65 61 64 65 72 2e 0a  e table header..
15b50 2a 2a 0a 2a 2a 20 49 66 20 73 75 63 63 65 73 73  **.** If success
15b60 66 75 6c 2c 20 53 51 4c 49 54 45 5f 4f 4b 20 69  ful, SQLITE_OK i
15b70 73 20 72 65 74 75 72 6e 65 64 2e 20 4f 74 68 65  s returned. Othe
15b80 72 77 69 73 65 2c 20 61 6e 20 53 51 4c 69 74 65  rwise, an SQLite
15b90 20 65 72 72 6f 72 20 63 6f 64 65 0a 2a 2a 20 69   error code.** i
15ba0 73 20 72 65 74 75 72 6e 65 64 20 61 6e 64 20 74  s returned and t
15bb0 68 65 20 66 69 6e 61 6c 20 76 61 6c 75 65 73 20  he final values 
15bc0 6f 66 20 74 68 65 20 76 61 72 69 6f 75 73 20 66  of the various f
15bd0 69 65 6c 64 73 20 65 6e 75 6d 65 72 61 74 65 64  ields enumerated
15be0 20 61 62 6f 76 65 0a 2a 2a 20 61 72 65 20 75 6e   above.** are un
15bf0 64 65 66 69 6e 65 64 2e 0a 2a 2f 0a 73 74 61 74  defined..*/.stat
15c00 69 63 20 69 6e 74 20 73 65 73 73 69 6f 6e 43 68  ic int sessionCh
15c10 61 6e 67 65 73 65 74 52 65 61 64 54 62 6c 68 64  angesetReadTblhd
15c20 72 28 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65  r(sqlite3_change
15c30 73 65 74 5f 69 74 65 72 20 2a 70 29 7b 0a 20 20  set_iter *p){.  
15c40 69 6e 74 20 72 63 3b 0a 20 20 69 6e 74 20 6e 43  int rc;.  int nC
15c50 6f 70 79 3b 0a 20 20 61 73 73 65 72 74 28 20 70  opy;.  assert( p
15c60 2d 3e 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20  ->rc==SQLITE_OK 
15c70 29 3b 0a 0a 20 20 72 63 20 3d 20 73 65 73 73 69  );..  rc = sessi
15c80 6f 6e 43 68 61 6e 67 65 73 65 74 42 75 66 66 65  onChangesetBuffe
15c90 72 54 62 6c 68 64 72 28 26 70 2d 3e 69 6e 2c 20  rTblhdr(&p->in, 
15ca0 26 6e 43 6f 70 79 29 3b 0a 20 20 69 66 28 20 72  &nCopy);.  if( r
15cb0 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a  c==SQLITE_OK ){.
15cc0 20 20 20 20 69 6e 74 20 6e 42 79 74 65 3b 0a 20      int nByte;. 
15cd0 20 20 20 69 6e 74 20 6e 56 61 72 69 6e 74 3b 0a     int nVarint;.
15ce0 20 20 20 20 6e 56 61 72 69 6e 74 20 3d 20 73 65      nVarint = se
15cf0 73 73 69 6f 6e 56 61 72 69 6e 74 47 65 74 28 26  ssionVarintGet(&
15d00 70 2d 3e 69 6e 2e 61 44 61 74 61 5b 70 2d 3e 69  p->in.aData[p->i
15d10 6e 2e 69 4e 65 78 74 5d 2c 20 26 70 2d 3e 6e 43  n.iNext], &p->nC
15d20 6f 6c 29 3b 0a 20 20 20 20 6e 43 6f 70 79 20 2d  ol);.    nCopy -
15d30 3d 20 6e 56 61 72 69 6e 74 3b 0a 20 20 20 20 70  = nVarint;.    p
15d40 2d 3e 69 6e 2e 69 4e 65 78 74 20 2b 3d 20 6e 56  ->in.iNext += nV
15d50 61 72 69 6e 74 3b 0a 20 20 20 20 6e 42 79 74 65  arint;.    nByte
15d60 20 3d 20 70 2d 3e 6e 43 6f 6c 20 2a 20 73 69 7a   = p->nCol * siz
15d70 65 6f 66 28 73 71 6c 69 74 65 33 5f 76 61 6c 75  eof(sqlite3_valu
15d80 65 2a 29 20 2a 20 32 20 2b 20 6e 43 6f 70 79 3b  e*) * 2 + nCopy;
15d90 0a 20 20 20 20 70 2d 3e 74 62 6c 68 64 72 2e 6e  .    p->tblhdr.n
15da0 42 75 66 20 3d 20 30 3b 0a 20 20 20 20 73 65 73  Buf = 0;.    ses
15db0 73 69 6f 6e 42 75 66 66 65 72 47 72 6f 77 28 26  sionBufferGrow(&
15dc0 70 2d 3e 74 62 6c 68 64 72 2c 20 6e 42 79 74 65  p->tblhdr, nByte
15dd0 2c 20 26 72 63 29 3b 0a 20 20 7d 0a 0a 20 20 69  , &rc);.  }..  i
15de0 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b  f( rc==SQLITE_OK
15df0 20 29 7b 0a 20 20 20 20 69 6e 74 20 69 50 4b 20   ){.    int iPK 
15e00 3d 20 73 69 7a 65 6f 66 28 73 71 6c 69 74 65 33  = sizeof(sqlite3
15e10 5f 76 61 6c 75 65 2a 29 2a 70 2d 3e 6e 43 6f 6c  _value*)*p->nCol
15e20 2a 32 3b 0a 20 20 20 20 6d 65 6d 73 65 74 28 70  *2;.    memset(p
15e30 2d 3e 74 62 6c 68 64 72 2e 61 42 75 66 2c 20 30  ->tblhdr.aBuf, 0
15e40 2c 20 69 50 4b 29 3b 0a 20 20 20 20 6d 65 6d 63  , iPK);.    memc
15e50 70 79 28 26 70 2d 3e 74 62 6c 68 64 72 2e 61 42  py(&p->tblhdr.aB
15e60 75 66 5b 69 50 4b 5d 2c 20 26 70 2d 3e 69 6e 2e  uf[iPK], &p->in.
15e70 61 44 61 74 61 5b 70 2d 3e 69 6e 2e 69 4e 65 78  aData[p->in.iNex
15e80 74 5d 2c 20 6e 43 6f 70 79 29 3b 0a 20 20 20 20  t], nCopy);.    
15e90 70 2d 3e 69 6e 2e 69 4e 65 78 74 20 2b 3d 20 6e  p->in.iNext += n
15ea0 43 6f 70 79 3b 0a 20 20 7d 0a 0a 20 20 70 2d 3e  Copy;.  }..  p->
15eb0 61 70 56 61 6c 75 65 20 3d 20 28 73 71 6c 69 74  apValue = (sqlit
15ec0 65 33 5f 76 61 6c 75 65 2a 2a 29 70 2d 3e 74 62  e3_value**)p->tb
15ed0 6c 68 64 72 2e 61 42 75 66 3b 0a 20 20 70 2d 3e  lhdr.aBuf;.  p->
15ee0 61 62 50 4b 20 3d 20 28 75 38 2a 29 26 70 2d 3e  abPK = (u8*)&p->
15ef0 61 70 56 61 6c 75 65 5b 70 2d 3e 6e 43 6f 6c 2a  apValue[p->nCol*
15f00 32 5d 3b 0a 20 20 70 2d 3e 7a 54 61 62 20 3d 20  2];.  p->zTab = 
15f10 28 63 68 61 72 2a 29 26 70 2d 3e 61 62 50 4b 5b  (char*)&p->abPK[
15f20 70 2d 3e 6e 43 6f 6c 5d 3b 0a 20 20 72 65 74 75  p->nCol];.  retu
15f30 72 6e 20 28 70 2d 3e 72 63 20 3d 20 72 63 29 3b  rn (p->rc = rc);
15f40 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 41 64 76 61 6e 63  .}../*.** Advanc
15f50 65 20 74 68 65 20 63 68 61 6e 67 65 73 65 74 20  e the changeset 
15f60 69 74 65 72 61 74 6f 72 20 74 6f 20 74 68 65 20  iterator to the 
15f70 6e 65 78 74 20 63 68 61 6e 67 65 2e 0a 2a 2a 0a  next change..**.
15f80 2a 2a 20 49 66 20 62 6f 74 68 20 70 61 52 65 63  ** If both paRec
15f90 20 61 6e 64 20 70 6e 52 65 63 20 61 72 65 20 4e   and pnRec are N
15fa0 55 4c 4c 2c 20 74 68 65 6e 20 74 68 69 73 20 66  ULL, then this f
15fb0 75 6e 63 74 69 6f 6e 20 77 6f 72 6b 73 20 6c 69  unction works li
15fc0 6b 65 20 74 68 65 20 70 75 62 6c 69 63 0a 2a 2a  ke the public.**
15fd0 20 41 50 49 20 73 71 6c 69 74 65 33 63 68 61 6e   API sqlite3chan
15fe0 67 65 73 65 74 5f 6e 65 78 74 28 29 2e 20 49 66  geset_next(). If
15ff0 20 53 51 4c 49 54 45 5f 52 4f 57 20 69 73 20 72   SQLITE_ROW is r
16000 65 74 75 72 6e 65 64 2c 20 74 68 65 6e 20 74 68  eturned, then th
16010 65 0a 2a 2a 20 73 71 6c 69 74 65 33 63 68 61 6e  e.** sqlite3chan
16020 67 65 73 65 74 5f 6e 65 77 28 29 20 61 6e 64 20  geset_new() and 
16030 6f 6c 64 28 29 20 41 50 49 73 20 6d 61 79 20 62  old() APIs may b
16040 65 20 75 73 65 64 20 74 6f 20 71 75 65 72 79 20  e used to query 
16050 66 6f 72 20 76 61 6c 75 65 73 2e 0a 2a 2a 0a 2a  for values..**.*
16060 2a 20 4f 74 68 65 72 77 69 73 65 2c 20 69 66 20  * Otherwise, if 
16070 70 61 52 65 63 20 61 6e 64 20 70 6e 52 65 63 20  paRec and pnRec 
16080 61 72 65 20 6e 6f 74 20 4e 55 4c 4c 2c 20 74 68  are not NULL, th
16090 65 6e 20 61 20 70 6f 69 6e 74 65 72 20 74 6f 20  en a pointer to 
160a0 74 68 65 20 63 68 61 6e 67 65 0a 2a 2a 20 72 65  the change.** re
160b0 63 6f 72 64 20 69 73 20 77 72 69 74 74 65 6e 20  cord is written 
160c0 74 6f 20 2a 70 61 52 65 63 20 62 65 66 6f 72 65  to *paRec before
160d0 20 72 65 74 75 72 6e 69 6e 67 20 61 6e 64 20 74   returning and t
160e0 68 65 20 6e 75 6d 62 65 72 20 6f 66 20 62 79 74  he number of byt
160f0 65 73 20 69 6e 0a 2a 2a 20 74 68 65 20 72 65 63  es in.** the rec
16100 6f 72 64 20 74 6f 20 2a 70 6e 52 65 63 2e 0a 2a  ord to *pnRec..*
16110 2a 0a 2a 2a 20 45 69 74 68 65 72 20 77 61 79 2c  *.** Either way,
16120 20 74 68 69 73 20 66 75 6e 63 74 69 6f 6e 20 72   this function r
16130 65 74 75 72 6e 73 20 53 51 4c 49 54 45 5f 52 4f  eturns SQLITE_RO
16140 57 20 69 66 20 74 68 65 20 69 74 65 72 61 74 6f  W if the iterato
16150 72 20 69 73 20 0a 2a 2a 20 73 75 63 63 65 73 73  r is .** success
16160 66 75 6c 6c 79 20 61 64 76 61 6e 63 65 64 20 74  fully advanced t
16170 6f 20 74 68 65 20 6e 65 78 74 20 63 68 61 6e 67  o the next chang
16180 65 20 69 6e 20 74 68 65 20 63 68 61 6e 67 65 73  e in the changes
16190 65 74 2c 20 61 6e 20 53 51 4c 69 74 65 20 0a 2a  et, an SQLite .*
161a0 2a 20 65 72 72 6f 72 20 63 6f 64 65 20 69 66 20  * error code if 
161b0 61 6e 20 65 72 72 6f 72 20 6f 63 63 75 72 73 2c  an error occurs,
161c0 20 6f 72 20 53 51 4c 49 54 45 5f 44 4f 4e 45 20   or SQLITE_DONE 
161d0 69 66 20 74 68 65 72 65 20 61 72 65 20 6e 6f 20  if there are no 
161e0 66 75 72 74 68 65 72 20 0a 2a 2a 20 63 68 61 6e  further .** chan
161f0 67 65 73 20 69 6e 20 74 68 65 20 63 68 61 6e 67  ges in the chang
16200 65 73 65 74 2e 0a 2a 2f 0a 73 74 61 74 69 63 20  eset..*/.static 
16210 69 6e 74 20 73 65 73 73 69 6f 6e 43 68 61 6e 67  int sessionChang
16220 65 73 65 74 4e 65 78 74 28 0a 20 20 73 71 6c 69  esetNext(.  sqli
16230 74 65 33 5f 63 68 61 6e 67 65 73 65 74 5f 69 74  te3_changeset_it
16240 65 72 20 2a 70 2c 20 20 20 20 20 20 2f 2a 20 43  er *p,      /* C
16250 68 61 6e 67 65 73 65 74 20 69 74 65 72 61 74 6f  hangeset iterato
16260 72 20 2a 2f 0a 20 20 75 38 20 2a 2a 70 61 52 65  r */.  u8 **paRe
16270 63 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20  c,              
16280 20 20 20 20 20 20 20 2f 2a 20 49 66 20 6e 6f 6e         /* If non
16290 2d 4e 55 4c 4c 2c 20 73 74 6f 72 65 20 72 65 63  -NULL, store rec
162a0 6f 72 64 20 70 6f 69 6e 74 65 72 20 68 65 72 65  ord pointer here
162b0 20 2a 2f 0a 20 20 69 6e 74 20 2a 70 6e 52 65 63   */.  int *pnRec
162c0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
162d0 20 20 20 20 20 20 2f 2a 20 49 66 20 6e 6f 6e 2d        /* If non-
162e0 4e 55 4c 4c 2c 20 73 74 6f 72 65 20 73 69 7a 65  NULL, store size
162f0 20 6f 66 20 72 65 63 6f 72 64 20 68 65 72 65 20   of record here 
16300 2a 2f 0a 29 7b 0a 20 20 69 6e 74 20 69 3b 0a 20  */.){.  int i;. 
16310 20 75 38 20 6f 70 3b 0a 0a 20 20 61 73 73 65 72   u8 op;..  asser
16320 74 28 20 28 70 61 52 65 63 3d 3d 30 20 26 26 20  t( (paRec==0 && 
16330 70 6e 52 65 63 3d 3d 30 29 20 7c 7c 20 28 70 61  pnRec==0) || (pa
16340 52 65 63 20 26 26 20 70 6e 52 65 63 29 20 29 3b  Rec && pnRec) );
16350 0a 0a 20 20 2f 2a 20 49 66 20 74 68 65 20 69 74  ..  /* If the it
16360 65 72 61 74 6f 72 20 69 73 20 69 6e 20 74 68 65  erator is in the
16370 20 65 72 72 6f 72 2d 73 74 61 74 65 2c 20 72 65   error-state, re
16380 74 75 72 6e 20 69 6d 6d 65 64 69 61 74 65 6c 79  turn immediately
16390 2e 20 2a 2f 0a 20 20 69 66 28 20 70 2d 3e 72 63  . */.  if( p->rc
163a0 21 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 20 72 65  !=SQLITE_OK ) re
163b0 74 75 72 6e 20 70 2d 3e 72 63 3b 0a 0a 20 20 2f  turn p->rc;..  /
163c0 2a 20 46 72 65 65 20 74 68 65 20 63 75 72 72 65  * Free the curre
163d0 6e 74 20 63 6f 6e 74 65 6e 74 73 20 6f 66 20 70  nt contents of p
163e0 2d 3e 61 70 56 61 6c 75 65 5b 5d 2c 20 69 66 20  ->apValue[], if 
163f0 61 6e 79 2e 20 2a 2f 0a 20 20 69 66 28 20 70 2d  any. */.  if( p-
16400 3e 61 70 56 61 6c 75 65 20 29 7b 0a 20 20 20 20  >apValue ){.    
16410 66 6f 72 28 69 3d 30 3b 20 69 3c 70 2d 3e 6e 43  for(i=0; i<p->nC
16420 6f 6c 2a 32 3b 20 69 2b 2b 29 7b 0a 20 20 20 20  ol*2; i++){.    
16430 20 20 73 71 6c 69 74 65 33 56 61 6c 75 65 46 72    sqlite3ValueFr
16440 65 65 28 70 2d 3e 61 70 56 61 6c 75 65 5b 69 5d  ee(p->apValue[i]
16450 29 3b 0a 20 20 20 20 7d 0a 20 20 20 20 6d 65 6d  );.    }.    mem
16460 73 65 74 28 70 2d 3e 61 70 56 61 6c 75 65 2c 20  set(p->apValue, 
16470 30 2c 20 73 69 7a 65 6f 66 28 73 71 6c 69 74 65  0, sizeof(sqlite
16480 33 5f 76 61 6c 75 65 2a 29 2a 70 2d 3e 6e 43 6f  3_value*)*p->nCo
16490 6c 2a 32 29 3b 0a 20 20 7d 0a 0a 20 20 2f 2a 20  l*2);.  }..  /* 
164a0 4d 61 6b 65 20 73 75 72 65 20 74 68 65 20 62 75  Make sure the bu
164b0 66 66 65 72 20 63 6f 6e 74 61 69 6e 73 20 61 74  ffer contains at
164c0 20 6c 65 61 73 74 20 31 30 20 62 79 74 65 73 20   least 10 bytes 
164d0 6f 66 20 69 6e 70 75 74 20 64 61 74 61 2c 20 6f  of input data, o
164e0 72 20 61 6c 6c 0a 20 20 2a 2a 20 72 65 6d 61 69  r all.  ** remai
164f0 6e 69 6e 67 20 64 61 74 61 20 69 66 20 74 68 65  ning data if the
16500 72 65 20 61 72 65 20 6c 65 73 73 20 74 68 61 6e  re are less than
16510 20 31 30 20 62 79 74 65 73 20 61 76 61 69 6c 61   10 bytes availa
16520 62 6c 65 2e 20 54 68 69 73 20 69 73 0a 20 20 2a  ble. This is.  *
16530 2a 20 73 75 66 66 69 63 69 65 6e 74 20 65 69 74  * sufficient eit
16540 68 65 72 20 66 6f 72 20 74 68 65 20 27 54 27 20  her for the 'T' 
16550 6f 72 20 27 50 27 20 62 79 74 65 20 61 6e 64 20  or 'P' byte and 
16560 74 68 65 20 76 61 72 69 6e 74 20 74 68 61 74 20  the varint that 
16570 66 6f 6c 6c 6f 77 73 0a 20 20 2a 2a 20 69 74 2c  follows.  ** it,
16580 20 6f 72 20 66 6f 72 20 74 68 65 20 74 77 6f 20   or for the two 
16590 73 69 6e 67 6c 65 20 62 79 74 65 20 76 61 6c 75  single byte valu
165a0 65 73 20 6f 74 68 65 72 77 69 73 65 2e 20 2a 2f  es otherwise. */
165b0 0a 20 20 70 2d 3e 72 63 20 3d 20 73 65 73 73 69  .  p->rc = sessi
165c0 6f 6e 49 6e 70 75 74 42 75 66 66 65 72 28 26 70  onInputBuffer(&p
165d0 2d 3e 69 6e 2c 20 32 29 3b 0a 20 20 69 66 28 20  ->in, 2);.  if( 
165e0 70 2d 3e 72 63 21 3d 53 51 4c 49 54 45 5f 4f 4b  p->rc!=SQLITE_OK
165f0 20 29 20 72 65 74 75 72 6e 20 70 2d 3e 72 63 3b   ) return p->rc;
16600 0a 0a 20 20 2f 2a 20 49 66 20 74 68 65 20 69 74  ..  /* If the it
16610 65 72 61 74 6f 72 20 69 73 20 61 6c 72 65 61 64  erator is alread
16620 79 20 61 74 20 74 68 65 20 65 6e 64 20 6f 66 20  y at the end of 
16630 74 68 65 20 63 68 61 6e 67 65 73 65 74 2c 20 72  the changeset, r
16640 65 74 75 72 6e 20 44 4f 4e 45 2e 20 2a 2f 0a 20  eturn DONE. */. 
16650 20 69 66 28 20 70 2d 3e 69 6e 2e 69 4e 65 78 74   if( p->in.iNext
16660 3e 3d 70 2d 3e 69 6e 2e 6e 44 61 74 61 20 29 7b  >=p->in.nData ){
16670 0a 20 20 20 20 72 65 74 75 72 6e 20 53 51 4c 49  .    return SQLI
16680 54 45 5f 44 4f 4e 45 3b 0a 20 20 7d 0a 0a 20 20  TE_DONE;.  }..  
16690 73 65 73 73 69 6f 6e 44 69 73 63 61 72 64 44 61  sessionDiscardDa
166a0 74 61 28 26 70 2d 3e 69 6e 29 3b 0a 20 20 70 2d  ta(&p->in);.  p-
166b0 3e 69 6e 2e 69 43 75 72 72 65 6e 74 20 3d 20 70  >in.iCurrent = p
166c0 2d 3e 69 6e 2e 69 4e 65 78 74 3b 0a 0a 20 20 6f  ->in.iNext;..  o
166d0 70 20 3d 20 70 2d 3e 69 6e 2e 61 44 61 74 61 5b  p = p->in.aData[
166e0 70 2d 3e 69 6e 2e 69 4e 65 78 74 2b 2b 5d 3b 0a  p->in.iNext++];.
166f0 20 20 69 66 28 20 6f 70 3d 3d 27 54 27 20 7c 7c    if( op=='T' ||
16700 20 6f 70 3d 3d 27 50 27 20 29 7b 0a 20 20 20 20   op=='P' ){.    
16710 70 2d 3e 62 50 61 74 63 68 73 65 74 20 3d 20 28  p->bPatchset = (
16720 6f 70 3d 3d 27 50 27 29 3b 0a 20 20 20 20 69 66  op=='P');.    if
16730 28 20 73 65 73 73 69 6f 6e 43 68 61 6e 67 65 73  ( sessionChanges
16740 65 74 52 65 61 64 54 62 6c 68 64 72 28 70 29 20  etReadTblhdr(p) 
16750 29 20 72 65 74 75 72 6e 20 70 2d 3e 72 63 3b 0a  ) return p->rc;.
16760 20 20 20 20 69 66 28 20 28 70 2d 3e 72 63 20 3d      if( (p->rc =
16770 20 73 65 73 73 69 6f 6e 49 6e 70 75 74 42 75 66   sessionInputBuf
16780 66 65 72 28 26 70 2d 3e 69 6e 2c 20 32 29 29 20  fer(&p->in, 2)) 
16790 29 20 72 65 74 75 72 6e 20 70 2d 3e 72 63 3b 0a  ) return p->rc;.
167a0 20 20 20 20 70 2d 3e 69 6e 2e 69 43 75 72 72 65      p->in.iCurre
167b0 6e 74 20 3d 20 70 2d 3e 69 6e 2e 69 4e 65 78 74  nt = p->in.iNext
167c0 3b 0a 20 20 20 20 6f 70 20 3d 20 70 2d 3e 69 6e  ;.    op = p->in
167d0 2e 61 44 61 74 61 5b 70 2d 3e 69 6e 2e 69 4e 65  .aData[p->in.iNe
167e0 78 74 2b 2b 5d 3b 0a 20 20 7d 0a 0a 20 20 70 2d  xt++];.  }..  p-
167f0 3e 6f 70 20 3d 20 6f 70 3b 0a 20 20 70 2d 3e 62  >op = op;.  p->b
16800 49 6e 64 69 72 65 63 74 20 3d 20 70 2d 3e 69 6e  Indirect = p->in
16810 2e 61 44 61 74 61 5b 70 2d 3e 69 6e 2e 69 4e 65  .aData[p->in.iNe
16820 78 74 2b 2b 5d 3b 0a 20 20 69 66 28 20 70 2d 3e  xt++];.  if( p->
16830 6f 70 21 3d 53 51 4c 49 54 45 5f 55 50 44 41 54  op!=SQLITE_UPDAT
16840 45 20 26 26 20 70 2d 3e 6f 70 21 3d 53 51 4c 49  E && p->op!=SQLI
16850 54 45 5f 44 45 4c 45 54 45 20 26 26 20 70 2d 3e  TE_DELETE && p->
16860 6f 70 21 3d 53 51 4c 49 54 45 5f 49 4e 53 45 52  op!=SQLITE_INSER
16870 54 20 29 7b 0a 20 20 20 20 72 65 74 75 72 6e 20  T ){.    return 
16880 28 70 2d 3e 72 63 20 3d 20 53 51 4c 49 54 45 5f  (p->rc = SQLITE_
16890 43 4f 52 52 55 50 54 5f 42 4b 50 54 29 3b 0a 20  CORRUPT_BKPT);. 
168a0 20 7d 0a 0a 20 20 69 66 28 20 70 61 52 65 63 20   }..  if( paRec 
168b0 29 7b 20 0a 20 20 20 20 69 6e 74 20 6e 56 61 6c  ){ .    int nVal
168c0 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  ;               
168d0 20 20 20 20 20 20 2f 2a 20 4e 75 6d 62 65 72 20        /* Number 
168e0 6f 66 20 76 61 6c 75 65 73 20 74 6f 20 62 75 66  of values to buf
168f0 66 65 72 20 2a 2f 0a 20 20 20 20 69 66 28 20 70  fer */.    if( p
16900 2d 3e 62 50 61 74 63 68 73 65 74 3d 3d 30 20 26  ->bPatchset==0 &
16910 26 20 6f 70 3d 3d 53 51 4c 49 54 45 5f 55 50 44  & op==SQLITE_UPD
16920 41 54 45 20 29 7b 0a 20 20 20 20 20 20 6e 56 61  ATE ){.      nVa
16930 6c 20 3d 20 70 2d 3e 6e 43 6f 6c 20 2a 20 32 3b  l = p->nCol * 2;
16940 0a 20 20 20 20 7d 65 6c 73 65 20 69 66 28 20 70  .    }else if( p
16950 2d 3e 62 50 61 74 63 68 73 65 74 20 26 26 20 6f  ->bPatchset && o
16960 70 3d 3d 53 51 4c 49 54 45 5f 44 45 4c 45 54 45  p==SQLITE_DELETE
16970 20 29 7b 0a 20 20 20 20 20 20 6e 56 61 6c 20 3d   ){.      nVal =
16980 20 30 3b 0a 20 20 20 20 20 20 66 6f 72 28 69 3d   0;.      for(i=
16990 30 3b 20 69 3c 70 2d 3e 6e 43 6f 6c 3b 20 69 2b  0; i<p->nCol; i+
169a0 2b 29 20 69 66 28 20 70 2d 3e 61 62 50 4b 5b 69  +) if( p->abPK[i
169b0 5d 20 29 20 6e 56 61 6c 2b 2b 3b 0a 20 20 20 20  ] ) nVal++;.    
169c0 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 6e 56 61  }else{.      nVa
169d0 6c 20 3d 20 70 2d 3e 6e 43 6f 6c 3b 0a 20 20 20  l = p->nCol;.   
169e0 20 7d 0a 20 20 20 20 70 2d 3e 72 63 20 3d 20 73   }.    p->rc = s
169f0 65 73 73 69 6f 6e 43 68 61 6e 67 65 73 65 74 42  essionChangesetB
16a00 75 66 66 65 72 52 65 63 6f 72 64 28 26 70 2d 3e  ufferRecord(&p->
16a10 69 6e 2c 20 6e 56 61 6c 2c 20 70 6e 52 65 63 29  in, nVal, pnRec)
16a20 3b 0a 20 20 20 20 69 66 28 20 70 2d 3e 72 63 21  ;.    if( p->rc!
16a30 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 20 72 65 74  =SQLITE_OK ) ret
16a40 75 72 6e 20 70 2d 3e 72 63 3b 0a 20 20 20 20 2a  urn p->rc;.    *
16a50 70 61 52 65 63 20 3d 20 26 70 2d 3e 69 6e 2e 61  paRec = &p->in.a
16a60 44 61 74 61 5b 70 2d 3e 69 6e 2e 69 4e 65 78 74  Data[p->in.iNext
16a70 5d 3b 0a 20 20 20 20 70 2d 3e 69 6e 2e 69 4e 65  ];.    p->in.iNe
16a80 78 74 20 2b 3d 20 2a 70 6e 52 65 63 3b 0a 20 20  xt += *pnRec;.  
16a90 7d 65 6c 73 65 7b 0a 0a 20 20 20 20 2f 2a 20 49  }else{..    /* I
16aa0 66 20 74 68 69 73 20 69 73 20 61 6e 20 55 50 44  f this is an UPD
16ab0 41 54 45 20 6f 72 20 44 45 4c 45 54 45 2c 20 72  ATE or DELETE, r
16ac0 65 61 64 20 74 68 65 20 6f 6c 64 2e 2a 20 72 65  ead the old.* re
16ad0 63 6f 72 64 2e 20 2a 2f 0a 20 20 20 20 69 66 28  cord. */.    if(
16ae0 20 70 2d 3e 6f 70 21 3d 53 51 4c 49 54 45 5f 49   p->op!=SQLITE_I
16af0 4e 53 45 52 54 20 26 26 20 28 70 2d 3e 62 50 61  NSERT && (p->bPa
16b00 74 63 68 73 65 74 3d 3d 30 20 7c 7c 20 70 2d 3e  tchset==0 || p->
16b10 6f 70 3d 3d 53 51 4c 49 54 45 5f 44 45 4c 45 54  op==SQLITE_DELET
16b20 45 29 20 29 7b 0a 20 20 20 20 20 20 75 38 20 2a  E) ){.      u8 *
16b30 61 62 50 4b 20 3d 20 70 2d 3e 62 50 61 74 63 68  abPK = p->bPatch
16b40 73 65 74 20 3f 20 70 2d 3e 61 62 50 4b 20 3a 20  set ? p->abPK : 
16b50 30 3b 0a 20 20 20 20 20 20 70 2d 3e 72 63 20 3d  0;.      p->rc =
16b60 20 73 65 73 73 69 6f 6e 52 65 61 64 52 65 63 6f   sessionReadReco
16b70 72 64 28 26 70 2d 3e 69 6e 2c 20 70 2d 3e 6e 43  rd(&p->in, p->nC
16b80 6f 6c 2c 20 61 62 50 4b 2c 20 70 2d 3e 61 70 56  ol, abPK, p->apV
16b90 61 6c 75 65 29 3b 0a 20 20 20 20 20 20 69 66 28  alue);.      if(
16ba0 20 70 2d 3e 72 63 21 3d 53 51 4c 49 54 45 5f 4f   p->rc!=SQLITE_O
16bb0 4b 20 29 20 72 65 74 75 72 6e 20 70 2d 3e 72 63  K ) return p->rc
16bc0 3b 0a 20 20 20 20 7d 0a 0a 20 20 20 20 2f 2a 20  ;.    }..    /* 
16bd0 49 66 20 74 68 69 73 20 69 73 20 61 6e 20 49 4e  If this is an IN
16be0 53 45 52 54 20 6f 72 20 55 50 44 41 54 45 2c 20  SERT or UPDATE, 
16bf0 72 65 61 64 20 74 68 65 20 6e 65 77 2e 2a 20 72  read the new.* r
16c00 65 63 6f 72 64 2e 20 2a 2f 0a 20 20 20 20 69 66  ecord. */.    if
16c10 28 20 70 2d 3e 6f 70 21 3d 53 51 4c 49 54 45 5f  ( p->op!=SQLITE_
16c20 44 45 4c 45 54 45 20 29 7b 0a 20 20 20 20 20 20  DELETE ){.      
16c30 70 2d 3e 72 63 20 3d 20 73 65 73 73 69 6f 6e 52  p->rc = sessionR
16c40 65 61 64 52 65 63 6f 72 64 28 26 70 2d 3e 69 6e  eadRecord(&p->in
16c50 2c 20 70 2d 3e 6e 43 6f 6c 2c 20 30 2c 20 26 70  , p->nCol, 0, &p
16c60 2d 3e 61 70 56 61 6c 75 65 5b 70 2d 3e 6e 43 6f  ->apValue[p->nCo
16c70 6c 5d 29 3b 0a 20 20 20 20 20 20 69 66 28 20 70  l]);.      if( p
16c80 2d 3e 72 63 21 3d 53 51 4c 49 54 45 5f 4f 4b 20  ->rc!=SQLITE_OK 
16c90 29 20 72 65 74 75 72 6e 20 70 2d 3e 72 63 3b 0a  ) return p->rc;.
16ca0 20 20 20 20 7d 0a 0a 20 20 20 20 69 66 28 20 70      }..    if( p
16cb0 2d 3e 62 50 61 74 63 68 73 65 74 20 26 26 20 70  ->bPatchset && p
16cc0 2d 3e 6f 70 3d 3d 53 51 4c 49 54 45 5f 55 50 44  ->op==SQLITE_UPD
16cd0 41 54 45 20 29 7b 0a 20 20 20 20 20 20 2f 2a 20  ATE ){.      /* 
16ce0 49 66 20 74 68 69 73 20 69 73 20 61 6e 20 55 50  If this is an UP
16cf0 44 41 54 45 20 74 68 61 74 20 69 73 20 70 61 72  DATE that is par
16d00 74 20 6f 66 20 61 20 70 61 74 63 68 73 65 74 2c  t of a patchset,
16d10 20 74 68 65 6e 20 61 6c 6c 20 50 4b 20 61 6e 64   then all PK and
16d20 0a 20 20 20 20 20 20 2a 2a 20 6d 6f 64 69 66 69  .      ** modifi
16d30 65 64 20 66 69 65 6c 64 73 20 61 72 65 20 70 72  ed fields are pr
16d40 65 73 65 6e 74 20 69 6e 20 74 68 65 20 6e 65 77  esent in the new
16d50 2e 2a 20 72 65 63 6f 72 64 2e 20 54 68 65 20 6f  .* record. The o
16d60 6c 64 2e 2a 20 72 65 63 6f 72 64 0a 20 20 20 20  ld.* record.    
16d70 20 20 2a 2a 20 69 73 20 63 75 72 72 65 6e 74 6c    ** is currentl
16d80 79 20 63 6f 6d 70 6c 65 74 65 6c 79 20 65 6d 70  y completely emp
16d90 74 79 2e 20 54 68 69 73 20 62 6c 6f 63 6b 20 73  ty. This block s
16da0 68 69 66 74 73 20 74 68 65 20 50 4b 20 66 69 65  hifts the PK fie
16db0 6c 64 73 20 66 72 6f 6d 0a 20 20 20 20 20 20 2a  lds from.      *
16dc0 2a 20 6e 65 77 2e 2a 20 74 6f 20 6f 6c 64 2e 2a  * new.* to old.*
16dd0 2c 20 74 6f 20 61 63 63 6f 6d 6d 6f 64 61 74 65  , to accommodate
16de0 20 74 68 65 20 63 6f 64 65 20 74 68 61 74 20 72   the code that r
16df0 65 61 64 73 20 74 68 65 73 65 20 61 72 72 61 79  eads these array
16e00 73 2e 20 20 2a 2f 0a 20 20 20 20 20 20 66 6f 72  s.  */.      for
16e10 28 69 3d 30 3b 20 69 3c 70 2d 3e 6e 43 6f 6c 3b  (i=0; i<p->nCol;
16e20 20 69 2b 2b 29 7b 0a 20 20 20 20 20 20 20 20 61   i++){.        a
16e30 73 73 65 72 74 28 20 70 2d 3e 61 70 56 61 6c 75  ssert( p->apValu
16e40 65 5b 69 5d 3d 3d 30 20 29 3b 0a 20 20 20 20 20  e[i]==0 );.     
16e50 20 20 20 61 73 73 65 72 74 28 20 70 2d 3e 61 62     assert( p->ab
16e60 50 4b 5b 69 5d 3d 3d 30 20 7c 7c 20 70 2d 3e 61  PK[i]==0 || p->a
16e70 70 56 61 6c 75 65 5b 69 2b 70 2d 3e 6e 43 6f 6c  pValue[i+p->nCol
16e80 5d 20 29 3b 0a 20 20 20 20 20 20 20 20 69 66 28  ] );.        if(
16e90 20 70 2d 3e 61 62 50 4b 5b 69 5d 20 29 7b 0a 20   p->abPK[i] ){. 
16ea0 20 20 20 20 20 20 20 20 20 70 2d 3e 61 70 56 61           p->apVa
16eb0 6c 75 65 5b 69 5d 20 3d 20 70 2d 3e 61 70 56 61  lue[i] = p->apVa
16ec0 6c 75 65 5b 69 2b 70 2d 3e 6e 43 6f 6c 5d 3b 0a  lue[i+p->nCol];.
16ed0 20 20 20 20 20 20 20 20 20 20 70 2d 3e 61 70 56            p->apV
16ee0 61 6c 75 65 5b 69 2b 70 2d 3e 6e 43 6f 6c 5d 20  alue[i+p->nCol] 
16ef0 3d 20 30 3b 0a 20 20 20 20 20 20 20 20 7d 0a 20  = 0;.        }. 
16f00 20 20 20 20 20 7d 0a 20 20 20 20 7d 0a 20 20 7d       }.    }.  }
16f10 0a 0a 20 20 72 65 74 75 72 6e 20 53 51 4c 49 54  ..  return SQLIT
16f20 45 5f 52 4f 57 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20  E_ROW;.}../*.** 
16f30 41 64 76 61 6e 63 65 20 61 6e 20 69 74 65 72 61  Advance an itera
16f40 74 6f 72 20 63 72 65 61 74 65 64 20 62 79 20 73  tor created by s
16f50 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74 5f  qlite3changeset_
16f60 73 74 61 72 74 28 29 20 74 6f 20 74 68 65 20 6e  start() to the n
16f70 65 78 74 0a 2a 2a 20 63 68 61 6e 67 65 20 69 6e  ext.** change in
16f80 20 74 68 65 20 63 68 61 6e 67 65 73 65 74 2e 20   the changeset. 
16f90 54 68 69 73 20 66 75 6e 63 74 69 6f 6e 20 6d 61  This function ma
16fa0 79 20 72 65 74 75 72 6e 20 53 51 4c 49 54 45 5f  y return SQLITE_
16fb0 52 4f 57 2c 20 53 51 4c 49 54 45 5f 44 4f 4e 45  ROW, SQLITE_DONE
16fc0 0a 2a 2a 20 6f 72 20 53 51 4c 49 54 45 5f 43 4f  .** or SQLITE_CO
16fd0 52 52 55 50 54 2e 0a 2a 2a 0a 2a 2a 20 54 68 69  RRUPT..**.** Thi
16fe0 73 20 66 75 6e 63 74 69 6f 6e 20 6d 61 79 20 6e  s function may n
16ff0 6f 74 20 62 65 20 63 61 6c 6c 65 64 20 6f 6e 20  ot be called on 
17000 69 74 65 72 61 74 6f 72 73 20 70 61 73 73 65 64  iterators passed
17010 20 74 6f 20 61 20 63 6f 6e 66 6c 69 63 74 20 68   to a conflict h
17020 61 6e 64 6c 65 72 0a 2a 2a 20 63 61 6c 6c 62 61  andler.** callba
17030 63 6b 20 62 79 20 63 68 61 6e 67 65 73 65 74 5f  ck by changeset_
17040 61 70 70 6c 79 28 29 2e 0a 2a 2f 0a 69 6e 74 20  apply()..*/.int 
17050 73 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74  sqlite3changeset
17060 5f 6e 65 78 74 28 73 71 6c 69 74 65 33 5f 63 68  _next(sqlite3_ch
17070 61 6e 67 65 73 65 74 5f 69 74 65 72 20 2a 70 29  angeset_iter *p)
17080 7b 0a 20 20 72 65 74 75 72 6e 20 73 65 73 73 69  {.  return sessi
17090 6f 6e 43 68 61 6e 67 65 73 65 74 4e 65 78 74 28  onChangesetNext(
170a0 70 2c 20 30 2c 20 30 29 3b 0a 7d 0a 0a 2f 2a 0a  p, 0, 0);.}../*.
170b0 2a 2a 20 54 68 65 20 66 6f 6c 6c 6f 77 69 6e 67  ** The following
170c0 20 66 75 6e 63 74 69 6f 6e 20 65 78 74 72 61 63   function extrac
170d0 74 73 20 69 6e 66 6f 72 6d 61 74 69 6f 6e 20 6f  ts information o
170e0 6e 20 74 68 65 20 63 75 72 72 65 6e 74 20 63 68  n the current ch
170f0 61 6e 67 65 0a 2a 2a 20 66 72 6f 6d 20 61 20 63  ange.** from a c
17100 68 61 6e 67 65 73 65 74 20 69 74 65 72 61 74 6f  hangeset iterato
17110 72 2e 20 49 74 20 6d 61 79 20 6f 6e 6c 79 20 62  r. It may only b
17120 65 20 63 61 6c 6c 65 64 20 61 66 74 65 72 20 63  e called after c
17130 68 61 6e 67 65 73 65 74 5f 6e 65 78 74 28 29 0a  hangeset_next().
17140 2a 2a 20 68 61 73 20 72 65 74 75 72 6e 65 64 20  ** has returned 
17150 53 51 4c 49 54 45 5f 52 4f 57 2e 0a 2a 2f 0a 69  SQLITE_ROW..*/.i
17160 6e 74 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65  nt sqlite3change
17170 73 65 74 5f 6f 70 28 0a 20 20 73 71 6c 69 74 65  set_op(.  sqlite
17180 33 5f 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72  3_changeset_iter
17190 20 2a 70 49 74 65 72 2c 20 20 2f 2a 20 49 74 65   *pIter,  /* Ite
171a0 72 61 74 6f 72 20 68 61 6e 64 6c 65 20 2a 2f 0a  rator handle */.
171b0 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 2a 70    const char **p
171c0 7a 54 61 62 2c 20 20 20 20 20 20 20 20 20 20 20  zTab,           
171d0 20 20 2f 2a 20 4f 55 54 3a 20 50 6f 69 6e 74 65    /* OUT: Pointe
171e0 72 20 74 6f 20 74 61 62 6c 65 20 6e 61 6d 65 20  r to table name 
171f0 2a 2f 0a 20 20 69 6e 74 20 2a 70 6e 43 6f 6c 2c  */.  int *pnCol,
17200 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
17210 20 20 20 20 20 2f 2a 20 4f 55 54 3a 20 4e 75 6d       /* OUT: Num
17220 62 65 72 20 6f 66 20 63 6f 6c 75 6d 6e 73 20 69  ber of columns i
17230 6e 20 74 61 62 6c 65 20 2a 2f 0a 20 20 69 6e 74  n table */.  int
17240 20 2a 70 4f 70 2c 20 20 20 20 20 20 20 20 20 20   *pOp,          
17250 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
17260 4f 55 54 3a 20 53 51 4c 49 54 45 5f 49 4e 53 45  OUT: SQLITE_INSE
17270 52 54 2c 20 44 45 4c 45 54 45 20 6f 72 20 55 50  RT, DELETE or UP
17280 44 41 54 45 20 2a 2f 0a 20 20 69 6e 74 20 2a 70  DATE */.  int *p
17290 62 49 6e 64 69 72 65 63 74 20 20 20 20 20 20 20  bIndirect       
172a0 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4f 55 54            /* OUT
172b0 3a 20 54 72 75 65 20 69 66 20 63 68 61 6e 67 65  : True if change
172c0 20 69 73 20 69 6e 64 69 72 65 63 74 20 2a 2f 0a   is indirect */.
172d0 29 7b 0a 20 20 2a 70 4f 70 20 3d 20 70 49 74 65  ){.  *pOp = pIte
172e0 72 2d 3e 6f 70 3b 0a 20 20 2a 70 6e 43 6f 6c 20  r->op;.  *pnCol 
172f0 3d 20 70 49 74 65 72 2d 3e 6e 43 6f 6c 3b 0a 20  = pIter->nCol;. 
17300 20 2a 70 7a 54 61 62 20 3d 20 70 49 74 65 72 2d   *pzTab = pIter-
17310 3e 7a 54 61 62 3b 0a 20 20 69 66 28 20 70 62 49  >zTab;.  if( pbI
17320 6e 64 69 72 65 63 74 20 29 20 2a 70 62 49 6e 64  ndirect ) *pbInd
17330 69 72 65 63 74 20 3d 20 70 49 74 65 72 2d 3e 62  irect = pIter->b
17340 49 6e 64 69 72 65 63 74 3b 0a 20 20 72 65 74 75  Indirect;.  retu
17350 72 6e 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a 7d 0a  rn SQLITE_OK;.}.
17360 0a 2f 2a 0a 2a 2a 20 52 65 74 75 72 6e 20 69 6e  ./*.** Return in
17370 66 6f 72 6d 61 74 69 6f 6e 20 72 65 67 61 72 64  formation regard
17380 69 6e 67 20 74 68 65 20 50 52 49 4d 41 52 59 20  ing the PRIMARY 
17390 4b 45 59 20 61 6e 64 20 6e 75 6d 62 65 72 20 6f  KEY and number o
173a0 66 20 63 6f 6c 75 6d 6e 73 20 69 6e 0a 2a 2a 20  f columns in.** 
173b0 74 68 65 20 64 61 74 61 62 61 73 65 20 74 61 62  the database tab
173c0 6c 65 20 61 66 66 65 63 74 65 64 20 62 79 20 74  le affected by t
173d0 68 65 20 63 68 61 6e 67 65 20 74 68 61 74 20 70  he change that p
173e0 49 74 65 72 20 63 75 72 72 65 6e 74 6c 79 20 70  Iter currently p
173f0 6f 69 6e 74 73 0a 2a 2a 20 74 6f 2e 20 54 68 69  oints.** to. Thi
17400 73 20 66 75 6e 63 74 69 6f 6e 20 6d 61 79 20 6f  s function may o
17410 6e 6c 79 20 62 65 20 63 61 6c 6c 65 64 20 61 66  nly be called af
17420 74 65 72 20 63 68 61 6e 67 65 73 65 74 5f 6e 65  ter changeset_ne
17430 78 74 28 29 20 72 65 74 75 72 6e 73 0a 2a 2a 20  xt() returns.** 
17440 53 51 4c 49 54 45 5f 52 4f 57 2e 0a 2a 2f 0a 69  SQLITE_ROW..*/.i
17450 6e 74 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65  nt sqlite3change
17460 73 65 74 5f 70 6b 28 0a 20 20 73 71 6c 69 74 65  set_pk(.  sqlite
17470 33 5f 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72  3_changeset_iter
17480 20 2a 70 49 74 65 72 2c 20 20 2f 2a 20 49 74 65   *pIter,  /* Ite
17490 72 61 74 6f 72 20 6f 62 6a 65 63 74 20 2a 2f 0a  rator object */.
174a0 20 20 75 6e 73 69 67 6e 65 64 20 63 68 61 72 20    unsigned char 
174b0 2a 2a 70 61 62 50 4b 2c 20 20 20 20 20 20 20 20  **pabPK,        
174c0 20 20 2f 2a 20 4f 55 54 3a 20 41 72 72 61 79 20    /* OUT: Array 
174d0 6f 66 20 62 6f 6f 6c 65 61 6e 20 2d 20 74 72 75  of boolean - tru
174e0 65 20 66 6f 72 20 50 4b 20 63 6f 6c 73 20 2a 2f  e for PK cols */
174f0 0a 20 20 69 6e 74 20 2a 70 6e 43 6f 6c 20 20 20  .  int *pnCol   
17500 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
17510 20 20 20 2f 2a 20 4f 55 54 3a 20 4e 75 6d 62 65     /* OUT: Numbe
17520 72 20 6f 66 20 65 6e 74 72 69 65 73 20 69 6e 20  r of entries in 
17530 6f 75 74 70 75 74 20 61 72 72 61 79 20 2a 2f 0a  output array */.
17540 29 7b 0a 20 20 2a 70 61 62 50 4b 20 3d 20 70 49  ){.  *pabPK = pI
17550 74 65 72 2d 3e 61 62 50 4b 3b 0a 20 20 69 66 28  ter->abPK;.  if(
17560 20 70 6e 43 6f 6c 20 29 20 2a 70 6e 43 6f 6c 20   pnCol ) *pnCol 
17570 3d 20 70 49 74 65 72 2d 3e 6e 43 6f 6c 3b 0a 20  = pIter->nCol;. 
17580 20 72 65 74 75 72 6e 20 53 51 4c 49 54 45 5f 4f   return SQLITE_O
17590 4b 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68 69 73  K;.}../*.** This
175a0 20 66 75 6e 63 74 69 6f 6e 20 6d 61 79 20 6f 6e   function may on
175b0 6c 79 20 62 65 20 63 61 6c 6c 65 64 20 77 68 69  ly be called whi
175c0 6c 65 20 74 68 65 20 69 74 65 72 61 74 6f 72 20  le the iterator 
175d0 69 73 20 70 6f 69 6e 74 69 6e 67 20 74 6f 20 61  is pointing to a
175e0 6e 0a 2a 2a 20 53 51 4c 49 54 45 5f 55 50 44 41  n.** SQLITE_UPDA
175f0 54 45 20 6f 72 20 53 51 4c 49 54 45 5f 44 45 4c  TE or SQLITE_DEL
17600 45 54 45 20 63 68 61 6e 67 65 20 28 73 65 65 20  ETE change (see 
17610 73 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74  sqlite3changeset
17620 5f 6f 70 28 29 29 2e 0a 2a 2a 20 4f 74 68 65 72  _op())..** Other
17630 77 69 73 65 2c 20 53 51 4c 49 54 45 5f 4d 49 53  wise, SQLITE_MIS
17640 55 53 45 20 69 73 20 72 65 74 75 72 6e 65 64 2e  USE is returned.
17650 0a 2a 2a 0a 2a 2a 20 49 74 20 73 65 74 73 20 2a  .**.** It sets *
17660 70 70 56 61 6c 75 65 20 74 6f 20 70 6f 69 6e 74  ppValue to point
17670 20 74 6f 20 61 6e 20 73 71 6c 69 74 65 33 5f 76   to an sqlite3_v
17680 61 6c 75 65 20 73 74 72 75 63 74 75 72 65 20 63  alue structure c
17690 6f 6e 74 61 69 6e 69 6e 67 20 74 68 65 0a 2a 2a  ontaining the.**
176a0 20 69 56 61 6c 27 74 68 20 76 61 6c 75 65 20 69   iVal'th value i
176b0 6e 20 74 68 65 20 6f 6c 64 2e 2a 20 72 65 63 6f  n the old.* reco
176c0 72 64 2e 20 4f 72 2c 20 69 66 20 74 68 61 74 20  rd. Or, if that 
176d0 70 61 72 74 69 63 75 6c 61 72 20 76 61 6c 75 65  particular value
176e0 20 69 73 20 6e 6f 74 0a 2a 2a 20 69 6e 63 6c 75   is not.** inclu
176f0 64 65 64 20 69 6e 20 74 68 65 20 72 65 63 6f 72  ded in the recor
17700 64 20 28 62 65 63 61 75 73 65 20 74 68 65 20 63  d (because the c
17710 68 61 6e 67 65 20 69 73 20 61 6e 20 55 50 44 41  hange is an UPDA
17720 54 45 20 61 6e 64 20 74 68 65 20 66 69 65 6c 64  TE and the field
17730 0a 2a 2a 20 77 61 73 20 6e 6f 74 20 6d 6f 64 69  .** was not modi
17740 66 69 65 64 20 61 6e 64 20 69 73 20 6e 6f 74 20  fied and is not 
17750 61 20 50 4b 20 63 6f 6c 75 6d 6e 29 2c 20 73 65  a PK column), se
17760 74 20 2a 70 70 56 61 6c 75 65 20 74 6f 20 4e 55  t *ppValue to NU
17770 4c 4c 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 76 61 6c  LL..**.** If val
17780 75 65 20 69 56 61 6c 20 69 73 20 6f 75 74 2d 6f  ue iVal is out-o
17790 66 2d 72 61 6e 67 65 2c 20 53 51 4c 49 54 45 5f  f-range, SQLITE_
177a0 52 41 4e 47 45 20 69 73 20 72 65 74 75 72 6e 65  RANGE is returne
177b0 64 20 61 6e 64 20 2a 70 70 56 61 6c 75 65 20 69  d and *ppValue i
177c0 73 0a 2a 2a 20 6e 6f 74 20 6d 6f 64 69 66 69 65  s.** not modifie
177d0 64 2e 20 4f 74 68 65 72 77 69 73 65 2c 20 53 51  d. Otherwise, SQ
177e0 4c 49 54 45 5f 4f 4b 2e 0a 2a 2f 0a 69 6e 74 20  LITE_OK..*/.int 
177f0 73 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74  sqlite3changeset
17800 5f 6f 6c 64 28 0a 20 20 73 71 6c 69 74 65 33 5f  _old(.  sqlite3_
17810 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72 20 2a  changeset_iter *
17820 70 49 74 65 72 2c 20 20 2f 2a 20 43 68 61 6e 67  pIter,  /* Chang
17830 65 73 65 74 20 69 74 65 72 61 74 6f 72 20 2a 2f  eset iterator */
17840 0a 20 20 69 6e 74 20 69 56 61 6c 2c 20 20 20 20  .  int iVal,    
17850 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
17860 20 20 20 2f 2a 20 49 6e 64 65 78 20 6f 66 20 6f     /* Index of o
17870 6c 64 2e 2a 20 76 61 6c 75 65 20 74 6f 20 72 65  ld.* value to re
17880 74 72 69 65 76 65 20 2a 2f 0a 20 20 73 71 6c 69  trieve */.  sqli
17890 74 65 33 5f 76 61 6c 75 65 20 2a 2a 70 70 56 61  te3_value **ppVa
178a0 6c 75 65 20 20 20 20 20 20 20 20 20 2f 2a 20 4f  lue         /* O
178b0 55 54 3a 20 4f 6c 64 20 76 61 6c 75 65 20 28 6f  UT: Old value (o
178c0 72 20 4e 55 4c 4c 20 70 6f 69 6e 74 65 72 29 20  r NULL pointer) 
178d0 2a 2f 0a 29 7b 0a 20 20 69 66 28 20 70 49 74 65  */.){.  if( pIte
178e0 72 2d 3e 6f 70 21 3d 53 51 4c 49 54 45 5f 55 50  r->op!=SQLITE_UP
178f0 44 41 54 45 20 26 26 20 70 49 74 65 72 2d 3e 6f  DATE && pIter->o
17900 70 21 3d 53 51 4c 49 54 45 5f 44 45 4c 45 54 45  p!=SQLITE_DELETE
17910 20 29 7b 0a 20 20 20 20 72 65 74 75 72 6e 20 53   ){.    return S
17920 51 4c 49 54 45 5f 4d 49 53 55 53 45 3b 0a 20 20  QLITE_MISUSE;.  
17930 7d 0a 20 20 69 66 28 20 69 56 61 6c 3c 30 20 7c  }.  if( iVal<0 |
17940 7c 20 69 56 61 6c 3e 3d 70 49 74 65 72 2d 3e 6e  | iVal>=pIter->n
17950 43 6f 6c 20 29 7b 0a 20 20 20 20 72 65 74 75 72  Col ){.    retur
17960 6e 20 53 51 4c 49 54 45 5f 52 41 4e 47 45 3b 0a  n SQLITE_RANGE;.
17970 20 20 7d 0a 20 20 2a 70 70 56 61 6c 75 65 20 3d    }.  *ppValue =
17980 20 70 49 74 65 72 2d 3e 61 70 56 61 6c 75 65 5b   pIter->apValue[
17990 69 56 61 6c 5d 3b 0a 20 20 72 65 74 75 72 6e 20  iVal];.  return 
179a0 53 51 4c 49 54 45 5f 4f 4b 3b 0a 7d 0a 0a 2f 2a  SQLITE_OK;.}../*
179b0 0a 2a 2a 20 54 68 69 73 20 66 75 6e 63 74 69 6f  .** This functio
179c0 6e 20 6d 61 79 20 6f 6e 6c 79 20 62 65 20 63 61  n may only be ca
179d0 6c 6c 65 64 20 77 68 69 6c 65 20 74 68 65 20 69  lled while the i
179e0 74 65 72 61 74 6f 72 20 69 73 20 70 6f 69 6e 74  terator is point
179f0 69 6e 67 20 74 6f 20 61 6e 0a 2a 2a 20 53 51 4c  ing to an.** SQL
17a00 49 54 45 5f 55 50 44 41 54 45 20 6f 72 20 53 51  ITE_UPDATE or SQ
17a10 4c 49 54 45 5f 49 4e 53 45 52 54 20 63 68 61 6e  LITE_INSERT chan
17a20 67 65 20 28 73 65 65 20 73 71 6c 69 74 65 33 63  ge (see sqlite3c
17a30 68 61 6e 67 65 73 65 74 5f 6f 70 28 29 29 2e 0a  hangeset_op())..
17a40 2a 2a 20 4f 74 68 65 72 77 69 73 65 2c 20 53 51  ** Otherwise, SQ
17a50 4c 49 54 45 5f 4d 49 53 55 53 45 20 69 73 20 72  LITE_MISUSE is r
17a60 65 74 75 72 6e 65 64 2e 0a 2a 2a 0a 2a 2a 20 49  eturned..**.** I
17a70 74 20 73 65 74 73 20 2a 70 70 56 61 6c 75 65 20  t sets *ppValue 
17a80 74 6f 20 70 6f 69 6e 74 20 74 6f 20 61 6e 20 73  to point to an s
17a90 71 6c 69 74 65 33 5f 76 61 6c 75 65 20 73 74 72  qlite3_value str
17aa0 75 63 74 75 72 65 20 63 6f 6e 74 61 69 6e 69 6e  ucture containin
17ab0 67 20 74 68 65 0a 2a 2a 20 69 56 61 6c 27 74 68  g the.** iVal'th
17ac0 20 76 61 6c 75 65 20 69 6e 20 74 68 65 20 6e 65   value in the ne
17ad0 77 2e 2a 20 72 65 63 6f 72 64 2e 20 4f 72 2c 20  w.* record. Or, 
17ae0 69 66 20 74 68 61 74 20 70 61 72 74 69 63 75 6c  if that particul
17af0 61 72 20 76 61 6c 75 65 20 69 73 20 6e 6f 74 0a  ar value is not.
17b00 2a 2a 20 69 6e 63 6c 75 64 65 64 20 69 6e 20 74  ** included in t
17b10 68 65 20 72 65 63 6f 72 64 20 28 62 65 63 61 75  he record (becau
17b20 73 65 20 74 68 65 20 63 68 61 6e 67 65 20 69 73  se the change is
17b30 20 61 6e 20 55 50 44 41 54 45 20 61 6e 64 20 74   an UPDATE and t
17b40 68 65 20 66 69 65 6c 64 0a 2a 2a 20 77 61 73 20  he field.** was 
17b50 6e 6f 74 20 6d 6f 64 69 66 69 65 64 29 2c 20 73  not modified), s
17b60 65 74 20 2a 70 70 56 61 6c 75 65 20 74 6f 20 4e  et *ppValue to N
17b70 55 4c 4c 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 76 61  ULL..**.** If va
17b80 6c 75 65 20 69 56 61 6c 20 69 73 20 6f 75 74 2d  lue iVal is out-
17b90 6f 66 2d 72 61 6e 67 65 2c 20 53 51 4c 49 54 45  of-range, SQLITE
17ba0 5f 52 41 4e 47 45 20 69 73 20 72 65 74 75 72 6e  _RANGE is return
17bb0 65 64 20 61 6e 64 20 2a 70 70 56 61 6c 75 65 20  ed and *ppValue 
17bc0 69 73 0a 2a 2a 20 6e 6f 74 20 6d 6f 64 69 66 69  is.** not modifi
17bd0 65 64 2e 20 4f 74 68 65 72 77 69 73 65 2c 20 53  ed. Otherwise, S
17be0 51 4c 49 54 45 5f 4f 4b 2e 0a 2a 2f 0a 69 6e 74  QLITE_OK..*/.int
17bf0 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65   sqlite3changese
17c00 74 5f 6e 65 77 28 0a 20 20 73 71 6c 69 74 65 33  t_new(.  sqlite3
17c10 5f 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72 20  _changeset_iter 
17c20 2a 70 49 74 65 72 2c 20 20 2f 2a 20 43 68 61 6e  *pIter,  /* Chan
17c30 67 65 73 65 74 20 69 74 65 72 61 74 6f 72 20 2a  geset iterator *
17c40 2f 0a 20 20 69 6e 74 20 69 56 61 6c 2c 20 20 20  /.  int iVal,   
17c50 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
17c60 20 20 20 20 2f 2a 20 49 6e 64 65 78 20 6f 66 20      /* Index of 
17c70 6e 65 77 2e 2a 20 76 61 6c 75 65 20 74 6f 20 72  new.* value to r
17c80 65 74 72 69 65 76 65 20 2a 2f 0a 20 20 73 71 6c  etrieve */.  sql
17c90 69 74 65 33 5f 76 61 6c 75 65 20 2a 2a 70 70 56  ite3_value **ppV
17ca0 61 6c 75 65 20 20 20 20 20 20 20 20 20 2f 2a 20  alue         /* 
17cb0 4f 55 54 3a 20 4e 65 77 20 76 61 6c 75 65 20 28  OUT: New value (
17cc0 6f 72 20 4e 55 4c 4c 20 70 6f 69 6e 74 65 72 29  or NULL pointer)
17cd0 20 2a 2f 0a 29 7b 0a 20 20 69 66 28 20 70 49 74   */.){.  if( pIt
17ce0 65 72 2d 3e 6f 70 21 3d 53 51 4c 49 54 45 5f 55  er->op!=SQLITE_U
17cf0 50 44 41 54 45 20 26 26 20 70 49 74 65 72 2d 3e  PDATE && pIter->
17d00 6f 70 21 3d 53 51 4c 49 54 45 5f 49 4e 53 45 52  op!=SQLITE_INSER
17d10 54 20 29 7b 0a 20 20 20 20 72 65 74 75 72 6e 20  T ){.    return 
17d20 53 51 4c 49 54 45 5f 4d 49 53 55 53 45 3b 0a 20  SQLITE_MISUSE;. 
17d30 20 7d 0a 20 20 69 66 28 20 69 56 61 6c 3c 30 20   }.  if( iVal<0 
17d40 7c 7c 20 69 56 61 6c 3e 3d 70 49 74 65 72 2d 3e  || iVal>=pIter->
17d50 6e 43 6f 6c 20 29 7b 0a 20 20 20 20 72 65 74 75  nCol ){.    retu
17d60 72 6e 20 53 51 4c 49 54 45 5f 52 41 4e 47 45 3b  rn SQLITE_RANGE;
17d70 0a 20 20 7d 0a 20 20 2a 70 70 56 61 6c 75 65 20  .  }.  *ppValue 
17d80 3d 20 70 49 74 65 72 2d 3e 61 70 56 61 6c 75 65  = pIter->apValue
17d90 5b 70 49 74 65 72 2d 3e 6e 43 6f 6c 2b 69 56 61  [pIter->nCol+iVa
17da0 6c 5d 3b 0a 20 20 72 65 74 75 72 6e 20 53 51 4c  l];.  return SQL
17db0 49 54 45 5f 4f 4b 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a  ITE_OK;.}../*.**
17dc0 20 54 68 65 20 66 6f 6c 6c 6f 77 69 6e 67 20 74   The following t
17dd0 77 6f 20 6d 61 63 72 6f 73 20 61 72 65 20 75 73  wo macros are us
17de0 65 64 20 69 6e 74 65 72 6e 61 6c 6c 79 2e 20 54  ed internally. T
17df0 68 65 79 20 61 72 65 20 73 69 6d 69 6c 61 72 20  hey are similar 
17e00 74 6f 20 74 68 65 0a 2a 2a 20 73 71 6c 69 74 65  to the.** sqlite
17e10 33 63 68 61 6e 67 65 73 65 74 5f 6e 65 77 28 29  3changeset_new()
17e20 20 61 6e 64 20 73 71 6c 69 74 65 33 63 68 61 6e   and sqlite3chan
17e30 67 65 73 65 74 5f 6f 6c 64 28 29 20 66 75 6e 63  geset_old() func
17e40 74 69 6f 6e 73 2c 20 65 78 63 65 70 74 20 74 68  tions, except th
17e50 61 74 0a 2a 2a 20 74 68 65 79 20 6f 6d 69 74 20  at.** they omit 
17e60 61 6c 6c 20 65 72 72 6f 72 20 63 68 65 63 6b 69  all error checki
17e70 6e 67 20 61 6e 64 20 72 65 74 75 72 6e 20 61 20  ng and return a 
17e80 70 6f 69 6e 74 65 72 20 74 6f 20 74 68 65 20 72  pointer to the r
17e90 65 71 75 65 73 74 65 64 20 76 61 6c 75 65 2e 0a  equested value..
17ea0 2a 2f 0a 23 64 65 66 69 6e 65 20 73 65 73 73 69  */.#define sessi
17eb0 6f 6e 43 68 61 6e 67 65 73 65 74 4e 65 77 28 70  onChangesetNew(p
17ec0 49 74 65 72 2c 20 69 56 61 6c 29 20 28 70 49 74  Iter, iVal) (pIt
17ed0 65 72 29 2d 3e 61 70 56 61 6c 75 65 5b 28 70 49  er)->apValue[(pI
17ee0 74 65 72 29 2d 3e 6e 43 6f 6c 2b 28 69 56 61 6c  ter)->nCol+(iVal
17ef0 29 5d 0a 23 64 65 66 69 6e 65 20 73 65 73 73 69  )].#define sessi
17f00 6f 6e 43 68 61 6e 67 65 73 65 74 4f 6c 64 28 70  onChangesetOld(p
17f10 49 74 65 72 2c 20 69 56 61 6c 29 20 28 70 49 74  Iter, iVal) (pIt
17f20 65 72 29 2d 3e 61 70 56 61 6c 75 65 5b 28 69 56  er)->apValue[(iV
17f30 61 6c 29 5d 0a 0a 2f 2a 0a 2a 2a 20 54 68 69 73  al)]../*.** This
17f40 20 66 75 6e 63 74 69 6f 6e 20 6d 61 79 20 6f 6e   function may on
17f50 6c 79 20 62 65 20 63 61 6c 6c 65 64 20 77 69 74  ly be called wit
17f60 68 20 61 20 63 68 61 6e 67 65 73 65 74 20 69 74  h a changeset it
17f70 65 72 61 74 6f 72 20 74 68 61 74 20 68 61 73 20  erator that has 
17f80 62 65 65 6e 0a 2a 2a 20 70 61 73 73 65 64 20 74  been.** passed t
17f90 6f 20 61 6e 20 53 51 4c 49 54 45 5f 43 48 41 4e  o an SQLITE_CHAN
17fa0 47 45 53 45 54 5f 44 41 54 41 20 6f 72 20 53 51  GESET_DATA or SQ
17fb0 4c 49 54 45 5f 43 48 41 4e 47 45 53 45 54 5f 43  LITE_CHANGESET_C
17fc0 4f 4e 46 4c 49 43 54 20 0a 2a 2a 20 63 6f 6e 66  ONFLICT .** conf
17fd0 6c 69 63 74 2d 68 61 6e 64 6c 65 72 20 66 75 6e  lict-handler fun
17fe0 63 74 69 6f 6e 2e 20 4f 74 68 65 72 77 69 73 65  ction. Otherwise
17ff0 2c 20 53 51 4c 49 54 45 5f 4d 49 53 55 53 45 20  , SQLITE_MISUSE 
18000 69 73 20 72 65 74 75 72 6e 65 64 2e 0a 2a 2a 0a  is returned..**.
18010 2a 2a 20 49 66 20 73 75 63 63 65 73 73 66 75 6c  ** If successful
18020 2c 20 2a 70 70 56 61 6c 75 65 20 69 73 20 73 65  , *ppValue is se
18030 74 20 74 6f 20 70 6f 69 6e 74 20 74 6f 20 61 6e  t to point to an
18040 20 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 20 73   sqlite3_value s
18050 74 72 75 63 74 75 72 65 0a 2a 2a 20 63 6f 6e 74  tructure.** cont
18060 61 69 6e 69 6e 67 20 74 68 65 20 69 56 61 6c 27  aining the iVal'
18070 74 68 20 76 61 6c 75 65 20 6f 66 20 74 68 65 20  th value of the 
18080 63 6f 6e 66 6c 69 63 74 69 6e 67 20 72 65 63 6f  conflicting reco
18090 72 64 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 76 61 6c  rd..**.** If val
180a0 75 65 20 69 56 61 6c 20 69 73 20 6f 75 74 2d 6f  ue iVal is out-o
180b0 66 2d 72 61 6e 67 65 20 6f 72 20 73 6f 6d 65 20  f-range or some 
180c0 6f 74 68 65 72 20 65 72 72 6f 72 20 6f 63 63 75  other error occu
180d0 72 73 2c 20 61 6e 20 53 51 4c 69 74 65 20 65 72  rs, an SQLite er
180e0 72 6f 72 0a 2a 2a 20 63 6f 64 65 20 69 73 20 72  ror.** code is r
180f0 65 74 75 72 6e 65 64 2e 20 4f 74 68 65 72 77 69  eturned. Otherwi
18100 73 65 2c 20 53 51 4c 49 54 45 5f 4f 4b 2e 0a 2a  se, SQLITE_OK..*
18110 2f 0a 69 6e 74 20 73 71 6c 69 74 65 33 63 68 61  /.int sqlite3cha
18120 6e 67 65 73 65 74 5f 63 6f 6e 66 6c 69 63 74 28  ngeset_conflict(
18130 0a 20 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67  .  sqlite3_chang
18140 65 73 65 74 5f 69 74 65 72 20 2a 70 49 74 65 72  eset_iter *pIter
18150 2c 20 20 2f 2a 20 43 68 61 6e 67 65 73 65 74 20  ,  /* Changeset 
18160 69 74 65 72 61 74 6f 72 20 2a 2f 0a 20 20 69 6e  iterator */.  in
18170 74 20 69 56 61 6c 2c 20 20 20 20 20 20 20 20 20  t iVal,         
18180 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
18190 20 49 6e 64 65 78 20 6f 66 20 63 6f 6e 66 6c 69   Index of confli
181a0 63 74 20 72 65 63 6f 72 64 20 76 61 6c 75 65 20  ct record value 
181b0 74 6f 20 66 65 74 63 68 20 2a 2f 0a 20 20 73 71  to fetch */.  sq
181c0 6c 69 74 65 33 5f 76 61 6c 75 65 20 2a 2a 70 70  lite3_value **pp
181d0 56 61 6c 75 65 20 20 20 20 20 20 20 20 20 2f 2a  Value         /*
181e0 20 4f 55 54 3a 20 56 61 6c 75 65 20 66 72 6f 6d   OUT: Value from
181f0 20 63 6f 6e 66 6c 69 63 74 69 6e 67 20 72 6f 77   conflicting row
18200 20 2a 2f 0a 29 7b 0a 20 20 69 66 28 20 21 70 49   */.){.  if( !pI
18210 74 65 72 2d 3e 70 43 6f 6e 66 6c 69 63 74 20 29  ter->pConflict )
18220 7b 0a 20 20 20 20 72 65 74 75 72 6e 20 53 51 4c  {.    return SQL
18230 49 54 45 5f 4d 49 53 55 53 45 3b 0a 20 20 7d 0a  ITE_MISUSE;.  }.
18240 20 20 69 66 28 20 69 56 61 6c 3c 30 20 7c 7c 20    if( iVal<0 || 
18250 69 56 61 6c 3e 3d 70 49 74 65 72 2d 3e 6e 43 6f  iVal>=pIter->nCo
18260 6c 20 29 7b 0a 20 20 20 20 72 65 74 75 72 6e 20  l ){.    return 
18270 53 51 4c 49 54 45 5f 52 41 4e 47 45 3b 0a 20 20  SQLITE_RANGE;.  
18280 7d 0a 20 20 2a 70 70 56 61 6c 75 65 20 3d 20 73  }.  *ppValue = s
18290 71 6c 69 74 65 33 5f 63 6f 6c 75 6d 6e 5f 76 61  qlite3_column_va
182a0 6c 75 65 28 70 49 74 65 72 2d 3e 70 43 6f 6e 66  lue(pIter->pConf
182b0 6c 69 63 74 2c 20 69 56 61 6c 29 3b 0a 20 20 72  lict, iVal);.  r
182c0 65 74 75 72 6e 20 53 51 4c 49 54 45 5f 4f 4b 3b  eturn SQLITE_OK;
182d0 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54 68 69 73 20 66  .}../*.** This f
182e0 75 6e 63 74 69 6f 6e 20 6d 61 79 20 6f 6e 6c 79  unction may only
182f0 20 62 65 20 63 61 6c 6c 65 64 20 77 69 74 68 20   be called with 
18300 61 6e 20 69 74 65 72 61 74 6f 72 20 70 61 73 73  an iterator pass
18310 65 64 20 74 6f 20 61 6e 0a 2a 2a 20 53 51 4c 49  ed to an.** SQLI
18320 54 45 5f 43 48 41 4e 47 45 53 45 54 5f 46 4f 52  TE_CHANGESET_FOR
18330 45 49 47 4e 5f 4b 45 59 20 63 6f 6e 66 6c 69 63  EIGN_KEY conflic
18340 74 20 68 61 6e 64 6c 65 72 20 63 61 6c 6c 62 61  t handler callba
18350 63 6b 2e 20 49 6e 20 74 68 69 73 20 63 61 73 65  ck. In this case
18360 0a 2a 2a 20 69 74 20 73 65 74 73 20 74 68 65 20  .** it sets the 
18370 6f 75 74 70 75 74 20 76 61 72 69 61 62 6c 65 20  output variable 
18380 74 6f 20 74 68 65 20 74 6f 74 61 6c 20 6e 75 6d  to the total num
18390 62 65 72 20 6f 66 20 6b 6e 6f 77 6e 20 66 6f 72  ber of known for
183a0 65 69 67 6e 20 6b 65 79 0a 2a 2a 20 76 69 6f 6c  eign key.** viol
183b0 61 74 69 6f 6e 73 20 69 6e 20 74 68 65 20 64 65  ations in the de
183c0 73 74 69 6e 61 74 69 6f 6e 20 64 61 74 61 62 61  stination databa
183d0 73 65 20 61 6e 64 20 72 65 74 75 72 6e 73 20 53  se and returns S
183e0 51 4c 49 54 45 5f 4f 4b 2e 0a 2a 2a 0a 2a 2a 20  QLITE_OK..**.** 
183f0 49 6e 20 61 6c 6c 20 6f 74 68 65 72 20 63 61 73  In all other cas
18400 65 73 20 74 68 69 73 20 66 75 6e 63 74 69 6f 6e  es this function
18410 20 72 65 74 75 72 6e 73 20 53 51 4c 49 54 45 5f   returns SQLITE_
18420 4d 49 53 55 53 45 2e 0a 2a 2f 0a 69 6e 74 20 73  MISUSE..*/.int s
18430 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74 5f  qlite3changeset_
18440 66 6b 5f 63 6f 6e 66 6c 69 63 74 73 28 0a 20 20  fk_conflicts(.  
18450 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 73 65  sqlite3_changese
18460 74 5f 69 74 65 72 20 2a 70 49 74 65 72 2c 20 20  t_iter *pIter,  
18470 2f 2a 20 43 68 61 6e 67 65 73 65 74 20 69 74 65  /* Changeset ite
18480 72 61 74 6f 72 20 2a 2f 0a 20 20 69 6e 74 20 2a  rator */.  int *
18490 70 6e 4f 75 74 20 20 20 20 20 20 20 20 20 20 20  pnOut           
184a0 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4f 55             /* OU
184b0 54 3a 20 4e 75 6d 62 65 72 20 6f 66 20 46 4b 20  T: Number of FK 
184c0 76 69 6f 6c 61 74 69 6f 6e 73 20 2a 2f 0a 29 7b  violations */.){
184d0 0a 20 20 69 66 28 20 70 49 74 65 72 2d 3e 70 43  .  if( pIter->pC
184e0 6f 6e 66 6c 69 63 74 20 7c 7c 20 70 49 74 65 72  onflict || pIter
184f0 2d 3e 61 70 56 61 6c 75 65 20 29 7b 0a 20 20 20  ->apValue ){.   
18500 20 72 65 74 75 72 6e 20 53 51 4c 49 54 45 5f 4d   return SQLITE_M
18510 49 53 55 53 45 3b 0a 20 20 7d 0a 20 20 2a 70 6e  ISUSE;.  }.  *pn
18520 4f 75 74 20 3d 20 70 49 74 65 72 2d 3e 6e 43 6f  Out = pIter->nCo
18530 6c 3b 0a 20 20 72 65 74 75 72 6e 20 53 51 4c 49  l;.  return SQLI
18540 54 45 5f 4f 4b 3b 0a 7d 0a 0a 0a 2f 2a 0a 2a 2a  TE_OK;.}.../*.**
18550 20 46 69 6e 61 6c 69 7a 65 20 61 6e 20 69 74 65   Finalize an ite
18560 72 61 74 6f 72 20 61 6c 6c 6f 63 61 74 65 64 20  rator allocated 
18570 77 69 74 68 20 73 71 6c 69 74 65 33 63 68 61 6e  with sqlite3chan
18580 67 65 73 65 74 5f 73 74 61 72 74 28 29 2e 0a 2a  geset_start()..*
18590 2a 0a 2a 2a 20 54 68 69 73 20 66 75 6e 63 74 69  *.** This functi
185a0 6f 6e 20 6d 61 79 20 6e 6f 74 20 62 65 20 63 61  on may not be ca
185b0 6c 6c 65 64 20 6f 6e 20 69 74 65 72 61 74 6f 72  lled on iterator
185c0 73 20 70 61 73 73 65 64 20 74 6f 20 61 20 63 6f  s passed to a co
185d0 6e 66 6c 69 63 74 20 68 61 6e 64 6c 65 72 0a 2a  nflict handler.*
185e0 2a 20 63 61 6c 6c 62 61 63 6b 20 62 79 20 63 68  * callback by ch
185f0 61 6e 67 65 73 65 74 5f 61 70 70 6c 79 28 29 2e  angeset_apply().
18600 0a 2a 2f 0a 69 6e 74 20 73 71 6c 69 74 65 33 63  .*/.int sqlite3c
18610 68 61 6e 67 65 73 65 74 5f 66 69 6e 61 6c 69 7a  hangeset_finaliz
18620 65 28 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65  e(sqlite3_change
18630 73 65 74 5f 69 74 65 72 20 2a 70 29 7b 0a 20 20  set_iter *p){.  
18640 69 6e 74 20 72 63 20 3d 20 53 51 4c 49 54 45 5f  int rc = SQLITE_
18650 4f 4b 3b 0a 20 20 69 66 28 20 70 20 29 7b 0a 20  OK;.  if( p ){. 
18660 20 20 20 69 6e 74 20 69 3b 20 20 20 20 20 20 20     int i;       
18670 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
18680 20 2f 2a 20 55 73 65 64 20 74 6f 20 69 74 65 72   /* Used to iter
18690 61 74 65 20 74 68 72 6f 75 67 68 20 70 2d 3e 61  ate through p->a
186a0 70 56 61 6c 75 65 5b 5d 20 2a 2f 0a 20 20 20 20  pValue[] */.    
186b0 72 63 20 3d 20 70 2d 3e 72 63 3b 0a 20 20 20 20  rc = p->rc;.    
186c0 69 66 28 20 70 2d 3e 61 70 56 61 6c 75 65 20 29  if( p->apValue )
186d0 7b 0a 20 20 20 20 20 20 66 6f 72 28 69 3d 30 3b  {.      for(i=0;
186e0 20 69 3c 70 2d 3e 6e 43 6f 6c 2a 32 3b 20 69 2b   i<p->nCol*2; i+
186f0 2b 29 20 73 71 6c 69 74 65 33 56 61 6c 75 65 46  +) sqlite3ValueF
18700 72 65 65 28 70 2d 3e 61 70 56 61 6c 75 65 5b 69  ree(p->apValue[i
18710 5d 29 3b 0a 20 20 20 20 7d 0a 20 20 20 20 73 71  ]);.    }.    sq
18720 6c 69 74 65 33 5f 66 72 65 65 28 70 2d 3e 74 62  lite3_free(p->tb
18730 6c 68 64 72 2e 61 42 75 66 29 3b 0a 20 20 20 20  lhdr.aBuf);.    
18740 73 71 6c 69 74 65 33 5f 66 72 65 65 28 70 2d 3e  sqlite3_free(p->
18750 69 6e 2e 62 75 66 2e 61 42 75 66 29 3b 0a 20 20  in.buf.aBuf);.  
18760 20 20 73 71 6c 69 74 65 33 5f 66 72 65 65 28 70    sqlite3_free(p
18770 29 3b 0a 20 20 7d 0a 20 20 72 65 74 75 72 6e 20  );.  }.  return 
18780 72 63 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 69 6e  rc;.}..static in
18790 74 20 73 65 73 73 69 6f 6e 43 68 61 6e 67 65 73  t sessionChanges
187a0 65 74 49 6e 76 65 72 74 28 0a 20 20 53 65 73 73  etInvert(.  Sess
187b0 69 6f 6e 49 6e 70 75 74 20 2a 70 49 6e 70 75 74  ionInput *pInput
187c0 2c 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 49  ,           /* I
187d0 6e 70 75 74 20 63 68 61 6e 67 65 73 65 74 20 2a  nput changeset *
187e0 2f 0a 20 20 69 6e 74 20 28 2a 78 4f 75 74 70 75  /.  int (*xOutpu
187f0 74 29 28 76 6f 69 64 20 2a 70 4f 75 74 2c 20 63  t)(void *pOut, c
18800 6f 6e 73 74 20 76 6f 69 64 20 2a 70 44 61 74 61  onst void *pData
18810 2c 20 69 6e 74 20 6e 44 61 74 61 29 2c 0a 20 20  , int nData),.  
18820 76 6f 69 64 20 2a 70 4f 75 74 2c 0a 20 20 69 6e  void *pOut,.  in
18830 74 20 2a 70 6e 49 6e 76 65 72 74 65 64 2c 20 20  t *pnInverted,  
18840 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
18850 20 4f 55 54 3a 20 4e 75 6d 62 65 72 20 6f 66 20   OUT: Number of 
18860 62 79 74 65 73 20 69 6e 20 6f 75 74 70 75 74 20  bytes in output 
18870 63 68 61 6e 67 65 73 65 74 20 2a 2f 0a 20 20 76  changeset */.  v
18880 6f 69 64 20 2a 2a 70 70 49 6e 76 65 72 74 65 64  oid **ppInverted
18890 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
188a0 2a 20 4f 55 54 3a 20 49 6e 76 65 72 73 65 20 6f  * OUT: Inverse o
188b0 66 20 70 43 68 61 6e 67 65 73 65 74 20 2a 2f 0a  f pChangeset */.
188c0 29 7b 0a 20 20 69 6e 74 20 72 63 20 3d 20 53 51  ){.  int rc = SQ
188d0 4c 49 54 45 5f 4f 4b 3b 20 20 20 20 20 20 20 20  LITE_OK;        
188e0 20 20 20 20 20 2f 2a 20 52 65 74 75 72 6e 20 76       /* Return v
188f0 61 6c 75 65 20 2a 2f 0a 20 20 53 65 73 73 69 6f  alue */.  Sessio
18900 6e 42 75 66 66 65 72 20 73 4f 75 74 3b 20 20 20  nBuffer sOut;   
18910 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4f 75 74            /* Out
18920 70 75 74 20 62 75 66 66 65 72 20 2a 2f 0a 20 20  put buffer */.  
18930 69 6e 74 20 6e 43 6f 6c 20 3d 20 30 3b 20 20 20  int nCol = 0;   
18940 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
18950 2f 2a 20 4e 75 6d 62 65 72 20 6f 66 20 63 6f 6c  /* Number of col
18960 73 20 69 6e 20 63 75 72 72 65 6e 74 20 74 61 62  s in current tab
18970 6c 65 20 2a 2f 0a 20 20 75 38 20 2a 61 62 50 4b  le */.  u8 *abPK
18980 20 3d 20 30 3b 20 20 20 20 20 20 20 20 20 20 20   = 0;           
18990 20 20 20 20 20 20 20 20 2f 2a 20 50 4b 20 61 72          /* PK ar
189a0 72 61 79 20 66 6f 72 20 63 75 72 72 65 6e 74 20  ray for current 
189b0 74 61 62 6c 65 20 2a 2f 0a 20 20 73 71 6c 69 74  table */.  sqlit
189c0 65 33 5f 76 61 6c 75 65 20 2a 2a 61 70 56 61 6c  e3_value **apVal
189d0 20 3d 20 30 3b 20 20 20 20 20 20 2f 2a 20 53 70   = 0;      /* Sp
189e0 61 63 65 20 66 6f 72 20 76 61 6c 75 65 73 20 66  ace for values f
189f0 6f 72 20 55 50 44 41 54 45 20 69 6e 76 65 72 73  or UPDATE invers
18a00 69 6f 6e 20 2a 2f 0a 20 20 53 65 73 73 69 6f 6e  ion */.  Session
18a10 42 75 66 66 65 72 20 73 50 4b 20 3d 20 7b 30 2c  Buffer sPK = {0,
18a20 20 30 2c 20 30 7d 3b 20 20 2f 2a 20 50 4b 20 61   0, 0};  /* PK a
18a30 72 72 61 79 20 66 6f 72 20 63 75 72 72 65 6e 74  rray for current
18a40 20 74 61 62 6c 65 20 2a 2f 0a 0a 20 20 2f 2a 20   table */..  /* 
18a50 49 6e 69 74 69 61 6c 69 7a 65 20 74 68 65 20 6f  Initialize the o
18a60 75 74 70 75 74 20 62 75 66 66 65 72 20 2a 2f 0a  utput buffer */.
18a70 20 20 6d 65 6d 73 65 74 28 26 73 4f 75 74 2c 20    memset(&sOut, 
18a80 30 2c 20 73 69 7a 65 6f 66 28 53 65 73 73 69 6f  0, sizeof(Sessio
18a90 6e 42 75 66 66 65 72 29 29 3b 0a 0a 20 20 2f 2a  nBuffer));..  /*
18aa0 20 5a 65 72 6f 20 74 68 65 20 6f 75 74 70 75 74   Zero the output
18ab0 20 76 61 72 69 61 62 6c 65 73 20 69 6e 20 63 61   variables in ca
18ac0 73 65 20 61 6e 20 65 72 72 6f 72 20 6f 63 63 75  se an error occu
18ad0 72 73 2e 20 2a 2f 0a 20 20 69 66 28 20 70 70 49  rs. */.  if( ppI
18ae0 6e 76 65 72 74 65 64 20 29 7b 0a 20 20 20 20 2a  nverted ){.    *
18af0 70 70 49 6e 76 65 72 74 65 64 20 3d 20 30 3b 0a  ppInverted = 0;.
18b00 20 20 20 20 2a 70 6e 49 6e 76 65 72 74 65 64 20      *pnInverted 
18b10 3d 20 30 3b 0a 20 20 7d 0a 0a 20 20 77 68 69 6c  = 0;.  }..  whil
18b20 65 28 20 31 20 29 7b 0a 20 20 20 20 75 38 20 65  e( 1 ){.    u8 e
18b30 54 79 70 65 3b 0a 0a 20 20 20 20 2f 2a 20 54 65  Type;..    /* Te
18b40 73 74 20 66 6f 72 20 45 4f 46 2e 20 2a 2f 0a 20  st for EOF. */. 
18b50 20 20 20 69 66 28 20 28 72 63 20 3d 20 73 65 73     if( (rc = ses
18b60 73 69 6f 6e 49 6e 70 75 74 42 75 66 66 65 72 28  sionInputBuffer(
18b70 70 49 6e 70 75 74 2c 20 32 29 29 20 29 20 67 6f  pInput, 2)) ) go
18b80 74 6f 20 66 69 6e 69 73 68 65 64 5f 69 6e 76 65  to finished_inve
18b90 72 74 3b 0a 20 20 20 20 69 66 28 20 70 49 6e 70  rt;.    if( pInp
18ba0 75 74 2d 3e 69 4e 65 78 74 3e 3d 70 49 6e 70 75  ut->iNext>=pInpu
18bb0 74 2d 3e 6e 44 61 74 61 20 29 20 62 72 65 61 6b  t->nData ) break
18bc0 3b 0a 20 20 20 20 65 54 79 70 65 20 3d 20 70 49  ;.    eType = pI
18bd0 6e 70 75 74 2d 3e 61 44 61 74 61 5b 70 49 6e 70  nput->aData[pInp
18be0 75 74 2d 3e 69 4e 65 78 74 5d 3b 0a 0a 20 20 20  ut->iNext];..   
18bf0 20 73 77 69 74 63 68 28 20 65 54 79 70 65 20 29   switch( eType )
18c00 7b 0a 20 20 20 20 20 20 63 61 73 65 20 27 54 27  {.      case 'T'
18c10 3a 20 7b 0a 20 20 20 20 20 20 20 20 2f 2a 20 41  : {.        /* A
18c20 20 27 74 61 62 6c 65 27 20 72 65 63 6f 72 64 20   'table' record 
18c30 63 6f 6e 73 69 73 74 73 20 6f 66 3a 0a 20 20 20  consists of:.   
18c40 20 20 20 20 20 2a 2a 0a 20 20 20 20 20 20 20 20       **.        
18c50 2a 2a 20 20 20 2a 20 41 20 63 6f 6e 73 74 61 6e  **   * A constan
18c60 74 20 27 54 27 20 63 68 61 72 61 63 74 65 72 2c  t 'T' character,
18c70 0a 20 20 20 20 20 20 20 20 2a 2a 20 20 20 2a 20  .        **   * 
18c80 4e 75 6d 62 65 72 20 6f 66 20 63 6f 6c 75 6d 6e  Number of column
18c90 73 20 69 6e 20 73 61 69 64 20 74 61 62 6c 65 20  s in said table 
18ca0 28 61 20 76 61 72 69 6e 74 29 2c 0a 20 20 20 20  (a varint),.    
18cb0 20 20 20 20 2a 2a 20 20 20 2a 20 41 6e 20 61 72      **   * An ar
18cc0 72 61 79 20 6f 66 20 6e 43 6f 6c 20 62 79 74 65  ray of nCol byte
18cd0 73 20 28 73 50 4b 29 2c 0a 20 20 20 20 20 20 20  s (sPK),.       
18ce0 20 2a 2a 20 20 20 2a 20 41 20 6e 75 6c 2d 74 65   **   * A nul-te
18cf0 72 6d 69 6e 61 74 65 64 20 74 61 62 6c 65 20 6e  rminated table n
18d00 61 6d 65 2e 0a 20 20 20 20 20 20 20 20 2a 2f 0a  ame..        */.
18d10 20 20 20 20 20 20 20 20 69 6e 74 20 6e 42 79 74          int nByt
18d20 65 3b 0a 20 20 20 20 20 20 20 20 69 6e 74 20 6e  e;.        int n
18d30 56 61 72 3b 0a 20 20 20 20 20 20 20 20 70 49 6e  Var;.        pIn
18d40 70 75 74 2d 3e 69 4e 65 78 74 2b 2b 3b 0a 20 20  put->iNext++;.  
18d50 20 20 20 20 20 20 69 66 28 20 28 72 63 20 3d 20        if( (rc = 
18d60 73 65 73 73 69 6f 6e 43 68 61 6e 67 65 73 65 74  sessionChangeset
18d70 42 75 66 66 65 72 54 62 6c 68 64 72 28 70 49 6e  BufferTblhdr(pIn
18d80 70 75 74 2c 20 26 6e 42 79 74 65 29 29 20 29 7b  put, &nByte)) ){
18d90 0a 20 20 20 20 20 20 20 20 20 20 67 6f 74 6f 20  .          goto 
18da0 66 69 6e 69 73 68 65 64 5f 69 6e 76 65 72 74 3b  finished_invert;
18db0 0a 20 20 20 20 20 20 20 20 7d 0a 20 20 20 20 20  .        }.     
18dc0 20 20 20 6e 56 61 72 20 3d 20 73 65 73 73 69 6f     nVar = sessio
18dd0 6e 56 61 72 69 6e 74 47 65 74 28 26 70 49 6e 70  nVarintGet(&pInp
18de0 75 74 2d 3e 61 44 61 74 61 5b 70 49 6e 70 75 74  ut->aData[pInput
18df0 2d 3e 69 4e 65 78 74 5d 2c 20 26 6e 43 6f 6c 29  ->iNext], &nCol)
18e00 3b 0a 20 20 20 20 20 20 20 20 73 50 4b 2e 6e 42  ;.        sPK.nB
18e10 75 66 20 3d 20 30 3b 0a 20 20 20 20 20 20 20 20  uf = 0;.        
18e20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 42 6c 6f  sessionAppendBlo
18e30 62 28 26 73 50 4b 2c 20 26 70 49 6e 70 75 74 2d  b(&sPK, &pInput-
18e40 3e 61 44 61 74 61 5b 70 49 6e 70 75 74 2d 3e 69  >aData[pInput->i
18e50 4e 65 78 74 2b 6e 56 61 72 5d 2c 20 6e 43 6f 6c  Next+nVar], nCol
18e60 2c 20 26 72 63 29 3b 0a 20 20 20 20 20 20 20 20  , &rc);.        
18e70 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 42 79 74  sessionAppendByt
18e80 65 28 26 73 4f 75 74 2c 20 65 54 79 70 65 2c 20  e(&sOut, eType, 
18e90 26 72 63 29 3b 0a 20 20 20 20 20 20 20 20 73 65  &rc);.        se
18ea0 73 73 69 6f 6e 41 70 70 65 6e 64 42 6c 6f 62 28  ssionAppendBlob(
18eb0 26 73 4f 75 74 2c 20 26 70 49 6e 70 75 74 2d 3e  &sOut, &pInput->
18ec0 61 44 61 74 61 5b 70 49 6e 70 75 74 2d 3e 69 4e  aData[pInput->iN
18ed0 65 78 74 5d 2c 20 6e 42 79 74 65 2c 20 26 72 63  ext], nByte, &rc
18ee0 29 3b 0a 20 20 20 20 20 20 20 20 69 66 28 20 72  );.        if( r
18ef0 63 20 29 20 67 6f 74 6f 20 66 69 6e 69 73 68 65  c ) goto finishe
18f00 64 5f 69 6e 76 65 72 74 3b 0a 0a 20 20 20 20 20  d_invert;..     
18f10 20 20 20 70 49 6e 70 75 74 2d 3e 69 4e 65 78 74     pInput->iNext
18f20 20 2b 3d 20 6e 42 79 74 65 3b 0a 20 20 20 20 20   += nByte;.     
18f30 20 20 20 73 71 6c 69 74 65 33 5f 66 72 65 65 28     sqlite3_free(
18f40 61 70 56 61 6c 29 3b 0a 20 20 20 20 20 20 20 20  apVal);.        
18f50 61 70 56 61 6c 20 3d 20 30 3b 0a 20 20 20 20 20  apVal = 0;.     
18f60 20 20 20 61 62 50 4b 20 3d 20 73 50 4b 2e 61 42     abPK = sPK.aB
18f70 75 66 3b 0a 20 20 20 20 20 20 20 20 62 72 65 61  uf;.        brea
18f80 6b 3b 0a 20 20 20 20 20 20 7d 0a 0a 20 20 20 20  k;.      }..    
18f90 20 20 63 61 73 65 20 53 51 4c 49 54 45 5f 49 4e    case SQLITE_IN
18fa0 53 45 52 54 3a 0a 20 20 20 20 20 20 63 61 73 65  SERT:.      case
18fb0 20 53 51 4c 49 54 45 5f 44 45 4c 45 54 45 3a 20   SQLITE_DELETE: 
18fc0 7b 0a 20 20 20 20 20 20 20 20 69 6e 74 20 6e 42  {.        int nB
18fd0 79 74 65 3b 0a 20 20 20 20 20 20 20 20 69 6e 74  yte;.        int
18fe0 20 62 49 6e 64 69 72 65 63 74 20 3d 20 70 49 6e   bIndirect = pIn
18ff0 70 75 74 2d 3e 61 44 61 74 61 5b 70 49 6e 70 75  put->aData[pInpu
19000 74 2d 3e 69 4e 65 78 74 2b 31 5d 3b 0a 20 20 20  t->iNext+1];.   
19010 20 20 20 20 20 69 6e 74 20 65 54 79 70 65 32 20       int eType2 
19020 3d 20 28 65 54 79 70 65 3d 3d 53 51 4c 49 54 45  = (eType==SQLITE
19030 5f 44 45 4c 45 54 45 20 3f 20 53 51 4c 49 54 45  _DELETE ? SQLITE
19040 5f 49 4e 53 45 52 54 20 3a 20 53 51 4c 49 54 45  _INSERT : SQLITE
19050 5f 44 45 4c 45 54 45 29 3b 0a 20 20 20 20 20 20  _DELETE);.      
19060 20 20 70 49 6e 70 75 74 2d 3e 69 4e 65 78 74 20    pInput->iNext 
19070 2b 3d 20 32 3b 0a 20 20 20 20 20 20 20 20 61 73  += 2;.        as
19080 73 65 72 74 28 20 72 63 3d 3d 53 51 4c 49 54 45  sert( rc==SQLITE
19090 5f 4f 4b 20 29 3b 0a 20 20 20 20 20 20 20 20 72  _OK );.        r
190a0 63 20 3d 20 73 65 73 73 69 6f 6e 43 68 61 6e 67  c = sessionChang
190b0 65 73 65 74 42 75 66 66 65 72 52 65 63 6f 72 64  esetBufferRecord
190c0 28 70 49 6e 70 75 74 2c 20 6e 43 6f 6c 2c 20 26  (pInput, nCol, &
190d0 6e 42 79 74 65 29 3b 0a 20 20 20 20 20 20 20 20  nByte);.        
190e0 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 42 79 74  sessionAppendByt
190f0 65 28 26 73 4f 75 74 2c 20 65 54 79 70 65 32 2c  e(&sOut, eType2,
19100 20 26 72 63 29 3b 0a 20 20 20 20 20 20 20 20 73   &rc);.        s
19110 65 73 73 69 6f 6e 41 70 70 65 6e 64 42 79 74 65  essionAppendByte
19120 28 26 73 4f 75 74 2c 20 62 49 6e 64 69 72 65 63  (&sOut, bIndirec
19130 74 2c 20 26 72 63 29 3b 0a 20 20 20 20 20 20 20  t, &rc);.       
19140 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 42 6c   sessionAppendBl
19150 6f 62 28 26 73 4f 75 74 2c 20 26 70 49 6e 70 75  ob(&sOut, &pInpu
19160 74 2d 3e 61 44 61 74 61 5b 70 49 6e 70 75 74 2d  t->aData[pInput-
19170 3e 69 4e 65 78 74 5d 2c 20 6e 42 79 74 65 2c 20  >iNext], nByte, 
19180 26 72 63 29 3b 0a 20 20 20 20 20 20 20 20 70 49  &rc);.        pI
19190 6e 70 75 74 2d 3e 69 4e 65 78 74 20 2b 3d 20 6e  nput->iNext += n
191a0 42 79 74 65 3b 0a 20 20 20 20 20 20 20 20 69 66  Byte;.        if
191b0 28 20 72 63 20 29 20 67 6f 74 6f 20 66 69 6e 69  ( rc ) goto fini
191c0 73 68 65 64 5f 69 6e 76 65 72 74 3b 0a 20 20 20  shed_invert;.   
191d0 20 20 20 20 20 62 72 65 61 6b 3b 0a 20 20 20 20       break;.    
191e0 20 20 7d 0a 0a 20 20 20 20 20 20 63 61 73 65 20    }..      case 
191f0 53 51 4c 49 54 45 5f 55 50 44 41 54 45 3a 20 7b  SQLITE_UPDATE: {
19200 0a 20 20 20 20 20 20 20 20 69 6e 74 20 69 43 6f  .        int iCo
19210 6c 3b 0a 0a 20 20 20 20 20 20 20 20 69 66 28 20  l;..        if( 
19220 30 3d 3d 61 70 56 61 6c 20 29 7b 0a 20 20 20 20  0==apVal ){.    
19230 20 20 20 20 20 20 61 70 56 61 6c 20 3d 20 28 73        apVal = (s
19240 71 6c 69 74 65 33 5f 76 61 6c 75 65 20 2a 2a 29  qlite3_value **)
19250 73 71 6c 69 74 65 33 5f 6d 61 6c 6c 6f 63 28 73  sqlite3_malloc(s
19260 69 7a 65 6f 66 28 61 70 56 61 6c 5b 30 5d 29 2a  izeof(apVal[0])*
19270 6e 43 6f 6c 2a 32 29 3b 0a 20 20 20 20 20 20 20  nCol*2);.       
19280 20 20 20 69 66 28 20 30 3d 3d 61 70 56 61 6c 20     if( 0==apVal 
19290 29 7b 0a 20 20 20 20 20 20 20 20 20 20 20 20 72  ){.            r
192a0 63 20 3d 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d  c = SQLITE_NOMEM
192b0 3b 0a 20 20 20 20 20 20 20 20 20 20 20 20 67 6f  ;.            go
192c0 74 6f 20 66 69 6e 69 73 68 65 64 5f 69 6e 76 65  to finished_inve
192d0 72 74 3b 0a 20 20 20 20 20 20 20 20 20 20 7d 0a  rt;.          }.
192e0 20 20 20 20 20 20 20 20 20 20 6d 65 6d 73 65 74            memset
192f0 28 61 70 56 61 6c 2c 20 30 2c 20 73 69 7a 65 6f  (apVal, 0, sizeo
19300 66 28 61 70 56 61 6c 5b 30 5d 29 2a 6e 43 6f 6c  f(apVal[0])*nCol
19310 2a 32 29 3b 0a 20 20 20 20 20 20 20 20 7d 0a 0a  *2);.        }..
19320 20 20 20 20 20 20 20 20 2f 2a 20 57 72 69 74 65          /* Write
19330 20 74 68 65 20 68 65 61 64 65 72 20 66 6f 72 20   the header for 
19340 74 68 65 20 6e 65 77 20 55 50 44 41 54 45 20 63  the new UPDATE c
19350 68 61 6e 67 65 2e 20 53 61 6d 65 20 61 73 20 74  hange. Same as t
19360 68 65 20 6f 72 69 67 69 6e 61 6c 2e 20 2a 2f 0a  he original. */.
19370 20 20 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41          sessionA
19380 70 70 65 6e 64 42 79 74 65 28 26 73 4f 75 74 2c  ppendByte(&sOut,
19390 20 65 54 79 70 65 2c 20 26 72 63 29 3b 0a 20 20   eType, &rc);.  
193a0 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70 70        sessionApp
193b0 65 6e 64 42 79 74 65 28 26 73 4f 75 74 2c 20 70  endByte(&sOut, p
193c0 49 6e 70 75 74 2d 3e 61 44 61 74 61 5b 70 49 6e  Input->aData[pIn
193d0 70 75 74 2d 3e 69 4e 65 78 74 2b 31 5d 2c 20 26  put->iNext+1], &
193e0 72 63 29 3b 0a 0a 20 20 20 20 20 20 20 20 2f 2a  rc);..        /*
193f0 20 52 65 61 64 20 74 68 65 20 6f 6c 64 2e 2a 20   Read the old.* 
19400 61 6e 64 20 6e 65 77 2e 2a 20 72 65 63 6f 72 64  and new.* record
19410 73 20 66 6f 72 20 74 68 65 20 75 70 64 61 74 65  s for the update
19420 20 63 68 61 6e 67 65 2e 20 2a 2f 0a 20 20 20 20   change. */.    
19430 20 20 20 20 70 49 6e 70 75 74 2d 3e 69 4e 65 78      pInput->iNex
19440 74 20 2b 3d 20 32 3b 0a 20 20 20 20 20 20 20 20  t += 2;.        
19450 72 63 20 3d 20 73 65 73 73 69 6f 6e 52 65 61 64  rc = sessionRead
19460 52 65 63 6f 72 64 28 70 49 6e 70 75 74 2c 20 6e  Record(pInput, n
19470 43 6f 6c 2c 20 30 2c 20 26 61 70 56 61 6c 5b 30  Col, 0, &apVal[0
19480 5d 29 3b 0a 20 20 20 20 20 20 20 20 69 66 28 20  ]);.        if( 
19490 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b  rc==SQLITE_OK ){
194a0 0a 20 20 20 20 20 20 20 20 20 20 72 63 20 3d 20  .          rc = 
194b0 73 65 73 73 69 6f 6e 52 65 61 64 52 65 63 6f 72  sessionReadRecor
194c0 64 28 70 49 6e 70 75 74 2c 20 6e 43 6f 6c 2c 20  d(pInput, nCol, 
194d0 30 2c 20 26 61 70 56 61 6c 5b 6e 43 6f 6c 5d 29  0, &apVal[nCol])
194e0 3b 0a 20 20 20 20 20 20 20 20 7d 0a 0a 20 20 20  ;.        }..   
194f0 20 20 20 20 20 2f 2a 20 57 72 69 74 65 20 74 68       /* Write th
19500 65 20 6e 65 77 20 6f 6c 64 2e 2a 20 72 65 63 6f  e new old.* reco
19510 72 64 2e 20 43 6f 6e 73 69 73 74 73 20 6f 66 20  rd. Consists of 
19520 74 68 65 20 50 4b 20 63 6f 6c 75 6d 6e 73 20 66  the PK columns f
19530 72 6f 6d 20 74 68 65 0a 20 20 20 20 20 20 20 20  rom the.        
19540 2a 2a 20 6f 72 69 67 69 6e 61 6c 20 6f 6c 64 2e  ** original old.
19550 2a 20 72 65 63 6f 72 64 2c 20 61 6e 64 20 74 68  * record, and th
19560 65 20 6f 74 68 65 72 20 76 61 6c 75 65 73 20 66  e other values f
19570 72 6f 6d 20 74 68 65 20 6f 72 69 67 69 6e 61 6c  rom the original
19580 0a 20 20 20 20 20 20 20 20 2a 2a 20 6e 65 77 2e  .        ** new.
19590 2a 20 72 65 63 6f 72 64 2e 20 2a 2f 0a 20 20 20  * record. */.   
195a0 20 20 20 20 20 66 6f 72 28 69 43 6f 6c 3d 30 3b       for(iCol=0;
195b0 20 69 43 6f 6c 3c 6e 43 6f 6c 3b 20 69 43 6f 6c   iCol<nCol; iCol
195c0 2b 2b 29 7b 0a 20 20 20 20 20 20 20 20 20 20 73  ++){.          s
195d0 71 6c 69 74 65 33 5f 76 61 6c 75 65 20 2a 70 56  qlite3_value *pV
195e0 61 6c 20 3d 20 61 70 56 61 6c 5b 69 43 6f 6c 20  al = apVal[iCol 
195f0 2b 20 28 61 62 50 4b 5b 69 43 6f 6c 5d 20 3f 20  + (abPK[iCol] ? 
19600 30 20 3a 20 6e 43 6f 6c 29 5d 3b 0a 20 20 20 20  0 : nCol)];.    
19610 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70 70        sessionApp
19620 65 6e 64 56 61 6c 75 65 28 26 73 4f 75 74 2c 20  endValue(&sOut, 
19630 70 56 61 6c 2c 20 26 72 63 29 3b 0a 20 20 20 20  pVal, &rc);.    
19640 20 20 20 20 7d 0a 0a 20 20 20 20 20 20 20 20 2f      }..        /
19650 2a 20 57 72 69 74 65 20 74 68 65 20 6e 65 77 20  * Write the new 
19660 6e 65 77 2e 2a 20 72 65 63 6f 72 64 2e 20 43 6f  new.* record. Co
19670 6e 73 69 73 74 73 20 6f 66 20 61 20 63 6f 70 79  nsists of a copy
19680 20 6f 66 20 61 6c 6c 20 76 61 6c 75 65 73 0a 20   of all values. 
19690 20 20 20 20 20 20 20 2a 2a 20 66 72 6f 6d 20 74         ** from t
196a0 68 65 20 6f 72 69 67 69 6e 61 6c 20 6f 6c 64 2e  he original old.
196b0 2a 20 72 65 63 6f 72 64 2c 20 65 78 63 65 70 74  * record, except
196c0 20 66 6f 72 20 74 68 65 20 50 4b 20 63 6f 6c 75   for the PK colu
196d0 6d 6e 73 2c 20 77 68 69 63 68 0a 20 20 20 20 20  mns, which.     
196e0 20 20 20 2a 2a 20 61 72 65 20 73 65 74 20 74 6f     ** are set to
196f0 20 22 75 6e 64 65 66 69 6e 65 64 22 2e 20 2a 2f   "undefined". */
19700 0a 20 20 20 20 20 20 20 20 66 6f 72 28 69 43 6f  .        for(iCo
19710 6c 3d 30 3b 20 69 43 6f 6c 3c 6e 43 6f 6c 3b 20  l=0; iCol<nCol; 
19720 69 43 6f 6c 2b 2b 29 7b 0a 20 20 20 20 20 20 20  iCol++){.       
19730 20 20 20 73 71 6c 69 74 65 33 5f 76 61 6c 75 65     sqlite3_value
19740 20 2a 70 56 61 6c 20 3d 20 28 61 62 50 4b 5b 69   *pVal = (abPK[i
19750 43 6f 6c 5d 20 3f 20 30 20 3a 20 61 70 56 61 6c  Col] ? 0 : apVal
19760 5b 69 43 6f 6c 5d 29 3b 0a 20 20 20 20 20 20 20  [iCol]);.       
19770 20 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64     sessionAppend
19780 56 61 6c 75 65 28 26 73 4f 75 74 2c 20 70 56 61  Value(&sOut, pVa
19790 6c 2c 20 26 72 63 29 3b 0a 20 20 20 20 20 20 20  l, &rc);.       
197a0 20 7d 0a 0a 20 20 20 20 20 20 20 20 66 6f 72 28   }..        for(
197b0 69 43 6f 6c 3d 30 3b 20 69 43 6f 6c 3c 6e 43 6f  iCol=0; iCol<nCo
197c0 6c 2a 32 3b 20 69 43 6f 6c 2b 2b 29 7b 0a 20 20  l*2; iCol++){.  
197d0 20 20 20 20 20 20 20 20 73 71 6c 69 74 65 33 56          sqlite3V
197e0 61 6c 75 65 46 72 65 65 28 61 70 56 61 6c 5b 69  alueFree(apVal[i
197f0 43 6f 6c 5d 29 3b 0a 20 20 20 20 20 20 20 20 7d  Col]);.        }
19800 0a 20 20 20 20 20 20 20 20 6d 65 6d 73 65 74 28  .        memset(
19810 61 70 56 61 6c 2c 20 30 2c 20 73 69 7a 65 6f 66  apVal, 0, sizeof
19820 28 61 70 56 61 6c 5b 30 5d 29 2a 6e 43 6f 6c 2a  (apVal[0])*nCol*
19830 32 29 3b 0a 20 20 20 20 20 20 20 20 69 66 28 20  2);.        if( 
19840 72 63 21 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b  rc!=SQLITE_OK ){
19850 0a 20 20 20 20 20 20 20 20 20 20 67 6f 74 6f 20  .          goto 
19860 66 69 6e 69 73 68 65 64 5f 69 6e 76 65 72 74 3b  finished_invert;
19870 0a 20 20 20 20 20 20 20 20 7d 0a 0a 20 20 20 20  .        }..    
19880 20 20 20 20 62 72 65 61 6b 3b 0a 20 20 20 20 20      break;.     
19890 20 7d 0a 0a 20 20 20 20 20 20 64 65 66 61 75 6c   }..      defaul
198a0 74 3a 0a 20 20 20 20 20 20 20 20 72 63 20 3d 20  t:.        rc = 
198b0 53 51 4c 49 54 45 5f 43 4f 52 52 55 50 54 5f 42  SQLITE_CORRUPT_B
198c0 4b 50 54 3b 0a 20 20 20 20 20 20 20 20 67 6f 74  KPT;.        got
198d0 6f 20 66 69 6e 69 73 68 65 64 5f 69 6e 76 65 72  o finished_inver
198e0 74 3b 0a 20 20 20 20 7d 0a 0a 20 20 20 20 61 73  t;.    }..    as
198f0 73 65 72 74 28 20 72 63 3d 3d 53 51 4c 49 54 45  sert( rc==SQLITE
19900 5f 4f 4b 20 29 3b 0a 20 20 20 20 69 66 28 20 78  _OK );.    if( x
19910 4f 75 74 70 75 74 20 26 26 20 73 4f 75 74 2e 6e  Output && sOut.n
19920 42 75 66 3e 3d 53 45 53 53 49 4f 4e 53 5f 53 54  Buf>=SESSIONS_ST
19930 52 4d 5f 43 48 55 4e 4b 5f 53 49 5a 45 20 29 7b  RM_CHUNK_SIZE ){
19940 0a 20 20 20 20 20 20 72 63 20 3d 20 78 4f 75 74  .      rc = xOut
19950 70 75 74 28 70 4f 75 74 2c 20 73 4f 75 74 2e 61  put(pOut, sOut.a
19960 42 75 66 2c 20 73 4f 75 74 2e 6e 42 75 66 29 3b  Buf, sOut.nBuf);
19970 0a 20 20 20 20 20 20 73 4f 75 74 2e 6e 42 75 66  .      sOut.nBuf
19980 20 3d 20 30 3b 0a 20 20 20 20 20 20 69 66 28 20   = 0;.      if( 
19990 72 63 21 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 20  rc!=SQLITE_OK ) 
199a0 67 6f 74 6f 20 66 69 6e 69 73 68 65 64 5f 69 6e  goto finished_in
199b0 76 65 72 74 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a  vert;.    }.  }.
199c0 0a 20 20 61 73 73 65 72 74 28 20 72 63 3d 3d 53  .  assert( rc==S
199d0 51 4c 49 54 45 5f 4f 4b 20 29 3b 0a 20 20 69 66  QLITE_OK );.  if
199e0 28 20 70 6e 49 6e 76 65 72 74 65 64 20 29 7b 0a  ( pnInverted ){.
199f0 20 20 20 20 2a 70 6e 49 6e 76 65 72 74 65 64 20      *pnInverted 
19a00 3d 20 73 4f 75 74 2e 6e 42 75 66 3b 0a 20 20 20  = sOut.nBuf;.   
19a10 20 2a 70 70 49 6e 76 65 72 74 65 64 20 3d 20 73   *ppInverted = s
19a20 4f 75 74 2e 61 42 75 66 3b 0a 20 20 20 20 73 4f  Out.aBuf;.    sO
19a30 75 74 2e 61 42 75 66 20 3d 20 30 3b 0a 20 20 7d  ut.aBuf = 0;.  }
19a40 65 6c 73 65 20 69 66 28 20 73 4f 75 74 2e 6e 42  else if( sOut.nB
19a50 75 66 3e 30 20 29 7b 0a 20 20 20 20 72 63 20 3d  uf>0 ){.    rc =
19a60 20 78 4f 75 74 70 75 74 28 70 4f 75 74 2c 20 73   xOutput(pOut, s
19a70 4f 75 74 2e 61 42 75 66 2c 20 73 4f 75 74 2e 6e  Out.aBuf, sOut.n
19a80 42 75 66 29 3b 0a 20 20 7d 0a 0a 20 66 69 6e 69  Buf);.  }.. fini
19a90 73 68 65 64 5f 69 6e 76 65 72 74 3a 0a 20 20 73  shed_invert:.  s
19aa0 71 6c 69 74 65 33 5f 66 72 65 65 28 73 4f 75 74  qlite3_free(sOut
19ab0 2e 61 42 75 66 29 3b 0a 20 20 73 71 6c 69 74 65  .aBuf);.  sqlite
19ac0 33 5f 66 72 65 65 28 61 70 56 61 6c 29 3b 0a 20  3_free(apVal);. 
19ad0 20 73 71 6c 69 74 65 33 5f 66 72 65 65 28 73 50   sqlite3_free(sP
19ae0 4b 2e 61 42 75 66 29 3b 0a 20 20 72 65 74 75 72  K.aBuf);.  retur
19af0 6e 20 72 63 3b 0a 7d 0a 0a 0a 2f 2a 0a 2a 2a 20  n rc;.}.../*.** 
19b00 49 6e 76 65 72 74 20 61 20 63 68 61 6e 67 65 73  Invert a changes
19b10 65 74 20 6f 62 6a 65 63 74 2e 0a 2a 2f 0a 69 6e  et object..*/.in
19b20 74 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65 73  t sqlite3changes
19b30 65 74 5f 69 6e 76 65 72 74 28 0a 20 20 69 6e 74  et_invert(.  int
19b40 20 6e 43 68 61 6e 67 65 73 65 74 2c 20 20 20 20   nChangeset,    
19b50 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
19b60 4e 75 6d 62 65 72 20 6f 66 20 62 79 74 65 73 20  Number of bytes 
19b70 69 6e 20 69 6e 70 75 74 20 2a 2f 0a 20 20 63 6f  in input */.  co
19b80 6e 73 74 20 76 6f 69 64 20 2a 70 43 68 61 6e 67  nst void *pChang
19b90 65 73 65 74 2c 20 20 20 20 20 20 20 20 20 2f 2a  eset,         /*
19ba0 20 49 6e 70 75 74 20 63 68 61 6e 67 65 73 65 74   Input changeset
19bb0 20 2a 2f 0a 20 20 69 6e 74 20 2a 70 6e 49 6e 76   */.  int *pnInv
19bc0 65 72 74 65 64 2c 20 20 20 20 20 20 20 20 20 20  erted,          
19bd0 20 20 20 20 20 20 2f 2a 20 4f 55 54 3a 20 4e 75        /* OUT: Nu
19be0 6d 62 65 72 20 6f 66 20 62 79 74 65 73 20 69 6e  mber of bytes in
19bf0 20 6f 75 74 70 75 74 20 63 68 61 6e 67 65 73 65   output changese
19c00 74 20 2a 2f 0a 20 20 76 6f 69 64 20 2a 2a 70 70  t */.  void **pp
19c10 49 6e 76 65 72 74 65 64 20 20 20 20 20 20 20 20  Inverted        
19c20 20 20 20 20 20 20 20 2f 2a 20 4f 55 54 3a 20 49         /* OUT: I
19c30 6e 76 65 72 73 65 20 6f 66 20 70 43 68 61 6e 67  nverse of pChang
19c40 65 73 65 74 20 2a 2f 0a 29 7b 0a 20 20 53 65 73  eset */.){.  Ses
19c50 73 69 6f 6e 49 6e 70 75 74 20 73 49 6e 70 75 74  sionInput sInput
19c60 3b 0a 0a 20 20 2f 2a 20 53 65 74 20 75 70 20 74  ;..  /* Set up t
19c70 68 65 20 69 6e 70 75 74 20 73 74 72 65 61 6d 20  he input stream 
19c80 2a 2f 0a 20 20 6d 65 6d 73 65 74 28 26 73 49 6e  */.  memset(&sIn
19c90 70 75 74 2c 20 30 2c 20 73 69 7a 65 6f 66 28 53  put, 0, sizeof(S
19ca0 65 73 73 69 6f 6e 49 6e 70 75 74 29 29 3b 0a 20  essionInput));. 
19cb0 20 73 49 6e 70 75 74 2e 6e 44 61 74 61 20 3d 20   sInput.nData = 
19cc0 6e 43 68 61 6e 67 65 73 65 74 3b 0a 20 20 73 49  nChangeset;.  sI
19cd0 6e 70 75 74 2e 61 44 61 74 61 20 3d 20 28 75 38  nput.aData = (u8
19ce0 2a 29 70 43 68 61 6e 67 65 73 65 74 3b 0a 0a 20  *)pChangeset;.. 
19cf0 20 72 65 74 75 72 6e 20 73 65 73 73 69 6f 6e 43   return sessionC
19d00 68 61 6e 67 65 73 65 74 49 6e 76 65 72 74 28 26  hangesetInvert(&
19d10 73 49 6e 70 75 74 2c 20 30 2c 20 30 2c 20 70 6e  sInput, 0, 0, pn
19d20 49 6e 76 65 72 74 65 64 2c 20 70 70 49 6e 76 65  Inverted, ppInve
19d30 72 74 65 64 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20  rted);.}../*.** 
19d40 53 74 72 65 61 6d 69 6e 67 20 76 65 72 73 69 6f  Streaming versio
19d50 6e 20 6f 66 20 73 71 6c 69 74 65 33 63 68 61 6e  n of sqlite3chan
19d60 67 65 73 65 74 5f 69 6e 76 65 72 74 28 29 2e 0a  geset_invert()..
19d70 2a 2f 0a 69 6e 74 20 73 71 6c 69 74 65 33 63 68  */.int sqlite3ch
19d80 61 6e 67 65 73 65 74 5f 69 6e 76 65 72 74 5f 73  angeset_invert_s
19d90 74 72 6d 28 0a 20 20 69 6e 74 20 28 2a 78 49 6e  trm(.  int (*xIn
19da0 70 75 74 29 28 76 6f 69 64 20 2a 70 49 6e 2c 20  put)(void *pIn, 
19db0 76 6f 69 64 20 2a 70 44 61 74 61 2c 20 69 6e 74  void *pData, int
19dc0 20 2a 70 6e 44 61 74 61 29 2c 0a 20 20 76 6f 69   *pnData),.  voi
19dd0 64 20 2a 70 49 6e 2c 0a 20 20 69 6e 74 20 28 2a  d *pIn,.  int (*
19de0 78 4f 75 74 70 75 74 29 28 76 6f 69 64 20 2a 70  xOutput)(void *p
19df0 4f 75 74 2c 20 63 6f 6e 73 74 20 76 6f 69 64 20  Out, const void 
19e00 2a 70 44 61 74 61 2c 20 69 6e 74 20 6e 44 61 74  *pData, int nDat
19e10 61 29 2c 0a 20 20 76 6f 69 64 20 2a 70 4f 75 74  a),.  void *pOut
19e20 0a 29 7b 0a 20 20 53 65 73 73 69 6f 6e 49 6e 70  .){.  SessionInp
19e30 75 74 20 73 49 6e 70 75 74 3b 0a 20 20 69 6e 74  ut sInput;.  int
19e40 20 72 63 3b 0a 0a 20 20 2f 2a 20 53 65 74 20 75   rc;..  /* Set u
19e50 70 20 74 68 65 20 69 6e 70 75 74 20 73 74 72 65  p the input stre
19e60 61 6d 20 2a 2f 0a 20 20 6d 65 6d 73 65 74 28 26  am */.  memset(&
19e70 73 49 6e 70 75 74 2c 20 30 2c 20 73 69 7a 65 6f  sInput, 0, sizeo
19e80 66 28 53 65 73 73 69 6f 6e 49 6e 70 75 74 29 29  f(SessionInput))
19e90 3b 0a 20 20 73 49 6e 70 75 74 2e 78 49 6e 70 75  ;.  sInput.xInpu
19ea0 74 20 3d 20 78 49 6e 70 75 74 3b 0a 20 20 73 49  t = xInput;.  sI
19eb0 6e 70 75 74 2e 70 49 6e 20 3d 20 70 49 6e 3b 0a  nput.pIn = pIn;.
19ec0 0a 20 20 72 63 20 3d 20 73 65 73 73 69 6f 6e 43  .  rc = sessionC
19ed0 68 61 6e 67 65 73 65 74 49 6e 76 65 72 74 28 26  hangesetInvert(&
19ee0 73 49 6e 70 75 74 2c 20 78 4f 75 74 70 75 74 2c  sInput, xOutput,
19ef0 20 70 4f 75 74 2c 20 30 2c 20 30 29 3b 0a 20 20   pOut, 0, 0);.  
19f00 73 71 6c 69 74 65 33 5f 66 72 65 65 28 73 49 6e  sqlite3_free(sIn
19f10 70 75 74 2e 62 75 66 2e 61 42 75 66 29 3b 0a 20  put.buf.aBuf);. 
19f20 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 74   return rc;.}..t
19f30 79 70 65 64 65 66 20 73 74 72 75 63 74 20 53 65  ypedef struct Se
19f40 73 73 69 6f 6e 41 70 70 6c 79 43 74 78 20 53 65  ssionApplyCtx Se
19f50 73 73 69 6f 6e 41 70 70 6c 79 43 74 78 3b 0a 73  ssionApplyCtx;.s
19f60 74 72 75 63 74 20 53 65 73 73 69 6f 6e 41 70 70  truct SessionApp
19f70 6c 79 43 74 78 20 7b 0a 20 20 73 71 6c 69 74 65  lyCtx {.  sqlite
19f80 33 20 2a 64 62 3b 0a 20 20 73 71 6c 69 74 65 33  3 *db;.  sqlite3
19f90 5f 73 74 6d 74 20 2a 70 44 65 6c 65 74 65 3b 20  _stmt *pDelete; 
19fa0 20 20 20 20 20 20 20 20 20 2f 2a 20 44 45 4c 45           /* DELE
19fb0 54 45 20 73 74 61 74 65 6d 65 6e 74 20 2a 2f 0a  TE statement */.
19fc0 20 20 73 71 6c 69 74 65 33 5f 73 74 6d 74 20 2a    sqlite3_stmt *
19fd0 70 55 70 64 61 74 65 3b 20 20 20 20 20 20 20 20  pUpdate;        
19fe0 20 20 2f 2a 20 55 50 44 41 54 45 20 73 74 61 74    /* UPDATE stat
19ff0 65 6d 65 6e 74 20 2a 2f 0a 20 20 73 71 6c 69 74  ement */.  sqlit
1a000 65 33 5f 73 74 6d 74 20 2a 70 49 6e 73 65 72 74  e3_stmt *pInsert
1a010 3b 20 20 20 20 20 20 20 20 20 20 2f 2a 20 49 4e  ;          /* IN
1a020 53 45 52 54 20 73 74 61 74 65 6d 65 6e 74 20 2a  SERT statement *
1a030 2f 0a 20 20 73 71 6c 69 74 65 33 5f 73 74 6d 74  /.  sqlite3_stmt
1a040 20 2a 70 53 65 6c 65 63 74 3b 20 20 20 20 20 20   *pSelect;      
1a050 20 20 20 20 2f 2a 20 53 45 4c 45 43 54 20 73 74      /* SELECT st
1a060 61 74 65 6d 65 6e 74 20 2a 2f 0a 20 20 69 6e 74  atement */.  int
1a070 20 6e 43 6f 6c 3b 20 20 20 20 20 20 20 20 20 20   nCol;          
1a080 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
1a090 53 69 7a 65 20 6f 66 20 61 7a 43 6f 6c 5b 5d 20  Size of azCol[] 
1a0a0 61 6e 64 20 61 62 50 4b 5b 5d 20 61 72 72 61 79  and abPK[] array
1a0b0 73 20 2a 2f 0a 20 20 63 6f 6e 73 74 20 63 68 61  s */.  const cha
1a0c0 72 20 2a 2a 61 7a 43 6f 6c 3b 20 20 20 20 20 20  r **azCol;      
1a0d0 20 20 20 20 20 20 20 2f 2a 20 41 72 72 61 79 20         /* Array 
1a0e0 6f 66 20 63 6f 6c 75 6d 6e 20 6e 61 6d 65 73 20  of column names 
1a0f0 2a 2f 0a 20 20 75 38 20 2a 61 62 50 4b 3b 20 20  */.  u8 *abPK;  
1a100 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1a110 20 20 20 20 20 2f 2a 20 42 6f 6f 6c 65 61 6e 20       /* Boolean 
1a120 61 72 72 61 79 20 2d 20 74 72 75 65 20 69 66 20  array - true if 
1a130 63 6f 6c 75 6d 6e 20 69 73 20 69 6e 20 50 4b 20  column is in PK 
1a140 2a 2f 0a 0a 20 20 69 6e 74 20 62 44 65 66 65 72  */..  int bDefer
1a150 43 6f 6e 73 74 72 61 69 6e 74 73 3b 20 20 20 20  Constraints;    
1a160 20 20 20 20 20 20 2f 2a 20 54 72 75 65 20 74 6f        /* True to
1a170 20 64 65 66 65 72 20 63 6f 6e 73 74 72 61 69 6e   defer constrain
1a180 74 73 20 2a 2f 0a 20 20 53 65 73 73 69 6f 6e 42  ts */.  SessionB
1a190 75 66 66 65 72 20 63 6f 6e 73 74 72 61 69 6e 74  uffer constraint
1a1a0 73 3b 20 20 20 20 20 20 2f 2a 20 44 65 66 65 72  s;      /* Defer
1a1b0 72 65 64 20 63 6f 6e 73 74 72 61 69 6e 74 73 20  red constraints 
1a1c0 61 72 65 20 73 74 6f 72 65 64 20 68 65 72 65 20  are stored here 
1a1d0 2a 2f 0a 7d 3b 0a 0a 2f 2a 0a 2a 2a 20 46 6f 72  */.};../*.** For
1a1e0 6d 75 6c 61 74 65 20 61 20 73 74 61 74 65 6d 65  mulate a stateme
1a1f0 6e 74 20 74 6f 20 44 45 4c 45 54 45 20 61 20 72  nt to DELETE a r
1a200 6f 77 20 66 72 6f 6d 20 64 61 74 61 62 61 73 65  ow from database
1a210 20 64 62 2e 20 41 73 73 75 6d 69 6e 67 20 61 20   db. Assuming a 
1a220 74 61 62 6c 65 0a 2a 2a 20 73 74 72 75 63 74 75  table.** structu
1a230 72 65 20 6c 69 6b 65 20 74 68 69 73 3a 0a 2a 2a  re like this:.**
1a240 0a 2a 2a 20 20 20 20 20 43 52 45 41 54 45 20 54  .**     CREATE T
1a250 41 42 4c 45 20 78 28 61 2c 20 62 2c 20 63 2c 20  ABLE x(a, b, c, 
1a260 64 2c 20 50 52 49 4d 41 52 59 20 4b 45 59 28 61  d, PRIMARY KEY(a
1a270 2c 20 63 29 29 3b 0a 2a 2a 0a 2a 2a 20 54 68 65  , c));.**.** The
1a280 20 44 45 4c 45 54 45 20 73 74 61 74 65 6d 65 6e   DELETE statemen
1a290 74 20 6c 6f 6f 6b 73 20 6c 69 6b 65 20 74 68 69  t looks like thi
1a2a0 73 3a 0a 2a 2a 0a 2a 2a 20 20 20 20 20 44 45 4c  s:.**.**     DEL
1a2b0 45 54 45 20 46 52 4f 4d 20 78 20 57 48 45 52 45  ETE FROM x WHERE
1a2c0 20 61 20 3d 20 3a 31 20 41 4e 44 20 63 20 3d 20   a = :1 AND c = 
1a2d0 3a 33 20 41 4e 44 20 28 3a 35 20 4f 52 20 62 20  :3 AND (:5 OR b 
1a2e0 49 53 20 3a 32 20 41 4e 44 20 64 20 49 53 20 3a  IS :2 AND d IS :
1a2f0 34 29 0a 2a 2a 0a 2a 2a 20 56 61 72 69 61 62 6c  4).**.** Variabl
1a300 65 20 3a 35 20 28 6e 43 6f 6c 2b 31 29 20 69 73  e :5 (nCol+1) is
1a310 20 61 20 62 6f 6f 6c 65 61 6e 2e 20 49 74 20 73   a boolean. It s
1a320 68 6f 75 6c 64 20 62 65 20 73 65 74 20 74 6f 20  hould be set to 
1a330 30 20 69 66 20 77 65 20 72 65 71 75 69 72 65 0a  0 if we require.
1a340 2a 2a 20 6d 61 74 63 68 69 6e 67 20 62 20 61 6e  ** matching b an
1a350 64 20 64 20 76 61 6c 75 65 73 2c 20 6f 72 20 31  d d values, or 1
1a360 20 6f 74 68 65 72 77 69 73 65 2e 20 54 68 65 20   otherwise. The 
1a370 73 65 63 6f 6e 64 20 63 61 73 65 20 63 6f 6d 65  second case come
1a380 73 20 75 70 20 69 66 20 74 68 65 0a 2a 2a 20 63  s up if the.** c
1a390 6f 6e 66 6c 69 63 74 20 68 61 6e 64 6c 65 72 20  onflict handler 
1a3a0 69 73 20 69 6e 76 6f 6b 65 64 20 77 69 74 68 20  is invoked with 
1a3b0 4e 4f 54 46 4f 55 4e 44 20 61 6e 64 20 72 65 74  NOTFOUND and ret
1a3c0 75 72 6e 73 20 43 48 41 4e 47 45 53 45 54 5f 52  urns CHANGESET_R
1a3d0 45 50 4c 41 43 45 2e 0a 2a 2a 0a 2a 2a 20 49 66  EPLACE..**.** If
1a3e0 20 73 75 63 63 65 73 73 66 75 6c 2c 20 53 51 4c   successful, SQL
1a3f0 49 54 45 5f 4f 4b 20 69 73 20 72 65 74 75 72 6e  ITE_OK is return
1a400 65 64 20 61 6e 64 20 53 65 73 73 69 6f 6e 41 70  ed and SessionAp
1a410 70 6c 79 43 74 78 2e 70 44 65 6c 65 74 65 20 69  plyCtx.pDelete i
1a420 73 20 6c 65 66 74 0a 2a 2a 20 70 6f 69 6e 74 69  s left.** pointi
1a430 6e 67 20 74 6f 20 74 68 65 20 70 72 65 70 61 72  ng to the prepar
1a440 65 64 20 76 65 72 73 69 6f 6e 20 6f 66 20 74 68  ed version of th
1a450 65 20 53 51 4c 20 73 74 61 74 65 6d 65 6e 74 2e  e SQL statement.
1a460 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73  .*/.static int s
1a470 65 73 73 69 6f 6e 44 65 6c 65 74 65 52 6f 77 28  essionDeleteRow(
1a480 0a 20 20 73 71 6c 69 74 65 33 20 2a 64 62 2c 20  .  sqlite3 *db, 
1a490 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1a4a0 20 20 20 2f 2a 20 44 61 74 61 62 61 73 65 20 68     /* Database h
1a4b0 61 6e 64 6c 65 20 2a 2f 0a 20 20 63 6f 6e 73 74  andle */.  const
1a4c0 20 63 68 61 72 20 2a 7a 54 61 62 2c 20 20 20 20   char *zTab,    
1a4d0 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 54 61             /* Ta
1a4e0 62 6c 65 20 6e 61 6d 65 20 2a 2f 0a 20 20 53 65  ble name */.  Se
1a4f0 73 73 69 6f 6e 41 70 70 6c 79 43 74 78 20 2a 70  ssionApplyCtx *p
1a500 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
1a510 20 53 65 73 73 69 6f 6e 20 63 68 61 6e 67 65 73   Session changes
1a520 65 74 2d 61 70 70 6c 79 20 63 6f 6e 74 65 78 74  et-apply context
1a530 20 2a 2f 0a 29 7b 0a 20 20 69 6e 74 20 69 3b 0a   */.){.  int i;.
1a540 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 53    const char *zS
1a550 65 70 20 3d 20 22 22 3b 0a 20 20 69 6e 74 20 72  ep = "";.  int r
1a560 63 20 3d 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a 20  c = SQLITE_OK;. 
1a570 20 53 65 73 73 69 6f 6e 42 75 66 66 65 72 20 62   SessionBuffer b
1a580 75 66 20 3d 20 7b 30 2c 20 30 2c 20 30 7d 3b 0a  uf = {0, 0, 0};.
1a590 20 20 69 6e 74 20 6e 50 6b 20 3d 20 30 3b 0a 0a    int nPk = 0;..
1a5a0 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 53    sessionAppendS
1a5b0 74 72 28 26 62 75 66 2c 20 22 44 45 4c 45 54 45  tr(&buf, "DELETE
1a5c0 20 46 52 4f 4d 20 22 2c 20 26 72 63 29 3b 0a 20   FROM ", &rc);. 
1a5d0 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 49 64   sessionAppendId
1a5e0 65 6e 74 28 26 62 75 66 2c 20 7a 54 61 62 2c 20  ent(&buf, zTab, 
1a5f0 26 72 63 29 3b 0a 20 20 73 65 73 73 69 6f 6e 41  &rc);.  sessionA
1a600 70 70 65 6e 64 53 74 72 28 26 62 75 66 2c 20 22  ppendStr(&buf, "
1a610 20 57 48 45 52 45 20 22 2c 20 26 72 63 29 3b 0a   WHERE ", &rc);.
1a620 0a 20 20 66 6f 72 28 69 3d 30 3b 20 69 3c 70 2d  .  for(i=0; i<p-
1a630 3e 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a 20 20 20  >nCol; i++){.   
1a640 20 69 66 28 20 70 2d 3e 61 62 50 4b 5b 69 5d 20   if( p->abPK[i] 
1a650 29 7b 0a 20 20 20 20 20 20 6e 50 6b 2b 2b 3b 0a  ){.      nPk++;.
1a660 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70 70        sessionApp
1a670 65 6e 64 53 74 72 28 26 62 75 66 2c 20 7a 53 65  endStr(&buf, zSe
1a680 70 2c 20 26 72 63 29 3b 0a 20 20 20 20 20 20 73  p, &rc);.      s
1a690 65 73 73 69 6f 6e 41 70 70 65 6e 64 49 64 65 6e  essionAppendIden
1a6a0 74 28 26 62 75 66 2c 20 70 2d 3e 61 7a 43 6f 6c  t(&buf, p->azCol
1a6b0 5b 69 5d 2c 20 26 72 63 29 3b 0a 20 20 20 20 20  [i], &rc);.     
1a6c0 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 53 74   sessionAppendSt
1a6d0 72 28 26 62 75 66 2c 20 22 20 3d 20 3f 22 2c 20  r(&buf, " = ?", 
1a6e0 26 72 63 29 3b 0a 20 20 20 20 20 20 73 65 73 73  &rc);.      sess
1a6f0 69 6f 6e 41 70 70 65 6e 64 49 6e 74 65 67 65 72  ionAppendInteger
1a700 28 26 62 75 66 2c 20 69 2b 31 2c 20 26 72 63 29  (&buf, i+1, &rc)
1a710 3b 0a 20 20 20 20 20 20 7a 53 65 70 20 3d 20 22  ;.      zSep = "
1a720 20 41 4e 44 20 22 3b 0a 20 20 20 20 7d 0a 20 20   AND ";.    }.  
1a730 7d 0a 0a 20 20 69 66 28 20 6e 50 6b 3c 70 2d 3e  }..  if( nPk<p->
1a740 6e 43 6f 6c 20 29 7b 0a 20 20 20 20 73 65 73 73  nCol ){.    sess
1a750 69 6f 6e 41 70 70 65 6e 64 53 74 72 28 26 62 75  ionAppendStr(&bu
1a760 66 2c 20 22 20 41 4e 44 20 28 3f 22 2c 20 26 72  f, " AND (?", &r
1a770 63 29 3b 0a 20 20 20 20 73 65 73 73 69 6f 6e 41  c);.    sessionA
1a780 70 70 65 6e 64 49 6e 74 65 67 65 72 28 26 62 75  ppendInteger(&bu
1a790 66 2c 20 70 2d 3e 6e 43 6f 6c 2b 31 2c 20 26 72  f, p->nCol+1, &r
1a7a0 63 29 3b 0a 20 20 20 20 73 65 73 73 69 6f 6e 41  c);.    sessionA
1a7b0 70 70 65 6e 64 53 74 72 28 26 62 75 66 2c 20 22  ppendStr(&buf, "
1a7c0 20 4f 52 20 22 2c 20 26 72 63 29 3b 0a 0a 20 20   OR ", &rc);..  
1a7d0 20 20 7a 53 65 70 20 3d 20 22 22 3b 0a 20 20 20    zSep = "";.   
1a7e0 20 66 6f 72 28 69 3d 30 3b 20 69 3c 70 2d 3e 6e   for(i=0; i<p->n
1a7f0 43 6f 6c 3b 20 69 2b 2b 29 7b 0a 20 20 20 20 20  Col; i++){.     
1a800 20 69 66 28 20 21 70 2d 3e 61 62 50 4b 5b 69 5d   if( !p->abPK[i]
1a810 20 29 7b 0a 20 20 20 20 20 20 20 20 73 65 73 73   ){.        sess
1a820 69 6f 6e 41 70 70 65 6e 64 53 74 72 28 26 62 75  ionAppendStr(&bu
1a830 66 2c 20 7a 53 65 70 2c 20 26 72 63 29 3b 0a 20  f, zSep, &rc);. 
1a840 20 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70         sessionAp
1a850 70 65 6e 64 49 64 65 6e 74 28 26 62 75 66 2c 20  pendIdent(&buf, 
1a860 70 2d 3e 61 7a 43 6f 6c 5b 69 5d 2c 20 26 72 63  p->azCol[i], &rc
1a870 29 3b 0a 20 20 20 20 20 20 20 20 73 65 73 73 69  );.        sessi
1a880 6f 6e 41 70 70 65 6e 64 53 74 72 28 26 62 75 66  onAppendStr(&buf
1a890 2c 20 22 20 49 53 20 3f 22 2c 20 26 72 63 29 3b  , " IS ?", &rc);
1a8a0 0a 20 20 20 20 20 20 20 20 73 65 73 73 69 6f 6e  .        session
1a8b0 41 70 70 65 6e 64 49 6e 74 65 67 65 72 28 26 62  AppendInteger(&b
1a8c0 75 66 2c 20 69 2b 31 2c 20 26 72 63 29 3b 0a 20  uf, i+1, &rc);. 
1a8d0 20 20 20 20 20 20 20 7a 53 65 70 20 3d 20 22 41         zSep = "A
1a8e0 4e 44 20 22 3b 0a 20 20 20 20 20 20 7d 0a 20 20  ND ";.      }.  
1a8f0 20 20 7d 0a 20 20 20 20 73 65 73 73 69 6f 6e 41    }.    sessionA
1a900 70 70 65 6e 64 53 74 72 28 26 62 75 66 2c 20 22  ppendStr(&buf, "
1a910 29 22 2c 20 26 72 63 29 3b 0a 20 20 7d 0a 0a 20  )", &rc);.  }.. 
1a920 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f   if( rc==SQLITE_
1a930 4f 4b 20 29 7b 0a 20 20 20 20 72 63 20 3d 20 73  OK ){.    rc = s
1a940 71 6c 69 74 65 33 5f 70 72 65 70 61 72 65 5f 76  qlite3_prepare_v
1a950 32 28 64 62 2c 20 28 63 68 61 72 20 2a 29 62 75  2(db, (char *)bu
1a960 66 2e 61 42 75 66 2c 20 62 75 66 2e 6e 42 75 66  f.aBuf, buf.nBuf
1a970 2c 20 26 70 2d 3e 70 44 65 6c 65 74 65 2c 20 30  , &p->pDelete, 0
1a980 29 3b 0a 20 20 7d 0a 20 20 73 71 6c 69 74 65 33  );.  }.  sqlite3
1a990 5f 66 72 65 65 28 62 75 66 2e 61 42 75 66 29 3b  _free(buf.aBuf);
1a9a0 0a 0a 20 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d  ..  return rc;.}
1a9b0 0a 0a 2f 2a 0a 2a 2a 20 46 6f 72 6d 75 6c 61 74  ../*.** Formulat
1a9c0 65 20 61 6e 64 20 70 72 65 70 61 72 65 20 61 20  e and prepare a 
1a9d0 73 74 61 74 65 6d 65 6e 74 20 74 6f 20 55 50 44  statement to UPD
1a9e0 41 54 45 20 61 20 72 6f 77 20 66 72 6f 6d 20 64  ATE a row from d
1a9f0 61 74 61 62 61 73 65 20 64 62 2e 20 0a 2a 2a 20  atabase db. .** 
1aa00 41 73 73 75 6d 69 6e 67 20 61 20 74 61 62 6c 65  Assuming a table
1aa10 20 73 74 72 75 63 74 75 72 65 20 6c 69 6b 65 20   structure like 
1aa20 74 68 69 73 3a 0a 2a 2a 0a 2a 2a 20 20 20 20 20  this:.**.**     
1aa30 43 52 45 41 54 45 20 54 41 42 4c 45 20 78 28 61  CREATE TABLE x(a
1aa40 2c 20 62 2c 20 63 2c 20 64 2c 20 50 52 49 4d 41  , b, c, d, PRIMA
1aa50 52 59 20 4b 45 59 28 61 2c 20 63 29 29 3b 0a 2a  RY KEY(a, c));.*
1aa60 2a 0a 2a 2a 20 54 68 65 20 55 50 44 41 54 45 20  *.** The UPDATE 
1aa70 73 74 61 74 65 6d 65 6e 74 20 6c 6f 6f 6b 73 20  statement looks 
1aa80 6c 69 6b 65 20 74 68 69 73 3a 0a 2a 2a 0a 2a 2a  like this:.**.**
1aa90 20 20 20 20 20 55 50 44 41 54 45 20 78 20 53 45       UPDATE x SE
1aaa0 54 0a 2a 2a 20 20 20 20 20 61 20 3d 20 43 41 53  T.**     a = CAS
1aab0 45 20 57 48 45 4e 20 3f 32 20 20 54 48 45 4e 20  E WHEN ?2  THEN 
1aac0 3f 33 20 20 45 4c 53 45 20 61 20 45 4e 44 2c 0a  ?3  ELSE a END,.
1aad0 2a 2a 20 20 20 20 20 62 20 3d 20 43 41 53 45 20  **     b = CASE 
1aae0 57 48 45 4e 20 3f 35 20 20 54 48 45 4e 20 3f 36  WHEN ?5  THEN ?6
1aaf0 20 20 45 4c 53 45 20 62 20 45 4e 44 2c 0a 2a 2a    ELSE b END,.**
1ab00 20 20 20 20 20 63 20 3d 20 43 41 53 45 20 57 48       c = CASE WH
1ab10 45 4e 20 3f 38 20 20 54 48 45 4e 20 3f 39 20 20  EN ?8  THEN ?9  
1ab20 45 4c 53 45 20 63 20 45 4e 44 2c 0a 2a 2a 20 20  ELSE c END,.**  
1ab30 20 20 20 64 20 3d 20 43 41 53 45 20 57 48 45 4e     d = CASE WHEN
1ab40 20 3f 31 31 20 54 48 45 4e 20 3f 31 32 20 45 4c   ?11 THEN ?12 EL
1ab50 53 45 20 64 20 45 4e 44 0a 2a 2a 20 20 20 20 20  SE d END.**     
1ab60 57 48 45 52 45 20 61 20 3d 20 3f 31 20 41 4e 44  WHERE a = ?1 AND
1ab70 20 63 20 3d 20 3f 37 20 41 4e 44 20 28 3f 31 33   c = ?7 AND (?13
1ab80 20 4f 52 20 0a 2a 2a 20 20 20 20 20 20 20 28 3f   OR .**       (?
1ab90 35 3d 3d 30 20 4f 52 20 62 20 49 53 20 3f 34 29  5==0 OR b IS ?4)
1aba0 20 41 4e 44 20 28 3f 31 31 3d 3d 30 20 4f 52 20   AND (?11==0 OR 
1abb0 64 20 49 53 20 3f 31 30 29 20 41 4e 44 0a 2a 2a  d IS ?10) AND.**
1abc0 20 20 20 20 20 29 0a 2a 2a 0a 2a 2a 20 46 6f 72       ).**.** For
1abd0 20 65 61 63 68 20 63 6f 6c 75 6d 6e 20 69 6e 20   each column in 
1abe0 74 68 65 20 74 61 62 6c 65 2c 20 74 68 65 72 65  the table, there
1abf0 20 61 72 65 20 74 68 72 65 65 20 76 61 72 69 61   are three varia
1ac00 62 6c 65 73 20 74 6f 20 62 69 6e 64 3a 0a 2a 2a  bles to bind:.**
1ac10 0a 2a 2a 20 20 20 20 20 3f 28 69 2a 33 2b 31 29  .**     ?(i*3+1)
1ac20 20 20 20 20 54 68 65 20 6f 6c 64 2e 2a 20 76 61      The old.* va
1ac30 6c 75 65 20 6f 66 20 74 68 65 20 63 6f 6c 75 6d  lue of the colum
1ac40 6e 2c 20 69 66 20 61 6e 79 2e 0a 2a 2a 20 20 20  n, if any..**   
1ac50 20 20 3f 28 69 2a 33 2b 32 29 20 20 20 20 41 20    ?(i*3+2)    A 
1ac60 62 6f 6f 6c 65 61 6e 20 66 6c 61 67 20 69 6e 64  boolean flag ind
1ac70 69 63 61 74 69 6e 67 20 74 68 61 74 20 74 68 65  icating that the
1ac80 20 76 61 6c 75 65 20 69 73 20 62 65 69 6e 67 20   value is being 
1ac90 6d 6f 64 69 66 69 65 64 2e 0a 2a 2a 20 20 20 20  modified..**    
1aca0 20 3f 28 69 2a 33 2b 33 29 20 20 20 20 54 68 65   ?(i*3+3)    The
1acb0 20 6e 65 77 2e 2a 20 76 61 6c 75 65 20 6f 66 20   new.* value of 
1acc0 74 68 65 20 63 6f 6c 75 6d 6e 2c 20 69 66 20 61  the column, if a
1acd0 6e 79 2e 0a 2a 2a 0a 2a 2a 20 41 6c 73 6f 2c 20  ny..**.** Also, 
1ace0 61 20 62 6f 6f 6c 65 61 6e 20 66 6c 61 67 20 74  a boolean flag t
1acf0 68 61 74 2c 20 69 66 20 73 65 74 20 74 6f 20 74  hat, if set to t
1ad00 72 75 65 2c 20 63 61 75 73 65 73 20 74 68 65 20  rue, causes the 
1ad10 73 74 61 74 65 6d 65 6e 74 20 74 6f 20 75 70 64  statement to upd
1ad20 61 74 65 0a 2a 2a 20 61 20 72 6f 77 20 65 76 65  ate.** a row eve
1ad30 6e 20 69 66 20 74 68 65 20 6e 6f 6e 2d 50 4b 20  n if the non-PK 
1ad40 76 61 6c 75 65 73 20 64 6f 20 6e 6f 74 20 6d 61  values do not ma
1ad50 74 63 68 2e 20 54 68 69 73 20 69 73 20 72 65 71  tch. This is req
1ad60 75 69 72 65 64 20 69 66 20 74 68 65 0a 2a 2a 20  uired if the.** 
1ad70 63 6f 6e 66 6c 69 63 74 2d 68 61 6e 64 6c 65 72  conflict-handler
1ad80 20 69 73 20 69 6e 76 6f 6b 65 64 20 77 69 74 68   is invoked with
1ad90 20 43 48 41 4e 47 45 53 45 54 5f 44 41 54 41 20   CHANGESET_DATA 
1ada0 61 6e 64 20 72 65 74 75 72 6e 73 0a 2a 2a 20 43  and returns.** C
1adb0 48 41 4e 47 45 53 45 54 5f 52 45 50 4c 41 43 45  HANGESET_REPLACE
1adc0 2e 20 54 68 69 73 20 69 73 20 76 61 72 69 61 62  . This is variab
1add0 6c 65 20 22 3f 28 6e 43 6f 6c 2a 33 2b 31 29 22  le "?(nCol*3+1)"
1ade0 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 73 75 63 63 65  ..**.** If succe
1adf0 73 73 66 75 6c 2c 20 53 51 4c 49 54 45 5f 4f 4b  ssful, SQLITE_OK
1ae00 20 69 73 20 72 65 74 75 72 6e 65 64 20 61 6e 64   is returned and
1ae10 20 53 65 73 73 69 6f 6e 41 70 70 6c 79 43 74 78   SessionApplyCtx
1ae20 2e 70 55 70 64 61 74 65 20 69 73 20 6c 65 66 74  .pUpdate is left
1ae30 0a 2a 2a 20 70 6f 69 6e 74 69 6e 67 20 74 6f 20  .** pointing to 
1ae40 74 68 65 20 70 72 65 70 61 72 65 64 20 76 65 72  the prepared ver
1ae50 73 69 6f 6e 20 6f 66 20 74 68 65 20 53 51 4c 20  sion of the SQL 
1ae60 73 74 61 74 65 6d 65 6e 74 2e 0a 2a 2f 0a 73 74  statement..*/.st
1ae70 61 74 69 63 20 69 6e 74 20 73 65 73 73 69 6f 6e  atic int session
1ae80 55 70 64 61 74 65 52 6f 77 28 0a 20 20 73 71 6c  UpdateRow(.  sql
1ae90 69 74 65 33 20 2a 64 62 2c 20 20 20 20 20 20 20  ite3 *db,       
1aea0 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
1aeb0 44 61 74 61 62 61 73 65 20 68 61 6e 64 6c 65 20  Database handle 
1aec0 2a 2f 0a 20 20 63 6f 6e 73 74 20 63 68 61 72 20  */.  const char 
1aed0 2a 7a 54 61 62 2c 20 20 20 20 20 20 20 20 20 20  *zTab,          
1aee0 20 20 20 20 20 2f 2a 20 54 61 62 6c 65 20 6e 61       /* Table na
1aef0 6d 65 20 2a 2f 0a 20 20 53 65 73 73 69 6f 6e 41  me */.  SessionA
1af00 70 70 6c 79 43 74 78 20 2a 70 20 20 20 20 20 20  pplyCtx *p      
1af10 20 20 20 20 20 20 20 20 2f 2a 20 53 65 73 73 69          /* Sessi
1af20 6f 6e 20 63 68 61 6e 67 65 73 65 74 2d 61 70 70  on changeset-app
1af30 6c 79 20 63 6f 6e 74 65 78 74 20 2a 2f 0a 29 7b  ly context */.){
1af40 0a 20 20 69 6e 74 20 72 63 20 3d 20 53 51 4c 49  .  int rc = SQLI
1af50 54 45 5f 4f 4b 3b 0a 20 20 69 6e 74 20 69 3b 0a  TE_OK;.  int i;.
1af60 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 53    const char *zS
1af70 65 70 20 3d 20 22 22 3b 0a 20 20 53 65 73 73 69  ep = "";.  Sessi
1af80 6f 6e 42 75 66 66 65 72 20 62 75 66 20 3d 20 7b  onBuffer buf = {
1af90 30 2c 20 30 2c 20 30 7d 3b 0a 0a 20 20 2f 2a 20  0, 0, 0};..  /* 
1afa0 41 70 70 65 6e 64 20 22 55 50 44 41 54 45 20 74  Append "UPDATE t
1afb0 62 6c 20 53 45 54 20 22 20 2a 2f 0a 20 20 73 65  bl SET " */.  se
1afc0 73 73 69 6f 6e 41 70 70 65 6e 64 53 74 72 28 26  ssionAppendStr(&
1afd0 62 75 66 2c 20 22 55 50 44 41 54 45 20 22 2c 20  buf, "UPDATE ", 
1afe0 26 72 63 29 3b 0a 20 20 73 65 73 73 69 6f 6e 41  &rc);.  sessionA
1aff0 70 70 65 6e 64 49 64 65 6e 74 28 26 62 75 66 2c  ppendIdent(&buf,
1b000 20 7a 54 61 62 2c 20 26 72 63 29 3b 0a 20 20 73   zTab, &rc);.  s
1b010 65 73 73 69 6f 6e 41 70 70 65 6e 64 53 74 72 28  essionAppendStr(
1b020 26 62 75 66 2c 20 22 20 53 45 54 20 22 2c 20 26  &buf, " SET ", &
1b030 72 63 29 3b 0a 0a 20 20 2f 2a 20 41 70 70 65 6e  rc);..  /* Appen
1b040 64 20 74 68 65 20 61 73 73 69 67 6e 6d 65 6e 74  d the assignment
1b050 73 20 2a 2f 0a 20 20 66 6f 72 28 69 3d 30 3b 20  s */.  for(i=0; 
1b060 69 3c 70 2d 3e 6e 43 6f 6c 3b 20 69 2b 2b 29 7b  i<p->nCol; i++){
1b070 0a 20 20 20 20 73 65 73 73 69 6f 6e 41 70 70 65  .    sessionAppe
1b080 6e 64 53 74 72 28 26 62 75 66 2c 20 7a 53 65 70  ndStr(&buf, zSep
1b090 2c 20 26 72 63 29 3b 0a 20 20 20 20 73 65 73 73  , &rc);.    sess
1b0a0 69 6f 6e 41 70 70 65 6e 64 49 64 65 6e 74 28 26  ionAppendIdent(&
1b0b0 62 75 66 2c 20 70 2d 3e 61 7a 43 6f 6c 5b 69 5d  buf, p->azCol[i]
1b0c0 2c 20 26 72 63 29 3b 0a 20 20 20 20 73 65 73 73  , &rc);.    sess
1b0d0 69 6f 6e 41 70 70 65 6e 64 53 74 72 28 26 62 75  ionAppendStr(&bu
1b0e0 66 2c 20 22 20 3d 20 43 41 53 45 20 57 48 45 4e  f, " = CASE WHEN
1b0f0 20 3f 22 2c 20 26 72 63 29 3b 0a 20 20 20 20 73   ?", &rc);.    s
1b100 65 73 73 69 6f 6e 41 70 70 65 6e 64 49 6e 74 65  essionAppendInte
1b110 67 65 72 28 26 62 75 66 2c 20 69 2a 33 2b 32 2c  ger(&buf, i*3+2,
1b120 20 26 72 63 29 3b 0a 20 20 20 20 73 65 73 73 69   &rc);.    sessi
1b130 6f 6e 41 70 70 65 6e 64 53 74 72 28 26 62 75 66  onAppendStr(&buf
1b140 2c 20 22 20 54 48 45 4e 20 3f 22 2c 20 26 72 63  , " THEN ?", &rc
1b150 29 3b 0a 20 20 20 20 73 65 73 73 69 6f 6e 41 70  );.    sessionAp
1b160 70 65 6e 64 49 6e 74 65 67 65 72 28 26 62 75 66  pendInteger(&buf
1b170 2c 20 69 2a 33 2b 33 2c 20 26 72 63 29 3b 0a 20  , i*3+3, &rc);. 
1b180 20 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64     sessionAppend
1b190 53 74 72 28 26 62 75 66 2c 20 22 20 45 4c 53 45  Str(&buf, " ELSE
1b1a0 20 22 2c 20 26 72 63 29 3b 0a 20 20 20 20 73 65   ", &rc);.    se
1b1b0 73 73 69 6f 6e 41 70 70 65 6e 64 49 64 65 6e 74  ssionAppendIdent
1b1c0 28 26 62 75 66 2c 20 70 2d 3e 61 7a 43 6f 6c 5b  (&buf, p->azCol[
1b1d0 69 5d 2c 20 26 72 63 29 3b 0a 20 20 20 20 73 65  i], &rc);.    se
1b1e0 73 73 69 6f 6e 41 70 70 65 6e 64 53 74 72 28 26  ssionAppendStr(&
1b1f0 62 75 66 2c 20 22 20 45 4e 44 22 2c 20 26 72 63  buf, " END", &rc
1b200 29 3b 0a 20 20 20 20 7a 53 65 70 20 3d 20 22 2c  );.    zSep = ",
1b210 20 22 3b 0a 20 20 7d 0a 0a 20 20 2f 2a 20 41 70   ";.  }..  /* Ap
1b220 70 65 6e 64 20 74 68 65 20 50 4b 20 70 61 72 74  pend the PK part
1b230 20 6f 66 20 74 68 65 20 57 48 45 52 45 20 63 6c   of the WHERE cl
1b240 61 75 73 65 20 2a 2f 0a 20 20 73 65 73 73 69 6f  ause */.  sessio
1b250 6e 41 70 70 65 6e 64 53 74 72 28 26 62 75 66 2c  nAppendStr(&buf,
1b260 20 22 20 57 48 45 52 45 20 22 2c 20 26 72 63 29   " WHERE ", &rc)
1b270 3b 0a 20 20 66 6f 72 28 69 3d 30 3b 20 69 3c 70  ;.  for(i=0; i<p
1b280 2d 3e 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a 20 20  ->nCol; i++){.  
1b290 20 20 69 66 28 20 70 2d 3e 61 62 50 4b 5b 69 5d    if( p->abPK[i]
1b2a0 20 29 7b 0a 20 20 20 20 20 20 73 65 73 73 69 6f   ){.      sessio
1b2b0 6e 41 70 70 65 6e 64 49 64 65 6e 74 28 26 62 75  nAppendIdent(&bu
1b2c0 66 2c 20 70 2d 3e 61 7a 43 6f 6c 5b 69 5d 2c 20  f, p->azCol[i], 
1b2d0 26 72 63 29 3b 0a 20 20 20 20 20 20 73 65 73 73  &rc);.      sess
1b2e0 69 6f 6e 41 70 70 65 6e 64 53 74 72 28 26 62 75  ionAppendStr(&bu
1b2f0 66 2c 20 22 20 3d 20 3f 22 2c 20 26 72 63 29 3b  f, " = ?", &rc);
1b300 0a 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70  .      sessionAp
1b310 70 65 6e 64 49 6e 74 65 67 65 72 28 26 62 75 66  pendInteger(&buf
1b320 2c 20 69 2a 33 2b 31 2c 20 26 72 63 29 3b 0a 20  , i*3+1, &rc);. 
1b330 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70 70 65       sessionAppe
1b340 6e 64 53 74 72 28 26 62 75 66 2c 20 22 20 41 4e  ndStr(&buf, " AN
1b350 44 20 22 2c 20 26 72 63 29 3b 0a 20 20 20 20 7d  D ", &rc);.    }
1b360 0a 20 20 7d 0a 0a 20 20 2f 2a 20 41 70 70 65 6e  .  }..  /* Appen
1b370 64 20 74 68 65 20 6e 6f 6e 2d 50 4b 20 70 61 72  d the non-PK par
1b380 74 20 6f 66 20 74 68 65 20 57 48 45 52 45 20 63  t of the WHERE c
1b390 6c 61 75 73 65 20 2a 2f 0a 20 20 73 65 73 73 69  lause */.  sessi
1b3a0 6f 6e 41 70 70 65 6e 64 53 74 72 28 26 62 75 66  onAppendStr(&buf
1b3b0 2c 20 22 20 28 3f 22 2c 20 26 72 63 29 3b 0a 20  , " (?", &rc);. 
1b3c0 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 49 6e   sessionAppendIn
1b3d0 74 65 67 65 72 28 26 62 75 66 2c 20 70 2d 3e 6e  teger(&buf, p->n
1b3e0 43 6f 6c 2a 33 2b 31 2c 20 26 72 63 29 3b 0a 20  Col*3+1, &rc);. 
1b3f0 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 53 74   sessionAppendSt
1b400 72 28 26 62 75 66 2c 20 22 20 4f 52 20 31 22 2c  r(&buf, " OR 1",
1b410 20 26 72 63 29 3b 0a 20 20 66 6f 72 28 69 3d 30   &rc);.  for(i=0
1b420 3b 20 69 3c 70 2d 3e 6e 43 6f 6c 3b 20 69 2b 2b  ; i<p->nCol; i++
1b430 29 7b 0a 20 20 20 20 69 66 28 20 21 70 2d 3e 61  ){.    if( !p->a
1b440 62 50 4b 5b 69 5d 20 29 7b 0a 20 20 20 20 20 20  bPK[i] ){.      
1b450 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 53 74 72  sessionAppendStr
1b460 28 26 62 75 66 2c 20 22 20 41 4e 44 20 28 3f 22  (&buf, " AND (?"
1b470 2c 20 26 72 63 29 3b 0a 20 20 20 20 20 20 73 65  , &rc);.      se
1b480 73 73 69 6f 6e 41 70 70 65 6e 64 49 6e 74 65 67  ssionAppendInteg
1b490 65 72 28 26 62 75 66 2c 20 69 2a 33 2b 32 2c 20  er(&buf, i*3+2, 
1b4a0 26 72 63 29 3b 0a 20 20 20 20 20 20 73 65 73 73  &rc);.      sess
1b4b0 69 6f 6e 41 70 70 65 6e 64 53 74 72 28 26 62 75  ionAppendStr(&bu
1b4c0 66 2c 20 22 3d 30 20 4f 52 20 22 2c 20 26 72 63  f, "=0 OR ", &rc
1b4d0 29 3b 0a 20 20 20 20 20 20 73 65 73 73 69 6f 6e  );.      session
1b4e0 41 70 70 65 6e 64 49 64 65 6e 74 28 26 62 75 66  AppendIdent(&buf
1b4f0 2c 20 70 2d 3e 61 7a 43 6f 6c 5b 69 5d 2c 20 26  , p->azCol[i], &
1b500 72 63 29 3b 0a 20 20 20 20 20 20 73 65 73 73 69  rc);.      sessi
1b510 6f 6e 41 70 70 65 6e 64 53 74 72 28 26 62 75 66  onAppendStr(&buf
1b520 2c 20 22 20 49 53 20 3f 22 2c 20 26 72 63 29 3b  , " IS ?", &rc);
1b530 0a 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70  .      sessionAp
1b540 70 65 6e 64 49 6e 74 65 67 65 72 28 26 62 75 66  pendInteger(&buf
1b550 2c 20 69 2a 33 2b 31 2c 20 26 72 63 29 3b 0a 20  , i*3+1, &rc);. 
1b560 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70 70 65       sessionAppe
1b570 6e 64 53 74 72 28 26 62 75 66 2c 20 22 29 22 2c  ndStr(&buf, ")",
1b580 20 26 72 63 29 3b 0a 20 20 20 20 7d 0a 20 20 7d   &rc);.    }.  }
1b590 0a 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64  .  sessionAppend
1b5a0 53 74 72 28 26 62 75 66 2c 20 22 29 22 2c 20 26  Str(&buf, ")", &
1b5b0 72 63 29 3b 0a 0a 20 20 69 66 28 20 72 63 3d 3d  rc);..  if( rc==
1b5c0 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20  SQLITE_OK ){.   
1b5d0 20 72 63 20 3d 20 73 71 6c 69 74 65 33 5f 70 72   rc = sqlite3_pr
1b5e0 65 70 61 72 65 5f 76 32 28 64 62 2c 20 28 63 68  epare_v2(db, (ch
1b5f0 61 72 20 2a 29 62 75 66 2e 61 42 75 66 2c 20 62  ar *)buf.aBuf, b
1b600 75 66 2e 6e 42 75 66 2c 20 26 70 2d 3e 70 55 70  uf.nBuf, &p->pUp
1b610 64 61 74 65 2c 20 30 29 3b 0a 20 20 7d 0a 20 20  date, 0);.  }.  
1b620 73 71 6c 69 74 65 33 5f 66 72 65 65 28 62 75 66  sqlite3_free(buf
1b630 2e 61 42 75 66 29 3b 0a 0a 20 20 72 65 74 75 72  .aBuf);..  retur
1b640 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 46  n rc;.}../*.** F
1b650 6f 72 6d 75 6c 61 74 65 20 61 6e 64 20 70 72 65  ormulate and pre
1b660 70 61 72 65 20 61 6e 20 53 51 4c 20 73 74 61 74  pare an SQL stat
1b670 65 6d 65 6e 74 20 74 6f 20 71 75 65 72 79 20 74  ement to query t
1b680 61 62 6c 65 20 7a 54 61 62 20 62 79 20 70 72 69  able zTab by pri
1b690 6d 61 72 79 0a 2a 2a 20 6b 65 79 2e 20 41 73 73  mary.** key. Ass
1b6a0 75 6d 69 6e 67 20 74 68 65 20 66 6f 6c 6c 6f 77  uming the follow
1b6b0 69 6e 67 20 74 61 62 6c 65 20 73 74 72 75 63 74  ing table struct
1b6c0 75 72 65 3a 0a 2a 2a 0a 2a 2a 20 20 20 20 20 43  ure:.**.**     C
1b6d0 52 45 41 54 45 20 54 41 42 4c 45 20 78 28 61 2c  REATE TABLE x(a,
1b6e0 20 62 2c 20 63 2c 20 64 2c 20 50 52 49 4d 41 52   b, c, d, PRIMAR
1b6f0 59 20 4b 45 59 28 61 2c 20 63 29 29 3b 0a 2a 2a  Y KEY(a, c));.**
1b700 0a 2a 2a 20 54 68 65 20 53 45 4c 45 43 54 20 73  .** The SELECT s
1b710 74 61 74 65 6d 65 6e 74 20 6c 6f 6f 6b 73 20 6c  tatement looks l
1b720 69 6b 65 20 74 68 69 73 3a 0a 2a 2a 0a 2a 2a 20  ike this:.**.** 
1b730 20 20 20 20 53 45 4c 45 43 54 20 2a 20 46 52 4f      SELECT * FRO
1b740 4d 20 78 20 57 48 45 52 45 20 61 20 3d 20 3f 31  M x WHERE a = ?1
1b750 20 41 4e 44 20 63 20 3d 20 3f 33 0a 2a 2a 0a 2a   AND c = ?3.**.*
1b760 2a 20 49 66 20 73 75 63 63 65 73 73 66 75 6c 2c  * If successful,
1b770 20 53 51 4c 49 54 45 5f 4f 4b 20 69 73 20 72 65   SQLITE_OK is re
1b780 74 75 72 6e 65 64 20 61 6e 64 20 53 65 73 73 69  turned and Sessi
1b790 6f 6e 41 70 70 6c 79 43 74 78 2e 70 53 65 6c 65  onApplyCtx.pSele
1b7a0 63 74 20 69 73 20 6c 65 66 74 0a 2a 2a 20 70 6f  ct is left.** po
1b7b0 69 6e 74 69 6e 67 20 74 6f 20 74 68 65 20 70 72  inting to the pr
1b7c0 65 70 61 72 65 64 20 76 65 72 73 69 6f 6e 20 6f  epared version o
1b7d0 66 20 74 68 65 20 53 51 4c 20 73 74 61 74 65 6d  f the SQL statem
1b7e0 65 6e 74 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69  ent..*/.static i
1b7f0 6e 74 20 73 65 73 73 69 6f 6e 53 65 6c 65 63 74  nt sessionSelect
1b800 52 6f 77 28 0a 20 20 73 71 6c 69 74 65 33 20 2a  Row(.  sqlite3 *
1b810 64 62 2c 20 20 20 20 20 20 20 20 20 20 20 20 20  db,             
1b820 20 20 20 20 20 20 20 2f 2a 20 44 61 74 61 62 61         /* Databa
1b830 73 65 20 68 61 6e 64 6c 65 20 2a 2f 0a 20 20 63  se handle */.  c
1b840 6f 6e 73 74 20 63 68 61 72 20 2a 7a 54 61 62 2c  onst char *zTab,
1b850 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
1b860 2a 20 54 61 62 6c 65 20 6e 61 6d 65 20 2a 2f 0a  * Table name */.
1b870 20 20 53 65 73 73 69 6f 6e 41 70 70 6c 79 43 74    SessionApplyCt
1b880 78 20 2a 70 20 20 20 20 20 20 20 20 20 20 20 20  x *p            
1b890 20 20 2f 2a 20 53 65 73 73 69 6f 6e 20 63 68 61    /* Session cha
1b8a0 6e 67 65 73 65 74 2d 61 70 70 6c 79 20 63 6f 6e  ngeset-apply con
1b8b0 74 65 78 74 20 2a 2f 0a 29 7b 0a 20 20 72 65 74  text */.){.  ret
1b8c0 75 72 6e 20 73 65 73 73 69 6f 6e 53 65 6c 65 63  urn sessionSelec
1b8d0 74 53 74 6d 74 28 0a 20 20 20 20 20 20 64 62 2c  tStmt(.      db,
1b8e0 20 22 6d 61 69 6e 22 2c 20 7a 54 61 62 2c 20 70   "main", zTab, p
1b8f0 2d 3e 6e 43 6f 6c 2c 20 70 2d 3e 61 7a 43 6f 6c  ->nCol, p->azCol
1b900 2c 20 70 2d 3e 61 62 50 4b 2c 20 26 70 2d 3e 70  , p->abPK, &p->p
1b910 53 65 6c 65 63 74 29 3b 0a 7d 0a 0a 2f 2a 0a 2a  Select);.}../*.*
1b920 2a 20 46 6f 72 6d 75 6c 61 74 65 20 61 6e 64 20  * Formulate and 
1b930 70 72 65 70 61 72 65 20 61 6e 20 49 4e 53 45 52  prepare an INSER
1b940 54 20 73 74 61 74 65 6d 65 6e 74 20 74 6f 20 61  T statement to a
1b950 64 64 20 61 20 72 65 63 6f 72 64 20 74 6f 20 74  dd a record to t
1b960 61 62 6c 65 20 7a 54 61 62 2e 0a 2a 2a 20 46 6f  able zTab..** Fo
1b970 72 20 65 78 61 6d 70 6c 65 3a 0a 2a 2a 0a 2a 2a  r example:.**.**
1b980 20 20 20 20 20 49 4e 53 45 52 54 20 49 4e 54 4f       INSERT INTO
1b990 20 6d 61 69 6e 2e 22 7a 54 61 62 22 20 56 41 4c   main."zTab" VAL
1b9a0 55 45 53 28 3f 31 2c 20 3f 32 2c 20 3f 33 20 2e  UES(?1, ?2, ?3 .
1b9b0 2e 2e 29 3b 0a 2a 2a 0a 2a 2a 20 49 66 20 73 75  ..);.**.** If su
1b9c0 63 63 65 73 73 66 75 6c 2c 20 53 51 4c 49 54 45  ccessful, SQLITE
1b9d0 5f 4f 4b 20 69 73 20 72 65 74 75 72 6e 65 64 20  _OK is returned 
1b9e0 61 6e 64 20 53 65 73 73 69 6f 6e 41 70 70 6c 79  and SessionApply
1b9f0 43 74 78 2e 70 49 6e 73 65 72 74 20 69 73 20 6c  Ctx.pInsert is l
1ba00 65 66 74 0a 2a 2a 20 70 6f 69 6e 74 69 6e 67 20  eft.** pointing 
1ba10 74 6f 20 74 68 65 20 70 72 65 70 61 72 65 64 20  to the prepared 
1ba20 76 65 72 73 69 6f 6e 20 6f 66 20 74 68 65 20 53  version of the S
1ba30 51 4c 20 73 74 61 74 65 6d 65 6e 74 2e 0a 2a 2f  QL statement..*/
1ba40 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73 73  .static int sess
1ba50 69 6f 6e 49 6e 73 65 72 74 52 6f 77 28 0a 20 20  ionInsertRow(.  
1ba60 73 71 6c 69 74 65 33 20 2a 64 62 2c 20 20 20 20  sqlite3 *db,    
1ba70 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1ba80 2f 2a 20 44 61 74 61 62 61 73 65 20 68 61 6e 64  /* Database hand
1ba90 6c 65 20 2a 2f 0a 20 20 63 6f 6e 73 74 20 63 68  le */.  const ch
1baa0 61 72 20 2a 7a 54 61 62 2c 20 20 20 20 20 20 20  ar *zTab,       
1bab0 20 20 20 20 20 20 20 20 2f 2a 20 54 61 62 6c 65          /* Table
1bac0 20 6e 61 6d 65 20 2a 2f 0a 20 20 53 65 73 73 69   name */.  Sessi
1bad0 6f 6e 41 70 70 6c 79 43 74 78 20 2a 70 20 20 20  onApplyCtx *p   
1bae0 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 53 65             /* Se
1baf0 73 73 69 6f 6e 20 63 68 61 6e 67 65 73 65 74 2d  ssion changeset-
1bb00 61 70 70 6c 79 20 63 6f 6e 74 65 78 74 20 2a 2f  apply context */
1bb10 0a 29 7b 0a 20 20 69 6e 74 20 72 63 20 3d 20 53  .){.  int rc = S
1bb20 51 4c 49 54 45 5f 4f 4b 3b 0a 20 20 69 6e 74 20  QLITE_OK;.  int 
1bb30 69 3b 0a 20 20 53 65 73 73 69 6f 6e 42 75 66 66  i;.  SessionBuff
1bb40 65 72 20 62 75 66 20 3d 20 7b 30 2c 20 30 2c 20  er buf = {0, 0, 
1bb50 30 7d 3b 0a 0a 20 20 73 65 73 73 69 6f 6e 41 70  0};..  sessionAp
1bb60 70 65 6e 64 53 74 72 28 26 62 75 66 2c 20 22 49  pendStr(&buf, "I
1bb70 4e 53 45 52 54 20 49 4e 54 4f 20 6d 61 69 6e 2e  NSERT INTO main.
1bb80 22 2c 20 26 72 63 29 3b 0a 20 20 73 65 73 73 69  ", &rc);.  sessi
1bb90 6f 6e 41 70 70 65 6e 64 49 64 65 6e 74 28 26 62  onAppendIdent(&b
1bba0 75 66 2c 20 7a 54 61 62 2c 20 26 72 63 29 3b 0a  uf, zTab, &rc);.
1bbb0 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 53    sessionAppendS
1bbc0 74 72 28 26 62 75 66 2c 20 22 28 22 2c 20 26 72  tr(&buf, "(", &r
1bbd0 63 29 3b 0a 20 20 66 6f 72 28 69 3d 30 3b 20 69  c);.  for(i=0; i
1bbe0 3c 70 2d 3e 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a  <p->nCol; i++){.
1bbf0 20 20 20 20 69 66 28 20 69 21 3d 30 20 29 20 73      if( i!=0 ) s
1bc00 65 73 73 69 6f 6e 41 70 70 65 6e 64 53 74 72 28  essionAppendStr(
1bc10 26 62 75 66 2c 20 22 2c 20 22 2c 20 26 72 63 29  &buf, ", ", &rc)
1bc20 3b 0a 20 20 20 20 73 65 73 73 69 6f 6e 41 70 70  ;.    sessionApp
1bc30 65 6e 64 49 64 65 6e 74 28 26 62 75 66 2c 20 70  endIdent(&buf, p
1bc40 2d 3e 61 7a 43 6f 6c 5b 69 5d 2c 20 26 72 63 29  ->azCol[i], &rc)
1bc50 3b 0a 20 20 7d 0a 0a 20 20 73 65 73 73 69 6f 6e  ;.  }..  session
1bc60 41 70 70 65 6e 64 53 74 72 28 26 62 75 66 2c 20  AppendStr(&buf, 
1bc70 22 29 20 56 41 4c 55 45 53 28 3f 22 2c 20 26 72  ") VALUES(?", &r
1bc80 63 29 3b 0a 20 20 66 6f 72 28 69 3d 31 3b 20 69  c);.  for(i=1; i
1bc90 3c 70 2d 3e 6e 43 6f 6c 3b 20 69 2b 2b 29 7b 0a  <p->nCol; i++){.
1bca0 20 20 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e      sessionAppen
1bcb0 64 53 74 72 28 26 62 75 66 2c 20 22 2c 20 3f 22  dStr(&buf, ", ?"
1bcc0 2c 20 26 72 63 29 3b 0a 20 20 7d 0a 20 20 73 65  , &rc);.  }.  se
1bcd0 73 73 69 6f 6e 41 70 70 65 6e 64 53 74 72 28 26  ssionAppendStr(&
1bce0 62 75 66 2c 20 22 29 22 2c 20 26 72 63 29 3b 0a  buf, ")", &rc);.
1bcf0 0a 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54  .  if( rc==SQLIT
1bd00 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 72 63 20 3d  E_OK ){.    rc =
1bd10 20 73 71 6c 69 74 65 33 5f 70 72 65 70 61 72 65   sqlite3_prepare
1bd20 5f 76 32 28 64 62 2c 20 28 63 68 61 72 20 2a 29  _v2(db, (char *)
1bd30 62 75 66 2e 61 42 75 66 2c 20 62 75 66 2e 6e 42  buf.aBuf, buf.nB
1bd40 75 66 2c 20 26 70 2d 3e 70 49 6e 73 65 72 74 2c  uf, &p->pInsert,
1bd50 20 30 29 3b 0a 20 20 7d 0a 20 20 73 71 6c 69 74   0);.  }.  sqlit
1bd60 65 33 5f 66 72 65 65 28 62 75 66 2e 61 42 75 66  e3_free(buf.aBuf
1bd70 29 3b 0a 20 20 72 65 74 75 72 6e 20 72 63 3b 0a  );.  return rc;.
1bd80 7d 0a 0a 2f 2a 0a 2a 2a 20 41 20 77 72 61 70 70  }../*.** A wrapp
1bd90 65 72 20 61 72 6f 75 6e 64 20 73 71 6c 69 74 65  er around sqlite
1bda0 33 5f 62 69 6e 64 5f 76 61 6c 75 65 28 29 20 74  3_bind_value() t
1bdb0 68 61 74 20 64 65 74 65 63 74 73 20 61 6e 20 65  hat detects an e
1bdc0 78 74 72 61 20 70 72 6f 62 6c 65 6d 2e 20 0a 2a  xtra problem. .*
1bdd0 2a 20 53 65 65 20 63 6f 6d 6d 65 6e 74 73 20 69  * See comments i
1bde0 6e 20 74 68 65 20 62 6f 64 79 20 6f 66 20 74 68  n the body of th
1bdf0 69 73 20 66 75 6e 63 74 69 6f 6e 20 66 6f 72 20  is function for 
1be00 64 65 74 61 69 6c 73 2e 0a 2a 2f 0a 73 74 61 74  details..*/.stat
1be10 69 63 20 69 6e 74 20 73 65 73 73 69 6f 6e 42 69  ic int sessionBi
1be20 6e 64 56 61 6c 75 65 28 0a 20 20 73 71 6c 69 74  ndValue(.  sqlit
1be30 65 33 5f 73 74 6d 74 20 2a 70 53 74 6d 74 2c 20  e3_stmt *pStmt, 
1be40 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 53 74             /* St
1be50 61 74 65 6d 65 6e 74 20 74 6f 20 62 69 6e 64 20  atement to bind 
1be60 76 61 6c 75 65 20 74 6f 20 2a 2f 0a 20 20 69 6e  value to */.  in
1be70 74 20 69 2c 20 20 20 20 20 20 20 20 20 20 20 20  t i,            
1be80 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
1be90 20 50 61 72 61 6d 65 74 65 72 20 6e 75 6d 62 65   Parameter numbe
1bea0 72 20 74 6f 20 62 69 6e 64 20 74 6f 20 2a 2f 0a  r to bind to */.
1beb0 20 20 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 20    sqlite3_value 
1bec0 2a 70 56 61 6c 20 20 20 20 20 20 20 20 20 20 20  *pVal           
1bed0 20 20 2f 2a 20 56 61 6c 75 65 20 74 6f 20 62 69    /* Value to bi
1bee0 6e 64 20 2a 2f 0a 29 7b 0a 20 20 69 6e 74 20 65  nd */.){.  int e
1bef0 54 79 70 65 20 3d 20 73 71 6c 69 74 65 33 5f 76  Type = sqlite3_v
1bf00 61 6c 75 65 5f 74 79 70 65 28 70 56 61 6c 29 3b  alue_type(pVal);
1bf10 0a 20 20 2f 2a 20 43 4f 56 45 52 41 47 45 3a 20  .  /* COVERAGE: 
1bf20 54 68 65 20 28 70 56 61 6c 2d 3e 7a 3d 3d 30 29  The (pVal->z==0)
1bf30 20 62 72 61 6e 63 68 20 69 73 20 6e 65 76 65 72   branch is never
1bf40 20 74 72 75 65 20 75 73 69 6e 67 20 63 75 72 72   true using curr
1bf50 65 6e 74 20 76 65 72 73 69 6f 6e 73 0a 20 20 2a  ent versions.  *
1bf60 2a 20 6f 66 20 53 51 4c 69 74 65 2e 20 49 66 20  * of SQLite. If 
1bf70 61 20 6d 61 6c 6c 6f 63 20 66 61 69 6c 73 20 69  a malloc fails i
1bf80 6e 20 61 6e 20 73 71 6c 69 74 65 33 5f 76 61 6c  n an sqlite3_val
1bf90 75 65 5f 78 78 78 28 29 20 66 75 6e 63 74 69 6f  ue_xxx() functio
1bfa0 6e 2c 20 65 69 74 68 65 72 0a 20 20 2a 2a 20 74  n, either.  ** t
1bfb0 68 65 20 28 70 56 61 6c 2d 3e 7a 29 20 76 61 72  he (pVal->z) var
1bfc0 69 61 62 6c 65 20 72 65 6d 61 69 6e 73 20 61 73  iable remains as
1bfd0 20 69 74 20 77 61 73 20 6f 72 20 74 68 65 20 74   it was or the t
1bfe0 79 70 65 20 6f 66 20 74 68 65 20 76 61 6c 75 65  ype of the value
1bff0 20 69 73 0a 20 20 2a 2a 20 73 65 74 20 74 6f 20   is.  ** set to 
1c000 53 51 4c 49 54 45 5f 4e 55 4c 4c 2e 20 20 2a 2f  SQLITE_NULL.  */
1c010 0a 20 20 69 66 28 20 28 65 54 79 70 65 3d 3d 53  .  if( (eType==S
1c020 51 4c 49 54 45 5f 54 45 58 54 20 7c 7c 20 65 54  QLITE_TEXT || eT
1c030 79 70 65 3d 3d 53 51 4c 49 54 45 5f 42 4c 4f 42  ype==SQLITE_BLOB
1c040 29 20 26 26 20 70 56 61 6c 2d 3e 7a 3d 3d 30 20  ) && pVal->z==0 
1c050 29 7b 0a 20 20 20 20 2f 2a 20 54 68 69 73 20 63  ){.    /* This c
1c060 6f 6e 64 69 74 69 6f 6e 20 6f 63 63 75 72 73 20  ondition occurs 
1c070 77 68 65 6e 20 61 6e 20 65 61 72 6c 69 65 72 20  when an earlier 
1c080 4f 4f 4d 20 69 6e 20 61 20 63 61 6c 6c 20 74 6f  OOM in a call to
1c090 0a 20 20 20 20 2a 2a 20 73 71 6c 69 74 65 33 5f  .    ** sqlite3_
1c0a0 76 61 6c 75 65 5f 74 65 78 74 28 29 20 6f 72 20  value_text() or 
1c0b0 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 5f 62 6c  sqlite3_value_bl
1c0c0 6f 62 28 29 20 28 70 65 72 68 61 70 73 20 66 72  ob() (perhaps fr
1c0d0 6f 6d 20 77 69 74 68 69 6e 0a 20 20 20 20 2a 2a  om within.    **
1c0e0 20 61 20 63 6f 6e 66 6c 69 63 74 2d 68 61 6e 64   a conflict-hand
1c0f0 6c 65 72 29 20 68 61 73 20 7a 65 72 6f 65 64 20  ler) has zeroed 
1c100 74 68 65 20 70 56 61 6c 2d 3e 7a 20 70 6f 69 6e  the pVal->z poin
1c110 74 65 72 2e 20 52 65 74 75 72 6e 20 4e 4f 4d 45  ter. Return NOME
1c120 4d 2e 20 2a 2f 0a 20 20 20 20 72 65 74 75 72 6e  M. */.    return
1c130 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 3b 0a 20   SQLITE_NOMEM;. 
1c140 20 7d 0a 20 20 72 65 74 75 72 6e 20 73 71 6c 69   }.  return sqli
1c150 74 65 33 5f 62 69 6e 64 5f 76 61 6c 75 65 28 70  te3_bind_value(p
1c160 53 74 6d 74 2c 20 69 2c 20 70 56 61 6c 29 3b 0a  Stmt, i, pVal);.
1c170 7d 0a 0a 2f 2a 0a 2a 2a 20 49 74 65 72 61 74 6f  }../*.** Iterato
1c180 72 20 70 49 74 65 72 20 6d 75 73 74 20 70 6f 69  r pIter must poi
1c190 6e 74 20 74 6f 20 61 6e 20 53 51 4c 49 54 45 5f  nt to an SQLITE_
1c1a0 49 4e 53 45 52 54 20 65 6e 74 72 79 2e 20 54 68  INSERT entry. Th
1c1b0 69 73 20 66 75 6e 63 74 69 6f 6e 20 0a 2a 2a 20  is function .** 
1c1c0 74 72 61 6e 73 66 65 72 73 20 6e 65 77 2e 2a 20  transfers new.* 
1c1d0 76 61 6c 75 65 73 20 66 72 6f 6d 20 74 68 65 20  values from the 
1c1e0 63 75 72 72 65 6e 74 20 69 74 65 72 61 74 6f 72  current iterator
1c1f0 20 65 6e 74 72 79 20 74 6f 20 73 74 61 74 65 6d   entry to statem
1c200 65 6e 74 0a 2a 2a 20 70 53 74 6d 74 2e 20 54 68  ent.** pStmt. Th
1c210 65 20 74 61 62 6c 65 20 62 65 69 6e 67 20 69 6e  e table being in
1c220 73 65 72 74 65 64 20 69 6e 74 6f 20 68 61 73 20  serted into has 
1c230 6e 43 6f 6c 20 63 6f 6c 75 6d 6e 73 2e 0a 2a 2a  nCol columns..**
1c240 0a 2a 2a 20 4e 65 77 2e 2a 20 76 61 6c 75 65 20  .** New.* value 
1c250 24 69 20 66 72 6f 6d 20 74 68 65 20 69 74 65 72  $i from the iter
1c260 61 74 6f 72 20 69 73 20 62 6f 75 6e 64 20 74 6f  ator is bound to
1c270 20 76 61 72 69 61 62 6c 65 20 28 24 69 2b 31 29   variable ($i+1)
1c280 20 6f 66 20 0a 2a 2a 20 73 74 61 74 65 6d 65 6e   of .** statemen
1c290 74 20 70 53 74 6d 74 2e 20 49 66 20 70 61 72 61  t pStmt. If para
1c2a0 6d 65 74 65 72 20 61 62 50 4b 20 69 73 20 4e 55  meter abPK is NU
1c2b0 4c 4c 2c 20 61 6c 6c 20 76 61 6c 75 65 73 20 66  LL, all values f
1c2c0 72 6f 6d 20 30 20 74 6f 20 28 6e 43 6f 6c 2d 31  rom 0 to (nCol-1
1c2d0 29 0a 2a 2a 20 61 72 65 20 74 72 61 6e 73 66 65  ).** are transfe
1c2e0 72 65 64 20 74 6f 20 74 68 65 20 73 74 61 74 65  red to the state
1c2f0 6d 65 6e 74 2e 20 4f 74 68 65 72 77 69 73 65 2c  ment. Otherwise,
1c300 20 69 66 20 61 62 50 4b 20 69 73 20 6e 6f 74 20   if abPK is not 
1c310 4e 55 4c 4c 2c 20 69 74 20 70 6f 69 6e 74 73 0a  NULL, it points.
1c320 2a 2a 20 74 6f 20 61 6e 20 61 72 72 61 79 20 6e  ** to an array n
1c330 43 6f 6c 20 65 6c 65 6d 65 6e 74 73 20 69 6e 20  Col elements in 
1c340 73 69 7a 65 2e 20 49 6e 20 74 68 69 73 20 63 61  size. In this ca
1c350 73 65 20 6f 6e 6c 79 20 74 68 6f 73 65 20 76 61  se only those va
1c360 6c 75 65 73 20 66 6f 72 20 0a 2a 2a 20 77 68 69  lues for .** whi
1c370 63 68 20 61 62 50 4b 5b 24 69 5d 20 69 73 20 74  ch abPK[$i] is t
1c380 72 75 65 20 61 72 65 20 72 65 61 64 20 66 72 6f  rue are read fro
1c390 6d 20 74 68 65 20 69 74 65 72 61 74 6f 72 20 61  m the iterator a
1c3a0 6e 64 20 62 6f 75 6e 64 20 74 6f 20 74 68 65 20  nd bound to the 
1c3b0 0a 2a 2a 20 73 74 61 74 65 6d 65 6e 74 2e 0a 2a  .** statement..*
1c3c0 2a 0a 2a 2a 20 41 6e 20 53 51 4c 69 74 65 20 65  *.** An SQLite e
1c3d0 72 72 6f 72 20 63 6f 64 65 20 69 73 20 72 65 74  rror code is ret
1c3e0 75 72 6e 65 64 20 69 66 20 61 6e 20 65 72 72 6f  urned if an erro
1c3f0 72 20 6f 63 63 75 72 73 2e 20 4f 74 68 65 72 77  r occurs. Otherw
1c400 69 73 65 2c 20 53 51 4c 49 54 45 5f 4f 4b 2e 0a  ise, SQLITE_OK..
1c410 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65  */.static int se
1c420 73 73 69 6f 6e 42 69 6e 64 52 6f 77 28 0a 20 20  ssionBindRow(.  
1c430 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 73 65  sqlite3_changese
1c440 74 5f 69 74 65 72 20 2a 70 49 74 65 72 2c 20 20  t_iter *pIter,  
1c450 2f 2a 20 49 74 65 72 61 74 6f 72 20 74 6f 20 72  /* Iterator to r
1c460 65 61 64 20 76 61 6c 75 65 73 20 66 72 6f 6d 20  ead values from 
1c470 2a 2f 0a 20 20 69 6e 74 28 2a 78 56 61 6c 75 65  */.  int(*xValue
1c480 29 28 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65  )(sqlite3_change
1c490 73 65 74 5f 69 74 65 72 20 2a 2c 20 69 6e 74 2c  set_iter *, int,
1c4a0 20 73 71 6c 69 74 65 33 5f 76 61 6c 75 65 20 2a   sqlite3_value *
1c4b0 2a 29 2c 0a 20 20 69 6e 74 20 6e 43 6f 6c 2c 20  *),.  int nCol, 
1c4c0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1c4d0 20 20 20 20 20 20 2f 2a 20 4e 75 6d 62 65 72 20        /* Number 
1c4e0 6f 66 20 63 6f 6c 75 6d 6e 73 20 2a 2f 0a 20 20  of columns */.  
1c4f0 75 38 20 2a 61 62 50 4b 2c 20 20 20 20 20 20 20  u8 *abPK,       
1c500 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1c510 2f 2a 20 49 66 20 6e 6f 74 20 4e 55 4c 4c 2c 20  /* If not NULL, 
1c520 62 69 6e 64 20 6f 6e 6c 79 20 69 66 20 74 72 75  bind only if tru
1c530 65 20 2a 2f 0a 20 20 73 71 6c 69 74 65 33 5f 73  e */.  sqlite3_s
1c540 74 6d 74 20 2a 70 53 74 6d 74 20 20 20 20 20 20  tmt *pStmt      
1c550 20 20 20 20 20 20 20 2f 2a 20 42 69 6e 64 20 76         /* Bind v
1c560 61 6c 75 65 73 20 74 6f 20 74 68 69 73 20 73 74  alues to this st
1c570 61 74 65 6d 65 6e 74 20 2a 2f 0a 29 7b 0a 20 20  atement */.){.  
1c580 69 6e 74 20 69 3b 0a 20 20 69 6e 74 20 72 63 20  int i;.  int rc 
1c590 3d 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a 0a 20 20  = SQLITE_OK;..  
1c5a0 2f 2a 20 4e 65 69 74 68 65 72 20 73 71 6c 69 74  /* Neither sqlit
1c5b0 65 33 63 68 61 6e 67 65 73 65 74 5f 6f 6c 64 20  e3changeset_old 
1c5c0 6f 72 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65  or sqlite3change
1c5d0 73 65 74 5f 6e 65 77 20 63 61 6e 20 66 61 69 6c  set_new can fail
1c5e0 20 69 66 20 74 68 65 0a 20 20 2a 2a 20 61 72 67   if the.  ** arg
1c5f0 75 6d 65 6e 74 20 69 74 65 72 61 74 6f 72 20 70  ument iterator p
1c600 6f 69 6e 74 73 20 74 6f 20 61 20 73 75 69 74 61  oints to a suita
1c610 62 6c 65 20 65 6e 74 72 79 2e 20 4d 61 6b 65 20  ble entry. Make 
1c620 73 75 72 65 20 74 68 61 74 20 78 56 61 6c 75 65  sure that xValue
1c630 20 0a 20 20 2a 2a 20 69 73 20 6f 6e 65 20 6f 66   .  ** is one of
1c640 20 74 68 65 73 65 20 74 6f 20 67 75 61 72 61 6e   these to guaran
1c650 74 65 65 20 74 68 61 74 20 69 74 20 69 73 20 73  tee that it is s
1c660 61 66 65 20 74 6f 20 69 67 6e 6f 72 65 20 74 68  afe to ignore th
1c670 65 20 72 65 74 75 72 6e 20 0a 20 20 2a 2a 20 69  e return .  ** i
1c680 6e 20 74 68 65 20 63 6f 64 65 20 62 65 6c 6f 77  n the code below
1c690 2e 20 2a 2f 0a 20 20 61 73 73 65 72 74 28 20 78  . */.  assert( x
1c6a0 56 61 6c 75 65 3d 3d 73 71 6c 69 74 65 33 63 68  Value==sqlite3ch
1c6b0 61 6e 67 65 73 65 74 5f 6f 6c 64 20 7c 7c 20 78  angeset_old || x
1c6c0 56 61 6c 75 65 3d 3d 73 71 6c 69 74 65 33 63 68  Value==sqlite3ch
1c6d0 61 6e 67 65 73 65 74 5f 6e 65 77 20 29 3b 0a 0a  angeset_new );..
1c6e0 20 20 66 6f 72 28 69 3d 30 3b 20 72 63 3d 3d 53    for(i=0; rc==S
1c6f0 51 4c 49 54 45 5f 4f 4b 20 26 26 20 69 3c 6e 43  QLITE_OK && i<nC
1c700 6f 6c 3b 20 69 2b 2b 29 7b 0a 20 20 20 20 69 66  ol; i++){.    if
1c710 28 20 21 61 62 50 4b 20 7c 7c 20 61 62 50 4b 5b  ( !abPK || abPK[
1c720 69 5d 20 29 7b 0a 20 20 20 20 20 20 73 71 6c 69  i] ){.      sqli
1c730 74 65 33 5f 76 61 6c 75 65 20 2a 70 56 61 6c 3b  te3_value *pVal;
1c740 0a 20 20 20 20 20 20 28 76 6f 69 64 29 78 56 61  .      (void)xVa
1c750 6c 75 65 28 70 49 74 65 72 2c 20 69 2c 20 26 70  lue(pIter, i, &p
1c760 56 61 6c 29 3b 0a 20 20 20 20 20 20 72 63 20 3d  Val);.      rc =
1c770 20 73 65 73 73 69 6f 6e 42 69 6e 64 56 61 6c 75   sessionBindValu
1c780 65 28 70 53 74 6d 74 2c 20 69 2b 31 2c 20 70 56  e(pStmt, i+1, pV
1c790 61 6c 29 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a 20  al);.    }.  }. 
1c7a0 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f   return rc;.}../
1c7b0 2a 0a 2a 2a 20 53 51 4c 20 73 74 61 74 65 6d 65  *.** SQL stateme
1c7c0 6e 74 20 70 53 65 6c 65 63 74 20 69 73 20 61 73  nt pSelect is as
1c7d0 20 67 65 6e 65 72 61 74 65 64 20 62 79 20 74 68   generated by th
1c7e0 65 20 73 65 73 73 69 6f 6e 53 65 6c 65 63 74 52  e sessionSelectR
1c7f0 6f 77 28 29 20 66 75 6e 63 74 69 6f 6e 2e 0a 2a  ow() function..*
1c800 2a 20 54 68 69 73 20 66 75 6e 63 74 69 6f 6e 20  * This function 
1c810 62 69 6e 64 73 20 74 68 65 20 70 72 69 6d 61 72  binds the primar
1c820 79 20 6b 65 79 20 76 61 6c 75 65 73 20 66 72 6f  y key values fro
1c830 6d 20 74 68 65 20 63 68 61 6e 67 65 20 74 68 61  m the change tha
1c840 74 20 63 68 61 6e 67 65 73 65 74 0a 2a 2a 20 69  t changeset.** i
1c850 74 65 72 61 74 6f 72 20 70 49 74 65 72 20 70 6f  terator pIter po
1c860 69 6e 74 73 20 74 6f 20 74 6f 20 74 68 65 20 53  ints to to the S
1c870 45 4c 45 43 54 20 61 6e 64 20 61 74 74 65 6d 70  ELECT and attemp
1c880 74 73 20 74 6f 20 73 65 65 6b 20 74 6f 20 74 68  ts to seek to th
1c890 65 20 74 61 62 6c 65 0a 2a 2a 20 65 6e 74 72 79  e table.** entry
1c8a0 2e 20 49 66 20 61 20 72 6f 77 20 69 73 20 66 6f  . If a row is fo
1c8b0 75 6e 64 2c 20 74 68 65 20 53 45 4c 45 43 54 20  und, the SELECT 
1c8c0 73 74 61 74 65 6d 65 6e 74 20 6c 65 66 74 20 70  statement left p
1c8d0 6f 69 6e 74 69 6e 67 20 61 74 20 74 68 65 20 72  ointing at the r
1c8e0 6f 77 20 0a 2a 2a 20 61 6e 64 20 53 51 4c 49 54  ow .** and SQLIT
1c8f0 45 5f 52 4f 57 20 69 73 20 72 65 74 75 72 6e 65  E_ROW is returne
1c900 64 2e 20 4f 74 68 65 72 77 69 73 65 2c 20 69 66  d. Otherwise, if
1c910 20 6e 6f 20 72 6f 77 20 69 73 20 66 6f 75 6e 64   no row is found
1c920 20 61 6e 64 20 6e 6f 20 65 72 72 6f 72 0a 2a 2a   and no error.**
1c930 20 68 61 73 20 6f 63 63 75 72 65 64 2c 20 74 68   has occured, th
1c940 65 20 73 74 61 74 65 6d 65 6e 74 20 69 73 20 72  e statement is r
1c950 65 73 65 74 20 61 6e 64 20 53 51 4c 49 54 45 5f  eset and SQLITE_
1c960 4f 4b 20 69 73 20 72 65 74 75 72 6e 65 64 2e 20  OK is returned. 
1c970 49 66 20 61 6e 0a 2a 2a 20 65 72 72 6f 72 20 6f  If an.** error o
1c980 63 63 75 72 73 2c 20 74 68 65 20 73 74 61 74 65  ccurs, the state
1c990 6d 65 6e 74 20 69 73 20 72 65 73 65 74 20 61 6e  ment is reset an
1c9a0 64 20 61 6e 20 53 51 4c 69 74 65 20 65 72 72 6f  d an SQLite erro
1c9b0 72 20 63 6f 64 65 20 69 73 20 72 65 74 75 72 6e  r code is return
1c9c0 65 64 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 74 68 69  ed..**.** If thi
1c9d0 73 20 66 75 6e 63 74 69 6f 6e 20 72 65 74 75 72  s function retur
1c9e0 6e 73 20 53 51 4c 49 54 45 5f 52 4f 57 2c 20 74  ns SQLITE_ROW, t
1c9f0 68 65 20 63 61 6c 6c 65 72 20 6d 75 73 74 20 65  he caller must e
1ca00 76 65 6e 74 75 61 6c 6c 79 20 72 65 73 65 74 28  ventually reset(
1ca10 29 20 0a 2a 2a 20 73 74 61 74 65 6d 65 6e 74 20  ) .** statement 
1ca20 70 53 65 6c 65 63 74 2e 20 49 66 20 61 6e 79 20  pSelect. If any 
1ca30 6f 74 68 65 72 20 76 61 6c 75 65 20 69 73 20 72  other value is r
1ca40 65 74 75 72 6e 65 64 2c 20 74 68 65 20 73 74 61  eturned, the sta
1ca50 74 65 6d 65 6e 74 20 64 6f 65 73 0a 2a 2a 20 6e  tement does.** n
1ca60 6f 74 20 72 65 71 75 69 72 65 20 61 20 72 65 73  ot require a res
1ca70 65 74 28 29 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 74  et()..**.** If t
1ca80 68 65 20 69 74 65 72 61 74 6f 72 20 63 75 72 72  he iterator curr
1ca90 65 6e 74 6c 79 20 70 6f 69 6e 74 73 20 74 6f 20  ently points to 
1caa0 61 6e 20 49 4e 53 45 52 54 20 72 65 63 6f 72 64  an INSERT record
1cab0 2c 20 62 69 6e 64 20 76 61 6c 75 65 73 20 66 72  , bind values fr
1cac0 6f 6d 20 74 68 65 0a 2a 2a 20 6e 65 77 2e 2a 20  om the.** new.* 
1cad0 72 65 63 6f 72 64 20 74 6f 20 74 68 65 20 53 45  record to the SE
1cae0 4c 45 43 54 20 73 74 61 74 65 6d 65 6e 74 2e 20  LECT statement. 
1caf0 4f 72 2c 20 69 66 20 69 74 20 70 6f 69 6e 74 73  Or, if it points
1cb00 20 74 6f 20 61 20 44 45 4c 45 54 45 20 6f 72 0a   to a DELETE or.
1cb10 2a 2a 20 55 50 44 41 54 45 2c 20 62 69 6e 64 20  ** UPDATE, bind 
1cb20 76 61 6c 75 65 73 20 66 72 6f 6d 20 74 68 65 20  values from the 
1cb30 6f 6c 64 2e 2a 20 72 65 63 6f 72 64 2e 20 0a 2a  old.* record. .*
1cb40 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73  /.static int ses
1cb50 73 69 6f 6e 53 65 65 6b 54 6f 52 6f 77 28 0a 20  sionSeekToRow(. 
1cb60 20 73 71 6c 69 74 65 33 20 2a 64 62 2c 20 20 20   sqlite3 *db,   
1cb70 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1cb80 20 2f 2a 20 44 61 74 61 62 61 73 65 20 68 61 6e   /* Database han
1cb90 64 6c 65 20 2a 2f 0a 20 20 73 71 6c 69 74 65 33  dle */.  sqlite3
1cba0 5f 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72 20  _changeset_iter 
1cbb0 2a 70 49 74 65 72 2c 20 20 2f 2a 20 43 68 61 6e  *pIter,  /* Chan
1cbc0 67 65 73 65 74 20 69 74 65 72 61 74 6f 72 20 2a  geset iterator *
1cbd0 2f 0a 20 20 75 38 20 2a 61 62 50 4b 2c 20 20 20  /.  u8 *abPK,   
1cbe0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1cbf0 20 20 20 20 2f 2a 20 50 72 69 6d 61 72 79 20 6b      /* Primary k
1cc00 65 79 20 66 6c 61 67 73 20 61 72 72 61 79 20 2a  ey flags array *
1cc10 2f 0a 20 20 73 71 6c 69 74 65 33 5f 73 74 6d 74  /.  sqlite3_stmt
1cc20 20 2a 70 53 65 6c 65 63 74 20 20 20 20 20 20 20   *pSelect       
1cc30 20 20 20 20 2f 2a 20 53 45 4c 45 43 54 20 73 74      /* SELECT st
1cc40 61 74 65 6d 65 6e 74 20 66 72 6f 6d 20 73 65 73  atement from ses
1cc50 73 69 6f 6e 53 65 6c 65 63 74 52 6f 77 28 29 20  sionSelectRow() 
1cc60 2a 2f 0a 29 7b 0a 20 20 69 6e 74 20 72 63 3b 20  */.){.  int rc; 
1cc70 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1cc80 20 20 20 20 20 20 20 20 2f 2a 20 52 65 74 75 72          /* Retur
1cc90 6e 20 63 6f 64 65 20 2a 2f 0a 20 20 69 6e 74 20  n code */.  int 
1cca0 6e 43 6f 6c 3b 20 20 20 20 20 20 20 20 20 20 20  nCol;           
1ccb0 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4e              /* N
1ccc0 75 6d 62 65 72 20 6f 66 20 63 6f 6c 75 6d 6e 73  umber of columns
1ccd0 20 69 6e 20 74 61 62 6c 65 20 2a 2f 0a 20 20 69   in table */.  i
1cce0 6e 74 20 6f 70 3b 20 20 20 20 20 20 20 20 20 20  nt op;          
1ccf0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
1cd00 2a 20 43 68 61 6e 67 73 65 74 20 6f 70 65 72 61  * Changset opera
1cd10 74 69 6f 6e 20 28 53 51 4c 49 54 45 5f 55 50 44  tion (SQLITE_UPD
1cd20 41 54 45 20 65 74 63 2e 29 20 2a 2f 0a 20 20 63  ATE etc.) */.  c
1cd30 6f 6e 73 74 20 63 68 61 72 20 2a 7a 44 75 6d 6d  onst char *zDumm
1cd40 79 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 2f  y;             /
1cd50 2a 20 55 6e 75 73 65 64 20 2a 2f 0a 0a 20 20 73  * Unused */..  s
1cd60 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74 5f  qlite3changeset_
1cd70 6f 70 28 70 49 74 65 72 2c 20 26 7a 44 75 6d 6d  op(pIter, &zDumm
1cd80 79 2c 20 26 6e 43 6f 6c 2c 20 26 6f 70 2c 20 30  y, &nCol, &op, 0
1cd90 29 3b 0a 20 20 72 63 20 3d 20 73 65 73 73 69 6f  );.  rc = sessio
1cda0 6e 42 69 6e 64 52 6f 77 28 70 49 74 65 72 2c 20  nBindRow(pIter, 
1cdb0 0a 20 20 20 20 20 20 6f 70 3d 3d 53 51 4c 49 54  .      op==SQLIT
1cdc0 45 5f 49 4e 53 45 52 54 20 3f 20 73 71 6c 69 74  E_INSERT ? sqlit
1cdd0 65 33 63 68 61 6e 67 65 73 65 74 5f 6e 65 77 20  e3changeset_new 
1cde0 3a 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65 73  : sqlite3changes
1cdf0 65 74 5f 6f 6c 64 2c 0a 20 20 20 20 20 20 6e 43  et_old,.      nC
1ce00 6f 6c 2c 20 61 62 50 4b 2c 20 70 53 65 6c 65 63  ol, abPK, pSelec
1ce10 74 0a 20 20 29 3b 0a 0a 20 20 69 66 28 20 72 63  t.  );..  if( rc
1ce20 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20  ==SQLITE_OK ){. 
1ce30 20 20 20 72 63 20 3d 20 73 71 6c 69 74 65 33 5f     rc = sqlite3_
1ce40 73 74 65 70 28 70 53 65 6c 65 63 74 29 3b 0a 20  step(pSelect);. 
1ce50 20 20 20 69 66 28 20 72 63 21 3d 53 51 4c 49 54     if( rc!=SQLIT
1ce60 45 5f 52 4f 57 20 29 20 72 63 20 3d 20 73 71 6c  E_ROW ) rc = sql
1ce70 69 74 65 33 5f 72 65 73 65 74 28 70 53 65 6c 65  ite3_reset(pSele
1ce80 63 74 29 3b 0a 20 20 7d 0a 0a 20 20 72 65 74 75  ct);.  }..  retu
1ce90 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20  rn rc;.}../*.** 
1cea0 49 6e 76 6f 6b 65 20 74 68 65 20 63 6f 6e 66 6c  Invoke the confl
1ceb0 69 63 74 20 68 61 6e 64 6c 65 72 20 66 6f 72 20  ict handler for 
1cec0 74 68 65 20 63 68 61 6e 67 65 20 74 68 61 74 20  the change that 
1ced0 74 68 65 20 63 68 61 6e 67 65 73 65 74 20 69 74  the changeset it
1cee0 65 72 61 74 6f 72 0a 2a 2a 20 63 75 72 72 65 6e  erator.** curren
1cef0 74 6c 79 20 70 6f 69 6e 74 73 20 74 6f 2e 0a 2a  tly points to..*
1cf00 2a 0a 2a 2a 20 41 72 67 75 6d 65 6e 74 20 65 54  *.** Argument eT
1cf10 79 70 65 20 6d 75 73 74 20 62 65 20 65 69 74 68  ype must be eith
1cf20 65 72 20 43 48 41 4e 47 45 53 45 54 5f 44 41 54  er CHANGESET_DAT
1cf30 41 20 6f 72 20 43 48 41 4e 47 45 53 45 54 5f 43  A or CHANGESET_C
1cf40 4f 4e 46 4c 49 43 54 2e 0a 2a 2a 20 49 66 20 61  ONFLICT..** If a
1cf50 72 67 75 6d 65 6e 74 20 70 62 52 65 70 6c 61 63  rgument pbReplac
1cf60 65 20 69 73 20 4e 55 4c 4c 2c 20 74 68 65 6e 20  e is NULL, then 
1cf70 74 68 65 20 74 79 70 65 20 6f 66 20 63 6f 6e 66  the type of conf
1cf80 6c 69 63 74 20 68 61 6e 64 6c 65 72 20 69 6e 76  lict handler inv
1cf90 6f 6b 65 64 0a 2a 2a 20 64 65 70 65 6e 64 73 20  oked.** depends 
1cfa0 73 6f 6c 65 6c 79 20 6f 6e 20 65 54 79 70 65 2c  solely on eType,
1cfb0 20 61 73 20 66 6f 6c 6c 6f 77 73 3a 0a 2a 2a 0a   as follows:.**.
1cfc0 2a 2a 20 20 20 20 65 54 79 70 65 20 76 61 6c 75  **    eType valu
1cfd0 65 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  e               
1cfe0 20 20 56 61 6c 75 65 20 70 61 73 73 65 64 20 74    Value passed t
1cff0 6f 20 78 43 6f 6e 66 6c 69 63 74 0a 2a 2a 20 20  o xConflict.**  
1d000 20 20 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d    --------------
1d010 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d  ----------------
1d020 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d  ----------------
1d030 2d 2d 2d 0a 2a 2a 20 20 20 20 43 48 41 4e 47 45  ---.**    CHANGE
1d040 53 45 54 5f 44 41 54 41 20 20 20 20 20 20 20 20  SET_DATA        
1d050 20 20 20 20 20 20 43 48 41 4e 47 45 53 45 54 5f        CHANGESET_
1d060 4e 4f 54 46 4f 55 4e 44 0a 2a 2a 20 20 20 20 43  NOTFOUND.**    C
1d070 48 41 4e 47 45 53 45 54 5f 43 4f 4e 46 4c 49 43  HANGESET_CONFLIC
1d080 54 20 20 20 20 20 20 20 20 20 20 43 48 41 4e 47  T          CHANG
1d090 45 53 45 54 5f 43 4f 4e 53 54 52 41 49 4e 54 0a  ESET_CONSTRAINT.
1d0a0 2a 2a 0a 2a 2a 20 4f 72 2c 20 69 66 20 70 62 52  **.** Or, if pbR
1d0b0 65 70 6c 61 63 65 20 69 73 20 6e 6f 74 20 4e 55  eplace is not NU
1d0c0 4c 4c 2c 20 74 68 65 6e 20 61 6e 20 61 74 74 65  LL, then an atte
1d0d0 6d 70 74 20 69 73 20 6d 61 64 65 20 74 6f 20 66  mpt is made to f
1d0e0 69 6e 64 20 61 6e 20 65 78 69 73 74 69 6e 67 0a  ind an existing.
1d0f0 2a 2a 20 72 65 63 6f 72 64 20 77 69 74 68 20 74  ** record with t
1d100 68 65 20 73 61 6d 65 20 70 72 69 6d 61 72 79 20  he same primary 
1d110 6b 65 79 20 61 73 20 74 68 65 20 72 65 63 6f 72  key as the recor
1d120 64 20 61 62 6f 75 74 20 74 6f 20 62 65 20 64 65  d about to be de
1d130 6c 65 74 65 64 2c 20 75 70 64 61 74 65 64 0a 2a  leted, updated.*
1d140 2a 20 6f 72 20 69 6e 73 65 72 74 65 64 2e 20 49  * or inserted. I
1d150 66 20 73 75 63 68 20 61 20 72 65 63 6f 72 64 20  f such a record 
1d160 63 61 6e 20 62 65 20 66 6f 75 6e 64 2c 20 69 74  can be found, it
1d170 20 69 73 20 61 76 61 69 6c 61 62 6c 65 20 74 6f   is available to
1d180 20 74 68 65 20 63 6f 6e 66 6c 69 63 74 0a 2a 2a   the conflict.**
1d190 20 68 61 6e 64 6c 65 72 20 61 73 20 74 68 65 20   handler as the 
1d1a0 22 63 6f 6e 66 6c 69 63 74 69 6e 67 22 20 72 65  "conflicting" re
1d1b0 63 6f 72 64 2e 20 49 6e 20 74 68 69 73 20 63 61  cord. In this ca
1d1c0 73 65 20 74 68 65 20 74 79 70 65 20 6f 66 20 63  se the type of c
1d1d0 6f 6e 66 6c 69 63 74 0a 2a 2a 20 68 61 6e 64 6c  onflict.** handl
1d1e0 65 72 20 69 6e 76 6f 6b 65 64 20 69 73 20 61 73  er invoked is as
1d1f0 20 66 6f 6c 6c 6f 77 73 3a 0a 2a 2a 0a 2a 2a 20   follows:.**.** 
1d200 20 20 20 65 54 79 70 65 20 76 61 6c 75 65 20 20     eType value  
1d210 20 20 20 20 20 20 20 50 4b 20 52 65 63 6f 72 64         PK Record
1d220 20 66 6f 75 6e 64 3f 20 20 20 56 61 6c 75 65 20   found?   Value 
1d230 70 61 73 73 65 64 20 74 6f 20 78 43 6f 6e 66 6c  passed to xConfl
1d240 69 63 74 0a 2a 2a 20 20 20 20 2d 2d 2d 2d 2d 2d  ict.**    ------
1d250 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d  ----------------
1d260 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d  ----------------
1d270 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d  ----------------
1d280 2d 2d 2d 2d 2d 2d 2d 2d 2d 2d 0a 2a 2a 20 20 20  ----------.**   
1d290 20 43 48 41 4e 47 45 53 45 54 5f 44 41 54 41 20   CHANGESET_DATA 
1d2a0 20 20 20 20 20 59 65 73 20 20 20 20 20 20 20 20       Yes        
1d2b0 20 20 20 20 20 20 20 20 43 48 41 4e 47 45 53 45          CHANGESE
1d2c0 54 5f 44 41 54 41 0a 2a 2a 20 20 20 20 43 48 41  T_DATA.**    CHA
1d2d0 4e 47 45 53 45 54 5f 44 41 54 41 20 20 20 20 20  NGESET_DATA     
1d2e0 20 4e 6f 20 20 20 20 20 20 20 20 20 20 20 20 20   No             
1d2f0 20 20 20 20 43 48 41 4e 47 45 53 45 54 5f 4e 4f      CHANGESET_NO
1d300 54 46 4f 55 4e 44 0a 2a 2a 20 20 20 20 43 48 41  TFOUND.**    CHA
1d310 4e 47 45 53 45 54 5f 43 4f 4e 46 4c 49 43 54 20  NGESET_CONFLICT 
1d320 20 59 65 73 20 20 20 20 20 20 20 20 20 20 20 20   Yes            
1d330 20 20 20 20 43 48 41 4e 47 45 53 45 54 5f 43 4f      CHANGESET_CO
1d340 4e 46 4c 49 43 54 0a 2a 2a 20 20 20 20 43 48 41  NFLICT.**    CHA
1d350 4e 47 45 53 45 54 5f 43 4f 4e 46 4c 49 43 54 20  NGESET_CONFLICT 
1d360 20 4e 6f 20 20 20 20 20 20 20 20 20 20 20 20 20   No             
1d370 20 20 20 20 43 48 41 4e 47 45 53 45 54 5f 43 4f      CHANGESET_CO
1d380 4e 53 54 52 41 49 4e 54 0a 2a 2a 0a 2a 2a 20 49  NSTRAINT.**.** I
1d390 66 20 70 62 52 65 70 6c 61 63 65 20 69 73 20 6e  f pbReplace is n
1d3a0 6f 74 20 4e 55 4c 4c 2c 20 61 6e 64 20 61 20 72  ot NULL, and a r
1d3b0 65 63 6f 72 64 20 77 69 74 68 20 61 20 6d 61 74  ecord with a mat
1d3c0 63 68 69 6e 67 20 50 4b 20 69 73 20 66 6f 75 6e  ching PK is foun
1d3d0 64 2c 20 61 6e 64 0a 2a 2a 20 74 68 65 20 63 6f  d, and.** the co
1d3e0 6e 66 6c 69 63 74 20 68 61 6e 64 6c 65 72 20 66  nflict handler f
1d3f0 75 6e 63 74 69 6f 6e 20 72 65 74 75 72 6e 73 20  unction returns 
1d400 53 51 4c 49 54 45 5f 43 48 41 4e 47 45 53 45 54  SQLITE_CHANGESET
1d410 5f 52 45 50 4c 41 43 45 2c 20 2a 70 62 52 65 70  _REPLACE, *pbRep
1d420 6c 61 63 65 0a 2a 2a 20 69 73 20 73 65 74 20 74  lace.** is set t
1d430 6f 20 6e 6f 6e 2d 7a 65 72 6f 20 62 65 66 6f 72  o non-zero befor
1d440 65 20 72 65 74 75 72 6e 69 6e 67 20 53 51 4c 49  e returning SQLI
1d450 54 45 5f 4f 4b 2e 0a 2a 2a 0a 2a 2a 20 49 66 20  TE_OK..**.** If 
1d460 74 68 65 20 63 6f 6e 66 6c 69 63 74 20 68 61 6e  the conflict han
1d470 64 6c 65 72 20 72 65 74 75 72 6e 73 20 53 51 4c  dler returns SQL
1d480 49 54 45 5f 43 48 41 4e 47 45 53 45 54 5f 41 42  ITE_CHANGESET_AB
1d490 4f 52 54 2c 20 53 51 4c 49 54 45 5f 41 42 4f 52  ORT, SQLITE_ABOR
1d4a0 54 20 69 73 0a 2a 2a 20 72 65 74 75 72 6e 65 64  T is.** returned
1d4b0 2e 20 4f 72 2c 20 69 66 20 74 68 65 20 63 6f 6e  . Or, if the con
1d4c0 66 6c 69 63 74 20 68 61 6e 64 6c 65 72 20 72 65  flict handler re
1d4d0 74 75 72 6e 73 20 61 6e 20 69 6e 76 61 6c 69 64  turns an invalid
1d4e0 20 76 61 6c 75 65 2c 20 0a 2a 2a 20 53 51 4c 49   value, .** SQLI
1d4f0 54 45 5f 4d 49 53 55 53 45 2e 20 49 66 20 74 68  TE_MISUSE. If th
1d500 65 20 63 6f 6e 66 6c 69 63 74 20 68 61 6e 64 6c  e conflict handl
1d510 65 72 20 72 65 74 75 72 6e 73 20 53 51 4c 49 54  er returns SQLIT
1d520 45 5f 43 48 41 4e 47 45 53 45 54 5f 4f 4d 49 54  E_CHANGESET_OMIT
1d530 2c 0a 2a 2a 20 74 68 69 73 20 66 75 6e 63 74 69  ,.** this functi
1d540 6f 6e 20 72 65 74 75 72 6e 73 20 53 51 4c 49 54  on returns SQLIT
1d550 45 5f 4f 4b 2e 0a 2a 2f 0a 73 74 61 74 69 63 20  E_OK..*/.static 
1d560 69 6e 74 20 73 65 73 73 69 6f 6e 43 6f 6e 66 6c  int sessionConfl
1d570 69 63 74 48 61 6e 64 6c 65 72 28 0a 20 20 69 6e  ictHandler(.  in
1d580 74 20 65 54 79 70 65 2c 20 20 20 20 20 20 20 20  t eType,        
1d590 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
1d5a0 20 45 69 74 68 65 72 20 43 48 41 4e 47 45 53 45   Either CHANGESE
1d5b0 54 5f 44 41 54 41 20 6f 72 20 43 4f 4e 46 4c 49  T_DATA or CONFLI
1d5c0 43 54 20 2a 2f 0a 20 20 53 65 73 73 69 6f 6e 41  CT */.  SessionA
1d5d0 70 70 6c 79 43 74 78 20 2a 70 2c 20 20 20 20 20  pplyCtx *p,     
1d5e0 20 20 20 20 20 20 20 20 2f 2a 20 63 68 61 6e 67          /* chang
1d5f0 65 73 65 74 5f 61 70 70 6c 79 28 29 20 63 6f 6e  eset_apply() con
1d600 74 65 78 74 20 2a 2f 0a 20 20 73 71 6c 69 74 65  text */.  sqlite
1d610 33 5f 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72  3_changeset_iter
1d620 20 2a 70 49 74 65 72 2c 20 20 2f 2a 20 43 68 61   *pIter,  /* Cha
1d630 6e 67 65 73 65 74 20 69 74 65 72 61 74 6f 72 20  ngeset iterator 
1d640 2a 2f 0a 20 20 69 6e 74 28 2a 78 43 6f 6e 66 6c  */.  int(*xConfl
1d650 69 63 74 29 28 76 6f 69 64 20 2a 2c 20 69 6e 74  ict)(void *, int
1d660 2c 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65  , sqlite3_change
1d670 73 65 74 5f 69 74 65 72 2a 29 2c 0a 20 20 76 6f  set_iter*),.  vo
1d680 69 64 20 2a 70 43 74 78 2c 20 20 20 20 20 20 20  id *pCtx,       
1d690 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
1d6a0 20 46 69 72 73 74 20 61 72 67 75 6d 65 6e 74 20   First argument 
1d6b0 66 6f 72 20 63 6f 6e 66 6c 69 63 74 20 68 61 6e  for conflict han
1d6c0 64 6c 65 72 20 2a 2f 0a 20 20 69 6e 74 20 2a 70  dler */.  int *p
1d6d0 62 52 65 70 6c 61 63 65 20 20 20 20 20 20 20 20  bReplace        
1d6e0 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4f 55 54            /* OUT
1d6f0 3a 20 53 65 74 20 74 6f 20 74 72 75 65 20 69 66  : Set to true if
1d700 20 50 4b 20 72 6f 77 20 69 73 20 66 6f 75 6e 64   PK row is found
1d710 20 2a 2f 0a 29 7b 0a 20 20 69 6e 74 20 72 65 73   */.){.  int res
1d720 20 3d 20 30 3b 20 20 20 20 20 20 20 20 20 20 20   = 0;           
1d730 20 20 20 20 20 20 20 20 20 2f 2a 20 56 61 6c 75           /* Valu
1d740 65 20 72 65 74 75 72 6e 65 64 20 62 79 20 63 6f  e returned by co
1d750 6e 66 6c 69 63 74 20 68 61 6e 64 6c 65 72 20 2a  nflict handler *
1d760 2f 0a 20 20 69 6e 74 20 72 63 3b 0a 20 20 69 6e  /.  int rc;.  in
1d770 74 20 6e 43 6f 6c 3b 0a 20 20 69 6e 74 20 6f 70  t nCol;.  int op
1d780 3b 0a 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a  ;.  const char *
1d790 7a 44 75 6d 6d 79 3b 0a 0a 20 20 73 71 6c 69 74  zDummy;..  sqlit
1d7a0 65 33 63 68 61 6e 67 65 73 65 74 5f 6f 70 28 70  e3changeset_op(p
1d7b0 49 74 65 72 2c 20 26 7a 44 75 6d 6d 79 2c 20 26  Iter, &zDummy, &
1d7c0 6e 43 6f 6c 2c 20 26 6f 70 2c 20 30 29 3b 0a 0a  nCol, &op, 0);..
1d7d0 20 20 61 73 73 65 72 74 28 20 65 54 79 70 65 3d    assert( eType=
1d7e0 3d 53 51 4c 49 54 45 5f 43 48 41 4e 47 45 53 45  =SQLITE_CHANGESE
1d7f0 54 5f 43 4f 4e 46 4c 49 43 54 20 7c 7c 20 65 54  T_CONFLICT || eT
1d800 79 70 65 3d 3d 53 51 4c 49 54 45 5f 43 48 41 4e  ype==SQLITE_CHAN
1d810 47 45 53 45 54 5f 44 41 54 41 20 29 3b 0a 20 20  GESET_DATA );.  
1d820 61 73 73 65 72 74 28 20 53 51 4c 49 54 45 5f 43  assert( SQLITE_C
1d830 48 41 4e 47 45 53 45 54 5f 43 4f 4e 46 4c 49 43  HANGESET_CONFLIC
1d840 54 2b 31 3d 3d 53 51 4c 49 54 45 5f 43 48 41 4e  T+1==SQLITE_CHAN
1d850 47 45 53 45 54 5f 43 4f 4e 53 54 52 41 49 4e 54  GESET_CONSTRAINT
1d860 20 29 3b 0a 20 20 61 73 73 65 72 74 28 20 53 51   );.  assert( SQ
1d870 4c 49 54 45 5f 43 48 41 4e 47 45 53 45 54 5f 44  LITE_CHANGESET_D
1d880 41 54 41 2b 31 3d 3d 53 51 4c 49 54 45 5f 43 48  ATA+1==SQLITE_CH
1d890 41 4e 47 45 53 45 54 5f 4e 4f 54 46 4f 55 4e 44  ANGESET_NOTFOUND
1d8a0 20 29 3b 0a 0a 20 20 2f 2a 20 42 69 6e 64 20 74   );..  /* Bind t
1d8b0 68 65 20 6e 65 77 2e 2a 20 50 52 49 4d 41 52 59  he new.* PRIMARY
1d8c0 20 4b 45 59 20 76 61 6c 75 65 73 20 74 6f 20 74   KEY values to t
1d8d0 68 65 20 53 45 4c 45 43 54 20 73 74 61 74 65 6d  he SELECT statem
1d8e0 65 6e 74 2e 20 2a 2f 0a 20 20 69 66 28 20 70 62  ent. */.  if( pb
1d8f0 52 65 70 6c 61 63 65 20 29 7b 0a 20 20 20 20 72  Replace ){.    r
1d900 63 20 3d 20 73 65 73 73 69 6f 6e 53 65 65 6b 54  c = sessionSeekT
1d910 6f 52 6f 77 28 70 2d 3e 64 62 2c 20 70 49 74 65  oRow(p->db, pIte
1d920 72 2c 20 70 2d 3e 61 62 50 4b 2c 20 70 2d 3e 70  r, p->abPK, p->p
1d930 53 65 6c 65 63 74 29 3b 0a 20 20 7d 65 6c 73 65  Select);.  }else
1d940 7b 0a 20 20 20 20 72 63 20 3d 20 53 51 4c 49 54  {.    rc = SQLIT
1d950 45 5f 4f 4b 3b 0a 20 20 7d 0a 0a 20 20 69 66 28  E_OK;.  }..  if(
1d960 20 72 63 3d 3d 53 51 4c 49 54 45 5f 52 4f 57 20   rc==SQLITE_ROW 
1d970 29 7b 0a 20 20 20 20 2f 2a 20 54 68 65 72 65 20  ){.    /* There 
1d980 65 78 69 73 74 73 20 61 6e 6f 74 68 65 72 20 72  exists another r
1d990 6f 77 20 77 69 74 68 20 74 68 65 20 6e 65 77 2e  ow with the new.
1d9a0 2a 20 70 72 69 6d 61 72 79 20 6b 65 79 2e 20 2a  * primary key. *
1d9b0 2f 0a 20 20 20 20 70 49 74 65 72 2d 3e 70 43 6f  /.    pIter->pCo
1d9c0 6e 66 6c 69 63 74 20 3d 20 70 2d 3e 70 53 65 6c  nflict = p->pSel
1d9d0 65 63 74 3b 0a 20 20 20 20 72 65 73 20 3d 20 78  ect;.    res = x
1d9e0 43 6f 6e 66 6c 69 63 74 28 70 43 74 78 2c 20 65  Conflict(pCtx, e
1d9f0 54 79 70 65 2c 20 70 49 74 65 72 29 3b 0a 20 20  Type, pIter);.  
1da00 20 20 70 49 74 65 72 2d 3e 70 43 6f 6e 66 6c 69    pIter->pConfli
1da10 63 74 20 3d 20 30 3b 0a 20 20 20 20 72 63 20 3d  ct = 0;.    rc =
1da20 20 73 71 6c 69 74 65 33 5f 72 65 73 65 74 28 70   sqlite3_reset(p
1da30 2d 3e 70 53 65 6c 65 63 74 29 3b 0a 20 20 7d 65  ->pSelect);.  }e
1da40 6c 73 65 20 69 66 28 20 72 63 3d 3d 53 51 4c 49  lse if( rc==SQLI
1da50 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 69 66 28  TE_OK ){.    if(
1da60 20 70 2d 3e 62 44 65 66 65 72 43 6f 6e 73 74 72   p->bDeferConstr
1da70 61 69 6e 74 73 20 26 26 20 65 54 79 70 65 3d 3d  aints && eType==
1da80 53 51 4c 49 54 45 5f 43 48 41 4e 47 45 53 45 54  SQLITE_CHANGESET
1da90 5f 43 4f 4e 46 4c 49 43 54 20 29 7b 0a 20 20 20  _CONFLICT ){.   
1daa0 20 20 20 2f 2a 20 49 6e 73 74 65 61 64 20 6f 66     /* Instead of
1dab0 20 69 6e 76 6f 6b 69 6e 67 20 74 68 65 20 63 6f   invoking the co
1dac0 6e 66 6c 69 63 74 20 68 61 6e 64 6c 65 72 2c 20  nflict handler, 
1dad0 61 70 70 65 6e 64 20 74 68 65 20 63 68 61 6e 67  append the chang
1dae0 65 20 62 6c 6f 62 0a 20 20 20 20 20 20 2a 2a 20  e blob.      ** 
1daf0 74 6f 20 74 68 65 20 53 65 73 73 69 6f 6e 41 70  to the SessionAp
1db00 70 6c 79 43 74 78 2e 63 6f 6e 73 74 72 61 69 6e  plyCtx.constrain
1db10 74 73 20 62 75 66 66 65 72 2e 20 2a 2f 0a 20 20  ts buffer. */.  
1db20 20 20 20 20 75 38 20 2a 61 42 6c 6f 62 20 3d 20      u8 *aBlob = 
1db30 26 70 49 74 65 72 2d 3e 69 6e 2e 61 44 61 74 61  &pIter->in.aData
1db40 5b 70 49 74 65 72 2d 3e 69 6e 2e 69 43 75 72 72  [pIter->in.iCurr
1db50 65 6e 74 5d 3b 0a 20 20 20 20 20 20 69 6e 74 20  ent];.      int 
1db60 6e 42 6c 6f 62 20 3d 20 70 49 74 65 72 2d 3e 69  nBlob = pIter->i
1db70 6e 2e 69 4e 65 78 74 20 2d 20 70 49 74 65 72 2d  n.iNext - pIter-
1db80 3e 69 6e 2e 69 43 75 72 72 65 6e 74 3b 0a 20 20  >in.iCurrent;.  
1db90 20 20 20 20 73 65 73 73 69 6f 6e 41 70 70 65 6e      sessionAppen
1dba0 64 42 6c 6f 62 28 26 70 2d 3e 63 6f 6e 73 74 72  dBlob(&p->constr
1dbb0 61 69 6e 74 73 2c 20 61 42 6c 6f 62 2c 20 6e 42  aints, aBlob, nB
1dbc0 6c 6f 62 2c 20 26 72 63 29 3b 0a 20 20 20 20 20  lob, &rc);.     
1dbd0 20 72 65 73 20 3d 20 53 51 4c 49 54 45 5f 43 48   res = SQLITE_CH
1dbe0 41 4e 47 45 53 45 54 5f 4f 4d 49 54 3b 0a 20 20  ANGESET_OMIT;.  
1dbf0 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 2f    }else{.      /
1dc00 2a 20 4e 6f 20 6f 74 68 65 72 20 72 6f 77 20 77  * No other row w
1dc10 69 74 68 20 74 68 65 20 6e 65 77 2e 2a 20 70 72  ith the new.* pr
1dc20 69 6d 61 72 79 20 6b 65 79 2e 20 2a 2f 0a 20 20  imary key. */.  
1dc30 20 20 20 20 72 65 73 20 3d 20 78 43 6f 6e 66 6c      res = xConfl
1dc40 69 63 74 28 70 43 74 78 2c 20 65 54 79 70 65 2b  ict(pCtx, eType+
1dc50 31 2c 20 70 49 74 65 72 29 3b 0a 20 20 20 20 20  1, pIter);.     
1dc60 20 69 66 28 20 72 65 73 3d 3d 53 51 4c 49 54 45   if( res==SQLITE
1dc70 5f 43 48 41 4e 47 45 53 45 54 5f 52 45 50 4c 41  _CHANGESET_REPLA
1dc80 43 45 20 29 20 72 63 20 3d 20 53 51 4c 49 54 45  CE ) rc = SQLITE
1dc90 5f 4d 49 53 55 53 45 3b 0a 20 20 20 20 7d 0a 20  _MISUSE;.    }. 
1dca0 20 7d 0a 0a 20 20 69 66 28 20 72 63 3d 3d 53 51   }..  if( rc==SQ
1dcb0 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 73  LITE_OK ){.    s
1dcc0 77 69 74 63 68 28 20 72 65 73 20 29 7b 0a 20 20  witch( res ){.  
1dcd0 20 20 20 20 63 61 73 65 20 53 51 4c 49 54 45 5f      case SQLITE_
1dce0 43 48 41 4e 47 45 53 45 54 5f 52 45 50 4c 41 43  CHANGESET_REPLAC
1dcf0 45 3a 0a 20 20 20 20 20 20 20 20 61 73 73 65 72  E:.        asser
1dd00 74 28 20 70 62 52 65 70 6c 61 63 65 20 29 3b 0a  t( pbReplace );.
1dd10 20 20 20 20 20 20 20 20 2a 70 62 52 65 70 6c 61          *pbRepla
1dd20 63 65 20 3d 20 31 3b 0a 20 20 20 20 20 20 20 20  ce = 1;.        
1dd30 62 72 65 61 6b 3b 0a 0a 20 20 20 20 20 20 63 61  break;..      ca
1dd40 73 65 20 53 51 4c 49 54 45 5f 43 48 41 4e 47 45  se SQLITE_CHANGE
1dd50 53 45 54 5f 4f 4d 49 54 3a 0a 20 20 20 20 20 20  SET_OMIT:.      
1dd60 20 20 62 72 65 61 6b 3b 0a 0a 20 20 20 20 20 20    break;..      
1dd70 63 61 73 65 20 53 51 4c 49 54 45 5f 43 48 41 4e  case SQLITE_CHAN
1dd80 47 45 53 45 54 5f 41 42 4f 52 54 3a 0a 20 20 20  GESET_ABORT:.   
1dd90 20 20 20 20 20 72 63 20 3d 20 53 51 4c 49 54 45       rc = SQLITE
1dda0 5f 41 42 4f 52 54 3b 0a 20 20 20 20 20 20 20 20  _ABORT;.        
1ddb0 62 72 65 61 6b 3b 0a 0a 20 20 20 20 20 20 64 65  break;..      de
1ddc0 66 61 75 6c 74 3a 0a 20 20 20 20 20 20 20 20 72  fault:.        r
1ddd0 63 20 3d 20 53 51 4c 49 54 45 5f 4d 49 53 55 53  c = SQLITE_MISUS
1dde0 45 3b 0a 20 20 20 20 20 20 20 20 62 72 65 61 6b  E;.        break
1ddf0 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a 0a 20 20 72  ;.    }.  }..  r
1de00 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a  eturn rc;.}../*.
1de10 2a 2a 20 41 74 74 65 6d 70 74 20 74 6f 20 61 70  ** Attempt to ap
1de20 70 6c 79 20 74 68 65 20 63 68 61 6e 67 65 20 74  ply the change t
1de30 68 61 74 20 74 68 65 20 69 74 65 72 61 74 6f 72  hat the iterator
1de40 20 70 61 73 73 65 64 20 61 73 20 74 68 65 20 66   passed as the f
1de50 69 72 73 74 20 61 72 67 75 6d 65 6e 74 0a 2a 2a  irst argument.**
1de60 20 63 75 72 72 65 6e 74 6c 79 20 70 6f 69 6e 74   currently point
1de70 73 20 74 6f 20 74 6f 20 74 68 65 20 64 61 74 61  s to to the data
1de80 62 61 73 65 2e 20 49 66 20 61 20 63 6f 6e 66 6c  base. If a confl
1de90 69 63 74 20 69 73 20 65 6e 63 6f 75 6e 74 65 72  ict is encounter
1dea0 65 64 2c 20 69 6e 76 6f 6b 65 0a 2a 2a 20 74 68  ed, invoke.** th
1deb0 65 20 63 6f 6e 66 6c 69 63 74 20 68 61 6e 64 6c  e conflict handl
1dec0 65 72 20 63 61 6c 6c 62 61 63 6b 2e 0a 2a 2a 0a  er callback..**.
1ded0 2a 2a 20 49 66 20 61 72 67 75 6d 65 6e 74 20 70  ** If argument p
1dee0 62 52 65 74 72 79 20 69 73 20 4e 55 4c 4c 2c 20  bRetry is NULL, 
1def0 74 68 65 6e 20 69 67 6e 6f 72 65 20 61 6e 79 20  then ignore any 
1df00 43 48 41 4e 47 45 53 45 54 5f 44 41 54 41 20 63  CHANGESET_DATA c
1df10 6f 6e 66 6c 69 63 74 2e 20 49 66 0a 2a 2a 20 6f  onflict. If.** o
1df20 6e 65 20 69 73 20 65 6e 63 6f 75 6e 74 65 72 65  ne is encountere
1df30 64 2c 20 75 70 64 61 74 65 20 6f 72 20 64 65 6c  d, update or del
1df40 65 74 65 20 74 68 65 20 72 6f 77 20 77 69 74 68  ete the row with
1df50 20 74 68 65 20 6d 61 74 63 68 69 6e 67 20 70 72   the matching pr
1df60 69 6d 61 72 79 20 6b 65 79 0a 2a 2a 20 69 6e 73  imary key.** ins
1df70 74 65 61 64 2e 20 4f 72 2c 20 69 66 20 70 62 52  tead. Or, if pbR
1df80 65 74 72 79 20 69 73 20 6e 6f 74 20 4e 55 4c 4c  etry is not NULL
1df90 20 61 6e 64 20 61 20 43 48 41 4e 47 45 53 45 54   and a CHANGESET
1dfa0 5f 44 41 54 41 20 63 6f 6e 66 6c 69 63 74 20 6f  _DATA conflict o
1dfb0 63 63 75 72 73 2c 0a 2a 2a 20 69 6e 76 6f 6b 65  ccurs,.** invoke
1dfc0 20 74 68 65 20 63 6f 6e 66 6c 69 63 74 20 68 61   the conflict ha
1dfd0 6e 64 6c 65 72 2e 20 49 66 20 69 74 20 72 65 74  ndler. If it ret
1dfe0 75 72 6e 73 20 43 48 41 4e 47 45 53 45 54 5f 52  urns CHANGESET_R
1dff0 45 50 4c 41 43 45 2c 20 73 65 74 20 2a 70 62 52  EPLACE, set *pbR
1e000 65 74 72 79 0a 2a 2a 20 74 6f 20 74 72 75 65 20  etry.** to true 
1e010 62 65 66 6f 72 65 20 72 65 74 75 72 6e 69 6e 67  before returning
1e020 2e 20 49 6e 20 74 68 69 73 20 63 61 73 65 20 74  . In this case t
1e030 68 65 20 63 61 6c 6c 65 72 20 77 69 6c 6c 20 69  he caller will i
1e040 6e 76 6f 6b 65 20 74 68 69 73 20 66 75 6e 63 74  nvoke this funct
1e050 69 6f 6e 0a 2a 2a 20 61 67 61 69 6e 2c 20 74 68  ion.** again, th
1e060 69 73 20 74 69 6d 65 20 77 69 74 68 20 70 62 52  is time with pbR
1e070 65 74 72 79 20 73 65 74 20 74 6f 20 4e 55 4c 4c  etry set to NULL
1e080 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 61 72 67 75 6d  ..**.** If argum
1e090 65 6e 74 20 70 62 52 65 70 6c 61 63 65 20 69 73  ent pbReplace is
1e0a0 20 4e 55 4c 4c 20 61 6e 64 20 61 20 43 48 41 4e   NULL and a CHAN
1e0b0 47 45 53 45 54 5f 43 4f 4e 46 4c 49 43 54 20 63  GESET_CONFLICT c
1e0c0 6f 6e 66 6c 69 63 74 20 69 73 20 0a 2a 2a 20 65  onflict is .** e
1e0d0 6e 63 6f 75 6e 74 65 72 65 64 20 69 6e 76 6f 6b  ncountered invok
1e0e0 65 20 74 68 65 20 63 6f 6e 66 6c 69 63 74 20 68  e the conflict h
1e0f0 61 6e 64 6c 65 72 20 77 69 74 68 20 43 48 41 4e  andler with CHAN
1e100 47 45 53 45 54 5f 43 4f 4e 53 54 52 41 49 4e 54  GESET_CONSTRAINT
1e110 20 69 6e 73 74 65 61 64 2e 0a 2a 2a 20 4f 72 2c   instead..** Or,
1e120 20 69 66 20 70 62 52 65 70 6c 61 63 65 20 69 73   if pbReplace is
1e130 20 6e 6f 74 20 4e 55 4c 4c 2c 20 69 6e 76 6f 6b   not NULL, invok
1e140 65 20 69 74 20 77 69 74 68 20 43 48 41 4e 47 45  e it with CHANGE
1e150 53 45 54 5f 43 4f 4e 46 4c 49 43 54 2e 20 49 66  SET_CONFLICT. If
1e160 20 73 75 63 68 0a 2a 2a 20 61 6e 20 69 6e 76 6f   such.** an invo
1e170 63 61 74 69 6f 6e 20 72 65 74 75 72 6e 73 20 53  cation returns S
1e180 51 4c 49 54 45 5f 43 48 41 4e 47 45 53 45 54 5f  QLITE_CHANGESET_
1e190 52 45 50 4c 41 43 45 2c 20 73 65 74 20 2a 70 62  REPLACE, set *pb
1e1a0 52 65 70 6c 61 63 65 20 74 6f 20 74 72 75 65 0a  Replace to true.
1e1b0 2a 2a 20 62 65 66 6f 72 65 20 72 65 74 72 79 69  ** before retryi
1e1c0 6e 67 2e 20 49 6e 20 74 68 69 73 20 63 61 73 65  ng. In this case
1e1d0 20 74 68 65 20 63 61 6c 6c 65 72 20 61 74 74 65   the caller atte
1e1e0 6d 70 74 73 20 74 6f 20 72 65 6d 6f 76 65 20 74  mpts to remove t
1e1f0 68 65 20 63 6f 6e 66 6c 69 63 74 69 6e 67 0a 2a  he conflicting.*
1e200 2a 20 72 6f 77 20 62 65 66 6f 72 65 20 69 6e 76  * row before inv
1e210 6f 6b 69 6e 67 20 74 68 69 73 20 66 75 6e 63 74  oking this funct
1e220 69 6f 6e 20 61 67 61 69 6e 2c 20 74 68 69 73 20  ion again, this 
1e230 74 69 6d 65 20 77 69 74 68 20 70 62 52 65 70 6c  time with pbRepl
1e240 61 63 65 20 73 65 74 20 0a 2a 2a 20 74 6f 20 4e  ace set .** to N
1e250 55 4c 4c 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 61 6e  ULL..**.** If an
1e260 79 20 63 6f 6e 66 6c 69 63 74 20 68 61 6e 64 6c  y conflict handl
1e270 65 72 20 72 65 74 75 72 6e 73 20 53 51 4c 49 54  er returns SQLIT
1e280 45 5f 43 48 41 4e 47 45 53 45 54 5f 41 42 4f 52  E_CHANGESET_ABOR
1e290 54 2c 20 74 68 69 73 20 66 75 6e 63 74 69 6f 6e  T, this function
1e2a0 0a 2a 2a 20 72 65 74 75 72 6e 73 20 53 51 4c 49  .** returns SQLI
1e2b0 54 45 5f 41 42 4f 52 54 2e 20 4f 74 68 65 72 77  TE_ABORT. Otherw
1e2c0 69 73 65 2c 20 69 66 20 6e 6f 20 65 72 72 6f 72  ise, if no error
1e2d0 20 6f 63 63 75 72 73 2c 20 53 51 4c 49 54 45 5f   occurs, SQLITE_
1e2e0 4f 4b 20 69 73 20 0a 2a 2a 20 72 65 74 75 72 6e  OK is .** return
1e2f0 65 64 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e  ed..*/.static in
1e300 74 20 73 65 73 73 69 6f 6e 41 70 70 6c 79 4f 6e  t sessionApplyOn
1e310 65 4f 70 28 0a 20 20 73 71 6c 69 74 65 33 5f 63  eOp(.  sqlite3_c
1e320 68 61 6e 67 65 73 65 74 5f 69 74 65 72 20 2a 70  hangeset_iter *p
1e330 49 74 65 72 2c 20 20 2f 2a 20 43 68 61 6e 67 65  Iter,  /* Change
1e340 73 65 74 20 69 74 65 72 61 74 6f 72 20 2a 2f 0a  set iterator */.
1e350 20 20 53 65 73 73 69 6f 6e 41 70 70 6c 79 43 74    SessionApplyCt
1e360 78 20 2a 70 2c 20 20 20 20 20 20 20 20 20 20 20  x *p,           
1e370 20 20 2f 2a 20 63 68 61 6e 67 65 73 65 74 5f 61    /* changeset_a
1e380 70 70 6c 79 28 29 20 63 6f 6e 74 65 78 74 20 2a  pply() context *
1e390 2f 0a 20 20 69 6e 74 28 2a 78 43 6f 6e 66 6c 69  /.  int(*xConfli
1e3a0 63 74 29 28 76 6f 69 64 20 2a 2c 20 69 6e 74 2c  ct)(void *, int,
1e3b0 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 73   sqlite3_changes
1e3c0 65 74 5f 69 74 65 72 20 2a 29 2c 0a 20 20 76 6f  et_iter *),.  vo
1e3d0 69 64 20 2a 70 43 74 78 2c 20 20 20 20 20 20 20  id *pCtx,       
1e3e0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
1e3f0 20 46 69 72 73 74 20 61 72 67 75 6d 65 6e 74 20   First argument 
1e400 66 6f 72 20 74 68 65 20 63 6f 6e 66 6c 69 63 74  for the conflict
1e410 20 68 61 6e 64 6c 65 72 20 2a 2f 0a 20 20 69 6e   handler */.  in
1e420 74 20 2a 70 62 52 65 70 6c 61 63 65 2c 20 20 20  t *pbReplace,   
1e430 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
1e440 20 4f 55 54 3a 20 54 72 75 65 20 74 6f 20 72 65   OUT: True to re
1e450 6d 6f 76 65 20 50 4b 20 72 6f 77 20 61 6e 64 20  move PK row and 
1e460 72 65 74 72 79 20 2a 2f 0a 20 20 69 6e 74 20 2a  retry */.  int *
1e470 70 62 52 65 74 72 79 20 20 20 20 20 20 20 20 20  pbRetry         
1e480 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 4f 55             /* OU
1e490 54 3a 20 54 72 75 65 20 74 6f 20 72 65 74 72 79  T: True to retry
1e4a0 2e 20 2a 2f 0a 29 7b 0a 20 20 63 6f 6e 73 74 20  . */.){.  const 
1e4b0 63 68 61 72 20 2a 7a 44 75 6d 6d 79 3b 0a 20 20  char *zDummy;.  
1e4c0 69 6e 74 20 6f 70 3b 0a 20 20 69 6e 74 20 6e 43  int op;.  int nC
1e4d0 6f 6c 3b 0a 20 20 69 6e 74 20 72 63 20 3d 20 53  ol;.  int rc = S
1e4e0 51 4c 49 54 45 5f 4f 4b 3b 0a 0a 20 20 61 73 73  QLITE_OK;..  ass
1e4f0 65 72 74 28 20 70 2d 3e 70 44 65 6c 65 74 65 20  ert( p->pDelete 
1e500 26 26 20 70 2d 3e 70 55 70 64 61 74 65 20 26 26  && p->pUpdate &&
1e510 20 70 2d 3e 70 49 6e 73 65 72 74 20 26 26 20 70   p->pInsert && p
1e520 2d 3e 70 53 65 6c 65 63 74 20 29 3b 0a 20 20 61  ->pSelect );.  a
1e530 73 73 65 72 74 28 20 70 2d 3e 61 7a 43 6f 6c 20  ssert( p->azCol 
1e540 26 26 20 70 2d 3e 61 62 50 4b 20 29 3b 0a 20 20  && p->abPK );.  
1e550 61 73 73 65 72 74 28 20 21 70 62 52 65 70 6c 61  assert( !pbRepla
1e560 63 65 20 7c 7c 20 2a 70 62 52 65 70 6c 61 63 65  ce || *pbReplace
1e570 3d 3d 30 20 29 3b 0a 0a 20 20 73 71 6c 69 74 65  ==0 );..  sqlite
1e580 33 63 68 61 6e 67 65 73 65 74 5f 6f 70 28 70 49  3changeset_op(pI
1e590 74 65 72 2c 20 26 7a 44 75 6d 6d 79 2c 20 26 6e  ter, &zDummy, &n
1e5a0 43 6f 6c 2c 20 26 6f 70 2c 20 30 29 3b 0a 0a 20  Col, &op, 0);.. 
1e5b0 20 69 66 28 20 6f 70 3d 3d 53 51 4c 49 54 45 5f   if( op==SQLITE_
1e5c0 44 45 4c 45 54 45 20 29 7b 0a 0a 20 20 20 20 2f  DELETE ){..    /
1e5d0 2a 20 42 69 6e 64 20 76 61 6c 75 65 73 20 74 6f  * Bind values to
1e5e0 20 74 68 65 20 44 45 4c 45 54 45 20 73 74 61 74   the DELETE stat
1e5f0 65 6d 65 6e 74 2e 20 49 66 20 63 6f 6e 66 6c 69  ement. If confli
1e600 63 74 20 68 61 6e 64 6c 69 6e 67 20 69 73 20 72  ct handling is r
1e610 65 71 75 69 72 65 64 2c 0a 20 20 20 20 2a 2a 20  equired,.    ** 
1e620 62 69 6e 64 20 76 61 6c 75 65 73 20 66 6f 72 20  bind values for 
1e630 61 6c 6c 20 63 6f 6c 75 6d 6e 73 20 61 6e 64 20  all columns and 
1e640 73 65 74 20 62 6f 75 6e 64 20 76 61 72 69 61 62  set bound variab
1e650 6c 65 20 28 6e 43 6f 6c 2b 31 29 20 74 6f 20 74  le (nCol+1) to t
1e660 72 75 65 2e 0a 20 20 20 20 2a 2a 20 4f 72 2c 20  rue..    ** Or, 
1e670 69 66 20 63 6f 6e 66 6c 69 63 74 20 68 61 6e 64  if conflict hand
1e680 6c 69 6e 67 20 69 73 20 6e 6f 74 20 72 65 71 75  ling is not requ
1e690 69 72 65 64 2c 20 62 69 6e 64 20 6a 75 73 74 20  ired, bind just 
1e6a0 74 68 65 20 50 4b 20 63 6f 6c 75 6d 6e 0a 20 20  the PK column.  
1e6b0 20 20 2a 2a 20 76 61 6c 75 65 73 20 61 6e 64 2c    ** values and,
1e6c0 20 69 66 20 69 74 20 65 78 69 73 74 73 2c 20 73   if it exists, s
1e6d0 65 74 20 28 6e 43 6f 6c 2b 31 29 20 74 6f 20 66  et (nCol+1) to f
1e6e0 61 6c 73 65 2e 20 43 6f 6e 66 6c 69 63 74 20 68  alse. Conflict h
1e6f0 61 6e 64 6c 69 6e 67 0a 20 20 20 20 2a 2a 20 69  andling.    ** i
1e700 73 20 6e 6f 74 20 72 65 71 75 69 72 65 64 20 69  s not required i
1e710 66 3a 0a 20 20 20 20 2a 2a 0a 20 20 20 20 2a 2a  f:.    **.    **
1e720 20 20 20 2a 20 74 68 69 73 20 69 73 20 61 20 70     * this is a p
1e730 61 74 63 68 73 65 74 2c 20 6f 72 0a 20 20 20 20  atchset, or.    
1e740 2a 2a 20 20 20 2a 20 28 70 62 52 65 74 72 79 3d  **   * (pbRetry=
1e750 3d 30 29 2c 20 6f 72 0a 20 20 20 20 2a 2a 20 20  =0), or.    **  
1e760 20 2a 20 61 6c 6c 20 63 6f 6c 75 6d 6e 73 20 6f   * all columns o
1e770 66 20 74 68 65 20 74 61 62 6c 65 20 61 72 65 20  f the table are 
1e780 50 4b 20 63 6f 6c 75 6d 6e 73 20 28 69 6e 20 74  PK columns (in t
1e790 68 69 73 20 63 61 73 65 20 74 68 65 72 65 20 69  his case there i
1e7a0 73 0a 20 20 20 20 2a 2a 20 20 20 20 20 6e 6f 20  s.    **     no 
1e7b0 28 6e 43 6f 6c 2b 31 29 20 76 61 72 69 61 62 6c  (nCol+1) variabl
1e7c0 65 20 74 6f 20 62 69 6e 64 20 74 6f 29 2e 0a 20  e to bind to).. 
1e7d0 20 20 20 2a 2f 0a 20 20 20 20 75 38 20 2a 61 62     */.    u8 *ab
1e7e0 50 4b 20 3d 20 28 70 49 74 65 72 2d 3e 62 50 61  PK = (pIter->bPa
1e7f0 74 63 68 73 65 74 20 3f 20 70 2d 3e 61 62 50 4b  tchset ? p->abPK
1e800 20 3a 20 30 29 3b 0a 20 20 20 20 72 63 20 3d 20   : 0);.    rc = 
1e810 73 65 73 73 69 6f 6e 42 69 6e 64 52 6f 77 28 70  sessionBindRow(p
1e820 49 74 65 72 2c 20 73 71 6c 69 74 65 33 63 68 61  Iter, sqlite3cha
1e830 6e 67 65 73 65 74 5f 6f 6c 64 2c 20 6e 43 6f 6c  ngeset_old, nCol
1e840 2c 20 61 62 50 4b 2c 20 70 2d 3e 70 44 65 6c 65  , abPK, p->pDele
1e850 74 65 29 3b 0a 20 20 20 20 69 66 28 20 72 63 3d  te);.    if( rc=
1e860 3d 53 51 4c 49 54 45 5f 4f 4b 20 26 26 20 73 71  =SQLITE_OK && sq
1e870 6c 69 74 65 33 5f 62 69 6e 64 5f 70 61 72 61 6d  lite3_bind_param
1e880 65 74 65 72 5f 63 6f 75 6e 74 28 70 2d 3e 70 44  eter_count(p->pD
1e890 65 6c 65 74 65 29 3e 6e 43 6f 6c 20 29 7b 0a 20  elete)>nCol ){. 
1e8a0 20 20 20 20 20 72 63 20 3d 20 73 71 6c 69 74 65       rc = sqlite
1e8b0 33 5f 62 69 6e 64 5f 69 6e 74 28 70 2d 3e 70 44  3_bind_int(p->pD
1e8c0 65 6c 65 74 65 2c 20 6e 43 6f 6c 2b 31 2c 20 28  elete, nCol+1, (
1e8d0 70 62 52 65 74 72 79 3d 3d 30 20 7c 7c 20 61 62  pbRetry==0 || ab
1e8e0 50 4b 29 29 3b 0a 20 20 20 20 7d 0a 20 20 20 20  PK));.    }.    
1e8f0 69 66 28 20 72 63 21 3d 53 51 4c 49 54 45 5f 4f  if( rc!=SQLITE_O
1e900 4b 20 29 20 72 65 74 75 72 6e 20 72 63 3b 0a 0a  K ) return rc;..
1e910 20 20 20 20 73 71 6c 69 74 65 33 5f 73 74 65 70      sqlite3_step
1e920 28 70 2d 3e 70 44 65 6c 65 74 65 29 3b 0a 20 20  (p->pDelete);.  
1e930 20 20 72 63 20 3d 20 73 71 6c 69 74 65 33 5f 72    rc = sqlite3_r
1e940 65 73 65 74 28 70 2d 3e 70 44 65 6c 65 74 65 29  eset(p->pDelete)
1e950 3b 0a 20 20 20 20 69 66 28 20 72 63 3d 3d 53 51  ;.    if( rc==SQ
1e960 4c 49 54 45 5f 4f 4b 20 26 26 20 73 71 6c 69 74  LITE_OK && sqlit
1e970 65 33 5f 63 68 61 6e 67 65 73 28 70 2d 3e 64 62  e3_changes(p->db
1e980 29 3d 3d 30 20 29 7b 0a 20 20 20 20 20 20 72 63  )==0 ){.      rc
1e990 20 3d 20 73 65 73 73 69 6f 6e 43 6f 6e 66 6c 69   = sessionConfli
1e9a0 63 74 48 61 6e 64 6c 65 72 28 0a 20 20 20 20 20  ctHandler(.     
1e9b0 20 20 20 20 20 53 51 4c 49 54 45 5f 43 48 41 4e       SQLITE_CHAN
1e9c0 47 45 53 45 54 5f 44 41 54 41 2c 20 70 2c 20 70  GESET_DATA, p, p
1e9d0 49 74 65 72 2c 20 78 43 6f 6e 66 6c 69 63 74 2c  Iter, xConflict,
1e9e0 20 70 43 74 78 2c 20 70 62 52 65 74 72 79 0a 20   pCtx, pbRetry. 
1e9f0 20 20 20 20 20 29 3b 0a 20 20 20 20 7d 65 6c 73       );.    }els
1ea00 65 20 69 66 28 20 28 72 63 26 30 78 66 66 29 3d  e if( (rc&0xff)=
1ea10 3d 53 51 4c 49 54 45 5f 43 4f 4e 53 54 52 41 49  =SQLITE_CONSTRAI
1ea20 4e 54 20 29 7b 0a 20 20 20 20 20 20 72 63 20 3d  NT ){.      rc =
1ea30 20 73 65 73 73 69 6f 6e 43 6f 6e 66 6c 69 63 74   sessionConflict
1ea40 48 61 6e 64 6c 65 72 28 0a 20 20 20 20 20 20 20  Handler(.       
1ea50 20 20 20 53 51 4c 49 54 45 5f 43 48 41 4e 47 45     SQLITE_CHANGE
1ea60 53 45 54 5f 43 4f 4e 46 4c 49 43 54 2c 20 70 2c  SET_CONFLICT, p,
1ea70 20 70 49 74 65 72 2c 20 78 43 6f 6e 66 6c 69 63   pIter, xConflic
1ea80 74 2c 20 70 43 74 78 2c 20 30 0a 20 20 20 20 20  t, pCtx, 0.     
1ea90 20 29 3b 0a 20 20 20 20 7d 0a 0a 20 20 7d 65 6c   );.    }..  }el
1eaa0 73 65 20 69 66 28 20 6f 70 3d 3d 53 51 4c 49 54  se if( op==SQLIT
1eab0 45 5f 55 50 44 41 54 45 20 29 7b 0a 20 20 20 20  E_UPDATE ){.    
1eac0 69 6e 74 20 69 3b 0a 0a 20 20 20 20 2f 2a 20 42  int i;..    /* B
1ead0 69 6e 64 20 76 61 6c 75 65 73 20 74 6f 20 74 68  ind values to th
1eae0 65 20 55 50 44 41 54 45 20 73 74 61 74 65 6d 65  e UPDATE stateme
1eaf0 6e 74 2e 20 2a 2f 0a 20 20 20 20 66 6f 72 28 69  nt. */.    for(i
1eb00 3d 30 3b 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f  =0; rc==SQLITE_O
1eb10 4b 20 26 26 20 69 3c 6e 43 6f 6c 3b 20 69 2b 2b  K && i<nCol; i++
1eb20 29 7b 0a 20 20 20 20 20 20 73 71 6c 69 74 65 33  ){.      sqlite3
1eb30 5f 76 61 6c 75 65 20 2a 70 4f 6c 64 20 3d 20 73  _value *pOld = s
1eb40 65 73 73 69 6f 6e 43 68 61 6e 67 65 73 65 74 4f  essionChangesetO
1eb50 6c 64 28 70 49 74 65 72 2c 20 69 29 3b 0a 20 20  ld(pIter, i);.  
1eb60 20 20 20 20 73 71 6c 69 74 65 33 5f 76 61 6c 75      sqlite3_valu
1eb70 65 20 2a 70 4e 65 77 20 3d 20 73 65 73 73 69 6f  e *pNew = sessio
1eb80 6e 43 68 61 6e 67 65 73 65 74 4e 65 77 28 70 49  nChangesetNew(pI
1eb90 74 65 72 2c 20 69 29 3b 0a 0a 20 20 20 20 20 20  ter, i);..      
1eba0 73 71 6c 69 74 65 33 5f 62 69 6e 64 5f 69 6e 74  sqlite3_bind_int
1ebb0 28 70 2d 3e 70 55 70 64 61 74 65 2c 20 69 2a 33  (p->pUpdate, i*3
1ebc0 2b 32 2c 20 21 21 70 4e 65 77 29 3b 0a 20 20 20  +2, !!pNew);.   
1ebd0 20 20 20 69 66 28 20 70 4f 6c 64 20 29 7b 0a 20     if( pOld ){. 
1ebe0 20 20 20 20 20 20 20 72 63 20 3d 20 73 65 73 73         rc = sess
1ebf0 69 6f 6e 42 69 6e 64 56 61 6c 75 65 28 70 2d 3e  ionBindValue(p->
1ec00 70 55 70 64 61 74 65 2c 20 69 2a 33 2b 31 2c 20  pUpdate, i*3+1, 
1ec10 70 4f 6c 64 29 3b 0a 20 20 20 20 20 20 7d 0a 20  pOld);.      }. 
1ec20 20 20 20 20 20 69 66 28 20 72 63 3d 3d 53 51 4c       if( rc==SQL
1ec30 49 54 45 5f 4f 4b 20 26 26 20 70 4e 65 77 20 29  ITE_OK && pNew )
1ec40 7b 0a 20 20 20 20 20 20 20 20 72 63 20 3d 20 73  {.        rc = s
1ec50 65 73 73 69 6f 6e 42 69 6e 64 56 61 6c 75 65 28  essionBindValue(
1ec60 70 2d 3e 70 55 70 64 61 74 65 2c 20 69 2a 33 2b  p->pUpdate, i*3+
1ec70 33 2c 20 70 4e 65 77 29 3b 0a 20 20 20 20 20 20  3, pNew);.      
1ec80 7d 0a 20 20 20 20 7d 0a 20 20 20 20 69 66 28 20  }.    }.    if( 
1ec90 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b  rc==SQLITE_OK ){
1eca0 0a 20 20 20 20 20 20 73 71 6c 69 74 65 33 5f 62  .      sqlite3_b
1ecb0 69 6e 64 5f 69 6e 74 28 70 2d 3e 70 55 70 64 61  ind_int(p->pUpda
1ecc0 74 65 2c 20 6e 43 6f 6c 2a 33 2b 31 2c 20 70 62  te, nCol*3+1, pb
1ecd0 52 65 74 72 79 3d 3d 30 20 7c 7c 20 70 49 74 65  Retry==0 || pIte
1ece0 72 2d 3e 62 50 61 74 63 68 73 65 74 29 3b 0a 20  r->bPatchset);. 
1ecf0 20 20 20 7d 0a 20 20 20 20 69 66 28 20 72 63 21     }.    if( rc!
1ed00 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 20 72 65 74  =SQLITE_OK ) ret
1ed10 75 72 6e 20 72 63 3b 0a 0a 20 20 20 20 2f 2a 20  urn rc;..    /* 
1ed20 41 74 74 65 6d 70 74 20 74 68 65 20 55 50 44 41  Attempt the UPDA
1ed30 54 45 2e 20 49 6e 20 74 68 65 20 63 61 73 65 20  TE. In the case 
1ed40 6f 66 20 61 20 4e 4f 54 46 4f 55 4e 44 20 6f 72  of a NOTFOUND or
1ed50 20 44 41 54 41 20 63 6f 6e 66 6c 69 63 74 2c 0a   DATA conflict,.
1ed60 20 20 20 20 2a 2a 20 74 68 65 20 72 65 73 75 6c      ** the resul
1ed70 74 20 77 69 6c 6c 20 62 65 20 53 51 4c 49 54 45  t will be SQLITE
1ed80 5f 4f 4b 20 77 69 74 68 20 30 20 72 6f 77 73 20  _OK with 0 rows 
1ed90 6d 6f 64 69 66 69 65 64 2e 20 2a 2f 0a 20 20 20  modified. */.   
1eda0 20 73 71 6c 69 74 65 33 5f 73 74 65 70 28 70 2d   sqlite3_step(p-
1edb0 3e 70 55 70 64 61 74 65 29 3b 0a 20 20 20 20 72  >pUpdate);.    r
1edc0 63 20 3d 20 73 71 6c 69 74 65 33 5f 72 65 73 65  c = sqlite3_rese
1edd0 74 28 70 2d 3e 70 55 70 64 61 74 65 29 3b 0a 0a  t(p->pUpdate);..
1ede0 20 20 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49      if( rc==SQLI
1edf0 54 45 5f 4f 4b 20 26 26 20 73 71 6c 69 74 65 33  TE_OK && sqlite3
1ee00 5f 63 68 61 6e 67 65 73 28 70 2d 3e 64 62 29 3d  _changes(p->db)=
1ee10 3d 30 20 29 7b 0a 20 20 20 20 20 20 2f 2a 20 41  =0 ){.      /* A
1ee20 20 4e 4f 54 46 4f 55 4e 44 20 6f 72 20 44 41 54   NOTFOUND or DAT
1ee30 41 20 65 72 72 6f 72 2e 20 53 65 61 72 63 68 20  A error. Search 
1ee40 74 68 65 20 74 61 62 6c 65 20 74 6f 20 73 65 65  the table to see
1ee50 20 69 66 20 69 74 20 63 6f 6e 74 61 69 6e 73 0a   if it contains.
1ee60 20 20 20 20 20 20 2a 2a 20 61 20 72 6f 77 20 77        ** a row w
1ee70 69 74 68 20 61 20 6d 61 74 63 68 69 6e 67 20 70  ith a matching p
1ee80 72 69 6d 61 72 79 20 6b 65 79 2e 20 49 66 20 73  rimary key. If s
1ee90 6f 2c 20 74 68 69 73 20 69 73 20 61 20 44 41 54  o, this is a DAT
1eea0 41 20 63 6f 6e 66 6c 69 63 74 2e 0a 20 20 20 20  A conflict..    
1eeb0 20 20 2a 2a 20 4f 74 68 65 72 77 69 73 65 2c 20    ** Otherwise, 
1eec0 69 66 20 74 68 65 72 65 20 69 73 20 6e 6f 20 70  if there is no p
1eed0 72 69 6d 61 72 79 20 6b 65 79 20 6d 61 74 63 68  rimary key match
1eee0 2c 20 69 74 20 69 73 20 61 20 4e 4f 54 46 4f 55  , it is a NOTFOU
1eef0 4e 44 2e 20 2a 2f 0a 0a 20 20 20 20 20 20 72 63  ND. */..      rc
1ef00 20 3d 20 73 65 73 73 69 6f 6e 43 6f 6e 66 6c 69   = sessionConfli
1ef10 63 74 48 61 6e 64 6c 65 72 28 0a 20 20 20 20 20  ctHandler(.     
1ef20 20 20 20 20 20 53 51 4c 49 54 45 5f 43 48 41 4e       SQLITE_CHAN
1ef30 47 45 53 45 54 5f 44 41 54 41 2c 20 70 2c 20 70  GESET_DATA, p, p
1ef40 49 74 65 72 2c 20 78 43 6f 6e 66 6c 69 63 74 2c  Iter, xConflict,
1ef50 20 70 43 74 78 2c 20 70 62 52 65 74 72 79 0a 20   pCtx, pbRetry. 
1ef60 20 20 20 20 20 29 3b 0a 0a 20 20 20 20 7d 65 6c       );..    }el
1ef70 73 65 20 69 66 28 20 28 72 63 26 30 78 66 66 29  se if( (rc&0xff)
1ef80 3d 3d 53 51 4c 49 54 45 5f 43 4f 4e 53 54 52 41  ==SQLITE_CONSTRA
1ef90 49 4e 54 20 29 7b 0a 20 20 20 20 20 20 2f 2a 20  INT ){.      /* 
1efa0 54 68 69 73 20 69 73 20 61 6c 77 61 79 73 20 61  This is always a
1efb0 20 43 4f 4e 53 54 52 41 49 4e 54 20 63 6f 6e 66   CONSTRAINT conf
1efc0 6c 69 63 74 2e 20 2a 2f 0a 20 20 20 20 20 20 72  lict. */.      r
1efd0 63 20 3d 20 73 65 73 73 69 6f 6e 43 6f 6e 66 6c  c = sessionConfl
1efe0 69 63 74 48 61 6e 64 6c 65 72 28 0a 20 20 20 20  ictHandler(.    
1eff0 20 20 20 20 20 20 53 51 4c 49 54 45 5f 43 48 41        SQLITE_CHA
1f000 4e 47 45 53 45 54 5f 43 4f 4e 46 4c 49 43 54 2c  NGESET_CONFLICT,
1f010 20 70 2c 20 70 49 74 65 72 2c 20 78 43 6f 6e 66   p, pIter, xConf
1f020 6c 69 63 74 2c 20 70 43 74 78 2c 20 30 0a 20 20  lict, pCtx, 0.  
1f030 20 20 20 20 29 3b 0a 20 20 20 20 7d 0a 0a 20 20      );.    }..  
1f040 7d 65 6c 73 65 7b 0a 20 20 20 20 61 73 73 65 72  }else{.    asser
1f050 74 28 20 6f 70 3d 3d 53 51 4c 49 54 45 5f 49 4e  t( op==SQLITE_IN
1f060 53 45 52 54 20 29 3b 0a 20 20 20 20 72 63 20 3d  SERT );.    rc =
1f070 20 73 65 73 73 69 6f 6e 42 69 6e 64 52 6f 77 28   sessionBindRow(
1f080 70 49 74 65 72 2c 20 73 71 6c 69 74 65 33 63 68  pIter, sqlite3ch
1f090 61 6e 67 65 73 65 74 5f 6e 65 77 2c 20 6e 43 6f  angeset_new, nCo
1f0a0 6c 2c 20 30 2c 20 70 2d 3e 70 49 6e 73 65 72 74  l, 0, p->pInsert
1f0b0 29 3b 0a 20 20 20 20 69 66 28 20 72 63 21 3d 53  );.    if( rc!=S
1f0c0 51 4c 49 54 45 5f 4f 4b 20 29 20 72 65 74 75 72  QLITE_OK ) retur
1f0d0 6e 20 72 63 3b 0a 0a 20 20 20 20 73 71 6c 69 74  n rc;..    sqlit
1f0e0 65 33 5f 73 74 65 70 28 70 2d 3e 70 49 6e 73 65  e3_step(p->pInse
1f0f0 72 74 29 3b 0a 20 20 20 20 72 63 20 3d 20 73 71  rt);.    rc = sq
1f100 6c 69 74 65 33 5f 72 65 73 65 74 28 70 2d 3e 70  lite3_reset(p->p
1f110 49 6e 73 65 72 74 29 3b 0a 20 20 20 20 69 66 28  Insert);.    if(
1f120 20 28 72 63 26 30 78 66 66 29 3d 3d 53 51 4c 49   (rc&0xff)==SQLI
1f130 54 45 5f 43 4f 4e 53 54 52 41 49 4e 54 20 29 7b  TE_CONSTRAINT ){
1f140 0a 20 20 20 20 20 20 72 63 20 3d 20 73 65 73 73  .      rc = sess
1f150 69 6f 6e 43 6f 6e 66 6c 69 63 74 48 61 6e 64 6c  ionConflictHandl
1f160 65 72 28 0a 20 20 20 20 20 20 20 20 20 20 53 51  er(.          SQ
1f170 4c 49 54 45 5f 43 48 41 4e 47 45 53 45 54 5f 43  LITE_CHANGESET_C
1f180 4f 4e 46 4c 49 43 54 2c 20 70 2c 20 70 49 74 65  ONFLICT, p, pIte
1f190 72 2c 20 78 43 6f 6e 66 6c 69 63 74 2c 20 70 43  r, xConflict, pC
1f1a0 74 78 2c 20 70 62 52 65 70 6c 61 63 65 0a 20 20  tx, pbReplace.  
1f1b0 20 20 20 20 29 3b 0a 20 20 20 20 7d 0a 20 20 7d      );.    }.  }
1f1c0 0a 0a 20 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d  ..  return rc;.}
1f1d0 0a 0a 2f 2a 0a 2a 2a 20 41 74 74 65 6d 70 74 20  ../*.** Attempt 
1f1e0 74 6f 20 61 70 70 6c 79 20 74 68 65 20 63 68 61  to apply the cha
1f1f0 6e 67 65 20 74 68 61 74 20 74 68 65 20 69 74 65  nge that the ite
1f200 72 61 74 6f 72 20 70 61 73 73 65 64 20 61 73 20  rator passed as 
1f210 74 68 65 20 66 69 72 73 74 20 61 72 67 75 6d 65  the first argume
1f220 6e 74 0a 2a 2a 20 63 75 72 72 65 6e 74 6c 79 20  nt.** currently 
1f230 70 6f 69 6e 74 73 20 74 6f 20 74 6f 20 74 68 65  points to to the
1f240 20 64 61 74 61 62 61 73 65 2e 20 49 66 20 61 20   database. If a 
1f250 63 6f 6e 66 6c 69 63 74 20 69 73 20 65 6e 63 6f  conflict is enco
1f260 75 6e 74 65 72 65 64 2c 20 69 6e 76 6f 6b 65 0a  untered, invoke.
1f270 2a 2a 20 74 68 65 20 63 6f 6e 66 6c 69 63 74 20  ** the conflict 
1f280 68 61 6e 64 6c 65 72 20 63 61 6c 6c 62 61 63 6b  handler callback
1f290 2e 0a 2a 2a 0a 2a 2a 20 54 68 65 20 64 69 66 66  ..**.** The diff
1f2a0 65 72 65 6e 63 65 20 62 65 74 77 65 65 6e 20 74  erence between t
1f2b0 68 69 73 20 66 75 6e 63 74 69 6f 6e 20 61 6e 64  his function and
1f2c0 20 73 65 73 73 69 6f 6e 41 70 70 6c 79 4f 6e 65   sessionApplyOne
1f2d0 28 29 20 69 73 20 74 68 61 74 20 74 68 69 73 0a  () is that this.
1f2e0 2a 2a 20 66 75 6e 63 74 69 6f 6e 20 68 61 6e 64  ** function hand
1f2f0 6c 65 73 20 74 68 65 20 63 61 73 65 20 77 68 65  les the case whe
1f300 72 65 20 74 68 65 20 63 6f 6e 66 6c 69 63 74 2d  re the conflict-
1f310 68 61 6e 64 6c 65 72 20 69 73 20 69 6e 76 6f 6b  handler is invok
1f320 65 64 20 61 6e 64 20 0a 2a 2a 20 72 65 74 75 72  ed and .** retur
1f330 6e 73 20 53 51 4c 49 54 45 5f 43 48 41 4e 47 45  ns SQLITE_CHANGE
1f340 53 45 54 5f 52 45 50 4c 41 43 45 20 2d 20 69 6e  SET_REPLACE - in
1f350 64 69 63 61 74 69 6e 67 20 74 68 61 74 20 74 68  dicating that th
1f360 65 20 63 68 61 6e 67 65 20 73 68 6f 75 6c 64 20  e change should 
1f370 62 65 0a 2a 2a 20 72 65 74 72 69 65 64 20 69 6e  be.** retried in
1f380 20 73 6f 6d 65 20 6d 61 6e 6e 65 72 2e 0a 2a 2f   some manner..*/
1f390 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73 73  .static int sess
1f3a0 69 6f 6e 41 70 70 6c 79 4f 6e 65 57 69 74 68 52  ionApplyOneWithR
1f3b0 65 74 72 79 28 0a 20 20 73 71 6c 69 74 65 33 20  etry(.  sqlite3 
1f3c0 2a 64 62 2c 20 20 20 20 20 20 20 20 20 20 20 20  *db,            
1f3d0 20 20 20 20 20 20 20 20 2f 2a 20 41 70 70 6c 79          /* Apply
1f3e0 20 63 68 61 6e 67 65 20 74 6f 20 22 6d 61 69 6e   change to "main
1f3f0 22 20 64 62 20 6f 66 20 74 68 69 73 20 68 61 6e  " db of this han
1f400 64 6c 65 20 2a 2f 0a 20 20 73 71 6c 69 74 65 33  dle */.  sqlite3
1f410 5f 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72 20  _changeset_iter 
1f420 2a 70 49 74 65 72 2c 20 20 2f 2a 20 43 68 61 6e  *pIter,  /* Chan
1f430 67 65 73 65 74 20 69 74 65 72 61 74 6f 72 20 74  geset iterator t
1f440 6f 20 72 65 61 64 20 63 68 61 6e 67 65 20 66 72  o read change fr
1f450 6f 6d 20 2a 2f 0a 20 20 53 65 73 73 69 6f 6e 41  om */.  SessionA
1f460 70 70 6c 79 43 74 78 20 2a 70 41 70 70 6c 79 2c  pplyCtx *pApply,
1f470 20 20 20 20 20 20 20 20 2f 2a 20 41 70 70 6c 79          /* Apply
1f480 20 63 6f 6e 74 65 78 74 20 2a 2f 0a 20 20 69 6e   context */.  in
1f490 74 28 2a 78 43 6f 6e 66 6c 69 63 74 29 28 76 6f  t(*xConflict)(vo
1f4a0 69 64 2a 2c 20 69 6e 74 2c 20 73 71 6c 69 74 65  id*, int, sqlite
1f4b0 33 5f 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72  3_changeset_iter
1f4c0 2a 29 2c 0a 20 20 76 6f 69 64 20 2a 70 43 74 78  *),.  void *pCtx
1f4d0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1f4e0 20 20 20 20 20 20 2f 2a 20 46 69 72 73 74 20 61        /* First a
1f4f0 72 67 75 6d 65 6e 74 20 70 61 73 73 65 64 20 74  rgument passed t
1f500 6f 20 78 43 6f 6e 66 6c 69 63 74 20 2a 2f 0a 29  o xConflict */.)
1f510 7b 0a 20 20 69 6e 74 20 62 52 65 70 6c 61 63 65  {.  int bReplace
1f520 20 3d 20 30 3b 0a 20 20 69 6e 74 20 62 52 65 74   = 0;.  int bRet
1f530 72 79 20 3d 20 30 3b 0a 20 20 69 6e 74 20 72 63  ry = 0;.  int rc
1f540 3b 0a 0a 20 20 72 63 20 3d 20 73 65 73 73 69 6f  ;..  rc = sessio
1f550 6e 41 70 70 6c 79 4f 6e 65 4f 70 28 70 49 74 65  nApplyOneOp(pIte
1f560 72 2c 20 70 41 70 70 6c 79 2c 20 78 43 6f 6e 66  r, pApply, xConf
1f570 6c 69 63 74 2c 20 70 43 74 78 2c 20 26 62 52 65  lict, pCtx, &bRe
1f580 70 6c 61 63 65 2c 20 26 62 52 65 74 72 79 29 3b  place, &bRetry);
1f590 0a 20 20 61 73 73 65 72 74 28 20 72 63 3d 3d 53  .  assert( rc==S
1f5a0 51 4c 49 54 45 5f 4f 4b 20 7c 7c 20 28 62 52 65  QLITE_OK || (bRe
1f5b0 74 72 79 3d 3d 30 20 26 26 20 62 52 65 70 6c 61  try==0 && bRepla
1f5c0 63 65 3d 3d 30 29 20 29 3b 0a 0a 20 20 2f 2a 20  ce==0) );..  /* 
1f5d0 49 66 20 74 68 65 20 62 52 65 74 72 79 20 66 6c  If the bRetry fl
1f5e0 61 67 20 69 73 20 73 65 74 2c 20 74 68 65 20 63  ag is set, the c
1f5f0 68 61 6e 67 65 20 68 61 73 20 6e 6f 74 20 62 65  hange has not be
1f600 65 6e 20 61 70 70 6c 69 65 64 20 64 75 65 20 74  en applied due t
1f610 6f 20 61 6e 0a 20 20 2a 2a 20 53 51 4c 49 54 45  o an.  ** SQLITE
1f620 5f 43 48 41 4e 47 45 53 45 54 5f 44 41 54 41 20  _CHANGESET_DATA 
1f630 70 72 6f 62 6c 65 6d 20 28 69 2e 65 2e 20 74 68  problem (i.e. th
1f640 69 73 20 69 73 20 61 6e 20 55 50 44 41 54 45 20  is is an UPDATE 
1f650 6f 72 20 44 45 4c 45 54 45 20 61 6e 64 0a 20 20  or DELETE and.  
1f660 2a 2a 20 61 20 72 6f 77 20 77 69 74 68 20 74 68  ** a row with th
1f670 65 20 63 6f 72 72 65 63 74 20 50 4b 20 69 73 20  e correct PK is 
1f680 70 72 65 73 65 6e 74 20 69 6e 20 74 68 65 20 64  present in the d
1f690 62 2c 20 62 75 74 20 6f 6e 65 20 6f 72 20 6d 6f  b, but one or mo
1f6a0 72 65 20 6f 74 68 65 72 0a 20 20 2a 2a 20 66 69  re other.  ** fi
1f6b0 65 6c 64 73 20 64 6f 20 6e 6f 74 20 63 6f 6e 74  elds do not cont
1f6c0 61 69 6e 20 74 68 65 20 65 78 70 65 63 74 65 64  ain the expected
1f6d0 20 76 61 6c 75 65 73 29 20 61 6e 64 20 74 68 65   values) and the
1f6e0 20 63 6f 6e 66 6c 69 63 74 20 68 61 6e 64 6c 65   conflict handle
1f6f0 72 20 0a 20 20 2a 2a 20 72 65 74 75 72 6e 65 64  r .  ** returned
1f700 20 53 51 4c 49 54 45 5f 43 48 41 4e 47 45 53 45   SQLITE_CHANGESE
1f710 54 5f 52 45 50 4c 41 43 45 2e 20 49 6e 20 74 68  T_REPLACE. In th
1f720 69 73 20 63 61 73 65 20 72 65 74 72 79 20 74 68  is case retry th
1f730 65 20 6f 70 65 72 61 74 69 6f 6e 2c 0a 20 20 2a  e operation,.  *
1f740 2a 20 62 75 74 20 70 61 73 73 20 4e 55 4c 4c 20  * but pass NULL 
1f750 61 73 20 74 68 65 20 66 69 6e 61 6c 20 61 72 67  as the final arg
1f760 75 6d 65 6e 74 20 73 6f 20 74 68 61 74 20 73 65  ument so that se
1f770 73 73 69 6f 6e 41 70 70 6c 79 4f 6e 65 4f 70 28  ssionApplyOneOp(
1f780 29 20 69 67 6e 6f 72 65 73 0a 20 20 2a 2a 20 74  ) ignores.  ** t
1f790 68 65 20 53 51 4c 49 54 45 5f 43 48 41 4e 47 45  he SQLITE_CHANGE
1f7a0 53 45 54 5f 44 41 54 41 20 70 72 6f 62 6c 65 6d  SET_DATA problem
1f7b0 2e 20 20 2a 2f 0a 20 20 69 66 28 20 62 52 65 74  .  */.  if( bRet
1f7c0 72 79 20 29 7b 0a 20 20 20 20 61 73 73 65 72 74  ry ){.    assert
1f7d0 28 20 70 49 74 65 72 2d 3e 6f 70 3d 3d 53 51 4c  ( pIter->op==SQL
1f7e0 49 54 45 5f 55 50 44 41 54 45 20 7c 7c 20 70 49  ITE_UPDATE || pI
1f7f0 74 65 72 2d 3e 6f 70 3d 3d 53 51 4c 49 54 45 5f  ter->op==SQLITE_
1f800 44 45 4c 45 54 45 20 29 3b 0a 20 20 20 20 72 63  DELETE );.    rc
1f810 20 3d 20 73 65 73 73 69 6f 6e 41 70 70 6c 79 4f   = sessionApplyO
1f820 6e 65 4f 70 28 70 49 74 65 72 2c 20 70 41 70 70  neOp(pIter, pApp
1f830 6c 79 2c 20 78 43 6f 6e 66 6c 69 63 74 2c 20 70  ly, xConflict, p
1f840 43 74 78 2c 20 30 2c 20 30 29 3b 0a 20 20 7d 0a  Ctx, 0, 0);.  }.
1f850 0a 20 20 2f 2a 20 49 66 20 74 68 65 20 62 52 65  .  /* If the bRe
1f860 70 6c 61 63 65 20 66 6c 61 67 20 69 73 20 73 65  place flag is se
1f870 74 2c 20 74 68 65 20 63 68 61 6e 67 65 20 69 73  t, the change is
1f880 20 61 6e 20 49 4e 53 45 52 54 20 74 68 61 74 20   an INSERT that 
1f890 68 61 73 20 6e 6f 74 0a 20 20 2a 2a 20 62 65 65  has not.  ** bee
1f8a0 6e 20 70 65 72 66 6f 72 6d 65 64 20 62 65 63 61  n performed beca
1f8b0 75 73 65 20 74 68 65 20 64 61 74 61 62 61 73 65  use the database
1f8c0 20 61 6c 72 65 61 64 79 20 63 6f 6e 74 61 69 6e   already contain
1f8d0 73 20 61 20 72 6f 77 20 77 69 74 68 20 74 68 65  s a row with the
1f8e0 0a 20 20 2a 2a 20 73 70 65 63 69 66 69 65 64 20  .  ** specified 
1f8f0 70 72 69 6d 61 72 79 20 6b 65 79 20 61 6e 64 20  primary key and 
1f900 74 68 65 20 63 6f 6e 66 6c 69 63 74 20 68 61 6e  the conflict han
1f910 64 6c 65 72 20 72 65 74 75 72 6e 65 64 0a 20 20  dler returned.  
1f920 2a 2a 20 53 51 4c 49 54 45 5f 43 48 41 4e 47 45  ** SQLITE_CHANGE
1f930 53 45 54 5f 52 45 50 4c 41 43 45 2e 20 49 6e 20  SET_REPLACE. In 
1f940 74 68 69 73 20 63 61 73 65 20 72 65 6d 6f 76 65  this case remove
1f950 20 74 68 65 20 63 6f 6e 66 6c 69 63 74 69 6e 67   the conflicting
1f960 20 72 6f 77 0a 20 20 2a 2a 20 62 65 66 6f 72 65   row.  ** before
1f970 20 72 65 61 74 74 65 6d 70 74 69 6e 67 20 74 68   reattempting th
1f980 65 20 49 4e 53 45 52 54 2e 20 20 2a 2f 0a 20 20  e INSERT.  */.  
1f990 65 6c 73 65 20 69 66 28 20 62 52 65 70 6c 61 63  else if( bReplac
1f9a0 65 20 29 7b 0a 20 20 20 20 61 73 73 65 72 74 28  e ){.    assert(
1f9b0 20 70 49 74 65 72 2d 3e 6f 70 3d 3d 53 51 4c 49   pIter->op==SQLI
1f9c0 54 45 5f 49 4e 53 45 52 54 20 29 3b 0a 20 20 20  TE_INSERT );.   
1f9d0 20 72 63 20 3d 20 73 71 6c 69 74 65 33 5f 65 78   rc = sqlite3_ex
1f9e0 65 63 28 64 62 2c 20 22 53 41 56 45 50 4f 49 4e  ec(db, "SAVEPOIN
1f9f0 54 20 72 65 70 6c 61 63 65 5f 6f 70 22 2c 20 30  T replace_op", 0
1fa00 2c 20 30 2c 20 30 29 3b 0a 20 20 20 20 69 66 28  , 0, 0);.    if(
1fa10 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29   rc==SQLITE_OK )
1fa20 7b 0a 20 20 20 20 20 20 72 63 20 3d 20 73 65 73  {.      rc = ses
1fa30 73 69 6f 6e 42 69 6e 64 52 6f 77 28 70 49 74 65  sionBindRow(pIte
1fa40 72 2c 20 0a 20 20 20 20 20 20 20 20 20 20 73 71  r, .          sq
1fa50 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74 5f 6e  lite3changeset_n
1fa60 65 77 2c 20 70 41 70 70 6c 79 2d 3e 6e 43 6f 6c  ew, pApply->nCol
1fa70 2c 20 70 41 70 70 6c 79 2d 3e 61 62 50 4b 2c 20  , pApply->abPK, 
1fa80 70 41 70 70 6c 79 2d 3e 70 44 65 6c 65 74 65 29  pApply->pDelete)
1fa90 3b 0a 20 20 20 20 20 20 73 71 6c 69 74 65 33 5f  ;.      sqlite3_
1faa0 62 69 6e 64 5f 69 6e 74 28 70 41 70 70 6c 79 2d  bind_int(pApply-
1fab0 3e 70 44 65 6c 65 74 65 2c 20 70 41 70 70 6c 79  >pDelete, pApply
1fac0 2d 3e 6e 43 6f 6c 2b 31 2c 20 31 29 3b 0a 20 20  ->nCol+1, 1);.  
1fad0 20 20 7d 0a 20 20 20 20 69 66 28 20 72 63 3d 3d    }.    if( rc==
1fae0 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20  SQLITE_OK ){.   
1faf0 20 20 20 73 71 6c 69 74 65 33 5f 73 74 65 70 28     sqlite3_step(
1fb00 70 41 70 70 6c 79 2d 3e 70 44 65 6c 65 74 65 29  pApply->pDelete)
1fb10 3b 0a 20 20 20 20 20 20 72 63 20 3d 20 73 71 6c  ;.      rc = sql
1fb20 69 74 65 33 5f 72 65 73 65 74 28 70 41 70 70 6c  ite3_reset(pAppl
1fb30 79 2d 3e 70 44 65 6c 65 74 65 29 3b 0a 20 20 20  y->pDelete);.   
1fb40 20 7d 0a 20 20 20 20 69 66 28 20 72 63 3d 3d 53   }.    if( rc==S
1fb50 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20  QLITE_OK ){.    
1fb60 20 20 72 63 20 3d 20 73 65 73 73 69 6f 6e 41 70    rc = sessionAp
1fb70 70 6c 79 4f 6e 65 4f 70 28 70 49 74 65 72 2c 20  plyOneOp(pIter, 
1fb80 70 41 70 70 6c 79 2c 20 78 43 6f 6e 66 6c 69 63  pApply, xConflic
1fb90 74 2c 20 70 43 74 78 2c 20 30 2c 20 30 29 3b 0a  t, pCtx, 0, 0);.
1fba0 20 20 20 20 7d 0a 20 20 20 20 69 66 28 20 72 63      }.    if( rc
1fbb0 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20  ==SQLITE_OK ){. 
1fbc0 20 20 20 20 20 72 63 20 3d 20 73 71 6c 69 74 65       rc = sqlite
1fbd0 33 5f 65 78 65 63 28 64 62 2c 20 22 52 45 4c 45  3_exec(db, "RELE
1fbe0 41 53 45 20 72 65 70 6c 61 63 65 5f 6f 70 22 2c  ASE replace_op",
1fbf0 20 30 2c 20 30 2c 20 30 29 3b 0a 20 20 20 20 7d   0, 0, 0);.    }
1fc00 0a 20 20 7d 0a 0a 20 20 72 65 74 75 72 6e 20 72  .  }..  return r
1fc10 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 52 65 74 72  c;.}../*.** Retr
1fc20 79 20 74 68 65 20 63 68 61 6e 67 65 73 20 61 63  y the changes ac
1fc30 63 75 6d 75 6c 61 74 65 64 20 69 6e 20 74 68 65  cumulated in the
1fc40 20 70 41 70 70 6c 79 2d 3e 63 6f 6e 73 74 72 61   pApply->constra
1fc50 69 6e 74 73 20 62 75 66 66 65 72 2e 0a 2a 2f 0a  ints buffer..*/.
1fc60 73 74 61 74 69 63 20 69 6e 74 20 73 65 73 73 69  static int sessi
1fc70 6f 6e 52 65 74 72 79 43 6f 6e 73 74 72 61 69 6e  onRetryConstrain
1fc80 74 73 28 0a 20 20 73 71 6c 69 74 65 33 20 2a 64  ts(.  sqlite3 *d
1fc90 62 2c 20 0a 20 20 69 6e 74 20 62 50 61 74 63 68  b, .  int bPatch
1fca0 73 65 74 2c 0a 20 20 63 6f 6e 73 74 20 63 68 61  set,.  const cha
1fcb0 72 20 2a 7a 54 61 62 2c 0a 20 20 53 65 73 73 69  r *zTab,.  Sessi
1fcc0 6f 6e 41 70 70 6c 79 43 74 78 20 2a 70 41 70 70  onApplyCtx *pApp
1fcd0 6c 79 2c 0a 20 20 69 6e 74 28 2a 78 43 6f 6e 66  ly,.  int(*xConf
1fce0 6c 69 63 74 29 28 76 6f 69 64 2a 2c 20 69 6e 74  lict)(void*, int
1fcf0 2c 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65  , sqlite3_change
1fd00 73 65 74 5f 69 74 65 72 2a 29 2c 0a 20 20 76 6f  set_iter*),.  vo
1fd10 69 64 20 2a 70 43 74 78 20 20 20 20 20 20 20 20  id *pCtx        
1fd20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
1fd30 20 46 69 72 73 74 20 61 72 67 75 6d 65 6e 74 20   First argument 
1fd40 70 61 73 73 65 64 20 74 6f 20 78 43 6f 6e 66 6c  passed to xConfl
1fd50 69 63 74 20 2a 2f 0a 29 7b 0a 20 20 69 6e 74 20  ict */.){.  int 
1fd60 72 63 20 3d 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a  rc = SQLITE_OK;.
1fd70 0a 20 20 77 68 69 6c 65 28 20 70 41 70 70 6c 79  .  while( pApply
1fd80 2d 3e 63 6f 6e 73 74 72 61 69 6e 74 73 2e 6e 42  ->constraints.nB
1fd90 75 66 20 29 7b 0a 20 20 20 20 73 71 6c 69 74 65  uf ){.    sqlite
1fda0 33 5f 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72  3_changeset_iter
1fdb0 20 2a 70 49 74 65 72 32 20 3d 20 30 3b 0a 20 20   *pIter2 = 0;.  
1fdc0 20 20 53 65 73 73 69 6f 6e 42 75 66 66 65 72 20    SessionBuffer 
1fdd0 63 6f 6e 73 20 3d 20 70 41 70 70 6c 79 2d 3e 63  cons = pApply->c
1fde0 6f 6e 73 74 72 61 69 6e 74 73 3b 0a 20 20 20 20  onstraints;.    
1fdf0 6d 65 6d 73 65 74 28 26 70 41 70 70 6c 79 2d 3e  memset(&pApply->
1fe00 63 6f 6e 73 74 72 61 69 6e 74 73 2c 20 30 2c 20  constraints, 0, 
1fe10 73 69 7a 65 6f 66 28 53 65 73 73 69 6f 6e 42 75  sizeof(SessionBu
1fe20 66 66 65 72 29 29 3b 0a 0a 20 20 20 20 72 63 20  ffer));..    rc 
1fe30 3d 20 73 65 73 73 69 6f 6e 43 68 61 6e 67 65 73  = sessionChanges
1fe40 65 74 53 74 61 72 74 28 26 70 49 74 65 72 32 2c  etStart(&pIter2,
1fe50 20 30 2c 20 30 2c 20 63 6f 6e 73 2e 6e 42 75 66   0, 0, cons.nBuf
1fe60 2c 20 63 6f 6e 73 2e 61 42 75 66 29 3b 0a 20 20  , cons.aBuf);.  
1fe70 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54 45    if( rc==SQLITE
1fe80 5f 4f 4b 20 29 7b 0a 20 20 20 20 20 20 69 6e 74  _OK ){.      int
1fe90 20 6e 42 79 74 65 20 3d 20 32 2a 70 41 70 70 6c   nByte = 2*pAppl
1fea0 79 2d 3e 6e 43 6f 6c 2a 73 69 7a 65 6f 66 28 73  y->nCol*sizeof(s
1feb0 71 6c 69 74 65 33 5f 76 61 6c 75 65 2a 29 3b 0a  qlite3_value*);.
1fec0 20 20 20 20 20 20 69 6e 74 20 72 63 32 3b 0a 20        int rc2;. 
1fed0 20 20 20 20 20 70 49 74 65 72 32 2d 3e 62 50 61       pIter2->bPa
1fee0 74 63 68 73 65 74 20 3d 20 62 50 61 74 63 68 73  tchset = bPatchs
1fef0 65 74 3b 0a 20 20 20 20 20 20 70 49 74 65 72 32  et;.      pIter2
1ff00 2d 3e 7a 54 61 62 20 3d 20 28 63 68 61 72 2a 29  ->zTab = (char*)
1ff10 7a 54 61 62 3b 0a 20 20 20 20 20 20 70 49 74 65  zTab;.      pIte
1ff20 72 32 2d 3e 6e 43 6f 6c 20 3d 20 70 41 70 70 6c  r2->nCol = pAppl
1ff30 79 2d 3e 6e 43 6f 6c 3b 0a 20 20 20 20 20 20 70  y->nCol;.      p
1ff40 49 74 65 72 32 2d 3e 61 62 50 4b 20 3d 20 70 41  Iter2->abPK = pA
1ff50 70 70 6c 79 2d 3e 61 62 50 4b 3b 0a 20 20 20 20  pply->abPK;.    
1ff60 20 20 73 65 73 73 69 6f 6e 42 75 66 66 65 72 47    sessionBufferG
1ff70 72 6f 77 28 26 70 49 74 65 72 32 2d 3e 74 62 6c  row(&pIter2->tbl
1ff80 68 64 72 2c 20 6e 42 79 74 65 2c 20 26 72 63 29  hdr, nByte, &rc)
1ff90 3b 0a 20 20 20 20 20 20 70 49 74 65 72 32 2d 3e  ;.      pIter2->
1ffa0 61 70 56 61 6c 75 65 20 3d 20 28 73 71 6c 69 74  apValue = (sqlit
1ffb0 65 33 5f 76 61 6c 75 65 2a 2a 29 70 49 74 65 72  e3_value**)pIter
1ffc0 32 2d 3e 74 62 6c 68 64 72 2e 61 42 75 66 3b 0a  2->tblhdr.aBuf;.
1ffd0 20 20 20 20 20 20 69 66 28 20 72 63 3d 3d 53 51        if( rc==SQ
1ffe0 4c 49 54 45 5f 4f 4b 20 29 20 6d 65 6d 73 65 74  LITE_OK ) memset
1fff0 28 70 49 74 65 72 32 2d 3e 61 70 56 61 6c 75 65  (pIter2->apValue
20000 2c 20 30 2c 20 6e 42 79 74 65 29 3b 0a 0a 20 20  , 0, nByte);..  
20010 20 20 20 20 77 68 69 6c 65 28 20 72 63 3d 3d 53      while( rc==S
20020 51 4c 49 54 45 5f 4f 4b 20 26 26 20 53 51 4c 49  QLITE_OK && SQLI
20030 54 45 5f 52 4f 57 3d 3d 73 71 6c 69 74 65 33 63  TE_ROW==sqlite3c
20040 68 61 6e 67 65 73 65 74 5f 6e 65 78 74 28 70 49  hangeset_next(pI
20050 74 65 72 32 29 20 29 7b 0a 20 20 20 20 20 20 20  ter2) ){.       
20060 20 72 63 20 3d 20 73 65 73 73 69 6f 6e 41 70 70   rc = sessionApp
20070 6c 79 4f 6e 65 57 69 74 68 52 65 74 72 79 28 64  lyOneWithRetry(d
20080 62 2c 20 70 49 74 65 72 32 2c 20 70 41 70 70 6c  b, pIter2, pAppl
20090 79 2c 20 78 43 6f 6e 66 6c 69 63 74 2c 20 70 43  y, xConflict, pC
200a0 74 78 29 3b 0a 20 20 20 20 20 20 7d 0a 0a 20 20  tx);.      }..  
200b0 20 20 20 20 72 63 32 20 3d 20 73 71 6c 69 74 65      rc2 = sqlite
200c0 33 63 68 61 6e 67 65 73 65 74 5f 66 69 6e 61 6c  3changeset_final
200d0 69 7a 65 28 70 49 74 65 72 32 29 3b 0a 20 20 20  ize(pIter2);.   
200e0 20 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54     if( rc==SQLIT
200f0 45 5f 4f 4b 20 29 20 72 63 20 3d 20 72 63 32 3b  E_OK ) rc = rc2;
20100 0a 20 20 20 20 7d 0a 20 20 20 20 61 73 73 65 72  .    }.    asser
20110 74 28 20 70 41 70 70 6c 79 2d 3e 62 44 65 66 65  t( pApply->bDefe
20120 72 43 6f 6e 73 74 72 61 69 6e 74 73 20 7c 7c 20  rConstraints || 
20130 70 41 70 70 6c 79 2d 3e 63 6f 6e 73 74 72 61 69  pApply->constrai
20140 6e 74 73 2e 6e 42 75 66 3d 3d 30 20 29 3b 0a 0a  nts.nBuf==0 );..
20150 20 20 20 20 73 71 6c 69 74 65 33 5f 66 72 65 65      sqlite3_free
20160 28 63 6f 6e 73 2e 61 42 75 66 29 3b 0a 20 20 20  (cons.aBuf);.   
20170 20 69 66 28 20 72 63 21 3d 53 51 4c 49 54 45 5f   if( rc!=SQLITE_
20180 4f 4b 20 29 20 62 72 65 61 6b 3b 0a 20 20 20 20  OK ) break;.    
20190 69 66 28 20 70 41 70 70 6c 79 2d 3e 63 6f 6e 73  if( pApply->cons
201a0 74 72 61 69 6e 74 73 2e 6e 42 75 66 3e 3d 63 6f  traints.nBuf>=co
201b0 6e 73 2e 6e 42 75 66 20 29 7b 0a 20 20 20 20 20  ns.nBuf ){.     
201c0 20 2f 2a 20 4e 6f 20 70 72 6f 67 72 65 73 73 20   /* No progress 
201d0 77 61 73 20 6d 61 64 65 20 6f 6e 20 74 68 65 20  was made on the 
201e0 6c 61 73 74 20 72 6f 75 6e 64 2e 20 2a 2f 0a 20  last round. */. 
201f0 20 20 20 20 20 70 41 70 70 6c 79 2d 3e 62 44 65       pApply->bDe
20200 66 65 72 43 6f 6e 73 74 72 61 69 6e 74 73 20 3d  ferConstraints =
20210 20 30 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a 0a 20   0;.    }.  }.. 
20220 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f   return rc;.}../
20230 2a 0a 2a 2a 20 41 72 67 75 6d 65 6e 74 20 70 49  *.** Argument pI
20240 74 65 72 20 69 73 20 61 20 63 68 61 6e 67 65 73  ter is a changes
20250 65 74 20 69 74 65 72 61 74 6f 72 20 74 68 61 74  et iterator that
20260 20 68 61 73 20 62 65 65 6e 20 69 6e 69 74 69 61   has been initia
20270 6c 69 7a 65 64 2c 20 62 75 74 0a 2a 2a 20 6e 6f  lized, but.** no
20280 74 20 79 65 74 20 70 61 73 73 65 64 20 74 6f 20  t yet passed to 
20290 73 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74  sqlite3changeset
202a0 5f 6e 65 78 74 28 29 2e 20 54 68 69 73 20 66 75  _next(). This fu
202b0 6e 63 74 69 6f 6e 20 61 70 70 6c 69 65 73 20 74  nction applies t
202c0 68 65 20 0a 2a 2a 20 63 68 61 6e 67 65 73 65 74  he .** changeset
202d0 20 74 6f 20 74 68 65 20 6d 61 69 6e 20 64 61 74   to the main dat
202e0 61 62 61 73 65 20 61 74 74 61 63 68 65 64 20 74  abase attached t
202f0 6f 20 68 61 6e 64 6c 65 20 22 64 62 22 2e 20 54  o handle "db". T
20300 68 65 20 73 75 70 70 6c 69 65 64 0a 2a 2a 20 63  he supplied.** c
20310 6f 6e 66 6c 69 63 74 20 68 61 6e 64 6c 65 72 20  onflict handler 
20320 63 61 6c 6c 62 61 63 6b 20 69 73 20 69 6e 76 6f  callback is invo
20330 6b 65 64 20 74 6f 20 72 65 73 6f 6c 76 65 20 61  ked to resolve a
20340 6e 79 20 63 6f 6e 66 6c 69 63 74 73 20 65 6e 63  ny conflicts enc
20350 6f 75 6e 74 65 72 65 64 0a 2a 2a 20 77 68 69 6c  ountered.** whil
20360 65 20 61 70 70 6c 79 69 6e 67 20 74 68 65 20 63  e applying the c
20370 68 61 6e 67 65 2e 0a 2a 2f 0a 73 74 61 74 69 63  hange..*/.static
20380 20 69 6e 74 20 73 65 73 73 69 6f 6e 43 68 61 6e   int sessionChan
20390 67 65 73 65 74 41 70 70 6c 79 28 0a 20 20 73 71  gesetApply(.  sq
203a0 6c 69 74 65 33 20 2a 64 62 2c 20 20 20 20 20 20  lite3 *db,      
203b0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
203c0 20 41 70 70 6c 79 20 63 68 61 6e 67 65 20 74 6f   Apply change to
203d0 20 22 6d 61 69 6e 22 20 64 62 20 6f 66 20 74 68   "main" db of th
203e0 69 73 20 68 61 6e 64 6c 65 20 2a 2f 0a 20 20 73  is handle */.  s
203f0 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 73 65 74  qlite3_changeset
20400 5f 69 74 65 72 20 2a 70 49 74 65 72 2c 20 20 2f  _iter *pIter,  /
20410 2a 20 43 68 61 6e 67 65 73 65 74 20 74 6f 20 61  * Changeset to a
20420 70 70 6c 79 20 2a 2f 0a 20 20 69 6e 74 28 2a 78  pply */.  int(*x
20430 46 69 6c 74 65 72 29 28 0a 20 20 20 20 76 6f 69  Filter)(.    voi
20440 64 20 2a 70 43 74 78 2c 20 20 20 20 20 20 20 20  d *pCtx,        
20450 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 43 6f             /* Co
20460 70 79 20 6f 66 20 73 69 78 74 68 20 61 72 67 20  py of sixth arg 
20470 74 6f 20 5f 61 70 70 6c 79 28 29 20 2a 2f 0a 20  to _apply() */. 
20480 20 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a     const char *z
20490 54 61 62 20 20 20 20 20 20 20 20 20 20 20 20 20  Tab             
204a0 20 2f 2a 20 54 61 62 6c 65 20 6e 61 6d 65 20 2a   /* Table name *
204b0 2f 0a 20 20 29 2c 0a 20 20 69 6e 74 28 2a 78 43  /.  ),.  int(*xC
204c0 6f 6e 66 6c 69 63 74 29 28 0a 20 20 20 20 76 6f  onflict)(.    vo
204d0 69 64 20 2a 70 43 74 78 2c 20 20 20 20 20 20 20  id *pCtx,       
204e0 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 43              /* C
204f0 6f 70 79 20 6f 66 20 66 69 66 74 68 20 61 72 67  opy of fifth arg
20500 20 74 6f 20 5f 61 70 70 6c 79 28 29 20 2a 2f 0a   to _apply() */.
20510 20 20 20 20 69 6e 74 20 65 43 6f 6e 66 6c 69 63      int eConflic
20520 74 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20  t,              
20530 20 20 2f 2a 20 44 41 54 41 2c 20 4d 49 53 53 49    /* DATA, MISSI
20540 4e 47 2c 20 43 4f 4e 46 4c 49 43 54 2c 20 43 4f  NG, CONFLICT, CO
20550 4e 53 54 52 41 49 4e 54 20 2a 2f 0a 20 20 20 20  NSTRAINT */.    
20560 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 73 65  sqlite3_changese
20570 74 5f 69 74 65 72 20 2a 70 20 20 20 20 20 2f 2a  t_iter *p     /*
20580 20 48 61 6e 64 6c 65 20 64 65 73 63 72 69 62 69   Handle describi
20590 6e 67 20 63 68 61 6e 67 65 20 61 6e 64 20 63 6f  ng change and co
205a0 6e 66 6c 69 63 74 20 2a 2f 0a 20 20 29 2c 0a 20  nflict */.  ),. 
205b0 20 76 6f 69 64 20 2a 70 43 74 78 20 20 20 20 20   void *pCtx     
205c0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
205d0 20 2f 2a 20 46 69 72 73 74 20 61 72 67 75 6d 65   /* First argume
205e0 6e 74 20 70 61 73 73 65 64 20 74 6f 20 78 43 6f  nt passed to xCo
205f0 6e 66 6c 69 63 74 20 2a 2f 0a 29 7b 0a 20 20 69  nflict */.){.  i
20600 6e 74 20 73 63 68 65 6d 61 4d 69 73 6d 61 74 63  nt schemaMismatc
20610 68 20 3d 20 30 3b 0a 20 20 69 6e 74 20 72 63 3b  h = 0;.  int rc;
20620 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
20630 20 20 20 20 20 20 20 20 20 2f 2a 20 52 65 74 75           /* Retu
20640 72 6e 20 63 6f 64 65 20 2a 2f 0a 20 20 63 6f 6e  rn code */.  con
20650 73 74 20 63 68 61 72 20 2a 7a 54 61 62 20 3d 20  st char *zTab = 
20660 30 3b 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20  0;           /* 
20670 4e 61 6d 65 20 6f 66 20 63 75 72 72 65 6e 74 20  Name of current 
20680 74 61 62 6c 65 20 2a 2f 0a 20 20 69 6e 74 20 6e  table */.  int n
20690 54 61 62 20 3d 20 30 3b 20 20 20 20 20 20 20 20  Tab = 0;        
206a0 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 52 65             /* Re
206b0 73 75 6c 74 20 6f 66 20 73 71 6c 69 74 65 33 53  sult of sqlite3S
206c0 74 72 6c 65 6e 33 30 28 7a 54 61 62 29 20 2a 2f  trlen30(zTab) */
206d0 0a 20 20 53 65 73 73 69 6f 6e 41 70 70 6c 79 43  .  SessionApplyC
206e0 74 78 20 73 41 70 70 6c 79 3b 20 20 20 20 20 20  tx sApply;      
206f0 20 20 20 2f 2a 20 63 68 61 6e 67 65 73 65 74 5f     /* changeset_
20700 61 70 70 6c 79 28 29 20 63 6f 6e 74 65 78 74 20  apply() context 
20710 6f 62 6a 65 63 74 20 2a 2f 0a 20 20 69 6e 74 20  object */.  int 
20720 62 50 61 74 63 68 73 65 74 3b 0a 0a 20 20 61 73  bPatchset;..  as
20730 73 65 72 74 28 20 78 43 6f 6e 66 6c 69 63 74 21  sert( xConflict!
20740 3d 30 20 29 3b 0a 0a 20 20 70 49 74 65 72 2d 3e  =0 );..  pIter->
20750 69 6e 2e 62 4e 6f 44 69 73 63 61 72 64 20 3d 20  in.bNoDiscard = 
20760 31 3b 0a 20 20 6d 65 6d 73 65 74 28 26 73 41 70  1;.  memset(&sAp
20770 70 6c 79 2c 20 30 2c 20 73 69 7a 65 6f 66 28 73  ply, 0, sizeof(s
20780 41 70 70 6c 79 29 29 3b 0a 20 20 73 71 6c 69 74  Apply));.  sqlit
20790 65 33 5f 6d 75 74 65 78 5f 65 6e 74 65 72 28 73  e3_mutex_enter(s
207a0 71 6c 69 74 65 33 5f 64 62 5f 6d 75 74 65 78 28  qlite3_db_mutex(
207b0 64 62 29 29 3b 0a 20 20 72 63 20 3d 20 73 71 6c  db));.  rc = sql
207c0 69 74 65 33 5f 65 78 65 63 28 64 62 2c 20 22 53  ite3_exec(db, "S
207d0 41 56 45 50 4f 49 4e 54 20 63 68 61 6e 67 65 73  AVEPOINT changes
207e0 65 74 5f 61 70 70 6c 79 22 2c 20 30 2c 20 30 2c  et_apply", 0, 0,
207f0 20 30 29 3b 0a 20 20 69 66 28 20 72 63 3d 3d 53   0);.  if( rc==S
20800 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20  QLITE_OK ){.    
20810 72 63 20 3d 20 73 71 6c 69 74 65 33 5f 65 78 65  rc = sqlite3_exe
20820 63 28 64 62 2c 20 22 50 52 41 47 4d 41 20 64 65  c(db, "PRAGMA de
20830 66 65 72 5f 66 6f 72 65 69 67 6e 5f 6b 65 79 73  fer_foreign_keys
20840 20 3d 20 31 22 2c 20 30 2c 20 30 2c 20 30 29 3b   = 1", 0, 0, 0);
20850 0a 20 20 7d 0a 20 20 77 68 69 6c 65 28 20 72 63  .  }.  while( rc
20860 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 26 26 20 53  ==SQLITE_OK && S
20870 51 4c 49 54 45 5f 52 4f 57 3d 3d 73 71 6c 69 74  QLITE_ROW==sqlit
20880 65 33 63 68 61 6e 67 65 73 65 74 5f 6e 65 78 74  e3changeset_next
20890 28 70 49 74 65 72 29 20 29 7b 0a 20 20 20 20 69  (pIter) ){.    i
208a0 6e 74 20 6e 43 6f 6c 3b 0a 20 20 20 20 69 6e 74  nt nCol;.    int
208b0 20 6f 70 3b 0a 20 20 20 20 63 6f 6e 73 74 20 63   op;.    const c
208c0 68 61 72 20 2a 7a 4e 65 77 3b 0a 20 20 20 20 0a  har *zNew;.    .
208d0 20 20 20 20 73 71 6c 69 74 65 33 63 68 61 6e 67      sqlite3chang
208e0 65 73 65 74 5f 6f 70 28 70 49 74 65 72 2c 20 26  eset_op(pIter, &
208f0 7a 4e 65 77 2c 20 26 6e 43 6f 6c 2c 20 26 6f 70  zNew, &nCol, &op
20900 2c 20 30 29 3b 0a 0a 20 20 20 20 69 66 28 20 7a  , 0);..    if( z
20910 54 61 62 3d 3d 30 20 7c 7c 20 73 71 6c 69 74 65  Tab==0 || sqlite
20920 33 5f 73 74 72 6e 69 63 6d 70 28 7a 4e 65 77 2c  3_strnicmp(zNew,
20930 20 7a 54 61 62 2c 20 6e 54 61 62 2b 31 29 20 29   zTab, nTab+1) )
20940 7b 0a 20 20 20 20 20 20 75 38 20 2a 61 62 50 4b  {.      u8 *abPK
20950 3b 0a 0a 20 20 20 20 20 20 72 63 20 3d 20 73 65  ;..      rc = se
20960 73 73 69 6f 6e 52 65 74 72 79 43 6f 6e 73 74 72  ssionRetryConstr
20970 61 69 6e 74 73 28 0a 20 20 20 20 20 20 20 20 20  aints(.         
20980 20 64 62 2c 20 70 49 74 65 72 2d 3e 62 50 61 74   db, pIter->bPat
20990 63 68 73 65 74 2c 20 7a 54 61 62 2c 20 26 73 41  chset, zTab, &sA
209a0 70 70 6c 79 2c 20 78 43 6f 6e 66 6c 69 63 74 2c  pply, xConflict,
209b0 20 70 43 74 78 0a 20 20 20 20 20 20 29 3b 0a 20   pCtx.      );. 
209c0 20 20 20 20 20 69 66 28 20 72 63 21 3d 53 51 4c       if( rc!=SQL
209d0 49 54 45 5f 4f 4b 20 29 20 62 72 65 61 6b 3b 0a  ITE_OK ) break;.
209e0 0a 20 20 20 20 20 20 73 71 6c 69 74 65 33 5f 66  .      sqlite3_f
209f0 72 65 65 28 28 63 68 61 72 2a 29 73 41 70 70 6c  ree((char*)sAppl
20a00 79 2e 61 7a 43 6f 6c 29 3b 20 20 2f 2a 20 63 61  y.azCol);  /* ca
20a10 73 74 20 77 6f 72 6b 73 20 61 72 6f 75 6e 64 20  st works around 
20a20 56 43 2b 2b 20 62 75 67 20 2a 2f 0a 20 20 20 20  VC++ bug */.    
20a30 20 20 73 71 6c 69 74 65 33 5f 66 69 6e 61 6c 69    sqlite3_finali
20a40 7a 65 28 73 41 70 70 6c 79 2e 70 44 65 6c 65 74  ze(sApply.pDelet
20a50 65 29 3b 0a 20 20 20 20 20 20 73 71 6c 69 74 65  e);.      sqlite
20a60 33 5f 66 69 6e 61 6c 69 7a 65 28 73 41 70 70 6c  3_finalize(sAppl
20a70 79 2e 70 55 70 64 61 74 65 29 3b 20 0a 20 20 20  y.pUpdate); .   
20a80 20 20 20 73 71 6c 69 74 65 33 5f 66 69 6e 61 6c     sqlite3_final
20a90 69 7a 65 28 73 41 70 70 6c 79 2e 70 49 6e 73 65  ize(sApply.pInse
20aa0 72 74 29 3b 0a 20 20 20 20 20 20 73 71 6c 69 74  rt);.      sqlit
20ab0 65 33 5f 66 69 6e 61 6c 69 7a 65 28 73 41 70 70  e3_finalize(sApp
20ac0 6c 79 2e 70 53 65 6c 65 63 74 29 3b 0a 20 20 20  ly.pSelect);.   
20ad0 20 20 20 6d 65 6d 73 65 74 28 26 73 41 70 70 6c     memset(&sAppl
20ae0 79 2c 20 30 2c 20 73 69 7a 65 6f 66 28 73 41 70  y, 0, sizeof(sAp
20af0 70 6c 79 29 29 3b 0a 20 20 20 20 20 20 73 41 70  ply));.      sAp
20b00 70 6c 79 2e 64 62 20 3d 20 64 62 3b 0a 20 20 20  ply.db = db;.   
20b10 20 20 20 73 41 70 70 6c 79 2e 62 44 65 66 65 72     sApply.bDefer
20b20 43 6f 6e 73 74 72 61 69 6e 74 73 20 3d 20 31 3b  Constraints = 1;
20b30 0a 0a 20 20 20 20 20 20 2f 2a 20 49 66 20 61 6e  ..      /* If an
20b40 20 78 46 69 6c 74 65 72 28 29 20 63 61 6c 6c 62   xFilter() callb
20b50 61 63 6b 20 77 61 73 20 73 70 65 63 69 66 69 65  ack was specifie
20b60 64 2c 20 69 6e 76 6f 6b 65 20 69 74 20 6e 6f 77  d, invoke it now
20b70 2e 20 49 66 20 74 68 65 20 0a 20 20 20 20 20 20  . If the .      
20b80 2a 2a 20 78 46 69 6c 74 65 72 20 63 61 6c 6c 62  ** xFilter callb
20b90 61 63 6b 20 72 65 74 75 72 6e 73 20 7a 65 72 6f  ack returns zero
20ba0 2c 20 73 6b 69 70 20 74 68 69 73 20 74 61 62 6c  , skip this tabl
20bb0 65 2e 20 49 66 20 69 74 20 72 65 74 75 72 6e 73  e. If it returns
20bc0 0a 20 20 20 20 20 20 2a 2a 20 6e 6f 6e 2d 7a 65  .      ** non-ze
20bd0 72 6f 2c 20 70 72 6f 63 65 65 64 2e 20 2a 2f 0a  ro, proceed. */.
20be0 20 20 20 20 20 20 73 63 68 65 6d 61 4d 69 73 6d        schemaMism
20bf0 61 74 63 68 20 3d 20 28 78 46 69 6c 74 65 72 20  atch = (xFilter 
20c00 26 26 20 28 30 3d 3d 78 46 69 6c 74 65 72 28 70  && (0==xFilter(p
20c10 43 74 78 2c 20 7a 4e 65 77 29 29 29 3b 0a 20 20  Ctx, zNew)));.  
20c20 20 20 20 20 69 66 28 20 73 63 68 65 6d 61 4d 69      if( schemaMi
20c30 73 6d 61 74 63 68 20 29 7b 0a 20 20 20 20 20 20  smatch ){.      
20c40 20 20 7a 54 61 62 20 3d 20 73 71 6c 69 74 65 33    zTab = sqlite3
20c50 5f 6d 70 72 69 6e 74 66 28 22 25 73 22 2c 20 7a  _mprintf("%s", z
20c60 4e 65 77 29 3b 0a 20 20 20 20 20 20 20 20 69 66  New);.        if
20c70 28 20 7a 54 61 62 3d 3d 30 20 29 7b 0a 20 20 20  ( zTab==0 ){.   
20c80 20 20 20 20 20 20 20 72 63 20 3d 20 53 51 4c 49         rc = SQLI
20c90 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 20 20 20 20  TE_NOMEM;.      
20ca0 20 20 20 20 62 72 65 61 6b 3b 0a 20 20 20 20 20      break;.     
20cb0 20 20 20 7d 0a 20 20 20 20 20 20 20 20 6e 54 61     }.        nTa
20cc0 62 20 3d 20 28 69 6e 74 29 73 74 72 6c 65 6e 28  b = (int)strlen(
20cd0 7a 54 61 62 29 3b 0a 20 20 20 20 20 20 20 20 73  zTab);.        s
20ce0 41 70 70 6c 79 2e 61 7a 43 6f 6c 20 3d 20 28 63  Apply.azCol = (c
20cf0 6f 6e 73 74 20 63 68 61 72 20 2a 2a 29 7a 54 61  onst char **)zTa
20d00 62 3b 0a 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a  b;.      }else{.
20d10 20 20 20 20 20 20 20 20 69 6e 74 20 6e 4d 69 6e          int nMin
20d20 43 6f 6c 20 3d 20 30 3b 0a 20 20 20 20 20 20 20  Col = 0;.       
20d30 20 69 6e 74 20 69 3b 0a 0a 20 20 20 20 20 20 20   int i;..       
20d40 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65   sqlite3changese
20d50 74 5f 70 6b 28 70 49 74 65 72 2c 20 26 61 62 50  t_pk(pIter, &abP
20d60 4b 2c 20 30 29 3b 0a 20 20 20 20 20 20 20 20 72  K, 0);.        r
20d70 63 20 3d 20 73 65 73 73 69 6f 6e 54 61 62 6c 65  c = sessionTable
20d80 49 6e 66 6f 28 0a 20 20 20 20 20 20 20 20 20 20  Info(.          
20d90 20 20 64 62 2c 20 22 6d 61 69 6e 22 2c 20 7a 4e    db, "main", zN
20da0 65 77 2c 20 26 73 41 70 70 6c 79 2e 6e 43 6f 6c  ew, &sApply.nCol
20db0 2c 20 26 7a 54 61 62 2c 20 26 73 41 70 70 6c 79  , &zTab, &sApply
20dc0 2e 61 7a 43 6f 6c 2c 20 26 73 41 70 70 6c 79 2e  .azCol, &sApply.
20dd0 61 62 50 4b 0a 20 20 20 20 20 20 20 20 29 3b 0a  abPK.        );.
20de0 20 20 20 20 20 20 20 20 69 66 28 20 72 63 21 3d          if( rc!=
20df0 53 51 4c 49 54 45 5f 4f 4b 20 29 20 62 72 65 61  SQLITE_OK ) brea
20e00 6b 3b 0a 20 20 20 20 20 20 20 20 66 6f 72 28 69  k;.        for(i
20e10 3d 30 3b 20 69 3c 73 41 70 70 6c 79 2e 6e 43 6f  =0; i<sApply.nCo
20e20 6c 3b 20 69 2b 2b 29 7b 0a 20 20 20 20 20 20 20  l; i++){.       
20e30 20 20 20 69 66 28 20 73 41 70 70 6c 79 2e 61 62     if( sApply.ab
20e40 50 4b 5b 69 5d 20 29 20 6e 4d 69 6e 43 6f 6c 20  PK[i] ) nMinCol 
20e50 3d 20 69 2b 31 3b 0a 20 20 20 20 20 20 20 20 7d  = i+1;.        }
20e60 0a 20 20 0a 20 20 20 20 20 20 20 20 69 66 28 20  .  .        if( 
20e70 73 41 70 70 6c 79 2e 6e 43 6f 6c 3d 3d 30 20 29  sApply.nCol==0 )
20e80 7b 0a 20 20 20 20 20 20 20 20 20 20 73 63 68 65  {.          sche
20e90 6d 61 4d 69 73 6d 61 74 63 68 20 3d 20 31 3b 0a  maMismatch = 1;.
20ea0 20 20 20 20 20 20 20 20 20 20 73 71 6c 69 74 65            sqlite
20eb0 33 5f 6c 6f 67 28 53 51 4c 49 54 45 5f 53 43 48  3_log(SQLITE_SCH
20ec0 45 4d 41 2c 20 0a 20 20 20 20 20 20 20 20 20 20  EMA, .          
20ed0 20 20 20 20 22 73 71 6c 69 74 65 33 63 68 61 6e      "sqlite3chan
20ee0 67 65 73 65 74 5f 61 70 70 6c 79 28 29 3a 20 6e  geset_apply(): n
20ef0 6f 20 73 75 63 68 20 74 61 62 6c 65 3a 20 25 73  o such table: %s
20f00 22 2c 20 7a 54 61 62 0a 20 20 20 20 20 20 20 20  ", zTab.        
20f10 20 20 29 3b 0a 20 20 20 20 20 20 20 20 7d 0a 20    );.        }. 
20f20 20 20 20 20 20 20 20 65 6c 73 65 20 69 66 28 20         else if( 
20f30 73 41 70 70 6c 79 2e 6e 43 6f 6c 3c 6e 43 6f 6c  sApply.nCol<nCol
20f40 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 73 63   ){.          sc
20f50 68 65 6d 61 4d 69 73 6d 61 74 63 68 20 3d 20 31  hemaMismatch = 1
20f60 3b 0a 20 20 20 20 20 20 20 20 20 20 73 71 6c 69  ;.          sqli
20f70 74 65 33 5f 6c 6f 67 28 53 51 4c 49 54 45 5f 53  te3_log(SQLITE_S
20f80 43 48 45 4d 41 2c 20 0a 20 20 20 20 20 20 20 20  CHEMA, .        
20f90 20 20 20 20 20 20 22 73 71 6c 69 74 65 33 63 68        "sqlite3ch
20fa0 61 6e 67 65 73 65 74 5f 61 70 70 6c 79 28 29 3a  angeset_apply():
20fb0 20 74 61 62 6c 65 20 25 73 20 68 61 73 20 25 64   table %s has %d
20fc0 20 63 6f 6c 75 6d 6e 73 2c 20 22 0a 20 20 20 20   columns, ".    
20fd0 20 20 20 20 20 20 20 20 20 20 22 65 78 70 65 63            "expec
20fe0 74 65 64 20 25 64 20 6f 72 20 6d 6f 72 65 22 2c  ted %d or more",
20ff0 20 0a 20 20 20 20 20 20 20 20 20 20 20 20 20 20   .              
21000 7a 54 61 62 2c 20 73 41 70 70 6c 79 2e 6e 43 6f  zTab, sApply.nCo
21010 6c 2c 20 6e 43 6f 6c 0a 20 20 20 20 20 20 20 20  l, nCol.        
21020 20 20 29 3b 0a 20 20 20 20 20 20 20 20 7d 0a 20    );.        }. 
21030 20 20 20 20 20 20 20 65 6c 73 65 20 69 66 28 20         else if( 
21040 6e 43 6f 6c 3c 6e 4d 69 6e 43 6f 6c 20 7c 7c 20  nCol<nMinCol || 
21050 6d 65 6d 63 6d 70 28 73 41 70 70 6c 79 2e 61 62  memcmp(sApply.ab
21060 50 4b 2c 20 61 62 50 4b 2c 20 6e 43 6f 6c 29 21  PK, abPK, nCol)!
21070 3d 30 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20  =0 ){.          
21080 73 63 68 65 6d 61 4d 69 73 6d 61 74 63 68 20 3d  schemaMismatch =
21090 20 31 3b 0a 20 20 20 20 20 20 20 20 20 20 73 71   1;.          sq
210a0 6c 69 74 65 33 5f 6c 6f 67 28 53 51 4c 49 54 45  lite3_log(SQLITE
210b0 5f 53 43 48 45 4d 41 2c 20 22 73 71 6c 69 74 65  _SCHEMA, "sqlite
210c0 33 63 68 61 6e 67 65 73 65 74 5f 61 70 70 6c 79  3changeset_apply
210d0 28 29 3a 20 22 0a 20 20 20 20 20 20 20 20 20 20  (): ".          
210e0 20 20 20 20 22 70 72 69 6d 61 72 79 20 6b 65 79      "primary key
210f0 20 6d 69 73 6d 61 74 63 68 20 66 6f 72 20 74 61   mismatch for ta
21100 62 6c 65 20 25 73 22 2c 20 7a 54 61 62 0a 20 20  ble %s", zTab.  
21110 20 20 20 20 20 20 20 20 29 3b 0a 20 20 20 20 20          );.     
21120 20 20 20 7d 0a 20 20 20 20 20 20 20 20 65 6c 73     }.        els
21130 65 7b 0a 20 20 20 20 20 20 20 20 20 20 73 41 70  e{.          sAp
21140 70 6c 79 2e 6e 43 6f 6c 20 3d 20 6e 43 6f 6c 3b  ply.nCol = nCol;
21150 0a 20 20 20 20 20 20 20 20 20 20 69 66 28 28 72  .          if((r
21160 63 20 3d 20 73 65 73 73 69 6f 6e 53 65 6c 65 63  c = sessionSelec
21170 74 52 6f 77 28 64 62 2c 20 7a 54 61 62 2c 20 26  tRow(db, zTab, &
21180 73 41 70 70 6c 79 29 29 0a 20 20 20 20 20 20 20  sApply)).       
21190 20 20 20 7c 7c 20 28 72 63 20 3d 20 73 65 73 73     || (rc = sess
211a0 69 6f 6e 55 70 64 61 74 65 52 6f 77 28 64 62 2c  ionUpdateRow(db,
211b0 20 7a 54 61 62 2c 20 26 73 41 70 70 6c 79 29 29   zTab, &sApply))
211c0 0a 20 20 20 20 20 20 20 20 20 20 7c 7c 20 28 72  .          || (r
211d0 63 20 3d 20 73 65 73 73 69 6f 6e 44 65 6c 65 74  c = sessionDelet
211e0 65 52 6f 77 28 64 62 2c 20 7a 54 61 62 2c 20 26  eRow(db, zTab, &
211f0 73 41 70 70 6c 79 29 29 0a 20 20 20 20 20 20 20  sApply)).       
21200 20 20 20 7c 7c 20 28 72 63 20 3d 20 73 65 73 73     || (rc = sess
21210 69 6f 6e 49 6e 73 65 72 74 52 6f 77 28 64 62 2c  ionInsertRow(db,
21220 20 7a 54 61 62 2c 20 26 73 41 70 70 6c 79 29 29   zTab, &sApply))
21230 0a 20 20 20 20 20 20 20 20 20 20 29 7b 0a 20 20  .          ){.  
21240 20 20 20 20 20 20 20 20 20 20 62 72 65 61 6b 3b            break;
21250 0a 20 20 20 20 20 20 20 20 20 20 7d 0a 20 20 20  .          }.   
21260 20 20 20 20 20 7d 0a 20 20 20 20 20 20 20 20 6e       }.        n
21270 54 61 62 20 3d 20 73 71 6c 69 74 65 33 53 74 72  Tab = sqlite3Str
21280 6c 65 6e 33 30 28 7a 54 61 62 29 3b 0a 20 20 20  len30(zTab);.   
21290 20 20 20 7d 0a 20 20 20 20 7d 0a 0a 20 20 20 20     }.    }..    
212a0 2f 2a 20 49 66 20 74 68 65 72 65 20 69 73 20 61  /* If there is a
212b0 20 73 63 68 65 6d 61 20 6d 69 73 6d 61 74 63 68   schema mismatch
212c0 20 6f 6e 20 74 68 65 20 63 75 72 72 65 6e 74 20   on the current 
212d0 74 61 62 6c 65 2c 20 70 72 6f 63 65 65 64 20 74  table, proceed t
212e0 6f 20 74 68 65 0a 20 20 20 20 2a 2a 20 6e 65 78  o the.    ** nex
212f0 74 20 63 68 61 6e 67 65 2e 20 41 20 6c 6f 67 20  t change. A log 
21300 6d 65 73 73 61 67 65 20 68 61 73 20 61 6c 72 65  message has alre
21310 61 64 79 20 62 65 65 6e 20 69 73 73 75 65 64 2e  ady been issued.
21320 20 2a 2f 0a 20 20 20 20 69 66 28 20 73 63 68 65   */.    if( sche
21330 6d 61 4d 69 73 6d 61 74 63 68 20 29 20 63 6f 6e  maMismatch ) con
21340 74 69 6e 75 65 3b 0a 0a 20 20 20 20 72 63 20 3d  tinue;..    rc =
21350 20 73 65 73 73 69 6f 6e 41 70 70 6c 79 4f 6e 65   sessionApplyOne
21360 57 69 74 68 52 65 74 72 79 28 64 62 2c 20 70 49  WithRetry(db, pI
21370 74 65 72 2c 20 26 73 41 70 70 6c 79 2c 20 78 43  ter, &sApply, xC
21380 6f 6e 66 6c 69 63 74 2c 20 70 43 74 78 29 3b 0a  onflict, pCtx);.
21390 20 20 7d 0a 0a 20 20 62 50 61 74 63 68 73 65 74    }..  bPatchset
213a0 20 3d 20 70 49 74 65 72 2d 3e 62 50 61 74 63 68   = pIter->bPatch
213b0 73 65 74 3b 0a 20 20 69 66 28 20 72 63 3d 3d 53  set;.  if( rc==S
213c0 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20  QLITE_OK ){.    
213d0 72 63 20 3d 20 73 71 6c 69 74 65 33 63 68 61 6e  rc = sqlite3chan
213e0 67 65 73 65 74 5f 66 69 6e 61 6c 69 7a 65 28 70  geset_finalize(p
213f0 49 74 65 72 29 3b 0a 20 20 7d 65 6c 73 65 7b 0a  Iter);.  }else{.
21400 20 20 20 20 73 71 6c 69 74 65 33 63 68 61 6e 67      sqlite3chang
21410 65 73 65 74 5f 66 69 6e 61 6c 69 7a 65 28 70 49  eset_finalize(pI
21420 74 65 72 29 3b 0a 20 20 7d 0a 0a 20 20 69 66 28  ter);.  }..  if(
21430 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29   rc==SQLITE_OK )
21440 7b 0a 20 20 20 20 72 63 20 3d 20 73 65 73 73 69  {.    rc = sessi
21450 6f 6e 52 65 74 72 79 43 6f 6e 73 74 72 61 69 6e  onRetryConstrain
21460 74 73 28 64 62 2c 20 62 50 61 74 63 68 73 65 74  ts(db, bPatchset
21470 2c 20 7a 54 61 62 2c 20 26 73 41 70 70 6c 79 2c  , zTab, &sApply,
21480 20 78 43 6f 6e 66 6c 69 63 74 2c 20 70 43 74 78   xConflict, pCtx
21490 29 3b 0a 20 20 7d 0a 0a 20 20 69 66 28 20 72 63  );.  }..  if( rc
214a0 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20  ==SQLITE_OK ){. 
214b0 20 20 20 69 6e 74 20 6e 46 6b 2c 20 6e 6f 74 55     int nFk, notU
214c0 73 65 64 3b 0a 20 20 20 20 73 71 6c 69 74 65 33  sed;.    sqlite3
214d0 5f 64 62 5f 73 74 61 74 75 73 28 64 62 2c 20 53  _db_status(db, S
214e0 51 4c 49 54 45 5f 44 42 53 54 41 54 55 53 5f 44  QLITE_DBSTATUS_D
214f0 45 46 45 52 52 45 44 5f 46 4b 53 2c 20 26 6e 46  EFERRED_FKS, &nF
21500 6b 2c 20 26 6e 6f 74 55 73 65 64 2c 20 30 29 3b  k, &notUsed, 0);
21510 0a 20 20 20 20 69 66 28 20 6e 46 6b 21 3d 30 20  .    if( nFk!=0 
21520 29 7b 0a 20 20 20 20 20 20 69 6e 74 20 72 65 73  ){.      int res
21530 20 3d 20 53 51 4c 49 54 45 5f 43 48 41 4e 47 45   = SQLITE_CHANGE
21540 53 45 54 5f 41 42 4f 52 54 3b 0a 20 20 20 20 20  SET_ABORT;.     
21550 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 73   sqlite3_changes
21560 65 74 5f 69 74 65 72 20 73 49 74 65 72 3b 0a 20  et_iter sIter;. 
21570 20 20 20 20 20 6d 65 6d 73 65 74 28 26 73 49 74       memset(&sIt
21580 65 72 2c 20 30 2c 20 73 69 7a 65 6f 66 28 73 49  er, 0, sizeof(sI
21590 74 65 72 29 29 3b 0a 20 20 20 20 20 20 73 49 74  ter));.      sIt
215a0 65 72 2e 6e 43 6f 6c 20 3d 20 6e 46 6b 3b 0a 20  er.nCol = nFk;. 
215b0 20 20 20 20 20 72 65 73 20 3d 20 78 43 6f 6e 66       res = xConf
215c0 6c 69 63 74 28 70 43 74 78 2c 20 53 51 4c 49 54  lict(pCtx, SQLIT
215d0 45 5f 43 48 41 4e 47 45 53 45 54 5f 46 4f 52 45  E_CHANGESET_FORE
215e0 49 47 4e 5f 4b 45 59 2c 20 26 73 49 74 65 72 29  IGN_KEY, &sIter)
215f0 3b 0a 20 20 20 20 20 20 69 66 28 20 72 65 73 21  ;.      if( res!
21600 3d 53 51 4c 49 54 45 5f 43 48 41 4e 47 45 53 45  =SQLITE_CHANGESE
21610 54 5f 4f 4d 49 54 20 29 7b 0a 20 20 20 20 20 20  T_OMIT ){.      
21620 20 20 72 63 20 3d 20 53 51 4c 49 54 45 5f 43 4f    rc = SQLITE_CO
21630 4e 53 54 52 41 49 4e 54 3b 0a 20 20 20 20 20 20  NSTRAINT;.      
21640 7d 0a 20 20 20 20 7d 0a 20 20 7d 0a 20 20 73 71  }.    }.  }.  sq
21650 6c 69 74 65 33 5f 65 78 65 63 28 64 62 2c 20 22  lite3_exec(db, "
21660 50 52 41 47 4d 41 20 64 65 66 65 72 5f 66 6f 72  PRAGMA defer_for
21670 65 69 67 6e 5f 6b 65 79 73 20 3d 20 30 22 2c 20  eign_keys = 0", 
21680 30 2c 20 30 2c 20 30 29 3b 0a 0a 20 20 69 66 28  0, 0, 0);..  if(
21690 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29   rc==SQLITE_OK )
216a0 7b 0a 20 20 20 20 72 63 20 3d 20 73 71 6c 69 74  {.    rc = sqlit
216b0 65 33 5f 65 78 65 63 28 64 62 2c 20 22 52 45 4c  e3_exec(db, "REL
216c0 45 41 53 45 20 63 68 61 6e 67 65 73 65 74 5f 61  EASE changeset_a
216d0 70 70 6c 79 22 2c 20 30 2c 20 30 2c 20 30 29 3b  pply", 0, 0, 0);
216e0 0a 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 73 71  .  }else{.    sq
216f0 6c 69 74 65 33 5f 65 78 65 63 28 64 62 2c 20 22  lite3_exec(db, "
21700 52 4f 4c 4c 42 41 43 4b 20 54 4f 20 63 68 61 6e  ROLLBACK TO chan
21710 67 65 73 65 74 5f 61 70 70 6c 79 22 2c 20 30 2c  geset_apply", 0,
21720 20 30 2c 20 30 29 3b 0a 20 20 20 20 73 71 6c 69   0, 0);.    sqli
21730 74 65 33 5f 65 78 65 63 28 64 62 2c 20 22 52 45  te3_exec(db, "RE
21740 4c 45 41 53 45 20 63 68 61 6e 67 65 73 65 74 5f  LEASE changeset_
21750 61 70 70 6c 79 22 2c 20 30 2c 20 30 2c 20 30 29  apply", 0, 0, 0)
21760 3b 0a 20 20 7d 0a 0a 20 20 73 71 6c 69 74 65 33  ;.  }..  sqlite3
21770 5f 66 69 6e 61 6c 69 7a 65 28 73 41 70 70 6c 79  _finalize(sApply
21780 2e 70 49 6e 73 65 72 74 29 3b 0a 20 20 73 71 6c  .pInsert);.  sql
21790 69 74 65 33 5f 66 69 6e 61 6c 69 7a 65 28 73 41  ite3_finalize(sA
217a0 70 70 6c 79 2e 70 44 65 6c 65 74 65 29 3b 0a 20  pply.pDelete);. 
217b0 20 73 71 6c 69 74 65 33 5f 66 69 6e 61 6c 69 7a   sqlite3_finaliz
217c0 65 28 73 41 70 70 6c 79 2e 70 55 70 64 61 74 65  e(sApply.pUpdate
217d0 29 3b 0a 20 20 73 71 6c 69 74 65 33 5f 66 69 6e  );.  sqlite3_fin
217e0 61 6c 69 7a 65 28 73 41 70 70 6c 79 2e 70 53 65  alize(sApply.pSe
217f0 6c 65 63 74 29 3b 0a 20 20 73 71 6c 69 74 65 33  lect);.  sqlite3
21800 5f 66 72 65 65 28 28 63 68 61 72 2a 29 73 41 70  _free((char*)sAp
21810 70 6c 79 2e 61 7a 43 6f 6c 29 3b 20 20 2f 2a 20  ply.azCol);  /* 
21820 63 61 73 74 20 77 6f 72 6b 73 20 61 72 6f 75 6e  cast works aroun
21830 64 20 56 43 2b 2b 20 62 75 67 20 2a 2f 0a 20 20  d VC++ bug */.  
21840 73 71 6c 69 74 65 33 5f 66 72 65 65 28 28 63 68  sqlite3_free((ch
21850 61 72 2a 29 73 41 70 70 6c 79 2e 63 6f 6e 73 74  ar*)sApply.const
21860 72 61 69 6e 74 73 2e 61 42 75 66 29 3b 0a 20 20  raints.aBuf);.  
21870 73 71 6c 69 74 65 33 5f 6d 75 74 65 78 5f 6c 65  sqlite3_mutex_le
21880 61 76 65 28 73 71 6c 69 74 65 33 5f 64 62 5f 6d  ave(sqlite3_db_m
21890 75 74 65 78 28 64 62 29 29 3b 0a 20 20 72 65 74  utex(db));.  ret
218a0 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a  urn rc;.}../*.**
218b0 20 41 70 70 6c 79 20 74 68 65 20 63 68 61 6e 67   Apply the chang
218c0 65 73 65 74 20 70 61 73 73 65 64 20 76 69 61 20  eset passed via 
218d0 70 43 68 61 6e 67 65 73 65 74 2f 6e 43 68 61 6e  pChangeset/nChan
218e0 67 65 73 65 74 20 74 6f 20 74 68 65 20 6d 61 69  geset to the mai
218f0 6e 20 64 61 74 61 62 61 73 65 0a 2a 2a 20 61 74  n database.** at
21900 74 61 63 68 65 64 20 74 6f 20 68 61 6e 64 6c 65  tached to handle
21910 20 22 64 62 22 2e 20 49 6e 76 6f 6b 65 20 74 68   "db". Invoke th
21920 65 20 73 75 70 70 6c 69 65 64 20 63 6f 6e 66 6c  e supplied confl
21930 69 63 74 20 68 61 6e 64 6c 65 72 20 63 61 6c 6c  ict handler call
21940 62 61 63 6b 0a 2a 2a 20 74 6f 20 72 65 73 6f 6c  back.** to resol
21950 76 65 20 61 6e 79 20 63 6f 6e 66 6c 69 63 74 73  ve any conflicts
21960 20 65 6e 63 6f 75 6e 74 65 72 65 64 20 77 68 69   encountered whi
21970 6c 65 20 61 70 70 6c 79 69 6e 67 20 74 68 65 20  le applying the 
21980 63 68 61 6e 67 65 2e 0a 2a 2f 0a 69 6e 74 20 73  change..*/.int s
21990 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74 5f  qlite3changeset_
219a0 61 70 70 6c 79 28 0a 20 20 73 71 6c 69 74 65 33  apply(.  sqlite3
219b0 20 2a 64 62 2c 20 20 20 20 20 20 20 20 20 20 20   *db,           
219c0 20 20 20 20 20 20 20 20 20 2f 2a 20 41 70 70 6c           /* Appl
219d0 79 20 63 68 61 6e 67 65 20 74 6f 20 22 6d 61 69  y change to "mai
219e0 6e 22 20 64 62 20 6f 66 20 74 68 69 73 20 68 61  n" db of this ha
219f0 6e 64 6c 65 20 2a 2f 0a 20 20 69 6e 74 20 6e 43  ndle */.  int nC
21a00 68 61 6e 67 65 73 65 74 2c 20 20 20 20 20 20 20  hangeset,       
21a10 20 20 20 20 20 20 20 20 20 20 2f 2a 20 53 69 7a            /* Siz
21a20 65 20 6f 66 20 63 68 61 6e 67 65 73 65 74 20 69  e of changeset i
21a30 6e 20 62 79 74 65 73 20 2a 2f 0a 20 20 76 6f 69  n bytes */.  voi
21a40 64 20 2a 70 43 68 61 6e 67 65 73 65 74 2c 20 20  d *pChangeset,  
21a50 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
21a60 43 68 61 6e 67 65 73 65 74 20 62 6c 6f 62 20 2a  Changeset blob *
21a70 2f 0a 20 20 69 6e 74 28 2a 78 46 69 6c 74 65 72  /.  int(*xFilter
21a80 29 28 0a 20 20 20 20 76 6f 69 64 20 2a 70 43 74  )(.    void *pCt
21a90 78 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20  x,              
21aa0 20 20 20 20 20 2f 2a 20 43 6f 70 79 20 6f 66 20       /* Copy of 
21ab0 73 69 78 74 68 20 61 72 67 20 74 6f 20 5f 61 70  sixth arg to _ap
21ac0 70 6c 79 28 29 20 2a 2f 0a 20 20 20 20 63 6f 6e  ply() */.    con
21ad0 73 74 20 63 68 61 72 20 2a 7a 54 61 62 20 20 20  st char *zTab   
21ae0 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 54 61             /* Ta
21af0 62 6c 65 20 6e 61 6d 65 20 2a 2f 0a 20 20 29 2c  ble name */.  ),
21b00 0a 20 20 69 6e 74 28 2a 78 43 6f 6e 66 6c 69 63  .  int(*xConflic
21b10 74 29 28 0a 20 20 20 20 76 6f 69 64 20 2a 70 43  t)(.    void *pC
21b20 74 78 2c 20 20 20 20 20 20 20 20 20 20 20 20 20  tx,             
21b30 20 20 20 20 20 20 2f 2a 20 43 6f 70 79 20 6f 66        /* Copy of
21b40 20 66 69 66 74 68 20 61 72 67 20 74 6f 20 5f 61   fifth arg to _a
21b50 70 70 6c 79 28 29 20 2a 2f 0a 20 20 20 20 69 6e  pply() */.    in
21b60 74 20 65 43 6f 6e 66 6c 69 63 74 2c 20 20 20 20  t eConflict,    
21b70 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 44              /* D
21b80 41 54 41 2c 20 4d 49 53 53 49 4e 47 2c 20 43 4f  ATA, MISSING, CO
21b90 4e 46 4c 49 43 54 2c 20 43 4f 4e 53 54 52 41 49  NFLICT, CONSTRAI
21ba0 4e 54 20 2a 2f 0a 20 20 20 20 73 71 6c 69 74 65  NT */.    sqlite
21bb0 33 5f 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72  3_changeset_iter
21bc0 20 2a 70 20 20 20 20 20 2f 2a 20 48 61 6e 64 6c   *p     /* Handl
21bd0 65 20 64 65 73 63 72 69 62 69 6e 67 20 63 68 61  e describing cha
21be0 6e 67 65 20 61 6e 64 20 63 6f 6e 66 6c 69 63 74  nge and conflict
21bf0 20 2a 2f 0a 20 20 29 2c 0a 20 20 76 6f 69 64 20   */.  ),.  void 
21c00 2a 70 43 74 78 20 20 20 20 20 20 20 20 20 20 20  *pCtx           
21c10 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 46 69             /* Fi
21c20 72 73 74 20 61 72 67 75 6d 65 6e 74 20 70 61 73  rst argument pas
21c30 73 65 64 20 74 6f 20 78 43 6f 6e 66 6c 69 63 74  sed to xConflict
21c40 20 2a 2f 0a 29 7b 0a 20 20 73 71 6c 69 74 65 33   */.){.  sqlite3
21c50 5f 63 68 61 6e 67 65 73 65 74 5f 69 74 65 72 20  _changeset_iter 
21c60 2a 70 49 74 65 72 3b 20 20 2f 2a 20 49 74 65 72  *pIter;  /* Iter
21c70 61 74 6f 72 20 74 6f 20 73 6b 69 70 20 74 68 72  ator to skip thr
21c80 6f 75 67 68 20 63 68 61 6e 67 65 73 65 74 20 2a  ough changeset *
21c90 2f 20 20 0a 20 20 69 6e 74 20 72 63 20 3d 20 73  /  .  int rc = s
21ca0 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74 5f  qlite3changeset_
21cb0 73 74 61 72 74 28 26 70 49 74 65 72 2c 20 6e 43  start(&pIter, nC
21cc0 68 61 6e 67 65 73 65 74 2c 20 70 43 68 61 6e 67  hangeset, pChang
21cd0 65 73 65 74 29 3b 0a 20 20 69 66 28 20 72 63 3d  eset);.  if( rc=
21ce0 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20  =SQLITE_OK ){.  
21cf0 20 20 72 63 20 3d 20 73 65 73 73 69 6f 6e 43 68    rc = sessionCh
21d00 61 6e 67 65 73 65 74 41 70 70 6c 79 28 64 62 2c  angesetApply(db,
21d10 20 70 49 74 65 72 2c 20 78 46 69 6c 74 65 72 2c   pIter, xFilter,
21d20 20 78 43 6f 6e 66 6c 69 63 74 2c 20 70 43 74 78   xConflict, pCtx
21d30 29 3b 0a 20 20 7d 0a 20 20 72 65 74 75 72 6e 20  );.  }.  return 
21d40 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 41 70 70  rc;.}../*.** App
21d50 6c 79 20 74 68 65 20 63 68 61 6e 67 65 73 65 74  ly the changeset
21d60 20 70 61 73 73 65 64 20 76 69 61 20 78 49 6e 70   passed via xInp
21d70 75 74 2f 70 49 6e 20 74 6f 20 74 68 65 20 6d 61  ut/pIn to the ma
21d80 69 6e 20 64 61 74 61 62 61 73 65 0a 2a 2a 20 61  in database.** a
21d90 74 74 61 63 68 65 64 20 74 6f 20 68 61 6e 64 6c  ttached to handl
21da0 65 20 22 64 62 22 2e 20 49 6e 76 6f 6b 65 20 74  e "db". Invoke t
21db0 68 65 20 73 75 70 70 6c 69 65 64 20 63 6f 6e 66  he supplied conf
21dc0 6c 69 63 74 20 68 61 6e 64 6c 65 72 20 63 61 6c  lict handler cal
21dd0 6c 62 61 63 6b 0a 2a 2a 20 74 6f 20 72 65 73 6f  lback.** to reso
21de0 6c 76 65 20 61 6e 79 20 63 6f 6e 66 6c 69 63 74  lve any conflict
21df0 73 20 65 6e 63 6f 75 6e 74 65 72 65 64 20 77 68  s encountered wh
21e00 69 6c 65 20 61 70 70 6c 79 69 6e 67 20 74 68 65  ile applying the
21e10 20 63 68 61 6e 67 65 2e 0a 2a 2f 0a 69 6e 74 20   change..*/.int 
21e20 73 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74  sqlite3changeset
21e30 5f 61 70 70 6c 79 5f 73 74 72 6d 28 0a 20 20 73  _apply_strm(.  s
21e40 71 6c 69 74 65 33 20 2a 64 62 2c 20 20 20 20 20  qlite3 *db,     
21e50 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
21e60 2a 20 41 70 70 6c 79 20 63 68 61 6e 67 65 20 74  * Apply change t
21e70 6f 20 22 6d 61 69 6e 22 20 64 62 20 6f 66 20 74  o "main" db of t
21e80 68 69 73 20 68 61 6e 64 6c 65 20 2a 2f 0a 20 20  his handle */.  
21e90 69 6e 74 20 28 2a 78 49 6e 70 75 74 29 28 76 6f  int (*xInput)(vo
21ea0 69 64 20 2a 70 49 6e 2c 20 76 6f 69 64 20 2a 70  id *pIn, void *p
21eb0 44 61 74 61 2c 20 69 6e 74 20 2a 70 6e 44 61 74  Data, int *pnDat
21ec0 61 29 2c 20 2f 2a 20 49 6e 70 75 74 20 66 75 6e  a), /* Input fun
21ed0 63 74 69 6f 6e 20 2a 2f 0a 20 20 76 6f 69 64 20  ction */.  void 
21ee0 2a 70 49 6e 2c 20 20 20 20 20 20 20 20 20 20 20  *pIn,           
21ef0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
21f00 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
21f10 2a 20 46 69 72 73 74 20 61 72 67 20 66 6f 72 20  * First arg for 
21f20 78 49 6e 70 75 74 20 2a 2f 0a 20 20 69 6e 74 28  xInput */.  int(
21f30 2a 78 46 69 6c 74 65 72 29 28 0a 20 20 20 20 76  *xFilter)(.    v
21f40 6f 69 64 20 2a 70 43 74 78 2c 20 20 20 20 20 20  oid *pCtx,      
21f50 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
21f60 43 6f 70 79 20 6f 66 20 73 69 78 74 68 20 61 72  Copy of sixth ar
21f70 67 20 74 6f 20 5f 61 70 70 6c 79 28 29 20 2a 2f  g to _apply() */
21f80 0a 20 20 20 20 63 6f 6e 73 74 20 63 68 61 72 20  .    const char 
21f90 2a 7a 54 61 62 20 20 20 20 20 20 20 20 20 20 20  *zTab           
21fa0 20 20 20 2f 2a 20 54 61 62 6c 65 20 6e 61 6d 65     /* Table name
21fb0 20 2a 2f 0a 20 20 29 2c 0a 20 20 69 6e 74 28 2a   */.  ),.  int(*
21fc0 78 43 6f 6e 66 6c 69 63 74 29 28 0a 20 20 20 20  xConflict)(.    
21fd0 76 6f 69 64 20 2a 70 43 74 78 2c 20 20 20 20 20  void *pCtx,     
21fe0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
21ff0 20 43 6f 70 79 20 6f 66 20 73 69 78 74 68 20 61   Copy of sixth a
22000 72 67 20 74 6f 20 5f 61 70 70 6c 79 28 29 20 2a  rg to _apply() *
22010 2f 0a 20 20 20 20 69 6e 74 20 65 43 6f 6e 66 6c  /.    int eConfl
22020 69 63 74 2c 20 20 20 20 20 20 20 20 20 20 20 20  ict,            
22030 20 20 20 20 2f 2a 20 44 41 54 41 2c 20 4d 49 53      /* DATA, MIS
22040 53 49 4e 47 2c 20 43 4f 4e 46 4c 49 43 54 2c 20  SING, CONFLICT, 
22050 43 4f 4e 53 54 52 41 49 4e 54 20 2a 2f 0a 20 20  CONSTRAINT */.  
22060 20 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65    sqlite3_change
22070 73 65 74 5f 69 74 65 72 20 2a 70 20 20 20 20 20  set_iter *p     
22080 2f 2a 20 48 61 6e 64 6c 65 20 64 65 73 63 72 69  /* Handle descri
22090 62 69 6e 67 20 63 68 61 6e 67 65 20 61 6e 64 20  bing change and 
220a0 63 6f 6e 66 6c 69 63 74 20 2a 2f 0a 20 20 29 2c  conflict */.  ),
220b0 0a 20 20 76 6f 69 64 20 2a 70 43 74 78 20 20 20  .  void *pCtx   
220c0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
220d0 20 20 20 2f 2a 20 46 69 72 73 74 20 61 72 67 75     /* First argu
220e0 6d 65 6e 74 20 70 61 73 73 65 64 20 74 6f 20 78  ment passed to x
220f0 43 6f 6e 66 6c 69 63 74 20 2a 2f 0a 29 7b 0a 20  Conflict */.){. 
22100 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 73   sqlite3_changes
22110 65 74 5f 69 74 65 72 20 2a 70 49 74 65 72 3b 20  et_iter *pIter; 
22120 20 2f 2a 20 49 74 65 72 61 74 6f 72 20 74 6f 20   /* Iterator to 
22130 73 6b 69 70 20 74 68 72 6f 75 67 68 20 63 68 61  skip through cha
22140 6e 67 65 73 65 74 20 2a 2f 20 20 0a 20 20 69 6e  ngeset */  .  in
22150 74 20 72 63 20 3d 20 73 71 6c 69 74 65 33 63 68  t rc = sqlite3ch
22160 61 6e 67 65 73 65 74 5f 73 74 61 72 74 5f 73 74  angeset_start_st
22170 72 6d 28 26 70 49 74 65 72 2c 20 78 49 6e 70 75  rm(&pIter, xInpu
22180 74 2c 20 70 49 6e 29 3b 0a 20 20 69 66 28 20 72  t, pIn);.  if( r
22190 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a  c==SQLITE_OK ){.
221a0 20 20 20 20 72 63 20 3d 20 73 65 73 73 69 6f 6e      rc = session
221b0 43 68 61 6e 67 65 73 65 74 41 70 70 6c 79 28 64  ChangesetApply(d
221c0 62 2c 20 70 49 74 65 72 2c 20 78 46 69 6c 74 65  b, pIter, xFilte
221d0 72 2c 20 78 43 6f 6e 66 6c 69 63 74 2c 20 70 43  r, xConflict, pC
221e0 74 78 29 3b 0a 20 20 7d 0a 20 20 72 65 74 75 72  tx);.  }.  retur
221f0 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 73  n rc;.}../*.** s
22200 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 67 72 6f  qlite3_changegro
22210 75 70 20 68 61 6e 64 6c 65 2e 0a 2a 2f 0a 73 74  up handle..*/.st
22220 72 75 63 74 20 73 71 6c 69 74 65 33 5f 63 68 61  ruct sqlite3_cha
22230 6e 67 65 67 72 6f 75 70 20 7b 0a 20 20 69 6e 74  ngegroup {.  int
22240 20 72 63 3b 20 20 20 20 20 20 20 20 20 20 20 20   rc;            
22250 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
22260 45 72 72 6f 72 20 63 6f 64 65 20 2a 2f 0a 20 20  Error code */.  
22270 69 6e 74 20 62 50 61 74 63 68 3b 20 20 20 20 20  int bPatch;     
22280 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
22290 2f 2a 20 54 72 75 65 20 74 6f 20 61 63 63 75 6d  /* True to accum
222a0 75 6c 61 74 65 20 70 61 74 63 68 73 65 74 73 20  ulate patchsets 
222b0 2a 2f 0a 20 20 53 65 73 73 69 6f 6e 54 61 62 6c  */.  SessionTabl
222c0 65 20 2a 70 4c 69 73 74 3b 20 20 20 20 20 20 20  e *pList;       
222d0 20 20 20 20 20 2f 2a 20 4c 69 73 74 20 6f 66 20       /* List of 
222e0 74 61 62 6c 65 73 20 69 6e 20 63 75 72 72 65 6e  tables in curren
222f0 74 20 70 61 74 63 68 20 2a 2f 0a 7d 3b 0a 0a 2f  t patch */.};../
22300 2a 0a 2a 2a 20 54 68 69 73 20 66 75 6e 63 74 69  *.** This functi
22310 6f 6e 20 69 73 20 63 61 6c 6c 65 64 20 74 6f 20  on is called to 
22320 6d 65 72 67 65 20 74 77 6f 20 63 68 61 6e 67 65  merge two change
22330 73 20 74 6f 20 74 68 65 20 73 61 6d 65 20 72 6f  s to the same ro
22340 77 20 74 6f 67 65 74 68 65 72 20 61 73 0a 2a 2a  w together as.**
22350 20 70 61 72 74 20 6f 66 20 61 6e 20 73 71 6c 69   part of an sqli
22360 74 65 33 63 68 61 6e 67 65 73 65 74 5f 63 6f 6e  te3changeset_con
22370 63 61 74 28 29 20 6f 70 65 72 61 74 69 6f 6e 2e  cat() operation.
22380 20 41 20 6e 65 77 20 63 68 61 6e 67 65 20 6f 62   A new change ob
22390 6a 65 63 74 20 69 73 0a 2a 2a 20 61 6c 6c 6f 63  ject is.** alloc
223a0 61 74 65 64 20 61 6e 64 20 61 20 70 6f 69 6e 74  ated and a point
223b0 65 72 20 74 6f 20 69 74 20 73 74 6f 72 65 64 20  er to it stored 
223c0 69 6e 20 2a 70 70 4e 65 77 2e 0a 2a 2f 0a 73 74  in *ppNew..*/.st
223d0 61 74 69 63 20 69 6e 74 20 73 65 73 73 69 6f 6e  atic int session
223e0 43 68 61 6e 67 65 4d 65 72 67 65 28 0a 20 20 53  ChangeMerge(.  S
223f0 65 73 73 69 6f 6e 54 61 62 6c 65 20 2a 70 54 61  essionTable *pTa
22400 62 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 2f  b,             /
22410 2a 20 54 61 62 6c 65 20 73 74 72 75 63 74 75 72  * Table structur
22420 65 20 2a 2f 0a 20 20 69 6e 74 20 62 50 61 74 63  e */.  int bPatc
22430 68 73 65 74 2c 20 20 20 20 20 20 20 20 20 20 20  hset,           
22440 20 20 20 20 20 20 20 2f 2a 20 54 72 75 65 20 66         /* True f
22450 6f 72 20 70 61 74 63 68 73 65 74 73 20 2a 2f 0a  or patchsets */.
22460 20 20 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 20    SessionChange 
22470 2a 70 45 78 69 73 74 2c 20 20 20 20 20 20 20 20  *pExist,        
22480 20 20 2f 2a 20 45 78 69 73 74 69 6e 67 20 63 68    /* Existing ch
22490 61 6e 67 65 20 2a 2f 0a 20 20 69 6e 74 20 6f 70  ange */.  int op
224a0 32 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20  2,              
224b0 20 20 20 20 20 20 20 20 20 20 2f 2a 20 53 65 63            /* Sec
224c0 6f 6e 64 20 63 68 61 6e 67 65 20 6f 70 65 72 61  ond change opera
224d0 74 69 6f 6e 20 2a 2f 0a 20 20 69 6e 74 20 62 49  tion */.  int bI
224e0 6e 64 69 72 65 63 74 2c 20 20 20 20 20 20 20 20  ndirect,        
224f0 20 20 20 20 20 20 20 20 20 20 2f 2a 20 54 72 75            /* Tru
22500 65 20 69 66 20 73 65 63 6f 6e 64 20 63 68 61 6e  e if second chan
22510 67 65 20 69 73 20 69 6e 64 69 72 65 63 74 20 2a  ge is indirect *
22520 2f 0a 20 20 75 38 20 2a 61 52 65 63 2c 20 20 20  /.  u8 *aRec,   
22530 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
22540 20 20 20 20 2f 2a 20 53 65 63 6f 6e 64 20 63 68      /* Second ch
22550 61 6e 67 65 20 72 65 63 6f 72 64 20 2a 2f 0a 20  ange record */. 
22560 20 69 6e 74 20 6e 52 65 63 2c 20 20 20 20 20 20   int nRec,      
22570 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
22580 20 2f 2a 20 4e 75 6d 62 65 72 20 6f 66 20 62 79   /* Number of by
22590 74 65 73 20 69 6e 20 61 52 65 63 20 2a 2f 0a 20  tes in aRec */. 
225a0 20 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 20 2a   SessionChange *
225b0 2a 70 70 4e 65 77 20 20 20 20 20 20 20 20 20 20  *ppNew          
225c0 20 2f 2a 20 4f 55 54 3a 20 4d 65 72 67 65 64 20   /* OUT: Merged 
225d0 63 68 61 6e 67 65 20 2a 2f 0a 29 7b 0a 20 20 53  change */.){.  S
225e0 65 73 73 69 6f 6e 43 68 61 6e 67 65 20 2a 70 4e  essionChange *pN
225f0 65 77 20 3d 20 30 3b 0a 0a 20 20 69 66 28 20 21  ew = 0;..  if( !
22600 70 45 78 69 73 74 20 29 7b 0a 20 20 20 20 70 4e  pExist ){.    pN
22610 65 77 20 3d 20 28 53 65 73 73 69 6f 6e 43 68 61  ew = (SessionCha
22620 6e 67 65 20 2a 29 73 71 6c 69 74 65 33 5f 6d 61  nge *)sqlite3_ma
22630 6c 6c 6f 63 28 73 69 7a 65 6f 66 28 53 65 73 73  lloc(sizeof(Sess
22640 69 6f 6e 43 68 61 6e 67 65 29 20 2b 20 6e 52 65  ionChange) + nRe
22650 63 29 3b 0a 20 20 20 20 69 66 28 20 21 70 4e 65  c);.    if( !pNe
22660 77 20 29 7b 0a 20 20 20 20 20 20 72 65 74 75 72  w ){.      retur
22670 6e 20 53 51 4c 49 54 45 5f 4e 4f 4d 45 4d 3b 0a  n SQLITE_NOMEM;.
22680 20 20 20 20 7d 0a 20 20 20 20 6d 65 6d 73 65 74      }.    memset
22690 28 70 4e 65 77 2c 20 30 2c 20 73 69 7a 65 6f 66  (pNew, 0, sizeof
226a0 28 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 29 29  (SessionChange))
226b0 3b 0a 20 20 20 20 70 4e 65 77 2d 3e 6f 70 20 3d  ;.    pNew->op =
226c0 20 6f 70 32 3b 0a 20 20 20 20 70 4e 65 77 2d 3e   op2;.    pNew->
226d0 62 49 6e 64 69 72 65 63 74 20 3d 20 62 49 6e 64  bIndirect = bInd
226e0 69 72 65 63 74 3b 0a 20 20 20 20 70 4e 65 77 2d  irect;.    pNew-
226f0 3e 6e 52 65 63 6f 72 64 20 3d 20 6e 52 65 63 3b  >nRecord = nRec;
22700 0a 20 20 20 20 70 4e 65 77 2d 3e 61 52 65 63 6f  .    pNew->aReco
22710 72 64 20 3d 20 28 75 38 2a 29 26 70 4e 65 77 5b  rd = (u8*)&pNew[
22720 31 5d 3b 0a 20 20 20 20 6d 65 6d 63 70 79 28 70  1];.    memcpy(p
22730 4e 65 77 2d 3e 61 52 65 63 6f 72 64 2c 20 61 52  New->aRecord, aR
22740 65 63 2c 20 6e 52 65 63 29 3b 0a 20 20 7d 65 6c  ec, nRec);.  }el
22750 73 65 7b 0a 20 20 20 20 69 6e 74 20 6f 70 31 20  se{.    int op1 
22760 3d 20 70 45 78 69 73 74 2d 3e 6f 70 3b 0a 0a 20  = pExist->op;.. 
22770 20 20 20 2f 2a 20 0a 20 20 20 20 2a 2a 20 20 20     /* .    **   
22780 6f 70 31 3d 49 4e 53 45 52 54 2c 20 6f 70 32 3d  op1=INSERT, op2=
22790 49 4e 53 45 52 54 20 20 20 20 20 20 2d 3e 20 20  INSERT      ->  
227a0 20 20 20 20 55 6e 73 75 70 70 6f 72 74 65 64 2e      Unsupported.
227b0 20 44 69 73 63 61 72 64 20 6f 70 32 2e 0a 20 20   Discard op2..  
227c0 20 20 2a 2a 20 20 20 6f 70 31 3d 49 4e 53 45 52    **   op1=INSER
227d0 54 2c 20 6f 70 32 3d 55 50 44 41 54 45 20 20 20  T, op2=UPDATE   
227e0 20 20 20 2d 3e 20 20 20 20 20 20 49 4e 53 45 52     ->      INSER
227f0 54 2e 0a 20 20 20 20 2a 2a 20 20 20 6f 70 31 3d  T..    **   op1=
22800 49 4e 53 45 52 54 2c 20 6f 70 32 3d 44 45 4c 45  INSERT, op2=DELE
22810 54 45 20 20 20 20 20 20 2d 3e 20 20 20 20 20 20  TE      ->      
22820 28 6e 6f 6e 65 29 0a 20 20 20 20 2a 2a 0a 20 20  (none).    **.  
22830 20 20 2a 2a 20 20 20 6f 70 31 3d 55 50 44 41 54    **   op1=UPDAT
22840 45 2c 20 6f 70 32 3d 49 4e 53 45 52 54 20 20 20  E, op2=INSERT   
22850 20 20 20 2d 3e 20 20 20 20 20 20 55 6e 73 75 70     ->      Unsup
22860 70 6f 72 74 65 64 2e 20 44 69 73 63 61 72 64 20  ported. Discard 
22870 6f 70 32 2e 0a 20 20 20 20 2a 2a 20 20 20 6f 70  op2..    **   op
22880 31 3d 55 50 44 41 54 45 2c 20 6f 70 32 3d 55 50  1=UPDATE, op2=UP
22890 44 41 54 45 20 20 20 20 20 20 2d 3e 20 20 20 20  DATE      ->    
228a0 20 20 55 50 44 41 54 45 2e 0a 20 20 20 20 2a 2a    UPDATE..    **
228b0 20 20 20 6f 70 31 3d 55 50 44 41 54 45 2c 20 6f     op1=UPDATE, o
228c0 70 32 3d 44 45 4c 45 54 45 20 20 20 20 20 20 2d  p2=DELETE      -
228d0 3e 20 20 20 20 20 20 44 45 4c 45 54 45 2e 0a 20  >      DELETE.. 
228e0 20 20 20 2a 2a 0a 20 20 20 20 2a 2a 20 20 20 6f     **.    **   o
228f0 70 31 3d 44 45 4c 45 54 45 2c 20 6f 70 32 3d 49  p1=DELETE, op2=I
22900 4e 53 45 52 54 20 20 20 20 20 20 2d 3e 20 20 20  NSERT      ->   
22910 20 20 20 55 50 44 41 54 45 2e 0a 20 20 20 20 2a     UPDATE..    *
22920 2a 20 20 20 6f 70 31 3d 44 45 4c 45 54 45 2c 20  *   op1=DELETE, 
22930 6f 70 32 3d 55 50 44 41 54 45 20 20 20 20 20 20  op2=UPDATE      
22940 2d 3e 20 20 20 20 20 20 55 6e 73 75 70 70 6f 72  ->      Unsuppor
22950 74 65 64 2e 20 44 69 73 63 61 72 64 20 6f 70 32  ted. Discard op2
22960 2e 0a 20 20 20 20 2a 2a 20 20 20 6f 70 31 3d 44  ..    **   op1=D
22970 45 4c 45 54 45 2c 20 6f 70 32 3d 44 45 4c 45 54  ELETE, op2=DELET
22980 45 20 20 20 20 20 20 2d 3e 20 20 20 20 20 20 55  E      ->      U
22990 6e 73 75 70 70 6f 72 74 65 64 2e 20 44 69 73 63  nsupported. Disc
229a0 61 72 64 20 6f 70 32 2e 0a 20 20 20 20 2a 2f 20  ard op2..    */ 
229b0 20 20 0a 20 20 20 20 69 66 28 20 28 6f 70 31 3d    .    if( (op1=
229c0 3d 53 51 4c 49 54 45 5f 49 4e 53 45 52 54 20 26  =SQLITE_INSERT &
229d0 26 20 6f 70 32 3d 3d 53 51 4c 49 54 45 5f 49 4e  & op2==SQLITE_IN
229e0 53 45 52 54 29 0a 20 20 20 20 20 7c 7c 20 28 6f  SERT).     || (o
229f0 70 31 3d 3d 53 51 4c 49 54 45 5f 55 50 44 41 54  p1==SQLITE_UPDAT
22a00 45 20 26 26 20 6f 70 32 3d 3d 53 51 4c 49 54 45  E && op2==SQLITE
22a10 5f 49 4e 53 45 52 54 29 0a 20 20 20 20 20 7c 7c  _INSERT).     ||
22a20 20 28 6f 70 31 3d 3d 53 51 4c 49 54 45 5f 44 45   (op1==SQLITE_DE
22a30 4c 45 54 45 20 26 26 20 6f 70 32 3d 3d 53 51 4c  LETE && op2==SQL
22a40 49 54 45 5f 55 50 44 41 54 45 29 0a 20 20 20 20  ITE_UPDATE).    
22a50 20 7c 7c 20 28 6f 70 31 3d 3d 53 51 4c 49 54 45   || (op1==SQLITE
22a60 5f 44 45 4c 45 54 45 20 26 26 20 6f 70 32 3d 3d  _DELETE && op2==
22a70 53 51 4c 49 54 45 5f 44 45 4c 45 54 45 29 0a 20  SQLITE_DELETE). 
22a80 20 20 20 29 7b 0a 20 20 20 20 20 20 70 4e 65 77     ){.      pNew
22a90 20 3d 20 70 45 78 69 73 74 3b 0a 20 20 20 20 7d   = pExist;.    }
22aa0 65 6c 73 65 20 69 66 28 20 6f 70 31 3d 3d 53 51  else if( op1==SQ
22ab0 4c 49 54 45 5f 49 4e 53 45 52 54 20 26 26 20 6f  LITE_INSERT && o
22ac0 70 32 3d 3d 53 51 4c 49 54 45 5f 44 45 4c 45 54  p2==SQLITE_DELET
22ad0 45 20 29 7b 0a 20 20 20 20 20 20 73 71 6c 69 74  E ){.      sqlit
22ae0 65 33 5f 66 72 65 65 28 70 45 78 69 73 74 29 3b  e3_free(pExist);
22af0 0a 20 20 20 20 20 20 61 73 73 65 72 74 28 20 70  .      assert( p
22b00 4e 65 77 3d 3d 30 20 29 3b 0a 20 20 20 20 7d 65  New==0 );.    }e
22b10 6c 73 65 7b 0a 20 20 20 20 20 20 75 38 20 2a 61  lse{.      u8 *a
22b20 45 78 69 73 74 20 3d 20 70 45 78 69 73 74 2d 3e  Exist = pExist->
22b30 61 52 65 63 6f 72 64 3b 0a 20 20 20 20 20 20 69  aRecord;.      i
22b40 6e 74 20 6e 42 79 74 65 3b 0a 20 20 20 20 20 20  nt nByte;.      
22b50 75 38 20 2a 61 43 73 72 3b 0a 0a 20 20 20 20 20  u8 *aCsr;..     
22b60 20 2f 2a 20 41 6c 6c 6f 63 61 74 65 20 61 20 6e   /* Allocate a n
22b70 65 77 20 53 65 73 73 69 6f 6e 43 68 61 6e 67 65  ew SessionChange
22b80 20 6f 62 6a 65 63 74 2e 20 45 6e 73 75 72 65 20   object. Ensure 
22b90 74 68 61 74 20 74 68 65 20 61 52 65 63 6f 72 64  that the aRecord
22ba0 5b 5d 0a 20 20 20 20 20 20 2a 2a 20 62 75 66 66  [].      ** buff
22bb0 65 72 20 6f 66 20 74 68 65 20 6e 65 77 20 6f 62  er of the new ob
22bc0 6a 65 63 74 20 69 73 20 6c 61 72 67 65 20 65 6e  ject is large en
22bd0 6f 75 67 68 20 74 6f 20 68 6f 6c 64 20 61 6e 79  ough to hold any
22be0 20 72 65 63 6f 72 64 20 74 68 61 74 0a 20 20 20   record that.   
22bf0 20 20 20 2a 2a 20 6d 61 79 20 62 65 20 67 65 6e     ** may be gen
22c00 65 72 61 74 65 64 20 62 79 20 63 6f 6d 62 69 6e  erated by combin
22c10 69 6e 67 20 74 68 65 20 69 6e 70 75 74 20 72 65  ing the input re
22c20 63 6f 72 64 73 2e 20 20 2a 2f 0a 20 20 20 20 20  cords.  */.     
22c30 20 6e 42 79 74 65 20 3d 20 73 69 7a 65 6f 66 28   nByte = sizeof(
22c40 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 29 20 2b  SessionChange) +
22c50 20 70 45 78 69 73 74 2d 3e 6e 52 65 63 6f 72 64   pExist->nRecord
22c60 20 2b 20 6e 52 65 63 3b 0a 20 20 20 20 20 20 70   + nRec;.      p
22c70 4e 65 77 20 3d 20 28 53 65 73 73 69 6f 6e 43 68  New = (SessionCh
22c80 61 6e 67 65 20 2a 29 73 71 6c 69 74 65 33 5f 6d  ange *)sqlite3_m
22c90 61 6c 6c 6f 63 28 6e 42 79 74 65 29 3b 0a 20 20  alloc(nByte);.  
22ca0 20 20 20 20 69 66 28 20 21 70 4e 65 77 20 29 7b      if( !pNew ){
22cb0 0a 20 20 20 20 20 20 20 20 73 71 6c 69 74 65 33  .        sqlite3
22cc0 5f 66 72 65 65 28 70 45 78 69 73 74 29 3b 0a 20  _free(pExist);. 
22cd0 20 20 20 20 20 20 20 72 65 74 75 72 6e 20 53 51         return SQ
22ce0 4c 49 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 20 20  LITE_NOMEM;.    
22cf0 20 20 7d 0a 20 20 20 20 20 20 6d 65 6d 73 65 74    }.      memset
22d00 28 70 4e 65 77 2c 20 30 2c 20 73 69 7a 65 6f 66  (pNew, 0, sizeof
22d10 28 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 29 29  (SessionChange))
22d20 3b 0a 20 20 20 20 20 20 70 4e 65 77 2d 3e 62 49  ;.      pNew->bI
22d30 6e 64 69 72 65 63 74 20 3d 20 28 62 49 6e 64 69  ndirect = (bIndi
22d40 72 65 63 74 20 26 26 20 70 45 78 69 73 74 2d 3e  rect && pExist->
22d50 62 49 6e 64 69 72 65 63 74 29 3b 0a 20 20 20 20  bIndirect);.    
22d60 20 20 61 43 73 72 20 3d 20 70 4e 65 77 2d 3e 61    aCsr = pNew->a
22d70 52 65 63 6f 72 64 20 3d 20 28 75 38 20 2a 29 26  Record = (u8 *)&
22d80 70 4e 65 77 5b 31 5d 3b 0a 0a 20 20 20 20 20 20  pNew[1];..      
22d90 69 66 28 20 6f 70 31 3d 3d 53 51 4c 49 54 45 5f  if( op1==SQLITE_
22da0 49 4e 53 45 52 54 20 29 7b 20 20 20 20 20 20 20  INSERT ){       
22db0 20 20 20 20 20 20 2f 2a 20 49 4e 53 45 52 54 20        /* INSERT 
22dc0 2b 20 55 50 44 41 54 45 20 2a 2f 0a 20 20 20 20  + UPDATE */.    
22dd0 20 20 20 20 75 38 20 2a 61 31 20 3d 20 61 52 65      u8 *a1 = aRe
22de0 63 3b 0a 20 20 20 20 20 20 20 20 61 73 73 65 72  c;.        asser
22df0 74 28 20 6f 70 32 3d 3d 53 51 4c 49 54 45 5f 55  t( op2==SQLITE_U
22e00 50 44 41 54 45 20 29 3b 0a 20 20 20 20 20 20 20  PDATE );.       
22e10 20 70 4e 65 77 2d 3e 6f 70 20 3d 20 53 51 4c 49   pNew->op = SQLI
22e20 54 45 5f 49 4e 53 45 52 54 3b 0a 20 20 20 20 20  TE_INSERT;.     
22e30 20 20 20 69 66 28 20 62 50 61 74 63 68 73 65 74     if( bPatchset
22e40 3d 3d 30 20 29 20 73 65 73 73 69 6f 6e 53 6b 69  ==0 ) sessionSki
22e50 70 52 65 63 6f 72 64 28 26 61 31 2c 20 70 54 61  pRecord(&a1, pTa
22e60 62 2d 3e 6e 43 6f 6c 29 3b 0a 20 20 20 20 20 20  b->nCol);.      
22e70 20 20 73 65 73 73 69 6f 6e 4d 65 72 67 65 52 65    sessionMergeRe
22e80 63 6f 72 64 28 26 61 43 73 72 2c 20 70 54 61 62  cord(&aCsr, pTab
22e90 2d 3e 6e 43 6f 6c 2c 20 61 45 78 69 73 74 2c 20  ->nCol, aExist, 
22ea0 61 31 29 3b 0a 20 20 20 20 20 20 7d 65 6c 73 65  a1);.      }else
22eb0 20 69 66 28 20 6f 70 31 3d 3d 53 51 4c 49 54 45   if( op1==SQLITE
22ec0 5f 44 45 4c 45 54 45 20 29 7b 20 20 20 20 20 20  _DELETE ){      
22ed0 20 2f 2a 20 44 45 4c 45 54 45 20 2b 20 49 4e 53   /* DELETE + INS
22ee0 45 52 54 20 2a 2f 0a 20 20 20 20 20 20 20 20 61  ERT */.        a
22ef0 73 73 65 72 74 28 20 6f 70 32 3d 3d 53 51 4c 49  ssert( op2==SQLI
22f00 54 45 5f 49 4e 53 45 52 54 20 29 3b 0a 20 20 20  TE_INSERT );.   
22f10 20 20 20 20 20 70 4e 65 77 2d 3e 6f 70 20 3d 20       pNew->op = 
22f20 53 51 4c 49 54 45 5f 55 50 44 41 54 45 3b 0a 20  SQLITE_UPDATE;. 
22f30 20 20 20 20 20 20 20 69 66 28 20 62 50 61 74 63         if( bPatc
22f40 68 73 65 74 20 29 7b 0a 20 20 20 20 20 20 20 20  hset ){.        
22f50 20 20 6d 65 6d 63 70 79 28 61 43 73 72 2c 20 61    memcpy(aCsr, a
22f60 52 65 63 2c 20 6e 52 65 63 29 3b 0a 20 20 20 20  Rec, nRec);.    
22f70 20 20 20 20 20 20 61 43 73 72 20 2b 3d 20 6e 52        aCsr += nR
22f80 65 63 3b 0a 20 20 20 20 20 20 20 20 7d 65 6c 73  ec;.        }els
22f90 65 7b 0a 20 20 20 20 20 20 20 20 20 20 69 66 28  e{.          if(
22fa0 20 30 3d 3d 73 65 73 73 69 6f 6e 4d 65 72 67 65   0==sessionMerge
22fb0 55 70 64 61 74 65 28 26 61 43 73 72 2c 20 70 54  Update(&aCsr, pT
22fc0 61 62 2c 20 62 50 61 74 63 68 73 65 74 2c 20 61  ab, bPatchset, a
22fd0 45 78 69 73 74 2c 20 30 2c 61 52 65 63 2c 30 29  Exist, 0,aRec,0)
22fe0 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 20 20   ){.            
22ff0 73 71 6c 69 74 65 33 5f 66 72 65 65 28 70 4e 65  sqlite3_free(pNe
23000 77 29 3b 0a 20 20 20 20 20 20 20 20 20 20 20 20  w);.            
23010 70 4e 65 77 20 3d 20 30 3b 0a 20 20 20 20 20 20  pNew = 0;.      
23020 20 20 20 20 7d 0a 20 20 20 20 20 20 20 20 7d 0a      }.        }.
23030 20 20 20 20 20 20 7d 65 6c 73 65 20 69 66 28 20        }else if( 
23040 6f 70 32 3d 3d 53 51 4c 49 54 45 5f 55 50 44 41  op2==SQLITE_UPDA
23050 54 45 20 29 7b 20 20 20 20 20 20 20 2f 2a 20 55  TE ){       /* U
23060 50 44 41 54 45 20 2b 20 55 50 44 41 54 45 20 2a  PDATE + UPDATE *
23070 2f 0a 20 20 20 20 20 20 20 20 75 38 20 2a 61 31  /.        u8 *a1
23080 20 3d 20 61 45 78 69 73 74 3b 0a 20 20 20 20 20   = aExist;.     
23090 20 20 20 75 38 20 2a 61 32 20 3d 20 61 52 65 63     u8 *a2 = aRec
230a0 3b 0a 20 20 20 20 20 20 20 20 61 73 73 65 72 74  ;.        assert
230b0 28 20 6f 70 31 3d 3d 53 51 4c 49 54 45 5f 55 50  ( op1==SQLITE_UP
230c0 44 41 54 45 20 29 3b 0a 20 20 20 20 20 20 20 20  DATE );.        
230d0 69 66 28 20 62 50 61 74 63 68 73 65 74 3d 3d 30  if( bPatchset==0
230e0 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 73 65   ){.          se
230f0 73 73 69 6f 6e 53 6b 69 70 52 65 63 6f 72 64 28  ssionSkipRecord(
23100 26 61 31 2c 20 70 54 61 62 2d 3e 6e 43 6f 6c 29  &a1, pTab->nCol)
23110 3b 0a 20 20 20 20 20 20 20 20 20 20 73 65 73 73  ;.          sess
23120 69 6f 6e 53 6b 69 70 52 65 63 6f 72 64 28 26 61  ionSkipRecord(&a
23130 32 2c 20 70 54 61 62 2d 3e 6e 43 6f 6c 29 3b 0a  2, pTab->nCol);.
23140 20 20 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20          }.      
23150 20 20 70 4e 65 77 2d 3e 6f 70 20 3d 20 53 51 4c    pNew->op = SQL
23160 49 54 45 5f 55 50 44 41 54 45 3b 0a 20 20 20 20  ITE_UPDATE;.    
23170 20 20 20 20 69 66 28 20 30 3d 3d 73 65 73 73 69      if( 0==sessi
23180 6f 6e 4d 65 72 67 65 55 70 64 61 74 65 28 26 61  onMergeUpdate(&a
23190 43 73 72 2c 20 70 54 61 62 2c 20 62 50 61 74 63  Csr, pTab, bPatc
231a0 68 73 65 74 2c 20 61 52 65 63 2c 20 61 45 78 69  hset, aRec, aExi
231b0 73 74 2c 61 31 2c 61 32 29 20 29 7b 0a 20 20 20  st,a1,a2) ){.   
231c0 20 20 20 20 20 20 20 73 71 6c 69 74 65 33 5f 66         sqlite3_f
231d0 72 65 65 28 70 4e 65 77 29 3b 0a 20 20 20 20 20  ree(pNew);.     
231e0 20 20 20 20 20 70 4e 65 77 20 3d 20 30 3b 0a 20       pNew = 0;. 
231f0 20 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 7d         }.      }
23200 65 6c 73 65 7b 20 20 20 20 20 20 20 20 20 20 20  else{           
23210 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
23220 20 20 20 20 20 2f 2a 20 55 50 44 41 54 45 20 2b       /* UPDATE +
23230 20 44 45 4c 45 54 45 20 2a 2f 0a 20 20 20 20 20   DELETE */.     
23240 20 20 20 61 73 73 65 72 74 28 20 6f 70 31 3d 3d     assert( op1==
23250 53 51 4c 49 54 45 5f 55 50 44 41 54 45 20 26 26  SQLITE_UPDATE &&
23260 20 6f 70 32 3d 3d 53 51 4c 49 54 45 5f 44 45 4c   op2==SQLITE_DEL
23270 45 54 45 20 29 3b 0a 20 20 20 20 20 20 20 20 70  ETE );.        p
23280 4e 65 77 2d 3e 6f 70 20 3d 20 53 51 4c 49 54 45  New->op = SQLITE
23290 5f 44 45 4c 45 54 45 3b 0a 20 20 20 20 20 20 20  _DELETE;.       
232a0 20 69 66 28 20 62 50 61 74 63 68 73 65 74 20 29   if( bPatchset )
232b0 7b 0a 20 20 20 20 20 20 20 20 20 20 6d 65 6d 63  {.          memc
232c0 70 79 28 61 43 73 72 2c 20 61 52 65 63 2c 20 6e  py(aCsr, aRec, n
232d0 52 65 63 29 3b 0a 20 20 20 20 20 20 20 20 20 20  Rec);.          
232e0 61 43 73 72 20 2b 3d 20 6e 52 65 63 3b 0a 20 20  aCsr += nRec;.  
232f0 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20 20        }else{.   
23300 20 20 20 20 20 20 20 73 65 73 73 69 6f 6e 4d 65         sessionMe
23310 72 67 65 52 65 63 6f 72 64 28 26 61 43 73 72 2c  rgeRecord(&aCsr,
23320 20 70 54 61 62 2d 3e 6e 43 6f 6c 2c 20 61 52 65   pTab->nCol, aRe
23330 63 2c 20 61 45 78 69 73 74 29 3b 0a 20 20 20 20  c, aExist);.    
23340 20 20 20 20 7d 0a 20 20 20 20 20 20 7d 0a 0a 20      }.      }.. 
23350 20 20 20 20 20 69 66 28 20 70 4e 65 77 20 29 7b       if( pNew ){
23360 0a 20 20 20 20 20 20 20 20 70 4e 65 77 2d 3e 6e  .        pNew->n
23370 52 65 63 6f 72 64 20 3d 20 28 69 6e 74 29 28 61  Record = (int)(a
23380 43 73 72 20 2d 20 70 4e 65 77 2d 3e 61 52 65 63  Csr - pNew->aRec
23390 6f 72 64 29 3b 0a 20 20 20 20 20 20 7d 0a 20 20  ord);.      }.  
233a0 20 20 20 20 73 71 6c 69 74 65 33 5f 66 72 65 65      sqlite3_free
233b0 28 70 45 78 69 73 74 29 3b 0a 20 20 20 20 7d 0a  (pExist);.    }.
233c0 20 20 7d 0a 0a 20 20 2a 70 70 4e 65 77 20 3d 20    }..  *ppNew = 
233d0 70 4e 65 77 3b 0a 20 20 72 65 74 75 72 6e 20 53  pNew;.  return S
233e0 51 4c 49 54 45 5f 4f 4b 3b 0a 7d 0a 0a 2f 2a 0a  QLITE_OK;.}../*.
233f0 2a 2a 20 41 64 64 20 61 6c 6c 20 63 68 61 6e 67  ** Add all chang
23400 65 73 20 69 6e 20 74 68 65 20 63 68 61 6e 67 65  es in the change
23410 73 65 74 20 74 72 61 76 65 72 73 65 64 20 62 79  set traversed by
23420 20 74 68 65 20 69 74 65 72 61 74 6f 72 20 70 61   the iterator pa
23430 73 73 65 64 20 61 73 0a 2a 2a 20 74 68 65 20 66  ssed as.** the f
23440 69 72 73 74 20 61 72 67 75 6d 65 6e 74 20 74 6f  irst argument to
23450 20 74 68 65 20 63 68 61 6e 67 65 67 72 6f 75 70   the changegroup
23460 20 68 61 73 68 20 74 61 62 6c 65 73 2e 0a 2a 2f   hash tables..*/
23470 0a 73 74 61 74 69 63 20 69 6e 74 20 73 65 73 73  .static int sess
23480 69 6f 6e 43 68 61 6e 67 65 73 65 74 54 6f 48 61  ionChangesetToHa
23490 73 68 28 0a 20 20 73 71 6c 69 74 65 33 5f 63 68  sh(.  sqlite3_ch
234a0 61 6e 67 65 73 65 74 5f 69 74 65 72 20 2a 70 49  angeset_iter *pI
234b0 74 65 72 2c 20 20 20 2f 2a 20 49 74 65 72 61 74  ter,   /* Iterat
234c0 6f 72 20 74 6f 20 72 65 61 64 20 66 72 6f 6d 20  or to read from 
234d0 2a 2f 0a 20 20 73 71 6c 69 74 65 33 5f 63 68 61  */.  sqlite3_cha
234e0 6e 67 65 67 72 6f 75 70 20 2a 70 47 72 70 20 20  ngegroup *pGrp  
234f0 20 20 20 20 20 20 2f 2a 20 43 68 61 6e 67 65 67        /* Changeg
23500 72 6f 75 70 20 6f 62 6a 65 63 74 20 74 6f 20 61  roup object to a
23510 64 64 20 63 68 61 6e 67 65 73 65 74 20 74 6f 20  dd changeset to 
23520 2a 2f 0a 29 7b 0a 20 20 75 38 20 2a 61 52 65 63  */.){.  u8 *aRec
23530 3b 0a 20 20 69 6e 74 20 6e 52 65 63 3b 0a 20 20  ;.  int nRec;.  
23540 69 6e 74 20 72 63 20 3d 20 53 51 4c 49 54 45 5f  int rc = SQLITE_
23550 4f 4b 3b 0a 20 20 53 65 73 73 69 6f 6e 54 61 62  OK;.  SessionTab
23560 6c 65 20 2a 70 54 61 62 20 3d 20 30 3b 0a 0a 0a  le *pTab = 0;...
23570 20 20 77 68 69 6c 65 28 20 53 51 4c 49 54 45 5f    while( SQLITE_
23580 52 4f 57 3d 3d 73 65 73 73 69 6f 6e 43 68 61 6e  ROW==sessionChan
23590 67 65 73 65 74 4e 65 78 74 28 70 49 74 65 72 2c  gesetNext(pIter,
235a0 20 26 61 52 65 63 2c 20 26 6e 52 65 63 29 20 29   &aRec, &nRec) )
235b0 7b 0a 20 20 20 20 63 6f 6e 73 74 20 63 68 61 72  {.    const char
235c0 20 2a 7a 4e 65 77 3b 0a 20 20 20 20 69 6e 74 20   *zNew;.    int 
235d0 6e 43 6f 6c 3b 0a 20 20 20 20 69 6e 74 20 6f 70  nCol;.    int op
235e0 3b 0a 20 20 20 20 69 6e 74 20 69 48 61 73 68 3b  ;.    int iHash;
235f0 0a 20 20 20 20 69 6e 74 20 62 49 6e 64 69 72 65  .    int bIndire
23600 63 74 3b 0a 20 20 20 20 53 65 73 73 69 6f 6e 43  ct;.    SessionC
23610 68 61 6e 67 65 20 2a 70 43 68 61 6e 67 65 3b 0a  hange *pChange;.
23620 20 20 20 20 53 65 73 73 69 6f 6e 43 68 61 6e 67      SessionChang
23630 65 20 2a 70 45 78 69 73 74 20 3d 20 30 3b 0a 20  e *pExist = 0;. 
23640 20 20 20 53 65 73 73 69 6f 6e 43 68 61 6e 67 65     SessionChange
23650 20 2a 2a 70 70 3b 0a 0a 20 20 20 20 69 66 28 20   **pp;..    if( 
23660 70 47 72 70 2d 3e 70 4c 69 73 74 3d 3d 30 20 29  pGrp->pList==0 )
23670 7b 0a 20 20 20 20 20 20 70 47 72 70 2d 3e 62 50  {.      pGrp->bP
23680 61 74 63 68 20 3d 20 70 49 74 65 72 2d 3e 62 50  atch = pIter->bP
23690 61 74 63 68 73 65 74 3b 0a 20 20 20 20 7d 65 6c  atchset;.    }el
236a0 73 65 20 69 66 28 20 70 49 74 65 72 2d 3e 62 50  se if( pIter->bP
236b0 61 74 63 68 73 65 74 21 3d 70 47 72 70 2d 3e 62  atchset!=pGrp->b
236c0 50 61 74 63 68 20 29 7b 0a 20 20 20 20 20 20 72  Patch ){.      r
236d0 63 20 3d 20 53 51 4c 49 54 45 5f 45 52 52 4f 52  c = SQLITE_ERROR
236e0 3b 0a 20 20 20 20 20 20 62 72 65 61 6b 3b 0a 20  ;.      break;. 
236f0 20 20 20 7d 0a 0a 20 20 20 20 73 71 6c 69 74 65     }..    sqlite
23700 33 63 68 61 6e 67 65 73 65 74 5f 6f 70 28 70 49  3changeset_op(pI
23710 74 65 72 2c 20 26 7a 4e 65 77 2c 20 26 6e 43 6f  ter, &zNew, &nCo
23720 6c 2c 20 26 6f 70 2c 20 26 62 49 6e 64 69 72 65  l, &op, &bIndire
23730 63 74 29 3b 0a 20 20 20 20 69 66 28 20 21 70 54  ct);.    if( !pT
23740 61 62 20 7c 7c 20 73 71 6c 69 74 65 33 5f 73 74  ab || sqlite3_st
23750 72 69 63 6d 70 28 7a 4e 65 77 2c 20 70 54 61 62  ricmp(zNew, pTab
23760 2d 3e 7a 4e 61 6d 65 29 20 29 7b 0a 20 20 20 20  ->zName) ){.    
23770 20 20 2f 2a 20 53 65 61 72 63 68 20 74 68 65 20    /* Search the 
23780 6c 69 73 74 20 66 6f 72 20 61 20 6d 61 74 63 68  list for a match
23790 69 6e 67 20 74 61 62 6c 65 20 2a 2f 0a 20 20 20  ing table */.   
237a0 20 20 20 69 6e 74 20 6e 4e 65 77 20 3d 20 28 69     int nNew = (i
237b0 6e 74 29 73 74 72 6c 65 6e 28 7a 4e 65 77 29 3b  nt)strlen(zNew);
237c0 0a 20 20 20 20 20 20 75 38 20 2a 61 62 50 4b 3b  .      u8 *abPK;
237d0 0a 0a 20 20 20 20 20 20 73 71 6c 69 74 65 33 63  ..      sqlite3c
237e0 68 61 6e 67 65 73 65 74 5f 70 6b 28 70 49 74 65  hangeset_pk(pIte
237f0 72 2c 20 26 61 62 50 4b 2c 20 30 29 3b 0a 20 20  r, &abPK, 0);.  
23800 20 20 20 20 66 6f 72 28 70 54 61 62 20 3d 20 70      for(pTab = p
23810 47 72 70 2d 3e 70 4c 69 73 74 3b 20 70 54 61 62  Grp->pList; pTab
23820 3b 20 70 54 61 62 3d 70 54 61 62 2d 3e 70 4e 65  ; pTab=pTab->pNe
23830 78 74 29 7b 0a 20 20 20 20 20 20 20 20 69 66 28  xt){.        if(
23840 20 30 3d 3d 73 71 6c 69 74 65 33 5f 73 74 72 6e   0==sqlite3_strn
23850 69 63 6d 70 28 70 54 61 62 2d 3e 7a 4e 61 6d 65  icmp(pTab->zName
23860 2c 20 7a 4e 65 77 2c 20 6e 4e 65 77 2b 31 29 20  , zNew, nNew+1) 
23870 29 20 62 72 65 61 6b 3b 0a 20 20 20 20 20 20 7d  ) break;.      }
23880 0a 20 20 20 20 20 20 69 66 28 20 21 70 54 61 62  .      if( !pTab
23890 20 29 7b 0a 20 20 20 20 20 20 20 20 53 65 73 73   ){.        Sess
238a0 69 6f 6e 54 61 62 6c 65 20 2a 2a 70 70 54 61 62  ionTable **ppTab
238b0 3b 0a 0a 20 20 20 20 20 20 20 20 70 54 61 62 20  ;..        pTab 
238c0 3d 20 73 71 6c 69 74 65 33 5f 6d 61 6c 6c 6f 63  = sqlite3_malloc
238d0 28 73 69 7a 65 6f 66 28 53 65 73 73 69 6f 6e 54  (sizeof(SessionT
238e0 61 62 6c 65 29 20 2b 20 6e 43 6f 6c 20 2b 20 6e  able) + nCol + n
238f0 4e 65 77 2b 31 29 3b 0a 20 20 20 20 20 20 20 20  New+1);.        
23900 69 66 28 20 21 70 54 61 62 20 29 7b 0a 20 20 20  if( !pTab ){.   
23910 20 20 20 20 20 20 20 72 63 20 3d 20 53 51 4c 49         rc = SQLI
23920 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 20 20 20 20  TE_NOMEM;.      
23930 20 20 20 20 62 72 65 61 6b 3b 0a 20 20 20 20 20      break;.     
23940 20 20 20 7d 0a 20 20 20 20 20 20 20 20 6d 65 6d     }.        mem
23950 73 65 74 28 70 54 61 62 2c 20 30 2c 20 73 69 7a  set(pTab, 0, siz
23960 65 6f 66 28 53 65 73 73 69 6f 6e 54 61 62 6c 65  eof(SessionTable
23970 29 29 3b 0a 20 20 20 20 20 20 20 20 70 54 61 62  ));.        pTab
23980 2d 3e 6e 43 6f 6c 20 3d 20 6e 43 6f 6c 3b 0a 20  ->nCol = nCol;. 
23990 20 20 20 20 20 20 20 70 54 61 62 2d 3e 61 62 50         pTab->abP
239a0 4b 20 3d 20 28 75 38 2a 29 26 70 54 61 62 5b 31  K = (u8*)&pTab[1
239b0 5d 3b 0a 20 20 20 20 20 20 20 20 6d 65 6d 63 70  ];.        memcp
239c0 79 28 70 54 61 62 2d 3e 61 62 50 4b 2c 20 61 62  y(pTab->abPK, ab
239d0 50 4b 2c 20 6e 43 6f 6c 29 3b 0a 20 20 20 20 20  PK, nCol);.     
239e0 20 20 20 70 54 61 62 2d 3e 7a 4e 61 6d 65 20 3d     pTab->zName =
239f0 20 28 63 68 61 72 2a 29 26 70 54 61 62 2d 3e 61   (char*)&pTab->a
23a00 62 50 4b 5b 6e 43 6f 6c 5d 3b 0a 20 20 20 20 20  bPK[nCol];.     
23a10 20 20 20 6d 65 6d 63 70 79 28 70 54 61 62 2d 3e     memcpy(pTab->
23a20 7a 4e 61 6d 65 2c 20 7a 4e 65 77 2c 20 6e 4e 65  zName, zNew, nNe
23a30 77 2b 31 29 3b 0a 0a 20 20 20 20 20 20 20 20 2f  w+1);..        /
23a40 2a 20 54 68 65 20 6e 65 77 20 6f 62 6a 65 63 74  * The new object
23a50 20 6d 75 73 74 20 62 65 20 6c 69 6e 6b 65 64 20   must be linked 
23a60 6f 6e 20 74 6f 20 74 68 65 20 65 6e 64 20 6f 66  on to the end of
23a70 20 74 68 65 20 6c 69 73 74 2c 20 6e 6f 74 0a 20   the list, not. 
23a80 20 20 20 20 20 20 20 2a 2a 20 73 69 6d 70 6c 79         ** simply
23a90 20 61 64 64 65 64 20 74 6f 20 74 68 65 20 73 74   added to the st
23aa0 61 72 74 20 6f 66 20 69 74 2e 20 54 68 69 73 20  art of it. This 
23ab0 69 73 20 74 6f 20 65 6e 73 75 72 65 20 74 68 61  is to ensure tha
23ac0 74 20 74 68 65 0a 20 20 20 20 20 20 20 20 2a 2a  t the.        **
23ad0 20 74 61 62 6c 65 73 20 77 69 74 68 69 6e 20 74   tables within t
23ae0 68 65 20 6f 75 74 70 75 74 20 6f 66 20 73 71 6c  he output of sql
23af0 69 74 65 33 63 68 61 6e 67 65 67 72 6f 75 70 5f  ite3changegroup_
23b00 6f 75 74 70 75 74 28 29 20 61 72 65 20 69 6e 20  output() are in 
23b10 0a 20 20 20 20 20 20 20 20 2a 2a 20 74 68 65 20  .        ** the 
23b20 72 69 67 68 74 20 6f 72 64 65 72 2e 20 20 2a 2f  right order.  */
23b30 0a 20 20 20 20 20 20 20 20 66 6f 72 28 70 70 54  .        for(ppT
23b40 61 62 3d 26 70 47 72 70 2d 3e 70 4c 69 73 74 3b  ab=&pGrp->pList;
23b50 20 2a 70 70 54 61 62 3b 20 70 70 54 61 62 3d 26   *ppTab; ppTab=&
23b60 28 2a 70 70 54 61 62 29 2d 3e 70 4e 65 78 74 29  (*ppTab)->pNext)
23b70 3b 0a 20 20 20 20 20 20 20 20 2a 70 70 54 61 62  ;.        *ppTab
23b80 20 3d 20 70 54 61 62 3b 0a 20 20 20 20 20 20 7d   = pTab;.      }
23b90 65 6c 73 65 20 69 66 28 20 70 54 61 62 2d 3e 6e  else if( pTab->n
23ba0 43 6f 6c 21 3d 6e 43 6f 6c 20 7c 7c 20 6d 65 6d  Col!=nCol || mem
23bb0 63 6d 70 28 70 54 61 62 2d 3e 61 62 50 4b 2c 20  cmp(pTab->abPK, 
23bc0 61 62 50 4b 2c 20 6e 43 6f 6c 29 20 29 7b 0a 20  abPK, nCol) ){. 
23bd0 20 20 20 20 20 20 20 72 63 20 3d 20 53 51 4c 49         rc = SQLI
23be0 54 45 5f 53 43 48 45 4d 41 3b 0a 20 20 20 20 20  TE_SCHEMA;.     
23bf0 20 20 20 62 72 65 61 6b 3b 0a 20 20 20 20 20 20     break;.      
23c00 7d 0a 20 20 20 20 7d 0a 0a 20 20 20 20 69 66 28  }.    }..    if(
23c10 20 73 65 73 73 69 6f 6e 47 72 6f 77 48 61 73 68   sessionGrowHash
23c20 28 70 49 74 65 72 2d 3e 62 50 61 74 63 68 73 65  (pIter->bPatchse
23c30 74 2c 20 70 54 61 62 29 20 29 7b 0a 20 20 20 20  t, pTab) ){.    
23c40 20 20 72 63 20 3d 20 53 51 4c 49 54 45 5f 4e 4f    rc = SQLITE_NO
23c50 4d 45 4d 3b 0a 20 20 20 20 20 20 62 72 65 61 6b  MEM;.      break
23c60 3b 0a 20 20 20 20 7d 0a 20 20 20 20 69 48 61 73  ;.    }.    iHas
23c70 68 20 3d 20 73 65 73 73 69 6f 6e 43 68 61 6e 67  h = sessionChang
23c80 65 48 61 73 68 28 0a 20 20 20 20 20 20 20 20 70  eHash(.        p
23c90 54 61 62 2c 20 28 70 49 74 65 72 2d 3e 62 50 61  Tab, (pIter->bPa
23ca0 74 63 68 73 65 74 20 26 26 20 6f 70 3d 3d 53 51  tchset && op==SQ
23cb0 4c 49 54 45 5f 44 45 4c 45 54 45 29 2c 20 61 52  LITE_DELETE), aR
23cc0 65 63 2c 20 70 54 61 62 2d 3e 6e 43 68 61 6e 67  ec, pTab->nChang
23cd0 65 0a 20 20 20 20 29 3b 0a 0a 20 20 20 20 2f 2a  e.    );..    /*
23ce0 20 53 65 61 72 63 68 20 66 6f 72 20 65 78 69 73   Search for exis
23cf0 74 69 6e 67 20 65 6e 74 72 79 2e 20 49 66 20 66  ting entry. If f
23d00 6f 75 6e 64 2c 20 72 65 6d 6f 76 65 20 69 74 20  ound, remove it 
23d10 66 72 6f 6d 20 74 68 65 20 68 61 73 68 20 74 61  from the hash ta
23d20 62 6c 65 2e 20 0a 20 20 20 20 2a 2a 20 43 6f 64  ble. .    ** Cod
23d30 65 20 62 65 6c 6f 77 20 6d 61 79 20 6c 69 6e 6b  e below may link
23d40 20 69 74 20 62 61 63 6b 20 69 6e 2e 0a 20 20 20   it back in..   
23d50 20 2a 2f 0a 20 20 20 20 66 6f 72 28 70 70 3d 26   */.    for(pp=&
23d60 70 54 61 62 2d 3e 61 70 43 68 61 6e 67 65 5b 69  pTab->apChange[i
23d70 48 61 73 68 5d 3b 20 2a 70 70 3b 20 70 70 3d 26  Hash]; *pp; pp=&
23d80 28 2a 70 70 29 2d 3e 70 4e 65 78 74 29 7b 0a 20  (*pp)->pNext){. 
23d90 20 20 20 20 20 69 6e 74 20 62 50 6b 4f 6e 6c 79       int bPkOnly
23da0 31 20 3d 20 30 3b 0a 20 20 20 20 20 20 69 6e 74  1 = 0;.      int
23db0 20 62 50 6b 4f 6e 6c 79 32 20 3d 20 30 3b 0a 20   bPkOnly2 = 0;. 
23dc0 20 20 20 20 20 69 66 28 20 70 49 74 65 72 2d 3e       if( pIter->
23dd0 62 50 61 74 63 68 73 65 74 20 29 7b 0a 20 20 20  bPatchset ){.   
23de0 20 20 20 20 20 62 50 6b 4f 6e 6c 79 31 20 3d 20       bPkOnly1 = 
23df0 28 2a 70 70 29 2d 3e 6f 70 3d 3d 53 51 4c 49 54  (*pp)->op==SQLIT
23e00 45 5f 44 45 4c 45 54 45 3b 0a 20 20 20 20 20 20  E_DELETE;.      
23e10 20 20 62 50 6b 4f 6e 6c 79 32 20 3d 20 6f 70 3d    bPkOnly2 = op=
23e20 3d 53 51 4c 49 54 45 5f 44 45 4c 45 54 45 3b 0a  =SQLITE_DELETE;.
23e30 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 69 66        }.      if
23e40 28 20 73 65 73 73 69 6f 6e 43 68 61 6e 67 65 45  ( sessionChangeE
23e50 71 75 61 6c 28 70 54 61 62 2c 20 62 50 6b 4f 6e  qual(pTab, bPkOn
23e60 6c 79 31 2c 20 28 2a 70 70 29 2d 3e 61 52 65 63  ly1, (*pp)->aRec
23e70 6f 72 64 2c 20 62 50 6b 4f 6e 6c 79 32 2c 20 61  ord, bPkOnly2, a
23e80 52 65 63 29 20 29 7b 0a 20 20 20 20 20 20 20 20  Rec) ){.        
23e90 70 45 78 69 73 74 20 3d 20 2a 70 70 3b 0a 20 20  pExist = *pp;.  
23ea0 20 20 20 20 20 20 2a 70 70 20 3d 20 28 2a 70 70        *pp = (*pp
23eb0 29 2d 3e 70 4e 65 78 74 3b 0a 20 20 20 20 20 20  )->pNext;.      
23ec0 20 20 70 54 61 62 2d 3e 6e 45 6e 74 72 79 2d 2d    pTab->nEntry--
23ed0 3b 0a 20 20 20 20 20 20 20 20 62 72 65 61 6b 3b  ;.        break;
23ee0 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 7d 0a 0a  .      }.    }..
23ef0 20 20 20 20 72 63 20 3d 20 73 65 73 73 69 6f 6e      rc = session
23f00 43 68 61 6e 67 65 4d 65 72 67 65 28 70 54 61 62  ChangeMerge(pTab
23f10 2c 20 0a 20 20 20 20 20 20 20 20 70 49 74 65 72  , .        pIter
23f20 2d 3e 62 50 61 74 63 68 73 65 74 2c 20 70 45 78  ->bPatchset, pEx
23f30 69 73 74 2c 20 6f 70 2c 20 62 49 6e 64 69 72 65  ist, op, bIndire
23f40 63 74 2c 20 61 52 65 63 2c 20 6e 52 65 63 2c 20  ct, aRec, nRec, 
23f50 26 70 43 68 61 6e 67 65 0a 20 20 20 20 29 3b 0a  &pChange.    );.
23f60 20 20 20 20 69 66 28 20 72 63 20 29 20 62 72 65      if( rc ) bre
23f70 61 6b 3b 0a 20 20 20 20 69 66 28 20 70 43 68 61  ak;.    if( pCha
23f80 6e 67 65 20 29 7b 0a 20 20 20 20 20 20 70 43 68  nge ){.      pCh
23f90 61 6e 67 65 2d 3e 70 4e 65 78 74 20 3d 20 70 54  ange->pNext = pT
23fa0 61 62 2d 3e 61 70 43 68 61 6e 67 65 5b 69 48 61  ab->apChange[iHa
23fb0 73 68 5d 3b 0a 20 20 20 20 20 20 70 54 61 62 2d  sh];.      pTab-
23fc0 3e 61 70 43 68 61 6e 67 65 5b 69 48 61 73 68 5d  >apChange[iHash]
23fd0 20 3d 20 70 43 68 61 6e 67 65 3b 0a 20 20 20 20   = pChange;.    
23fe0 20 20 70 54 61 62 2d 3e 6e 45 6e 74 72 79 2b 2b    pTab->nEntry++
23ff0 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a 0a 20 20 69  ;.    }.  }..  i
24000 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b  f( rc==SQLITE_OK
24010 20 29 20 72 63 20 3d 20 70 49 74 65 72 2d 3e 72   ) rc = pIter->r
24020 63 3b 0a 20 20 72 65 74 75 72 6e 20 72 63 3b 0a  c;.  return rc;.
24030 7d 0a 0a 2f 2a 0a 2a 2a 20 53 65 72 69 61 6c 69  }../*.** Seriali
24040 7a 65 20 61 20 63 68 61 6e 67 65 73 65 74 20 28  ze a changeset (
24050 6f 72 20 70 61 74 63 68 73 65 74 29 20 62 61 73  or patchset) bas
24060 65 64 20 6f 6e 20 61 6c 6c 20 63 68 61 6e 67 65  ed on all change
24070 73 65 74 73 20 28 6f 72 20 70 61 74 63 68 73 65  sets (or patchse
24080 74 73 29 0a 2a 2a 20 61 64 64 65 64 20 74 6f 20  ts).** added to 
24090 74 68 65 20 63 68 61 6e 67 65 67 72 6f 75 70 20  the changegroup 
240a0 6f 62 6a 65 63 74 20 70 61 73 73 65 64 20 61 73  object passed as
240b0 20 74 68 65 20 66 69 72 73 74 20 61 72 67 75 6d   the first argum
240c0 65 6e 74 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 78 4f  ent..**.** If xO
240d0 75 74 70 75 74 20 69 73 20 6e 6f 74 20 4e 55 4c  utput is not NUL
240e0 4c 2c 20 74 68 65 6e 20 74 68 65 20 63 68 61 6e  L, then the chan
240f0 67 65 73 65 74 2f 70 61 74 63 68 73 65 74 20 69  geset/patchset i
24100 73 20 72 65 74 75 72 6e 65 64 20 74 6f 20 74 68  s returned to th
24110 65 0a 2a 2a 20 75 73 65 72 20 76 69 61 20 6f 6e  e.** user via on
24120 65 20 6f 72 20 6d 6f 72 65 20 63 61 6c 6c 73 20  e or more calls 
24130 74 6f 20 78 4f 75 74 70 75 74 2c 20 61 73 20 77  to xOutput, as w
24140 69 74 68 20 74 68 65 20 6f 74 68 65 72 20 73 74  ith the other st
24150 72 65 61 6d 69 6e 67 0a 2a 2a 20 69 6e 74 65 72  reaming.** inter
24160 66 61 63 65 73 2e 20 0a 2a 2a 0a 2a 2a 20 4f 72  faces. .**.** Or
24170 2c 20 69 66 20 78 4f 75 74 70 75 74 20 69 73 20  , if xOutput is 
24180 4e 55 4c 4c 2c 20 74 68 65 6e 20 28 2a 70 70 4f  NULL, then (*ppO
24190 75 74 29 20 69 73 20 70 6f 70 75 6c 61 74 65 64  ut) is populated
241a0 20 77 69 74 68 20 61 20 70 6f 69 6e 74 65 72 20   with a pointer 
241b0 74 6f 20 61 0a 2a 2a 20 62 75 66 66 65 72 20 63  to a.** buffer c
241c0 6f 6e 74 61 69 6e 69 6e 67 20 74 68 65 20 6f 75  ontaining the ou
241d0 74 70 75 74 20 63 68 61 6e 67 65 73 65 74 20 62  tput changeset b
241e0 65 66 6f 72 65 20 74 68 69 73 20 66 75 6e 63 74  efore this funct
241f0 69 6f 6e 20 72 65 74 75 72 6e 73 2e 20 49 6e 0a  ion returns. In.
24200 2a 2a 20 74 68 69 73 20 63 61 73 65 20 28 2a 70  ** this case (*p
24210 6e 4f 75 74 29 20 69 73 20 73 65 74 20 74 6f 20  nOut) is set to 
24220 74 68 65 20 73 69 7a 65 20 6f 66 20 74 68 65 20  the size of the 
24230 6f 75 74 70 75 74 20 62 75 66 66 65 72 20 69 6e  output buffer in
24240 20 62 79 74 65 73 2e 20 49 74 0a 2a 2a 20 69 73   bytes. It.** is
24250 20 74 68 65 20 72 65 73 70 6f 6e 73 69 62 69 6c   the responsibil
24260 69 74 79 20 6f 66 20 74 68 65 20 63 61 6c 6c 65  ity of the calle
24270 72 20 74 6f 20 66 72 65 65 20 74 68 65 20 6f 75  r to free the ou
24280 74 70 75 74 20 62 75 66 66 65 72 20 75 73 69 6e  tput buffer usin
24290 67 0a 2a 2a 20 73 71 6c 69 74 65 33 5f 66 72 65  g.** sqlite3_fre
242a0 65 28 29 20 77 68 65 6e 20 69 74 20 69 73 20 6e  e() when it is n
242b0 6f 20 6c 6f 6e 67 65 72 20 72 65 71 75 69 72 65  o longer require
242c0 64 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 73 75 63 63  d..**.** If succ
242d0 65 73 73 66 75 6c 2c 20 53 51 4c 49 54 45 5f 4f  essful, SQLITE_O
242e0 4b 20 69 73 20 72 65 74 75 72 6e 65 64 2e 20 4f  K is returned. O
242f0 72 2c 20 69 66 20 61 6e 20 65 72 72 6f 72 20 6f  r, if an error o
24300 63 63 75 72 73 2c 20 61 6e 20 53 51 4c 69 74 65  ccurs, an SQLite
24310 0a 2a 2a 20 65 72 72 6f 72 20 63 6f 64 65 2e 20  .** error code. 
24320 49 66 20 61 6e 20 65 72 72 6f 72 20 6f 63 63 75  If an error occu
24330 72 73 20 61 6e 64 20 78 4f 75 74 70 75 74 20 69  rs and xOutput i
24340 73 20 4e 55 4c 4c 2c 20 28 2a 70 70 4f 75 74 29  s NULL, (*ppOut)
24350 20 61 6e 64 20 28 2a 70 6e 4f 75 74 29 0a 2a 2a   and (*pnOut).**
24360 20 61 72 65 20 62 6f 74 68 20 73 65 74 20 74 6f   are both set to
24370 20 30 20 62 65 66 6f 72 65 20 72 65 74 75 72 6e   0 before return
24380 69 6e 67 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69  ing..*/.static i
24390 6e 74 20 73 65 73 73 69 6f 6e 43 68 61 6e 67 65  nt sessionChange
243a0 67 72 6f 75 70 4f 75 74 70 75 74 28 0a 20 20 73  groupOutput(.  s
243b0 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 67 72 6f  qlite3_changegro
243c0 75 70 20 2a 70 47 72 70 2c 0a 20 20 69 6e 74 20  up *pGrp,.  int 
243d0 28 2a 78 4f 75 74 70 75 74 29 28 76 6f 69 64 20  (*xOutput)(void 
243e0 2a 70 4f 75 74 2c 20 63 6f 6e 73 74 20 76 6f 69  *pOut, const voi
243f0 64 20 2a 70 44 61 74 61 2c 20 69 6e 74 20 6e 44  d *pData, int nD
24400 61 74 61 29 2c 0a 20 20 76 6f 69 64 20 2a 70 4f  ata),.  void *pO
24410 75 74 2c 0a 20 20 69 6e 74 20 2a 70 6e 4f 75 74  ut,.  int *pnOut
24420 2c 0a 20 20 76 6f 69 64 20 2a 2a 70 70 4f 75 74  ,.  void **ppOut
24430 0a 29 7b 0a 20 20 69 6e 74 20 72 63 20 3d 20 53  .){.  int rc = S
24440 51 4c 49 54 45 5f 4f 4b 3b 0a 20 20 53 65 73 73  QLITE_OK;.  Sess
24450 69 6f 6e 42 75 66 66 65 72 20 62 75 66 20 3d 20  ionBuffer buf = 
24460 7b 30 2c 20 30 2c 20 30 7d 3b 0a 20 20 53 65 73  {0, 0, 0};.  Ses
24470 73 69 6f 6e 54 61 62 6c 65 20 2a 70 54 61 62 3b  sionTable *pTab;
24480 0a 20 20 61 73 73 65 72 74 28 20 78 4f 75 74 70  .  assert( xOutp
24490 75 74 3d 3d 30 20 7c 7c 20 28 70 70 4f 75 74 3d  ut==0 || (ppOut=
244a0 3d 30 20 26 26 20 70 6e 4f 75 74 3d 3d 30 29 20  =0 && pnOut==0) 
244b0 29 3b 0a 0a 20 20 2f 2a 20 43 72 65 61 74 65 20  );..  /* Create 
244c0 74 68 65 20 73 65 72 69 61 6c 69 7a 65 64 20 6f  the serialized o
244d0 75 74 70 75 74 20 63 68 61 6e 67 65 73 65 74 20  utput changeset 
244e0 62 61 73 65 64 20 6f 6e 20 74 68 65 20 63 6f 6e  based on the con
244f0 74 65 6e 74 73 20 6f 66 20 74 68 65 0a 20 20 2a  tents of the.  *
24500 2a 20 68 61 73 68 20 74 61 62 6c 65 73 20 61 74  * hash tables at
24510 74 61 63 68 65 64 20 74 6f 20 74 68 65 20 53 65  tached to the Se
24520 73 73 69 6f 6e 54 61 62 6c 65 20 6f 62 6a 65 63  ssionTable objec
24530 74 73 20 69 6e 20 6c 69 73 74 20 70 2d 3e 70 4c  ts in list p->pL
24540 69 73 74 2e 20 0a 20 20 2a 2f 0a 20 20 66 6f 72  ist. .  */.  for
24550 28 70 54 61 62 3d 70 47 72 70 2d 3e 70 4c 69 73  (pTab=pGrp->pLis
24560 74 3b 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b  t; rc==SQLITE_OK
24570 20 26 26 20 70 54 61 62 3b 20 70 54 61 62 3d 70   && pTab; pTab=p
24580 54 61 62 2d 3e 70 4e 65 78 74 29 7b 0a 20 20 20  Tab->pNext){.   
24590 20 69 6e 74 20 69 3b 0a 20 20 20 20 69 66 28 20   int i;.    if( 
245a0 70 54 61 62 2d 3e 6e 45 6e 74 72 79 3d 3d 30 20  pTab->nEntry==0 
245b0 29 20 63 6f 6e 74 69 6e 75 65 3b 0a 0a 20 20 20  ) continue;..   
245c0 20 73 65 73 73 69 6f 6e 41 70 70 65 6e 64 54 61   sessionAppendTa
245d0 62 6c 65 48 64 72 28 26 62 75 66 2c 20 70 47 72  bleHdr(&buf, pGr
245e0 70 2d 3e 62 50 61 74 63 68 2c 20 70 54 61 62 2c  p->bPatch, pTab,
245f0 20 26 72 63 29 3b 0a 20 20 20 20 66 6f 72 28 69   &rc);.    for(i
24600 3d 30 3b 20 69 3c 70 54 61 62 2d 3e 6e 43 68 61  =0; i<pTab->nCha
24610 6e 67 65 3b 20 69 2b 2b 29 7b 0a 20 20 20 20 20  nge; i++){.     
24620 20 53 65 73 73 69 6f 6e 43 68 61 6e 67 65 20 2a   SessionChange *
24630 70 3b 0a 20 20 20 20 20 20 66 6f 72 28 70 3d 70  p;.      for(p=p
24640 54 61 62 2d 3e 61 70 43 68 61 6e 67 65 5b 69 5d  Tab->apChange[i]
24650 3b 20 70 3b 20 70 3d 70 2d 3e 70 4e 65 78 74 29  ; p; p=p->pNext)
24660 7b 0a 20 20 20 20 20 20 20 20 73 65 73 73 69 6f  {.        sessio
24670 6e 41 70 70 65 6e 64 42 79 74 65 28 26 62 75 66  nAppendByte(&buf
24680 2c 20 70 2d 3e 6f 70 2c 20 26 72 63 29 3b 0a 20  , p->op, &rc);. 
24690 20 20 20 20 20 20 20 73 65 73 73 69 6f 6e 41 70         sessionAp
246a0 70 65 6e 64 42 79 74 65 28 26 62 75 66 2c 20 70  pendByte(&buf, p
246b0 2d 3e 62 49 6e 64 69 72 65 63 74 2c 20 26 72 63  ->bIndirect, &rc
246c0 29 3b 0a 20 20 20 20 20 20 20 20 73 65 73 73 69  );.        sessi
246d0 6f 6e 41 70 70 65 6e 64 42 6c 6f 62 28 26 62 75  onAppendBlob(&bu
246e0 66 2c 20 70 2d 3e 61 52 65 63 6f 72 64 2c 20 70  f, p->aRecord, p
246f0 2d 3e 6e 52 65 63 6f 72 64 2c 20 26 72 63 29 3b  ->nRecord, &rc);
24700 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 7d 0a 0a  .      }.    }..
24710 20 20 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49      if( rc==SQLI
24720 54 45 5f 4f 4b 20 26 26 20 78 4f 75 74 70 75 74  TE_OK && xOutput
24730 20 26 26 20 62 75 66 2e 6e 42 75 66 3e 3d 53 45   && buf.nBuf>=SE
24740 53 53 49 4f 4e 53 5f 53 54 52 4d 5f 43 48 55 4e  SSIONS_STRM_CHUN
24750 4b 5f 53 49 5a 45 20 29 7b 0a 20 20 20 20 20 20  K_SIZE ){.      
24760 72 63 20 3d 20 78 4f 75 74 70 75 74 28 70 4f 75  rc = xOutput(pOu
24770 74 2c 20 62 75 66 2e 61 42 75 66 2c 20 62 75 66  t, buf.aBuf, buf
24780 2e 6e 42 75 66 29 3b 0a 20 20 20 20 20 20 62 75  .nBuf);.      bu
24790 66 2e 6e 42 75 66 20 3d 20 30 3b 0a 20 20 20 20  f.nBuf = 0;.    
247a0 7d 0a 20 20 7d 0a 0a 20 20 69 66 28 20 72 63 3d  }.  }..  if( rc=
247b0 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20  =SQLITE_OK ){.  
247c0 20 20 69 66 28 20 78 4f 75 74 70 75 74 20 29 7b    if( xOutput ){
247d0 0a 20 20 20 20 20 20 69 66 28 20 62 75 66 2e 6e  .      if( buf.n
247e0 42 75 66 3e 30 20 29 20 72 63 20 3d 20 78 4f 75  Buf>0 ) rc = xOu
247f0 74 70 75 74 28 70 4f 75 74 2c 20 62 75 66 2e 61  tput(pOut, buf.a
24800 42 75 66 2c 20 62 75 66 2e 6e 42 75 66 29 3b 0a  Buf, buf.nBuf);.
24810 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20      }else{.     
24820 20 2a 70 70 4f 75 74 20 3d 20 62 75 66 2e 61 42   *ppOut = buf.aB
24830 75 66 3b 0a 20 20 20 20 20 20 2a 70 6e 4f 75 74  uf;.      *pnOut
24840 20 3d 20 62 75 66 2e 6e 42 75 66 3b 0a 20 20 20   = buf.nBuf;.   
24850 20 20 20 62 75 66 2e 61 42 75 66 20 3d 20 30 3b     buf.aBuf = 0;
24860 0a 20 20 20 20 7d 0a 20 20 7d 0a 20 20 73 71 6c  .    }.  }.  sql
24870 69 74 65 33 5f 66 72 65 65 28 62 75 66 2e 61 42  ite3_free(buf.aB
24880 75 66 29 3b 0a 0a 20 20 72 65 74 75 72 6e 20 72  uf);..  return r
24890 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 41 6c 6c 6f  c;.}../*.** Allo
248a0 63 61 74 65 20 61 20 6e 65 77 2c 20 65 6d 70 74  cate a new, empt
248b0 79 2c 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67  y, sqlite3_chang
248c0 65 67 72 6f 75 70 2e 0a 2a 2f 0a 69 6e 74 20 73  egroup..*/.int s
248d0 71 6c 69 74 65 33 63 68 61 6e 67 65 67 72 6f 75  qlite3changegrou
248e0 70 5f 6e 65 77 28 73 71 6c 69 74 65 33 5f 63 68  p_new(sqlite3_ch
248f0 61 6e 67 65 67 72 6f 75 70 20 2a 2a 70 70 29 7b  angegroup **pp){
24900 0a 20 20 69 6e 74 20 72 63 20 3d 20 53 51 4c 49  .  int rc = SQLI
24910 54 45 5f 4f 4b 3b 20 20 20 20 20 20 20 20 20 20  TE_OK;          
24920 20 20 20 2f 2a 20 52 65 74 75 72 6e 20 63 6f 64     /* Return cod
24930 65 20 2a 2f 0a 20 20 73 71 6c 69 74 65 33 5f 63  e */.  sqlite3_c
24940 68 61 6e 67 65 67 72 6f 75 70 20 2a 70 3b 20 20  hangegroup *p;  
24950 20 20 20 20 20 20 20 2f 2a 20 4e 65 77 20 6f 62         /* New ob
24960 6a 65 63 74 20 2a 2f 0a 20 20 70 20 3d 20 28 73  ject */.  p = (s
24970 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 67 72 6f  qlite3_changegro
24980 75 70 2a 29 73 71 6c 69 74 65 33 5f 6d 61 6c 6c  up*)sqlite3_mall
24990 6f 63 28 73 69 7a 65 6f 66 28 73 71 6c 69 74 65  oc(sizeof(sqlite
249a0 33 5f 63 68 61 6e 67 65 67 72 6f 75 70 29 29 3b  3_changegroup));
249b0 0a 20 20 69 66 28 20 70 3d 3d 30 20 29 7b 0a 20  .  if( p==0 ){. 
249c0 20 20 20 72 63 20 3d 20 53 51 4c 49 54 45 5f 4e     rc = SQLITE_N
249d0 4f 4d 45 4d 3b 0a 20 20 7d 65 6c 73 65 7b 0a 20  OMEM;.  }else{. 
249e0 20 20 20 6d 65 6d 73 65 74 28 70 2c 20 30 2c 20     memset(p, 0, 
249f0 73 69 7a 65 6f 66 28 73 71 6c 69 74 65 33 5f 63  sizeof(sqlite3_c
24a00 68 61 6e 67 65 67 72 6f 75 70 29 29 3b 0a 20 20  hangegroup));.  
24a10 7d 0a 20 20 2a 70 70 20 3d 20 70 3b 0a 20 20 72  }.  *pp = p;.  r
24a20 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a  eturn rc;.}../*.
24a30 2a 2a 20 41 64 64 20 74 68 65 20 63 68 61 6e 67  ** Add the chang
24a40 65 73 65 74 20 63 75 72 72 65 6e 74 6c 79 20 73  eset currently s
24a50 74 6f 72 65 64 20 69 6e 20 62 75 66 66 65 72 20  tored in buffer 
24a60 70 44 61 74 61 2c 20 73 69 7a 65 20 6e 44 61 74  pData, size nDat
24a70 61 20 62 79 74 65 73 2c 0a 2a 2a 20 74 6f 20 63  a bytes,.** to c
24a80 68 61 6e 67 65 73 65 74 2d 67 72 6f 75 70 20 70  hangeset-group p
24a90 2e 0a 2a 2f 0a 69 6e 74 20 73 71 6c 69 74 65 33  ..*/.int sqlite3
24aa0 63 68 61 6e 67 65 67 72 6f 75 70 5f 61 64 64 28  changegroup_add(
24ab0 73 71 6c 69 74 65 33 5f 63 68 61 6e 67 65 67 72  sqlite3_changegr
24ac0 6f 75 70 20 2a 70 47 72 70 2c 20 69 6e 74 20 6e  oup *pGrp, int n
24ad0 44 61 74 61 2c 20 76 6f 69 64 20 2a 70 44 61 74  Data, void *pDat
24ae0 61 29 7b 0a 20 20 73 71 6c 69 74 65 33 5f 63 68  a){.  sqlite3_ch
24af0 61 6e 67 65 73 65 74 5f 69 74 65 72 20 2a 70 49  angeset_iter *pI
24b00 74 65 72 3b 20 20 2f 2a 20 49 74 65 72 61 74 6f  ter;  /* Iterato
24b10 72 20 6f 70 65 6e 65 64 20 6f 6e 20 70 44 61 74  r opened on pDat
24b20 61 2f 6e 44 61 74 61 20 2a 2f 0a 20 20 69 6e 74  a/nData */.  int
24b30 20 72 63 3b 20 20 20 20 20 20 20 20 20 20 20 20   rc;            
24b40 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
24b50 52 65 74 75 72 6e 20 63 6f 64 65 20 2a 2f 0a 0a  Return code */..
24b60 20 20 72 63 20 3d 20 73 71 6c 69 74 65 33 63 68    rc = sqlite3ch
24b70 61 6e 67 65 73 65 74 5f 73 74 61 72 74 28 26 70  angeset_start(&p
24b80 49 74 65 72 2c 20 6e 44 61 74 61 2c 20 70 44 61  Iter, nData, pDa
24b90 74 61 29 3b 0a 20 20 69 66 28 20 72 63 3d 3d 53  ta);.  if( rc==S
24ba0 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20  QLITE_OK ){.    
24bb0 72 63 20 3d 20 73 65 73 73 69 6f 6e 43 68 61 6e  rc = sessionChan
24bc0 67 65 73 65 74 54 6f 48 61 73 68 28 70 49 74 65  gesetToHash(pIte
24bd0 72 2c 20 70 47 72 70 29 3b 0a 20 20 7d 0a 20 20  r, pGrp);.  }.  
24be0 73 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74  sqlite3changeset
24bf0 5f 66 69 6e 61 6c 69 7a 65 28 70 49 74 65 72 29  _finalize(pIter)
24c00 3b 0a 20 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d  ;.  return rc;.}
24c10 0a 0a 2f 2a 0a 2a 2a 20 4f 62 74 61 69 6e 20 61  ../*.** Obtain a
24c20 20 62 75 66 66 65 72 20 63 6f 6e 74 61 69 6e 69   buffer containi
24c30 6e 67 20 61 20 63 68 61 6e 67 65 73 65 74 20 72  ng a changeset r
24c40 65 70 72 65 73 65 6e 74 69 6e 67 20 74 68 65 20  epresenting the 
24c50 63 6f 6e 63 61 74 65 6e 61 74 69 6f 6e 0a 2a 2a  concatenation.**
24c60 20 6f 66 20 61 6c 6c 20 63 68 61 6e 67 65 73 65   of all changese
24c70 74 73 20 61 64 64 65 64 20 74 6f 20 74 68 65 20  ts added to the 
24c80 67 72 6f 75 70 20 73 6f 20 66 61 72 2e 0a 2a 2f  group so far..*/
24c90 0a 69 6e 74 20 73 71 6c 69 74 65 33 63 68 61 6e  .int sqlite3chan
24ca0 67 65 67 72 6f 75 70 5f 6f 75 74 70 75 74 28 0a  gegroup_output(.
24cb0 20 20 20 20 73 71 6c 69 74 65 33 5f 63 68 61 6e      sqlite3_chan
24cc0 67 65 67 72 6f 75 70 20 2a 70 47 72 70 2c 0a 20  gegroup *pGrp,. 
24cd0 20 20 20 69 6e 74 20 2a 70 6e 44 61 74 61 2c 0a     int *pnData,.
24ce0 20 20 20 20 76 6f 69 64 20 2a 2a 70 70 44 61 74      void **ppDat
24cf0 61 0a 29 7b 0a 20 20 72 65 74 75 72 6e 20 73 65  a.){.  return se
24d00 73 73 69 6f 6e 43 68 61 6e 67 65 67 72 6f 75 70  ssionChangegroup
24d10 4f 75 74 70 75 74 28 70 47 72 70 2c 20 30 2c 20  Output(pGrp, 0, 
24d20 30 2c 20 70 6e 44 61 74 61 2c 20 70 70 44 61 74  0, pnData, ppDat
24d30 61 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 53 74 72  a);.}../*.** Str
24d40 65 61 6d 69 6e 67 20 76 65 72 73 69 6f 6e 73 20  eaming versions 
24d50 6f 66 20 63 68 61 6e 67 65 67 72 6f 75 70 5f 61  of changegroup_a
24d60 64 64 28 29 2e 0a 2a 2f 0a 69 6e 74 20 73 71 6c  dd()..*/.int sql
24d70 69 74 65 33 63 68 61 6e 67 65 67 72 6f 75 70 5f  ite3changegroup_
24d80 61 64 64 5f 73 74 72 6d 28 0a 20 20 73 71 6c 69  add_strm(.  sqli
24d90 74 65 33 5f 63 68 61 6e 67 65 67 72 6f 75 70 20  te3_changegroup 
24da0 2a 70 47 72 70 2c 0a 20 20 69 6e 74 20 28 2a 78  *pGrp,.  int (*x
24db0 49 6e 70 75 74 29 28 76 6f 69 64 20 2a 70 49 6e  Input)(void *pIn
24dc0 2c 20 76 6f 69 64 20 2a 70 44 61 74 61 2c 20 69  , void *pData, i
24dd0 6e 74 20 2a 70 6e 44 61 74 61 29 2c 0a 20 20 76  nt *pnData),.  v
24de0 6f 69 64 20 2a 70 49 6e 0a 29 7b 0a 20 20 73 71  oid *pIn.){.  sq
24df0 6c 69 74 65 33 5f 63 68 61 6e 67 65 73 65 74 5f  lite3_changeset_
24e00 69 74 65 72 20 2a 70 49 74 65 72 3b 20 20 2f 2a  iter *pIter;  /*
24e10 20 49 74 65 72 61 74 6f 72 20 6f 70 65 6e 65 64   Iterator opened
24e20 20 6f 6e 20 70 44 61 74 61 2f 6e 44 61 74 61 20   on pData/nData 
24e30 2a 2f 0a 20 20 69 6e 74 20 72 63 3b 20 20 20 20  */.  int rc;    
24e40 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
24e50 20 20 20 20 20 2f 2a 20 52 65 74 75 72 6e 20 63       /* Return c
24e60 6f 64 65 20 2a 2f 0a 0a 20 20 72 63 20 3d 20 73  ode */..  rc = s
24e70 71 6c 69 74 65 33 63 68 61 6e 67 65 73 65 74 5f  qlite3changeset_
24e80 73 74 61 72 74 5f 73 74 72 6d 28 26 70 49 74 65  start_strm(&pIte
24e90 72 2c 20 78 49 6e 70 75 74 2c 20 70 49 6e 29 3b  r, xInput, pIn);
24ea0 0a 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54  .  if( rc==SQLIT
24eb0 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 72 63 20 3d  E_OK ){.    rc =
24ec0 20 73 65 73 73 69 6f 6e 43 68 61 6e 67 65 73 65   sessionChangese
24ed0 74 54 6f 48 61 73 68 28 70 49 74 65 72 2c 20 70  tToHash(pIter, p
24ee0 47 72 70 29 3b 0a 20 20 7d 0a 20 20 73 71 6c 69  Grp);.  }.  sqli
24ef0 74 65 33 63 68 61 6e 67 65 73 65 74 5f 66 69 6e  te3changeset_fin
24f00 61 6c 69 7a 65 28 70 49 74 65 72 29 3b 0a 20 20  alize(pIter);.  
24f10 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a  return rc;.}../*
24f20 0a 2a 2a 20 53 74 72 65 61 6d 69 6e 67 20 76 65  .** Streaming ve
24f30 72 73 69 6f 6e 73 20 6f 66 20 63 68 61 6e 67 65  rsions of change
24f40 67 72 6f 75 70 5f 6f 75 74 70 75 74 28 29 2e 0a  group_output()..
24f50 2a 2f 0a 69 6e 74 20 73 71 6c 69 74 65 33 63 68  */.int sqlite3ch
24f60 61 6e 67 65 67 72 6f 75 70 5f 6f 75 74 70 75 74  angegroup_output
24f70 5f 73 74 72 6d 28 0a 20 20 73 71 6c 69 74 65 33  _strm(.  sqlite3
24f80 5f 63 68 61 6e 67 65 67 72 6f 75 70 20 2a 70 47  _changegroup *pG
24f90 72 70 2c 0a 20 20 69 6e 74 20 28 2a 78 4f 75 74  rp,.  int (*xOut
24fa0 70 75 74 29 28 76 6f 69 64 20 2a 70 4f 75 74 2c  put)(void *pOut,
24fb0 20 63 6f 6e 73 74 20 76 6f 69 64 20 2a 70 44 61   const void *pDa
24fc0 74 61 2c 20 69 6e 74 20 6e 44 61 74 61 29 2c 20  ta, int nData), 
24fd0 0a 20 20 76 6f 69 64 20 2a 70 4f 75 74 0a 29 7b  .  void *pOut.){
24fe0 0a 20 20 72 65 74 75 72 6e 20 73 65 73 73 69 6f  .  return sessio
24ff0 6e 43 68 61 6e 67 65 67 72 6f 75 70 4f 75 74 70  nChangegroupOutp
25000 75 74 28 70 47 72 70 2c 20 78 4f 75 74 70 75 74  ut(pGrp, xOutput
25010 2c 20 70 4f 75 74 2c 20 30 2c 20 30 29 3b 0a 7d  , pOut, 0, 0);.}
25020 0a 0a 2f 2a 0a 2a 2a 20 44 65 6c 65 74 65 20 61  ../*.** Delete a
25030 20 63 68 61 6e 67 65 67 72 6f 75 70 20 6f 62 6a   changegroup obj
25040 65 63 74 2e 0a 2a 2f 0a 76 6f 69 64 20 73 71 6c  ect..*/.void sql
25050 69 74 65 33 63 68 61 6e 67 65 67 72 6f 75 70 5f  ite3changegroup_
25060 64 65 6c 65 74 65 28 73 71 6c 69 74 65 33 5f 63  delete(sqlite3_c
25070 68 61 6e 67 65 67 72 6f 75 70 20 2a 70 47 72 70  hangegroup *pGrp
25080 29 7b 0a 20 20 69 66 28 20 70 47 72 70 20 29 7b  ){.  if( pGrp ){
25090 0a 20 20 20 20 73 65 73 73 69 6f 6e 44 65 6c 65  .    sessionDele
250a0 74 65 54 61 62 6c 65 28 70 47 72 70 2d 3e 70 4c  teTable(pGrp->pL
250b0 69 73 74 29 3b 0a 20 20 20 20 73 71 6c 69 74 65  ist);.    sqlite
250c0 33 5f 66 72 65 65 28 70 47 72 70 29 3b 0a 20 20  3_free(pGrp);.  
250d0 7d 0a 7d 0a 0a 2f 2a 20 0a 2a 2a 20 43 6f 6d 62  }.}../* .** Comb
250e0 69 6e 65 20 74 77 6f 20 63 68 61 6e 67 65 73 65  ine two changese
250f0 74 73 20 74 6f 67 65 74 68 65 72 2e 0a 2a 2f 0a  ts together..*/.
25100 69 6e 74 20 73 71 6c 69 74 65 33 63 68 61 6e 67  int sqlite3chang
25110 65 73 65 74 5f 63 6f 6e 63 61 74 28 0a 20 20 69  eset_concat(.  i
25120 6e 74 20 6e 4c 65 66 74 2c 20 20 20 20 20 20 20  nt nLeft,       
25130 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
25140 2a 20 4e 75 6d 62 65 72 20 6f 66 20 62 79 74 65  * Number of byte
25150 73 20 69 6e 20 6c 68 73 20 69 6e 70 75 74 20 2a  s in lhs input *
25160 2f 0a 20 20 76 6f 69 64 20 2a 70 4c 65 66 74 2c  /.  void *pLeft,
25170 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
25180 20 20 20 20 2f 2a 20 4c 68 73 20 69 6e 70 75 74      /* Lhs input
25190 20 63 68 61 6e 67 65 73 65 74 20 2a 2f 0a 20 20   changeset */.  
251a0 69 6e 74 20 6e 52 69 67 68 74 20 20 20 20 20 20  int nRight      
251b0 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
251c0 2f 2a 20 4e 75 6d 62 65 72 20 6f 66 20 62 79 74  /* Number of byt
251d0 65 73 20 69 6e 20 72 68 73 20 69 6e 70 75 74 20  es in rhs input 
251e0 2a 2f 2c 0a 20 20 76 6f 69 64 20 2a 70 52 69 67  */,.  void *pRig
251f0 68 74 2c 20 20 20 20 20 20 20 20 20 20 20 20 20  ht,             
25200 20 20 20 20 20 20 2f 2a 20 52 68 73 20 69 6e 70        /* Rhs inp
25210 75 74 20 63 68 61 6e 67 65 73 65 74 20 2a 2f 0a  ut changeset */.
25220 20 20 69 6e 74 20 2a 70 6e 4f 75 74 2c 20 20 20    int *pnOut,   
25230 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
25240 20 20 2f 2a 20 4f 55 54 3a 20 4e 75 6d 62 65 72    /* OUT: Number
25250 20 6f 66 20 62 79 74 65 73 20 69 6e 20 6f 75 74   of bytes in out
25260 70 75 74 20 63 68 61 6e 67 65 73 65 74 20 2a 2f  put changeset */
25270 0a 20 20 76 6f 69 64 20 2a 2a 70 70 4f 75 74 20  .  void **ppOut 
25280 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
25290 20 20 20 2f 2a 20 4f 55 54 3a 20 63 68 61 6e 67     /* OUT: chang
252a0 65 73 65 74 20 28 6c 65 66 74 20 3c 63 6f 6e 63  eset (left <conc
252b0 61 74 3e 20 72 69 67 68 74 29 20 2a 2f 0a 29 7b  at> right) */.){
252c0 0a 20 20 73 71 6c 69 74 65 33 5f 63 68 61 6e 67  .  sqlite3_chang
252d0 65 67 72 6f 75 70 20 2a 70 47 72 70 3b 0a 20 20  egroup *pGrp;.  
252e0 69 6e 74 20 72 63 3b 0a 0a 20 20 72 63 20 3d 20  int rc;..  rc = 
252f0 73 71 6c 69 74 65 33 63 68 61 6e 67 65 67 72 6f  sqlite3changegro
25300 75 70 5f 6e 65 77 28 26 70 47 72 70 29 3b 0a 20  up_new(&pGrp);. 
25310 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f   if( rc==SQLITE_
25320 4f 4b 20 29 7b 0a 20 20 20 20 72 63 20 3d 20 73  OK ){.    rc = s
25330 71 6c 69 74 65 33 63 68 61 6e 67 65 67 72 6f 75  qlite3changegrou
25340 70 5f 61 64 64 28 70 47 72 70 2c 20 6e 4c 65 66  p_add(pGrp, nLef
25350 74 2c 20 70 4c 65 66 74 29 3b 0a 20 20 7d 0a 20  t, pLeft);.  }. 
25360 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f   if( rc==SQLITE_
25370 4f 4b 20 29 7b 0a 20 20 20 20 72 63 20 3d 20 73  OK ){.    rc = s
25380 71 6c 69 74 65 33 63 68 61 6e 67 65 67 72 6f 75  qlite3changegrou
25390 70 5f 61 64 64 28 70 47 72 70 2c 20 6e 52 69 67  p_add(pGrp, nRig
253a0 68 74 2c 20 70 52 69 67 68 74 29 3b 0a 20 20 7d  ht, pRight);.  }
253b0 0a 20 20 69 66 28 20 72 63 3d 3d 53 51 4c 49 54  .  if( rc==SQLIT
253c0 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 72 63 20 3d  E_OK ){.    rc =
253d0 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65 67 72   sqlite3changegr
253e0 6f 75 70 5f 6f 75 74 70 75 74 28 70 47 72 70 2c  oup_output(pGrp,
253f0 20 70 6e 4f 75 74 2c 20 70 70 4f 75 74 29 3b 0a   pnOut, ppOut);.
25400 20 20 7d 0a 20 20 73 71 6c 69 74 65 33 63 68 61    }.  sqlite3cha
25410 6e 67 65 67 72 6f 75 70 5f 64 65 6c 65 74 65 28  ngegroup_delete(
25420 70 47 72 70 29 3b 0a 0a 20 20 72 65 74 75 72 6e  pGrp);..  return
25430 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 53 74   rc;.}../*.** St
25440 72 65 61 6d 69 6e 67 20 76 65 72 73 69 6f 6e 20  reaming version 
25450 6f 66 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65  of sqlite3change
25460 73 65 74 5f 63 6f 6e 63 61 74 28 29 2e 0a 2a 2f  set_concat()..*/
25470 0a 69 6e 74 20 73 71 6c 69 74 65 33 63 68 61 6e  .int sqlite3chan
25480 67 65 73 65 74 5f 63 6f 6e 63 61 74 5f 73 74 72  geset_concat_str
25490 6d 28 0a 20 20 69 6e 74 20 28 2a 78 49 6e 70 75  m(.  int (*xInpu
254a0 74 41 29 28 76 6f 69 64 20 2a 70 49 6e 2c 20 76  tA)(void *pIn, v
254b0 6f 69 64 20 2a 70 44 61 74 61 2c 20 69 6e 74 20  oid *pData, int 
254c0 2a 70 6e 44 61 74 61 29 2c 0a 20 20 76 6f 69 64  *pnData),.  void
254d0 20 2a 70 49 6e 41 2c 0a 20 20 69 6e 74 20 28 2a   *pInA,.  int (*
254e0 78 49 6e 70 75 74 42 29 28 76 6f 69 64 20 2a 70  xInputB)(void *p
254f0 49 6e 2c 20 76 6f 69 64 20 2a 70 44 61 74 61 2c  In, void *pData,
25500 20 69 6e 74 20 2a 70 6e 44 61 74 61 29 2c 0a 20   int *pnData),. 
25510 20 76 6f 69 64 20 2a 70 49 6e 42 2c 0a 20 20 69   void *pInB,.  i
25520 6e 74 20 28 2a 78 4f 75 74 70 75 74 29 28 76 6f  nt (*xOutput)(vo
25530 69 64 20 2a 70 4f 75 74 2c 20 63 6f 6e 73 74 20  id *pOut, const 
25540 76 6f 69 64 20 2a 70 44 61 74 61 2c 20 69 6e 74  void *pData, int
25550 20 6e 44 61 74 61 29 2c 0a 20 20 76 6f 69 64 20   nData),.  void 
25560 2a 70 4f 75 74 0a 29 7b 0a 20 20 73 71 6c 69 74  *pOut.){.  sqlit
25570 65 33 5f 63 68 61 6e 67 65 67 72 6f 75 70 20 2a  e3_changegroup *
25580 70 47 72 70 3b 0a 20 20 69 6e 74 20 72 63 3b 0a  pGrp;.  int rc;.
25590 0a 20 20 72 63 20 3d 20 73 71 6c 69 74 65 33 63  .  rc = sqlite3c
255a0 68 61 6e 67 65 67 72 6f 75 70 5f 6e 65 77 28 26  hangegroup_new(&
255b0 70 47 72 70 29 3b 0a 20 20 69 66 28 20 72 63 3d  pGrp);.  if( rc=
255c0 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20 20  =SQLITE_OK ){.  
255d0 20 20 72 63 20 3d 20 73 71 6c 69 74 65 33 63 68    rc = sqlite3ch
255e0 61 6e 67 65 67 72 6f 75 70 5f 61 64 64 5f 73 74  angegroup_add_st
255f0 72 6d 28 70 47 72 70 2c 20 78 49 6e 70 75 74 41  rm(pGrp, xInputA
25600 2c 20 70 49 6e 41 29 3b 0a 20 20 7d 0a 20 20 69  , pInA);.  }.  i
25610 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b  f( rc==SQLITE_OK
25620 20 29 7b 0a 20 20 20 20 72 63 20 3d 20 73 71 6c   ){.    rc = sql
25630 69 74 65 33 63 68 61 6e 67 65 67 72 6f 75 70 5f  ite3changegroup_
25640 61 64 64 5f 73 74 72 6d 28 70 47 72 70 2c 20 78  add_strm(pGrp, x
25650 49 6e 70 75 74 42 2c 20 70 49 6e 42 29 3b 0a 20  InputB, pInB);. 
25660 20 7d 0a 20 20 69 66 28 20 72 63 3d 3d 53 51 4c   }.  if( rc==SQL
25670 49 54 45 5f 4f 4b 20 29 7b 0a 20 20 20 20 72 63  ITE_OK ){.    rc
25680 20 3d 20 73 71 6c 69 74 65 33 63 68 61 6e 67 65   = sqlite3change
25690 67 72 6f 75 70 5f 6f 75 74 70 75 74 5f 73 74 72  group_output_str
256a0 6d 28 70 47 72 70 2c 20 78 4f 75 74 70 75 74 2c  m(pGrp, xOutput,
256b0 20 70 4f 75 74 29 3b 0a 20 20 7d 0a 20 20 73 71   pOut);.  }.  sq
256c0 6c 69 74 65 33 63 68 61 6e 67 65 67 72 6f 75 70  lite3changegroup
256d0 5f 64 65 6c 65 74 65 28 70 47 72 70 29 3b 0a 0a  _delete(pGrp);..
256e0 20 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a    return rc;.}..
256f0 23 65 6e 64 69 66 20 2f 2a 20 53 51 4c 49 54 45  #endif /* SQLITE
25700 5f 45 4e 41 42 4c 45 5f 53 45 53 53 49 4f 4e 20  _ENABLE_SESSION 
25710 26 26 20 53 51 4c 49 54 45 5f 45 4e 41 42 4c 45  && SQLITE_ENABLE
25720 5f 50 52 45 55 50 44 41 54 45 5f 48 4f 4f 4b 20  _PREUPDATE_HOOK 
25730 2a 2f 0a                                         */.