Fossil

Check-in [54dba74790]
Login

Check-in [54dba74790]

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

Overview
Comment:Merged in trunk and resolved numerous code clashes in /chat.
Downloads: Tarball | ZIP archive
Timelines: family | ancestors | descendants | both | markdown-tagrefs
Files: files | file ages | folders
SHA3-256: 54dba7479043bdbd47184f6e5950566617834d18e016dd9227b3c7bd53ebea86
User & Date: stephan 2021-12-16 04:20:53.731
Context
2021-12-31
02:59
Merged in trunk. ... (check-in: c800d2ca82 user: stephan tags: markdown-tagrefs)
2021-12-16
04:20
Merged in trunk and resolved numerous code clashes in /chat. ... (check-in: 54dba74790 user: stephan tags: markdown-tagrefs)
2021-12-14
14:49
Added help text doc for -k alias for --keep for the open command, per [forum:6f17cf142f80e2c3 | forum post 6f17cf142f80e2c3]. ... (check-in: 8fee91d408 user: stephan tags: trunk)
2021-10-06
02:38
Merge in trunk for test server deployment. ... (check-in: 664b04b280 user: stephan tags: markdown-tagrefs)
Changes
Unified Diff Ignore Whitespace Patch
Changes to VERSION.
1
2.17
|
1
2.18
Changes to auto.def.
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
    no-opt=0             => {Build without optimization}
    json=0               => {Build with fossil JSON API enabled}
}

# Update the minimum required SQLite version number here, and also
# in src/main.c near the sqlite3_libversion_number() call.  Take care
# that both places agree!
define MINIMUM_SQLITE_VERSION "3.35.0"

# This is useful for people wanting Fossil to use an external SQLite library
# to compare the one they have against the minimum required
if {[opt-bool print-minimum-sqlite-version]} {
    puts [get-define MINIMUM_SQLITE_VERSION]
    exit 0
}







|







30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
    no-opt=0             => {Build without optimization}
    json=0               => {Build with fossil JSON API enabled}
}

# Update the minimum required SQLite version number here, and also
# in src/main.c near the sqlite3_libversion_number() call.  Take care
# that both places agree!
define MINIMUM_SQLITE_VERSION "3.37.0"

# This is useful for people wanting Fossil to use an external SQLite library
# to compare the one they have against the minimum required
if {[opt-bool print-minimum-sqlite-version]} {
    puts [get-define MINIMUM_SQLITE_VERSION]
    exit 0
}
Changes to src/cgi.c.
2316
2317
2318
2319
2320
2321
2322
2323
2324
2325
2326










2327
2328
2329
2330
2331
2332
2333
  struct tm *pTm;
  time_t now = time(0);
  pTm = gmtime(&now);
  if( pTm==0 ){
    return mprintf("");
  }else{
    return mprintf("%04d-%02d-%02d %02d:%02d:%02d",
                   pTm->tm_year+1900, pTm->tm_mon, pTm->tm_mday,
                   pTm->tm_hour, pTm->tm_min, pTm->tm_sec);
  }
}











/*
** Parse an RFC822-formatted timestamp as we'd expect from HTTP and return
** a Unix epoch time. <= zero is returned on failure.
**
** Note that this won't handle all the _allowed_ HTTP formats, just the
** most popular one (the one generated by cgi_rfc822_datestamp(), actually).







|



>
>
>
>
>
>
>
>
>
>







2316
2317
2318
2319
2320
2321
2322
2323
2324
2325
2326
2327
2328
2329
2330
2331
2332
2333
2334
2335
2336
2337
2338
2339
2340
2341
2342
2343
  struct tm *pTm;
  time_t now = time(0);
  pTm = gmtime(&now);
  if( pTm==0 ){
    return mprintf("");
  }else{
    return mprintf("%04d-%02d-%02d %02d:%02d:%02d",
                   pTm->tm_year+1900, pTm->tm_mon+1, pTm->tm_mday,
                   pTm->tm_hour, pTm->tm_min, pTm->tm_sec);
  }
}

/*
** COMMAND: test-date
**
** Show the current date and time in both RFC822 and ISO8601.
*/
void test_date(void){
  fossil_print("%z = ", cgi_iso8601_datestamp());
  fossil_print("%z\n", cgi_rfc822_datestamp(time(0)));
}

/*
** Parse an RFC822-formatted timestamp as we'd expect from HTTP and return
** a Unix epoch time. <= zero is returned on failure.
**
** Note that this won't handle all the _allowed_ HTTP formats, just the
** most popular one (the one generated by cgi_rfc822_datestamp(), actually).
Changes to src/chat.c.
172
173
174
175
176
177
178
179








180
181
182
183
184
185
186
187
188
189
190
                db_get("chat-alert-sound","alerts/plunk.wav"));
  zProjectName = db_get("project-name","Unnamed project");
  zInputPlaceholder0 =
    mprintf("Type markdown-formatted message for %h.", zProjectName);
  style_set_current_feature("chat");
  style_header("Chat");
  @ <div id='chat-input-area'>
  @   <div id='chat-input-line' class='single-line'>








  @     <div contenteditable id="chat-input-field" \
  @      data-placeholder0="%h(zInputPlaceholder0)" \
  @      data-placeholder="%h(zInputPlaceholder0)" \
  @      class=""></div>
  @     <div id='chat-buttons-wrapper'>
  @       <span class='cbutton' id="chat-button-preview" \
  @         title="Preview message (Shift-Enter)">&#128065;</span>
  @       <span class='cbutton' id="chat-button-attach" \
  @         title="Attach file to message">%s(zPaperclip)</span>
  @       <span class='cbutton' id="chat-button-settings" \
  @         title="Configure chat">&#9881;</span>







|
>
>
>
>
>
>
>
>
|


|







172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
                db_get("chat-alert-sound","alerts/plunk.wav"));
  zProjectName = db_get("project-name","Unnamed project");
  zInputPlaceholder0 =
    mprintf("Type markdown-formatted message for %h.", zProjectName);
  style_set_current_feature("chat");
  style_header("Chat");
  @ <div id='chat-input-area'>
  @   <div id='chat-input-line-wrapper' class='compact'>
  @     <input type="text" id="chat-input-field-single" \
  @      data-placeholder0="%h(zInputPlaceholder0)" \
  @      data-placeholder="%h(zInputPlaceholder0)" \
  @      class="chat-input-field"></input>
  @     <textarea id="chat-input-field-multi" \
  @      data-placeholder0="%h(zInputPlaceholder0)" \
  @      data-placeholder="%h(zInputPlaceholder0)" \
  @      class="chat-input-field hidden"></textarea>
  @     <div contenteditable id="chat-input-field-x" \
  @      data-placeholder0="%h(zInputPlaceholder0)" \
  @      data-placeholder="%h(zInputPlaceholder0)" \
  @      class="chat-input-field hidden"></div>
  @     <div id='chat-buttons-wrapper'>
  @       <span class='cbutton' id="chat-button-preview" \
  @         title="Preview message (Shift-Enter)">&#128065;</span>
  @       <span class='cbutton' id="chat-button-attach" \
  @         title="Attach file to message">%s(zPaperclip)</span>
  @       <span class='cbutton' id="chat-button-settings" \
  @         title="Configure chat">&#9881;</span>
343
344
345
346
347
348
349












350
351
352
353
354
355
356
357
358
359
360
361
362
363
** to be entered into the chat history.
**
** On success it responds with an empty response: the new message
** should be fetched via /chat-poll. On error, e.g. login expiry,
** it emits a JSON response in the same form as described for
** /chat-poll errors, but as a standalone object instead of a
** list of objects.












*/
void chat_send_webpage(void){
  int nByte;
  const char *zMsg;
  const char *zUserName;
  login_check_credentials();
  if( !g.perm.Chat ) {
    chat_emit_permissions_error(0);
    return;
  }
  chat_create_tables();
  zUserName = (g.zLogin && g.zLogin[0]) ? g.zLogin : "nobody";
  nByte = atoi(PD("file:bytes","0"));
  zMsg = PD("msg","");







>
>
>
>
>
>
>
>
>
>
>
>






|







351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
** to be entered into the chat history.
**
** On success it responds with an empty response: the new message
** should be fetched via /chat-poll. On error, e.g. login expiry,
** it emits a JSON response in the same form as described for
** /chat-poll errors, but as a standalone object instead of a
** list of objects.
**
** Requests to this page should be POST, not GET.  POST parameters
** include:
**
**    msg        The (Markdown) text of the message to be sent
**
**    file       The content of the file attachment
**
**    lmtime     ISO-8601 formatted date-time string showing the local time
**               of the sender.
**
** At least one of the "msg" or "file" POST parameters must be provided.
*/
void chat_send_webpage(void){
  int nByte;
  const char *zMsg;
  const char *zUserName;
  login_check_credentials();
  if( 0==g.perm.Chat ) {
    chat_emit_permissions_error(0);
    return;
  }
  chat_create_tables();
  zUserName = (g.zLogin && g.zLogin[0]) ? g.zLogin : "nobody";
  nByte = atoi(PD("file:bytes","0"));
  zMsg = PD("msg","");
756
757
758
759
760
761
762

763

764
765
766
767
768
769
770
** Invoking fetch("chat-delete/"+msgid) from javascript in the client
** will delete a chat entry from the CHAT table.
**
** This routine both deletes the identified chat entry and also inserts
** a new entry with the current timestamp and with:
**
**   *  xmsg = NULL

**   *  file = NULL

**   *  mdel = The msgid of the row that was deleted
**
** This new entry will then be propagated to all listeners so that they
** will know to delete their copies of the message too.
*/
void chat_delete_webpage(void){
  int mdel;







>

>







776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
** Invoking fetch("chat-delete/"+msgid) from javascript in the client
** will delete a chat entry from the CHAT table.
**
** This routine both deletes the identified chat entry and also inserts
** a new entry with the current timestamp and with:
**
**   *  xmsg = NULL
**
**   *  file = NULL
**
**   *  mdel = The msgid of the row that was deleted
**
** This new entry will then be propagated to all listeners so that they
** will know to delete their copies of the message too.
*/
void chat_delete_webpage(void){
  int mdel;
795
796
797
798
799
800
801




802
803
804
805
806
807
808
809
810
811
812
813
814
815
816

817
818




819
820
821
822
823
824
825
** This command performs actions associated with the /chat instance
** on the default remote Fossil repository (the Fossil repository whose
** URL shows when you run the "fossil remote" command) or to the URL
** specified by the --remote option.  If there is no default remote
** Fossil repository and the --remote option is omitted, then this
** command fails with an error.
**




** When there is no SUBCOMMAND (when this command is simply "fossil chat")
** the response is to bring up a web-browser window to the chatroom
** on the default system web-browser.  You can accomplish the same by
** typing the appropriate URL into the web-browser yourself.  This
** command is merely a convenience for command-line oriented people.
**
** The following subcommands are supported:
**
** > fossil chat send [ARGUMENTS]
**
**      This command sends a new message to the chatroom.  The message
**      to be sent is determined by arguments as follows:
**
**        -f|--file FILENAME     File to attach to the message
**        -m|--message TEXT      Text of the chat message

**        --unsafe               Allow the use of unencrypted http://
**




** Additional subcommands may be added in the future.
*/
void chat_command(void){
  const char *zUrl = find_option("remote",0,1);
  int urlFlags = 0;
  int isDefaultUrl = 0;
  int i;







>
>
>
>
|
|
|
|
|
<
<








>


>
>
>
>







817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832


833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
** This command performs actions associated with the /chat instance
** on the default remote Fossil repository (the Fossil repository whose
** URL shows when you run the "fossil remote" command) or to the URL
** specified by the --remote option.  If there is no default remote
** Fossil repository and the --remote option is omitted, then this
** command fails with an error.
**
** Subcommands:
**
** > fossil chat
**
**      When there is no SUBCOMMAND (when this command is simply "fossil chat")
**      the response is to bring up a web-browser window to the chatroom
**      on the default system web-browser.  You can accomplish the same by
**      typing the appropriate URL into the web-browser yourself.  This
**      command is merely a convenience for command-line oriented people.


**
** > fossil chat send [ARGUMENTS]
**
**      This command sends a new message to the chatroom.  The message
**      to be sent is determined by arguments as follows:
**
**        -f|--file FILENAME     File to attach to the message
**        -m|--message TEXT      Text of the chat message
**        --remote URL           Send to this remote URL
**        --unsafe               Allow the use of unencrypted http://
**
** > fossil chat url
**
**      Show the default URL used to access the chat server.
**
** Additional subcommands may be added in the future.
*/
void chat_command(void){
  const char *zUrl = find_option("remote",0,1);
  int urlFlags = 0;
  int isDefaultUrl = 0;
  int i;
939
940
941
942
943
944
945
946
947
948
949
950
951
      }else{
        fossil_print("ERROR: %s\n", blob_str(&down));
      }
      fossil_fatal("unable to send the chat message");
    }
    blob_reset(&down);
  }else if( strcmp(g.argv[2],"url")==0 ){
    /* Undocumented command.  Show the URL to access chat. */
    fossil_print("%s/chat\n", zUrl);
  }else{
    fossil_fatal("no such subcommand \"%s\".  Use --help for help", g.argv[2]);
  }
}







|





968
969
970
971
972
973
974
975
976
977
978
979
980
      }else{
        fossil_print("ERROR: %s\n", blob_str(&down));
      }
      fossil_fatal("unable to send the chat message");
    }
    blob_reset(&down);
  }else if( strcmp(g.argv[2],"url")==0 ){
    /* Show the URL to access chat. */
    fossil_print("%s/chat\n", zUrl);
  }else{
    fossil_fatal("no such subcommand \"%s\".  Use --help for help", g.argv[2]);
  }
}
Changes to src/checkin.c.
1347
1348
1349
1350
1351
1352
1353

1354
1355
1356
1357
1358
1359
1360
1361
1362
1363
1364
1365
1366
1367
1368
1369
1370
1371
1372
1373
        '#'
    );
    diff_options(&DCfg, 0, 1);
    DCfg.diffFlags |= DIFF_VERBOSE;
    if( g.aCommitFile ){
      FileDirList *diffFiles;
      int i;

      diffFiles = fossil_malloc_zero((g.argc-1) * sizeof(*diffFiles));
      for( i=0; g.aCommitFile[i]!=0; ++i ){
        diffFiles[i].zName  = db_text(0,
         "SELECT pathname FROM vfile WHERE id=%d", g.aCommitFile[i]);
        if( fossil_strcmp(diffFiles[i].zName, "." )==0 ){
          diffFiles[0].zName[0] = '.';
          diffFiles[0].zName[1] = 0;
          break;
        }
        diffFiles[i].nName = strlen(diffFiles[i].zName);
        diffFiles[i].nUsed = 0;
      }
       diff_against_disk(0, &DCfg, diffFiles, &prompt);
      for( i=0; diffFiles[i].zName; ++i ){
        fossil_free(diffFiles[i].zName);
      }
      fossil_free(diffFiles);
    }else{
      diff_against_disk(0, &DCfg, 0, &prompt);
    }







>
|
|










|







1347
1348
1349
1350
1351
1352
1353
1354
1355
1356
1357
1358
1359
1360
1361
1362
1363
1364
1365
1366
1367
1368
1369
1370
1371
1372
1373
1374
        '#'
    );
    diff_options(&DCfg, 0, 1);
    DCfg.diffFlags |= DIFF_VERBOSE;
    if( g.aCommitFile ){
      FileDirList *diffFiles;
      int i;
      for(i=0; g.aCommitFile[i]!=0; ++i){}
      diffFiles = fossil_malloc_zero((i+1) * sizeof(*diffFiles));
      for(i=0; g.aCommitFile[i]!=0; ++i){
        diffFiles[i].zName  = db_text(0,
         "SELECT pathname FROM vfile WHERE id=%d", g.aCommitFile[i]);
        if( fossil_strcmp(diffFiles[i].zName, "." )==0 ){
          diffFiles[0].zName[0] = '.';
          diffFiles[0].zName[1] = 0;
          break;
        }
        diffFiles[i].nName = strlen(diffFiles[i].zName);
        diffFiles[i].nUsed = 0;
      }
      diff_against_disk(0, &DCfg, diffFiles, &prompt);
      for( i=0; diffFiles[i].zName; ++i ){
        fossil_free(diffFiles[i].zName);
      }
      fossil_free(diffFiles);
    }else{
      diff_against_disk(0, &DCfg, 0, &prompt);
    }
2131
2132
2133
2134
2135
2136
2137




2138
2139
2140
2141
2142
2143
2144
**                                 ("auto" lets Fossil choose it automatically,
**                                  even for private branches)
**    --close                    close the branch being committed
**    --date-override DATETIME   DATE to use instead of 'now'
**    --delta                    use a delta manifest in the commit process
**    --hash                     verify file status using hashing rather
**                               than relying on file mtimes




**    --integrate                close all merged-in branches
**    -m|--comment COMMENT-TEXT  use COMMENT-TEXT as commit comment
**    -M|--message-file FILE     read the commit comment from given file
**    --mimetype MIMETYPE        mimetype of check-in comment
**    -n|--dry-run               If given, display instead of run actions
**    -v|--verbose               Show a diff in the commit message prompt
**    --no-prompt                This option disables prompting the user for







>
>
>
>







2132
2133
2134
2135
2136
2137
2138
2139
2140
2141
2142
2143
2144
2145
2146
2147
2148
2149
**                                 ("auto" lets Fossil choose it automatically,
**                                  even for private branches)
**    --close                    close the branch being committed
**    --date-override DATETIME   DATE to use instead of 'now'
**    --delta                    use a delta manifest in the commit process
**    --hash                     verify file status using hashing rather
**                               than relying on file mtimes
**    --ignore-clock-skew        If a clock skew is detected, ignore it and
**                               behave as if the user had entered 'yes' to
**                               the question of whether to proceed despite
**                               the skew.
**    --integrate                close all merged-in branches
**    -m|--comment COMMENT-TEXT  use COMMENT-TEXT as commit comment
**    -M|--message-file FILE     read the commit comment from given file
**    --mimetype MIMETYPE        mimetype of check-in comment
**    -n|--dry-run               If given, display instead of run actions
**    -v|--verbose               Show a diff in the commit message prompt
**    --no-prompt                This option disables prompting the user for
2204
2205
2206
2207
2208
2209
2210

2211
2212
2213
2214
2215
2216
2217
  int szB;               /* Size of the baseline manifest */
  int nConflict = 0;     /* Number of unresolved merge conflicts */
  int abortCommit = 0;   /* Abort the commit due to text format conversions */
  Blob ans;              /* Answer to continuation prompts */
  char cReply;           /* First character of ans */
  int bRecheck = 0;      /* Repeat fork and closed-branch checks*/
  int bAutoBrClr = 0;    /* Value of "--branchcolor" is "auto" */


  memset(&sCiInfo, 0, sizeof(sCiInfo));
  url_proxy_options();
  /* --sha1sum is an undocumented alias for --hash for backwards compatiblity */
  useHash = find_option("hash",0,0)!=0 || find_option("sha1sum",0,0)!=0;
  noSign = find_option("nosign",0,0)!=0;
  privateFlag = find_option("private",0,0)!=0;







>







2209
2210
2211
2212
2213
2214
2215
2216
2217
2218
2219
2220
2221
2222
2223
  int szB;               /* Size of the baseline manifest */
  int nConflict = 0;     /* Number of unresolved merge conflicts */
  int abortCommit = 0;   /* Abort the commit due to text format conversions */
  Blob ans;              /* Answer to continuation prompts */
  char cReply;           /* First character of ans */
  int bRecheck = 0;      /* Repeat fork and closed-branch checks*/
  int bAutoBrClr = 0;    /* Value of "--branchcolor" is "auto" */
  int bIgnoreSkew = 0;   /* --ignore-clock-skew flag */

  memset(&sCiInfo, 0, sizeof(sCiInfo));
  url_proxy_options();
  /* --sha1sum is an undocumented alias for --hash for backwards compatiblity */
  useHash = find_option("hash",0,0)!=0 || find_option("sha1sum",0,0)!=0;
  noSign = find_option("nosign",0,0)!=0;
  privateFlag = find_option("private",0,0)!=0;
2261
2262
2263
2264
2265
2266
2267

2268
2269
2270
2271
2272
2273
2274
  zComFile = find_option("message-file", "M", 1);
  sCiInfo.zDateOvrd = find_option("date-override",0,1);
  sCiInfo.zUserOvrd = find_option("user-override",0,1);
  db_must_be_within_tree();
  noSign = db_get_boolean("omitsign", 0)|noSign;
  if( db_get_boolean("clearsign", 0)==0 ){ noSign = 1; }
  useCksum = db_get_boolean("repo-cksum", 1);

  outputManifest = db_get_manifest_setting();
  verify_all_options();

  /* Get the ID of the parent manifest artifact */
  vid = db_lget_int("checkout", 0);
  if( vid==0 ){
    useCksum = 1;







>







2267
2268
2269
2270
2271
2272
2273
2274
2275
2276
2277
2278
2279
2280
2281
  zComFile = find_option("message-file", "M", 1);
  sCiInfo.zDateOvrd = find_option("date-override",0,1);
  sCiInfo.zUserOvrd = find_option("user-override",0,1);
  db_must_be_within_tree();
  noSign = db_get_boolean("omitsign", 0)|noSign;
  if( db_get_boolean("clearsign", 0)==0 ){ noSign = 1; }
  useCksum = db_get_boolean("repo-cksum", 1);
  bIgnoreSkew = find_option("ignore-clock-skew",0,0)!=0;
  outputManifest = db_get_manifest_setting();
  verify_all_options();

  /* Get the ID of the parent manifest artifact */
  vid = db_lget_int("checkout", 0);
  if( vid==0 ){
    useCksum = 1;
2344
2345
2346
2347
2348
2349
2350



2351
2352
2353
2354
2355
2356
2357
2358
  }


  /* Require confirmation to continue with the check-in if there is
  ** clock skew
  */
  if( g.clockSkewSeen ){



    if( !noPrompt ){
      prompt_user("continue in spite of time skew (y/N)? ", &ans);
      cReply = blob_str(&ans)[0];
      blob_reset(&ans);
    }else{
      fossil_print("Abandoning commit due to time skew\n");
      cReply = 'N';
    }







>
>
>
|







2351
2352
2353
2354
2355
2356
2357
2358
2359
2360
2361
2362
2363
2364
2365
2366
2367
2368
  }


  /* Require confirmation to continue with the check-in if there is
  ** clock skew
  */
  if( g.clockSkewSeen ){
    if( bIgnoreSkew!=0 ){
      cReply = 'y';
      fossil_warning("Clock skew ignored due to --ignore-clock-skew.");
    }else if( !noPrompt ){
      prompt_user("continue in spite of time skew (y/N)? ", &ans);
      cReply = blob_str(&ans)[0];
      blob_reset(&ans);
    }else{
      fossil_print("Abandoning commit due to time skew\n");
      cReply = 'N';
    }
Changes to src/clone.c.
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
  }
  db_begin_transaction();
  if( db_exists("SELECT 1 FROM delta WHERE srcId IN phantom") ){
    fossil_fatal("there are unresolved deltas -"
                 " the clone is probably incomplete and unusable.");
  }
  fossil_print("Rebuilding repository meta-data...\n");
  rebuild_db(0, 1, 0);
  if( !noCompress ){
    fossil_print("Extra delta compression... "); fflush(stdout);
    extra_deltification();
    fossil_print("\n");
  }
  db_end_transaction(0);
  fossil_print("Vacuuming the database... "); fflush(stdout);







|







268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
  }
  db_begin_transaction();
  if( db_exists("SELECT 1 FROM delta WHERE srcId IN phantom") ){
    fossil_fatal("there are unresolved deltas -"
                 " the clone is probably incomplete and unusable.");
  }
  fossil_print("Rebuilding repository meta-data...\n");
  rebuild_db(1, 0);
  if( !noCompress ){
    fossil_print("Extra delta compression... "); fflush(stdout);
    extra_deltification();
    fossil_print("\n");
  }
  db_end_transaction(0);
  fossil_print("Vacuuming the database... "); fflush(stdout);
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
    Blob cmd;
    fossil_print("opening the new %s repository in directory %s...\n",
       zRepo, zWorkDir);
    blob_init(&cmd, 0, 0);
    blob_append_escaped_arg(&cmd, g.nameOfExe, 1);
    blob_append(&cmd, " open ", -1);
    blob_append_escaped_arg(&cmd, zRepo, 1);
    blob_append(&cmd, " --workdir ", -1);
    blob_append_escaped_arg(&cmd, zWorkDir, 1);
    if( allowNested ){
      blob_append(&cmd, " --nested", -1);
    }
    fossil_system(blob_str(&cmd));
    blob_reset(&cmd);
  }







|







295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
    Blob cmd;
    fossil_print("opening the new %s repository in directory %s...\n",
       zRepo, zWorkDir);
    blob_init(&cmd, 0, 0);
    blob_append_escaped_arg(&cmd, g.nameOfExe, 1);
    blob_append(&cmd, " open ", -1);
    blob_append_escaped_arg(&cmd, zRepo, 1);
    blob_append(&cmd, " --nosync --workdir ", -1);
    blob_append_escaped_arg(&cmd, zWorkDir, 1);
    if( allowNested ){
      blob_append(&cmd, " --nested", -1);
    }
    fossil_system(blob_str(&cmd));
    blob_reset(&cmd);
  }
Changes to src/db.c.
1912
1913
1914
1915
1916
1917
1918
1919
1920
1921
1922
1923
1924

1925
1926
1927
1928
1929
1930
1931
  if( file_size(zDbName, ExtFILE)<1024*3 ){
    char *zHome = file_dirname(zDbName);
    int rc;
    if( file_isdir(zHome, ExtFILE)==0 ){
      file_mkdir(zHome, ExtFILE, 0);
    }
    rc = file_access(zHome, W_OK);
    fossil_free(zHome);
    if( rc ){
      if( isOptional ) return 0;
      fossil_fatal("home directory \"%s\" must be writeable", zHome);
    }
    db_init_database(zDbName, zConfigSchema, (char*)0);

  }
  if( file_access(zDbName, W_OK) ){
    if( isOptional ) return 0;
    fossil_fatal("configuration file %s must be writeable", zDbName);
  }
  if( useAttach ){
    db_open_or_attach(zDbName, "configdb");







<





>







1912
1913
1914
1915
1916
1917
1918

1919
1920
1921
1922
1923
1924
1925
1926
1927
1928
1929
1930
1931
  if( file_size(zDbName, ExtFILE)<1024*3 ){
    char *zHome = file_dirname(zDbName);
    int rc;
    if( file_isdir(zHome, ExtFILE)==0 ){
      file_mkdir(zHome, ExtFILE, 0);
    }
    rc = file_access(zHome, W_OK);

    if( rc ){
      if( isOptional ) return 0;
      fossil_fatal("home directory \"%s\" must be writeable", zHome);
    }
    db_init_database(zDbName, zConfigSchema, (char*)0);
    fossil_free(zHome);
  }
  if( file_access(zDbName, W_OK) ){
    if( isOptional ) return 0;
    fossil_fatal("configuration file %s must be writeable", zDbName);
  }
  if( useAttach ){
    db_open_or_attach(zDbName, "configdb");
2123
2124
2125
2126
2127
2128
2129
2130
2131















































2132
2133
2134
2135

2136
2137
2138
2139
2140
2141
2142
2143
2144
2145



2146
2147
2148
2149
2150
2151
2152

/*
** Returns non-zero if support for symlinks is currently enabled.
*/
int db_allow_symlinks(void){
  return g.allowSymlinks;
}

/*















































** Open the repository database given by zDbName.  If zDbName==NULL then
** get the name from the already open local database.
*/
void db_open_repository(const char *zDbName){

  if( g.repositoryOpen ) return;
  if( zDbName==0 ){
    if( g.localOpen ){
      zDbName = db_repository_filename();
    }
    if( zDbName==0 ){
      db_err("unable to find the name of a repository database");
    }
  }
  if( file_access(zDbName, R_OK) || file_size(zDbName, ExtFILE)<1024 ){



    if( file_access(zDbName, F_OK) ){
#ifdef FOSSIL_ENABLE_JSON
      g.json.resultCode = FSL_JSON_E_DB_NOT_FOUND;
#endif
      fossil_fatal("repository does not exist or"
                   " is in an unreadable directory: %s", zDbName);
    }else if( file_access(zDbName, R_OK) ){









>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>




>









|
>
>
>







2123
2124
2125
2126
2127
2128
2129
2130
2131
2132
2133
2134
2135
2136
2137
2138
2139
2140
2141
2142
2143
2144
2145
2146
2147
2148
2149
2150
2151
2152
2153
2154
2155
2156
2157
2158
2159
2160
2161
2162
2163
2164
2165
2166
2167
2168
2169
2170
2171
2172
2173
2174
2175
2176
2177
2178
2179
2180
2181
2182
2183
2184
2185
2186
2187
2188
2189
2190
2191
2192
2193
2194
2195
2196
2197
2198
2199
2200
2201
2202
2203

/*
** Returns non-zero if support for symlinks is currently enabled.
*/
int db_allow_symlinks(void){
  return g.allowSymlinks;
}

/*
** Return TRUE if the file in the argument seems like it might be an
** SQLite database file that contains a Fossil repository schema.
*/
int db_looks_like_a_repository(const char *zDbName){
  sqlite3 *db = 0;
  i64 sz;
  int rc;
  int res = 0;
  sqlite3_stmt *pStmt = 0;

  sz = file_size(zDbName, ExtFILE);
  if( sz<16834 ) return 0;
  if( sz & 0x1ff ) return 0;
  rc = sqlite3_open(zDbName, &db);
  if( rc ) goto is_repo_end;
  rc = sqlite3_prepare_v2(db, 
       "SELECT count(*) FROM sqlite_schema"
       " WHERE name COLLATE nocase IN"
       "('blob','delta','rcvfrom','user','config','mlink','plink');",
       -1, &pStmt, 0);
  if( rc ) goto is_repo_end;
  rc = sqlite3_step(pStmt);
  if( rc!=SQLITE_ROW ) goto is_repo_end;
  if( sqlite3_column_int(pStmt, 0)!=7 ) goto is_repo_end;
  res = 1;

is_repo_end:
  sqlite3_finalize(pStmt);
  sqlite3_close(db);
  return res;
}

/*
** COMMAND: test-is-repo
*/
void test_is_repo(void){
  int i;
  for(i=2; i<g.argc; i++){
    fossil_print("%s: %s\n",
       db_looks_like_a_repository(g.argv[i]) ? "yes" : " no",
       g.argv[i]
    );
  }
}


/*
** Open the repository database given by zDbName.  If zDbName==NULL then
** get the name from the already open local database.
*/
void db_open_repository(const char *zDbName){
  i64 sz;
  if( g.repositoryOpen ) return;
  if( zDbName==0 ){
    if( g.localOpen ){
      zDbName = db_repository_filename();
    }
    if( zDbName==0 ){
      db_err("unable to find the name of a repository database");
    }
  }
  if( file_access(zDbName, R_OK) 
   || (sz = file_size(zDbName, ExtFILE))<16384
   || (sz&0x1ff)!=0
  ){
    if( file_access(zDbName, F_OK) ){
#ifdef FOSSIL_ENABLE_JSON
      g.json.resultCode = FSL_JSON_E_DB_NOT_FOUND;
#endif
      fossil_fatal("repository does not exist or"
                   " is in an unreadable directory: %s", zDbName);
    }else if( file_access(zDbName, R_OK) ){
3499
3500
3501
3502
3503
3504
3505
3506
3507
3508
3509
3510
3511
3512
3513


3514
3515
3516
3517
3518
3519
3520
3521
3522
3523
3524
3525
3526
3527
3528
3529
3530
3531
3532
3533

3534
3535
3536
3537
3538
3539
3540
3541
3542
3543
3544

3545
3546
3547
3548
3549
3550
3551
** Options:
**   --empty           Initialize checkout as being empty, but still connected
**                     with the local repository. If you commit this checkout,
**                     it will become a new "initial" commit in the repository.
**   -f|--force        Continue with the open even if the working directory is
**                     not empty.
**   --force-missing   Force opening a repository with missing content
**   --keep            Only modify the manifest and manifest.uuid files
**   --nested          Allow opening a repository inside an opened checkout
**   --nosync          Do not auto-sync the repository prior to opening
**   --repodir DIR     If REPOSITORY is a URI that will be cloned, store
**                     the clone in DIR rather than in "."
**   --setmtime        Set timestamps of all files to match their SCM-side
**                     times (the timestamp of the last checkin which modified
**                     them).


**   --workdir DIR     Use DIR as the working directory instead of ".". The DIR
**                     directory is created if it does not exist.
**
** See also: [[close]], [[clone]]
*/
void cmd_open(void){
  int emptyFlag;
  int keepFlag;
  int forceMissingFlag;
  int allowNested;
  int setmtimeFlag;              /* --setmtime.  Set mtimes on files */
  int bForce = 0;                /* --force.  Open even if non-empty dir */
  static char *azNewArgv[] = { 0, "checkout", "--prompt", 0, 0, 0, 0 };
  const char *zWorkDir;          /* --workdir value */
  const char *zRepo = 0;         /* Name of the repository file */
  const char *zRepoDir = 0;      /* --repodir value */
  char *zPwd;                    /* Initial working directory */
  int isUri = 0;                 /* True if REPOSITORY is a URI */
  int nLocal;                    /* Number of preexisting files in cwd */
  int bNosync = 0;               /* --nosync.  Omit auto-sync */


  url_proxy_options();
  emptyFlag = find_option("empty",0,0)!=0;
  keepFlag = find_option("keep",0,0)!=0;
  forceMissingFlag = find_option("force-missing",0,0)!=0;
  allowNested = find_option("nested",0,0)!=0;
  setmtimeFlag = find_option("setmtime",0,0)!=0;
  zWorkDir = find_option("workdir",0,1);
  zRepoDir = find_option("repodir",0,1);
  bForce = find_option("force","f",0)!=0;  
  bNosync = find_option("nosync",0,0)!=0;

  zPwd = file_getcwd(0,0);
  

  /* We should be done with options.. */
  verify_all_options();

  if( g.argc!=3 && g.argc!=4 ){







|







>
>




















>



|







>







3550
3551
3552
3553
3554
3555
3556
3557
3558
3559
3560
3561
3562
3563
3564
3565
3566
3567
3568
3569
3570
3571
3572
3573
3574
3575
3576
3577
3578
3579
3580
3581
3582
3583
3584
3585
3586
3587
3588
3589
3590
3591
3592
3593
3594
3595
3596
3597
3598
3599
3600
3601
3602
3603
3604
3605
3606
** Options:
**   --empty           Initialize checkout as being empty, but still connected
**                     with the local repository. If you commit this checkout,
**                     it will become a new "initial" commit in the repository.
**   -f|--force        Continue with the open even if the working directory is
**                     not empty.
**   --force-missing   Force opening a repository with missing content
**   -k|--keep         Only modify the manifest and manifest.uuid files
**   --nested          Allow opening a repository inside an opened checkout
**   --nosync          Do not auto-sync the repository prior to opening
**   --repodir DIR     If REPOSITORY is a URI that will be cloned, store
**                     the clone in DIR rather than in "."
**   --setmtime        Set timestamps of all files to match their SCM-side
**                     times (the timestamp of the last checkin which modified
**                     them).
**   --verbose         If passed a URI then this flag is passed on to the clone
**                     operation, otherwise it has no effect.
**   --workdir DIR     Use DIR as the working directory instead of ".". The DIR
**                     directory is created if it does not exist.
**
** See also: [[close]], [[clone]]
*/
void cmd_open(void){
  int emptyFlag;
  int keepFlag;
  int forceMissingFlag;
  int allowNested;
  int setmtimeFlag;              /* --setmtime.  Set mtimes on files */
  int bForce = 0;                /* --force.  Open even if non-empty dir */
  static char *azNewArgv[] = { 0, "checkout", "--prompt", 0, 0, 0, 0 };
  const char *zWorkDir;          /* --workdir value */
  const char *zRepo = 0;         /* Name of the repository file */
  const char *zRepoDir = 0;      /* --repodir value */
  char *zPwd;                    /* Initial working directory */
  int isUri = 0;                 /* True if REPOSITORY is a URI */
  int nLocal;                    /* Number of preexisting files in cwd */
  int bNosync = 0;               /* --nosync.  Omit auto-sync */
  int bVerbose = 0;              /* --verbose option for clone */

  url_proxy_options();
  emptyFlag = find_option("empty",0,0)!=0;
  keepFlag = find_option("keep","k",0)!=0;
  forceMissingFlag = find_option("force-missing",0,0)!=0;
  allowNested = find_option("nested",0,0)!=0;
  setmtimeFlag = find_option("setmtime",0,0)!=0;
  zWorkDir = find_option("workdir",0,1);
  zRepoDir = find_option("repodir",0,1);
  bForce = find_option("force","f",0)!=0;  
  bNosync = find_option("nosync",0,0)!=0;
  bVerbose = find_option("verbose",0,0)!=0;
  zPwd = file_getcwd(0,0);
  

  /* We should be done with options.. */
  verify_all_options();

  if( g.argc!=3 && g.argc!=4 ){
3580
3581
3582
3583
3584
3585
3586


3587
3588
3589
3590
3591
3592
3593
3594
  }
  if( keepFlag==0
   && bForce==0
   && (nLocal = file_directory_size(".", 0, 1))>0
   && (nLocal>1 || isUri || !file_in_cwd(zRepo))
  ){
    fossil_fatal("directory %s is not empty\n"


                 "use the -f or --force option to override", file_getcwd(0,0));
  }

  if( db_open_local_v2(0, allowNested) ){
    fossil_fatal("there is already an open tree at %s", g.zLocalRoot);
  }

  /* If REPOSITORY looks like a URI, then try to clone it first */







>
>
|







3635
3636
3637
3638
3639
3640
3641
3642
3643
3644
3645
3646
3647
3648
3649
3650
3651
  }
  if( keepFlag==0
   && bForce==0
   && (nLocal = file_directory_size(".", 0, 1))>0
   && (nLocal>1 || isUri || !file_in_cwd(zRepo))
  ){
    fossil_fatal("directory %s is not empty\n"
                 "use the -f (--force) option to override\n"
                 "or the -k (--keep) option to keep local files unchanged", 
                 file_getcwd(0,0));
  }

  if( db_open_local_v2(0, allowNested) ){
    fossil_fatal("there is already an open tree at %s", g.zLocalRoot);
  }

  /* If REPOSITORY looks like a URI, then try to clone it first */
3607
3608
3609
3610
3611
3612
3613



3614
3615
3616
3617
3618
3619
3620
    }
    if( zRepoDir==0 ) zRepoDir = zPwd;
    zRepo = mprintf("%s/%s.fossil", zRepoDir, zNewBase);
    fossil_free(zNewBase);
    blob_init(&cmd, 0, 0);
    blob_append_escaped_arg(&cmd, g.nameOfExe, 1);
    blob_append(&cmd, " clone", -1);



    blob_append_escaped_arg(&cmd, zUri, 1);
    blob_append_escaped_arg(&cmd, zRepo, 1);
    zCmd = blob_str(&cmd);
    fossil_print("%s\n", zCmd);
    if( zWorkDir ) file_chdir(zPwd, 0);
    rc = fossil_system(zCmd);
    if( rc ){







>
>
>







3664
3665
3666
3667
3668
3669
3670
3671
3672
3673
3674
3675
3676
3677
3678
3679
3680
    }
    if( zRepoDir==0 ) zRepoDir = zPwd;
    zRepo = mprintf("%s/%s.fossil", zRepoDir, zNewBase);
    fossil_free(zNewBase);
    blob_init(&cmd, 0, 0);
    blob_append_escaped_arg(&cmd, g.nameOfExe, 1);
    blob_append(&cmd, " clone", -1);
    if(0!=bVerbose){
      blob_append(&cmd, " --verbose", -1);
    }
    blob_append_escaped_arg(&cmd, zUri, 1);
    blob_append_escaped_arg(&cmd, zRepo, 1);
    zCmd = blob_str(&cmd);
    fossil_print("%s\n", zCmd);
    if( zWorkDir ) file_chdir(zPwd, 0);
    rc = fossil_system(zCmd);
    if( rc ){
3805
3806
3807
3808
3809
3810
3811

3812

3813
3814
3815
3816



3817
3818
3819
3820
3821
3822
3823
/*
** SETTING: auto-shun       boolean default=on
** If enabled, automatically pull the shunning list
** from a server to which the client autosyncs.
*/
/*
** SETTING: autosync        width=16 default=on

** This setting can take either a boolean value or "pullonly"

** If enabled, automatically pull prior to commit
** or update and automatically push after commit or
** tag or branch creation.  If the value is "pullonly"
** then only pull operations occur automatically.



*/
/*
** SETTING: autosync-tries  width=16 default=1
** If autosync is enabled setting this to a value greater
** than zero will cause autosync to try no more than this
** number of attempts if there is a sync failure.
*/







>
|
>
|

|
|
>
>
>







3865
3866
3867
3868
3869
3870
3871
3872
3873
3874
3875
3876
3877
3878
3879
3880
3881
3882
3883
3884
3885
3886
3887
3888
/*
** SETTING: auto-shun       boolean default=on
** If enabled, automatically pull the shunning list
** from a server to which the client autosyncs.
*/
/*
** SETTING: autosync        width=16 default=on
** This setting can be a boolean value  (0, 1, on, off, true, false)
** or "pullonly" or "all".
**
** If not false, automatically pull prior to commit
** or update and automatically push after commit or
** tag or branch creation.  Except, if the value is
** "pullonly" then only pull operations occur automatically.
** Normally, only the default remote is used, but if the
** value is "all" then push/pull operations occur on all
** remotes.
*/
/*
** SETTING: autosync-tries  width=16 default=1
** If autosync is enabled setting this to a value greater
** than zero will cause autosync to try no more than this
** number of attempts if there is a sync failure.
*/
Changes to src/diffcmd.c.
549
550
551
552
553
554
555



















556
557
558
559
560
561
562
    file_delete(blob_str(&temp2));

    blob_reset(&temp1);
    blob_reset(&temp2);
    blob_reset(&cmd);
  }
}




















/*
** Run a diff between the version zFrom and files on disk.  zFrom might
** be NULL which means to simply show the difference between the edited
** files on disk and the check-out on which they are based.
**
** Use the internal diff logic if zDiffCmd is NULL.  Otherwise call the







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
    file_delete(blob_str(&temp2));

    blob_reset(&temp1);
    blob_reset(&temp2);
    blob_reset(&cmd);
  }
}

/*
** Return true if the disk file is identical to the Blob.  Return zero
** if the files differ in any way.
*/
static int file_same_as_blob(Blob *blob, const char *zDiskFile){
  Blob file;
  int rc = 0;
  if( blob_size(blob)!=file_size(zDiskFile, ExtFILE) ) return 0;
  blob_zero(&file);
  blob_read_from_file(&file, zDiskFile, ExtFILE);
  if( blob_size(&file)!=blob_size(blob) ){
    rc = 0;
  }else{
    rc = memcmp(blob_buffer(&file), blob_buffer(blob), blob_size(&file))==0;
  }
  blob_reset(&file);
  return rc;
}

/*
** Run a diff between the version zFrom and files on disk.  zFrom might
** be NULL which means to simply show the difference between the edited
** files on disk and the check-out on which they are based.
**
** Use the internal diff logic if zDiffCmd is NULL.  Otherwise call the
670
671
672
673
674
675
676

677
678

679
680
681
682
683
684
685
        continue;
      }
      if( srcid>0 ){
        content_get(srcid, &content);
      }else{
        blob_zero(&content);
      }

      diff_print_index(zPathname, pCfg, pOut);
      diff_file(&content, zFullName, zPathname, pCfg, pOut);

      blob_reset(&content);
    }
    blob_reset(&fname);
  }
  db_finalize(&q);
  db_end_transaction(1);  /* ROLLBACK */
}







>
|
|
>







689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
        continue;
      }
      if( srcid>0 ){
        content_get(srcid, &content);
      }else{
        blob_zero(&content);
      }
      if( isChnged==0 || !file_same_as_blob(&content, zFullName) ){
        diff_print_index(zPathname, pCfg, pOut);
        diff_file(&content, zFullName, zPathname, pCfg, pOut);
      }
      blob_reset(&content);
    }
    blob_reset(&fname);
  }
  db_finalize(&q);
  db_end_transaction(1);  /* ROLLBACK */
}
Changes to src/fossil.bootstrap.js.
289
290
291
292
293
294
295






























296
  F.page.setPageTitle = function f(title){
    const t = document.querySelector('title');
    if(t) t.innerText = title || f.$orig;
    return this;
  };
  F.onPageLoad(()=>F.page.setPageTitle.$orig
               = document.querySelector('title').innerText);






























})(window);







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>

289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
  F.page.setPageTitle = function f(title){
    const t = document.querySelector('title');
    if(t) t.innerText = title || f.$orig;
    return this;
  };
  F.onPageLoad(()=>F.page.setPageTitle.$orig
               = document.querySelector('title').innerText);
  /**
     Returns a function, that, as long as it continues to be invoked,
     will not be triggered. The function will be called after it stops
     being called for N milliseconds. If `immediate` is passed, call
     the callback immediately and hinder future invocations until at
     least the given time has passed.

     If passed only 1 argument, or passed a falsy 2nd argument,
     the default wait time set in this function's $defaultDelay
     property is used.

     Source: underscore.js, by way of https://davidwalsh.name/javascript-debounce-function
  */
  F.debounce = function f(func, wait, immediate) {
    var timeout;
    if(!wait) wait = f.$defaultDelay;
    return function() {
      const context = this, args = Array.prototype.slice.call(arguments);
      const later = function() {
        timeout = undefined;
        if(!immediate) func.apply(context, args);
      };
      const callNow = immediate && !timeout;
      clearTimeout(timeout);
      timeout = setTimeout(later, wait);
      if(callNow) func.apply(context, args);
    };
  };
  F.debounce.$defaultDelay = 500 /*arbitrary*/;

})(window);
Changes to src/fossil.diff.js.
278
279
280
281
282
283
284
285

286
287
288
289
290
291
292
293
       of the diff, only between two diff chunks.
    */
    maybeReplaceButtons: function(){
      if(this.pos.next && this.pos.prev
         && (this.pos.endLhs - this.pos.startLhs <= Diff.config.chunkLoadLines)){
        D.clearElement(this.e.btnWrapper);
        D.append(this.e.btnWrapper, this.createButton(this.FetchType.FillGap));
        if( this.$fetchQueue && this.$fetchQueue.length>0 ){

          this.$fetchQueue = [this.FetchType.FillGap];
        }
      }
      return this;
    },

    /**
       Callack for /jchunk responses.







|
>
|







278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
       of the diff, only between two diff chunks.
    */
    maybeReplaceButtons: function(){
      if(this.pos.next && this.pos.prev
         && (this.pos.endLhs - this.pos.startLhs <= Diff.config.chunkLoadLines)){
        D.clearElement(this.e.btnWrapper);
        D.append(this.e.btnWrapper, this.createButton(this.FetchType.FillGap));
        if( this.$fetchQueue && this.$fetchQueue.length>1 ){
          this.$fetchQueue[1] = this.FetchType.FillGap;
          this.$fetchQueue.length = 2;
        }
      }
      return this;
    },

    /**
       Callack for /jchunk responses.
575
576
577
578
579
580
581

582
583



584
585
586
587
588
589
590
        if( this.pos.prev && this.pos.prev.endLhs >= up.from ){
          up.from = this.pos.prev.endLhs + 1;
          fetchType = this.FetchType.FillGap;
        }
      }
      //console.debug("fetchChunk(",fetchType,")",up);
      fOpt.onerror = function(err){

        self.msg(true,err.message);
        self.$fetchQueue = [];



      };
      Diff.fetchArtifactChunk(fOpt);
      return this;
    }
  };

  /**







>
|
|
>
>
>







576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
        if( this.pos.prev && this.pos.prev.endLhs >= up.from ){
          up.from = this.pos.prev.endLhs + 1;
          fetchType = this.FetchType.FillGap;
        }
      }
      //console.debug("fetchChunk(",fetchType,")",up);
      fOpt.onerror = function(err){
        if(self.e/*guard against a late-stage onerror() call*/){
          self.msg(true,err.message);
          self.$fetchQueue.length = 0;
        }else{
          Diff.config.chunkFetch.onerror.call(this,err);
        }
      };
      Diff.fetchArtifactChunk(fOpt);
      return this;
    }
  };

  /**
730
731
732
733
734
735
736
737
738
    return this;
  }
  window.fossil.page.tweakSbsDiffs = function(){
    document.querySelectorAll('table.splitdiff').forEach((e)=>Diff.initTableDiff(e));
    Diff.checkTableWidth();
  };
  Diff.initTableDiff().checkTableWidth();
  window.addEventListener('resize', ()=>Diff.checkTableWidth());
}, false);







|

735
736
737
738
739
740
741
742
743
    return this;
  }
  window.fossil.page.tweakSbsDiffs = function(){
    document.querySelectorAll('table.splitdiff').forEach((e)=>Diff.initTableDiff(e));
    Diff.checkTableWidth();
  };
  Diff.initTableDiff().checkTableWidth();
  window.addEventListener('resize', F.debounce(()=>Diff.checkTableWidth()));
}, false);
Changes to src/fossil.fetch.js.
25
26
27
28
29
30
31
32
33

34




35
36
37
38
39
40
41
   - onload: callback(responseData) (default = output response to the
   console). In the context of the callback, the options object is
   "this", noting that this call may have amended the options object
   with state other than what the caller provided.

   - onerror: callback(Error object) (default = output error message
   to console.error() and fossil.error()). Triggered if the request
   generates any response other than HTTP 200 or suffers a connection
   error or timeout while awaiting a response. In the context of the

   callback, the options object is "this".





   - method: 'POST' | 'GET' (default = 'GET'). CASE SENSITIVE!

   - payload: anything acceptable by XHR2.send(ARG) (DOMString,
   Document, FormData, Blob, File, ArrayBuffer), or a plain object or
   array, either of which gets JSON.stringify()'d. If payload is set
   then the method is automatically set to 'POST'. By default XHR2







|
|
>
|
>
>
>
>







25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
   - onload: callback(responseData) (default = output response to the
   console). In the context of the callback, the options object is
   "this", noting that this call may have amended the options object
   with state other than what the caller provided.

   - onerror: callback(Error object) (default = output error message
   to console.error() and fossil.error()). Triggered if the request
   generates any response other than HTTP 200, suffers a connection
   error or timeout while awaiting a response, or if the onload()
   handler throws an exception. In the context of the callback, the
   options object is "this". Note that this function is intended to be
   used solely for error reporting, not error recovery. Because
   onerror() may be called if onload() throws, it is up to the caller
   to ensure that their onerror() callback references only state which
   is valid in such a case.

   - method: 'POST' | 'GET' (default = 'GET'). CASE SENSITIVE!

   - payload: anything acceptable by XHR2.send(ARG) (DOMString,
   Document, FormData, Blob, File, ArrayBuffer), or a plain object or
   array, either of which gets JSON.stringify()'d. If payload is set
   then the method is automatically set to 'POST'. By default XHR2
Changes to src/fossil.page.chat.js.
41
42
43
44
45
46
47

48
49
50
51
52
53
54
     Returns an almost-ISO8601 form of Date object d.
  */
  const iso8601ish = function(d){
    return d.toISOString()
        .replace('T',' ').replace(/\.\d+/,'')
        .replace('Z', ' zulu');
  };

  /** Returns the local time string of Date object d, defaulting
      to the current time. */
  const localTimeString = function ff(d){
    d || (d = new Date());
    return [
      d.getFullYear(),'-',pad2(d.getMonth()+1/*sigh*/),
      '-',pad2(d.getDate()),







>







41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
     Returns an almost-ISO8601 form of Date object d.
  */
  const iso8601ish = function(d){
    return d.toISOString()
        .replace('T',' ').replace(/\.\d+/,'')
        .replace('Z', ' zulu');
  };
  const pad2 = (x)=>('0'+x).substr(-2);
  /** Returns the local time string of Date object d, defaulting
      to the current time. */
  const localTimeString = function ff(d){
    d || (d = new Date());
    return [
      d.getFullYear(),'-',pad2(d.getMonth()+1/*sigh*/),
      '-',pad2(d.getDate()),
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140


141
142
143
144
145
146
147
      var extra = 0;
      if(com){
        ht = wh;
      }else{
        elemsToCount.forEach((e)=>e ? extra += D.effectiveHeight(e) : false);
        ht = wh - extra;
      }
      f.chat.e.inputField.style.maxHeight = (ht/2)+"px";
      /* ^^^^ this is a middle ground between having no size cap
         on the input field and having a fixed arbitrary cap. */;
      contentArea.style.height =
        contentArea.style.maxHeight = [
          "calc(", (ht>=100 ? ht : 100), "px",
          " - 0.75em"/*fudge value*/,")"
          /* ^^^^ hypothetically not needed, but both Chrome/FF on
             Linux will force scrollbars on the body if this value is
             too small (<0.75em in my tests). */
        ].join('');
      if(false){
        console.debug("resized.",wh, extra, ht,
                      window.getComputedStyle(contentArea).maxHeight,
                      contentArea);
        console.debug("Set input max height to: ",
                      f.chat.e.inputField.style.maxHeight);
      }
    };
    var doit;
    window.addEventListener('resize',function(ev){
      clearTimeout(doit);
      doit = setTimeout(resized, 100);
    }, false);
    return resized;
  })();
  ForceResizeKludge.$disabled = true/*gets deleted when setup is finished*/;
  fossil.FRK = ForceResizeKludge/*for debugging*/;
  const Chat = ForceResizeKludge.chat = (function(){
    const cs = {
      verboseErrors: false /* if true then certain, mostly extraneous,
                              error messages may be sent to the console. */,
      e:{/*map of certain DOM elements.*/
        messageInjectPoint: E1('#message-inject-point'),
        pageTitle: E1('head title'),
        loadOlderToolbar: undefined /* the load-posts toolbar (dynamically created) */,
        inputWrapper: E1("#chat-input-area"),
        inputLine: E1('#chat-input-line'),
        fileSelectWrapper: E1('#chat-input-file-area'),
        viewMessages: E1('#chat-messages-wrapper'),
        btnSubmit: E1('#chat-button-submit'),
        btnAttach: E1('#chat-button-attach'),
        inputField: E1('#chat-input-field'),


        inputFile: E1('#chat-input-file'),
        contentDiv: E1('div.content'),
        viewConfig: E1('#chat-config'),
        viewPreview: E1('#chat-preview'),
        previewContent: E1('#chat-preview-content'),
        btnPreview: E1('#chat-button-preview'),
        views: document.querySelectorAll('.chat-view'),







|















|


|
|
<
<
<


<










|




|
>
>







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



120
121

122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
      var extra = 0;
      if(com){
        ht = wh;
      }else{
        elemsToCount.forEach((e)=>e ? extra += D.effectiveHeight(e) : false);
        ht = wh - extra;
      }
      f.chat.e.inputX.style.maxHeight = (ht/2)+"px";
      /* ^^^^ this is a middle ground between having no size cap
         on the input field and having a fixed arbitrary cap. */;
      contentArea.style.height =
        contentArea.style.maxHeight = [
          "calc(", (ht>=100 ? ht : 100), "px",
          " - 0.75em"/*fudge value*/,")"
          /* ^^^^ hypothetically not needed, but both Chrome/FF on
             Linux will force scrollbars on the body if this value is
             too small (<0.75em in my tests). */
        ].join('');
      if(false){
        console.debug("resized.",wh, extra, ht,
                      window.getComputedStyle(contentArea).maxHeight,
                      contentArea);
        console.debug("Set input max height to: ",
                      f.chat.e.inputX.style.maxHeight);
      }
    };
    resized.$disabled = true/*gets deleted when setup is finished*/;
    window.addEventListener('resize', F.debounce(resized, 250), false);



    return resized;
  })();

  fossil.FRK = ForceResizeKludge/*for debugging*/;
  const Chat = ForceResizeKludge.chat = (function(){
    const cs = {
      verboseErrors: false /* if true then certain, mostly extraneous,
                              error messages may be sent to the console. */,
      e:{/*map of certain DOM elements.*/
        messageInjectPoint: E1('#message-inject-point'),
        pageTitle: E1('head title'),
        loadOlderToolbar: undefined /* the load-posts toolbar (dynamically created) */,
        inputWrapper: E1("#chat-input-area"),
        inputElementWrapper: E1('#chat-input-line-wrapper'),
        fileSelectWrapper: E1('#chat-input-file-area'),
        viewMessages: E1('#chat-messages-wrapper'),
        btnSubmit: E1('#chat-button-submit'),
        btnAttach: E1('#chat-button-attach'),
        inputX: E1('#chat-input-field-x'),
        input1: E1('#chat-input-field-single'),
        inputM: E1('#chat-input-field-multi'),
        inputFile: E1('#chat-input-file'),
        contentDiv: E1('div.content'),
        viewConfig: E1('#chat-config'),
        viewPreview: E1('#chat-preview'),
        previewContent: E1('#chat-preview-content'),
        btnPreview: E1('#chat-button-preview'),
        views: document.querySelectorAll('.chat-view'),
190
191
192
193
194
195
196

197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
      },
      /** Gets (no args) or sets (1 arg) the current input text field value,
          taking into account single- vs multi-line input. The getter returns
          a string and the setter returns this object. */
      inputValue: function(){
        const e = this.inputElement();
        if(arguments.length){

          e.innerText = arguments[0];
          return this;
        }
        return e.innerText;
      },
      /** Asks the current user input field to take focus. Returns this. */
      inputFocus: function(){
        this.inputElement().focus();
        return this;
      },
      /** Returns the current message input element. */
      inputElement: function(){
        return this.e.inputField;
      },
      /** Enables (if yes is truthy) or disables all elements in
       * this.disableDuringAjax. */
      enableAjaxComponents: function(yes){
        D[yes ? 'enable' : 'disable'](this.disableDuringAjax);
        return this;
      },







>
|


|








|







189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
      },
      /** Gets (no args) or sets (1 arg) the current input text field value,
          taking into account single- vs multi-line input. The getter returns
          a string and the setter returns this object. */
      inputValue: function(){
        const e = this.inputElement();
        if(arguments.length){
          if(e.isContentEditable) e.innerText = arguments[0];
          else e.value = arguments[0];
          return this;
        }
        return e.isContentEditable ? e.innerText : e.value;
      },
      /** Asks the current user input field to take focus. Returns this. */
      inputFocus: function(){
        this.inputElement().focus();
        return this;
      },
      /** Returns the current message input element. */
      inputElement: function(){
        return this.e.inputFields[this.e.inputFields.$currentIndex];
      },
      /** Enables (if yes is truthy) or disables all elements in
       * this.disableDuringAjax. */
      enableAjaxComponents: function(yes){
        D[yes ? 'enable' : 'disable'](this.disableDuringAjax);
        return this;
      },
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439






440
441
442
443
444
445
446
          /* When on, the edit field starts as a single line and
             expands as the user types, and the relevant buttons are
             laid out in a compact form. When off, the edit field and
             buttons are larger. */
          "edit-compact-mode": true,
          /* When on, sets the font-family on messages and the edit
             field to monospace. */
          "monospace-messages": true,
          /* When on, non-chat UI elements (page header/footer) are
             hidden */
          "chat-only-mode": false,
          /* When set to a URI, it is assumed to be an audio file,
             which gets played when new messages arrive. When true,
             the first entry in the audio file selection list will be
             used. */
          "audible-alert": true,
          /* When on, show the list of "active" users - those from
             whom we have messages in the currently-loaded history
             (noting that deletions are also messages). */
          "active-user-list": false,
          /* When on, the [active-user-list] setting includes the
             timestamp of each user's most recent message. */
          "active-user-list-timestamps": false,
          /* When on, the [audible-alert] is played for one's own
             messages, else it is only played for other users'
             messages. */
          "alert-own-messages": false






        }
      },
      /** Plays a new-message notification sound IF the audible-alert
          setting is true, else this is a no-op. Returns this.
      */
      playNewMessageSound: function f(){
        if(f.uri){







|


















|
>
>
>
>
>
>







413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
          /* When on, the edit field starts as a single line and
             expands as the user types, and the relevant buttons are
             laid out in a compact form. When off, the edit field and
             buttons are larger. */
          "edit-compact-mode": true,
          /* When on, sets the font-family on messages and the edit
             field to monospace. */
          "monospace-messages": false,
          /* When on, non-chat UI elements (page header/footer) are
             hidden */
          "chat-only-mode": false,
          /* When set to a URI, it is assumed to be an audio file,
             which gets played when new messages arrive. When true,
             the first entry in the audio file selection list will be
             used. */
          "audible-alert": true,
          /* When on, show the list of "active" users - those from
             whom we have messages in the currently-loaded history
             (noting that deletions are also messages). */
          "active-user-list": false,
          /* When on, the [active-user-list] setting includes the
             timestamp of each user's most recent message. */
          "active-user-list-timestamps": false,
          /* When on, the [audible-alert] is played for one's own
             messages, else it is only played for other users'
             messages. */
          "alert-own-messages": false,
          /* "Experimental mode" input: use a contenteditable field
             for input. This is generally more comfortable to use,
             and more modern, than plain text input fields, but
             the list of browser-specific quirks and bugs is...
             not short. */
          "edit-widget-x": false
        }
      },
      /** Plays a new-message notification sound IF the audible-alert
          setting is true, else this is a no-op. Returns this.
      */
      playNewMessageSound: function f(){
        if(f.uri){
670
671
672
673
674
675
676






677
678
679
680
681
682
683
684
685
686
687
688
689
      animate: function f(e,a,cb){
        if(!f.$disabled){
          D.addClassBriefly(e, a, 0, cb);
        }
        return this;
      }
    };






    if(D.attr(cs.e.inputField,'contenteditable','plaintext-only').isContentEditable){
      cs.$browserHasPlaintextOnly = true;
    }else{
      /* Only the Chrome family supports contenteditable=plaintext-only */
      cs.$browserHasPlaintextOnly = false;
      D.attr(cs.e.inputField,'contenteditable','true');
    }
    cs.animate.$disabled = true;
    F.fetch.beforesend = ()=>cs.ajaxStart();
    F.fetch.aftersend = ()=>cs.ajaxEnd();
    cs.pageTitleOrig = cs.e.pageTitle.innerText;
    const qs = (e)=>document.querySelector(e);
    const argsToArray = function(args){







>
>
>
>
>
>
|




|







676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
      animate: function f(e,a,cb){
        if(!f.$disabled){
          D.addClassBriefly(e, a, 0, cb);
        }
        return this;
      }
    };
    cs.e.inputFields = [ cs.e.input1, cs.e.inputM, cs.e.inputX ];
    cs.e.inputFields.$currentIndex = 0;
    cs.e.inputFields.forEach(function(e,ndx){
      if(ndx===cs.e.inputFields.$currentIndex) D.removeClass(e,'hidden');
      else D.addClass(e,'hidden');
    });
    if(D.attr(cs.e.inputX,'contenteditable','plaintext-only').isContentEditable){
      cs.$browserHasPlaintextOnly = true;
    }else{
      /* Only the Chrome family supports contenteditable=plaintext-only */
      cs.$browserHasPlaintextOnly = false;
      D.attr(cs.e.inputX,'contenteditable','true');
    }
    cs.animate.$disabled = true;
    F.fetch.beforesend = ()=>cs.ajaxStart();
    F.fetch.aftersend = ()=>cs.ajaxEnd();
    cs.pageTitleOrig = cs.e.pageTitle.innerText;
    const qs = (e)=>document.querySelector(e);
    const argsToArray = function(args){
700
701
702
703
704
705
706
707

708


709
710
711
712
713
714
715
716
717
718
719
720
721
    };
    /**
       Reports an error in the form of a new message in the chat
       feed. All arguments are appended to the message's content area
       using fossil.dom.append(), so may be of any type supported by
       that function.
    */
    cs.reportErrorAsMessage = function(/*msg args*/){

      const args = argsToArray(arguments);


      console.error("chat error:",args);
      const d = new Date().toISOString(),
            mw = new this.MessageWidget({
              isError: true,
              xfrom: null,
              msgid: -1,
              mtime: d,
              lmtime: d,
              xmsg: args
            });
      this.injectMessageElem(mw.e.body);
      mw.scrollIntoView();
    };







|
>
|
>
>





|







712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
    };
    /**
       Reports an error in the form of a new message in the chat
       feed. All arguments are appended to the message's content area
       using fossil.dom.append(), so may be of any type supported by
       that function.
    */
    cs.reportErrorAsMessage = function f(/*msg args*/){
      if(undefined === f.$msgid) f.$msgid=0;
      const args = argsToArray(arguments).map(function(v){
        return (v instanceof Error) ? v.message : v;
      });
      console.error("chat error:",args);
      const d = new Date().toISOString(),
            mw = new this.MessageWidget({
              isError: true,
              xfrom: null,
              msgid: "error-"+(++f.$msgid),
              mtime: d,
              lmtime: d,
              xmsg: args
            });
      this.injectMessageElem(mw.e.body);
      mw.scrollIntoView();
    };
871
872
873
874
875
876
877










878
879
880
881
882
883
884
        this.deleteMessageElem(id);
      }
    };
    document.addEventListener('visibilitychange', function(ev){
      cs.pageIsActive = ('visible' === document.visibilityState);
      if(cs.pageIsActive){
        cs.e.pageTitle.innerText = cs.pageTitleOrig;










      }
    }, true);
    cs.setCurrentView(cs.e.viewMessages);

    cs.e.activeUserList.addEventListener('click', function f(ev){
      /* Filter messages on a user clicked in activeUserList */
      ev.stopPropagation();







>
>
>
>
>
>
>
>
>
>







886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
        this.deleteMessageElem(id);
      }
    };
    document.addEventListener('visibilitychange', function(ev){
      cs.pageIsActive = ('visible' === document.visibilityState);
      if(cs.pageIsActive){
        cs.e.pageTitle.innerText = cs.pageTitleOrig;
        if(document.activeElement!==cs.inputElement()){
          /* An attempt to resolve usability problem reported by Joe
             M. where the Pale Moon browser is giving input focus to
             the Preview button. The down-side of this is that it will
             deselect any text which was previously selected on this
             page. This also, unfortunately, places the focus at the
             start of the element, rather than the last cursor position
             (like a textarea would). */
          setTimeout(()=>cs.inputFocus(), 0);
        }
      }
    }, true);
    cs.setCurrentView(cs.e.viewMessages);

    cs.e.activeUserList.addEventListener('click', function f(ev){
      /* Filter messages on a user clicked in activeUserList */
      ev.stopPropagation();
987
988
989
990
991
992
993









994
995
996
997
998
999
1000
      e.dataset.hashtag = e.dataset.hashtag.toLowerCase();
      e.addEventListener('click', f.$click, false);
    })
    elem.querySelectorAll('[data-numtag]').forEach(
      (e)=>e.addEventListener('click', f.$clickNum, false)
    )
  }/*setupHashtags()*/;










  /**
     Custom widget type for rendering messages (one message per
     instance). These are modelled after FIELDSET elements but we
     don't use FIELDSET because of cross-browser inconsistencies in
     features of the FIELDSET/LEGEND combination, e.g. inability to
     align legends via CSS in Firefox and clicking-related







>
>
>
>
>
>
>
>
>







1012
1013
1014
1015
1016
1017
1018
1019
1020
1021
1022
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
      e.dataset.hashtag = e.dataset.hashtag.toLowerCase();
      e.addEventListener('click', f.$click, false);
    })
    elem.querySelectorAll('[data-numtag]').forEach(
      (e)=>e.addEventListener('click', f.$clickNum, false)
    )
  }/*setupHashtags()*/;

  /** Returns the first .message-widget element in DOM element
      e's lineage. */
  const findMessageWidgetParent = function(e){
    while( e && !e.classList.contains('message-widget')){
      e = e.parentNode;
    }
    return e;
  };

  /**
     Custom widget type for rendering messages (one message per
     instance). These are modelled after FIELDSET elements but we
     don't use FIELDSET because of cross-browser inconsistencies in
     features of the FIELDSET/LEGEND combination, e.g. inability to
     align legends via CSS in Firefox and clicking-related
1014
1015
1016
1017
1018
1019
1020
1021
1022
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
1035
1036
1037
1038

1039
1040
1041
1042
1043
1044
1045
      D.append(this.e.body, this.e.tab, this.e.content);
      this.e.tab.setAttribute('role', 'button');
      if(arguments.length){
        this.setMessage(arguments[0]);
      }
    };
    /* Left-zero-pad a number to at least 2 digits */
    const pad2 = (x)=>(''+x).length>1 ? x : '0'+x;
    const dowMap = {
      /* Map of Date.getDay() values to weekday names. */
      0: "Sunday", 1: "Monday", 2: "Tuesday",
      3: "Wednesday", 4: "Thursday", 5: "Friday",
      6: "Saturday"
    };
    /* Given a Date, returns the timestamp string used in the
       "tab" part of message widgets. */
    const theTime = function(d){
      return [
        //d.getFullYear(),'-',pad2(d.getMonth()+1/*sigh*/),
        //'-',pad2(d.getDate()), ' ',
        d.getHours(),":",
        (d.getMinutes()+100).toString().slice(1,3),
        ' ', dowMap[d.getDay()]
      ].join('');
    };

    cf.prototype = {
      scrollIntoView: function(){
        this.e.content.scrollIntoView();
      },
      setMessage: function(m){
        const ds = this.e.body.dataset;
        ds.timestamp = m.mtime;







<

















>







1048
1049
1050
1051
1052
1053
1054

1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
1066
1067
1068
1069
1070
1071
1072
1073
1074
1075
1076
1077
1078
1079
      D.append(this.e.body, this.e.tab, this.e.content);
      this.e.tab.setAttribute('role', 'button');
      if(arguments.length){
        this.setMessage(arguments[0]);
      }
    };
    /* Left-zero-pad a number to at least 2 digits */

    const dowMap = {
      /* Map of Date.getDay() values to weekday names. */
      0: "Sunday", 1: "Monday", 2: "Tuesday",
      3: "Wednesday", 4: "Thursday", 5: "Friday",
      6: "Saturday"
    };
    /* Given a Date, returns the timestamp string used in the
       "tab" part of message widgets. */
    const theTime = function(d){
      return [
        //d.getFullYear(),'-',pad2(d.getMonth()+1/*sigh*/),
        //'-',pad2(d.getDate()), ' ',
        d.getHours(),":",
        (d.getMinutes()+100).toString().slice(1,3),
        ' ', dowMap[d.getDay()]
      ].join('');
    };

    cf.prototype = {
      scrollIntoView: function(){
        this.e.content.scrollIntoView();
      },
      setMessage: function(m){
        const ds = this.e.body.dataset;
        ds.timestamp = m.mtime;
1066
1067
1068
1069
1070
1071
1072
1073
1074
1075
1076
1077
1078
1079
1080
        }else{/*notification*/
          D.addClass(this.e.body, 'notification');
          if(m.isError){
            D.addClass([contentTarget, this.e.tab], 'error');
          }
          D.append(
            this.e.tab,
            D.text('notification @ ',theTime(d))
          );
        }
        if( m.xfrom && m.fsize>0 ){
          if( m.fmime
              && m.fmime.startsWith("image/")
              && Chat.settings.getBool('images-inline',true)
            ){







|







1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
        }else{/*notification*/
          D.addClass(this.e.body, 'notification');
          if(m.isError){
            D.addClass([contentTarget, this.e.tab], 'error');
          }
          D.append(
            this.e.tab,
            D.append(D.code(), 'notification @ ',theTime(d))
          );
        }
        if( m.xfrom && m.fsize>0 ){
          if( m.fmime
              && m.fmime.startsWith("image/")
              && Chat.settings.getBool('images-inline',true)
            ){
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121


1122
1123
1124
1125
1126
1127
1128
          // sense that it is not possible for a malefactor to inject HTML
          // or javascript or CSS.  The m.xmsg content might contain
          // hyperlinks, but otherwise it will be markup-free.  See the
          // chat_format_to_html() routine in the server for details.
          //
          // Hence, even though innerHTML is normally frowned upon, it is
          // perfectly safe to use in this context.
          if(m.xmsg instanceof Array){
            // Used by Chat.reportErrorAsMessage()
            D.append(contentTarget, m.xmsg);
          }else{
            contentTarget.innerHTML = m.xmsg;
            contentTarget.querySelectorAll('a').forEach(addAnchorTargetBlank);
            setupHashtags(contentTarget);
            if(F.pikchr){
              F.pikchr.addSrcView(contentTarget.querySelectorAll('svg.pikchr'));
            }
          }
        }


        this.e.tab.firstElementChild.addEventListener('click', this._handleLegendClicked, false);
        /*if(eXFrom){
          eXFrom.addEventListener('click', ()=>this.e.tab.click(), false);
        }*/
        return this;
      },
      /* Event handler for clicking .message-user elements to show their







|











>
>







1137
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
          // sense that it is not possible for a malefactor to inject HTML
          // or javascript or CSS.  The m.xmsg content might contain
          // hyperlinks, but otherwise it will be markup-free.  See the
          // chat_format_to_html() routine in the server for details.
          //
          // Hence, even though innerHTML is normally frowned upon, it is
          // perfectly safe to use in this context.
          if(m.xmsg && 'string' !== typeof m.xmsg){
            // Used by Chat.reportErrorAsMessage()
            D.append(contentTarget, m.xmsg);
          }else{
            contentTarget.innerHTML = m.xmsg;
            contentTarget.querySelectorAll('a').forEach(addAnchorTargetBlank);
            setupHashtags(contentTarget);
            if(F.pikchr){
              F.pikchr.addSrcView(contentTarget.querySelectorAll('svg.pikchr'));
            }
          }
        }
        //console.debug("tab",this.e.tab);
        //console.debug("this.e.tab.firstElementChild",this.e.tab.firstElementChild);
        this.e.tab.firstElementChild.addEventListener('click', this._handleLegendClicked, false);
        /*if(eXFrom){
          eXFrom.addEventListener('click', ()=>this.e.tab.click(), false);
        }*/
        return this;
      },
      /* Event handler for clicking .message-user elements to show their
1247
1248
1249
1250
1251
1252
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262
1263
1264
                return;
              }
              this.$eMsg = tgtMsg;
              this.refresh();
            }
          }/*f.popup*/;
        }/*end static init*/
        let theMsg = ev.target;
        while( theMsg && !theMsg.classList.contains('message-widget')){
          theMsg = theMsg.parentNode;
        }
        if(theMsg) f.popup.show(theMsg);
      }/*_handleLegendClicked()*/
    }/*MessageWidget.prototype*/;
    /** Assumes that e is a MessageWidget element, ensures that
        Chat.e.viewMessages is visible, scrolls the message,
        and animates it a bit to make it more visible. */
    cf.scrollToMessageElem = function(e){







|
<
<
<







1283
1284
1285
1286
1287
1288
1289
1290



1291
1292
1293
1294
1295
1296
1297
                return;
              }
              this.$eMsg = tgtMsg;
              this.refresh();
            }
          }/*f.popup*/;
        }/*end static init*/
        const theMsg = findMessageWidgetParent(ev.target);



        if(theMsg) f.popup.show(theMsg);
      }/*_handleLegendClicked()*/
    }/*MessageWidget.prototype*/;
    /** Assumes that e is a MessageWidget element, ensures that
        Chat.e.viewMessages is visible, scrolls the message,
        and animates it a bit to make it more visible. */
    cf.scrollToMessageElem = function(e){
1281
1282
1283
1284
1285
1286
1287
1288
1289
1290
1291
1292
1293
1294
1295
        D.clearElement(this.dropDetails);
        Chat.e.inputFile.value = "";
      }
    };
    /** Updates the paste/drop zone with details of the pasted/dropped
        data. The argument must be a Blob or Blob-like object (File) or
        it can be falsy to reset/clear that state.*/
    const updateDropZoneContent = function(blob){
      //console.debug("updateDropZoneContent()",blob);
      const dd = bxs.dropDetails;
      bxs.blob = blob;
      D.clearElement(dd);
      if(!blob){
        Chat.e.inputFile.value = '';
        return;







|







1314
1315
1316
1317
1318
1319
1320
1321
1322
1323
1324
1325
1326
1327
1328
        D.clearElement(this.dropDetails);
        Chat.e.inputFile.value = "";
      }
    };
    /** Updates the paste/drop zone with details of the pasted/dropped
        data. The argument must be a Blob or Blob-like object (File) or
        it can be falsy to reset/clear that state.*/
    const updateDropZoneContent = bxs.updateDropZoneContent = function(blob){
      //console.debug("updateDropZoneContent()",blob);
      const dd = bxs.dropDetails;
      bxs.blob = blob;
      D.clearElement(dd);
      if(!blob){
        Chat.e.inputFile.value = '';
        return;
1330
1331
1332
1333
1334
1335
1336
1337
1338
1339
1340
1341
1342
1343
1344
    document.addEventListener('paste', pasteListener, true);
    if(window.Selection && window.Range && !Chat.$browserHasPlaintextOnly){
      /* Acrobatics to keep *some* installations of Firefox
         from pasting formatting into contenteditable fields.
         This also works on Chrome, but chrome has the
         contenteditable=plaintext-only property which does this
         for us. */
      Chat.inputElement().addEventListener(
        'paste',
        function(ev){
          if (ev.clipboardData && ev.clipboardData.getData) {
            const pastedText = ev.clipboardData.getData('text/plain');
            const selection = window.getSelection();
            if (!selection.rangeCount) return false;
            selection.deleteFromDocument(/*remove selected content*/);







|







1363
1364
1365
1366
1367
1368
1369
1370
1371
1372
1373
1374
1375
1376
1377
    document.addEventListener('paste', pasteListener, true);
    if(window.Selection && window.Range && !Chat.$browserHasPlaintextOnly){
      /* Acrobatics to keep *some* installations of Firefox
         from pasting formatting into contenteditable fields.
         This also works on Chrome, but chrome has the
         contenteditable=plaintext-only property which does this
         for us. */
      Chat.e.inputX.addEventListener(
        'paste',
        function(ev){
          if (ev.clipboardData && ev.clipboardData.getData) {
            const pastedText = ev.clipboardData.getData('text/plain');
            const selection = window.getSelection();
            if (!selection.rangeCount) return false;
            selection.deleteFromDocument(/*remove selected content*/);
1354
1355
1356
1357
1358
1359
1360
1361
1362
1363
1364
1365
1366
1367
1368
1369
1370
1371
1372
1373
1374
1375
1376
1377
1378
1379
1380


































1381
1382
1383
1384
1385
1386
1387
1388
1389
1390
1391
1392
1393
1394

1395
1396
1397
1398
1399
1400
1401
         which is not compatible with how we use it, so... */
      ev.dataTransfer.effectAllowed = 'none';
      ev.dataTransfer.dropEffect = 'none';
      ev.preventDefault();
      ev.stopPropagation();
      return false;
    };

    ['drop','dragenter','dragleave','dragend'].forEach(
      (k)=>{
        Chat.inputElement().addEventListener(k, noDragDropEvents, false);
      }
    );
    return bxs;
  })()/*drag/drop/paste*/;

  const tzOffsetToString = function(off){
    const hours = Math.round(off/60), min = Math.round(off % 30);
    return ''+(hours + (min ? '.5' : ''));
  };
  const pad2 = (x)=>('0'+x).substr(-2);
  const localTime8601 = function(d){
    return [
      d.getYear()+1900, '-', pad2(d.getMonth()+1), '-', pad2(d.getDate()),
      'T', pad2(d.getHours()),':', pad2(d.getMinutes()),':',pad2(d.getSeconds())
    ].join('');
  };



































  /**
     Submits the contents of the message input field (if not empty)
     and/or the file attachment field to the server. If both are
     empty, this is a no-op.
  */
  Chat.submitMessage = function f(){
    if(!f.spaces){
      f.spaces = /\s+$/;
      f.markdownContinuation = /\\\s+$/;
    }
    this.setCurrentView(this.e.viewMessages);
    const fd = new FormData();
    var msg = this.inputValue().trim();

    if(msg && (msg.indexOf('\n')>0 || f.spaces.test(msg))){
      /* Cosmetic: trim whitespace from the ends of lines to try to
         keep copy/paste from terminals, especially wide ones, from
         forcing a horizontal scrollbar on all clients. This breaks
         markdown's use of blackslash-space-space for paragraph
         continuation, but *not* doing this affects all clients every
         time someone pastes in console copy/paste from an affected







<

<
|
<








<






>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>













|
>







1387
1388
1389
1390
1391
1392
1393

1394

1395

1396
1397
1398
1399
1400
1401
1402
1403

1404
1405
1406
1407
1408
1409
1410
1411
1412
1413
1414
1415
1416
1417
1418
1419
1420
1421
1422
1423
1424
1425
1426
1427
1428
1429
1430
1431
1432
1433
1434
1435
1436
1437
1438
1439
1440
1441
1442
1443
1444
1445
1446
1447
1448
1449
1450
1451
1452
1453
1454
1455
1456
1457
1458
1459
1460
1461
1462
1463
1464
1465
         which is not compatible with how we use it, so... */
      ev.dataTransfer.effectAllowed = 'none';
      ev.dataTransfer.dropEffect = 'none';
      ev.preventDefault();
      ev.stopPropagation();
      return false;
    };

    ['drop','dragenter','dragleave','dragend'].forEach(

      (k)=>Chat.e.inputX.addEventListener(k, noDragDropEvents, false)

    );
    return bxs;
  })()/*drag/drop/paste*/;

  const tzOffsetToString = function(off){
    const hours = Math.round(off/60), min = Math.round(off % 30);
    return ''+(hours + (min ? '.5' : ''));
  };

  const localTime8601 = function(d){
    return [
      d.getYear()+1900, '-', pad2(d.getMonth()+1), '-', pad2(d.getDate()),
      'T', pad2(d.getHours()),':', pad2(d.getMinutes()),':',pad2(d.getSeconds())
    ].join('');
  };

  /**
     Called by Chat.submitMessage() when message sending failed. Injects a fake message
     containing the content and attachment of the failed message and gives the user buttons
     to discard it or edit and retry.
   */
  const recoverFailedMessage = function(state){
    const w = D.addClass(D.div(), 'failed-message');
    D.append(w, D.append(
      D.span(),"This message was not successfully sent to the server:"
    ));
    if(state.msg){
      const ta = D.textarea();
      ta.value = state.msg;
      D.append(w,ta);
    }
    if(state.blob){
      D.append(w,D.append(D.span(),"Attachment: ",(state.blob.name||"unnamed")));
      //console.debug("blob = ",state.blob);
    }
    const buttons = D.addClass(D.div(), 'buttons');
    D.append(w, buttons);
    D.append(buttons, D.button("Discard message?", function(){
      let theMsg = findMessageWidgetParent(w);
      if(theMsg) Chat.deleteMessageElem(theMsg);
    }));
    D.append(buttons, D.button("Edit message and try again?", function(){
      if(state.msg) Chat.inputValue(ta.value);
      if(state.blob) BlobXferState.updateDropZoneContent(state.blob);
      let theMsg = findMessageWidgetParent(w);
      if(theMsg) Chat.deleteMessageElem(theMsg);
    }));
    Chat.reportErrorAsMessage(w);
  };

  /**
     Submits the contents of the message input field (if not empty)
     and/or the file attachment field to the server. If both are
     empty, this is a no-op.
  */
  Chat.submitMessage = function f(){
    if(!f.spaces){
      f.spaces = /\s+$/;
      f.markdownContinuation = /\\\s+$/;
    }
    this.setCurrentView(this.e.viewMessages);
    const fd = new FormData();
    const fallback = {msg: this.inputValue()};
    var msg = fallback.msg.trim();
    if(msg && (msg.indexOf('\n')>0 || f.spaces.test(msg))){
      /* Cosmetic: trim whitespace from the ends of lines to try to
         keep copy/paste from terminals, especially wide ones, from
         forcing a horizontal scrollbar on all clients. This breaks
         markdown's use of blackslash-space-space for paragraph
         continuation, but *not* doing this affects all clients every
         time someone pastes in console copy/paste from an affected
1410
1411
1412
1413
1414
1415
1416

1417
1418
1419
1420
1421

1422


1423
1424
1425
1426
1427
1428
1429
1430
1431

1432
1433
1434
1435
1436
1437
1438
      });
      msg = xmsg.join('\n');
    }
    if(msg) fd.set('msg',msg);
    const file = BlobXferState.blob || this.e.inputFile.files[0];
    if(file) fd.set("file", file);
    if( !msg && !file ) return;

    const self = this;
    fd.set("lmtime", localTime8601(new Date()));
    F.fetch("chat-send",{
      payload: fd,
      responseType: 'text',

      onerror:(err)=>this.reportErrorAsMessage(err),


      onload:function(txt){
        if(!txt) return/*success response*/;
        try{
          const json = JSON.parse(txt);
          self.newContent({msgs:[json]});
        }catch(e){
          self.reportError(e);
          return;
        }

      }
    });
    BlobXferState.clear();
    Chat.inputValue("").inputFocus();
  };

  const inputWidgetKeydown = function f(ev){







>





>
|
>
>







<

>







1474
1475
1476
1477
1478
1479
1480
1481
1482
1483
1484
1485
1486
1487
1488
1489
1490
1491
1492
1493
1494
1495
1496
1497

1498
1499
1500
1501
1502
1503
1504
1505
1506
      });
      msg = xmsg.join('\n');
    }
    if(msg) fd.set('msg',msg);
    const file = BlobXferState.blob || this.e.inputFile.files[0];
    if(file) fd.set("file", file);
    if( !msg && !file ) return;
    fallback.blob = file;
    const self = this;
    fd.set("lmtime", localTime8601(new Date()));
    F.fetch("chat-send",{
      payload: fd,
      responseType: 'text',
      onerror:function(err){
        self.reportErrorAsMessage(err);
        recoverFailedMessage(fallback);
      },
      onload:function(txt){
        if(!txt) return/*success response*/;
        try{
          const json = JSON.parse(txt);
          self.newContent({msgs:[json]});
        }catch(e){
          self.reportError(e);

        }
        recoverFailedMessage(fallback);
      }
    });
    BlobXferState.clear();
    Chat.inputValue("").inputFocus();
  };

  const inputWidgetKeydown = function f(ev){
1492
1493
1494
1495
1496
1497
1498

1499

1500
1501
1502
1503
1504
1505
1506
      /* Ship it! */
      ev.preventDefault();
      ev.stopPropagation();
      Chat.submitMessage();
      return false;
    }
  };  

  Chat.e.inputField.addEventListener('keydown', inputWidgetKeydown, false);

  Chat.e.btnSubmit.addEventListener('click',(e)=>{
    e.preventDefault();
    Chat.submitMessage();
    return false;
  });
  Chat.e.btnAttach.addEventListener(
    'click', ()=>Chat.e.inputFile.click(), false);







>
|
>







1560
1561
1562
1563
1564
1565
1566
1567
1568
1569
1570
1571
1572
1573
1574
1575
1576
      /* Ship it! */
      ev.preventDefault();
      ev.stopPropagation();
      Chat.submitMessage();
      return false;
    }
  };  
  Chat.e.inputFields.forEach(
    (e)=>e.addEventListener('keydown', inputWidgetKeydown, false)
  );
  Chat.e.btnSubmit.addEventListener('click',(e)=>{
    e.preventDefault();
    Chat.submitMessage();
    return false;
  });
  Chat.e.btnAttach.addEventListener(
    'click', ()=>Chat.e.inputFile.click(), false);
1551
1552
1553
1554
1555
1556
1557
1558
1559
1560


1561
1562
1563
1564
1565







1566







1567
1568
1569
1570
1571
1572
1573

1574
1575













1576
1577
1578
1579
1580
1581
1582
1583
1584
1585
1586
1587
1588
1589
1590
1591
1592
1593












1594
1595
1596
1597
1598
1599
1600
1601
1602
1603
1604
1605
1606
1607
1608
1609
1610
1611
1612
1613
1614
1615
1616
1617
1618

1619
1620
1621
1622
1623

1624
1625
1626
1627
1628
1629
1630
    }/*namedOptions.activeUsers additional setup*/
    /**
       Settings options structure: an array of Objects with the
       following properties:

       label: string for the UI

       boolValue: string (name of Chat.settings setting) or a
       function which returns true or false. Gets mapped to
       a checkbox.



       select: SELECT element (instead of boolValue)

       callback: optional handler to call after setting is modified.
       It gets passed the setting object: {key:string, value:something}.















       If a setting has a boolValue set, that gets transformed into a
       checkbox which toggles the given persistent setting (if
       boolValue is a string) AND listens for changes to that setting
       fired via Chat.settings.set() so that the checkbox can stay in
       sync with external changes to that setting. Various Chat UI
       elements stay in sync with the config UI via those settings
       events.

    */
    const settingsOps = [{













      label: "Ctrl-enter to Send",
      hint: [
        "When on, only Ctrl-Enter will send messages and Enter adds ",
        "blank lines. ",
        "When off, both Enter and Ctrl-Enter send. ",
        "When the input field has focus, is empty, and preview ",
        "mode is NOT active then Ctrl-Enter toggles this setting."
      ].join(''),
      boolValue: 'edit-ctrl-send'
    },{
      label: "Compact mode",
      hint: [
        "Toggle between a space-saving or more spacious writing area. ",
        "When the input field has focus, is empty, and preview mode ",
        "is NOT active then Shift-Enter toggles this setting."
      ].join(''),
      boolValue: 'edit-compact-mode'
    },{












      label: "Left-align my posts",
      hint: "Default alignment of your own messages is selected "
        +"based window width/height relationship.",
      boolValue: ()=>!document.body.classList.contains('my-messages-right'),
      callback: function f(){
        document.body.classList[
          this.checkbox.checked ? 'remove' : 'add'
        ]('my-messages-right');
      }
    },{
      label: "Monospace message font",
      hint: "Use monospace font for message text?",
      boolValue: 'monospace-messages',
      callback: function(setting){
        document.body.classList[
          setting.value ? 'add' : 'remove'
        ]('monospace-messages');
      }
    },{
      label: "Chat-only mode",
      hint: "Toggle the page between normal fossil view and chat-only view.",
      boolValue: 'chat-only-mode'
    },{
      label: "Show images inline",
      hint: "Whether to show images inline or as a hyperlink.",

      boolValue: 'images-inline'
    },namedOptions.activeUsers,{
      label: "Timestamps in active users list",
      hint: "Whether to show last-message timestamps.",
      boolValue: 'active-user-list-timestamps'

    }];

    /** Set up selection list of notification sounds. */
    if(1){
      const selectSound = D.select();
      D.option(selectSound, "", "(no audio)");
      const firstSoundIndex = selectSound.options.length;







|
|
|
>
>





>
>
>
>
>
>
>

>
>
>
>
>
>
>
|





|
>


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







1621
1622
1623
1624
1625
1626
1627
1628
1629
1630
1631
1632
1633
1634
1635
1636
1637
1638
1639
1640
1641
1642
1643
1644
1645
1646
1647
1648
1649
1650
1651
1652
1653
1654
1655
1656
1657
1658
1659
1660
1661
1662
1663
1664
1665
1666
1667
1668
1669
1670
1671
1672
1673
1674
1675
1676
1677
1678

1679
1680
1681
1682
1683
1684
1685
1686
1687
1688
1689

1690
1691
1692
1693
1694
1695
1696
1697
1698
1699
1700
1701
1702
1703
1704
1705
1706
1707
1708
1709
1710
1711
1712
1713
1714
1715
1716
1717
1718
1719
1720
1721
1722




1723
1724
1725
1726




1727
1728
1729
1730
1731
1732
1733
1734
    }/*namedOptions.activeUsers additional setup*/
    /**
       Settings options structure: an array of Objects with the
       following properties:

       label: string for the UI

       boolValue: string (name of Chat.settings setting) or a function
       which returns true or false. If it is a string, it gets
       replaced by a function which returns
       Chat.settings.getBool(thatString) and the string gets assigned
       to the persistentSetting property of this object.

       select: SELECT element (instead of boolValue)

       callback: optional handler to call after setting is modified.
       It gets passed the setting object: {key:string, value:something}.
       Its "this" is the options object. If this object has a
       boolValue string or a persistentSetting property, the argument
       passed to the callback is a settings object in the form {key:K,
       value:V}. If this object does not have boolValue string or
       persistentSetting then the callback is passed an event object
       in response to the config option's UI widget being activated,
       normally a 'change' event.

       children: [array of settings objects]. These get listed under
       this element and indented slightly for visual grouping. Only
       one level of indention is supported.

       Elements which only have a label and maybe a hint and
       children can be used as headings.

       If a setting has a boolValue set, that gets rendered as a
       checkbox which toggles the given persistent setting (if
       boolValue is a string) AND listens for changes to that setting
       fired via Chat.settings.set() so that the checkbox can stay in
       sync with external changes to that setting. Various Chat UI
       elements stay in sync with the config UI via those settings
       events. The checkbox element gets added to the options object
       so that the callback() can reference it via this.checkbox.
    */
    const settingsOps = [{
      label: "Chat Configuration Options",
      hint: F.storage.isTransient()
        ? "Local store is unavailable. These settings are transient."
        : ["Most of these settings are persistent via ",
           F.storage.storageImplName(), ": ",
           F.storage.storageHelpDescription()].join('')
    },{
      label: "Editing Options...",
      children:[{
        label: "Chat-only mode",
        hint: "Toggle the page between normal fossil view and chat-only view.",
        boolValue: 'chat-only-mode'
      },{
        label: "Ctrl-enter to Send",
        hint: [
          "When on, only Ctrl-Enter will send messages and Enter adds ",

          "blank lines. When off, both Enter and Ctrl-Enter send. ",
          "When the input field has focus and is empty ",
          "then Ctrl-Enter toggles this setting."
        ].join(''),
        boolValue: 'edit-ctrl-send'
      },{
        label: "Compact mode",
        hint: [
          "Toggle between a space-saving or more spacious writing area. ",
          "When the input field has focus, is empty, and preview mode ",
          "is NOT active then Shift-Enter toggles this setting."].join(''),

        boolValue: 'edit-compact-mode'
      },{
        label: "Use 'contenteditable' editing mode",
        boolValue: 'edit-widget-x',
        hint: [
          "When enabled, chat input uses a so-called 'contenteditable' ",
          "field. Though generally more comfortable and modern than ",
          "plain-text input fields, browser-specific quirks and bugs ",
          "may lead to frustration. Ideal for mobile devices."
        ].join('')
      }]
    },{
      label: "Appearance Options...",
      children:[{
        label: "Left-align my posts",
        hint: "Default alignment of your own messages is selected "
          + "based window width/height ratio.",
        boolValue: ()=>!document.body.classList.contains('my-messages-right'),
        callback: function f(){
          document.body.classList[
            this.checkbox.checked ? 'remove' : 'add'
          ]('my-messages-right');
        }
      },{
        label: "Monospace message font",
        hint: "Use monospace font for message and input text.",
        boolValue: 'monospace-messages',
        callback: function(setting){
          document.body.classList[
            setting.value ? 'add' : 'remove'
          ]('monospace-messages');
        }
      },{




        label: "Show images inline",
        hint: "When enabled, attached images are shown inline, "+
          "else they appear as a download link.",
        boolValue: 'images-inline'




      }]
    }];

    /** Set up selection list of notification sounds. */
    if(1){
      const selectSound = D.select();
      D.option(selectSound, "", "(no audio)");
      const firstSoundIndex = selectSound.options.length;
1639
1640
1641
1642
1643
1644
1645

1646


1647
1648
1649
1650
1651
1652
1653
1654
1655
1656
1657
1658
1659
1660
1661
















1662
1663
1664
1665
1666
1667

1668
1669
1670
1671
1672
1673
1674
1675
1676


1677
1678
1679
1680
1681
1682
1683
1684
1685
1686
1687
1688
1689
1690
1691
1692
1693
1694
1695

1696
1697
1698

1699
1700
1701
1702
1703
1704
1705
1706

1707

1708
1709
1710
1711
1712
1713
1714
1715
1716
1717
1718
1719
1720
1721
1722
1723
1724
1725
1726
1727
1728
1729
1730




1731
1732
1733
1734
1735
1736
1737
1738
1739
1740
1741
1742
1743
1744
1745
1746
1747
1748
1749
1750





















1751




1752









1753
1754

1755
1756
1757
1758
1759



1760
1761
1762
1763
1764
1765
1766
          /* Missing file - removed after this setting was
            applied. Fall back to the first sound in the list. */
          selectSound.selectedIndex = firstSoundIndex;
        }
      }
      Chat.setNewMessageSound(selectSound.value);
      settingsOps.push({

        hint: "Audio alert. How to enable audio playback is browser-specific!",


        select: selectSound,
        callback: function(ev){
          const v = ev.target.value;
          Chat.setNewMessageSound(v);
          F.toast.message("Audio notifications "+(v ? "enabled" : "disabled")+".");
          if(v) setTimeout(()=>Chat.playNewMessageSound(), 0);
        }
      });
    }/*audio notification config*/
    settingsOps.push({
      label: "Play notification for your own messages.",
      hint: "When enabled, the audio notification will be played for all messages, "+
        "including your own. When disabled only messages from other users "+
        "will trigger a notification.",
      boolValue: 'alert-own-messages'
















    });
    /**
       Build UI for config options...
    */
    settingsOps.forEach(function f(op){
      const line = D.addClass(D.div(), 'menu-entry');

      const label = op.label
            ? D.append(D.label(),op.label) : undefined;
      const labelWrapper = D.addClass(D.div(), 'label-wrapper');
      var hint;
      const col0 = D.span();
      if(op.hint){
        hint = D.append(D.addClass(D.span(),'hint'),op.hint);
      }
      if(op.hasOwnProperty('select')){


        D.append(line, col0, labelWrapper);
        D.append(labelWrapper, op.select);
        if(hint) D.append(labelWrapper, hint);
        if(label) D.append(col0, label);
        if(op.callback){
          op.select.addEventListener('change', (ev)=>op.callback(ev), false);
        }
      }else if(op.hasOwnProperty('boolValue')){
        if(undefined === f.$id) f.$id = 0;
        ++f.$id;
        if('string' ===typeof op.boolValue){
          const key = op.boolValue;
          op.boolValue = ()=>Chat.settings.getBool(key);
          op.persistentSetting = key;
        }
        const check = op.checkbox
              = D.attr(D.checkbox(1, op.boolValue()),
                       'aria-label', op.label);
        const id = 'cfgopt'+f.$id;

        check.checked = op.boolValue();
        op.checkbox = check;
        D.attr(check, 'id', id);

        D.append(line, col0, labelWrapper);
        D.append(col0, check);
        if(label){
          D.attr(label, 'for', id);
          D.append(labelWrapper, label);
        }
        if(hint) D.append(labelWrapper, hint);
      }else{

        line.addEventListener('click', callback);

        D.append(line, col0, labelWrapper);
        if(label) D.append(labelWrapper, label);
        if(hint) D.append(labelWrapper, hint);
      }
      D.append(optionsMenu, line);
      if(op.persistentSetting){
        Chat.settings.addListener(
          op.persistentSetting,
          function(setting){
            if(op.checkbox) op.checkbox.checked = !!setting.value;
            else if(op.select) op.select.value = setting.value;
            if(op.callback) op.callback(setting);
          }             
        );
        if(op.checkbox){
          op.checkbox.addEventListener(
            'change', function(){
              Chat.settings.set(op.persistentSetting, op.checkbox.checked)
            }, false);
        }
      }else if(op.callback && op.checkbox){
        op.checkbox.addEventListener('change', (ev)=>op.callback(ev), false);
      }




    });
  })()/*#chat-button-settings setup*/;

  (function(){
    /* Install default settings... must come after
       chat-button-settings setup so that the listeners which that
       installs are notified via the properties getting initialized
       here. */
    Chat.settings.addListener('monospace-messages',function(s){
      document.body.classList[s.value ? 'add' : 'remove']('monospace-messages');
    })
    Chat.settings.addListener('active-user-list',function(s){
      Chat.showActiveUserList(s.value);
    });
    Chat.settings.addListener('active-user-list-timestamps',function(s){
      Chat.showActiveUserTimestamps(s.value);
    });
    Chat.settings.addListener('chat-only-mode',function(s){
      Chat.chatOnlyMode(s.value);
    });





















    Chat.settings.addListener('edit-compact-mode',function(s){




      Chat.e.inputLine.classList[









        s.value ? 'add' : 'remove'
      ]('compact');

    });
    Chat.settings.addListener('edit-ctrl-send',function(s){
      const label = (s.value ? "Ctrl-" : "")+"Enter submits messages.";
      const eInput = Chat.inputElement();
      eInput.dataset.placeholder = eInput.dataset.placeholder0 + " " +label;



      Chat.e.btnSubmit.title = label;
    });
    const valueKludges = {
      /* Convert certain string-format values to other types... */
      "false": false,
      "true": true
    };







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




|
|
>




<

|


>
>
|


|















>



>
|







>
|
>
|



|


















>
>
>
>




















>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>

>
>
>
>
|
>
>
>
>
>
>
>
>
>


>



|
|
>
>
>







1743
1744
1745
1746
1747
1748
1749
1750
1751
1752
1753
1754
1755
1756
1757
1758
1759
1760
1761


1762
1763
1764
1765
1766
1767
1768
1769
1770
1771
1772
1773
1774
1775
1776
1777
1778
1779
1780
1781
1782
1783
1784
1785
1786
1787
1788
1789
1790
1791
1792
1793

1794
1795
1796
1797
1798
1799
1800
1801
1802
1803
1804
1805
1806
1807
1808
1809
1810
1811
1812
1813
1814
1815
1816
1817
1818
1819
1820
1821
1822
1823
1824
1825
1826
1827
1828
1829
1830
1831
1832
1833
1834
1835
1836
1837
1838
1839
1840
1841
1842
1843
1844
1845
1846
1847
1848
1849
1850
1851
1852
1853
1854
1855
1856
1857
1858
1859
1860
1861
1862
1863
1864
1865
1866
1867
1868
1869
1870
1871
1872
1873
1874
1875
1876
1877
1878
1879
1880
1881
1882
1883
1884
1885
1886
1887
1888
1889
1890
1891
1892
1893
1894
1895
1896
1897
1898
1899
1900
1901
1902
1903
1904
1905
1906
1907
1908
1909
1910
1911
1912
1913
1914
1915
1916
1917
1918
1919
1920
1921
1922
1923
1924
1925
1926
1927
1928
1929
1930
1931
1932
1933
1934
1935
          /* Missing file - removed after this setting was
            applied. Fall back to the first sound in the list. */
          selectSound.selectedIndex = firstSoundIndex;
        }
      }
      Chat.setNewMessageSound(selectSound.value);
      settingsOps.push({
        label: "Sound Options...",
        hint: "How to enable audio playback is browser-specific!",
        children:[{
          hint: "Audio alert",
          select: selectSound,
          callback: function(ev){
            const v = ev.target.value;
            Chat.setNewMessageSound(v);
            F.toast.message("Audio notifications "+(v ? "enabled" : "disabled")+".");
            if(v) setTimeout(()=>Chat.playNewMessageSound(), 0);
          }
        },{


          label: "Play notification for your own messages",
          hint: "When enabled, the audio notification will be played for all messages, "+
            "including your own. When disabled only messages from other users "+
            "will trigger a notification.",
          boolValue: 'alert-own-messages'
        }]
      });
    }/*audio notification config*/
    settingsOps.push({
      label: "Active User List...",
      hint: [
        "/chat cannot track active connections, but it can tell ",
        "you who has posted recently..."].join(''),
      children:[
        namedOptions.activeUsers,{
          label: "Timestamps in active users list",
          indent: true,
          hint: "Show most recent message timestamps in the active user list.",
          boolValue: 'active-user-list-timestamps'
        }
      ]
    });
    /**
       Build UI for config options...
    */
    settingsOps.forEach(function f(op,indentOrIndex){
      const menuEntry = D.addClass(D.div(), 'menu-entry');
      if(true===indentOrIndex) D.addClass(menuEntry, 'child');
      const label = op.label
            ? D.append(D.label(),op.label) : undefined;
      const labelWrapper = D.addClass(D.div(), 'label-wrapper');
      var hint;

      if(op.hint){
        hint = D.append(D.addClass(D.label(),'hint'),op.hint);
      }
      if(op.hasOwnProperty('select')){
        const col0 = D.addClass(D.span(/*empty, but for spacing*/),
                                'toggle-wrapper');
        D.append(menuEntry, labelWrapper, col0);
        D.append(labelWrapper, op.select);
        if(hint) D.append(labelWrapper, hint);
        if(label) D.append(label);
        if(op.callback){
          op.select.addEventListener('change', (ev)=>op.callback(ev), false);
        }
      }else if(op.hasOwnProperty('boolValue')){
        if(undefined === f.$id) f.$id = 0;
        ++f.$id;
        if('string' ===typeof op.boolValue){
          const key = op.boolValue;
          op.boolValue = ()=>Chat.settings.getBool(key);
          op.persistentSetting = key;
        }
        const check = op.checkbox
              = D.attr(D.checkbox(1, op.boolValue()),
                       'aria-label', op.label);
        const id = 'cfgopt'+f.$id;
        const col0 = D.addClass(D.span(), 'toggle-wrapper');
        check.checked = op.boolValue();
        op.checkbox = check;
        D.attr(check, 'id', id);
        if(hint) D.attr(hint, 'for', id);
        D.append(menuEntry, labelWrapper, col0);
        D.append(col0, check);
        if(label){
          D.attr(label, 'for', id);
          D.append(labelWrapper, label);
        }
        if(hint) D.append(labelWrapper, hint);
      }else{
        if(op.callback){
          menuEntry.addEventListener('click', (ev)=>op.callback(ev));
        }
        D.append(menuEntry, labelWrapper);
        if(label) D.append(labelWrapper, label);
        if(hint) D.append(labelWrapper, hint);
      }
      D.append(optionsMenu, menuEntry);
      if(op.persistentSetting){
        Chat.settings.addListener(
          op.persistentSetting,
          function(setting){
            if(op.checkbox) op.checkbox.checked = !!setting.value;
            else if(op.select) op.select.value = setting.value;
            if(op.callback) op.callback(setting);
          }             
        );
        if(op.checkbox){
          op.checkbox.addEventListener(
            'change', function(){
              Chat.settings.set(op.persistentSetting, op.checkbox.checked)
            }, false);
        }
      }else if(op.callback && op.checkbox){
        op.checkbox.addEventListener('change', (ev)=>op.callback(ev), false);
      }
      if(op.children){
        D.addClass(menuEntry, 'parent');
        op.children.forEach((x)=>f(x,true));
      }
    });
  })()/*#chat-button-settings setup*/;

  (function(){
    /* Install default settings... must come after
       chat-button-settings setup so that the listeners which that
       installs are notified via the properties getting initialized
       here. */
    Chat.settings.addListener('monospace-messages',function(s){
      document.body.classList[s.value ? 'add' : 'remove']('monospace-messages');
    })
    Chat.settings.addListener('active-user-list',function(s){
      Chat.showActiveUserList(s.value);
    });
    Chat.settings.addListener('active-user-list-timestamps',function(s){
      Chat.showActiveUserTimestamps(s.value);
    });
    Chat.settings.addListener('chat-only-mode',function(s){
      Chat.chatOnlyMode(s.value);
    });
    Chat.settings.addListener('edit-widget-x',function(s){
      let eSelected;
      if(s.value){
        if(Chat.e.inputX===Chat.inputElement()) return;
        eSelected = Chat.e.inputX;
      }else{
        eSelected = Chat.settings.getBool('edit-compact-mode')
          ? Chat.e.input1 : Chat.e.inputM;
      }
      const v = Chat.inputValue();
      Chat.inputValue('');
      Chat.e.inputFields.forEach(function(e,ndx){
        if(eSelected===e){
          Chat.e.inputFields.$currentIndex = ndx;
          D.removeClass(e, 'hidden');
        }
        else D.addClass(e,'hidden');
      });
      Chat.inputValue(v);
      eSelected.focus();
    });
    Chat.settings.addListener('edit-compact-mode',function(s){
      if(Chat.e.inputX!==Chat.inputElement()){
        /* Text field/textarea mode: swap them if needed.
           Compact mode of inputX is toggled via CSS. */
        const a = s.value
              ? [Chat.e.input1, Chat.e.inputM, 0]
              : [Chat.e.inputM, Chat.e.input1, 1];
        const v = Chat.inputValue();
        Chat.inputValue('');
        Chat.e.inputFields.$currentIndex = a[2];
        Chat.inputValue(v);
        D.removeClass(a[0], 'hidden');
        D.addClass(a[1], 'hidden');
      }
      Chat.e.inputElementWrapper.classList[
        s.value ? 'add' : 'remove'
      ]('compact');
      Chat.e.inputFields[Chat.e.inputFields.$currentIndex].focus();
    });
    Chat.settings.addListener('edit-ctrl-send',function(s){
      const label = (s.value ? "Ctrl-" : "")+"Enter submits messages.";
      Chat.e.inputFields.forEach((e)=>{
        const v = e.dataset.placeholder0 + " " +label;
        if(e.isContentEditable) e.dataset.placeholder = v;
        else D.attr(e,'placeholder',v);
      });
      Chat.e.btnSubmit.title = label;
    });
    const valueKludges = {
      /* Convert certain string-format values to other types... */
      "false": false,
      "true": true
    };
1782
1783
1784
1785
1786
1787
1788
1789
1790
1791
1792
1793
1794
1795
1796
      this.e.viewPreview.querySelectorAll('a').forEach(addAnchorTargetBlank);
      setupHashtags(this.e.previewContent)/*arguable, for usability reasons*/;
      this.inputFocus();
    };
    Chat.e.viewPreview.querySelector('#chat-preview-close').
      addEventListener('click', ()=>Chat.setCurrentView(Chat.e.viewMessages), false);
    let previewPending = false;
    const elemsToEnable = [btnPreview, Chat.e.btnSubmit, Chat.e.inputField];
    const submit = function(ev){
      ev.preventDefault();
      ev.stopPropagation();
      if(previewPending) return false;
      const txt = Chat.inputValue();
      if(!txt){
        Chat.setPreviewText('');







|







1951
1952
1953
1954
1955
1956
1957
1958
1959
1960
1961
1962
1963
1964
1965
      this.e.viewPreview.querySelectorAll('a').forEach(addAnchorTargetBlank);
      setupHashtags(this.e.previewContent)/*arguable, for usability reasons*/;
      this.inputFocus();
    };
    Chat.e.viewPreview.querySelector('#chat-preview-close').
      addEventListener('click', ()=>Chat.setCurrentView(Chat.e.viewMessages), false);
    let previewPending = false;
    const elemsToEnable = [btnPreview, Chat.e.btnSubmit, Chat.e.inputFields];
    const submit = function(ev){
      ev.preventDefault();
      ev.stopPropagation();
      if(previewPending) return false;
      const txt = Chat.inputValue();
      if(!txt){
        Chat.setPreviewText('');
Changes to src/http_socket.c.
241
242
243
244
245
246
247

248
249
250


251
252
253
254
255
256
257
** if overridden in ~/.ssh/config) the rcvfrom may not match the host
** to which we connect.
*/
void socket_ssh_resolve_addr(UrlData *pUrlData){
  struct addrinfo *ai = 0;
  struct addrinfo hints;
  char zRemote[NI_MAXHOST];

  hints.ai_family = AF_UNSPEC;
  hints.ai_socktype = SOCK_STREAM;
  hints.ai_protocol = IPPROTO_TCP;


  if( getaddrinfo(pUrlData->name, NULL, &hints, &ai)==0
   && ai!=0
   && getnameinfo(ai->ai_addr, ai->ai_addrlen, zRemote,
                  sizeof(zRemote), 0, 0, NI_NUMERICHOST)==0 ){
    g.zIpAddr = mprintf("%s (%s)", zRemote, pUrlData->name);
  }
  if( ai ) freeaddrinfo(ai);







>



>
>







241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
** if overridden in ~/.ssh/config) the rcvfrom may not match the host
** to which we connect.
*/
void socket_ssh_resolve_addr(UrlData *pUrlData){
  struct addrinfo *ai = 0;
  struct addrinfo hints;
  char zRemote[NI_MAXHOST];
  memset(&hints, 0, sizeof(hints));
  hints.ai_family = AF_UNSPEC;
  hints.ai_socktype = SOCK_STREAM;
  hints.ai_protocol = IPPROTO_TCP;
  fossil_free(g.zIpAddr);
  g.zIpAddr = 0;
  if( getaddrinfo(pUrlData->name, NULL, &hints, &ai)==0
   && ai!=0
   && getnameinfo(ai->ai_addr, ai->ai_addrlen, zRemote,
                  sizeof(zRemote), 0, 0, NI_NUMERICHOST)==0 ){
    g.zIpAddr = mprintf("%s (%s)", zRemote, pUrlData->name);
  }
  if( ai ) freeaddrinfo(ai);
Changes to src/http_ssl.c.
87
88
89
90
91
92
93








































94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
static int ssl_client_cert_callback(SSL *ssl, X509 **x509, EVP_PKEY **pkey){
  fossil_warning("The remote server requested a client certificate for "
    "authentication. Specify the pathname to a file containing the PEM "
    "encoded certificate and private key with the --ssl-identity option "
    "or the ssl-identity setting.");
  return 0; /* no cert available */
}









































/*
** Call this routine once before any other use of the SSL interface.
** This routine does initial configuration of the SSL module.
*/
void ssl_global_init(void){
  const char *zCaSetting = 0, *zCaFile = 0, *zCaDirectory = 0;
  const char *identityFile;

  if( sslIsInit==0 ){
    SSL_library_init();
    SSL_load_error_strings();
    ERR_load_BIO_strings();
    OpenSSL_add_all_algorithms();
    sslCtx = SSL_CTX_new(SSLv23_client_method());
    /* Disable SSLv2 and SSLv3 */
    SSL_CTX_set_options(sslCtx, SSL_OP_NO_SSLv2|SSL_OP_NO_SSLv3);

    /* Set up acceptable CA root certificates */
    zCaSetting = db_get("ssl-ca-location", 0);







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>












<







87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145

146
147
148
149
150
151
152
static int ssl_client_cert_callback(SSL *ssl, X509 **x509, EVP_PKEY **pkey){
  fossil_warning("The remote server requested a client certificate for "
    "authentication. Specify the pathname to a file containing the PEM "
    "encoded certificate and private key with the --ssl-identity option "
    "or the ssl-identity setting.");
  return 0; /* no cert available */
}

/*
** Convert an OpenSSL ASN1_TIME to an ISO8601 timestamp.
**
** Per RFC 5280, ASN1 timestamps in X.509 certificates must 
** be in UTC (Zulu timezone) with no fractional seconds.
**
** If showUtc==1, add " UTC" at the end of the returned string. This is
** not ISO8601-compliant, but makes the displayed value more user-friendly.
*/
static const char *ssl_asn1time_to_iso8601(ASN1_TIME *asn1_time,
                                           int showUtc){
  assert( showUtc==0 || showUtc==1 );
  if( !ASN1_TIME_check(asn1_time) ){
    return mprintf("Bad time value");
  }else{
    char res[20];
    char *pr = res;
    const char *pt = (char *)asn1_time->data;
    /*                   0123456789 1234
    **  UTCTime:         YYMMDDHHMMSSZ      (YY >= 50 ? 19YY : 20YY)
    **  GeneralizedTime: YYYYMMDDHHMMSSZ */
    if( asn1_time->length < 15 ){
      /* UTCTime, fill out century digits */
      *pr++ = pt[0]>='5' ? '1' : '2';
      *pr++ = pt[0]>='5' ? '9' : '0';
    }else{
      /* GeneralizedTime, copy century digits and advance source */
      *pr++ = pt[0]; *pr++ = pt[1];
      pt += 2;
    }
    *pr++ = pt[0]; *pr++ = pt[1]; *pr++ = '-';
    *pr++ = pt[2]; *pr++ = pt[3]; *pr++ = '-';
    *pr++ = pt[4]; *pr++ = pt[5]; *pr++ = ' ';
    *pr++ = pt[6]; *pr++ = pt[7]; *pr++ = ':';
    *pr++ = pt[8]; *pr++ = pt[9]; *pr++ = ':';
    *pr++ = pt[10]; *pr++ = pt[11]; *pr = '\0';
    return mprintf("%s%s", res, (showUtc ? " UTC" : ""));
  }
}

/*
** Call this routine once before any other use of the SSL interface.
** This routine does initial configuration of the SSL module.
*/
void ssl_global_init(void){
  const char *zCaSetting = 0, *zCaFile = 0, *zCaDirectory = 0;
  const char *identityFile;

  if( sslIsInit==0 ){
    SSL_library_init();
    SSL_load_error_strings();

    OpenSSL_add_all_algorithms();
    sslCtx = SSL_CTX_new(SSLv23_client_method());
    /* Disable SSLv2 and SSLv3 */
    SSL_CTX_set_options(sslCtx, SSL_OP_NO_SSLv2|SSL_OP_NO_SSLv3);

    /* Set up acceptable CA root certificates */
    zCaSetting = db_get("ssl-ca-location", 0);
336
337
338
339
340
341
342







343
344
345
346
347
348
349

  if ( cert==NULL ){
    ssl_set_errmsg("No SSL certificate was presented by the peer");
    ssl_close();
    return 1;
  }








  if( !sslNoCertVerify && SSL_get_verify_result(ssl)!=X509_V_OK ){
    int x, desclen;
    char *desc, *prompt;
    Blob ans;
    char cReply;
    BIO *mem;
    unsigned char md[EVP_MAX_MD_SIZE];







>
>
>
>
>
>
>







375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395

  if ( cert==NULL ){
    ssl_set_errmsg("No SSL certificate was presented by the peer");
    ssl_close();
    return 1;
  }

  /* Debugging hint:   On unix-like system, run something like:
  **
  **     SSL_CERT_DIR=/tmp  ./fossil sync
  **
  ** to cause certificate validation to fail, and thus test the fallback
  ** logic.
  */
  if( !sslNoCertVerify && SSL_get_verify_result(ssl)!=X509_V_OK ){
    int x, desclen;
    char *desc, *prompt;
    Blob ans;
    char cReply;
    BIO *mem;
    unsigned char md[EVP_MAX_MD_SIZE];
369
370
371
372
373
374
375
376
377
378
379




380
381
382
383
384
385
386
387
388
389
390
391
392


393
394
395

396
397

398
399
400
401
402
403
404

    if( ssl_certificate_exception_exists(pUrlData, zHash) ){
      /* Ignore the failure because an exception exists */
      ssl_one_time_exception(pUrlData, zHash);
    }else{
      /* Tell the user about the failure and ask what to do */
      mem = BIO_new(BIO_s_mem());
      BIO_puts(mem,     "  subject: ");
      X509_NAME_print_ex(mem, X509_get_subject_name(cert), 0, XN_FLAG_ONELINE);
      BIO_puts(mem,   "\n  issuer:  ");
      X509_NAME_print_ex(mem, X509_get_issuer_name(cert), 0, XN_FLAG_ONELINE);




      BIO_printf(mem, "\n  sha256:  %s", zHash);
      desclen = BIO_get_mem_data(mem, &desc);
  
      prompt = mprintf("Unable to verify SSL cert from %s\n%.*s\n"
          "accept this cert and continue (y/N)? ",
          pUrlData->name, desclen, desc);
      BIO_free(mem);
  
      prompt_user(prompt, &ans);
      free(prompt);
      cReply = blob_str(&ans)[0];
      blob_reset(&ans);
      if( cReply!='y' && cReply!='Y' ){


        X509_free(cert);
        ssl_set_errmsg("SSL cert declined");
        ssl_close();

        return 1;
      }

      ssl_one_time_exception(pUrlData, zHash);
      prompt_user("remember this exception (y/N)? ", &ans);
      cReply = blob_str(&ans)[0];
      if( cReply=='y' || cReply=='Y') {
        db_open_config(0,0);
        ssl_remember_certificate_exception(pUrlData, zHash);
      }







|

|

>
>
>
>
|



|






<
|
>
>



>


>







415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440

441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457

    if( ssl_certificate_exception_exists(pUrlData, zHash) ){
      /* Ignore the failure because an exception exists */
      ssl_one_time_exception(pUrlData, zHash);
    }else{
      /* Tell the user about the failure and ask what to do */
      mem = BIO_new(BIO_s_mem());
      BIO_puts(mem,     "  subject:   ");
      X509_NAME_print_ex(mem, X509_get_subject_name(cert), 0, XN_FLAG_ONELINE);
      BIO_puts(mem,   "\n  issuer:    ");
      X509_NAME_print_ex(mem, X509_get_issuer_name(cert), 0, XN_FLAG_ONELINE);
      BIO_printf(mem, "\n  notBefore: %s",
                 ssl_asn1time_to_iso8601(X509_get_notBefore(cert), 1));
      BIO_printf(mem, "\n  notAfter:  %s",
                 ssl_asn1time_to_iso8601(X509_get_notAfter(cert), 1));
      BIO_printf(mem, "\n  sha256:    %s", zHash);
      desclen = BIO_get_mem_data(mem, &desc);
  
      prompt = mprintf("Unable to verify SSL cert from %s\n%.*s\n"
          "accept this cert and continue (y/N/fingerprint)? ",
          pUrlData->name, desclen, desc);
      BIO_free(mem);
  
      prompt_user(prompt, &ans);
      free(prompt);
      cReply = blob_str(&ans)[0];

      if( cReply!='y' && cReply!='Y'
       && fossil_stricmp(blob_str(&ans),zHash)!=0
      ){
        X509_free(cert);
        ssl_set_errmsg("SSL cert declined");
        ssl_close();
        blob_reset(&ans);
        return 1;
      }
      blob_reset(&ans);
      ssl_one_time_exception(pUrlData, zHash);
      prompt_user("remember this exception (y/N)? ", &ans);
      cReply = blob_str(&ans)[0];
      if( cReply=='y' || cReply=='Y') {
        db_open_config(0,0);
        ssl_remember_certificate_exception(pUrlData, zHash);
      }
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618

619

620
621
622
623
624
625
626
627
628
629
  if( strncmp("remove-exception",zCmd,nCmd)==0 ){
    int i;
    Blob sql;
    char *zSep = "(";
    db_begin_transaction();
    blob_init(&sql, 0, 0);
    if( g.argc==4 && find_option("all",0,0)!=0 ){
      db_unprotect(PROTECT_CONFIG);
      blob_append_sql(&sql,
        "DELETE FROM global_config WHERE name GLOB 'cert:*';\n"
        "DELETE FROM global_config WHERE name GLOB 'trusted:*';\n"
        "DELETE FROM config WHERE name GLOB 'cert:*';\n"
        "DELETE FROM config WHERE name GLOB 'trusted:*';\n"
      );
      db_protect_pop();
    }else{
      if( g.argc<4 ){
        usage("remove-exception DOMAIN-NAME ...");
      }
      blob_append_sql(&sql,"DELETE FROM global_config WHERE name IN ");
      for(i=3; i<g.argc; i++){
        blob_append_sql(&sql,"%s'cert:%q','trust:%q'",
           zSep/*safe-for-%s*/, g.argv[i], g.argv[i]);
        zSep = ",";
      }
      blob_append_sql(&sql,");\n");
      zSep = "(";
      blob_append_sql(&sql,"DELETE FROM config WHERE name IN ");
      for(i=3; i<g.argc; i++){
        blob_append_sql(&sql,"%s'cert:%q','trusted:%q'",
           zSep/*safe-for-%s*/, g.argv[i], g.argv[i]);
        zSep = ",";
      }
      blob_append_sql(&sql,");");
    }

    db_exec_sql(blob_str(&sql));

    db_commit_transaction();
    blob_reset(&sql);
  }else
  /*default*/{
    fossil_fatal("unknown sub-command \"%s\".\nshould be one of:"
                 " remove-exception show",
       zCmd);
  }
#endif
}







<






<




















>

>










637
638
639
640
641
642
643

644
645
646
647
648
649

650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
  if( strncmp("remove-exception",zCmd,nCmd)==0 ){
    int i;
    Blob sql;
    char *zSep = "(";
    db_begin_transaction();
    blob_init(&sql, 0, 0);
    if( g.argc==4 && find_option("all",0,0)!=0 ){

      blob_append_sql(&sql,
        "DELETE FROM global_config WHERE name GLOB 'cert:*';\n"
        "DELETE FROM global_config WHERE name GLOB 'trusted:*';\n"
        "DELETE FROM config WHERE name GLOB 'cert:*';\n"
        "DELETE FROM config WHERE name GLOB 'trusted:*';\n"
      );

    }else{
      if( g.argc<4 ){
        usage("remove-exception DOMAIN-NAME ...");
      }
      blob_append_sql(&sql,"DELETE FROM global_config WHERE name IN ");
      for(i=3; i<g.argc; i++){
        blob_append_sql(&sql,"%s'cert:%q','trust:%q'",
           zSep/*safe-for-%s*/, g.argv[i], g.argv[i]);
        zSep = ",";
      }
      blob_append_sql(&sql,");\n");
      zSep = "(";
      blob_append_sql(&sql,"DELETE FROM config WHERE name IN ");
      for(i=3; i<g.argc; i++){
        blob_append_sql(&sql,"%s'cert:%q','trusted:%q'",
           zSep/*safe-for-%s*/, g.argv[i], g.argv[i]);
        zSep = ",";
      }
      blob_append_sql(&sql,");");
    }
    db_unprotect(PROTECT_CONFIG);
    db_exec_sql(blob_str(&sql));
    db_protect_pop();
    db_commit_transaction();
    blob_reset(&sql);
  }else
  /*default*/{
    fossil_fatal("unknown sub-command \"%s\".\nshould be one of:"
                 " remove-exception show",
       zCmd);
  }
#endif
}
Changes to src/http_transport.c.
176
177
178
179
180
181
182



183
184
185
186
187
188
189
      if( rc==0 ) transport.isOpen = 1;
#else
      socket_set_errmsg("HTTPS: Fossil has been compiled without SSL support");
      rc = 1;
#endif
    }else if( pUrlData->isFile ){
      sqlite3_uint64 iRandId;



      sqlite3_randomness(sizeof(iRandId), &iRandId);
      transport.zOutFile = mprintf("%s-%llu-out.http",
                                       g.zRepositoryName, iRandId);
      transport.zInFile = mprintf("%s-%llu-in.http",
                                       g.zRepositoryName, iRandId);
      transport.pFile = fossil_fopen(transport.zOutFile, "wb");
      if( transport.pFile==0 ){







>
>
>







176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
      if( rc==0 ) transport.isOpen = 1;
#else
      socket_set_errmsg("HTTPS: Fossil has been compiled without SSL support");
      rc = 1;
#endif
    }else if( pUrlData->isFile ){
      sqlite3_uint64 iRandId;
      if( !db_looks_like_a_repository(pUrlData->name) ){
        fossil_fatal("not a fossil repository: \"%s\"", pUrlData->name);
      }
      sqlite3_randomness(sizeof(iRandId), &iRandId);
      transport.zOutFile = mprintf("%s-%llu-out.http",
                                       g.zRepositoryName, iRandId);
      transport.zInFile = mprintf("%s-%llu-in.http",
                                       g.zRepositoryName, iRandId);
      transport.pFile = fossil_fopen(transport.zOutFile, "wb");
      if( transport.pFile==0 ){
Changes to src/import.c.
2006
2007
2008
2009
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
  db_end_transaction(0);
  fossil_print("                               \r");
  if( omitRebuild ){
    omitVacuum = 1;
  }else{
    db_begin_transaction();
    fossil_print("Rebuilding repository meta-data...\n");
    rebuild_db(0, 1, !incrFlag);
    verify_cancel();
    db_end_transaction(0);
  }
  if( !omitVacuum ){
    fossil_print("Vacuuming..."); fflush(stdout);
    db_multi_exec("VACUUM");
  }







|







2006
2007
2008
2009
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
  db_end_transaction(0);
  fossil_print("                               \r");
  if( omitRebuild ){
    omitVacuum = 1;
  }else{
    db_begin_transaction();
    fossil_print("Rebuilding repository meta-data...\n");
    rebuild_db(1, !incrFlag);
    verify_cancel();
    db_end_transaction(0);
  }
  if( !omitVacuum ){
    fossil_print("Vacuuming..."); fflush(stdout);
    db_multi_exec("VACUUM");
  }
Changes to src/info.c.
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
  char const *zType;

  login_check_credentials();
  if( !g.perm.Read ){ login_needed(g.anon.Read); return; }
  rid = name_to_rid_www("name");
  if( rid==0 ){
    style_header("Check-in Information Error");
    @ No such object: %h(g.argv[2])
    style_finish_page();
    return;
  }
  zHash = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
  style_header("Tags and Properties");
  zType = whatis_rid_type_label(rid);
  if(!zType) zType = "Artifact";







|







491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
  char const *zType;

  login_check_credentials();
  if( !g.perm.Read ){ login_needed(g.anon.Read); return; }
  rid = name_to_rid_www("name");
  if( rid==0 ){
    style_header("Check-in Information Error");
    @ No such object: %h(PD("name",""))
    style_finish_page();
    return;
  }
  zHash = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
  style_header("Tags and Properties");
  zType = whatis_rid_type_label(rid);
  if(!zType) zType = "Artifact";
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
  login_check_credentials();
  if( !g.perm.Read ){ login_needed(g.anon.Read); return; }
  style_set_current_feature("vinfo");
  zName = P("name");
  rid = name_to_rid_www("name");
  if( rid==0 ){
    style_header("Check-in Information Error");
    @ No such object: %h(g.argv[2])
    style_finish_page();
    return;
  }
  zRe = P("regex");
  if( zRe ) re_compile(&pRe, zRe, 0);
  zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
  zParent = db_text(0,







|







625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
  login_check_credentials();
  if( !g.perm.Read ){ login_needed(g.anon.Read); return; }
  style_set_current_feature("vinfo");
  zName = P("name");
  rid = name_to_rid_www("name");
  if( rid==0 ){
    style_header("Check-in Information Error");
    @ No such object: %h(zName)
    style_finish_page();
    return;
  }
  zRe = P("regex");
  if( zRe ) re_compile(&pRe, zRe, 0);
  zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
  zParent = db_text(0,
1946
1947
1948
1949
1950
1951
1952
1953
1954
1955
1956
1957
1958
1959
1960
  if( iFrom<1 || iTo<iFrom ){
    ajax_route_error(500, "Invalid line range from=%d, to=%d.",
                     iFrom, iTo);
    return;
  }
  content_get(rid, &content);
  g.isConst = 1;
  cgi_set_content_type("text/json");
  ln = 0;
  while( go && ln<iFrom ){
    go = blob_line(&content, &line);
    ln++;
  }
  pOut = cgi_output_blob();
  blob_append(pOut, "[\n", 2);







|







1946
1947
1948
1949
1950
1951
1952
1953
1954
1955
1956
1957
1958
1959
1960
  if( iFrom<1 || iTo<iFrom ){
    ajax_route_error(500, "Invalid line range from=%d, to=%d.",
                     iFrom, iTo);
    return;
  }
  content_get(rid, &content);
  g.isConst = 1;
  cgi_set_content_type("application/json");
  ln = 0;
  while( go && ln<iFrom ){
    go = blob_line(&content, &line);
    ln++;
  }
  pOut = cgi_output_blob();
  blob_append(pOut, "[\n", 2);
2536
2537
2538
2539
2540
2541
2542

2543
2544
2545
2546
2547
2548
2549
    }
    style_submenu_element("Artifact", "%R/artifact/%S", zUuid);
    zMime = mimetype_from_name(zName);
    style_submenu_element("Annotate", "%R/annotate?filename=%T&checkin=%T",
                          zName, zCI);
    style_submenu_element("Blame", "%R/blame?filename=%T&checkin=%T",
                          zName, zCI);

    blob_init(&downloadName, zName, -1);
    objType = OBJTYPE_CONTENT;
  }else{
    @ <h2>Artifact
    style_copy_button(1, "hash-ar", 0, 2, "%s", zUuid);
    if( g.perm.Setup ){
      @  (%d(rid)):</h2>







>







2536
2537
2538
2539
2540
2541
2542
2543
2544
2545
2546
2547
2548
2549
2550
    }
    style_submenu_element("Artifact", "%R/artifact/%S", zUuid);
    zMime = mimetype_from_name(zName);
    style_submenu_element("Annotate", "%R/annotate?filename=%T&checkin=%T",
                          zName, zCI);
    style_submenu_element("Blame", "%R/blame?filename=%T&checkin=%T",
                          zName, zCI);
    style_submenu_element("Doc", "%R/doc/%T/%T", zCI, zName);
    blob_init(&downloadName, zName, -1);
    objType = OBJTYPE_CONTENT;
  }else{
    @ <h2>Artifact
    style_copy_button(1, "hash-ar", 0, 2, "%s", zUuid);
    if( g.perm.Setup ){
      @  (%d(rid)):</h2>
3305
3306
3307
3308
3309
3310
3311
3312
3313
3314
3315
3316
3317
3318
3319
    @ <input type="checkbox" name="pclr" checked="checked" />
  }else{
    @ <input type="checkbox" name="pclr" />
  }
  @ Propagate color to descendants</label></div>
  @ <div class='font-size-80'>Be aware that fixed background
  @ colors will not interact well with all available skins.
  @ It is recommended that fossil be allowed to select these
  @ colors automatically so that it can take the skin's
  @ preferences into account.</div>
  @ </td></tr>

  @ <tr><th align="right" valign="top">Tags:</th>
  @ <td valign="top">
  @ <label><input type="checkbox" id="newtag" name="newtag"%s(zNewTagFlag) />







|







3306
3307
3308
3309
3310
3311
3312
3313
3314
3315
3316
3317
3318
3319
3320
    @ <input type="checkbox" name="pclr" checked="checked" />
  }else{
    @ <input type="checkbox" name="pclr" />
  }
  @ Propagate color to descendants</label></div>
  @ <div class='font-size-80'>Be aware that fixed background
  @ colors will not interact well with all available skins.
  @ It is recommended that Fossil be allowed to select these
  @ colors automatically so that it can take the skin's
  @ preferences into account.</div>
  @ </td></tr>

  @ <tr><th align="right" valign="top">Tags:</th>
  @ <td valign="top">
  @ <label><input type="checkbox" id="newtag" name="newtag"%s(zNewTagFlag) />
Changes to src/json.c.
2183
2184
2185
2186
2187
2188
2189
2190
2191
2192
2193
2194
2195
2196
2197
     On large repos (e.g. fossil's) this operation is likely to take
     longer than the client timeout, which will cause it to fail (but
     it's sqlite3, so it'll fail gracefully).
  */
    db_close(1);
    db_open_repository(g.zRepositoryName);
    db_begin_transaction();
    rebuild_db(0, 0, 0);
    db_end_transaction(0);
    return NULL;
  }
}

/*
** Impl of /json/g. Requires admin/setup rights.







|







2183
2184
2185
2186
2187
2188
2189
2190
2191
2192
2193
2194
2195
2196
2197
     On large repos (e.g. fossil's) this operation is likely to take
     longer than the client timeout, which will cause it to fail (but
     it's sqlite3, so it'll fail gracefully).
  */
    db_close(1);
    db_open_repository(g.zRepositoryName);
    db_begin_transaction();
    rebuild_db(0, 0);
    db_end_transaction(0);
    return NULL;
  }
}

/*
** Impl of /json/g. Requires admin/setup rights.
Changes to src/login.c.
2114
2115
2116
2117
2118
2119
2120
2121

2122


2123
2124
2125
2126

2127
2128
2129
2130
2131
2132


2133
2134
2135




2136
2137
2138
2139
2140
2141
2142
2143
2144
2145
2146
2147
2148
2149
2150
2151
2152
2153
2154
2155
2156
2157
  );
  db_protect_pop();
}

/*
** COMMAND: login-group*
**
** Usage: %fossil login-group

**    or: %fossil login-group join REPO [-name NAME]


**    or: %fossil login-group leave
**
** With no arguments, this command shows the login-group to which the
** repository belongs.

**
** The "join" command adds this repository to login group to which REPO
** belongs, or creates a new login group between itself and REPO if REPO
** does not already belong to a login-group.  When creating a new login-
** group, the name of the new group is determined by the "--name" option.
**


** The "leave" command takes the repository out of whatever login group
** it is currently a part of.
**




** About Login Groups:
**
** A login-group is a set of repositories that share user credentials.
** If a user is logged into one member of the group, then that user can
** access any other group member as long as they have an entry in the
** USER table of that member.  If a user changes their password using
** web interface, their password is also automatically changed in every
** other member of the login group.
*/
void login_group_command(void){
  const char *zLGName;
  const char *zCmd;
  int nCmd;
  Stmt q;
  db_find_and_open_repository(0,0);
  if( g.argc>2 ){
    zCmd = g.argv[2];
    nCmd = (int)strlen(zCmd);
    if( strncmp(zCmd,"join",nCmd)==0 && nCmd>=1 ){
      const char *zNewName = find_option("name",0,1);
      const char *zOther;
      char *zErr = 0;







|
>
|
>
>
|

|
|
>

|
|
|
|

>
>
|
|

>
>
>
>

|
|

|
|
|
|






|







2114
2115
2116
2117
2118
2119
2120
2121
2122
2123
2124
2125
2126
2127
2128
2129
2130
2131
2132
2133
2134
2135
2136
2137
2138
2139
2140
2141
2142
2143
2144
2145
2146
2147
2148
2149
2150
2151
2152
2153
2154
2155
2156
2157
2158
2159
2160
2161
2162
2163
2164
2165
2166
2167
  );
  db_protect_pop();
}

/*
** COMMAND: login-group*
**
** Usage: %fossil login-group ?SUBCOMMAND? ?OPTIONS?
**
** Run various subcommands to manage login-group related settings of the open
** repository or of the repository identified by the -R or --repository option.
**
** >  fossil login-group
**
**     Show the login-group to which the repository belongs.
**
** >  fossil login-group join ?--name NAME?
**
**     Add this repository to login group to which REPO belongs, or creates a
**     new login group between itself and REPO if REPO does not already belong
**     to a login-group.  When creating a new login-group, the name of the new
**     group is determined by the "--name" option.
**
** >  fossil login-group leave
**
**     Takes the repository out of whatever login group it is currently 
**     a part of.
**
** Options valid for all subcommands:
**
**     -R|--repository REPO       Run commands on repository REPO
**
** About Login Groups:
** 
** A login-group is a set of repositories that share user credentials.  
** If a user is logged into one member of the group, then that user can
** access any other group member as long as they have an entry in the USER
** table of that member.  If a user changes their password using web
** interface, their password is also automatically changed in every other
** member of the login group.
*/
void login_group_command(void){
  const char *zLGName;
  const char *zCmd;
  int nCmd;
  Stmt q;
  db_find_and_open_repository(0, 0);
  if( g.argc>2 ){
    zCmd = g.argv[2];
    nCmd = (int)strlen(zCmd);
    if( strncmp(zCmd,"join",nCmd)==0 && nCmd>=1 ){
      const char *zNewName = find_option("name",0,1);
      const char *zOther;
      char *zErr = 0;
Changes to src/main.c.
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711

  fossil_printf_selfcheck();
  fossil_limit_memory(1);

  /* When updating the minimum SQLite version, change the number here,
  ** and also MINIMUM_SQLITE_VERSION value set in ../auto.def.  Take
  ** care that both places agree! */
  if( sqlite3_libversion_number()<3035000 ){
    fossil_panic("Unsuitable SQLite version %s, must be at least 3.35.0",
                 sqlite3_libversion());
  }

  sqlite3_config(SQLITE_CONFIG_MULTITHREAD);
  sqlite3_config(SQLITE_CONFIG_LOG, fossil_sqlite_log, 0);
  memset(&g, 0, sizeof(g));
  g.now = time(0);







|
|







696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711

  fossil_printf_selfcheck();
  fossil_limit_memory(1);

  /* When updating the minimum SQLite version, change the number here,
  ** and also MINIMUM_SQLITE_VERSION value set in ../auto.def.  Take
  ** care that both places agree! */
  if( sqlite3_libversion_number()<3037000 ){
    fossil_panic("Unsuitable SQLite version %s, must be at least 3.37.0",
                 sqlite3_libversion());
  }

  sqlite3_config(SQLITE_CONFIG_MULTITHREAD);
  sqlite3_config(SQLITE_CONFIG_LOG, fossil_sqlite_log, 0);
  memset(&g, 0, sizeof(g));
  g.now = time(0);
Changes to src/md5.c.
20
21
22
23
24
25
26
27



28
29
30
31
32
33
34
 */
#include "config.h"
#include <string.h>
#include <stdio.h>
#include <sqlite3.h>
#include "md5.h"

#ifdef FOSSIL_ENABLE_SSL




# include <openssl/md5.h>
# define MD5Context MD5_CTX
# define MD5Init MD5_Init
# define MD5Update MD5_Update
# define MD5Final MD5_Final








|
>
>
>







20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
 */
#include "config.h"
#include <string.h>
#include <stdio.h>
#include <sqlite3.h>
#include "md5.h"

#if  0  /* defined FOSSIL_ENABLE_SSL */

/* MD5 is deprecated in OpenSSL.  So we have to fall back to our own
** implementation */

# include <openssl/md5.h>
# define MD5Context MD5_CTX
# define MD5Init MD5_Init
# define MD5Update MD5_Update
# define MD5Final MD5_Final

Changes to src/merge.c.
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
**                           a sequence of changes in a branch to be merged
**                           without having to merge the entire branch.
**
**   --binary GLOBPATTERN    Treat files that match GLOBPATTERN as binary
**                           and do not try to merge parallel changes.  This
**                           option overrides the "binary-glob" setting.
**
**   --case-sensitive BOOL   Override the case-sensitive setting.  If false,
**                           files whose names differ only in case are taken
**                           to be the same file.
**
**   --cherrypick            Do a cherrypick merge VERSION into the current
**                           checkout.  A cherrypick merge pulls in the changes
**                           of the single check-in VERSION, rather than all
**                           changes back to the nearest common ancestor.
**
**   -f|--force              Force the merge even if it would be a no-op.
**







<
<
<
<







305
306
307
308
309
310
311




312
313
314
315
316
317
318
**                           a sequence of changes in a branch to be merged
**                           without having to merge the entire branch.
**
**   --binary GLOBPATTERN    Treat files that match GLOBPATTERN as binary
**                           and do not try to merge parallel changes.  This
**                           option overrides the "binary-glob" setting.
**




**   --cherrypick            Do a cherrypick merge VERSION into the current
**                           checkout.  A cherrypick merge pulls in the changes
**                           of the single check-in VERSION, rather than all
**                           changes back to the nearest common ancestor.
**
**   -f|--force              Force the merge even if it would be a no-op.
**
Changes to src/merge3.c.
114
115
116
117
118
119
120
121

122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
** The aC[] array is updated and the new index into aC[] is returned.
*/
static int output_one_side(
  Blob *pOut,     /* Write to this blob */
  Blob *pSrc,     /* The edited file that is to be copied to pOut */
  int *aC,        /* Array of integer triples describing the edit */
  int i,          /* Index in aC[] of current location in pSrc */
  int sz          /* Number of lines in unedited source to output */

){
  while( sz>0 ){
    if( aC[i]==0 && aC[i+1]==0 && aC[i+2]==0 ) break;
    if( aC[i]>=sz ){
      blob_copy_lines(pOut, pSrc, sz);
      aC[i] -= sz;
      break;
    }
    blob_copy_lines(pOut, pSrc, aC[i]);
    blob_copy_lines(pOut, pSrc, aC[i+2]);
    sz -= aC[i] + aC[i+1];
    i += 3;
  }
  return i;
}

/*
** Text of boundary markers for merge conflicts.
*/
static const char *const mergeMarker[] = {
 /*123456789 123456789 123456789 123456789 123456789 123456789 123456789*/
  "<<<<<<< BEGIN MERGE CONFLICT: local copy shown first <<<<<<<<<<<<<<<",
  "||||||| COMMON ANCESTOR content follows ||||||||||||||||||||||||||||",
  "======= MERGED IN content follows ==================================",
  ">>>>>>> END MERGE CONFLICT >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>"
};

/*
** Return true if the input blob contains any CR/LF pairs on the first
** ten lines. This should be enough to detect files that use mainly CR/LF
** line endings without causing a performance impact for LF only files.
*/







|
>




|



|
|











|
|
|
|







114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
** The aC[] array is updated and the new index into aC[] is returned.
*/
static int output_one_side(
  Blob *pOut,     /* Write to this blob */
  Blob *pSrc,     /* The edited file that is to be copied to pOut */
  int *aC,        /* Array of integer triples describing the edit */
  int i,          /* Index in aC[] of current location in pSrc */
  int sz,         /* Number of lines in unedited source to output */
  int *pLn        /* Line number counter */
){
  while( sz>0 ){
    if( aC[i]==0 && aC[i+1]==0 && aC[i+2]==0 ) break;
    if( aC[i]>=sz ){
      blob_copy_lines(pOut, pSrc, sz);  *pLn += sz;
      aC[i] -= sz;
      break;
    }
    blob_copy_lines(pOut, pSrc, aC[i]);      *pLn += aC[i];
    blob_copy_lines(pOut, pSrc, aC[i+2]);    *pLn += aC[i+2];
    sz -= aC[i] + aC[i+1];
    i += 3;
  }
  return i;
}

/*
** Text of boundary markers for merge conflicts.
*/
static const char *const mergeMarker[] = {
 /*123456789 123456789 123456789 123456789 123456789 123456789 123456789*/
  "<<<<<<< BEGIN MERGE CONFLICT: local copy shown first <<<<<<<<<<<<",
  "||||||| COMMON ANCESTOR content follows |||||||||||||||||||||||||",
  "======= MERGED IN content follows ===============================",
  ">>>>>>> END MERGE CONFLICT >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>"
};

/*
** Return true if the input blob contains any CR/LF pairs on the first
** ten lines. This should be enough to detect files that use mainly CR/LF
** line endings without causing a performance impact for LF only files.
*/
173
174
175
176
177
178
179










180
181
182
183
184
185
186
void ensure_line_end(Blob *pBlob, int useCrLf){
  if( pBlob->nUsed<=0 ) return;
  if( pBlob->aData[pBlob->nUsed-1]!='\n' ){
    if( useCrLf ) blob_append_char(pBlob, '\r');
    blob_append_char(pBlob, '\n');
  }
}











/*
** Do a three-way merge.  Initialize pOut to contain the result.
**
** The merge is an edit against pV2.  Both pV1 and pV2 have a
** common origin at pPivot.  Apply the changes of pPivot ==> pV1
** to pV2.







>
>
>
>
>
>
>
>
>
>







174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
void ensure_line_end(Blob *pBlob, int useCrLf){
  if( pBlob->nUsed<=0 ) return;
  if( pBlob->aData[pBlob->nUsed-1]!='\n' ){
    if( useCrLf ) blob_append_char(pBlob, '\r');
    blob_append_char(pBlob, '\n');
  }
}

/*
** Write out one of the four merge-marks.
*/
void append_merge_mark(Blob *pOut, int iMark, int ln, int useCrLf){
  ensure_line_end(pOut, useCrLf);
  blob_append(pOut, mergeMarker[iMark], -1);
  if( ln>0 ) blob_appendf(pOut, " (line %d)", ln);
  ensure_line_end(pOut, useCrLf);
}

/*
** Do a three-way merge.  Initialize pOut to contain the result.
**
** The merge is an edit against pV2.  Both pV1 and pV2 have a
** common origin at pPivot.  Apply the changes of pPivot ==> pV1
** to pV2.
194
195
196
197
198
199
200

201
202
203
204
205
206
207
  int *aC1;              /* Changes from pPivot to pV1 */
  int *aC2;              /* Changes from pPivot to pV2 */
  int i1, i2;            /* Index into aC1[] and aC2[] */
  int nCpy, nDel, nIns;  /* Number of lines to copy, delete, or insert */
  int limit1, limit2;    /* Sizes of aC1[] and aC2[] */
  int nConflict = 0;     /* Number of merge conflicts seen so far */
  int useCrLf = 0;

  DiffConfig DCfg;

  blob_zero(pOut);         /* Merge results stored in pOut */
  
  /* If both pV1 and pV2 start with a UTF-8 byte-order-mark (BOM),
  ** keep it in the output. This should be secure enough not to cause
  ** unintended changes to the merged file and consistent with what







>







205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
  int *aC1;              /* Changes from pPivot to pV1 */
  int *aC2;              /* Changes from pPivot to pV2 */
  int i1, i2;            /* Index into aC1[] and aC2[] */
  int nCpy, nDel, nIns;  /* Number of lines to copy, delete, or insert */
  int limit1, limit2;    /* Sizes of aC1[] and aC2[] */
  int nConflict = 0;     /* Number of merge conflicts seen so far */
  int useCrLf = 0;
  int ln1, ln2, lnPivot; /* Line numbers for all files */
  DiffConfig DCfg;

  blob_zero(pOut);         /* Merge results stored in pOut */
  
  /* If both pV1 and pV2 start with a UTF-8 byte-order-mark (BOM),
  ** keep it in the output. This should be secure enough not to cause
  ** unintended changes to the merged file and consistent with what
257
258
259
260
261
262
263

264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345

  /* Loop over the two edit vectors and use them to compute merged text
  ** which is written into pOut.  i1 and i2 are multiples of 3 which are
  ** indices into aC1[] and aC2[] to the edit triple currently being
  ** processed
  */
  i1 = i2 = 0;

  while( i1<limit1 && i2<limit2 ){
    DEBUG( printf("%d: %2d %2d %2d   %d: %2d %2d %2d\n",
           i1/3, aC1[i1], aC1[i1+1], aC1[i1+2],
           i2/3, aC2[i2], aC2[i2+1], aC2[i2+2]); )

    if( aC1[i1]>0 && aC2[i2]>0 ){
      /* Output text that is unchanged in both V1 and V2 */
      nCpy = min(aC1[i1], aC2[i2]);
      DEBUG( printf("COPY %d\n", nCpy); )
      blob_copy_lines(pOut, pPivot, nCpy);
      blob_copy_lines(0, pV1, nCpy);
      blob_copy_lines(0, pV2, nCpy);
      aC1[i1] -= nCpy;
      aC2[i2] -= nCpy;
    }else
    if( aC1[i1] >= aC2[i2+1] && aC1[i1]>0 && aC2[i2+1]+aC2[i2+2]>0 ){
      /* Output edits to V2 that occurs within unchanged regions of V1 */
      nDel = aC2[i2+1];
      nIns = aC2[i2+2];
      DEBUG( printf("EDIT -%d+%d left\n", nDel, nIns); )
      blob_copy_lines(0, pPivot, nDel);
      blob_copy_lines(0, pV1, nDel);
      blob_copy_lines(pOut, pV2, nIns);
      aC1[i1] -= nDel;
      i2 += 3;
    }else
    if( aC2[i2] >= aC1[i1+1] && aC2[i2]>0 && aC1[i1+1]+aC1[i1+2]>0 ){
      /* Output edits to V1 that occur within unchanged regions of V2 */
      nDel = aC1[i1+1];
      nIns = aC1[i1+2];
      DEBUG( printf("EDIT -%d+%d right\n", nDel, nIns); )
      blob_copy_lines(0, pPivot, nDel);
      blob_copy_lines(0, pV2, nDel);
      blob_copy_lines(pOut, pV1, nIns);
      aC2[i2] -= nDel;
      i1 += 3;
    }else
    if( sameEdit(&aC1[i1], &aC2[i2], pV1, pV2) ){
      /* Output edits that are identical in both V1 and V2. */
      assert( aC1[i1]==0 );
      nDel = aC1[i1+1];
      nIns = aC1[i1+2];
      DEBUG( printf("EDIT -%d+%d both\n", nDel, nIns); )
      blob_copy_lines(0, pPivot, nDel);
      blob_copy_lines(pOut, pV1, nIns);
      blob_copy_lines(0, pV2, nIns);
      i1 += 3;
      i2 += 3;
    }else
    {
      /* We have found a region where different edits to V1 and V2 overlap.
      ** This is a merge conflict.  Find the size of the conflict, then
      ** output both possible edits separated by distinctive marks.
      */
      int sz = 1;    /* Size of the conflict in lines */
      nConflict++;
      while( !ends_at_CPY(&aC1[i1], sz) || !ends_at_CPY(&aC2[i2], sz) ){
        sz++;
      }
      DEBUG( printf("CONFLICT %d\n", sz); )
      ensure_line_end(pOut, useCrLf);
      blob_append(pOut, mergeMarker[0], -1);
      ensure_line_end(pOut, useCrLf);
      i1 = output_one_side(pOut, pV1, aC1, i1, sz);
      ensure_line_end(pOut, useCrLf);
      blob_append(pOut, mergeMarker[1], -1);
      ensure_line_end(pOut, useCrLf);
      blob_copy_lines(pOut, pPivot, sz);
      ensure_line_end(pOut, useCrLf);
      blob_append(pOut, mergeMarker[2], -1);
      ensure_line_end(pOut, useCrLf);
      i2 = output_one_side(pOut, pV2, aC2, i2, sz);
      ensure_line_end(pOut, useCrLf);
      blob_append(pOut, mergeMarker[3], -1);
      ensure_line_end(pOut, useCrLf);
   }

    /* If we are finished with an edit triple, advance to the next
    ** triple.
    */
    if( i1<limit1 && aC1[i1]==0 && aC1[i1+1]==0 && aC1[i1+2]==0 ) i1+=3;
    if( i2<limit2 && aC2[i2]==0 && aC2[i2+1]==0 && aC2[i2+2]==0 ) i2+=3;







>









|
|
|








|
|
|








|
|
|









|
|
|














|
<
|
|
|
<
|
|
|
<
|
|
|
<
|







269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337

338
339
340

341
342
343

344
345
346

347
348
349
350
351
352
353
354

  /* Loop over the two edit vectors and use them to compute merged text
  ** which is written into pOut.  i1 and i2 are multiples of 3 which are
  ** indices into aC1[] and aC2[] to the edit triple currently being
  ** processed
  */
  i1 = i2 = 0;
  ln1 = ln2 = lnPivot = 1;
  while( i1<limit1 && i2<limit2 ){
    DEBUG( printf("%d: %2d %2d %2d   %d: %2d %2d %2d\n",
           i1/3, aC1[i1], aC1[i1+1], aC1[i1+2],
           i2/3, aC2[i2], aC2[i2+1], aC2[i2+2]); )

    if( aC1[i1]>0 && aC2[i2]>0 ){
      /* Output text that is unchanged in both V1 and V2 */
      nCpy = min(aC1[i1], aC2[i2]);
      DEBUG( printf("COPY %d\n", nCpy); )
      blob_copy_lines(pOut, pPivot, nCpy); lnPivot += nCpy;
      blob_copy_lines(0, pV1, nCpy);       ln1 += nCpy;
      blob_copy_lines(0, pV2, nCpy);       ln2 += nCpy;
      aC1[i1] -= nCpy;
      aC2[i2] -= nCpy;
    }else
    if( aC1[i1] >= aC2[i2+1] && aC1[i1]>0 && aC2[i2+1]+aC2[i2+2]>0 ){
      /* Output edits to V2 that occurs within unchanged regions of V1 */
      nDel = aC2[i2+1];
      nIns = aC2[i2+2];
      DEBUG( printf("EDIT -%d+%d left\n", nDel, nIns); )
      blob_copy_lines(0, pPivot, nDel);    lnPivot += nDel;
      blob_copy_lines(0, pV1, nDel);       ln1 += nDel;
      blob_copy_lines(pOut, pV2, nIns);    ln2 += nIns;
      aC1[i1] -= nDel;
      i2 += 3;
    }else
    if( aC2[i2] >= aC1[i1+1] && aC2[i2]>0 && aC1[i1+1]+aC1[i1+2]>0 ){
      /* Output edits to V1 that occur within unchanged regions of V2 */
      nDel = aC1[i1+1];
      nIns = aC1[i1+2];
      DEBUG( printf("EDIT -%d+%d right\n", nDel, nIns); )
      blob_copy_lines(0, pPivot, nDel);    lnPivot += nDel;
      blob_copy_lines(0, pV2, nDel);       ln2 += nDel;
      blob_copy_lines(pOut, pV1, nIns);    ln1 += nIns;
      aC2[i2] -= nDel;
      i1 += 3;
    }else
    if( sameEdit(&aC1[i1], &aC2[i2], pV1, pV2) ){
      /* Output edits that are identical in both V1 and V2. */
      assert( aC1[i1]==0 );
      nDel = aC1[i1+1];
      nIns = aC1[i1+2];
      DEBUG( printf("EDIT -%d+%d both\n", nDel, nIns); )
      blob_copy_lines(0, pPivot, nDel);    lnPivot += nDel;
      blob_copy_lines(pOut, pV1, nIns);    ln1 += nIns;
      blob_copy_lines(0, pV2, nIns);       ln2 += nIns;
      i1 += 3;
      i2 += 3;
    }else
    {
      /* We have found a region where different edits to V1 and V2 overlap.
      ** This is a merge conflict.  Find the size of the conflict, then
      ** output both possible edits separated by distinctive marks.
      */
      int sz = 1;    /* Size of the conflict in lines */
      nConflict++;
      while( !ends_at_CPY(&aC1[i1], sz) || !ends_at_CPY(&aC2[i2], sz) ){
        sz++;
      }
      DEBUG( printf("CONFLICT %d\n", sz); )


      append_merge_mark(pOut, 0, ln1, useCrLf);
      i1 = output_one_side(pOut, pV1, aC1, i1, sz, &ln1);


      append_merge_mark(pOut, 1, lnPivot, useCrLf);
      blob_copy_lines(pOut, pPivot, sz);   lnPivot += sz;


      append_merge_mark(pOut, 2, ln2, useCrLf);
      i2 = output_one_side(pOut, pV2, aC2, i2, sz, &ln2);


      append_merge_mark(pOut, 3, -1, useCrLf);
   }

    /* If we are finished with an edit triple, advance to the next
    ** triple.
    */
    if( i1<limit1 && aC1[i1]==0 && aC1[i1+1]==0 && aC1[i1+2]==0 ) i1+=3;
    if( i2<limit2 && aC2[i2]==0 && aC2[i2+1]==0 && aC2[i2+2]==0 ) i2+=3;
376
377
378
379
380
381
382
383
384

385
386
387
388
389
390
391
  int n = blob_size(p) - len + 1;
  assert( len==(int)strlen(mergeMarker[1]) );
  assert( len==(int)strlen(mergeMarker[2]) );
  assert( len==(int)strlen(mergeMarker[3]) );
  assert( count(mergeMarker)==4 );
  for(i=0; i<n; ){
    for(j=0; j<4; j++){
      if( (memcmp(&z[i], mergeMarker[j], len)==0)
          && (i+1==n || z[i+len]=='\n' || z[i+len]=='\r') ) return 1;

    }
    while( i<n && z[i]!='\n' ){ i++; }
    while( i<n && (z[i]=='\n' || z[i]=='\r') ){ i++; }
  }
  return 0;
}








|
|
>







385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
  int n = blob_size(p) - len + 1;
  assert( len==(int)strlen(mergeMarker[1]) );
  assert( len==(int)strlen(mergeMarker[2]) );
  assert( len==(int)strlen(mergeMarker[3]) );
  assert( count(mergeMarker)==4 );
  for(i=0; i<n; ){
    for(j=0; j<4; j++){
      if( (memcmp(&z[i], mergeMarker[j], len)==0) ){
        return 1;
      }
    }
    while( i<n && z[i]!='\n' ){ i++; }
    while( i<n && (z[i]=='\n' || z[i]=='\r') ){ i++; }
  }
  return 0;
}

Changes to src/piechart.c.
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
  rTooSmall = 0.0;
  nTooSmall = 0;
  if( (pieFlags & PIE_OTHER)!=0 && nTotal>1 ){
    db_prepare(&q, "SELECT sum(amt), count(*) FROM piechart WHERE amt<:amt");
    db_bind_double(&q, ":amt", rTotal/OTHER_CUTOFF);
    if( db_step(&q)==SQLITE_ROW ){
      rTooSmall = db_column_double(&q, 0);
      nTooSmall = db_column_double(&q, 1);
    }
    db_finalize(&q);
  }
  if( nTooSmall>1 ){
    db_prepare(&q, "SELECT amt, label FROM piechart WHERE amt>=:limit"
                   " UNION ALL SELECT %.17g, '%d others';",
                    rTooSmall, nTooSmall);







|







154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
  rTooSmall = 0.0;
  nTooSmall = 0;
  if( (pieFlags & PIE_OTHER)!=0 && nTotal>1 ){
    db_prepare(&q, "SELECT sum(amt), count(*) FROM piechart WHERE amt<:amt");
    db_bind_double(&q, ":amt", rTotal/OTHER_CUTOFF);
    if( db_step(&q)==SQLITE_ROW ){
      rTooSmall = db_column_double(&q, 0);
      nTooSmall = db_column_int(&q, 1);
    }
    db_finalize(&q);
  }
  if( nTooSmall>1 ){
    db_prepare(&q, "SELECT amt, label FROM piechart WHERE amt>=:limit"
                   " UNION ALL SELECT %.17g, '%d others';",
                    rTooSmall, nTooSmall);
Changes to src/pikchr.c.
6270
6271
6272
6273
6274
6275
6276
6277
6278
6279
6280
6281
6282
6283
6284
}

/*
** Round a PNum into the nearest integer
*/
static int pik_round(PNum v){
  if( isnan(v) ) return 0;
  if( v < -2147483647 ) return -2147483648;
  if( v >= 2147483647 ) return 2147483647;
  return (int)v;
}

/*
** Search for the variable named z[0..n-1] in:
**







|







6270
6271
6272
6273
6274
6275
6276
6277
6278
6279
6280
6281
6282
6283
6284
}

/*
** Round a PNum into the nearest integer
*/
static int pik_round(PNum v){
  if( isnan(v) ) return 0;
  if( v < -2147483647 ) return (-2147483647-1);
  if( v >= 2147483647 ) return 2147483647;
  return (int)v;
}

/*
** Search for the variable named z[0..n-1] in:
**
Changes to src/pivot.c.
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74

/*
** Set a secondary file.  The primary file must be set first.  There
** must be at least one secondary but there can be more than one if
** desired.
*/
void pivot_set_secondary(int rid){
  /* Insert the primary record */
  db_multi_exec(
    "INSERT OR IGNORE INTO aqueue(rid, mtime, pending, src)"
    "  SELECT %d, mtime, 1, 0 FROM event WHERE objid=%d AND type='ci'",
    rid, rid
  );
}








|







60
61
62
63
64
65
66
67
68
69
70
71
72
73
74

/*
** Set a secondary file.  The primary file must be set first.  There
** must be at least one secondary but there can be more than one if
** desired.
*/
void pivot_set_secondary(int rid){
  /* Insert the secondary record */
  db_multi_exec(
    "INSERT OR IGNORE INTO aqueue(rid, mtime, pending, src)"
    "  SELECT %d, mtime, 1, 0 FROM event WHERE objid=%d AND type='ci'",
    rid, rid
  );
}

Changes to src/rebuild.c.
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386

/*
** Core function to rebuild the information in the derived tables of a
** fossil repository from the blobs. This function is shared between
** 'rebuild_database' ('rebuild') and 'reconstruct_cmd'
** ('reconstruct'), both of which have to regenerate this information
** from scratch.
**
** If the randomize parameter is true, then the BLOBs are deliberately
** extracted in a random order.  This feature is used to test the
** ability of fossil to accept records in any order and still
** construct a sane repository.
*/
int rebuild_db(int randomize, int doOut, int doClustering){
  Stmt s, q;
  int errCnt = 0;
  int incrSize;
  Blob sql;

  bag_clear(&bagDone);
  ttyOutput = doOut;







<
<
<
<
<

|







366
367
368
369
370
371
372





373
374
375
376
377
378
379
380
381

/*
** Core function to rebuild the information in the derived tables of a
** fossil repository from the blobs. This function is shared between
** 'rebuild_database' ('rebuild') and 'reconstruct_cmd'
** ('reconstruct'), both of which have to regenerate this information
** from scratch.





*/
int rebuild_db(int doOut, int doClustering){
  Stmt s, q;
  int errCnt = 0;
  int incrSize;
  Blob sql;

  bag_clear(&bagDone);
  ttyOutput = doOut;
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
**   --force           Force the rebuild to complete even if errors are seen
**   --ifneeded        Only do the rebuild if it would change the schema version
**   --index           Always add in the full-text search index
**   --noverify        Skip the verification of changes to the BLOB table
**   --noindex         Always omit the full-text search index
**   --pagesize N      Set the database pagesize to N. (512..65536 and power of 2)
**   --quiet           Only show output if there are errors
**   --randomize       Scan artifacts in a random order
**   --stats           Show artifact statistics after rebuilding
**   --vacuum          Run VACUUM on the database after rebuilding
**   --wal             Set Write-Ahead-Log journalling mode on the database
*/
void rebuild_database(void){
  int forceFlag;
  int randomizeFlag;
  int errCnt = 0;
  int omitVerify;
  int doClustering;
  const char *zPagesize;
  int newPagesize = 0;
  int activateWal;
  int runVacuum;
  int runDeanalyze;
  int runAnalyze;
  int runCompress;
  int showStats;
  int runReindex;
  int optNoIndex;
  int optIndex;
  int optIfNeeded;
  int compressOnlyFlag;

  omitVerify = find_option("noverify",0,0)!=0;
  forceFlag = find_option("force","f",0)!=0;
  randomizeFlag = find_option("randomize", 0, 0)!=0;
  doClustering = find_option("cluster", 0, 0)!=0;
  runVacuum = find_option("vacuum",0,0)!=0;
  runDeanalyze = find_option("deanalyze",0,0)!=0;
  runAnalyze = find_option("analyze",0,0)!=0;
  runCompress = find_option("compress",0,0)!=0;
  zPagesize = find_option("pagesize",0,1);
  showStats = find_option("stats",0,0)!=0;







<






<



















<







598
599
600
601
602
603
604

605
606
607
608
609
610

611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629

630
631
632
633
634
635
636
**   --force           Force the rebuild to complete even if errors are seen
**   --ifneeded        Only do the rebuild if it would change the schema version
**   --index           Always add in the full-text search index
**   --noverify        Skip the verification of changes to the BLOB table
**   --noindex         Always omit the full-text search index
**   --pagesize N      Set the database pagesize to N. (512..65536 and power of 2)
**   --quiet           Only show output if there are errors

**   --stats           Show artifact statistics after rebuilding
**   --vacuum          Run VACUUM on the database after rebuilding
**   --wal             Set Write-Ahead-Log journalling mode on the database
*/
void rebuild_database(void){
  int forceFlag;

  int errCnt = 0;
  int omitVerify;
  int doClustering;
  const char *zPagesize;
  int newPagesize = 0;
  int activateWal;
  int runVacuum;
  int runDeanalyze;
  int runAnalyze;
  int runCompress;
  int showStats;
  int runReindex;
  int optNoIndex;
  int optIndex;
  int optIfNeeded;
  int compressOnlyFlag;

  omitVerify = find_option("noverify",0,0)!=0;
  forceFlag = find_option("force","f",0)!=0;

  doClustering = find_option("cluster", 0, 0)!=0;
  runVacuum = find_option("vacuum",0,0)!=0;
  runDeanalyze = find_option("deanalyze",0,0)!=0;
  runAnalyze = find_option("analyze",0,0)!=0;
  runCompress = find_option("compress",0,0)!=0;
  zPagesize = find_option("pagesize",0,1);
  showStats = find_option("stats",0,0)!=0;
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
  verify_all_options();

  db_begin_transaction();
  db_unprotect(PROTECT_ALL);
  if( !compressOnlyFlag ){
    search_drop_index();
    ttyOutput = 1;
    errCnt = rebuild_db(randomizeFlag, 1, doClustering);
    reconstruct_private_table();
  }
  db_multi_exec(
    "REPLACE INTO config(name,value,mtime) VALUES('content-schema',%Q,now());"
    "REPLACE INTO config(name,value,mtime) VALUES('aux-schema',%Q,now());"
    "REPLACE INTO config(name,value,mtime) VALUES('rebuilt',%Q,now());",
    CONTENT_SCHEMA, AUX_SCHEMA_MAX, get_version()







|







669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
  verify_all_options();

  db_begin_transaction();
  db_unprotect(PROTECT_ALL);
  if( !compressOnlyFlag ){
    search_drop_index();
    ttyOutput = 1;
    errCnt = rebuild_db(1, doClustering);
    reconstruct_private_table();
  }
  db_multi_exec(
    "REPLACE INTO config(name,value,mtime) VALUES('content-schema',%Q,now());"
    "REPLACE INTO config(name,value,mtime) VALUES('aux-schema',%Q,now());"
    "REPLACE INTO config(name,value,mtime) VALUES('rebuilt',%Q,now());",
    CONTENT_SCHEMA, AUX_SCHEMA_MAX, get_version()
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
  }
  if( !bNeedRebuild ){
    db_end_transaction(0);
    db_unprotect(PROTECT_ALL);
    db_multi_exec("VACUUM;");
    db_protect_pop();
  }else{
    rebuild_db(0, 1, 0);
    db_end_transaction(0);
  }
}

/*
** Recursively read all files from the directory zPath and install
** every file read as a new artifact in the repository.







|







953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
  }
  if( !bNeedRebuild ){
    db_end_transaction(0);
    db_unprotect(PROTECT_ALL);
    db_multi_exec("VACUUM;");
    db_protect_pop();
  }else{
    rebuild_db(1, 0);
    db_end_transaction(0);
  }
}

/*
** Recursively read all files from the directory zPath and install
** every file read as a new artifact in the repository.
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262
1263
1264
1265
1266
1267
  db_begin_transaction();
  db_initial_setup(0, 0, 0);

  fossil_print("Reading files from directory \"%s\"...\n", g.argv[3]);
  recon_read_dir(g.argv[3]);
  fossil_print("\nBuilding the Fossil repository...\n");

  rebuild_db(0, 1, 1);

  /* Backwards compatibility: Mark check-ins with "+private" tags as private. */
  reconstruct_private_table();
  /* Newer method: Import the list of private artifacts to the PRIVATE table. */
  if( fKeepPrivate ){
    char *zFnDotPrivate = mprintf("%s/.private", g.argv[3]);
    private_import(zFnDotPrivate);







|







1245
1246
1247
1248
1249
1250
1251
1252
1253
1254
1255
1256
1257
1258
1259
  db_begin_transaction();
  db_initial_setup(0, 0, 0);

  fossil_print("Reading files from directory \"%s\"...\n", g.argv[3]);
  recon_read_dir(g.argv[3]);
  fossil_print("\nBuilding the Fossil repository...\n");

  rebuild_db(1, 1);

  /* Backwards compatibility: Mark check-ins with "+private" tags as private. */
  reconstruct_private_table();
  /* Newer method: Import the list of private artifacts to the PRIVATE table. */
  if( fKeepPrivate ){
    char *zFnDotPrivate = mprintf("%s/.private", g.argv[3]);
    private_import(zFnDotPrivate);
Changes to src/shell.c.
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
  if( quote ){
    len += 2;
    for(i=0; i<nAppend; i++){
      if( zAppend[i]==quote ) len++;
    }
  }

  if( p->n+len>=p->nAlloc ){
    p->nAlloc = p->nAlloc*2 + len + 20;
    p->z = realloc(p->z, p->nAlloc);
    if( p->z==0 ) shell_out_of_memory();
  }

  if( quote ){
    char *zCsr = p->z+p->n;







|







870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
  if( quote ){
    len += 2;
    for(i=0; i<nAppend; i++){
      if( zAppend[i]==quote ) len++;
    }
  }

  if( p->z==0 || p->n+len>=p->nAlloc ){
    p->nAlloc = p->nAlloc*2 + len + 20;
    p->z = realloc(p->z, p->nAlloc);
    if( p->z==0 ) shell_out_of_memory();
  }

  if( quote ){
    char *zCsr = p->z+p->n;
6259
6260
6261
6262
6263
6264
6265
6266
6267
6268
6269
6270
6271
6272
6273
6274
6275
        }
        case RE_OP_ACCEPT: {
          rc = 1;
          goto re_match_end;
        }
        case RE_OP_CC_EXC: {
          if( c==0 ) break;
          /* fall-through */
        }
        case RE_OP_CC_INC: {
          int j = 1;
          int n = pRe->aArg[x];
          int hit = 0;
          for(j=1; j>0 && j<n; j++){
            if( pRe->aOp[x+j]==RE_OP_CC_VALUE ){
              if( pRe->aArg[x+j]==c ){
                hit = 1;







|

|







6259
6260
6261
6262
6263
6264
6265
6266
6267
6268
6269
6270
6271
6272
6273
6274
6275
        }
        case RE_OP_ACCEPT: {
          rc = 1;
          goto re_match_end;
        }
        case RE_OP_CC_EXC: {
          if( c==0 ) break;
          /* fall-through */ goto re_op_cc_inc;
        }
        case RE_OP_CC_INC: re_op_cc_inc: {
          int j = 1;
          int n = pRe->aArg[x];
          int hit = 0;
          for(j=1; j>0 && j<n; j++){
            if( pRe->aOp[x+j]==RE_OP_CC_VALUE ){
              if( pRe->aArg[x+j]==c ){
                hit = 1;
6792
6793
6794
6795
6796
6797
6798



6799
6800
6801
6802
6803
6804
6805
/* typedef sqlite3_int64 i64; */
/* typedef unsigned char u8; */
typedef UINT32_TYPE u32;           /* 4-byte unsigned integer */
typedef UINT16_TYPE u16;           /* 2-byte unsigned integer */
#define MIN(a,b) ((a)<(b) ? (a) : (b))

#if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_MUTATION_TEST)



# define ALWAYS(X)      (1)
# define NEVER(X)       (0)
#elif !defined(NDEBUG)
# define ALWAYS(X)      ((X)?1:(assert(0),0))
# define NEVER(X)       ((X)?(assert(0),1):0)
#else
# define ALWAYS(X)      (X)







>
>
>







6792
6793
6794
6795
6796
6797
6798
6799
6800
6801
6802
6803
6804
6805
6806
6807
6808
/* typedef sqlite3_int64 i64; */
/* typedef unsigned char u8; */
typedef UINT32_TYPE u32;           /* 4-byte unsigned integer */
typedef UINT16_TYPE u16;           /* 2-byte unsigned integer */
#define MIN(a,b) ((a)<(b) ? (a) : (b))

#if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_MUTATION_TEST)
# define SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS 1
#endif
#if defined(SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS)
# define ALWAYS(X)      (1)
# define NEVER(X)       (0)
#elif !defined(NDEBUG)
# define ALWAYS(X)      ((X)?1:(assert(0),0))
# define NEVER(X)       ((X)?(assert(0),1):0)
#else
# define ALWAYS(X)      (X)
8670
8671
8672
8673
8674
8675
8676
8677
8678
8679
8680
8681
8682
8683
8684
** xStep() callback for the zipfile() aggregate. This can be called in
** any of the following ways:
**
**   SELECT zipfile(name,data) ...
**   SELECT zipfile(name,mode,mtime,data) ...
**   SELECT zipfile(name,mode,mtime,data,method) ...
*/
void zipfileStep(sqlite3_context *pCtx, int nVal, sqlite3_value **apVal){
  ZipfileCtx *p;                  /* Aggregate function context */
  ZipfileEntry e;                 /* New entry to add to zip archive */

  sqlite3_value *pName = 0;
  sqlite3_value *pMode = 0;
  sqlite3_value *pMtime = 0;
  sqlite3_value *pData = 0;







|







8673
8674
8675
8676
8677
8678
8679
8680
8681
8682
8683
8684
8685
8686
8687
** xStep() callback for the zipfile() aggregate. This can be called in
** any of the following ways:
**
**   SELECT zipfile(name,data) ...
**   SELECT zipfile(name,mode,mtime,data) ...
**   SELECT zipfile(name,mode,mtime,data,method) ...
*/
static void zipfileStep(sqlite3_context *pCtx, int nVal, sqlite3_value **apVal){
  ZipfileCtx *p;                  /* Aggregate function context */
  ZipfileEntry e;                 /* New entry to add to zip archive */

  sqlite3_value *pName = 0;
  sqlite3_value *pMode = 0;
  sqlite3_value *pMtime = 0;
  sqlite3_value *pData = 0;
8845
8846
8847
8848
8849
8850
8851
8852
8853
8854
8855
8856
8857
8858
8859
  }
  sqlite3_free(zErr);
}

/*
** xFinalize() callback for zipfile aggregate function.
*/
void zipfileFinal(sqlite3_context *pCtx){
  ZipfileCtx *p;
  ZipfileEOCD eocd;
  sqlite3_int64 nZip;
  u8 *aZip;

  p = (ZipfileCtx*)sqlite3_aggregate_context(pCtx, sizeof(ZipfileCtx));
  if( p==0 ) return;







|







8848
8849
8850
8851
8852
8853
8854
8855
8856
8857
8858
8859
8860
8861
8862
  }
  sqlite3_free(zErr);
}

/*
** xFinalize() callback for zipfile aggregate function.
*/
static void zipfileFinal(sqlite3_context *pCtx){
  ZipfileCtx *p;
  ZipfileEOCD eocd;
  sqlite3_int64 nZip;
  u8 *aZip;

  p = (ZipfileCtx*)sqlite3_aggregate_context(pCtx, sizeof(ZipfileCtx));
  if( p==0 ) return;
9251
9252
9253
9254
9255
9256
9257

















9258
9259
9260
9261
9262
9263
9264
**
*************************************************************************
*/
/* #include "sqlite3expert.h" */
#include <assert.h>
#include <string.h>
#include <stdio.h>


















#ifndef SQLITE_OMIT_VIRTUALTABLE 

/* typedef sqlite3_int64 i64; */
/* typedef sqlite3_uint64 u64; */

typedef struct IdxColumn IdxColumn;







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







9254
9255
9256
9257
9258
9259
9260
9261
9262
9263
9264
9265
9266
9267
9268
9269
9270
9271
9272
9273
9274
9275
9276
9277
9278
9279
9280
9281
9282
9283
9284
**
*************************************************************************
*/
/* #include "sqlite3expert.h" */
#include <assert.h>
#include <string.h>
#include <stdio.h>

#if !defined(SQLITE_AMALGAMATION)
#if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_MUTATION_TEST)
# define SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS 1
#endif
#if defined(SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS)
# define ALWAYS(X)      (1)
# define NEVER(X)       (0)
#elif !defined(NDEBUG)
# define ALWAYS(X)      ((X)?1:(assert(0),0))
# define NEVER(X)       ((X)?(assert(0),1):0)
#else
# define ALWAYS(X)      (X)
# define NEVER(X)       (X)
#endif
#endif /* !defined(SQLITE_AMALGAMATION) */


#ifndef SQLITE_OMIT_VIRTUALTABLE 

/* typedef sqlite3_int64 i64; */
/* typedef sqlite3_uint64 u64; */

typedef struct IdxColumn IdxColumn;
9978
9979
9980
9981
9982
9983
9984
9985
9986
9987
9988
9989
9990
9991
9992
9993
9994
    nCol++;
  }
  idxFinalize(&rc, p1);

  if( rc!=SQLITE_OK ){
    sqlite3_free(pNew);
    pNew = 0;
  }else{
    pNew->zName = pCsr;
    memcpy(pNew->zName, zTab, nTab+1);
  }

  *ppOut = pNew;
  return rc;
}

/*







|

|







9998
9999
10000
10001
10002
10003
10004
10005
10006
10007
10008
10009
10010
10011
10012
10013
10014
    nCol++;
  }
  idxFinalize(&rc, p1);

  if( rc!=SQLITE_OK ){
    sqlite3_free(pNew);
    pNew = 0;
  }else if( ALWAYS(pNew!=0) ){
    pNew->zName = pCsr;
    if( ALWAYS(pNew->zName!=0) ) memcpy(pNew->zName, zTab, nTab+1);
  }

  *ppOut = pNew;
  return rc;
}

/*
10388
10389
10390
10391
10392
10393
10394
10395
10396
10397
10398
10399
10400
10401
10402


/*
** This function is called after candidate indexes have been created. It
** runs all the queries to see which indexes they prefer, and populates
** IdxStatement.zIdx and IdxStatement.zEQP with the results.
*/
int idxFindIndexes(
  sqlite3expert *p,
  char **pzErr                         /* OUT: Error message (sqlite3_malloc) */
){
  IdxStatement *pStmt;
  sqlite3 *dbm = p->dbm;
  int rc = SQLITE_OK;








|







10408
10409
10410
10411
10412
10413
10414
10415
10416
10417
10418
10419
10420
10421
10422


/*
** This function is called after candidate indexes have been created. It
** runs all the queries to see which indexes they prefer, and populates
** IdxStatement.zIdx and IdxStatement.zEQP with the results.
*/
static int idxFindIndexes(
  sqlite3expert *p,
  char **pzErr                         /* OUT: Error message (sqlite3_malloc) */
){
  IdxStatement *pStmt;
  sqlite3 *dbm = p->dbm;
  int rc = SQLITE_OK;

12287
12288
12289
12290
12291
12292
12293


12294
12295
12296
12297
12298
12299
12300
12301
12302
12303
12304
12305
12306
12307
12308
12309
12310
12311
12312


12313
12314
12315
12316
12317
12318
12319
#define MODE_Ascii   10  /* Use ASCII unit and record separators (0x1F/0x1E) */
#define MODE_Pretty  11  /* Pretty-print schemas */
#define MODE_EQP     12  /* Converts EXPLAIN QUERY PLAN output into a graph */
#define MODE_Json    13  /* Output JSON */
#define MODE_Markdown 14 /* Markdown formatting */
#define MODE_Table   15  /* MySQL-style table formatting */
#define MODE_Box     16  /* Unicode box-drawing characters */



static const char *modeDescr[] = {
  "line",
  "column",
  "list",
  "semi",
  "html",
  "insert",
  "quote",
  "tcl",
  "csv",
  "explain",
  "ascii",
  "prettyprint",
  "eqp",
  "json",
  "markdown",
  "table",
  "box"


};

/*
** These are the column/row/line separators used by the various
** import/export modes.
*/
#define SEP_Column    "|"







>
>


















|
>
>







12307
12308
12309
12310
12311
12312
12313
12314
12315
12316
12317
12318
12319
12320
12321
12322
12323
12324
12325
12326
12327
12328
12329
12330
12331
12332
12333
12334
12335
12336
12337
12338
12339
12340
12341
12342
12343
#define MODE_Ascii   10  /* Use ASCII unit and record separators (0x1F/0x1E) */
#define MODE_Pretty  11  /* Pretty-print schemas */
#define MODE_EQP     12  /* Converts EXPLAIN QUERY PLAN output into a graph */
#define MODE_Json    13  /* Output JSON */
#define MODE_Markdown 14 /* Markdown formatting */
#define MODE_Table   15  /* MySQL-style table formatting */
#define MODE_Box     16  /* Unicode box-drawing characters */
#define MODE_Count   17  /* Output only a count of the rows of output */
#define MODE_Off     18  /* No query output shown */

static const char *modeDescr[] = {
  "line",
  "column",
  "list",
  "semi",
  "html",
  "insert",
  "quote",
  "tcl",
  "csv",
  "explain",
  "ascii",
  "prettyprint",
  "eqp",
  "json",
  "markdown",
  "table",
  "box",
  "count",
  "off"
};

/*
** These are the column/row/line separators used by the various
** import/export modes.
*/
#define SEP_Column    "|"
12796
12797
12798
12799
12800
12801
12802
12803
12804
12805
12806
12807
12808
12809
12810
12811
12812
12813
12814
12815
12816
12817
12818
12819
12820
** is only issued if bSep is true.
*/
static void output_csv(ShellState *p, const char *z, int bSep){
  FILE *out = p->out;
  if( z==0 ){
    utf8_printf(out,"%s",p->nullValue);
  }else{
    int i;
    int nSep = strlen30(p->colSeparator);
    for(i=0; z[i]; i++){
      if( needCsvQuote[((unsigned char*)z)[i]]
         || (z[i]==p->colSeparator[0] &&
             (nSep==1 || memcmp(z, p->colSeparator, nSep)==0)) ){
        i = 0;
        break;
      }
    }
    if( i==0 ){
      char *zQuoted = sqlite3_mprintf("\"%w\"", z);
      utf8_printf(out, "%s", zQuoted);
      sqlite3_free(zQuoted);
    }else{
      utf8_printf(out, "%s", z);
    }
  }







|
<

|
<
<




|







12820
12821
12822
12823
12824
12825
12826
12827

12828
12829


12830
12831
12832
12833
12834
12835
12836
12837
12838
12839
12840
12841
** is only issued if bSep is true.
*/
static void output_csv(ShellState *p, const char *z, int bSep){
  FILE *out = p->out;
  if( z==0 ){
    utf8_printf(out,"%s",p->nullValue);
  }else{
    unsigned i;

    for(i=0; z[i]; i++){
      if( needCsvQuote[((unsigned char*)z)[i]] ){


        i = 0;
        break;
      }
    }
    if( i==0 || strstr(z, p->colSeparator)!=0 ){
      char *zQuoted = sqlite3_mprintf("\"%w\"", z);
      utf8_printf(out, "%s", zQuoted);
      sqlite3_free(zQuoted);
    }else{
      utf8_printf(out, "%s", z);
    }
  }
13130
13131
13132
13133
13134
13135
13136




13137
13138
13139
13140
13141
13142
13143
  int *aiType      /* Column types.  Might be NULL */
){
  int i;
  ShellState *p = (ShellState*)pArg;

  if( azArg==0 ) return 0;
  switch( p->cMode ){




    case MODE_Line: {
      int w = 5;
      if( azArg==0 ) break;
      for(i=0; i<nArg; i++){
        int len = strlen30(azCol[i] ? azCol[i] : "");
        if( len>w ) w = len;
      }







>
>
>
>







13151
13152
13153
13154
13155
13156
13157
13158
13159
13160
13161
13162
13163
13164
13165
13166
13167
13168
  int *aiType      /* Column types.  Might be NULL */
){
  int i;
  ShellState *p = (ShellState*)pArg;

  if( azArg==0 ) return 0;
  switch( p->cMode ){
    case MODE_Count:
    case MODE_Off: {
      break;
    }
    case MODE_Line: {
      int w = 5;
      if( azArg==0 ) break;
      for(i=0; i<nArg; i++){
        int len = strlen30(azCol[i] ? azCol[i] : "");
        if( len>w ) w = len;
      }
13640
13641
13642
13643
13644
13645
13646
13647
13648
13649
13650


13651
13652
13653
13654

13655
13656
13657
13658
13659
13660
13661
13662
13663
13664
                sqlite3_errmsg(p->db));
    if( (rc&0xff)!=SQLITE_CORRUPT ) p->nErr++;
  }
  return rc;
}

/*
** Allocate space and save off current error string.
*/
static char *save_err_msg(
  sqlite3 *db            /* Database to query */


){
  int nErrMsg = 1+strlen30(sqlite3_errmsg(db));
  char *zErrMsg = sqlite3_malloc64(nErrMsg);
  if( zErrMsg ){

    memcpy(zErrMsg, sqlite3_errmsg(db), nErrMsg);
  }
  return zErrMsg;
}

#ifdef __linux__
/*
** Attempt to display I/O stats on Linux using /proc/PID/io
*/
static void displayLinuxIoStats(FILE *out){







|


|
>
>

<
<
|
>
|
<
<







13665
13666
13667
13668
13669
13670
13671
13672
13673
13674
13675
13676
13677
13678


13679
13680
13681


13682
13683
13684
13685
13686
13687
13688
                sqlite3_errmsg(p->db));
    if( (rc&0xff)!=SQLITE_CORRUPT ) p->nErr++;
  }
  return rc;
}

/*
** Allocate space and save off string indicating current error.
*/
static char *save_err_msg(
  sqlite3 *db,           /* Database to query */
  const char *zWhen,     /* Qualifier (format) wrapper */
  int rc                 /* Error code returned from API */
){


  if( zWhen==0 )
    zWhen = "%s (%d)";
  return sqlite3_mprintf(zWhen, sqlite3_errmsg(db), rc);


}

#ifdef __linux__
/*
** Attempt to display I/O stats on Linux using /proc/PID/io
*/
static void displayLinuxIoStats(FILE *out){
13828
13829
13830
13831
13832
13833
13834

13835
13836
13837
13838
13839
13840
13841






13842
13843
13844
13845
13846
13847
13848
    iHiwtr = iCur = -1;
    sqlite3_db_status(db, SQLITE_DBSTATUS_STMT_USED, &iCur, &iHiwtr, bReset);
    raw_printf(pArg->out, "Statement Heap/Lookaside Usage:      %d bytes\n",
            iCur);
  }

  if( pArg->pStmt ){

    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_FULLSCAN_STEP,
                               bReset);
    raw_printf(pArg->out, "Fullscan Steps:                      %d\n", iCur);
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_SORT, bReset);
    raw_printf(pArg->out, "Sort Operations:                     %d\n", iCur);
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_AUTOINDEX,bReset);
    raw_printf(pArg->out, "Autoindex Inserts:                   %d\n", iCur);






    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_VM_STEP, bReset);
    raw_printf(pArg->out, "Virtual Machine Steps:               %d\n", iCur);
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_REPREPARE,bReset);
    raw_printf(pArg->out, "Reprepare operations:                %d\n", iCur);
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_RUN, bReset);
    raw_printf(pArg->out, "Number of times run:                 %d\n", iCur);
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_MEMUSED, bReset);







>







>
>
>
>
>
>







13852
13853
13854
13855
13856
13857
13858
13859
13860
13861
13862
13863
13864
13865
13866
13867
13868
13869
13870
13871
13872
13873
13874
13875
13876
13877
13878
13879
    iHiwtr = iCur = -1;
    sqlite3_db_status(db, SQLITE_DBSTATUS_STMT_USED, &iCur, &iHiwtr, bReset);
    raw_printf(pArg->out, "Statement Heap/Lookaside Usage:      %d bytes\n",
            iCur);
  }

  if( pArg->pStmt ){
    int iHit, iMiss;
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_FULLSCAN_STEP,
                               bReset);
    raw_printf(pArg->out, "Fullscan Steps:                      %d\n", iCur);
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_SORT, bReset);
    raw_printf(pArg->out, "Sort Operations:                     %d\n", iCur);
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_AUTOINDEX,bReset);
    raw_printf(pArg->out, "Autoindex Inserts:                   %d\n", iCur);
    iHit = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_FILTER_HIT, bReset);
    iMiss = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_FILTER_MISS, bReset);
    if( iHit || iMiss ){
      raw_printf(pArg->out, "Bloom filter bypass taken:           %d/%d\n",
            iHit, iHit+iMiss);
    }
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_VM_STEP, bReset);
    raw_printf(pArg->out, "Virtual Machine Steps:               %d\n", iCur);
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_REPREPARE,bReset);
    raw_printf(pArg->out, "Reprepare operations:                %d\n", iCur);
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_RUN, bReset);
    raw_printf(pArg->out, "Number of times run:                 %d\n", iCur);
    iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_MEMUSED, bReset);
14341
14342
14343
14344
14345
14346
14347

14348
14349
14350
14351
14352
14353
14354
** Run a prepared statement
*/
static void exec_prepared_stmt(
  ShellState *pArg,                                /* Pointer to ShellState */
  sqlite3_stmt *pStmt                              /* Statment to run */
){
  int rc;


  if( pArg->cMode==MODE_Column
   || pArg->cMode==MODE_Table
   || pArg->cMode==MODE_Box
   || pArg->cMode==MODE_Markdown
  ){
    exec_prepared_stmt_columnar(pArg, pStmt);







>







14372
14373
14374
14375
14376
14377
14378
14379
14380
14381
14382
14383
14384
14385
14386
** Run a prepared statement
*/
static void exec_prepared_stmt(
  ShellState *pArg,                                /* Pointer to ShellState */
  sqlite3_stmt *pStmt                              /* Statment to run */
){
  int rc;
  sqlite3_uint64 nRow = 0;

  if( pArg->cMode==MODE_Column
   || pArg->cMode==MODE_Table
   || pArg->cMode==MODE_Box
   || pArg->cMode==MODE_Markdown
  ){
    exec_prepared_stmt_columnar(pArg, pStmt);
14373
14374
14375
14376
14377
14378
14379

14380
14381
14382
14383
14384
14385
14386
      int i, x;
      assert(sizeof(int) <= sizeof(char *));
      /* save off ptrs to column names */
      for(i=0; i<nCol; i++){
        azCols[i] = (char *)sqlite3_column_name(pStmt, i);
      }
      do{

        /* extract the data and data types */
        for(i=0; i<nCol; i++){
          aiTypes[i] = x = sqlite3_column_type(pStmt, i);
          if( x==SQLITE_BLOB && pArg && pArg->cMode==MODE_Insert ){
            azVals[i] = "";
          }else{
            azVals[i] = (char*)sqlite3_column_text(pStmt, i);







>







14405
14406
14407
14408
14409
14410
14411
14412
14413
14414
14415
14416
14417
14418
14419
      int i, x;
      assert(sizeof(int) <= sizeof(char *));
      /* save off ptrs to column names */
      for(i=0; i<nCol; i++){
        azCols[i] = (char *)sqlite3_column_name(pStmt, i);
      }
      do{
        nRow++;
        /* extract the data and data types */
        for(i=0; i<nCol; i++){
          aiTypes[i] = x = sqlite3_column_type(pStmt, i);
          if( x==SQLITE_BLOB && pArg && pArg->cMode==MODE_Insert ){
            azVals[i] = "";
          }else{
            azVals[i] = (char*)sqlite3_column_text(pStmt, i);
14400
14401
14402
14403
14404
14405
14406


14407
14408
14409
14410
14411
14412
14413
            rc = sqlite3_step(pStmt);
          }
        }
      } while( SQLITE_ROW == rc );
      sqlite3_free(pData);
      if( pArg->cMode==MODE_Json ){
        fputs("]\n", pArg->out);


      }
    }
  }
}

#ifndef SQLITE_OMIT_VIRTUALTABLE
/*







>
>







14433
14434
14435
14436
14437
14438
14439
14440
14441
14442
14443
14444
14445
14446
14447
14448
            rc = sqlite3_step(pStmt);
          }
        }
      } while( SQLITE_ROW == rc );
      sqlite3_free(pData);
      if( pArg->cMode==MODE_Json ){
        fputs("]\n", pArg->out);
      }else if( pArg->cMode==MODE_Count ){
        printf("%llu row%s\n", nRow, nRow!=1 ? "s" : "");
      }
    }
  }
}

#ifndef SQLITE_OMIT_VIRTUALTABLE
/*
14572
14573
14574
14575
14576
14577
14578
14579
14580
14581
14582
14583
14584
14585
14586
#endif

  while( zSql[0] && (SQLITE_OK == rc) ){
    static const char *zStmtSql;
    rc = sqlite3_prepare_v2(db, zSql, -1, &pStmt, &zLeftover);
    if( SQLITE_OK != rc ){
      if( pzErrMsg ){
        *pzErrMsg = save_err_msg(db);
      }
    }else{
      if( !pStmt ){
        /* this happens for a comment or white-space */
        zSql = zLeftover;
        while( IsSpace(zSql[0]) ) zSql++;
        continue;







|







14607
14608
14609
14610
14611
14612
14613
14614
14615
14616
14617
14618
14619
14620
14621
#endif

  while( zSql[0] && (SQLITE_OK == rc) ){
    static const char *zStmtSql;
    rc = sqlite3_prepare_v2(db, zSql, -1, &pStmt, &zLeftover);
    if( SQLITE_OK != rc ){
      if( pzErrMsg ){
        *pzErrMsg = save_err_msg(db, "in prepare, %s (%d)", rc);
      }
    }else{
      if( !pStmt ){
        /* this happens for a comment or white-space */
        zSql = zLeftover;
        while( IsSpace(zSql[0]) ) zSql++;
        continue;
14686
14687
14688
14689
14690
14691
14692
14693
14694
14695
14696
14697
14698
14699
14700
      ** next statement to execute. */
      rc2 = sqlite3_finalize(pStmt);
      if( rc!=SQLITE_NOMEM ) rc = rc2;
      if( rc==SQLITE_OK ){
        zSql = zLeftover;
        while( IsSpace(zSql[0]) ) zSql++;
      }else if( pzErrMsg ){
        *pzErrMsg = save_err_msg(db);
      }

      /* clear saved stmt handle */
      if( pArg ){
        pArg->pStmt = NULL;
      }
    }







|







14721
14722
14723
14724
14725
14726
14727
14728
14729
14730
14731
14732
14733
14734
14735
      ** next statement to execute. */
      rc2 = sqlite3_finalize(pStmt);
      if( rc!=SQLITE_NOMEM ) rc = rc2;
      if( rc==SQLITE_OK ){
        zSql = zLeftover;
        while( IsSpace(zSql[0]) ) zSql++;
      }else if( pzErrMsg ){
        *pzErrMsg = save_err_msg(db, "stepping, %s (%d)", rc);
      }

      /* clear saved stmt handle */
      if( pArg ){
        pArg->pStmt = NULL;
      }
    }
15000
15001
15002
15003
15004
15005
15006

15007
15008
15009
15010
15011
15012
15013

15014
15015
15016
15017
15018
15019
15020
static const char *(azHelp[]) = {
#if defined(SQLITE_HAVE_ZLIB) && !defined(SQLITE_OMIT_VIRTUALTABLE)
  ".archive ...             Manage SQL archives",
  "   Each command must have exactly one of the following options:",
  "     -c, --create               Create a new archive",
  "     -u, --update               Add or update files with changed mtime",
  "     -i, --insert               Like -u but always add even if unchanged",

  "     -t, --list                 List contents of archive",
  "     -x, --extract              Extract files from archive",
  "   Optional arguments:",
  "     -v, --verbose              Print each filename as it is processed",
  "     -f FILE, --file FILE       Use archive FILE (default is current db)",
  "     -a FILE, --append FILE     Open FILE using the apndvfs VFS",
  "     -C DIR, --directory DIR    Read/extract files from directory DIR",

  "     -n, --dryrun               Show the SQL that would have occurred",
  "   Examples:",
  "     .ar -cf ARCHIVE foo bar  # Create ARCHIVE from files foo and bar",
  "     .ar -tf ARCHIVE          # List members of ARCHIVE",
  "     .ar -xvf ARCHIVE         # Verbosely extract files from ARCHIVE",
  "   See also:",
  "      http://sqlite.org/cli.html#sqlite_archive_support",







>







>







15035
15036
15037
15038
15039
15040
15041
15042
15043
15044
15045
15046
15047
15048
15049
15050
15051
15052
15053
15054
15055
15056
15057
static const char *(azHelp[]) = {
#if defined(SQLITE_HAVE_ZLIB) && !defined(SQLITE_OMIT_VIRTUALTABLE)
  ".archive ...             Manage SQL archives",
  "   Each command must have exactly one of the following options:",
  "     -c, --create               Create a new archive",
  "     -u, --update               Add or update files with changed mtime",
  "     -i, --insert               Like -u but always add even if unchanged",
  "     -r, --remove               Remove files from archive",
  "     -t, --list                 List contents of archive",
  "     -x, --extract              Extract files from archive",
  "   Optional arguments:",
  "     -v, --verbose              Print each filename as it is processed",
  "     -f FILE, --file FILE       Use archive FILE (default is current db)",
  "     -a FILE, --append FILE     Open FILE using the apndvfs VFS",
  "     -C DIR, --directory DIR    Read/extract files from directory DIR",
  "     -g, --glob                 Use glob matching for names in archive",
  "     -n, --dryrun               Show the SQL that would have occurred",
  "   Examples:",
  "     .ar -cf ARCHIVE foo bar  # Create ARCHIVE from files foo and bar",
  "     .ar -tf ARCHIVE          # List members of ARCHIVE",
  "     .ar -xvf ARCHIVE         # Verbosely extract files from ARCHIVE",
  "   See also:",
  "      http://sqlite.org/cli.html#sqlite_archive_support",
17167
17168
17169
17170
17171
17172
17173

17174
17175
17176
17177
17178
17179
17180
typedef struct ArCommand ArCommand;
struct ArCommand {
  u8 eCmd;                        /* An AR_CMD_* value */
  u8 bVerbose;                    /* True if --verbose */
  u8 bZip;                        /* True if the archive is a ZIP */
  u8 bDryRun;                     /* True if --dry-run */
  u8 bAppend;                     /* True if --append */

  u8 fromCmdLine;                 /* Run from -A instead of .archive */
  int nArg;                       /* Number of command arguments */
  char *zSrcTable;                /* "sqlar", "zipfile($file)" or "zip" */
  const char *zFile;              /* --file argument, or NULL */
  const char *zDir;               /* --directory argument, or NULL */
  char **azArg;                   /* Array of command arguments */
  ShellState *p;                  /* Shell state */







>







17204
17205
17206
17207
17208
17209
17210
17211
17212
17213
17214
17215
17216
17217
17218
typedef struct ArCommand ArCommand;
struct ArCommand {
  u8 eCmd;                        /* An AR_CMD_* value */
  u8 bVerbose;                    /* True if --verbose */
  u8 bZip;                        /* True if the archive is a ZIP */
  u8 bDryRun;                     /* True if --dry-run */
  u8 bAppend;                     /* True if --append */
  u8 bGlob;                       /* True if --glob */
  u8 fromCmdLine;                 /* Run from -A instead of .archive */
  int nArg;                       /* Number of command arguments */
  char *zSrcTable;                /* "sqlar", "zipfile($file)" or "zip" */
  const char *zFile;              /* --file argument, or NULL */
  const char *zDir;               /* --directory argument, or NULL */
  char **azArg;                   /* Array of command arguments */
  ShellState *p;                  /* Shell state */
17214
17215
17216
17217
17218
17219
17220

17221
17222
17223
17224
17225
17226
17227
17228
17229

17230
17231
17232
17233
17234
17235

17236
17237
17238
17239
17240
17241
17242
17243
17244
17245
17246



17247
17248
17249
17250
17251
17252
17253
*/
#define AR_CMD_CREATE       1
#define AR_CMD_UPDATE       2
#define AR_CMD_INSERT       3
#define AR_CMD_EXTRACT      4
#define AR_CMD_LIST         5
#define AR_CMD_HELP         6


/*
** Other (non-command) switches.
*/
#define AR_SWITCH_VERBOSE     7
#define AR_SWITCH_FILE        8
#define AR_SWITCH_DIRECTORY   9
#define AR_SWITCH_APPEND     10
#define AR_SWITCH_DRYRUN     11


static int arProcessSwitch(ArCommand *pAr, int eSwitch, const char *zArg){
  switch( eSwitch ){
    case AR_CMD_CREATE:
    case AR_CMD_EXTRACT:
    case AR_CMD_LIST:

    case AR_CMD_UPDATE:
    case AR_CMD_INSERT:
    case AR_CMD_HELP:
      if( pAr->eCmd ){
        return arErrorMsg(pAr, "multiple command options");
      }
      pAr->eCmd = eSwitch;
      break;

    case AR_SWITCH_DRYRUN:
      pAr->bDryRun = 1;



      break;
    case AR_SWITCH_VERBOSE:
      pAr->bVerbose = 1;
      break;
    case AR_SWITCH_APPEND:
      pAr->bAppend = 1;
      /* Fall thru into --file */







>




|
|
|
|
|
>






>











>
>
>







17252
17253
17254
17255
17256
17257
17258
17259
17260
17261
17262
17263
17264
17265
17266
17267
17268
17269
17270
17271
17272
17273
17274
17275
17276
17277
17278
17279
17280
17281
17282
17283
17284
17285
17286
17287
17288
17289
17290
17291
17292
17293
17294
17295
17296
17297
*/
#define AR_CMD_CREATE       1
#define AR_CMD_UPDATE       2
#define AR_CMD_INSERT       3
#define AR_CMD_EXTRACT      4
#define AR_CMD_LIST         5
#define AR_CMD_HELP         6
#define AR_CMD_REMOVE       7

/*
** Other (non-command) switches.
*/
#define AR_SWITCH_VERBOSE     8
#define AR_SWITCH_FILE        9
#define AR_SWITCH_DIRECTORY  10
#define AR_SWITCH_APPEND     11
#define AR_SWITCH_DRYRUN     12
#define AR_SWITCH_GLOB       13

static int arProcessSwitch(ArCommand *pAr, int eSwitch, const char *zArg){
  switch( eSwitch ){
    case AR_CMD_CREATE:
    case AR_CMD_EXTRACT:
    case AR_CMD_LIST:
    case AR_CMD_REMOVE:
    case AR_CMD_UPDATE:
    case AR_CMD_INSERT:
    case AR_CMD_HELP:
      if( pAr->eCmd ){
        return arErrorMsg(pAr, "multiple command options");
      }
      pAr->eCmd = eSwitch;
      break;

    case AR_SWITCH_DRYRUN:
      pAr->bDryRun = 1;
      break;
    case AR_SWITCH_GLOB:
      pAr->bGlob = 1;
      break;
    case AR_SWITCH_VERBOSE:
      pAr->bVerbose = 1;
      break;
    case AR_SWITCH_APPEND:
      pAr->bAppend = 1;
      /* Fall thru into --file */
17279
17280
17281
17282
17283
17284
17285

17286
17287
17288
17289
17290
17291
17292

17293
17294
17295
17296
17297
17298
17299
    u8 eSwitch;
    u8 bArg;
  } aSwitch[] = {
    { "create",    'c', AR_CMD_CREATE,       0 },
    { "extract",   'x', AR_CMD_EXTRACT,      0 },
    { "insert",    'i', AR_CMD_INSERT,       0 },
    { "list",      't', AR_CMD_LIST,         0 },

    { "update",    'u', AR_CMD_UPDATE,       0 },
    { "help",      'h', AR_CMD_HELP,         0 },
    { "verbose",   'v', AR_SWITCH_VERBOSE,   0 },
    { "file",      'f', AR_SWITCH_FILE,      1 },
    { "append",    'a', AR_SWITCH_APPEND,    1 },
    { "directory", 'C', AR_SWITCH_DIRECTORY, 1 },
    { "dryrun",    'n', AR_SWITCH_DRYRUN,    0 },

  };
  int nSwitch = sizeof(aSwitch) / sizeof(struct ArSwitch);
  struct ArSwitch *pEnd = &aSwitch[nSwitch];

  if( nArg<=1 ){
    utf8_printf(stderr, "Wrong number of arguments.  Usage:\n");
    return arUsage(stderr);







>







>







17323
17324
17325
17326
17327
17328
17329
17330
17331
17332
17333
17334
17335
17336
17337
17338
17339
17340
17341
17342
17343
17344
17345
    u8 eSwitch;
    u8 bArg;
  } aSwitch[] = {
    { "create",    'c', AR_CMD_CREATE,       0 },
    { "extract",   'x', AR_CMD_EXTRACT,      0 },
    { "insert",    'i', AR_CMD_INSERT,       0 },
    { "list",      't', AR_CMD_LIST,         0 },
    { "remove",    'r', AR_CMD_REMOVE,       0 },
    { "update",    'u', AR_CMD_UPDATE,       0 },
    { "help",      'h', AR_CMD_HELP,         0 },
    { "verbose",   'v', AR_SWITCH_VERBOSE,   0 },
    { "file",      'f', AR_SWITCH_FILE,      1 },
    { "append",    'a', AR_SWITCH_APPEND,    1 },
    { "directory", 'C', AR_SWITCH_DIRECTORY, 1 },
    { "dryrun",    'n', AR_SWITCH_DRYRUN,    0 },
    { "glob",      'g', AR_SWITCH_GLOB,      0 },
  };
  int nSwitch = sizeof(aSwitch) / sizeof(struct ArSwitch);
  struct ArSwitch *pEnd = &aSwitch[nSwitch];

  if( nArg<=1 ){
    utf8_printf(stderr, "Wrong number of arguments.  Usage:\n");
    return arUsage(stderr);
17402
17403
17404
17405
17406
17407
17408
17409
17410
17411
17412
17413


17414
17415
17416
17417
17418
17419
17420
17421
17422
17423



17424
17425
17426
17427
17428
17429
17430
17431
17432
17433
17434
17435
  }

  return SQLITE_OK;
}

/*
** This function assumes that all arguments within the ArCommand.azArg[]
** array refer to archive members, as for the --extract or --list commands. 
** It checks that each of them are present. If any specified file is not
** present in the archive, an error is printed to stderr and an error
** code returned. Otherwise, if all specified arguments are present in
** the archive, SQLITE_OK is returned.


**
** This function strips any trailing '/' characters from each argument.
** This is consistent with the way the [tar] command seems to work on
** Linux.
*/
static int arCheckEntries(ArCommand *pAr){
  int rc = SQLITE_OK;
  if( pAr->nArg ){
    int i, j;
    sqlite3_stmt *pTest = 0;




    shellPreparePrintf(pAr->db, &rc, &pTest,
        "SELECT name FROM %s WHERE name=$name", 
        pAr->zSrcTable
    );
    j = sqlite3_bind_parameter_index(pTest, "$name");
    for(i=0; i<pAr->nArg && rc==SQLITE_OK; i++){
      char *z = pAr->azArg[i];
      int n = strlen30(z);
      int bOk = 0;
      while( n>0 && z[n-1]=='/' ) n--;
      z[n] = '\0';







|
|
|
|
|
>
>










>
>
>

|
<
<
<







17448
17449
17450
17451
17452
17453
17454
17455
17456
17457
17458
17459
17460
17461
17462
17463
17464
17465
17466
17467
17468
17469
17470
17471
17472
17473
17474
17475
17476



17477
17478
17479
17480
17481
17482
17483
  }

  return SQLITE_OK;
}

/*
** This function assumes that all arguments within the ArCommand.azArg[]
** array refer to archive members, as for the --extract, --list or --remove
** commands. It checks that each of them are "present". If any specified
** file is not present in the archive, an error is printed to stderr and an
** error code returned. Otherwise, if all specified arguments are present
** in the archive, SQLITE_OK is returned. Here, "present" means either an
** exact equality when pAr->bGlob is false or a "name GLOB pattern" match
** when pAr->bGlob is true.
**
** This function strips any trailing '/' characters from each argument.
** This is consistent with the way the [tar] command seems to work on
** Linux.
*/
static int arCheckEntries(ArCommand *pAr){
  int rc = SQLITE_OK;
  if( pAr->nArg ){
    int i, j;
    sqlite3_stmt *pTest = 0;
    const char *zSel = (pAr->bGlob)
      ? "SELECT name FROM %s WHERE glob($name,name)"
      : "SELECT name FROM %s WHERE name=$name";

    shellPreparePrintf(pAr->db, &rc, &pTest, zSel, pAr->zSrcTable);



    j = sqlite3_bind_parameter_index(pTest, "$name");
    for(i=0; i<pAr->nArg && rc==SQLITE_OK; i++){
      char *z = pAr->azArg[i];
      int n = strlen30(z);
      int bOk = 0;
      while( n>0 && z[n-1]=='/' ) n--;
      z[n] = '\0';
17449
17450
17451
17452
17453
17454
17455
17456

17457
17458
17459
17460
17461
17462
17463

17464
17465
17466
17467
17468
17469
17470
17471
17472
17473
17474
17475
17476
17477
17478
17479
17480
17481
}

/*
** Format a WHERE clause that can be used against the "sqlar" table to
** identify all archive members that match the command arguments held
** in (*pAr). Leave this WHERE clause in (*pzWhere) before returning.
** The caller is responsible for eventually calling sqlite3_free() on
** any non-NULL (*pzWhere) value.

*/
static void arWhereClause(
  int *pRc, 
  ArCommand *pAr, 
  char **pzWhere                  /* OUT: New WHERE clause */
){
  char *zWhere = 0;

  if( *pRc==SQLITE_OK ){
    if( pAr->nArg==0 ){
      zWhere = sqlite3_mprintf("1");
    }else{
      int i;
      const char *zSep = "";
      for(i=0; i<pAr->nArg; i++){
        const char *z = pAr->azArg[i];
        zWhere = sqlite3_mprintf(
          "%z%s name = '%q' OR substr(name,1,%d) = '%q/'", 
          zWhere, zSep, z, strlen30(z)+1, z
        );
        if( zWhere==0 ){
          *pRc = SQLITE_NOMEM;
          break;
        }
        zSep = " OR ";
      }







|
>



|



>









|
|







17497
17498
17499
17500
17501
17502
17503
17504
17505
17506
17507
17508
17509
17510
17511
17512
17513
17514
17515
17516
17517
17518
17519
17520
17521
17522
17523
17524
17525
17526
17527
17528
17529
17530
17531
}

/*
** Format a WHERE clause that can be used against the "sqlar" table to
** identify all archive members that match the command arguments held
** in (*pAr). Leave this WHERE clause in (*pzWhere) before returning.
** The caller is responsible for eventually calling sqlite3_free() on
** any non-NULL (*pzWhere) value. Here, "match" means strict equality
** when pAr->bGlob is false and GLOB match when pAr->bGlob is true.
*/
static void arWhereClause(
  int *pRc, 
  ArCommand *pAr,
  char **pzWhere                  /* OUT: New WHERE clause */
){
  char *zWhere = 0;
  const char *zSameOp = (pAr->bGlob)? "GLOB" : "=";
  if( *pRc==SQLITE_OK ){
    if( pAr->nArg==0 ){
      zWhere = sqlite3_mprintf("1");
    }else{
      int i;
      const char *zSep = "";
      for(i=0; i<pAr->nArg; i++){
        const char *z = pAr->azArg[i];
        zWhere = sqlite3_mprintf(
          "%z%s name %s '%q' OR substr(name,1,%d) %s '%q/'", 
          zWhere, zSep, zSameOp, z, strlen30(z)+1, zSameOp, z
        );
        if( zWhere==0 ){
          *pRc = SQLITE_NOMEM;
          break;
        }
        zSep = " OR ";
      }
17520
17521
17522
17523
17524
17525
17526









































17527
17528
17529
17530
17531
17532
17533
    }
  }
  shellFinalize(&rc, pSql);
  sqlite3_free(zWhere);
  return rc;
}











































/*
** Implementation of .ar "eXtract" command. 
*/
static int arExtractCommand(ArCommand *pAr){
  const char *zSql1 = 
    "SELECT "







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







17570
17571
17572
17573
17574
17575
17576
17577
17578
17579
17580
17581
17582
17583
17584
17585
17586
17587
17588
17589
17590
17591
17592
17593
17594
17595
17596
17597
17598
17599
17600
17601
17602
17603
17604
17605
17606
17607
17608
17609
17610
17611
17612
17613
17614
17615
17616
17617
17618
17619
17620
17621
17622
17623
17624
    }
  }
  shellFinalize(&rc, pSql);
  sqlite3_free(zWhere);
  return rc;
}


/*
** Implementation of .ar "Remove" command.
*/
static int arRemoveCommand(ArCommand *pAr){
  int rc = 0;
  char *zSql = 0;
  char *zWhere = 0;

  if( pAr->nArg ){
    /* Verify that args actually exist within the archive before proceeding.
    ** And formulate a WHERE clause to match them.  */
    rc = arCheckEntries(pAr);
    arWhereClause(&rc, pAr, &zWhere);
  }
  if( rc==SQLITE_OK ){
    zSql = sqlite3_mprintf("DELETE FROM %s WHERE %s;",
                           pAr->zSrcTable, zWhere);
    if( pAr->bDryRun ){
      utf8_printf(pAr->p->out, "%s\n", zSql);
    }else{
      char *zErr = 0;
      rc = sqlite3_exec(pAr->db, "SAVEPOINT ar;", 0, 0, 0);
      if( rc==SQLITE_OK ){
        rc = sqlite3_exec(pAr->db, zSql, 0, 0, &zErr);
        if( rc!=SQLITE_OK ){
          sqlite3_exec(pAr->db, "ROLLBACK TO ar; RELEASE ar;", 0, 0, 0);
        }else{
          rc = sqlite3_exec(pAr->db, "RELEASE ar;", 0, 0, 0);
        }
      }
      if( zErr ){
        utf8_printf(stdout, "ERROR: %s\n", zErr);
        sqlite3_free(zErr);
      }
    }
  }
  sqlite3_free(zWhere);
  sqlite3_free(zSql);
  return rc;
}

/*
** Implementation of .ar "eXtract" command. 
*/
static int arExtractCommand(ArCommand *pAr){
  const char *zSql1 = 
    "SELECT "
17773
17774
17775
17776
17777
17778
17779
17780
17781
17782
17783
17784
17785
17786
17787
        }
      }
      cmd.bZip = 1;
    }else if( cmd.zFile ){
      int flags;
      if( cmd.bAppend ) eDbType = SHELL_OPEN_APPENDVFS;
      if( cmd.eCmd==AR_CMD_CREATE || cmd.eCmd==AR_CMD_INSERT 
           || cmd.eCmd==AR_CMD_UPDATE ){
        flags = SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE;
      }else{
        flags = SQLITE_OPEN_READONLY;
      }
      cmd.db = 0;
      if( cmd.bDryRun ){
        utf8_printf(pState->out, "-- open database '%s'%s\n", cmd.zFile,







|







17864
17865
17866
17867
17868
17869
17870
17871
17872
17873
17874
17875
17876
17877
17878
        }
      }
      cmd.bZip = 1;
    }else if( cmd.zFile ){
      int flags;
      if( cmd.bAppend ) eDbType = SHELL_OPEN_APPENDVFS;
      if( cmd.eCmd==AR_CMD_CREATE || cmd.eCmd==AR_CMD_INSERT 
           || cmd.eCmd==AR_CMD_REMOVE || cmd.eCmd==AR_CMD_UPDATE ){
        flags = SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE;
      }else{
        flags = SQLITE_OPEN_READONLY;
      }
      cmd.db = 0;
      if( cmd.bDryRun ){
        utf8_printf(pState->out, "-- open database '%s'%s\n", cmd.zFile,
17828
17829
17830
17831
17832
17833
17834




17835
17836
17837
17838
17839
17840
17841
      case AR_CMD_HELP:
        arUsage(pState->out);
        break;

      case AR_CMD_INSERT:
        rc = arCreateOrUpdateCommand(&cmd, 1, 0);
        break;





      default:
        assert( cmd.eCmd==AR_CMD_UPDATE );
        rc = arCreateOrUpdateCommand(&cmd, 1, 1);
        break;
    }
  }







>
>
>
>







17919
17920
17921
17922
17923
17924
17925
17926
17927
17928
17929
17930
17931
17932
17933
17934
17935
17936
      case AR_CMD_HELP:
        arUsage(pState->out);
        break;

      case AR_CMD_INSERT:
        rc = arCreateOrUpdateCommand(&cmd, 1, 0);
        break;

      case AR_CMD_REMOVE:
        rc = arRemoveCommand(&cmd);
        break;

      default:
        assert( cmd.eCmd==AR_CMD_UPDATE );
        rc = arCreateOrUpdateCommand(&cmd, 1, 1);
        break;
    }
  }
19317
19318
19319
19320
19321
19322
19323





19324
19325
19326
19327
19328
19329
19330
    char *(SQLITE_CDECL *xRead)(ImportCtx*); /* Func to read one value */
    int eVerbose = 0;           /* Larger for more console output */
    int nSkip = 0;              /* Initial lines to skip */
    int useOutputMode = 1;      /* Use output mode to determine separators */

    failIfSafeMode(p, "cannot run .import in safe mode");
    memset(&sCtx, 0, sizeof(sCtx));





    if( p->mode==MODE_Ascii ){
      xRead = ascii_read_one_field;
    }else{
      xRead = csv_read_one_field;
    }
    for(i=1; i<nArg; i++){
      char *z = azArg[i];







>
>
>
>
>







19412
19413
19414
19415
19416
19417
19418
19419
19420
19421
19422
19423
19424
19425
19426
19427
19428
19429
19430
    char *(SQLITE_CDECL *xRead)(ImportCtx*); /* Func to read one value */
    int eVerbose = 0;           /* Larger for more console output */
    int nSkip = 0;              /* Initial lines to skip */
    int useOutputMode = 1;      /* Use output mode to determine separators */

    failIfSafeMode(p, "cannot run .import in safe mode");
    memset(&sCtx, 0, sizeof(sCtx));
    sCtx.z = sqlite3_malloc64(120);
    if( sCtx.z==0 ){
      import_cleanup(&sCtx);
      shell_out_of_memory();
    }
    if( p->mode==MODE_Ascii ){
      xRead = ascii_read_one_field;
    }else{
      xRead = csv_read_one_field;
    }
    for(i=1; i<nArg; i++){
      char *z = azArg[i];
19426
19427
19428
19429
19430
19431
19432

19433
19434
19435
19436
19437
19438
19439
    }else{
      sCtx.in = fopen(sCtx.zFile, "rb");
      sCtx.xCloser = fclose;
    }
    if( sCtx.in==0 ){
      utf8_printf(stderr, "Error: cannot open \"%s\"\n", zFile);
      rc = 1;

      goto meta_command_exit;
    }
    if( eVerbose>=2 || (eVerbose>=1 && useOutputMode) ){
      char zSep[2];
      zSep[1] = 0;
      zSep[0] = sCtx.cColSep;
      utf8_printf(p->out, "Column separator ");







>







19526
19527
19528
19529
19530
19531
19532
19533
19534
19535
19536
19537
19538
19539
19540
    }else{
      sCtx.in = fopen(sCtx.zFile, "rb");
      sCtx.xCloser = fclose;
    }
    if( sCtx.in==0 ){
      utf8_printf(stderr, "Error: cannot open \"%s\"\n", zFile);
      rc = 1;
      import_cleanup(&sCtx);
      goto meta_command_exit;
    }
    if( eVerbose>=2 || (eVerbose>=1 && useOutputMode) ){
      char zSep[2];
      zSep[1] = 0;
      zSep[0] = sCtx.cColSep;
      utf8_printf(p->out, "Column separator ");
19844
19845
19846
19847
19848
19849
19850




19851
19852
19853
19854
19855
19856
19857
      sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator, SEP_Record);
    }else if( c2=='m' && strncmp(azArg[1],"markdown",n2)==0 ){
      p->mode = MODE_Markdown;
    }else if( c2=='t' && strncmp(azArg[1],"table",n2)==0 ){
      p->mode = MODE_Table;
    }else if( c2=='b' && strncmp(azArg[1],"box",n2)==0 ){
      p->mode = MODE_Box;




    }else if( c2=='j' && strncmp(azArg[1],"json",n2)==0 ){
      p->mode = MODE_Json;
    }else if( nArg==1 ){
      raw_printf(p->out, "current output mode: %s\n", modeDescr[p->mode]);
    }else{
      raw_printf(stderr, "Error: mode should be one of: "
         "ascii box column csv html insert json line list markdown "







>
>
>
>







19945
19946
19947
19948
19949
19950
19951
19952
19953
19954
19955
19956
19957
19958
19959
19960
19961
19962
      sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator, SEP_Record);
    }else if( c2=='m' && strncmp(azArg[1],"markdown",n2)==0 ){
      p->mode = MODE_Markdown;
    }else if( c2=='t' && strncmp(azArg[1],"table",n2)==0 ){
      p->mode = MODE_Table;
    }else if( c2=='b' && strncmp(azArg[1],"box",n2)==0 ){
      p->mode = MODE_Box;
    }else if( c2=='c' && strncmp(azArg[1],"count",n2)==0 ){
      p->mode = MODE_Count;
    }else if( c2=='o' && strncmp(azArg[1],"off",n2)==0 ){
      p->mode = MODE_Off;
    }else if( c2=='j' && strncmp(azArg[1],"json",n2)==0 ){
      p->mode = MODE_Json;
    }else if( nArg==1 ){
      raw_printf(p->out, "current output mode: %s\n", modeDescr[p->mode]);
    }else{
      raw_printf(stderr, "Error: mode should be one of: "
         "ascii box column csv html insert json line list markdown "
19913
19914
19915
19916
19917
19918
19919
19920
19921
19922
19923
19924
19925
19926
19927
19928
19929
19930
19931
19932
19933
19934
19935
19936
19937
19938
19939
19940
19941
19942
19943
19944
19945
19946
19947
19948
19949
19950
19951
19952
19953
19954
19955
19956
19957
19958
19959
19960
19961
19962
19963
19964
19965
19966












19967
19968
19969
19970
19971
19972
19973
  }else
#endif /* SQLITE_DEBUG */

  if( c=='o' && strncmp(azArg[0], "open", n)==0 && n>=2 ){
    char *zNewFilename = 0;  /* Name of the database file to open */
    int iName = 1;           /* Index in azArg[] of the filename */
    int newFlag = 0;         /* True to delete file before opening */
    /* Close the existing database */
    session_close_all(p, -1);
    close_db(p->db);
    p->db = 0;
    p->pAuxDb->zDbFilename = 0;
    sqlite3_free(p->pAuxDb->zFreeOnClose);
    p->pAuxDb->zFreeOnClose = 0;
    p->openMode = SHELL_OPEN_UNSPEC;
    p->openFlags = 0;
    p->szMax = 0;
    /* Check for command-line arguments */
    for(iName=1; iName<nArg; iName++){
      const char *z = azArg[iName];
      if( optionMatch(z,"new") ){
        newFlag = 1;
#ifdef SQLITE_HAVE_ZLIB
      }else if( optionMatch(z, "zip") ){
        p->openMode = SHELL_OPEN_ZIPFILE;
#endif
      }else if( optionMatch(z, "append") ){
        p->openMode = SHELL_OPEN_APPENDVFS;
      }else if( optionMatch(z, "readonly") ){
        p->openMode = SHELL_OPEN_READONLY;
      }else if( optionMatch(z, "nofollow") ){
        p->openFlags |= SQLITE_OPEN_NOFOLLOW;
      }else if( optionMatch(z, "excl") ){
        p->openFlags |= SQLITE_OPEN_EXCLUSIVE;
#ifndef SQLITE_OMIT_DESERIALIZE
      }else if( optionMatch(z, "deserialize") ){
        p->openMode = SHELL_OPEN_DESERIALIZE;
      }else if( optionMatch(z, "hexdb") ){
        p->openMode = SHELL_OPEN_HEXDB;
      }else if( optionMatch(z, "maxsize") && iName+1<nArg ){
        p->szMax = integerValue(azArg[++iName]);
#endif /* SQLITE_OMIT_DESERIALIZE */
      }else if( z[0]=='-' ){
        utf8_printf(stderr, "unknown option: %s\n", z);
        rc = 1;
        goto meta_command_exit;
      }else if( zNewFilename ){
        utf8_printf(stderr, "extra argument: \"%s\"\n", z);
        rc = 1;
        goto meta_command_exit;
      }else{
        zNewFilename = sqlite3_mprintf("%s", z);
      }
    }












    /* If a filename is specified, try to open it first */
    if( zNewFilename || p->openMode==SHELL_OPEN_HEXDB ){
      if( newFlag && !p->bSafeMode ) shellDeleteFile(zNewFilename);
      if( p->bSafeMode
       && p->openMode!=SHELL_OPEN_HEXDB
       && zNewFilename
       && strcmp(zNewFilename,":memory:")!=0







<
<
<
<
<
<
<
|
|
<







|


|

|


<
<


|

|















>
>
>
>
>
>
>
>
>
>
>
>







20018
20019
20020
20021
20022
20023
20024







20025
20026

20027
20028
20029
20030
20031
20032
20033
20034
20035
20036
20037
20038
20039
20040
20041


20042
20043
20044
20045
20046
20047
20048
20049
20050
20051
20052
20053
20054
20055
20056
20057
20058
20059
20060
20061
20062
20063
20064
20065
20066
20067
20068
20069
20070
20071
20072
20073
20074
20075
20076
20077
20078
20079
20080
  }else
#endif /* SQLITE_DEBUG */

  if( c=='o' && strncmp(azArg[0], "open", n)==0 && n>=2 ){
    char *zNewFilename = 0;  /* Name of the database file to open */
    int iName = 1;           /* Index in azArg[] of the filename */
    int newFlag = 0;         /* True to delete file before opening */







    int openMode = SHELL_OPEN_UNSPEC;


    /* Check for command-line arguments */
    for(iName=1; iName<nArg; iName++){
      const char *z = azArg[iName];
      if( optionMatch(z,"new") ){
        newFlag = 1;
#ifdef SQLITE_HAVE_ZLIB
      }else if( optionMatch(z, "zip") ){
        openMode = SHELL_OPEN_ZIPFILE;
#endif
      }else if( optionMatch(z, "append") ){
        openMode = SHELL_OPEN_APPENDVFS;
      }else if( optionMatch(z, "readonly") ){
        openMode = SHELL_OPEN_READONLY;
      }else if( optionMatch(z, "nofollow") ){
        p->openFlags |= SQLITE_OPEN_NOFOLLOW;


#ifndef SQLITE_OMIT_DESERIALIZE
      }else if( optionMatch(z, "deserialize") ){
        openMode = SHELL_OPEN_DESERIALIZE;
      }else if( optionMatch(z, "hexdb") ){
        openMode = SHELL_OPEN_HEXDB;
      }else if( optionMatch(z, "maxsize") && iName+1<nArg ){
        p->szMax = integerValue(azArg[++iName]);
#endif /* SQLITE_OMIT_DESERIALIZE */
      }else if( z[0]=='-' ){
        utf8_printf(stderr, "unknown option: %s\n", z);
        rc = 1;
        goto meta_command_exit;
      }else if( zNewFilename ){
        utf8_printf(stderr, "extra argument: \"%s\"\n", z);
        rc = 1;
        goto meta_command_exit;
      }else{
        zNewFilename = sqlite3_mprintf("%s", z);
      }
    }

    /* Close the existing database */
    session_close_all(p, -1);
    close_db(p->db);
    p->db = 0;
    p->pAuxDb->zDbFilename = 0;
    sqlite3_free(p->pAuxDb->zFreeOnClose);
    p->pAuxDb->zFreeOnClose = 0;
    p->openMode = openMode;
    p->openFlags = 0;
    p->szMax = 0;

    /* If a filename is specified, try to open it first */
    if( zNewFilename || p->openMode==SHELL_OPEN_HEXDB ){
      if( newFlag && !p->bSafeMode ) shellDeleteFile(zNewFilename);
      if( p->bSafeMode
       && p->openMode!=SHELL_OPEN_HEXDB
       && zNewFilename
       && strcmp(zNewFilename,":memory:")!=0
21178
21179
21180
21181
21182
21183
21184

21185
21186
21187
21188
21189
21190
21191
21192
21193
21194
21195
21196
21197
21198
21199
21200
21201
21202
21203
21204
21205
21206
21207
21208
21209
21210
21211
21212
21213
21214
21215
  }else

#ifndef SQLITE_UNTESTABLE
  if( c=='t' && n>=8 && strncmp(azArg[0], "testctrl", n)==0 ){
    static const struct {
       const char *zCtrlName;   /* Name of a test-control option */
       int ctrlCode;            /* Integer code for that option */

       const char *zUsage;      /* Usage notes */
    } aCtrl[] = {
      { "always",             SQLITE_TESTCTRL_ALWAYS,        "BOOLEAN"        },
      { "assert",             SQLITE_TESTCTRL_ASSERT,        "BOOLEAN"        },
    /*{ "benign_malloc_hooks",SQLITE_TESTCTRL_BENIGN_MALLOC_HOOKS, ""       },*/
    /*{ "bitvec_test",        SQLITE_TESTCTRL_BITVEC_TEST,   ""             },*/
      { "byteorder",          SQLITE_TESTCTRL_BYTEORDER,     ""               },
      { "extra_schema_checks",SQLITE_TESTCTRL_EXTRA_SCHEMA_CHECKS,"BOOLEAN"   },
    /*{ "fault_install",      SQLITE_TESTCTRL_FAULT_INSTALL, ""             },*/
      { "imposter",         SQLITE_TESTCTRL_IMPOSTER, "SCHEMA ON/OFF ROOTPAGE"},
      { "internal_functions", SQLITE_TESTCTRL_INTERNAL_FUNCTIONS, "" },
      { "localtime_fault",    SQLITE_TESTCTRL_LOCALTIME_FAULT,"BOOLEAN"       },
      { "never_corrupt",      SQLITE_TESTCTRL_NEVER_CORRUPT, "BOOLEAN"        },
      { "optimizations",      SQLITE_TESTCTRL_OPTIMIZATIONS, "DISABLE-MASK"   },
#ifdef YYCOVERAGE
      { "parser_coverage",    SQLITE_TESTCTRL_PARSER_COVERAGE, ""             },
#endif
      { "pending_byte",       SQLITE_TESTCTRL_PENDING_BYTE,  "OFFSET  "       },
      { "prng_restore",       SQLITE_TESTCTRL_PRNG_RESTORE,  ""               },
      { "prng_save",          SQLITE_TESTCTRL_PRNG_SAVE,     ""               },
      { "prng_seed",          SQLITE_TESTCTRL_PRNG_SEED,     "SEED ?db?"      },
      { "seek_count",         SQLITE_TESTCTRL_SEEK_COUNT,    ""               },
      { "sorter_mmap",        SQLITE_TESTCTRL_SORTER_MMAP,   "NMAX"           },
      { "tune",               SQLITE_TESTCTRL_TUNE,          "ID VALUE"       },
    };
    int testctrl = -1;
    int iCtrl = -1;
    int rc2 = 0;    /* 0: usage.  1: %d  2: %x  3: no-output */
    int isOk = 0;
    int i, n2;
    const char *zCmd = 0;







>


|
|
|
|
|
|
|
|
|
|
|
|

|

|
|
|
|
|
|
|







21285
21286
21287
21288
21289
21290
21291
21292
21293
21294
21295
21296
21297
21298
21299
21300
21301
21302
21303
21304
21305
21306
21307
21308
21309
21310
21311
21312
21313
21314
21315
21316
21317
21318
21319
21320
21321
21322
21323
  }else

#ifndef SQLITE_UNTESTABLE
  if( c=='t' && n>=8 && strncmp(azArg[0], "testctrl", n)==0 ){
    static const struct {
       const char *zCtrlName;   /* Name of a test-control option */
       int ctrlCode;            /* Integer code for that option */
       int unSafe;              /* Not valid for --safe mode */
       const char *zUsage;      /* Usage notes */
    } aCtrl[] = {
      { "always",             SQLITE_TESTCTRL_ALWAYS, 1,     "BOOLEAN"         },
      { "assert",             SQLITE_TESTCTRL_ASSERT, 1,     "BOOLEAN"         },
    /*{ "benign_malloc_hooks",SQLITE_TESTCTRL_BENIGN_MALLOC_HOOKS,1, ""        },*/
    /*{ "bitvec_test",        SQLITE_TESTCTRL_BITVEC_TEST, 1,  ""              },*/
      { "byteorder",          SQLITE_TESTCTRL_BYTEORDER, 0,  ""                },
      { "extra_schema_checks",SQLITE_TESTCTRL_EXTRA_SCHEMA_CHECKS,0,"BOOLEAN"  },
    /*{ "fault_install",      SQLITE_TESTCTRL_FAULT_INSTALL, 1,""              },*/
      { "imposter",         SQLITE_TESTCTRL_IMPOSTER,1,"SCHEMA ON/OFF ROOTPAGE"},
      { "internal_functions", SQLITE_TESTCTRL_INTERNAL_FUNCTIONS,0,""          },
      { "localtime_fault",    SQLITE_TESTCTRL_LOCALTIME_FAULT,0,"BOOLEAN"      },
      { "never_corrupt",      SQLITE_TESTCTRL_NEVER_CORRUPT,1, "BOOLEAN"       },
      { "optimizations",      SQLITE_TESTCTRL_OPTIMIZATIONS,0,"DISABLE-MASK"   },
#ifdef YYCOVERAGE
      { "parser_coverage",    SQLITE_TESTCTRL_PARSER_COVERAGE,0,""             },
#endif
      { "pending_byte",       SQLITE_TESTCTRL_PENDING_BYTE,0, "OFFSET  "       },
      { "prng_restore",       SQLITE_TESTCTRL_PRNG_RESTORE,0, ""               },
      { "prng_save",          SQLITE_TESTCTRL_PRNG_SAVE,   0, ""               },
      { "prng_seed",          SQLITE_TESTCTRL_PRNG_SEED,   0, "SEED ?db?"      },
      { "seek_count",         SQLITE_TESTCTRL_SEEK_COUNT,  0, ""               },
      { "sorter_mmap",        SQLITE_TESTCTRL_SORTER_MMAP, 0, "NMAX"           },
      { "tune",               SQLITE_TESTCTRL_TUNE,        1, "ID VALUE"       },
    };
    int testctrl = -1;
    int iCtrl = -1;
    int rc2 = 0;    /* 0: usage.  1: %d  2: %x  3: no-output */
    int isOk = 0;
    int i, n2;
    const char *zCmd = 0;
21249
21250
21251
21252
21253
21254
21255





21256
21257
21258
21259
21260
21261
21262
          goto meta_command_exit;
        }
      }
    }
    if( testctrl<0 ){
      utf8_printf(stderr,"Error: unknown test-control: %s\n"
                         "Use \".testctrl --help\" for help\n", zCmd);





    }else{
      switch(testctrl){

        /* sqlite3_test_control(int, db, int) */
        case SQLITE_TESTCTRL_OPTIMIZATIONS:
          if( nArg==3 ){
            unsigned int opt = (unsigned int)strtol(azArg[2], 0, 0);







>
>
>
>
>







21357
21358
21359
21360
21361
21362
21363
21364
21365
21366
21367
21368
21369
21370
21371
21372
21373
21374
21375
          goto meta_command_exit;
        }
      }
    }
    if( testctrl<0 ){
      utf8_printf(stderr,"Error: unknown test-control: %s\n"
                         "Use \".testctrl --help\" for help\n", zCmd);
    }else if( aCtrl[iCtrl].unSafe && p->bSafeMode ){
      utf8_printf(stderr,
         "line %d: \".testctrl %s\" may not be used in safe mode\n",
         p->lineno, aCtrl[iCtrl].zCtrlName);
      exit(1);
    }else{
      switch(testctrl){

        /* sqlite3_test_control(int, db, int) */
        case SQLITE_TESTCTRL_OPTIMIZATIONS:
          if( nArg==3 ){
            unsigned int opt = (unsigned int)strtol(azArg[2], 0, 0);
Changes to src/shun.c.
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
    login_needed(0);
    return;
  }
  if( P("rebuild") ){
    db_close(1);
    db_open_repository(g.zRepositoryName);
    db_begin_transaction();
    rebuild_db(0, 0, 0);
    admin_log("Rebuilt database.");
    db_end_transaction(0);
  }
  if( zUuid ){
    char *p;
    int i = 0;
    int j = 0;







|







58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
    login_needed(0);
    return;
  }
  if( P("rebuild") ){
    db_close(1);
    db_open_repository(g.zRepositoryName);
    db_begin_transaction();
    rebuild_db(0, 0);
    admin_log("Rebuilt database.");
    db_end_transaction(0);
  }
  if( zUuid ){
    char *p;
    int i = 0;
    int j = 0;
Changes to src/sqlite3.c.
1
2
3
4
5
6
7
8
9
10
/******************************************************************************
** This file is an amalgamation of many separate C source files from SQLite
** version 3.37.0.  By combining all the individual C code files into this
** single large file, the entire code can be compiled as a single translation
** unit.  This allows many compilers to do optimizations that would not be
** possible if the files were compiled separately.  Performance improvements
** of 5% or more are commonly seen when SQLite is compiled as a single
** translation unit.
**
** This file is all you need to compile SQLite.  To use SQLite in other


|







1
2
3
4
5
6
7
8
9
10
/******************************************************************************
** This file is an amalgamation of many separate C source files from SQLite
** version 3.38.0.  By combining all the individual C code files into this
** single large file, the entire code can be compiled as a single translation
** unit.  This allows many compilers to do optimizations that would not be
** possible if the files were compiled separately.  Performance improvements
** of 5% or more are commonly seen when SQLite is compiled as a single
** translation unit.
**
** This file is all you need to compile SQLite.  To use SQLite in other
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
** been edited in any way since it was last checked in, then the last
** four hexadecimal digits of the hash may be modified.
**
** See also: [sqlite3_libversion()],
** [sqlite3_libversion_number()], [sqlite3_sourceid()],
** [sqlite_version()] and [sqlite_source_id()].
*/
#define SQLITE_VERSION        "3.37.0"
#define SQLITE_VERSION_NUMBER 3037000
#define SQLITE_SOURCE_ID      "2021-10-04 11:10:15 8b24c177061c38361588f419eda9b7943b72a0c6b2855b6f39272451b8a1b813"

/*
** CAPI3REF: Run-Time Library Version Numbers
** KEYWORDS: sqlite3_version sqlite3_sourceid
**
** These interfaces provide the same information as the [SQLITE_VERSION],
** [SQLITE_VERSION_NUMBER], and [SQLITE_SOURCE_ID] C preprocessor macros







|
|
|







448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
** been edited in any way since it was last checked in, then the last
** four hexadecimal digits of the hash may be modified.
**
** See also: [sqlite3_libversion()],
** [sqlite3_libversion_number()], [sqlite3_sourceid()],
** [sqlite_version()] and [sqlite_source_id()].
*/
#define SQLITE_VERSION        "3.38.0"
#define SQLITE_VERSION_NUMBER 3038000
#define SQLITE_SOURCE_ID      "2021-12-09 20:06:18 633bfeeea2bccdd44126acf3f61ecca163c9d933bdc787a2c18a697dc9406882"

/*
** CAPI3REF: Run-Time Library Version Numbers
** KEYWORDS: sqlite3_version sqlite3_sourceid
**
** These interfaces provide the same information as the [SQLITE_VERSION],
** [SQLITE_VERSION_NUMBER], and [SQLITE_SOURCE_ID] C preprocessor macros
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
#define SQLITE_BUSY_TIMEOUT            (SQLITE_BUSY   |  (3<<8))
#define SQLITE_CANTOPEN_NOTEMPDIR      (SQLITE_CANTOPEN | (1<<8))
#define SQLITE_CANTOPEN_ISDIR          (SQLITE_CANTOPEN | (2<<8))
#define SQLITE_CANTOPEN_FULLPATH       (SQLITE_CANTOPEN | (3<<8))
#define SQLITE_CANTOPEN_CONVPATH       (SQLITE_CANTOPEN | (4<<8))
#define SQLITE_CANTOPEN_DIRTYWAL       (SQLITE_CANTOPEN | (5<<8)) /* Not Used */
#define SQLITE_CANTOPEN_SYMLINK        (SQLITE_CANTOPEN | (6<<8))
#define SQLITE_CANTOPEN_EXISTS         (SQLITE_CANTOPEN | (7<<8))
#define SQLITE_CORRUPT_VTAB            (SQLITE_CORRUPT | (1<<8))
#define SQLITE_CORRUPT_SEQUENCE        (SQLITE_CORRUPT | (2<<8))
#define SQLITE_CORRUPT_INDEX           (SQLITE_CORRUPT | (3<<8))
#define SQLITE_READONLY_RECOVERY       (SQLITE_READONLY | (1<<8))
#define SQLITE_READONLY_CANTLOCK       (SQLITE_READONLY | (2<<8))
#define SQLITE_READONLY_ROLLBACK       (SQLITE_READONLY | (3<<8))
#define SQLITE_READONLY_DBMOVED        (SQLITE_READONLY | (4<<8))







<







841
842
843
844
845
846
847

848
849
850
851
852
853
854
#define SQLITE_BUSY_TIMEOUT            (SQLITE_BUSY   |  (3<<8))
#define SQLITE_CANTOPEN_NOTEMPDIR      (SQLITE_CANTOPEN | (1<<8))
#define SQLITE_CANTOPEN_ISDIR          (SQLITE_CANTOPEN | (2<<8))
#define SQLITE_CANTOPEN_FULLPATH       (SQLITE_CANTOPEN | (3<<8))
#define SQLITE_CANTOPEN_CONVPATH       (SQLITE_CANTOPEN | (4<<8))
#define SQLITE_CANTOPEN_DIRTYWAL       (SQLITE_CANTOPEN | (5<<8)) /* Not Used */
#define SQLITE_CANTOPEN_SYMLINK        (SQLITE_CANTOPEN | (6<<8))

#define SQLITE_CORRUPT_VTAB            (SQLITE_CORRUPT | (1<<8))
#define SQLITE_CORRUPT_SEQUENCE        (SQLITE_CORRUPT | (2<<8))
#define SQLITE_CORRUPT_INDEX           (SQLITE_CORRUPT | (3<<8))
#define SQLITE_READONLY_RECOVERY       (SQLITE_READONLY | (1<<8))
#define SQLITE_READONLY_CANTLOCK       (SQLITE_READONLY | (2<<8))
#define SQLITE_READONLY_ROLLBACK       (SQLITE_READONLY | (3<<8))
#define SQLITE_READONLY_DBMOVED        (SQLITE_READONLY | (4<<8))
877
878
879
880
881
882
883













884
885
886
887
888
889
890

/*
** CAPI3REF: Flags For File Open Operations
**
** These bit values are intended for use in the
** 3rd parameter to the [sqlite3_open_v2()] interface and
** in the 4th parameter to the [sqlite3_vfs.xOpen] method.













*/
#define SQLITE_OPEN_READONLY         0x00000001  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_READWRITE        0x00000002  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_CREATE           0x00000004  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_DELETEONCLOSE    0x00000008  /* VFS only */
#define SQLITE_OPEN_EXCLUSIVE        0x00000010  /* VFS only */
#define SQLITE_OPEN_AUTOPROXY        0x00000020  /* VFS only */







>
>
>
>
>
>
>
>
>
>
>
>
>







876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902

/*
** CAPI3REF: Flags For File Open Operations
**
** These bit values are intended for use in the
** 3rd parameter to the [sqlite3_open_v2()] interface and
** in the 4th parameter to the [sqlite3_vfs.xOpen] method.
**
** Only those flags marked as "Ok for sqlite3_open_v2()" may be
** used as the third argument to the [sqlite3_open_v2()] interface.
** The other flags have historically been ignored by sqlite3_open_v2(),
** though future versions of SQLite might change so that an error is
** raised if any of the disallowed bits are passed into sqlite3_open_v2().
** Applications should not depend on the historical behavior.
**
** Note in particular that passing the SQLITE_OPEN_EXCLUSIVE flag into
** [sqlite3_open_v2()] does *not* cause the underlying database file
** to be opened using O_EXCL.  Passing SQLITE_OPEN_EXCLUSIVE into
** [sqlite3_open_v2()] has historically be a no-op and might become an
** error in future versions of SQLite.
*/
#define SQLITE_OPEN_READONLY         0x00000001  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_READWRITE        0x00000002  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_CREATE           0x00000004  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_DELETEONCLOSE    0x00000008  /* VFS only */
#define SQLITE_OPEN_EXCLUSIVE        0x00000010  /* VFS only */
#define SQLITE_OPEN_AUTOPROXY        0x00000020  /* VFS only */
899
900
901
902
903
904
905

906
907
908
909
910
911
912
#define SQLITE_OPEN_SUPER_JOURNAL    0x00004000  /* VFS only */
#define SQLITE_OPEN_NOMUTEX          0x00008000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_FULLMUTEX        0x00010000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_SHAREDCACHE      0x00020000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_PRIVATECACHE     0x00040000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_WAL              0x00080000  /* VFS only */
#define SQLITE_OPEN_NOFOLLOW         0x01000000  /* Ok for sqlite3_open_v2() */


/* Reserved:                         0x00F00000 */
/* Legacy compatibility: */
#define SQLITE_OPEN_MASTER_JOURNAL   0x00004000  /* VFS only */


/*







>







911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
#define SQLITE_OPEN_SUPER_JOURNAL    0x00004000  /* VFS only */
#define SQLITE_OPEN_NOMUTEX          0x00008000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_FULLMUTEX        0x00010000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_SHAREDCACHE      0x00020000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_PRIVATECACHE     0x00040000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_WAL              0x00080000  /* VFS only */
#define SQLITE_OPEN_NOFOLLOW         0x01000000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_EXRESCODE        0x02000000  /* Extended result codes */

/* Reserved:                         0x00F00000 */
/* Legacy compatibility: */
#define SQLITE_OPEN_MASTER_JOURNAL   0x00004000  /* VFS only */


/*
3718
3719
3720
3721
3722
3723
3724








3725
3726
3727
3728
3729
3730
3731
3732
3733
3734
3735
3736
3737
3738
3739








3740
3741
3742
3743
3744
3745
3746
** the default shared cache setting provided by
** [sqlite3_enable_shared_cache()].)^
**
** ^(<dt>[SQLITE_OPEN_PRIVATECACHE]</dt>
** <dd>The database is opened [shared cache] disabled, overriding
** the default shared cache setting provided by
** [sqlite3_enable_shared_cache()].)^








**
** [[OPEN_NOFOLLOW]] ^(<dt>[SQLITE_OPEN_NOFOLLOW]</dt>
** <dd>The database filename is not allowed to be a symbolic link</dd>
**
** [[OPEN_EXCLUSIVE]] ^(<dt>[SQLITE_OPEN_EXCLUSIVE]</dt>
** <dd>This flag causes the open to fail if the database file already
** exists.  The open will only be success if this flag is used in combination
** with the SQLITE_OPEN_CREATE and SQLITE_OPEN_READWRITE flags and if
** the file does not previously exist.</dd>
** </dl>)^
**
** If the 3rd parameter to sqlite3_open_v2() is not one of the
** required combinations shown above optionally combined with other
** [SQLITE_OPEN_READONLY | SQLITE_OPEN_* bits]
** then the behavior is undefined.








**
** ^The fourth parameter to sqlite3_open_v2() is the name of the
** [sqlite3_vfs] object that defines the operating system interface that
** the new database connection should use.  ^If the fourth parameter is
** a NULL pointer then the default [sqlite3_vfs] object is used.
**
** ^If the filename is ":memory:", then a private, temporary in-memory database







>
>
>
>
>
>
>
>



<
<
<
<
<
<





|
>
>
>
>
>
>
>
>







3731
3732
3733
3734
3735
3736
3737
3738
3739
3740
3741
3742
3743
3744
3745
3746
3747
3748






3749
3750
3751
3752
3753
3754
3755
3756
3757
3758
3759
3760
3761
3762
3763
3764
3765
3766
3767
3768
3769
** the default shared cache setting provided by
** [sqlite3_enable_shared_cache()].)^
**
** ^(<dt>[SQLITE_OPEN_PRIVATECACHE]</dt>
** <dd>The database is opened [shared cache] disabled, overriding
** the default shared cache setting provided by
** [sqlite3_enable_shared_cache()].)^
**
** [[OPEN_EXRESCODE]] ^(<dt>[SQLITE_OPEN_EXRESCODE]</dt>
** <dd>The database connection comes up in "extended result code mode".
** In other words, the database behaves has if
** [sqlite3_extended_result_codes(db,1)] where called on the database
** connection as soon as the connection is created. In addition to setting
** the extended result code mode, this flag also causes [sqlite3_open_v2()]
** to return an extended result code.</dd>
**
** [[OPEN_NOFOLLOW]] ^(<dt>[SQLITE_OPEN_NOFOLLOW]</dt>
** <dd>The database filename is not allowed to be a symbolic link</dd>






** </dl>)^
**
** If the 3rd parameter to sqlite3_open_v2() is not one of the
** required combinations shown above optionally combined with other
** [SQLITE_OPEN_READONLY | SQLITE_OPEN_* bits]
** then the behavior is undefined.  Historic versions of SQLite
** have silently ignored surplus bits in the flags parameter to
** sqlite3_open_v2(), however that behavior might not be carried through
** into future versions of SQLite and so applications should not rely
** upon it.  Note in particular that the SQLITE_OPEN_EXCLUSIVE flag is a no-op
** for sqlite3_open_v2().  The SQLITE_OPEN_EXCLUSIVE does *not* cause
** the open to fail if the database already exists.  The SQLITE_OPEN_EXCLUSIVE
** flag is intended for use by the [sqlite3_vfs|VFS interface] only, and not
** by sqlite3_open_v2().
**
** ^The fourth parameter to sqlite3_open_v2() is the name of the
** [sqlite3_vfs] object that defines the operating system interface that
** the new database connection should use.  ^If the fourth parameter is
** a NULL pointer then the default [sqlite3_vfs] object is used.
**
** ^If the filename is ":memory:", then a private, temporary in-memory database
6693
6694
6695
6696
6697
6698
6699


































































6700
6701
6702
6703
6704
6705
6706
** ^The rollback callback is not invoked if a transaction is
** automatically rolled back because the database connection is closed.
**
** See also the [sqlite3_update_hook()] interface.
*/
SQLITE_API void *sqlite3_commit_hook(sqlite3*, int(*)(void*), void*);
SQLITE_API void *sqlite3_rollback_hook(sqlite3*, void(*)(void *), void*);



































































/*
** CAPI3REF: Data Change Notification Callbacks
** METHOD: sqlite3
**
** ^The sqlite3_update_hook() interface registers a callback function
** with the [database connection] identified by the first argument







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







6716
6717
6718
6719
6720
6721
6722
6723
6724
6725
6726
6727
6728
6729
6730
6731
6732
6733
6734
6735
6736
6737
6738
6739
6740
6741
6742
6743
6744
6745
6746
6747
6748
6749
6750
6751
6752
6753
6754
6755
6756
6757
6758
6759
6760
6761
6762
6763
6764
6765
6766
6767
6768
6769
6770
6771
6772
6773
6774
6775
6776
6777
6778
6779
6780
6781
6782
6783
6784
6785
6786
6787
6788
6789
6790
6791
6792
6793
6794
6795
** ^The rollback callback is not invoked if a transaction is
** automatically rolled back because the database connection is closed.
**
** See also the [sqlite3_update_hook()] interface.
*/
SQLITE_API void *sqlite3_commit_hook(sqlite3*, int(*)(void*), void*);
SQLITE_API void *sqlite3_rollback_hook(sqlite3*, void(*)(void *), void*);

/*
** CAPI3REF: Autovacuum Compaction Amount Callback
** METHOD: sqlite3
**
** ^The sqlite3_autovacuum_pages(D,C,P,X) interface registers a callback
** function C that is invoked prior to each autovacuum of the database
** file.  ^The callback is passed a copy of the generic data pointer (P),
** the schema-name of the attached database that is being autovacuumed,
** the the size of the database file in pages, the number of free pages,
** and the number of bytes per page, respectively.  The callback should
** return the number of free pages that should be removed by the
** autovacuum.  ^If the callback returns zero, then no autovacuum happens.
** ^If the value returned is greater than or equal to the number of
** free pages, then a complete autovacuum happens.
**
** <p>^If there are multiple ATTACH-ed database files that are being
** modified as part of a transaction commit, then the autovacuum pages
** callback is invoked separately for each file.
**
** <p><b>The callback is not reentrant.</b> The callback function should
** not attempt to invoke any other SQLite interface.  If it does, bad
** things may happen, including segmentation faults and corrupt database
** files.  The callback function should be a simple function that
** does some arithmetic on its input parameters and returns a result.
**
** ^The X parameter to sqlite3_autovacuum_pages(D,C,P,X) is an optional
** destructor for the P parameter.  ^If X is not NULL, then X(P) is
** invoked whenever the database connection closes or when the callback
** is overwritten by another invocation of sqlite3_autovacuum_pages().
**
** <p>^There is only one autovacuum pages callback per database connection.
** ^Each call to the sqlite3_autovacuum_pages() interface overrides all
** previous invocations for that database connection.  ^If the callback
** argument (C) to sqlite3_autovacuum_pages(D,C,P,X) is a NULL pointer,
** then the autovacuum steps callback is cancelled.  The return value
** from sqlite3_autovacuum_pages() is normally SQLITE_OK, but might
** be some other error code if something goes wrong.  The current
** implementation will only return SQLITE_OK or SQLITE_MISUSE, but other
** return codes might be added in future releases.
**
** <p>If no autovacuum pages callback is specified (the usual case) or
** a NULL pointer is provided for the callback,
** then the default behavior is to vacuum all free pages.  So, in other
** words, the default behavior is the same as if the callback function
** were something like this:
**
** <blockquote><pre>
** &nbsp;   unsigned int demonstration_autovac_pages_callback(
** &nbsp;     void *pClientData,
** &nbsp;     const char *zSchema,
** &nbsp;     unsigned int nDbPage,
** &nbsp;     unsigned int nFreePage,
** &nbsp;     unsigned int nBytePerPage
** &nbsp;   ){
** &nbsp;     return nFreePage;
** &nbsp;   }
** </pre></blockquote>
*/
SQLITE_API int sqlite3_autovacuum_pages(
  sqlite3 *db,
  unsigned int(*)(void*,const char*,unsigned int,unsigned int,unsigned int),
  void*,
  void(*)(void*)
);


/*
** CAPI3REF: Data Change Notification Callbacks
** METHOD: sqlite3
**
** ^The sqlite3_update_hook() interface registers a callback function
** with the [database connection] identified by the first argument
8157
8158
8159
8160
8161
8162
8163

8164
8165
8166
8167
8168
8169
8170
8171
#define SQLITE_TESTCTRL_PARSER_COVERAGE         26
#define SQLITE_TESTCTRL_RESULT_INTREAL          27
#define SQLITE_TESTCTRL_PRNG_SEED               28
#define SQLITE_TESTCTRL_EXTRA_SCHEMA_CHECKS     29
#define SQLITE_TESTCTRL_SEEK_COUNT              30
#define SQLITE_TESTCTRL_TRACEFLAGS              31
#define SQLITE_TESTCTRL_TUNE                    32

#define SQLITE_TESTCTRL_LAST                    32  /* Largest TESTCTRL */

/*
** CAPI3REF: SQL Keyword Checking
**
** These routines provide access to the set of SQL language keywords
** recognized by SQLite.  Applications can uses these routines to determine
** whether or not a specific identifier needs to be escaped (for example,







>
|







8246
8247
8248
8249
8250
8251
8252
8253
8254
8255
8256
8257
8258
8259
8260
8261
#define SQLITE_TESTCTRL_PARSER_COVERAGE         26
#define SQLITE_TESTCTRL_RESULT_INTREAL          27
#define SQLITE_TESTCTRL_PRNG_SEED               28
#define SQLITE_TESTCTRL_EXTRA_SCHEMA_CHECKS     29
#define SQLITE_TESTCTRL_SEEK_COUNT              30
#define SQLITE_TESTCTRL_TRACEFLAGS              31
#define SQLITE_TESTCTRL_TUNE                    32
#define SQLITE_TESTCTRL_LOGEST                  33
#define SQLITE_TESTCTRL_LAST                    33  /* Largest TESTCTRL */

/*
** CAPI3REF: SQL Keyword Checking
**
** These routines provide access to the set of SQL language keywords
** recognized by SQLite.  Applications can uses these routines to determine
** whether or not a specific identifier needs to be escaped (for example,
8679
8680
8681
8682
8683
8684
8685










8686
8687
8688
8689
8690
8691
8692
8693
8694
8695
8696
8697
8698
8699
8700


8701
8702
8703
8704
8705
8706
8707
**
** [[SQLITE_STMTSTATUS_RUN]] <dt>SQLITE_STMTSTATUS_RUN</dt>
** <dd>^This is the number of times that the prepared statement has
** been run.  A single "run" for the purposes of this counter is one
** or more calls to [sqlite3_step()] followed by a call to [sqlite3_reset()].
** The counter is incremented on the first [sqlite3_step()] call of each
** cycle.










**
** [[SQLITE_STMTSTATUS_MEMUSED]] <dt>SQLITE_STMTSTATUS_MEMUSED</dt>
** <dd>^This is the approximate number of bytes of heap memory
** used to store the prepared statement.  ^This value is not actually
** a counter, and so the resetFlg parameter to sqlite3_stmt_status()
** is ignored when the opcode is SQLITE_STMTSTATUS_MEMUSED.
** </dd>
** </dl>
*/
#define SQLITE_STMTSTATUS_FULLSCAN_STEP     1
#define SQLITE_STMTSTATUS_SORT              2
#define SQLITE_STMTSTATUS_AUTOINDEX         3
#define SQLITE_STMTSTATUS_VM_STEP           4
#define SQLITE_STMTSTATUS_REPREPARE         5
#define SQLITE_STMTSTATUS_RUN               6


#define SQLITE_STMTSTATUS_MEMUSED           99

/*
** CAPI3REF: Custom Page Cache Object
**
** The sqlite3_pcache type is opaque.  It is implemented by
** the pluggable module.  The SQLite core has no knowledge of







>
>
>
>
>
>
>
>
>
>















>
>







8769
8770
8771
8772
8773
8774
8775
8776
8777
8778
8779
8780
8781
8782
8783
8784
8785
8786
8787
8788
8789
8790
8791
8792
8793
8794
8795
8796
8797
8798
8799
8800
8801
8802
8803
8804
8805
8806
8807
8808
8809
**
** [[SQLITE_STMTSTATUS_RUN]] <dt>SQLITE_STMTSTATUS_RUN</dt>
** <dd>^This is the number of times that the prepared statement has
** been run.  A single "run" for the purposes of this counter is one
** or more calls to [sqlite3_step()] followed by a call to [sqlite3_reset()].
** The counter is incremented on the first [sqlite3_step()] call of each
** cycle.
**
** [[SQLITE_STMTSTATUS_FILTER_MISS]]
** [[SQLITE_STMTSTATUS_FILTER HIT]]
** <dt>SQLITE_STMTSTATUS_FILTER_HIT<br>
** SQLITE_STMTSTATUS_FILTER_MISS</dt>
** <dd>^SQLITE_STMTSTATUS_FILTER_HIT is the number of times that a join
** step was bypassed because a Bloom filter returned not-found.  The
** corresponding SQLITE_STMTSTATUS_FILTER_MISS value is the number of
** times that the Bloom filter returned a find, and thus the join step
** had to be processed as normal.
**
** [[SQLITE_STMTSTATUS_MEMUSED]] <dt>SQLITE_STMTSTATUS_MEMUSED</dt>
** <dd>^This is the approximate number of bytes of heap memory
** used to store the prepared statement.  ^This value is not actually
** a counter, and so the resetFlg parameter to sqlite3_stmt_status()
** is ignored when the opcode is SQLITE_STMTSTATUS_MEMUSED.
** </dd>
** </dl>
*/
#define SQLITE_STMTSTATUS_FULLSCAN_STEP     1
#define SQLITE_STMTSTATUS_SORT              2
#define SQLITE_STMTSTATUS_AUTOINDEX         3
#define SQLITE_STMTSTATUS_VM_STEP           4
#define SQLITE_STMTSTATUS_REPREPARE         5
#define SQLITE_STMTSTATUS_RUN               6
#define SQLITE_STMTSTATUS_FILTER_MISS       7
#define SQLITE_STMTSTATUS_FILTER_HIT        8
#define SQLITE_STMTSTATUS_MEMUSED           99

/*
** CAPI3REF: Custom Page Cache Object
**
** The sqlite3_pcache type is opaque.  It is implemented by
** the pluggable module.  The SQLite core has no knowledge of
13158
13159
13160
13161
13162
13163
13164
13165
13166
13167

13168

13169
13170
13171
13172
13173
13174
13175
13176
** to help ensure adequate test coverage in places where simple
** condition/decision coverage is inadequate.  For example, testcase()
** can be used to make sure boundary values are tested.  For
** bitmask tests, testcase() can be used to make sure each bit
** is significant and used at least once.  On switch statements
** where multiple cases go to the same block of code, testcase()
** can insure that all cases are evaluated.
**
*/
#ifdef SQLITE_COVERAGE_TEST

SQLITE_PRIVATE   void sqlite3Coverage(int);

# define testcase(X)  if( X ){ sqlite3Coverage(__LINE__); }
#else
# define testcase(X)
#endif

/*
** The TESTONLY macro is used to enclose variable declarations or
** other bits of code that are needed to support the arguments







<

|
>
|
>
|







13260
13261
13262
13263
13264
13265
13266

13267
13268
13269
13270
13271
13272
13273
13274
13275
13276
13277
13278
13279
** to help ensure adequate test coverage in places where simple
** condition/decision coverage is inadequate.  For example, testcase()
** can be used to make sure boundary values are tested.  For
** bitmask tests, testcase() can be used to make sure each bit
** is significant and used at least once.  On switch statements
** where multiple cases go to the same block of code, testcase()
** can insure that all cases are evaluated.

*/
#if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_DEBUG)
# ifndef SQLITE_AMALGAMATION
    extern unsigned int sqlite3CoverageCounter;
# endif
# define testcase(X)  if( X ){ sqlite3CoverageCounter += (unsigned)__LINE__; }
#else
# define testcase(X)
#endif

/*
** The TESTONLY macro is used to enclose variable declarations or
** other bits of code that are needed to support the arguments
13192
13193
13194
13195
13196
13197
13198








13199
13200
13201
13202
13203
13204
13205
13206
13207
13208
13209
13210
13211
13212
13213
13214
13215
13216
13217
13218
13219
13220
13221
13222
13223
13224
13225
13226
13227
13228
13229
13230
13231
13232
13233
13234
13235
13236
13237
13238
13239
13240
13241
13242
13243
13244
13245
13246
13247
13248
13249
13250
13251
*/
#ifndef NDEBUG
# define VVA_ONLY(X)  X
#else
# define VVA_ONLY(X)
#endif









/*
** The ALWAYS and NEVER macros surround boolean expressions which
** are intended to always be true or false, respectively.  Such
** expressions could be omitted from the code completely.  But they
** are included in a few cases in order to enhance the resilience
** of SQLite to unexpected behavior - to make the code "self-healing"
** or "ductile" rather than being "brittle" and crashing at the first
** hint of unplanned behavior.
**
** In other words, ALWAYS and NEVER are added for defensive code.
**
** When doing coverage testing ALWAYS and NEVER are hard-coded to
** be true and false so that the unreachable code they specify will
** not be counted as untested code.
*/
#if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_MUTATION_TEST)
# define ALWAYS(X)      (1)
# define NEVER(X)       (0)
#elif !defined(NDEBUG)
# define ALWAYS(X)      ((X)?1:(assert(0),0))
# define NEVER(X)       ((X)?(assert(0),1):0)
#else
# define ALWAYS(X)      (X)
# define NEVER(X)       (X)
#endif

/*
** The harmless(X) macro indicates that expression X is usually false
** but can be true without causing any problems, but we don't know of
** any way to cause X to be true.
**
** In debugging and testing builds, this macro will abort if X is ever
** true.  In this way, developers are alerted to a possible test case
** that causes X to be true.  If a harmless macro ever fails, that is
** an opportunity to change the macro into a testcase() and add a new
** test case to the test suite.
**
** For normal production builds, harmless(X) is a no-op, since it does
** not matter whether expression X is true or false.
*/
#ifdef SQLITE_DEBUG
# define harmless(X)  assert(!(X));
#else
# define harmless(X)
#endif

/*
** Some conditionals are optimizations only.  In other words, if the
** conditionals are replaced with a constant 1 (true) or 0 (false) then
** the correct answer is still obtained, though perhaps not as quickly.
**
** The following macros mark these optimizations conditionals.
*/







>
>
>
>
>
>
>
>















|










<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<







13295
13296
13297
13298
13299
13300
13301
13302
13303
13304
13305
13306
13307
13308
13309
13310
13311
13312
13313
13314
13315
13316
13317
13318
13319
13320
13321
13322
13323
13324
13325
13326
13327
13328
13329
13330
13331
13332
13333
13334
13335




















13336
13337
13338
13339
13340
13341
13342
*/
#ifndef NDEBUG
# define VVA_ONLY(X)  X
#else
# define VVA_ONLY(X)
#endif

/*
** Disable ALWAYS() and NEVER() (make them pass-throughs) for coverage
** and mutation testing
*/
#if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_MUTATION_TEST)
# define SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS  1
#endif

/*
** The ALWAYS and NEVER macros surround boolean expressions which
** are intended to always be true or false, respectively.  Such
** expressions could be omitted from the code completely.  But they
** are included in a few cases in order to enhance the resilience
** of SQLite to unexpected behavior - to make the code "self-healing"
** or "ductile" rather than being "brittle" and crashing at the first
** hint of unplanned behavior.
**
** In other words, ALWAYS and NEVER are added for defensive code.
**
** When doing coverage testing ALWAYS and NEVER are hard-coded to
** be true and false so that the unreachable code they specify will
** not be counted as untested code.
*/
#if defined(SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS)
# define ALWAYS(X)      (1)
# define NEVER(X)       (0)
#elif !defined(NDEBUG)
# define ALWAYS(X)      ((X)?1:(assert(0),0))
# define NEVER(X)       ((X)?(assert(0),1):0)
#else
# define ALWAYS(X)      (X)
# define NEVER(X)       (X)
#endif





















/*
** Some conditionals are optimizations only.  In other words, if the
** conditionals are replaced with a constant 1 (true) or 0 (false) then
** the correct answer is still obtained, though perhaps not as quickly.
**
** The following macros mark these optimizations conditionals.
*/
13420
13421
13422
13423
13424
13425
13426
13427
13428
13429
13430
13431
13432
13433
13434
#define sqliteHashData(E)   ((E)->data)
/* #define sqliteHashKey(E)    ((E)->pKey) // NOT USED */
/* #define sqliteHashKeysize(E) ((E)->nKey)  // NOT USED */

/*
** Number of entries in a hash table
*/
/* #define sqliteHashCount(H)  ((H)->count) // NOT USED */

#endif /* SQLITE_HASH_H */

/************** End of hash.h ************************************************/
/************** Continuing where we left off in sqliteInt.h ******************/
/************** Include parse.h in the middle of sqliteInt.h *****************/
/************** Begin file parse.h *******************************************/







|







13511
13512
13513
13514
13515
13516
13517
13518
13519
13520
13521
13522
13523
13524
13525
#define sqliteHashData(E)   ((E)->data)
/* #define sqliteHashKey(E)    ((E)->pKey) // NOT USED */
/* #define sqliteHashKeysize(E) ((E)->nKey)  // NOT USED */

/*
** Number of entries in a hash table
*/
#define sqliteHashCount(H)  ((H)->count)

#endif /* SQLITE_HASH_H */

/************** End of hash.h ************************************************/
/************** Continuing where we left off in sqliteInt.h ******************/
/************** Include parse.h in the middle of sqliteInt.h *****************/
/************** Begin file parse.h *******************************************/
13472
13473
13474
13475
13476
13477
13478
13479
13480
13481
13482

13483
13484
13485
13486
13487
13488
13489
#define TK_DATABASE                        38
#define TK_DESC                            39
#define TK_DETACH                          40
#define TK_EACH                            41
#define TK_FAIL                            42
#define TK_OR                              43
#define TK_AND                             44
#define TK_IS                              45
#define TK_MATCH                           46
#define TK_LIKE_KW                         47
#define TK_BETWEEN                         48

#define TK_IN                              49
#define TK_ISNULL                          50
#define TK_NOTNULL                         51
#define TK_NE                              52
#define TK_EQ                              53
#define TK_GT                              54
#define TK_LE                              55







<
|
|
|
>







13563
13564
13565
13566
13567
13568
13569

13570
13571
13572
13573
13574
13575
13576
13577
13578
13579
13580
#define TK_DATABASE                        38
#define TK_DESC                            39
#define TK_DETACH                          40
#define TK_EACH                            41
#define TK_FAIL                            42
#define TK_OR                              43
#define TK_AND                             44

#define TK_MATCH                           45
#define TK_LIKE_KW                         46
#define TK_BETWEEN                         47
#define TK_IS                              48
#define TK_IN                              49
#define TK_ISNULL                          50
#define TK_NOTNULL                         51
#define TK_NE                              52
#define TK_EQ                              53
#define TK_GT                              54
#define TK_LE                              55
13716
13717
13718
13719
13720
13721
13722
13723
13724
13725
13726
13727
13728
13729
13730

/*
** The default initial allocation for the pagecache when using separate
** pagecaches for each database connection.  A positive number is the
** number of pages.  A negative number N translations means that a buffer
** of -1024*N bytes is allocated and used for as many pages as it will hold.
**
** The default value of "20" was choosen to minimize the run-time of the
** speedtest1 test program with options: --shrink-memory --reprepare
*/
#ifndef SQLITE_DEFAULT_PCACHE_INITSZ
# define SQLITE_DEFAULT_PCACHE_INITSZ 20
#endif

/*







|







13807
13808
13809
13810
13811
13812
13813
13814
13815
13816
13817
13818
13819
13820
13821

/*
** The default initial allocation for the pagecache when using separate
** pagecaches for each database connection.  A positive number is the
** number of pages.  A negative number N translations means that a buffer
** of -1024*N bytes is allocated and used for as many pages as it will hold.
**
** The default value of "20" was chosen to minimize the run-time of the
** speedtest1 test program with options: --shrink-memory --reprepare
*/
#ifndef SQLITE_DEFAULT_PCACHE_INITSZ
# define SQLITE_DEFAULT_PCACHE_INITSZ 20
#endif

/*
14073
14074
14075
14076
14077
14078
14079














14080
14081
14082
14083
14084
14085
14086
14087
14088
14089
14090
14091
14092
14093
14094
14095
14096
14097
14098
14099
14100
14101
14102
14103
  int (*xBusyHandler)(void *,int);  /* The busy callback */
  void *pBusyArg;                   /* First arg to busy callback */
  int nBusy;                        /* Incremented with each busy call */
};

/*
** Name of table that holds the database schema.














*/
#define DFLT_SCHEMA_TABLE          "sqlite_master"
#define DFLT_TEMP_SCHEMA_TABLE     "sqlite_temp_master"
#define ALT_SCHEMA_TABLE           "sqlite_schema"
#define ALT_TEMP_SCHEMA_TABLE      "sqlite_temp_schema"


/*
** The root-page of the schema table.
*/
#define SCHEMA_ROOT    1

/*
** The name of the schema table.  The name is different for TEMP.
*/
#define SCHEMA_TABLE(x) \
    ((!OMIT_TEMPDB)&&(x==1)?DFLT_TEMP_SCHEMA_TABLE:DFLT_SCHEMA_TABLE)

/*
** A convenience macro that returns the number of elements in
** an array.
*/
#define ArraySize(X)    ((int)(sizeof(X)/sizeof(X[0])))








>
>
>
>
>
>
>
>
>
>
>
>
>
>

|
|
|
|











|







14164
14165
14166
14167
14168
14169
14170
14171
14172
14173
14174
14175
14176
14177
14178
14179
14180
14181
14182
14183
14184
14185
14186
14187
14188
14189
14190
14191
14192
14193
14194
14195
14196
14197
14198
14199
14200
14201
14202
14203
14204
14205
14206
14207
14208
  int (*xBusyHandler)(void *,int);  /* The busy callback */
  void *pBusyArg;                   /* First arg to busy callback */
  int nBusy;                        /* Incremented with each busy call */
};

/*
** Name of table that holds the database schema.
**
** The PREFERRED names are used whereever possible.  But LEGACY is also
** used for backwards compatibility.
**
**  1.  Queries can use either the PREFERRED or the LEGACY names
**  2.  The sqlite3_set_authorizer() callback uses the LEGACY name
**  3.  The PRAGMA table_list statement uses the PREFERRED name
**
** The LEGACY names are stored in the internal symbol hash table
** in support of (2).  Names are translated using sqlite3PreferredTableName()
** for (3).  The sqlite3FindTable() function takes care of translating
** names for (1).
**
** Note that "sqlite_temp_schema" can also be called "temp.sqlite_schema".
*/
#define LEGACY_SCHEMA_TABLE          "sqlite_master"
#define LEGACY_TEMP_SCHEMA_TABLE     "sqlite_temp_master"
#define PREFERRED_SCHEMA_TABLE       "sqlite_schema"
#define PREFERRED_TEMP_SCHEMA_TABLE  "sqlite_temp_schema"


/*
** The root-page of the schema table.
*/
#define SCHEMA_ROOT    1

/*
** The name of the schema table.  The name is different for TEMP.
*/
#define SCHEMA_TABLE(x) \
    ((!OMIT_TEMPDB)&&(x==1)?LEGACY_TEMP_SCHEMA_TABLE:LEGACY_SCHEMA_TABLE)

/*
** A convenience macro that returns the number of elements in
** an array.
*/
#define ArraySize(X)    ((int)(sizeof(X)/sizeof(X[0])))

15157
15158
15159
15160
15161
15162
15163

15164
15165
15166
15167
15168
15169
15170
15171
15172
15173
15174
15175
15176
15177
15178
15179
15180
15181
15182
15183


15184
15185
15186
15187
15188
15189
15190
15191
15192
15193
15194
15195
15196
15197
15198
15199
15200
15201
15202
15203
15204
15205
15206
15207
15208
15209
15210
15211
15212
15213
15214
15215
15216
15217

15218
15219
15220
15221
15222
15223
15224
15225
15226
15227
15228
15229
15230
15231
15232
15233
15234
15235
15236
15237
15238
15239
15240
15241
15242
15243
15244
15245
15246
15247
15248
15249
15250
15251
15252
15253

15254
15255
15256
15257
15258
15259
15260
15261
15262
15263
15264
15265
15266
15267
15268
15269
15270
15271
15272
15273
15274
15275
15276

15277
15278
15279
15280
15281
15282
15283
15284
15285
15286
15287
15288
15289
15290
15291
15292
15293
15294
15295
15296
15297
15298
15299
15300
15301
15302
15303
15304
15305
15306
15307
15308
15309
15310
15311
15312
15313
15314
15315
15316
15317

15318
15319
15320
15321
15322
15323
15324
15325
15326
15327
15328
15329
15330
15331
15332
#define OP_Lt             56 /* jump, same as TK_LT, synopsis: IF r[P3]<r[P1] */
#define OP_Ge             57 /* jump, same as TK_GE, synopsis: IF r[P3]>=r[P1] */
#define OP_ElseEq         58 /* jump, same as TK_ESCAPE                    */
#define OP_IfNotZero      59 /* jump, synopsis: if r[P1]!=0 then r[P1]--, goto P2 */
#define OP_DecrJumpZero   60 /* jump, synopsis: if (--r[P1])==0 goto P2    */
#define OP_IncrVacuum     61 /* jump                                       */
#define OP_VNext          62 /* jump                                       */

#define OP_Init           63 /* jump, synopsis: Start at P2                */
#define OP_PureFunc       64 /* synopsis: r[P3]=func(r[P2@NP])             */
#define OP_Function       65 /* synopsis: r[P3]=func(r[P2@NP])             */
#define OP_Return         66
#define OP_EndCoroutine   67
#define OP_HaltIfNull     68 /* synopsis: if r[P3]=null halt               */
#define OP_Halt           69
#define OP_Integer        70 /* synopsis: r[P2]=P1                         */
#define OP_Int64          71 /* synopsis: r[P2]=P4                         */
#define OP_String         72 /* synopsis: r[P2]='P4' (len=P1)              */
#define OP_Null           73 /* synopsis: r[P2..P3]=NULL                   */
#define OP_SoftNull       74 /* synopsis: r[P1]=NULL                       */
#define OP_Blob           75 /* synopsis: r[P2]=P4 (len=P1)                */
#define OP_Variable       76 /* synopsis: r[P2]=parameter(P1,P4)           */
#define OP_Move           77 /* synopsis: r[P2@P3]=r[P1@P3]                */
#define OP_Copy           78 /* synopsis: r[P2@P3+1]=r[P1@P3+1]            */
#define OP_SCopy          79 /* synopsis: r[P2]=r[P1]                      */
#define OP_IntCopy        80 /* synopsis: r[P2]=r[P1]                      */
#define OP_ChngCntRow     81 /* synopsis: output=r[P1]                     */
#define OP_ResultRow      82 /* synopsis: output=r[P1@P2]                  */


#define OP_CollSeq        83
#define OP_AddImm         84 /* synopsis: r[P1]=r[P1]+P2                   */
#define OP_RealAffinity   85
#define OP_Cast           86 /* synopsis: affinity(r[P1])                  */
#define OP_Permutation    87
#define OP_Compare        88 /* synopsis: r[P1@P3] <-> r[P2@P3]            */
#define OP_IsTrue         89 /* synopsis: r[P2] = coalesce(r[P1]==TRUE,P3) ^ P4 */
#define OP_ZeroOrNull     90 /* synopsis: r[P2] = 0 OR NULL                */
#define OP_Offset         91 /* synopsis: r[P3] = sqlite_offset(P1)        */
#define OP_Column         92 /* synopsis: r[P3]=PX                         */
#define OP_TypeCheck      93 /* synopsis: typecheck(r[P1@P2])              */
#define OP_Affinity       94 /* synopsis: affinity(r[P1@P2])               */
#define OP_MakeRecord     95 /* synopsis: r[P3]=mkrec(r[P1@P2])            */
#define OP_Count          96 /* synopsis: r[P2]=count()                    */
#define OP_ReadCookie     97
#define OP_SetCookie      98
#define OP_ReopenIdx      99 /* synopsis: root=P2 iDb=P3                   */
#define OP_OpenRead      100 /* synopsis: root=P2 iDb=P3                   */
#define OP_OpenWrite     101 /* synopsis: root=P2 iDb=P3                   */
#define OP_BitAnd        102 /* same as TK_BITAND, synopsis: r[P3]=r[P1]&r[P2] */
#define OP_BitOr         103 /* same as TK_BITOR, synopsis: r[P3]=r[P1]|r[P2] */
#define OP_ShiftLeft     104 /* same as TK_LSHIFT, synopsis: r[P3]=r[P2]<<r[P1] */
#define OP_ShiftRight    105 /* same as TK_RSHIFT, synopsis: r[P3]=r[P2]>>r[P1] */
#define OP_Add           106 /* same as TK_PLUS, synopsis: r[P3]=r[P1]+r[P2] */
#define OP_Subtract      107 /* same as TK_MINUS, synopsis: r[P3]=r[P2]-r[P1] */
#define OP_Multiply      108 /* same as TK_STAR, synopsis: r[P3]=r[P1]*r[P2] */
#define OP_Divide        109 /* same as TK_SLASH, synopsis: r[P3]=r[P2]/r[P1] */
#define OP_Remainder     110 /* same as TK_REM, synopsis: r[P3]=r[P2]%r[P1] */
#define OP_Concat        111 /* same as TK_CONCAT, synopsis: r[P3]=r[P2]+r[P1] */
#define OP_OpenDup       112
#define OP_BitNot        113 /* same as TK_BITNOT, synopsis: r[P2]= ~r[P1] */
#define OP_OpenAutoindex 114 /* synopsis: nColumn=P2                       */
#define OP_OpenEphemeral 115 /* synopsis: nColumn=P2                       */
#define OP_String8       116 /* same as TK_STRING, synopsis: r[P2]='P4'    */

#define OP_SorterOpen    117
#define OP_SequenceTest  118 /* synopsis: if( cursor[P1].ctr++ ) pc = P2   */
#define OP_OpenPseudo    119 /* synopsis: P3 columns in r[P2]              */
#define OP_Close         120
#define OP_ColumnsUsed   121
#define OP_SeekScan      122 /* synopsis: Scan-ahead up to P1 rows         */
#define OP_SeekHit       123 /* synopsis: set P2<=seekHit<=P3              */
#define OP_Sequence      124 /* synopsis: r[P2]=cursor[P1].ctr++           */
#define OP_NewRowid      125 /* synopsis: r[P2]=rowid                      */
#define OP_Insert        126 /* synopsis: intkey=r[P3] data=r[P2]          */
#define OP_RowCell       127
#define OP_Delete        128
#define OP_ResetCount    129
#define OP_SorterCompare 130 /* synopsis: if key(P1)!=trim(r[P3],P4) goto P2 */
#define OP_SorterData    131 /* synopsis: r[P2]=data                       */
#define OP_RowData       132 /* synopsis: r[P2]=data                       */
#define OP_Rowid         133 /* synopsis: r[P2]=rowid                      */
#define OP_NullRow       134
#define OP_SeekEnd       135
#define OP_IdxInsert     136 /* synopsis: key=r[P2]                        */
#define OP_SorterInsert  137 /* synopsis: key=r[P2]                        */
#define OP_IdxDelete     138 /* synopsis: key=r[P2@P3]                     */
#define OP_DeferredSeek  139 /* synopsis: Move P3 to P1.rowid if needed    */
#define OP_IdxRowid      140 /* synopsis: r[P2]=rowid                      */
#define OP_FinishSeek    141
#define OP_Destroy       142
#define OP_Clear         143
#define OP_ResetSorter   144
#define OP_CreateBtree   145 /* synopsis: r[P2]=root iDb=P1 flags=P3       */
#define OP_SqlExec       146
#define OP_ParseSchema   147
#define OP_LoadAnalysis  148
#define OP_DropTable     149
#define OP_DropIndex     150
#define OP_DropTrigger   151
#define OP_Real          152 /* same as TK_FLOAT, synopsis: r[P2]=P4       */

#define OP_IntegrityCk   153
#define OP_RowSetAdd     154 /* synopsis: rowset(P1)=r[P2]                 */
#define OP_Param         155
#define OP_FkCounter     156 /* synopsis: fkctr[P1]+=P2                    */
#define OP_MemMax        157 /* synopsis: r[P1]=max(r[P1],r[P2])           */
#define OP_OffsetLimit   158 /* synopsis: if r[P1]>0 then r[P2]=r[P1]+max(0,r[P3]) else r[P2]=(-1) */
#define OP_AggInverse    159 /* synopsis: accum=r[P3] inverse(r[P2@P5])    */
#define OP_AggStep       160 /* synopsis: accum=r[P3] step(r[P2@P5])       */
#define OP_AggStep1      161 /* synopsis: accum=r[P3] step(r[P2@P5])       */
#define OP_AggValue      162 /* synopsis: r[P3]=value N=P2                 */
#define OP_AggFinal      163 /* synopsis: accum=r[P1] N=P2                 */
#define OP_Expire        164
#define OP_CursorLock    165
#define OP_CursorUnlock  166
#define OP_TableLock     167 /* synopsis: iDb=P1 root=P2 write=P3          */
#define OP_VBegin        168
#define OP_VCreate       169
#define OP_VDestroy      170
#define OP_VOpen         171
#define OP_VColumn       172 /* synopsis: r[P3]=vcolumn(P2)                */
#define OP_VRename       173
#define OP_Pagecount     174
#define OP_MaxPgcnt      175

#define OP_Trace         176
#define OP_CursorHint    177
#define OP_ReleaseReg    178 /* synopsis: release r[P1@P2] mask P3         */
#define OP_Noop          179
#define OP_Explain       180
#define OP_Abortable     181

/* Properties such as "out2" or "jump" that are specified in
** comments following the "case" for each opcode in the vdbe.c
** are encoded into bitvectors as follows:
*/
#define OPFLG_JUMP        0x01  /* jump:  P2 holds jmp target */
#define OPFLG_IN1         0x02  /* in1:   P1 is an input */
#define OPFLG_IN2         0x04  /* in2:   P2 is an input */
#define OPFLG_IN3         0x08  /* in3:   P3 is an input */
#define OPFLG_OUT2        0x10  /* out2:  P2 is an output */
#define OPFLG_OUT3        0x20  /* out3:  P3 is an output */
#define OPFLG_INITIALIZER {\
/*   0 */ 0x00, 0x00, 0x00, 0x01, 0x01, 0x01, 0x00, 0x10,\
/*   8 */ 0x00, 0x01, 0x00, 0x01, 0x01, 0x01, 0x03, 0x03,\
/*  16 */ 0x01, 0x01, 0x03, 0x12, 0x03, 0x03, 0x01, 0x09,\
/*  24 */ 0x09, 0x09, 0x09, 0x01, 0x09, 0x09, 0x09, 0x09,\
/*  32 */ 0x09, 0x09, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,\
/*  40 */ 0x01, 0x01, 0x01, 0x26, 0x26, 0x23, 0x0b, 0x01,\
/*  48 */ 0x01, 0x03, 0x03, 0x03, 0x0b, 0x0b, 0x0b, 0x0b,\
/*  56 */ 0x0b, 0x0b, 0x01, 0x03, 0x03, 0x01, 0x01, 0x01,\
/*  64 */ 0x00, 0x00, 0x02, 0x02, 0x08, 0x00, 0x10, 0x10,\
/*  72 */ 0x10, 0x10, 0x00, 0x10, 0x10, 0x00, 0x00, 0x10,\
/*  80 */ 0x10, 0x00, 0x00, 0x00, 0x02, 0x02, 0x02, 0x00,\
/*  88 */ 0x00, 0x12, 0x1e, 0x20, 0x00, 0x00, 0x00, 0x00,\
/*  96 */ 0x10, 0x10, 0x00, 0x00, 0x00, 0x00, 0x26, 0x26,\
/* 104 */ 0x26, 0x26, 0x26, 0x26, 0x26, 0x26, 0x26, 0x26,\
/* 112 */ 0x00, 0x12, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00,\
/* 120 */ 0x00, 0x00, 0x00, 0x00, 0x10, 0x10, 0x00, 0x00,\
/* 128 */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00,\
/* 136 */ 0x04, 0x04, 0x00, 0x00, 0x10, 0x00, 0x10, 0x00,\
/* 144 */ 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,\
/* 152 */ 0x10, 0x00, 0x06, 0x10, 0x00, 0x04, 0x1a, 0x00,\
/* 160 */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,\
/* 168 */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x10,\
/* 176 */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,}


/* The resolve3P2Values() routine is able to run faster if it knows
** the value of the largest JUMP opcode.  The smaller the maximum
** JUMP opcode the better, so the mkopcodeh.tcl script that
** generated this include file strives to group all JUMP opcodes
** together near the beginning of the list.
*/
#define SQLITE_MX_JUMP_OPCODE  63  /* Maximum JUMP opcode */

/************** End of opcodes.h *********************************************/
/************** Continuing where we left off in vdbe.h ***********************/

/*
** Additional non-public SQLITE_PREPARE_* flags
*/







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










|

|
|

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

>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
>
|
|
|
|
|
|




















|
|
|
|
|


|
|
|
|
|

|
|
>







|







15262
15263
15264
15265
15266
15267
15268
15269
15270
15271
15272
15273
15274
15275
15276
15277
15278
15279
15280
15281
15282
15283
15284
15285
15286
15287


15288
15289
15290
15291
15292
15293
15294
15295
15296
15297
15298
15299
15300
15301
15302
15303
15304
15305

15306
15307
15308
15309
15310
15311
15312
15313
15314
15315
15316
15317
15318
15319
15320
15321
15322
15323
15324
15325
15326
15327
15328
15329
15330
15331
15332
15333
15334
15335
15336
15337
15338
15339
15340
15341
15342
15343
15344
15345
15346
15347
15348
15349
15350
15351
15352
15353
15354
15355
15356
15357

15358
15359
15360
15361
15362
15363
15364
15365
15366
15367
15368
15369
15370
15371
15372
15373
15374
15375
15376
15377
15378
15379
15380
15381
15382
15383
15384
15385
15386
15387
15388
15389
15390
15391
15392
15393
15394
15395
15396
15397
15398
15399
15400
15401
15402
15403
15404
15405
15406
15407
15408
15409
15410
15411
15412
15413
15414
15415
15416
15417
15418
15419
15420
15421
15422
15423
15424
15425
15426
15427
15428
15429
15430
15431
15432
15433
15434
15435
15436
15437
15438
15439
15440
#define OP_Lt             56 /* jump, same as TK_LT, synopsis: IF r[P3]<r[P1] */
#define OP_Ge             57 /* jump, same as TK_GE, synopsis: IF r[P3]>=r[P1] */
#define OP_ElseEq         58 /* jump, same as TK_ESCAPE                    */
#define OP_IfNotZero      59 /* jump, synopsis: if r[P1]!=0 then r[P1]--, goto P2 */
#define OP_DecrJumpZero   60 /* jump, synopsis: if (--r[P1])==0 goto P2    */
#define OP_IncrVacuum     61 /* jump                                       */
#define OP_VNext          62 /* jump                                       */
#define OP_Filter         63 /* jump, synopsis: if key(P3@P4) not in filter(P1) goto P2 */
#define OP_Init           64 /* jump, synopsis: Start at P2                */
#define OP_PureFunc       65 /* synopsis: r[P3]=func(r[P2@NP])             */
#define OP_Function       66 /* synopsis: r[P3]=func(r[P2@NP])             */
#define OP_Return         67
#define OP_EndCoroutine   68
#define OP_HaltIfNull     69 /* synopsis: if r[P3]=null halt               */
#define OP_Halt           70
#define OP_Integer        71 /* synopsis: r[P2]=P1                         */
#define OP_Int64          72 /* synopsis: r[P2]=P4                         */
#define OP_String         73 /* synopsis: r[P2]='P4' (len=P1)              */
#define OP_Null           74 /* synopsis: r[P2..P3]=NULL                   */
#define OP_SoftNull       75 /* synopsis: r[P1]=NULL                       */
#define OP_Blob           76 /* synopsis: r[P2]=P4 (len=P1)                */
#define OP_Variable       77 /* synopsis: r[P2]=parameter(P1,P4)           */
#define OP_Move           78 /* synopsis: r[P2@P3]=r[P1@P3]                */
#define OP_Copy           79 /* synopsis: r[P2@P3+1]=r[P1@P3+1]            */
#define OP_SCopy          80 /* synopsis: r[P2]=r[P1]                      */
#define OP_IntCopy        81 /* synopsis: r[P2]=r[P1]                      */


#define OP_FkCheck        82
#define OP_ResultRow      83 /* synopsis: output=r[P1@P2]                  */
#define OP_CollSeq        84
#define OP_AddImm         85 /* synopsis: r[P1]=r[P1]+P2                   */
#define OP_RealAffinity   86
#define OP_Cast           87 /* synopsis: affinity(r[P1])                  */
#define OP_Permutation    88
#define OP_Compare        89 /* synopsis: r[P1@P3] <-> r[P2@P3]            */
#define OP_IsTrue         90 /* synopsis: r[P2] = coalesce(r[P1]==TRUE,P3) ^ P4 */
#define OP_ZeroOrNull     91 /* synopsis: r[P2] = 0 OR NULL                */
#define OP_Offset         92 /* synopsis: r[P3] = sqlite_offset(P1)        */
#define OP_Column         93 /* synopsis: r[P3]=PX                         */
#define OP_TypeCheck      94 /* synopsis: typecheck(r[P1@P2])              */
#define OP_Affinity       95 /* synopsis: affinity(r[P1@P2])               */
#define OP_MakeRecord     96 /* synopsis: r[P3]=mkrec(r[P1@P2])            */
#define OP_Count          97 /* synopsis: r[P2]=count()                    */
#define OP_ReadCookie     98
#define OP_SetCookie      99

#define OP_ReopenIdx     100 /* synopsis: root=P2 iDb=P3                   */
#define OP_OpenRead      101 /* synopsis: root=P2 iDb=P3                   */
#define OP_BitAnd        102 /* same as TK_BITAND, synopsis: r[P3]=r[P1]&r[P2] */
#define OP_BitOr         103 /* same as TK_BITOR, synopsis: r[P3]=r[P1]|r[P2] */
#define OP_ShiftLeft     104 /* same as TK_LSHIFT, synopsis: r[P3]=r[P2]<<r[P1] */
#define OP_ShiftRight    105 /* same as TK_RSHIFT, synopsis: r[P3]=r[P2]>>r[P1] */
#define OP_Add           106 /* same as TK_PLUS, synopsis: r[P3]=r[P1]+r[P2] */
#define OP_Subtract      107 /* same as TK_MINUS, synopsis: r[P3]=r[P2]-r[P1] */
#define OP_Multiply      108 /* same as TK_STAR, synopsis: r[P3]=r[P1]*r[P2] */
#define OP_Divide        109 /* same as TK_SLASH, synopsis: r[P3]=r[P2]/r[P1] */
#define OP_Remainder     110 /* same as TK_REM, synopsis: r[P3]=r[P2]%r[P1] */
#define OP_Concat        111 /* same as TK_CONCAT, synopsis: r[P3]=r[P2]+r[P1] */
#define OP_OpenWrite     112 /* synopsis: root=P2 iDb=P3                   */
#define OP_BitNot        113 /* same as TK_BITNOT, synopsis: r[P2]= ~r[P1] */
#define OP_OpenDup       114
#define OP_OpenAutoindex 115 /* synopsis: nColumn=P2                       */
#define OP_String8       116 /* same as TK_STRING, synopsis: r[P2]='P4'    */
#define OP_OpenEphemeral 117 /* synopsis: nColumn=P2                       */
#define OP_SorterOpen    118
#define OP_SequenceTest  119 /* synopsis: if( cursor[P1].ctr++ ) pc = P2   */
#define OP_OpenPseudo    120 /* synopsis: P3 columns in r[P2]              */
#define OP_Close         121
#define OP_ColumnsUsed   122
#define OP_SeekScan      123 /* synopsis: Scan-ahead up to P1 rows         */
#define OP_SeekHit       124 /* synopsis: set P2<=seekHit<=P3              */
#define OP_Sequence      125 /* synopsis: r[P2]=cursor[P1].ctr++           */
#define OP_NewRowid      126 /* synopsis: r[P2]=rowid                      */
#define OP_Insert        127 /* synopsis: intkey=r[P3] data=r[P2]          */
#define OP_RowCell       128
#define OP_Delete        129
#define OP_ResetCount    130
#define OP_SorterCompare 131 /* synopsis: if key(P1)!=trim(r[P3],P4) goto P2 */
#define OP_SorterData    132 /* synopsis: r[P2]=data                       */
#define OP_RowData       133 /* synopsis: r[P2]=data                       */
#define OP_Rowid         134 /* synopsis: r[P2]=rowid                      */
#define OP_NullRow       135
#define OP_SeekEnd       136
#define OP_IdxInsert     137 /* synopsis: key=r[P2]                        */
#define OP_SorterInsert  138 /* synopsis: key=r[P2]                        */
#define OP_IdxDelete     139 /* synopsis: key=r[P2@P3]                     */
#define OP_DeferredSeek  140 /* synopsis: Move P3 to P1.rowid if needed    */
#define OP_IdxRowid      141 /* synopsis: r[P2]=rowid                      */
#define OP_FinishSeek    142
#define OP_Destroy       143
#define OP_Clear         144
#define OP_ResetSorter   145
#define OP_CreateBtree   146 /* synopsis: r[P2]=root iDb=P1 flags=P3       */
#define OP_SqlExec       147
#define OP_ParseSchema   148
#define OP_LoadAnalysis  149
#define OP_DropTable     150
#define OP_DropIndex     151

#define OP_Real          152 /* same as TK_FLOAT, synopsis: r[P2]=P4       */
#define OP_DropTrigger   153
#define OP_IntegrityCk   154
#define OP_RowSetAdd     155 /* synopsis: rowset(P1)=r[P2]                 */
#define OP_Param         156
#define OP_FkCounter     157 /* synopsis: fkctr[P1]+=P2                    */
#define OP_MemMax        158 /* synopsis: r[P1]=max(r[P1],r[P2])           */
#define OP_OffsetLimit   159 /* synopsis: if r[P1]>0 then r[P2]=r[P1]+max(0,r[P3]) else r[P2]=(-1) */
#define OP_AggInverse    160 /* synopsis: accum=r[P3] inverse(r[P2@P5])    */
#define OP_AggStep       161 /* synopsis: accum=r[P3] step(r[P2@P5])       */
#define OP_AggStep1      162 /* synopsis: accum=r[P3] step(r[P2@P5])       */
#define OP_AggValue      163 /* synopsis: r[P3]=value N=P2                 */
#define OP_AggFinal      164 /* synopsis: accum=r[P1] N=P2                 */
#define OP_Expire        165
#define OP_CursorLock    166
#define OP_CursorUnlock  167
#define OP_TableLock     168 /* synopsis: iDb=P1 root=P2 write=P3          */
#define OP_VBegin        169
#define OP_VCreate       170
#define OP_VDestroy      171
#define OP_VOpen         172
#define OP_VColumn       173 /* synopsis: r[P3]=vcolumn(P2)                */
#define OP_VRename       174
#define OP_Pagecount     175
#define OP_MaxPgcnt      176
#define OP_FilterAdd     177 /* synopsis: filter(P1) += key(P3@P4)         */
#define OP_Trace         178
#define OP_CursorHint    179
#define OP_ReleaseReg    180 /* synopsis: release r[P1@P2] mask P3         */
#define OP_Noop          181
#define OP_Explain       182
#define OP_Abortable     183

/* Properties such as "out2" or "jump" that are specified in
** comments following the "case" for each opcode in the vdbe.c
** are encoded into bitvectors as follows:
*/
#define OPFLG_JUMP        0x01  /* jump:  P2 holds jmp target */
#define OPFLG_IN1         0x02  /* in1:   P1 is an input */
#define OPFLG_IN2         0x04  /* in2:   P2 is an input */
#define OPFLG_IN3         0x08  /* in3:   P3 is an input */
#define OPFLG_OUT2        0x10  /* out2:  P2 is an output */
#define OPFLG_OUT3        0x20  /* out3:  P3 is an output */
#define OPFLG_INITIALIZER {\
/*   0 */ 0x00, 0x00, 0x00, 0x01, 0x01, 0x01, 0x00, 0x10,\
/*   8 */ 0x00, 0x01, 0x00, 0x01, 0x01, 0x01, 0x03, 0x03,\
/*  16 */ 0x01, 0x01, 0x03, 0x12, 0x03, 0x03, 0x01, 0x09,\
/*  24 */ 0x09, 0x09, 0x09, 0x01, 0x09, 0x09, 0x09, 0x09,\
/*  32 */ 0x09, 0x09, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,\
/*  40 */ 0x01, 0x01, 0x01, 0x26, 0x26, 0x23, 0x0b, 0x01,\
/*  48 */ 0x01, 0x03, 0x03, 0x03, 0x0b, 0x0b, 0x0b, 0x0b,\
/*  56 */ 0x0b, 0x0b, 0x01, 0x03, 0x03, 0x01, 0x01, 0x01,\
/*  64 */ 0x01, 0x00, 0x00, 0x02, 0x02, 0x08, 0x00, 0x10,\
/*  72 */ 0x10, 0x10, 0x10, 0x00, 0x10, 0x10, 0x00, 0x00,\
/*  80 */ 0x10, 0x10, 0x00, 0x00, 0x00, 0x02, 0x02, 0x02,\
/*  88 */ 0x00, 0x00, 0x12, 0x1e, 0x20, 0x00, 0x00, 0x00,\
/*  96 */ 0x00, 0x10, 0x10, 0x00, 0x00, 0x00, 0x26, 0x26,\
/* 104 */ 0x26, 0x26, 0x26, 0x26, 0x26, 0x26, 0x26, 0x26,\
/* 112 */ 0x00, 0x12, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00,\
/* 120 */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x10, 0x00,\
/* 128 */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00,\
/* 136 */ 0x00, 0x04, 0x04, 0x00, 0x00, 0x10, 0x00, 0x10,\
/* 144 */ 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,\
/* 152 */ 0x10, 0x00, 0x00, 0x06, 0x10, 0x00, 0x04, 0x1a,\
/* 160 */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,\
/* 168 */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10,\
/* 176 */ 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,\
}

/* The resolve3P2Values() routine is able to run faster if it knows
** the value of the largest JUMP opcode.  The smaller the maximum
** JUMP opcode the better, so the mkopcodeh.tcl script that
** generated this include file strives to group all JUMP opcodes
** together near the beginning of the list.
*/
#define SQLITE_MX_JUMP_OPCODE  64  /* Maximum JUMP opcode */

/************** End of opcodes.h *********************************************/
/************** Continuing where we left off in vdbe.h ***********************/

/*
** Additional non-public SQLITE_PREPARE_* flags
*/
16418
16419
16420
16421
16422
16423
16424
16425
16426
16427
16428
16429
16430
16431
16432
16433
16434
16435
16436
16437
16438



16439
16440
16441
16442
16443
16444
16445
  int nVdbeRead;                /* Number of active VDBEs that read or write */
  int nVdbeWrite;               /* Number of active VDBEs that read and write */
  int nVdbeExec;                /* Number of nested calls to VdbeExec() */
  int nVDestroy;                /* Number of active OP_VDestroy operations */
  int nExtension;               /* Number of loaded extensions */
  void **aExtension;            /* Array of shared library handles */
  union {
    void (*xLegacy)(void*,const char*);     /* Legacy trace function */
    int (*xV2)(u32,void*,void*,void*);      /* V2 Trace function */
  } trace;
  void *pTraceArg;                          /* Argument to the trace function */
#ifndef SQLITE_OMIT_DEPRECATED
  void (*xProfile)(void*,const char*,u64);  /* Profiling function */
  void *pProfileArg;                        /* Argument to profile function */
#endif
  void *pCommitArg;                 /* Argument to xCommitCallback() */
  int (*xCommitCallback)(void*);    /* Invoked at every commit. */
  void *pRollbackArg;               /* Argument to xRollbackCallback() */
  void (*xRollbackCallback)(void*); /* Invoked at every commit. */
  void *pUpdateArg;
  void (*xUpdateCallback)(void*,int, const char*,const char*,sqlite_int64);



  Parse *pParse;                /* Current parse */
#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
  void *pPreUpdateArg;          /* First argument to xPreUpdateCallback */
  void (*xPreUpdateCallback)(   /* Registered using sqlite3_preupdate_hook() */
    void*,sqlite3*,int,char const*,char const*,sqlite3_int64,sqlite3_int64
  );
  PreUpdate *pPreUpdate;        /* Context for active pre-update callback */







|
|

|










>
>
>







16526
16527
16528
16529
16530
16531
16532
16533
16534
16535
16536
16537
16538
16539
16540
16541
16542
16543
16544
16545
16546
16547
16548
16549
16550
16551
16552
16553
16554
16555
16556
  int nVdbeRead;                /* Number of active VDBEs that read or write */
  int nVdbeWrite;               /* Number of active VDBEs that read and write */
  int nVdbeExec;                /* Number of nested calls to VdbeExec() */
  int nVDestroy;                /* Number of active OP_VDestroy operations */
  int nExtension;               /* Number of loaded extensions */
  void **aExtension;            /* Array of shared library handles */
  union {
    void (*xLegacy)(void*,const char*);   /* mTrace==SQLITE_TRACE_LEGACY */
    int (*xV2)(u32,void*,void*,void*);    /* All other mTrace values */
  } trace;
  void *pTraceArg;                        /* Argument to the trace function */
#ifndef SQLITE_OMIT_DEPRECATED
  void (*xProfile)(void*,const char*,u64);  /* Profiling function */
  void *pProfileArg;                        /* Argument to profile function */
#endif
  void *pCommitArg;                 /* Argument to xCommitCallback() */
  int (*xCommitCallback)(void*);    /* Invoked at every commit. */
  void *pRollbackArg;               /* Argument to xRollbackCallback() */
  void (*xRollbackCallback)(void*); /* Invoked at every commit. */
  void *pUpdateArg;
  void (*xUpdateCallback)(void*,int, const char*,const char*,sqlite_int64);
  void *pAutovacPagesArg;           /* Client argument to autovac_pages */
  void (*xAutovacDestr)(void*);     /* Destructor for pAutovacPAgesArg */
  unsigned int (*xAutovacPages)(void*,const char*,u32,u32,u32);
  Parse *pParse;                /* Current parse */
#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
  void *pPreUpdateArg;          /* First argument to xPreUpdateCallback */
  void (*xPreUpdateCallback)(   /* Registered using sqlite3_preupdate_hook() */
    void*,sqlite3*,int,char const*,char const*,sqlite3_int64,sqlite3_int64
  );
  PreUpdate *pPreUpdate;        /* Context for active pre-update callback */
16561
16562
16563
16564
16565
16566
16567

16568
16569
16570
16571
16572
16573
16574
#define SQLITE_Defensive      0x10000000  /* Input SQL is likely hostile */
#define SQLITE_DqsDDL         0x20000000  /* dbl-quoted strings allowed in DDL*/
#define SQLITE_DqsDML         0x40000000  /* dbl-quoted strings allowed in DML*/
#define SQLITE_EnableView     0x80000000  /* Enable the use of views */
#define SQLITE_CountRows      HI(0x00001) /* Count rows changed by INSERT, */
                                          /*   DELETE, or UPDATE and return */
                                          /*   the count using a callback. */


/* Flags used only if debugging */
#ifdef SQLITE_DEBUG
#define SQLITE_SqlTrace       HI(0x0100000) /* Debug print SQL as it executes */
#define SQLITE_VdbeListing    HI(0x0200000) /* Debug listings of VDBE progs */
#define SQLITE_VdbeTrace      HI(0x0400000) /* True to trace VDBE execution */
#define SQLITE_VdbeAddopTrace HI(0x0800000) /* Trace sqlite3VdbeAddOp() calls */







>







16672
16673
16674
16675
16676
16677
16678
16679
16680
16681
16682
16683
16684
16685
16686
#define SQLITE_Defensive      0x10000000  /* Input SQL is likely hostile */
#define SQLITE_DqsDDL         0x20000000  /* dbl-quoted strings allowed in DDL*/
#define SQLITE_DqsDML         0x40000000  /* dbl-quoted strings allowed in DML*/
#define SQLITE_EnableView     0x80000000  /* Enable the use of views */
#define SQLITE_CountRows      HI(0x00001) /* Count rows changed by INSERT, */
                                          /*   DELETE, or UPDATE and return */
                                          /*   the count using a callback. */
#define SQLITE_CorruptRdOnly  HI(0x00002) /* Prohibit writes due to error */

/* Flags used only if debugging */
#ifdef SQLITE_DEBUG
#define SQLITE_SqlTrace       HI(0x0100000) /* Debug print SQL as it executes */
#define SQLITE_VdbeListing    HI(0x0200000) /* Debug listings of VDBE progs */
#define SQLITE_VdbeTrace      HI(0x0400000) /* True to trace VDBE execution */
#define SQLITE_VdbeAddopTrace HI(0x0800000) /* Trace sqlite3VdbeAddOp() calls */
16609
16610
16611
16612
16613
16614
16615


16616
16617
16618
16619
16620
16621
16622
#define SQLITE_SimplifyJoin   0x00002000 /* Convert LEFT JOIN to JOIN */
#define SQLITE_SkipScan       0x00004000 /* Skip-scans */
#define SQLITE_PropagateConst 0x00008000 /* The constant propagation opt */
#define SQLITE_MinMaxOpt      0x00010000 /* The min/max optimization */
#define SQLITE_SeekScan       0x00020000 /* The OP_SeekScan optimization */
#define SQLITE_OmitOrderBy    0x00040000 /* Omit pointless ORDER BY */
   /* TH3 expects this value  ^^^^^^^^^^ to be 0x40000. Coordinate any change */


#define SQLITE_AllOpts        0xffffffff /* All optimizations */

/*
** Macros for testing whether or not optimizations are enabled or disabled.
*/
#define OptimizationDisabled(db, mask)  (((db)->dbOptFlags&(mask))!=0)
#define OptimizationEnabled(db, mask)   (((db)->dbOptFlags&(mask))==0)







>
>







16721
16722
16723
16724
16725
16726
16727
16728
16729
16730
16731
16732
16733
16734
16735
16736
#define SQLITE_SimplifyJoin   0x00002000 /* Convert LEFT JOIN to JOIN */
#define SQLITE_SkipScan       0x00004000 /* Skip-scans */
#define SQLITE_PropagateConst 0x00008000 /* The constant propagation opt */
#define SQLITE_MinMaxOpt      0x00010000 /* The min/max optimization */
#define SQLITE_SeekScan       0x00020000 /* The OP_SeekScan optimization */
#define SQLITE_OmitOrderBy    0x00040000 /* Omit pointless ORDER BY */
   /* TH3 expects this value  ^^^^^^^^^^ to be 0x40000. Coordinate any change */
#define SQLITE_BloomFilter    0x00080000 /* Use a Bloom filter on searches */
#define SQLITE_BloomPulldown  0x00100000 /* Run Bloom filters early */
#define SQLITE_AllOpts        0xffffffff /* All optimizations */

/*
** Macros for testing whether or not optimizations are enabled or disabled.
*/
#define OptimizationDisabled(db, mask)  (((db)->dbOptFlags&(mask))!=0)
#define OptimizationEnabled(db, mask)   (((db)->dbOptFlags&(mask))==0)
16657
16658
16659
16660
16661
16662
16663
16664
16665
16666
16667
16668
16669
16670
16671
  void (*xFinalize)(sqlite3_context*);                  /* Agg finalizer */
  void (*xValue)(sqlite3_context*);                     /* Current agg value */
  void (*xInverse)(sqlite3_context*,int,sqlite3_value**); /* inverse agg-step */
  const char *zName;   /* SQL name of the function. */
  union {
    FuncDef *pHash;      /* Next with a different name but the same hash */
    FuncDestructor *pDestructor;   /* Reference counted destructor function */
  } u;
};

/*
** This structure encapsulates a user-function destructor callback (as
** configured using create_function_v2()) and a reference counter. When
** create_function_v2() is called to create a function with a destructor,
** a single object of this type is allocated. FuncDestructor.nRef is set to







|







16771
16772
16773
16774
16775
16776
16777
16778
16779
16780
16781
16782
16783
16784
16785
  void (*xFinalize)(sqlite3_context*);                  /* Agg finalizer */
  void (*xValue)(sqlite3_context*);                     /* Current agg value */
  void (*xInverse)(sqlite3_context*,int,sqlite3_value**); /* inverse agg-step */
  const char *zName;   /* SQL name of the function. */
  union {
    FuncDef *pHash;      /* Next with a different name but the same hash */
    FuncDestructor *pDestructor;   /* Reference counted destructor function */
  } u; /* pHash if SQLITE_FUNC_BUILTIN, pDestructor otherwise */
};

/*
** This structure encapsulates a user-function destructor callback (as
** configured using create_function_v2()) and a reference counter. When
** create_function_v2() is called to create a function with a destructor,
** a single object of this type is allocated. FuncDestructor.nRef is set to
16718
16719
16720
16721
16722
16723
16724

16725
16726
16727
16728
16729
16730
16731
#define SQLITE_FUNC_OFFSET   0x8000 /* Built-in sqlite_offset() function */
#define SQLITE_FUNC_WINDOW   0x00010000 /* Built-in window-only function */
#define SQLITE_FUNC_INTERNAL 0x00040000 /* For use by NestedParse() only */
#define SQLITE_FUNC_DIRECT   0x00080000 /* Not for use in TRIGGERs or VIEWs */
#define SQLITE_FUNC_SUBTYPE  0x00100000 /* Result likely to have sub-type */
#define SQLITE_FUNC_UNSAFE   0x00200000 /* Function has side effects */
#define SQLITE_FUNC_INLINE   0x00400000 /* Functions implemented in-line */

#define SQLITE_FUNC_ANYORDER 0x08000000 /* count/min/max aggregate */

/* Identifier numbers for each in-line function */
#define INLINEFUNC_coalesce             0
#define INLINEFUNC_implies_nonnull_row  1
#define INLINEFUNC_expr_implies_expr    2
#define INLINEFUNC_expr_compare         3







>







16832
16833
16834
16835
16836
16837
16838
16839
16840
16841
16842
16843
16844
16845
16846
#define SQLITE_FUNC_OFFSET   0x8000 /* Built-in sqlite_offset() function */
#define SQLITE_FUNC_WINDOW   0x00010000 /* Built-in window-only function */
#define SQLITE_FUNC_INTERNAL 0x00040000 /* For use by NestedParse() only */
#define SQLITE_FUNC_DIRECT   0x00080000 /* Not for use in TRIGGERs or VIEWs */
#define SQLITE_FUNC_SUBTYPE  0x00100000 /* Result likely to have sub-type */
#define SQLITE_FUNC_UNSAFE   0x00200000 /* Function has side effects */
#define SQLITE_FUNC_INLINE   0x00400000 /* Functions implemented in-line */
#define SQLITE_FUNC_BUILTIN  0x00800000 /* This is a built-in function */
#define SQLITE_FUNC_ANYORDER 0x08000000 /* count/min/max aggregate */

/* Identifier numbers for each in-line function */
#define INLINEFUNC_coalesce             0
#define INLINEFUNC_implies_nonnull_row  1
#define INLINEFUNC_expr_implies_expr    2
#define INLINEFUNC_expr_compare         3
16796
16797
16798
16799
16800
16801
16802

16803
16804
16805
16806
16807
16808
16809
16810
16811
16812
16813
16814

16815
16816
16817

16818
16819
16820
16821
16822
16823
16824

16825
16826
16827

16828
16829
16830

16831
16832
16833
16834
16835
16836
16837
16838
16839

16840
16841
16842
16843
16844
16845
16846
16847
**     that accepts nArg arguments and is implemented by a call to C
**     function likeFunc. Argument pArg is cast to a (void *) and made
**     available as the function user-data (sqlite3_user_data()). The
**     FuncDef.flags variable is set to the value passed as the flags
**     parameter.
*/
#define FUNCTION(zName, nArg, iArg, bNC, xFunc) \

  {nArg, SQLITE_FUNC_CONSTANT|SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL), \
   SQLITE_INT_TO_PTR(iArg), 0, xFunc, 0, 0, 0, #zName, {0} }
#define VFUNCTION(zName, nArg, iArg, bNC, xFunc) \
  {nArg, SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL), \
   SQLITE_INT_TO_PTR(iArg), 0, xFunc, 0, 0, 0, #zName, {0} }
#define SFUNCTION(zName, nArg, iArg, bNC, xFunc) \
  {nArg, SQLITE_UTF8|SQLITE_DIRECTONLY|SQLITE_FUNC_UNSAFE, \
   SQLITE_INT_TO_PTR(iArg), 0, xFunc, 0, 0, 0, #zName, {0} }
#define MFUNCTION(zName, nArg, xPtr, xFunc) \
  {nArg, SQLITE_FUNC_CONSTANT|SQLITE_UTF8, \
   xPtr, 0, xFunc, 0, 0, 0, #zName, {0} }
#define INLINE_FUNC(zName, nArg, iArg, mFlags) \

  {nArg, SQLITE_UTF8|SQLITE_FUNC_INLINE|SQLITE_FUNC_CONSTANT|(mFlags), \
   SQLITE_INT_TO_PTR(iArg), 0, noopFunc, 0, 0, 0, #zName, {0} }
#define TEST_FUNC(zName, nArg, iArg, mFlags) \

  {nArg, SQLITE_UTF8|SQLITE_FUNC_INTERNAL|SQLITE_FUNC_TEST| \
         SQLITE_FUNC_INLINE|SQLITE_FUNC_CONSTANT|(mFlags), \
   SQLITE_INT_TO_PTR(iArg), 0, noopFunc, 0, 0, 0, #zName, {0} }
#define DFUNCTION(zName, nArg, iArg, bNC, xFunc) \
  {nArg, SQLITE_FUNC_SLOCHNG|SQLITE_UTF8, \
   0, 0, xFunc, 0, 0, 0, #zName, {0} }
#define PURE_DATE(zName, nArg, iArg, bNC, xFunc) \

  {nArg, SQLITE_FUNC_SLOCHNG|SQLITE_UTF8|SQLITE_FUNC_CONSTANT, \
   (void*)&sqlite3Config, 0, xFunc, 0, 0, 0, #zName, {0} }
#define FUNCTION2(zName, nArg, iArg, bNC, xFunc, extraFlags) \

  {nArg,SQLITE_FUNC_CONSTANT|SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL)|extraFlags,\
   SQLITE_INT_TO_PTR(iArg), 0, xFunc, 0, 0, 0, #zName, {0} }
#define STR_FUNCTION(zName, nArg, pArg, bNC, xFunc) \

  {nArg, SQLITE_FUNC_SLOCHNG|SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL), \
   pArg, 0, xFunc, 0, 0, 0, #zName, }
#define LIKEFUNC(zName, nArg, arg, flags) \
  {nArg, SQLITE_FUNC_CONSTANT|SQLITE_UTF8|flags, \
   (void *)arg, 0, likeFunc, 0, 0, 0, #zName, {0} }
#define WAGGREGATE(zName, nArg, arg, nc, xStep, xFinal, xValue, xInverse, f) \
  {nArg, SQLITE_UTF8|(nc*SQLITE_FUNC_NEEDCOLL)|f, \
   SQLITE_INT_TO_PTR(arg), 0, xStep,xFinal,xValue,xInverse,#zName, {0}}
#define INTERNAL_FUNCTION(zName, nArg, xFunc) \

  {nArg, SQLITE_FUNC_INTERNAL|SQLITE_UTF8|SQLITE_FUNC_CONSTANT, \
   0, 0, xFunc, 0, 0, 0, #zName, {0} }


/*
** All current savepoints are stored in a linked list starting at
** sqlite3.pSavepoint. The first element in the list is the most recently
** opened savepoint. Savepoints are added to the list by the vdbe







>
|


|


|


|


>
|


>
|



|


>
|


>
|


>
|


|


|


>
|







16911
16912
16913
16914
16915
16916
16917
16918
16919
16920
16921
16922
16923
16924
16925
16926
16927
16928
16929
16930
16931
16932
16933
16934
16935
16936
16937
16938
16939
16940
16941
16942
16943
16944
16945
16946
16947
16948
16949
16950
16951
16952
16953
16954
16955
16956
16957
16958
16959
16960
16961
16962
16963
16964
16965
16966
16967
16968
16969
**     that accepts nArg arguments and is implemented by a call to C
**     function likeFunc. Argument pArg is cast to a (void *) and made
**     available as the function user-data (sqlite3_user_data()). The
**     FuncDef.flags variable is set to the value passed as the flags
**     parameter.
*/
#define FUNCTION(zName, nArg, iArg, bNC, xFunc) \
  {nArg, SQLITE_FUNC_BUILTIN|\
   SQLITE_FUNC_CONSTANT|SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL), \
   SQLITE_INT_TO_PTR(iArg), 0, xFunc, 0, 0, 0, #zName, {0} }
#define VFUNCTION(zName, nArg, iArg, bNC, xFunc) \
  {nArg, SQLITE_FUNC_BUILTIN|SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL), \
   SQLITE_INT_TO_PTR(iArg), 0, xFunc, 0, 0, 0, #zName, {0} }
#define SFUNCTION(zName, nArg, iArg, bNC, xFunc) \
  {nArg, SQLITE_FUNC_BUILTIN|SQLITE_UTF8|SQLITE_DIRECTONLY|SQLITE_FUNC_UNSAFE, \
   SQLITE_INT_TO_PTR(iArg), 0, xFunc, 0, 0, 0, #zName, {0} }
#define MFUNCTION(zName, nArg, xPtr, xFunc) \
  {nArg, SQLITE_FUNC_BUILTIN|SQLITE_FUNC_CONSTANT|SQLITE_UTF8, \
   xPtr, 0, xFunc, 0, 0, 0, #zName, {0} }
#define INLINE_FUNC(zName, nArg, iArg, mFlags) \
  {nArg, SQLITE_FUNC_BUILTIN|\
   SQLITE_UTF8|SQLITE_FUNC_INLINE|SQLITE_FUNC_CONSTANT|(mFlags), \
   SQLITE_INT_TO_PTR(iArg), 0, noopFunc, 0, 0, 0, #zName, {0} }
#define TEST_FUNC(zName, nArg, iArg, mFlags) \
  {nArg, SQLITE_FUNC_BUILTIN|\
         SQLITE_UTF8|SQLITE_FUNC_INTERNAL|SQLITE_FUNC_TEST| \
         SQLITE_FUNC_INLINE|SQLITE_FUNC_CONSTANT|(mFlags), \
   SQLITE_INT_TO_PTR(iArg), 0, noopFunc, 0, 0, 0, #zName, {0} }
#define DFUNCTION(zName, nArg, iArg, bNC, xFunc) \
  {nArg, SQLITE_FUNC_BUILTIN|SQLITE_FUNC_SLOCHNG|SQLITE_UTF8, \
   0, 0, xFunc, 0, 0, 0, #zName, {0} }
#define PURE_DATE(zName, nArg, iArg, bNC, xFunc) \
  {nArg, SQLITE_FUNC_BUILTIN|\
         SQLITE_FUNC_SLOCHNG|SQLITE_UTF8|SQLITE_FUNC_CONSTANT, \
   (void*)&sqlite3Config, 0, xFunc, 0, 0, 0, #zName, {0} }
#define FUNCTION2(zName, nArg, iArg, bNC, xFunc, extraFlags) \
  {nArg, SQLITE_FUNC_BUILTIN|\
   SQLITE_FUNC_CONSTANT|SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL)|extraFlags,\
   SQLITE_INT_TO_PTR(iArg), 0, xFunc, 0, 0, 0, #zName, {0} }
#define STR_FUNCTION(zName, nArg, pArg, bNC, xFunc) \
  {nArg, SQLITE_FUNC_BUILTIN|\
   SQLITE_FUNC_SLOCHNG|SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL), \
   pArg, 0, xFunc, 0, 0, 0, #zName, }
#define LIKEFUNC(zName, nArg, arg, flags) \
  {nArg, SQLITE_FUNC_BUILTIN|SQLITE_FUNC_CONSTANT|SQLITE_UTF8|flags, \
   (void *)arg, 0, likeFunc, 0, 0, 0, #zName, {0} }
#define WAGGREGATE(zName, nArg, arg, nc, xStep, xFinal, xValue, xInverse, f) \
  {nArg, SQLITE_FUNC_BUILTIN|SQLITE_UTF8|(nc*SQLITE_FUNC_NEEDCOLL)|f, \
   SQLITE_INT_TO_PTR(arg), 0, xStep,xFinal,xValue,xInverse,#zName, {0}}
#define INTERNAL_FUNCTION(zName, nArg, xFunc) \
  {nArg, SQLITE_FUNC_BUILTIN|\
   SQLITE_FUNC_INTERNAL|SQLITE_UTF8|SQLITE_FUNC_CONSTANT, \
   0, 0, xFunc, 0, 0, 0, #zName, {0} }


/*
** All current savepoints are stored in a linked list starting at
** sqlite3.pSavepoint. The first element in the list is the most recently
** opened savepoint. Savepoints are added to the list by the vdbe
17556
17557
17558
17559
17560
17561
17562
17563
17564
17565
17566
17567
17568
17569
17570
17571
17572
17573
** Expr.op is the opcode. The integer parser token codes are reused
** as opcodes here. For example, the parser defines TK_GE to be an integer
** code representing the ">=" operator. This same integer code is reused
** to represent the greater-than-or-equal-to operator in the expression
** tree.
**
** If the expression is an SQL literal (TK_INTEGER, TK_FLOAT, TK_BLOB,
** or TK_STRING), then Expr.token contains the text of the SQL literal. If
** the expression is a variable (TK_VARIABLE), then Expr.token contains the
** variable name. Finally, if the expression is an SQL function (TK_FUNCTION),
** then Expr.token contains the name of the function.
**
** Expr.pRight and Expr.pLeft are the left and right subexpressions of a
** binary operator. Either or both may be NULL.
**
** Expr.x.pList is a list of arguments if the expression is an SQL function,
** a CASE expression or an IN expression of the form "<lhs> IN (<y>, <z>...)".
** Expr.x.pSelect is used if the expression is a sub-select or an expression of







|
|

|







17678
17679
17680
17681
17682
17683
17684
17685
17686
17687
17688
17689
17690
17691
17692
17693
17694
17695
** Expr.op is the opcode. The integer parser token codes are reused
** as opcodes here. For example, the parser defines TK_GE to be an integer
** code representing the ">=" operator. This same integer code is reused
** to represent the greater-than-or-equal-to operator in the expression
** tree.
**
** If the expression is an SQL literal (TK_INTEGER, TK_FLOAT, TK_BLOB,
** or TK_STRING), then Expr.u.zToken contains the text of the SQL literal. If
** the expression is a variable (TK_VARIABLE), then Expr.u.zToken contains the
** variable name. Finally, if the expression is an SQL function (TK_FUNCTION),
** then Expr.u.zToken contains the name of the function.
**
** Expr.pRight and Expr.pLeft are the left and right subexpressions of a
** binary operator. Either or both may be NULL.
**
** Expr.x.pList is a list of arguments if the expression is an SQL function,
** a CASE expression or an IN expression of the form "<lhs> IN (<y>, <z>...)".
** Expr.x.pSelect is used if the expression is a sub-select or an expression of
17599
17600
17601
17602
17603
17604
17605
17606
17607
17608
17609
17610
17611
17612
17613
**
** ALLOCATION NOTES:
**
** Expr objects can use a lot of memory space in database schema.  To
** help reduce memory requirements, sometimes an Expr object will be
** truncated.  And to reduce the number of memory allocations, sometimes
** two or more Expr objects will be stored in a single memory allocation,
** together with Expr.zToken strings.
**
** If the EP_Reduced and EP_TokenOnly flags are set when
** an Expr object is truncated.  When EP_Reduced is set, then all
** the child Expr objects in the Expr.pLeft and Expr.pRight subtrees
** are contained within the same memory allocation.  Note, however, that
** the subtrees in Expr.x.pList or Expr.x.pSelect are always separately
** allocated, regardless of whether or not EP_Reduced is set.







|







17721
17722
17723
17724
17725
17726
17727
17728
17729
17730
17731
17732
17733
17734
17735
**
** ALLOCATION NOTES:
**
** Expr objects can use a lot of memory space in database schema.  To
** help reduce memory requirements, sometimes an Expr object will be
** truncated.  And to reduce the number of memory allocations, sometimes
** two or more Expr objects will be stored in a single memory allocation,
** together with Expr.u.zToken strings.
**
** If the EP_Reduced and EP_TokenOnly flags are set when
** an Expr object is truncated.  When EP_Reduced is set, then all
** the child Expr objects in the Expr.pLeft and Expr.pRight subtrees
** are contained within the same memory allocation.  Note, however, that
** the subtrees in Expr.x.pList or Expr.x.pSelect are always separately
** allocated, regardless of whether or not EP_Reduced is set.
17668
17669
17670
17671
17672
17673
17674
17675
17676
17677
17678
17679
17680
17681
17682
17683
    struct {               /* TK_IN, TK_SELECT, and TK_EXISTS */
      int iAddr;             /* Subroutine entry address */
      int regReturn;         /* Register used to hold return address */
    } sub;
  } y;
};

/*
** The following are the meanings of bits in the Expr.flags field.
** Value restrictions:
**
**          EP_Agg == NC_HasAgg == SF_HasAgg
**          EP_Win == NC_HasWin
*/
#define EP_FromJoin   0x000001 /* Originates in ON/USING clause of outer join */
#define EP_Distinct   0x000002 /* Aggregate function with DISTINCT keyword */







<
|







17790
17791
17792
17793
17794
17795
17796

17797
17798
17799
17800
17801
17802
17803
17804
    struct {               /* TK_IN, TK_SELECT, and TK_EXISTS */
      int iAddr;             /* Subroutine entry address */
      int regReturn;         /* Register used to hold return address */
    } sub;
  } y;
};


/* The following are the meanings of bits in the Expr.flags field.
** Value restrictions:
**
**          EP_Agg == NC_HasAgg == SF_HasAgg
**          EP_Win == NC_HasWin
*/
#define EP_FromJoin   0x000001 /* Originates in ON/USING clause of outer join */
#define EP_Distinct   0x000002 /* Aggregate function with DISTINCT keyword */
17708
17709
17710
17711
17712
17713
17714
17715
17716
17717
17718
17719
17720
17721
17722
17723
17724
17725
17726
17727
17728
17729
17730
17731










17732
17733
17734
17735
17736
17737
17738
#define EP_Quoted    0x4000000 /* TK_ID was originally quoted */
#define EP_Static    0x8000000 /* Held in memory not obtained from malloc() */
#define EP_IsTrue   0x10000000 /* Always has boolean value of TRUE */
#define EP_IsFalse  0x20000000 /* Always has boolean value of FALSE */
#define EP_FromDDL  0x40000000 /* Originates from sqlite_schema */
               /*   0x80000000 // Available */

/*
** The EP_Propagate mask is a set of properties that automatically propagate
** upwards into parent nodes.
*/
#define EP_Propagate (EP_Collate|EP_Subquery|EP_HasFunc)

/*
** These macros can be used to test, set, or clear bits in the
** Expr.flags field.
*/
#define ExprHasProperty(E,P)     (((E)->flags&(P))!=0)
#define ExprHasAllProperty(E,P)  (((E)->flags&(P))==(P))
#define ExprSetProperty(E,P)     (E)->flags|=(P)
#define ExprClearProperty(E,P)   (E)->flags&=~(P)
#define ExprAlwaysTrue(E)   (((E)->flags&(EP_FromJoin|EP_IsTrue))==EP_IsTrue)
#define ExprAlwaysFalse(E)  (((E)->flags&(EP_FromJoin|EP_IsFalse))==EP_IsFalse)












/* Flags for use with Expr.vvaFlags
*/
#define EP_NoReduce   0x01  /* Cannot EXPRDUP_REDUCE this Expr */
#define EP_Immutable  0x02  /* Do not change this Expr node */

/* The ExprSetVVAProperty() macro is used for Verification, Validation,







<
|




<
|









>
>
>
>
>
>
>
>
>
>







17829
17830
17831
17832
17833
17834
17835

17836
17837
17838
17839
17840

17841
17842
17843
17844
17845
17846
17847
17848
17849
17850
17851
17852
17853
17854
17855
17856
17857
17858
17859
17860
17861
17862
17863
17864
17865
17866
17867
#define EP_Quoted    0x4000000 /* TK_ID was originally quoted */
#define EP_Static    0x8000000 /* Held in memory not obtained from malloc() */
#define EP_IsTrue   0x10000000 /* Always has boolean value of TRUE */
#define EP_IsFalse  0x20000000 /* Always has boolean value of FALSE */
#define EP_FromDDL  0x40000000 /* Originates from sqlite_schema */
               /*   0x80000000 // Available */


/* The EP_Propagate mask is a set of properties that automatically propagate
** upwards into parent nodes.
*/
#define EP_Propagate (EP_Collate|EP_Subquery|EP_HasFunc)


/* Macros can be used to test, set, or clear bits in the
** Expr.flags field.
*/
#define ExprHasProperty(E,P)     (((E)->flags&(P))!=0)
#define ExprHasAllProperty(E,P)  (((E)->flags&(P))==(P))
#define ExprSetProperty(E,P)     (E)->flags|=(P)
#define ExprClearProperty(E,P)   (E)->flags&=~(P)
#define ExprAlwaysTrue(E)   (((E)->flags&(EP_FromJoin|EP_IsTrue))==EP_IsTrue)
#define ExprAlwaysFalse(E)  (((E)->flags&(EP_FromJoin|EP_IsFalse))==EP_IsFalse)

/* Macros used to ensure that the correct members of unions are accessed
** in Expr.
*/
#define ExprUseUToken(E)    (((E)->flags&EP_IntValue)==0)
#define ExprUseUValue(E)    (((E)->flags&EP_IntValue)!=0)
#define ExprUseXList(E)     (((E)->flags&EP_xIsSelect)==0)
#define ExprUseXSelect(E)   (((E)->flags&EP_xIsSelect)!=0)
#define ExprUseYTab(E)      (((E)->flags&(EP_WinFunc|EP_Subrtn))==0)
#define ExprUseYWin(E)      (((E)->flags&EP_WinFunc)!=0)
#define ExprUseYSub(E)      (((E)->flags&EP_Subrtn)!=0)

/* Flags for use with Expr.vvaFlags
*/
#define EP_NoReduce   0x01  /* Cannot EXPRDUP_REDUCE this Expr */
#define EP_Immutable  0x02  /* Do not change this Expr node */

/* The ExprSetVVAProperty() macro is used for Verification, Validation,
17807
17808
17809
17810
17811
17812
17813
17814
17815
17816
17817
17818

17819
17820
17821
17822
17823
17824
17825
    u8 sortFlags;           /* Mask of KEYINFO_ORDER_* flags */
    unsigned eEName :2;     /* Meaning of zEName */
    unsigned done :1;       /* A flag to indicate when processing is finished */
    unsigned reusable :1;   /* Constant expression is reusable */
    unsigned bSorterRef :1; /* Defer evaluation until after sorting */
    unsigned bNulls: 1;     /* True if explicit "NULLS FIRST/LAST" */
    union {
      struct {
        u16 iOrderByCol;      /* For ORDER BY, column number in result set */
        u16 iAlias;           /* Index into Parse.aAlias[] for zName */
      } x;
      int iConstExprReg;      /* Register in which Expr value is cached */

    } u;
  } a[1];                  /* One slot for each expression in the list */
};

/*
** Allowed values for Expr.a.eEName
*/







|



|
>







17936
17937
17938
17939
17940
17941
17942
17943
17944
17945
17946
17947
17948
17949
17950
17951
17952
17953
17954
17955
    u8 sortFlags;           /* Mask of KEYINFO_ORDER_* flags */
    unsigned eEName :2;     /* Meaning of zEName */
    unsigned done :1;       /* A flag to indicate when processing is finished */
    unsigned reusable :1;   /* Constant expression is reusable */
    unsigned bSorterRef :1; /* Defer evaluation until after sorting */
    unsigned bNulls: 1;     /* True if explicit "NULLS FIRST/LAST" */
    union {
      struct {             /* Used by any ExprList other than Parse.pConsExpr */
        u16 iOrderByCol;      /* For ORDER BY, column number in result set */
        u16 iAlias;           /* Index into Parse.aAlias[] for zName */
      } x;
      int iConstExprReg;   /* Register in which Expr value is cached. Used only
                           ** by Parse.pConstExpr */
    } u;
  } a[1];                  /* One slot for each expression in the list */
};

/*
** Allowed values for Expr.a.eEName
*/
17849
17850
17851
17852
17853
17854
17855







17856
17857
17858
17859
17860
17861
17862
  } *a;
  int nId;         /* Number of identifiers on the list */
};

/*
** The SrcItem object represents a single term in the FROM clause of a query.
** The SrcList object is mostly an array of SrcItems.







*/
struct SrcItem {
  Schema *pSchema;  /* Schema to which this item is fixed */
  char *zDatabase;  /* Name of database holding this table */
  char *zName;      /* Name of the table */
  char *zAlias;     /* The "B" part of a "A AS B" phrase.  zName is the "A" */
  Table *pTab;      /* An SQL table corresponding to zName */







>
>
>
>
>
>
>







17979
17980
17981
17982
17983
17984
17985
17986
17987
17988
17989
17990
17991
17992
17993
17994
17995
17996
17997
17998
17999
  } *a;
  int nId;         /* Number of identifiers on the list */
};

/*
** The SrcItem object represents a single term in the FROM clause of a query.
** The SrcList object is mostly an array of SrcItems.
**
** Union member validity:
**
**    u1.zIndexedBy          fg.isIndexedBy && !fg.isTabFunc
**    u1.pFuncArg            fg.isTabFunc   && !fg.isIndexedBy
**    u2.pIBIndex            fg.isIndexedBy && !fg.isCte
**    u2.pCteUse             fg.isCte       && !fg.isIndexedBy
*/
struct SrcItem {
  Schema *pSchema;  /* Schema to which this item is fixed */
  char *zDatabase;  /* Name of database holding this table */
  char *zName;      /* Name of the table */
  char *zAlias;     /* The "B" part of a "A AS B" phrase.  zName is the "A" */
  Table *pTab;      /* An SQL table corresponding to zName */
18380
18381
18382
18383
18384
18385
18386
18387
18388
18389
18390
18391
18392
18393
18394
#ifndef SQLITE_OMIT_SHARED_CACHE
  int nTableLock;        /* Number of locks in aTableLock */
  TableLock *aTableLock; /* Required table locks for shared-cache mode */
#endif
  AutoincInfo *pAinc;  /* Information about AUTOINCREMENT counters */
  Parse *pToplevel;    /* Parse structure for main program (or NULL) */
  Table *pTriggerTab;  /* Table triggers are being coded for */
  Parse *pParentParse; /* Parent parser if this parser is nested */
  union {
    int addrCrTab;         /* Address of OP_CreateBtree on CREATE TABLE */
    Returning *pReturning; /* The RETURNING clause */
  } u1;
  u32 nQueryLoop;      /* Est number of iterations of a query (10*log2(N)) */
  u32 oldmask;         /* Mask of old.* columns referenced */
  u32 newmask;         /* Mask of new.* columns referenced */







<







18517
18518
18519
18520
18521
18522
18523

18524
18525
18526
18527
18528
18529
18530
#ifndef SQLITE_OMIT_SHARED_CACHE
  int nTableLock;        /* Number of locks in aTableLock */
  TableLock *aTableLock; /* Required table locks for shared-cache mode */
#endif
  AutoincInfo *pAinc;  /* Information about AUTOINCREMENT counters */
  Parse *pToplevel;    /* Parse structure for main program (or NULL) */
  Table *pTriggerTab;  /* Table triggers are being coded for */

  union {
    int addrCrTab;         /* Address of OP_CreateBtree on CREATE TABLE */
    Returning *pReturning; /* The RETURNING clause */
  } u1;
  u32 nQueryLoop;      /* Est number of iterations of a query (10*log2(N)) */
  u32 oldmask;         /* Mask of old.* columns referenced */
  u32 newmask;         /* Mask of new.* columns referenced */
18443
18444
18445
18446
18447
18448
18449


18450
18451
18452
18453
18454
18455
18456
  With *pWith;              /* Current WITH clause, or NULL */
  ParseCleanup *pCleanup;   /* List of cleanup operations to run after parse */
#ifndef SQLITE_OMIT_ALTERTABLE
  RenameToken *pRename;     /* Tokens subject to renaming by ALTER TABLE */
#endif
};



#define PARSE_MODE_NORMAL        0
#define PARSE_MODE_DECLARE_VTAB  1
#define PARSE_MODE_RENAME        2
#define PARSE_MODE_UNMAP         3

/*
** Sizes and pointers of various parts of the Parse object.







>
>







18579
18580
18581
18582
18583
18584
18585
18586
18587
18588
18589
18590
18591
18592
18593
18594
  With *pWith;              /* Current WITH clause, or NULL */
  ParseCleanup *pCleanup;   /* List of cleanup operations to run after parse */
#ifndef SQLITE_OMIT_ALTERTABLE
  RenameToken *pRename;     /* Tokens subject to renaming by ALTER TABLE */
#endif
};

/* Allowed values for Parse.eParseMode
*/
#define PARSE_MODE_NORMAL        0
#define PARSE_MODE_DECLARE_VTAB  1
#define PARSE_MODE_RENAME        2
#define PARSE_MODE_UNMAP         3

/*
** Sizes and pointers of various parts of the Parse object.
18664
18665
18666
18667
18668
18669
18670

18671
18672

18673
18674
18675
18676
18677
18678
18679
  u32 nInitRow;       /* Number of rows processed */
  Pgno mxPage;        /* Maximum page number.  0 for no limit. */
} InitData;

/*
** Allowed values for mInitFlags
*/

#define INITFLAG_AlterRename   0x0001  /* Reparse after a RENAME */
#define INITFLAG_AlterDrop     0x0002  /* Reparse after a DROP COLUMN */


/* Tuning parameters are set using SQLITE_TESTCTRL_TUNE and are controlled
** on debug-builds of the CLI using ".testctrl tune ID VALUE".  Tuning
** parameters are for temporary use during development, to help find
** optimial values for parameters in the query planner.  The should not
** be used on trunk check-ins.  They are a temporary mechanism available
** for transient development builds only.







>


>







18802
18803
18804
18805
18806
18807
18808
18809
18810
18811
18812
18813
18814
18815
18816
18817
18818
18819
  u32 nInitRow;       /* Number of rows processed */
  Pgno mxPage;        /* Maximum page number.  0 for no limit. */
} InitData;

/*
** Allowed values for mInitFlags
*/
#define INITFLAG_AlterMask     0x0003  /* Types of ALTER */
#define INITFLAG_AlterRename   0x0001  /* Reparse after a RENAME */
#define INITFLAG_AlterDrop     0x0002  /* Reparse after a DROP COLUMN */
#define INITFLAG_AlterAdd      0x0003  /* Reparse after an ADD COLUMN */

/* Tuning parameters are set using SQLITE_TESTCTRL_TUNE and are controlled
** on debug-builds of the CLI using ".testctrl tune ID VALUE".  Tuning
** parameters are for temporary use during development, to help find
** optimial values for parameters in the query planner.  The should not
** be used on trunk check-ins.  They are a temporary mechanism available
** for transient development builds only.
18786
18787
18788
18789
18790
18791
18792
18793
18794

18795
18796
18797
18798
18799
18800
18801
  int walkerDepth;                          /* Number of subqueries */
  u16 eCode;                                /* A small processing code */
  union {                                   /* Extra data for callback */
    NameContext *pNC;                         /* Naming context */
    int n;                                    /* A counter */
    int iCur;                                 /* A cursor number */
    SrcList *pSrcList;                        /* FROM clause */
    struct SrcCount *pSrcCount;               /* Counting column references */
    struct CCurHint *pCCurHint;               /* Used by codeCursorHint() */

    int *aiCol;                               /* array of column indexes */
    struct IdxCover *pIdxCover;               /* Check for index coverage */
    struct IdxExprTrans *pIdxTrans;           /* Convert idxed expr to column */
    ExprList *pGroupBy;                       /* GROUP BY clause */
    Select *pSelect;                          /* HAVING to WHERE clause ctx */
    struct WindowRewrite *pRewrite;           /* Window rewrite context */
    struct WhereConst *pConst;                /* WHERE clause constants */







<

>







18926
18927
18928
18929
18930
18931
18932

18933
18934
18935
18936
18937
18938
18939
18940
18941
  int walkerDepth;                          /* Number of subqueries */
  u16 eCode;                                /* A small processing code */
  union {                                   /* Extra data for callback */
    NameContext *pNC;                         /* Naming context */
    int n;                                    /* A counter */
    int iCur;                                 /* A cursor number */
    SrcList *pSrcList;                        /* FROM clause */

    struct CCurHint *pCCurHint;               /* Used by codeCursorHint() */
    struct RefSrcList *pRefSrcList;           /* sqlite3ReferencesSrcList() */
    int *aiCol;                               /* array of column indexes */
    struct IdxCover *pIdxCover;               /* Check for index coverage */
    struct IdxExprTrans *pIdxTrans;           /* Convert idxed expr to column */
    ExprList *pGroupBy;                       /* GROUP BY clause */
    Select *pSelect;                          /* HAVING to WHERE clause ctx */
    struct WindowRewrite *pRewrite;           /* Window rewrite context */
    struct WhereConst *pConst;                /* WHERE clause constants */
19385
19386
19387
19388
19389
19390
19391

19392
19393
19394
19395
19396
19397
19398
SQLITE_PRIVATE void sqlite3SelectDelete(sqlite3*, Select*);
SQLITE_PRIVATE Table *sqlite3SrcListLookup(Parse*, SrcList*);
SQLITE_PRIVATE int sqlite3IsReadOnly(Parse*, Table*, int);
SQLITE_PRIVATE void sqlite3OpenTable(Parse*, int iCur, int iDb, Table*, int);
#if defined(SQLITE_ENABLE_UPDATE_DELETE_LIMIT) && !defined(SQLITE_OMIT_SUBQUERY)
SQLITE_PRIVATE Expr *sqlite3LimitWhere(Parse*,SrcList*,Expr*,ExprList*,Expr*,char*);
#endif

SQLITE_PRIVATE void sqlite3DeleteFrom(Parse*, SrcList*, Expr*, ExprList*, Expr*);
SQLITE_PRIVATE void sqlite3Update(Parse*, SrcList*, ExprList*,Expr*,int,ExprList*,Expr*,
                   Upsert*);
SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin(Parse*,SrcList*,Expr*,ExprList*,ExprList*,u16,int);
SQLITE_PRIVATE void sqlite3WhereEnd(WhereInfo*);
SQLITE_PRIVATE LogEst sqlite3WhereOutputRowCount(WhereInfo*);
SQLITE_PRIVATE int sqlite3WhereIsDistinct(WhereInfo*);







>







19525
19526
19527
19528
19529
19530
19531
19532
19533
19534
19535
19536
19537
19538
19539
SQLITE_PRIVATE void sqlite3SelectDelete(sqlite3*, Select*);
SQLITE_PRIVATE Table *sqlite3SrcListLookup(Parse*, SrcList*);
SQLITE_PRIVATE int sqlite3IsReadOnly(Parse*, Table*, int);
SQLITE_PRIVATE void sqlite3OpenTable(Parse*, int iCur, int iDb, Table*, int);
#if defined(SQLITE_ENABLE_UPDATE_DELETE_LIMIT) && !defined(SQLITE_OMIT_SUBQUERY)
SQLITE_PRIVATE Expr *sqlite3LimitWhere(Parse*,SrcList*,Expr*,ExprList*,Expr*,char*);
#endif
SQLITE_PRIVATE void sqlite3CodeChangeCount(Vdbe*,int,const char*);
SQLITE_PRIVATE void sqlite3DeleteFrom(Parse*, SrcList*, Expr*, ExprList*, Expr*);
SQLITE_PRIVATE void sqlite3Update(Parse*, SrcList*, ExprList*,Expr*,int,ExprList*,Expr*,
                   Upsert*);
SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin(Parse*,SrcList*,Expr*,ExprList*,ExprList*,u16,int);
SQLITE_PRIVATE void sqlite3WhereEnd(WhereInfo*);
SQLITE_PRIVATE LogEst sqlite3WhereOutputRowCount(WhereInfo*);
SQLITE_PRIVATE int sqlite3WhereIsDistinct(WhereInfo*);
19428
19429
19430
19431
19432
19433
19434

19435
19436
19437
19438
19439
19440
19441
19442
19443
19444
19445
19446
19447
19448
19449
19450
19451
19452
19453
19454
19455
19456
19457
19458
SQLITE_PRIVATE void sqlite3ExprIfTrue(Parse*, Expr*, int, int);
SQLITE_PRIVATE void sqlite3ExprIfFalse(Parse*, Expr*, int, int);
SQLITE_PRIVATE void sqlite3ExprIfFalseDup(Parse*, Expr*, int, int);
SQLITE_PRIVATE Table *sqlite3FindTable(sqlite3*,const char*, const char*);
#define LOCATE_VIEW    0x01
#define LOCATE_NOERR   0x02
SQLITE_PRIVATE Table *sqlite3LocateTable(Parse*,u32 flags,const char*, const char*);

SQLITE_PRIVATE Table *sqlite3LocateTableItem(Parse*,u32 flags,SrcItem *);
SQLITE_PRIVATE Index *sqlite3FindIndex(sqlite3*,const char*, const char*);
SQLITE_PRIVATE void sqlite3UnlinkAndDeleteTable(sqlite3*,int,const char*);
SQLITE_PRIVATE void sqlite3UnlinkAndDeleteIndex(sqlite3*,int,const char*);
SQLITE_PRIVATE void sqlite3Vacuum(Parse*,Token*,Expr*);
SQLITE_PRIVATE int sqlite3RunVacuum(char**, sqlite3*, int, sqlite3_value*);
SQLITE_PRIVATE char *sqlite3NameFromToken(sqlite3*, const Token*);
SQLITE_PRIVATE int sqlite3ExprCompare(const Parse*,const Expr*,const Expr*, int);
SQLITE_PRIVATE int sqlite3ExprCompareSkip(Expr*,Expr*,int);
SQLITE_PRIVATE int sqlite3ExprListCompare(const ExprList*,const ExprList*, int);
SQLITE_PRIVATE int sqlite3ExprImpliesExpr(const Parse*,const Expr*,const Expr*, int);
SQLITE_PRIVATE int sqlite3ExprImpliesNonNullRow(Expr*,int);
SQLITE_PRIVATE void sqlite3AggInfoPersistWalkerInit(Walker*,Parse*);
SQLITE_PRIVATE void sqlite3ExprAnalyzeAggregates(NameContext*, Expr*);
SQLITE_PRIVATE void sqlite3ExprAnalyzeAggList(NameContext*,ExprList*);
SQLITE_PRIVATE int sqlite3ExprCoveredByIndex(Expr*, int iCur, Index *pIdx);
SQLITE_PRIVATE int sqlite3FunctionUsesThisSrc(Expr*, SrcList*);
SQLITE_PRIVATE Vdbe *sqlite3GetVdbe(Parse*);
#ifndef SQLITE_UNTESTABLE
SQLITE_PRIVATE void sqlite3PrngSaveState(void);
SQLITE_PRIVATE void sqlite3PrngRestoreState(void);
#endif
SQLITE_PRIVATE void sqlite3RollbackAll(sqlite3*,int);
SQLITE_PRIVATE void sqlite3CodeVerifySchema(Parse*, int);







>
















|







19569
19570
19571
19572
19573
19574
19575
19576
19577
19578
19579
19580
19581
19582
19583
19584
19585
19586
19587
19588
19589
19590
19591
19592
19593
19594
19595
19596
19597
19598
19599
19600
SQLITE_PRIVATE void sqlite3ExprIfTrue(Parse*, Expr*, int, int);
SQLITE_PRIVATE void sqlite3ExprIfFalse(Parse*, Expr*, int, int);
SQLITE_PRIVATE void sqlite3ExprIfFalseDup(Parse*, Expr*, int, int);
SQLITE_PRIVATE Table *sqlite3FindTable(sqlite3*,const char*, const char*);
#define LOCATE_VIEW    0x01
#define LOCATE_NOERR   0x02
SQLITE_PRIVATE Table *sqlite3LocateTable(Parse*,u32 flags,const char*, const char*);
SQLITE_PRIVATE const char *sqlite3PreferredTableName(const char*);
SQLITE_PRIVATE Table *sqlite3LocateTableItem(Parse*,u32 flags,SrcItem *);
SQLITE_PRIVATE Index *sqlite3FindIndex(sqlite3*,const char*, const char*);
SQLITE_PRIVATE void sqlite3UnlinkAndDeleteTable(sqlite3*,int,const char*);
SQLITE_PRIVATE void sqlite3UnlinkAndDeleteIndex(sqlite3*,int,const char*);
SQLITE_PRIVATE void sqlite3Vacuum(Parse*,Token*,Expr*);
SQLITE_PRIVATE int sqlite3RunVacuum(char**, sqlite3*, int, sqlite3_value*);
SQLITE_PRIVATE char *sqlite3NameFromToken(sqlite3*, const Token*);
SQLITE_PRIVATE int sqlite3ExprCompare(const Parse*,const Expr*,const Expr*, int);
SQLITE_PRIVATE int sqlite3ExprCompareSkip(Expr*,Expr*,int);
SQLITE_PRIVATE int sqlite3ExprListCompare(const ExprList*,const ExprList*, int);
SQLITE_PRIVATE int sqlite3ExprImpliesExpr(const Parse*,const Expr*,const Expr*, int);
SQLITE_PRIVATE int sqlite3ExprImpliesNonNullRow(Expr*,int);
SQLITE_PRIVATE void sqlite3AggInfoPersistWalkerInit(Walker*,Parse*);
SQLITE_PRIVATE void sqlite3ExprAnalyzeAggregates(NameContext*, Expr*);
SQLITE_PRIVATE void sqlite3ExprAnalyzeAggList(NameContext*,ExprList*);
SQLITE_PRIVATE int sqlite3ExprCoveredByIndex(Expr*, int iCur, Index *pIdx);
SQLITE_PRIVATE int sqlite3ReferencesSrcList(Parse*, Expr*, SrcList*);
SQLITE_PRIVATE Vdbe *sqlite3GetVdbe(Parse*);
#ifndef SQLITE_UNTESTABLE
SQLITE_PRIVATE void sqlite3PrngSaveState(void);
SQLITE_PRIVATE void sqlite3PrngRestoreState(void);
#endif
SQLITE_PRIVATE void sqlite3RollbackAll(sqlite3*,int);
SQLITE_PRIVATE void sqlite3CodeVerifySchema(Parse*, int);
19594
19595
19596
19597
19598
19599
19600
19601
19602
19603
19604
19605
19606
19607
19608
19609
19610
19611
19612
19613
19614
19615
#ifndef SQLITE_OMIT_UTF16
SQLITE_PRIVATE int sqlite3Utf16ByteLen(const void *pData, int nChar);
#endif
SQLITE_PRIVATE int sqlite3Utf8CharLen(const char *pData, int nByte);
SQLITE_PRIVATE u32 sqlite3Utf8Read(const u8**);
SQLITE_PRIVATE LogEst sqlite3LogEst(u64);
SQLITE_PRIVATE LogEst sqlite3LogEstAdd(LogEst,LogEst);
#ifndef SQLITE_OMIT_VIRTUALTABLE
SQLITE_PRIVATE LogEst sqlite3LogEstFromDouble(double);
#endif
#if defined(SQLITE_ENABLE_STMT_SCANSTATUS) || \
    defined(SQLITE_ENABLE_STAT4) || \
    defined(SQLITE_EXPLAIN_ESTIMATED_ROWS)
SQLITE_PRIVATE u64 sqlite3LogEstToInt(LogEst);
#endif
SQLITE_PRIVATE VList *sqlite3VListAdd(sqlite3*,VList*,const char*,int,int);
SQLITE_PRIVATE const char *sqlite3VListNumToName(VList*,int);
SQLITE_PRIVATE int sqlite3VListNameToNum(VList*,const char*,int);

/*
** Routines to read and write variable-length integers.  These used to
** be defined locally, but now we use the varint routines in the util.c







<

<
<
<
<

<







19736
19737
19738
19739
19740
19741
19742

19743




19744

19745
19746
19747
19748
19749
19750
19751
#ifndef SQLITE_OMIT_UTF16
SQLITE_PRIVATE int sqlite3Utf16ByteLen(const void *pData, int nChar);
#endif
SQLITE_PRIVATE int sqlite3Utf8CharLen(const char *pData, int nByte);
SQLITE_PRIVATE u32 sqlite3Utf8Read(const u8**);
SQLITE_PRIVATE LogEst sqlite3LogEst(u64);
SQLITE_PRIVATE LogEst sqlite3LogEstAdd(LogEst,LogEst);

SQLITE_PRIVATE LogEst sqlite3LogEstFromDouble(double);




SQLITE_PRIVATE u64 sqlite3LogEstToInt(LogEst);

SQLITE_PRIVATE VList *sqlite3VListAdd(sqlite3*,VList*,const char*,int,int);
SQLITE_PRIVATE const char *sqlite3VListNumToName(VList*,int);
SQLITE_PRIVATE int sqlite3VListNameToNum(VList*,const char*,int);

/*
** Routines to read and write variable-length integers.  These used to
** be defined locally, but now we use the varint routines in the util.c
19886
19887
19888
19889
19890
19891
19892

19893
19894
19895

19896
19897
19898
19899
19900
19901
19902
   );
#  define sqlite3VtabInSync(db) ((db)->nVTrans>0 && (db)->aVTrans==0)
#endif
SQLITE_PRIVATE int sqlite3ReadOnlyShadowTables(sqlite3 *db);
#ifndef SQLITE_OMIT_VIRTUALTABLE
SQLITE_PRIVATE   int sqlite3ShadowTableName(sqlite3 *db, const char *zName);
SQLITE_PRIVATE   int sqlite3IsShadowTableOf(sqlite3*,Table*,const char*);

#else
# define sqlite3ShadowTableName(A,B) 0
# define sqlite3IsShadowTableOf(A,B,C) 0

#endif
SQLITE_PRIVATE int sqlite3VtabEponymousTableInit(Parse*,Module*);
SQLITE_PRIVATE void sqlite3VtabEponymousTableClear(sqlite3*,Module*);
SQLITE_PRIVATE void sqlite3VtabMakeWritable(Parse*,Table*);
SQLITE_PRIVATE void sqlite3VtabBeginParse(Parse*, Token*, Token*, Token*, int);
SQLITE_PRIVATE void sqlite3VtabFinishParse(Parse*, Token*);
SQLITE_PRIVATE void sqlite3VtabArgInit(Parse*);







>



>







20022
20023
20024
20025
20026
20027
20028
20029
20030
20031
20032
20033
20034
20035
20036
20037
20038
20039
20040
   );
#  define sqlite3VtabInSync(db) ((db)->nVTrans>0 && (db)->aVTrans==0)
#endif
SQLITE_PRIVATE int sqlite3ReadOnlyShadowTables(sqlite3 *db);
#ifndef SQLITE_OMIT_VIRTUALTABLE
SQLITE_PRIVATE   int sqlite3ShadowTableName(sqlite3 *db, const char *zName);
SQLITE_PRIVATE   int sqlite3IsShadowTableOf(sqlite3*,Table*,const char*);
SQLITE_PRIVATE   void sqlite3MarkAllShadowTablesOf(sqlite3*, Table*);
#else
# define sqlite3ShadowTableName(A,B) 0
# define sqlite3IsShadowTableOf(A,B,C) 0
# define sqlite3MarkAllShadowTablesOf(A,B)
#endif
SQLITE_PRIVATE int sqlite3VtabEponymousTableInit(Parse*,Module*);
SQLITE_PRIVATE void sqlite3VtabEponymousTableClear(sqlite3*,Module*);
SQLITE_PRIVATE void sqlite3VtabMakeWritable(Parse*,Table*);
SQLITE_PRIVATE void sqlite3VtabBeginParse(Parse*, Token*, Token*, Token*, int);
SQLITE_PRIVATE void sqlite3VtabFinishParse(Parse*, Token*);
SQLITE_PRIVATE void sqlite3VtabArgInit(Parse*);
19931
19932
19933
19934
19935
19936
19937
19938
19939
19940
19941
19942
19943
19944
19945
SQLITE_PRIVATE   void sqlite3WithDelete(sqlite3*,With*);
SQLITE_PRIVATE   With *sqlite3WithPush(Parse*, With*, u8);
#else
# define sqlite3CteNew(P,T,E,S)   ((void*)0)
# define sqlite3CteDelete(D,C)
# define sqlite3CteWithAdd(P,W,C) ((void*)0)
# define sqlite3WithDelete(x,y)
# define sqlite3WithPush(x,y,z)
#endif
#ifndef SQLITE_OMIT_UPSERT
SQLITE_PRIVATE   Upsert *sqlite3UpsertNew(sqlite3*,ExprList*,Expr*,ExprList*,Expr*,Upsert*);
SQLITE_PRIVATE   void sqlite3UpsertDelete(sqlite3*,Upsert*);
SQLITE_PRIVATE   Upsert *sqlite3UpsertDup(sqlite3*,Upsert*);
SQLITE_PRIVATE   int sqlite3UpsertAnalyzeTarget(Parse*,SrcList*,Upsert*);
SQLITE_PRIVATE   void sqlite3UpsertDoUpdate(Parse*,Upsert*,Table*,Index*,int);







|







20069
20070
20071
20072
20073
20074
20075
20076
20077
20078
20079
20080
20081
20082
20083
SQLITE_PRIVATE   void sqlite3WithDelete(sqlite3*,With*);
SQLITE_PRIVATE   With *sqlite3WithPush(Parse*, With*, u8);
#else
# define sqlite3CteNew(P,T,E,S)   ((void*)0)
# define sqlite3CteDelete(D,C)
# define sqlite3CteWithAdd(P,W,C) ((void*)0)
# define sqlite3WithDelete(x,y)
# define sqlite3WithPush(x,y,z) ((void*)0)
#endif
#ifndef SQLITE_OMIT_UPSERT
SQLITE_PRIVATE   Upsert *sqlite3UpsertNew(sqlite3*,ExprList*,Expr*,ExprList*,Expr*,Upsert*);
SQLITE_PRIVATE   void sqlite3UpsertDelete(sqlite3*,Upsert*);
SQLITE_PRIVATE   Upsert *sqlite3UpsertDup(sqlite3*,Upsert*);
SQLITE_PRIVATE   int sqlite3UpsertAnalyzeTarget(Parse*,SrcList*,Upsert*);
SQLITE_PRIVATE   void sqlite3UpsertDoUpdate(Parse*,Upsert*,Table*,Index*,int);
20099
20100
20101
20102
20103
20104
20105
20106
20107
20108
20109
20110
20111
20112
20113
20114
** this constraint.
**
** All of this is no-op for a production build.  It only comes into
** play when the SQLITE_MEMDEBUG compile-time option is used.
*/
#ifdef SQLITE_MEMDEBUG
SQLITE_PRIVATE   void sqlite3MemdebugSetType(void*,u8);
SQLITE_PRIVATE   int sqlite3MemdebugHasType(void*,u8);
SQLITE_PRIVATE   int sqlite3MemdebugNoType(void*,u8);
#else
# define sqlite3MemdebugSetType(X,Y)  /* no-op */
# define sqlite3MemdebugHasType(X,Y)  1
# define sqlite3MemdebugNoType(X,Y)   1
#endif
#define MEMTYPE_HEAP       0x01  /* General heap allocations */
#define MEMTYPE_LOOKASIDE  0x02  /* Heap that might have been lookaside */







|
|







20237
20238
20239
20240
20241
20242
20243
20244
20245
20246
20247
20248
20249
20250
20251
20252
** this constraint.
**
** All of this is no-op for a production build.  It only comes into
** play when the SQLITE_MEMDEBUG compile-time option is used.
*/
#ifdef SQLITE_MEMDEBUG
SQLITE_PRIVATE   void sqlite3MemdebugSetType(void*,u8);
SQLITE_PRIVATE   int sqlite3MemdebugHasType(const void*,u8);
SQLITE_PRIVATE   int sqlite3MemdebugNoType(const void*,u8);
#else
# define sqlite3MemdebugSetType(X,Y)  /* no-op */
# define sqlite3MemdebugHasType(X,Y)  1
# define sqlite3MemdebugNoType(X,Y)   1
#endif
#define MEMTYPE_HEAP       0x01  /* General heap allocations */
#define MEMTYPE_LOOKASIDE  0x02  /* Heap that might have been lookaside */
21423
21424
21425
21426
21427
21428
21429












21430
21431
21432
21433
21434
21435
21436
/*
** Hash table for global functions - functions common to all
** database connections.  After initialization, this table is
** read-only.
*/
SQLITE_PRIVATE FuncDefHash sqlite3BuiltinFunctions;













#ifdef VDBE_PROFILE
/*
** The following performance counter can be used in place of
** sqlite3Hwtime() for profiling.  This is a no-op on standard builds.
*/
SQLITE_PRIVATE sqlite3_uint64 sqlite3NProfileCnt = 0;
#endif







>
>
>
>
>
>
>
>
>
>
>
>







21561
21562
21563
21564
21565
21566
21567
21568
21569
21570
21571
21572
21573
21574
21575
21576
21577
21578
21579
21580
21581
21582
21583
21584
21585
21586
/*
** Hash table for global functions - functions common to all
** database connections.  After initialization, this table is
** read-only.
*/
SQLITE_PRIVATE FuncDefHash sqlite3BuiltinFunctions;

#if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_DEBUG)
/*
** Counter used for coverage testing.  Does not come into play for
** release builds.
**
** Access to this global variable is not mutex protected.  This might
** result in TSAN warnings.  But as the variable does not exist in
** release builds, that should not be a concern.
*/
SQLITE_PRIVATE unsigned int sqlite3CoverageCounter;
#endif /* SQLITE_COVERAGE_TEST || SQLITE_DEBUG */

#ifdef VDBE_PROFILE
/*
** The following performance counter can be used in place of
** sqlite3Hwtime() for profiling.  This is a no-op on standard builds.
*/
SQLITE_PRIVATE sqlite3_uint64 sqlite3NProfileCnt = 0;
#endif
21967
21968
21969
21970
21971
21972
21973
21974
21975
21976
21977
21978
21979
21980
21981
  bft changeCntOn:1;      /* True to update the change-counter */
  bft runOnlyOnce:1;      /* Automatically expire on reset */
  bft usesStmtJournal:1;  /* True if uses a statement journal */
  bft readOnly:1;         /* True for statements that do not write */
  bft bIsReader:1;        /* True for statements that read */
  yDbMask btreeMask;      /* Bitmask of db->aDb[] entries referenced */
  yDbMask lockMask;       /* Subset of btreeMask that requires a lock */
  u32 aCounter[7];        /* Counters used by sqlite3_stmt_status() */
  char *zSql;             /* Text of the SQL statement that generated this */
#ifdef SQLITE_ENABLE_NORMALIZE
  char *zNormSql;         /* Normalization of the associated SQL statement */
  DblquoteStr *pDblStr;   /* List of double-quoted string literals */
#endif
  void *pFree;            /* Free this when deleting the vdbe */
  VdbeFrame *pFrame;      /* Parent frame */







|







22117
22118
22119
22120
22121
22122
22123
22124
22125
22126
22127
22128
22129
22130
22131
  bft changeCntOn:1;      /* True to update the change-counter */
  bft runOnlyOnce:1;      /* Automatically expire on reset */
  bft usesStmtJournal:1;  /* True if uses a statement journal */
  bft readOnly:1;         /* True for statements that do not write */
  bft bIsReader:1;        /* True for statements that read */
  yDbMask btreeMask;      /* Bitmask of db->aDb[] entries referenced */
  yDbMask lockMask;       /* Subset of btreeMask that requires a lock */
  u32 aCounter[9];        /* Counters used by sqlite3_stmt_status() */
  char *zSql;             /* Text of the SQL statement that generated this */
#ifdef SQLITE_ENABLE_NORMALIZE
  char *zNormSql;         /* Normalization of the associated SQL statement */
  DblquoteStr *pDblStr;   /* List of double-quoted string literals */
#endif
  void *pFree;            /* Free this when deleting the vdbe */
  VdbeFrame *pFrame;      /* Parent frame */
22063
22064
22065
22066
22067
22068
22069

22070



22071
22072
22073
22074
22075
22076
22077
22078
22079
22080
22081
22082
22083
22084
22085
# define sqlite3VdbeMemSetDouble sqlite3VdbeMemSetInt64
#else
SQLITE_PRIVATE   void sqlite3VdbeMemSetDouble(Mem*, double);
#endif
SQLITE_PRIVATE void sqlite3VdbeMemSetPointer(Mem*, void*, const char*, void(*)(void*));
SQLITE_PRIVATE void sqlite3VdbeMemInit(Mem*,sqlite3*,u16);
SQLITE_PRIVATE void sqlite3VdbeMemSetNull(Mem*);

SQLITE_PRIVATE void sqlite3VdbeMemSetZeroBlob(Mem*,int);



#ifdef SQLITE_DEBUG
SQLITE_PRIVATE int sqlite3VdbeMemIsRowSet(const Mem*);
#endif
SQLITE_PRIVATE int sqlite3VdbeMemSetRowSet(Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemMakeWriteable(Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemStringify(Mem*, u8, u8);
SQLITE_PRIVATE int sqlite3IntFloatCompare(i64,double);
SQLITE_PRIVATE i64 sqlite3VdbeIntValue(Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemIntegerify(Mem*);
SQLITE_PRIVATE double sqlite3VdbeRealValue(Mem*);
SQLITE_PRIVATE int sqlite3VdbeBooleanValue(Mem*, int ifNull);
SQLITE_PRIVATE void sqlite3VdbeIntegerAffinity(Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemRealify(Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemNumerify(Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemCast(Mem*,u8,u8);







>

>
>
>







|







22213
22214
22215
22216
22217
22218
22219
22220
22221
22222
22223
22224
22225
22226
22227
22228
22229
22230
22231
22232
22233
22234
22235
22236
22237
22238
22239
# define sqlite3VdbeMemSetDouble sqlite3VdbeMemSetInt64
#else
SQLITE_PRIVATE   void sqlite3VdbeMemSetDouble(Mem*, double);
#endif
SQLITE_PRIVATE void sqlite3VdbeMemSetPointer(Mem*, void*, const char*, void(*)(void*));
SQLITE_PRIVATE void sqlite3VdbeMemInit(Mem*,sqlite3*,u16);
SQLITE_PRIVATE void sqlite3VdbeMemSetNull(Mem*);
#ifndef SQLITE_OMIT_INCRBLOB
SQLITE_PRIVATE void sqlite3VdbeMemSetZeroBlob(Mem*,int);
#else
SQLITE_PRIVATE int sqlite3VdbeMemSetZeroBlob(Mem*,int);
#endif
#ifdef SQLITE_DEBUG
SQLITE_PRIVATE int sqlite3VdbeMemIsRowSet(const Mem*);
#endif
SQLITE_PRIVATE int sqlite3VdbeMemSetRowSet(Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemMakeWriteable(Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemStringify(Mem*, u8, u8);
SQLITE_PRIVATE int sqlite3IntFloatCompare(i64,double);
SQLITE_PRIVATE i64 sqlite3VdbeIntValue(const Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemIntegerify(Mem*);
SQLITE_PRIVATE double sqlite3VdbeRealValue(Mem*);
SQLITE_PRIVATE int sqlite3VdbeBooleanValue(Mem*, int ifNull);
SQLITE_PRIVATE void sqlite3VdbeIntegerAffinity(Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemRealify(Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemNumerify(Mem*);
SQLITE_PRIVATE int sqlite3VdbeMemCast(Mem*,u8,u8);
23069
23070
23071
23072
23073
23074
23075

23076

23077
23078
23079
23080
23081
23082
23083
#endif
  sqlite3_mutex_enter(mutex);
  pX = localtime(t);
#ifndef SQLITE_UNTESTABLE
  if( sqlite3GlobalConfig.bLocaltimeFault ) pX = 0;
#endif
  if( pX ) *pTm = *pX;

  sqlite3_mutex_leave(mutex);

  rc = pX==0;
#else
#ifndef SQLITE_UNTESTABLE
  if( sqlite3GlobalConfig.bLocaltimeFault ) return 1;
#endif
#if HAVE_LOCALTIME_R
  rc = localtime_r(t, pTm)==0;







>

>







23223
23224
23225
23226
23227
23228
23229
23230
23231
23232
23233
23234
23235
23236
23237
23238
23239
#endif
  sqlite3_mutex_enter(mutex);
  pX = localtime(t);
#ifndef SQLITE_UNTESTABLE
  if( sqlite3GlobalConfig.bLocaltimeFault ) pX = 0;
#endif
  if( pX ) *pTm = *pX;
#if SQLITE_THREADSAFE>0
  sqlite3_mutex_leave(mutex);
#endif
  rc = pX==0;
#else
#ifndef SQLITE_UNTESTABLE
  if( sqlite3GlobalConfig.bLocaltimeFault ) return 1;
#endif
#if HAVE_LOCALTIME_R
  rc = localtime_r(t, pTm)==0;
23208
23209
23210
23211
23212
23213
23214







































23215
23216
23217
23218
23219
23220
23221
  const char *z,              /* The text of the modifier */
  int n,                      /* Length of zMod in bytes */
  DateTime *p                 /* The date/time value to be modified */
){
  int rc = 1;
  double r;
  switch(sqlite3UpperToLower[(u8)z[0]] ){







































#ifndef SQLITE_OMIT_LOCALTIME
    case 'l': {
      /*    localtime
      **
      ** Assuming the current time value is UTC (a.k.a. GMT), shift it to
      ** show local time.
      */







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







23364
23365
23366
23367
23368
23369
23370
23371
23372
23373
23374
23375
23376
23377
23378
23379
23380
23381
23382
23383
23384
23385
23386
23387
23388
23389
23390
23391
23392
23393
23394
23395
23396
23397
23398
23399
23400
23401
23402
23403
23404
23405
23406
23407
23408
23409
23410
23411
23412
23413
23414
23415
23416
  const char *z,              /* The text of the modifier */
  int n,                      /* Length of zMod in bytes */
  DateTime *p                 /* The date/time value to be modified */
){
  int rc = 1;
  double r;
  switch(sqlite3UpperToLower[(u8)z[0]] ){
    case 'a': {
      /*
      **    auto
      **
      ** If rawS is available, then interpret as a julian day number, or
      ** a unix timestamp, depending on its magnitude.
      */
      if( sqlite3_stricmp(z, "auto")==0 ){
        if( !p->rawS || p->validJD ){
          rc = 0;
          p->rawS = 0;
        }else if( p->s>=-210866760000 && p->s<=253402300799 ){
          r = p->s*1000.0 + 210866760000000.0;
          clearYMD_HMS_TZ(p);
          p->iJD = (sqlite3_int64)(r + 0.5);
          p->validJD = 1;
          p->rawS = 0;
          rc = 0;
        }
      }
      break;
    }
    case 'j': {
      /*
      **    julianday
      **
      ** Always interpret the prior number as a julian-day value.  If this
      ** is not the first modifier, or if the prior argument is not a numeric
      ** value in the allowed range of julian day numbers understood by
      ** SQLite (0..5373484.5) then the result will be NULL.
      */
      if( sqlite3_stricmp(z, "julianday")==0 ){
        if( p->validJD && p->rawS ){
          rc = 0;
          p->rawS = 0;
        }
      }
      break;
    }
#ifndef SQLITE_OMIT_LOCALTIME
    case 'l': {
      /*    localtime
      **
      ** Assuming the current time value is UTC (a.k.a. GMT), shift it to
      ** show local time.
      */
23471
23472
23473
23474
23475
23476
23477


















23478
23479
23480
23481
23482
23483
23484
){
  DateTime x;
  if( isDate(context, argc, argv, &x)==0 ){
    computeJD(&x);
    sqlite3_result_double(context, x.iJD/86400000.0);
  }
}



















/*
**    datetime( TIMESTRING, MOD, MOD, ...)
**
** Return YYYY-MM-DD HH:MM:SS
*/
static void datetimeFunc(







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







23666
23667
23668
23669
23670
23671
23672
23673
23674
23675
23676
23677
23678
23679
23680
23681
23682
23683
23684
23685
23686
23687
23688
23689
23690
23691
23692
23693
23694
23695
23696
23697
){
  DateTime x;
  if( isDate(context, argc, argv, &x)==0 ){
    computeJD(&x);
    sqlite3_result_double(context, x.iJD/86400000.0);
  }
}

/*
**    unixepoch( TIMESTRING, MOD, MOD, ...)
**
** Return the number of seconds (including fractional seconds) since
** the unix epoch of 1970-01-01 00:00:00 GMT.
*/
static void unixepochFunc(
  sqlite3_context *context,
  int argc,
  sqlite3_value **argv
){
  DateTime x;
  if( isDate(context, argc, argv, &x)==0 ){
    computeJD(&x);
    sqlite3_result_int64(context, x.iJD/1000 - 21086676*(i64)10000);
  }
}

/*
**    datetime( TIMESTRING, MOD, MOD, ...)
**
** Return YYYY-MM-DD HH:MM:SS
*/
static void datetimeFunc(
23571
23572
23573
23574
23575
23576
23577
23578
23579
23580
23581
23582
23583
23584
23585
  db = sqlite3_context_db_handle(context);
  sqlite3StrAccumInit(&sRes, 0, 0, 0, db->aLimit[SQLITE_LIMIT_LENGTH]);

  computeJD(&x);
  computeYMD_HMS(&x);
  for(i=j=0; zFmt[i]; i++){
    if( zFmt[i]!='%' ) continue;
    if( j<i ) sqlite3_str_append(&sRes, zFmt+j, i-j);
    i++;
    j = i + 1;
    switch( zFmt[i] ){
      case 'd': {
        sqlite3_str_appendf(&sRes, "%02d", x.D);
        break;
      }







|







23784
23785
23786
23787
23788
23789
23790
23791
23792
23793
23794
23795
23796
23797
23798
  db = sqlite3_context_db_handle(context);
  sqlite3StrAccumInit(&sRes, 0, 0, 0, db->aLimit[SQLITE_LIMIT_LENGTH]);

  computeJD(&x);
  computeYMD_HMS(&x);
  for(i=j=0; zFmt[i]; i++){
    if( zFmt[i]!='%' ) continue;
    if( j<i ) sqlite3_str_append(&sRes, zFmt+j, (int)(i-j));
    i++;
    j = i + 1;
    switch( zFmt[i] ){
      case 'd': {
        sqlite3_str_appendf(&sRes, "%02d", x.D);
        break;
      }
23647
23648
23649
23650
23651
23652
23653
23654
23655
23656
23657
23658
23659
23660
23661
      }
      default: {
        sqlite3_str_reset(&sRes);
        return;
      }
    }
  }
  if( j<i ) sqlite3_str_append(&sRes, zFmt+j, i-j);
  sqlite3ResultStrAccum(context, &sRes);
}

/*
** current_time()
**
** This function returns the same value as time('now').







|







23860
23861
23862
23863
23864
23865
23866
23867
23868
23869
23870
23871
23872
23873
23874
      }
      default: {
        sqlite3_str_reset(&sRes);
        return;
      }
    }
  }
  if( j<i ) sqlite3_str_append(&sRes, zFmt+j, (int)(i-j));
  sqlite3ResultStrAccum(context, &sRes);
}

/*
** current_time()
**
** This function returns the same value as time('now').
23748
23749
23750
23751
23752
23753
23754

23755
23756
23757
23758
23759
23760
23761
** functions.  This should be the only routine in this file with
** external linkage.
*/
SQLITE_PRIVATE void sqlite3RegisterDateTimeFunctions(void){
  static FuncDef aDateTimeFuncs[] = {
#ifndef SQLITE_OMIT_DATETIME_FUNCS
    PURE_DATE(julianday,        -1, 0, 0, juliandayFunc ),

    PURE_DATE(date,             -1, 0, 0, dateFunc      ),
    PURE_DATE(time,             -1, 0, 0, timeFunc      ),
    PURE_DATE(datetime,         -1, 0, 0, datetimeFunc  ),
    PURE_DATE(strftime,         -1, 0, 0, strftimeFunc  ),
    DFUNCTION(current_time,      0, 0, 0, ctimeFunc     ),
    DFUNCTION(current_timestamp, 0, 0, 0, ctimestampFunc),
    DFUNCTION(current_date,      0, 0, 0, cdateFunc     ),







>







23961
23962
23963
23964
23965
23966
23967
23968
23969
23970
23971
23972
23973
23974
23975
** functions.  This should be the only routine in this file with
** external linkage.
*/
SQLITE_PRIVATE void sqlite3RegisterDateTimeFunctions(void){
  static FuncDef aDateTimeFuncs[] = {
#ifndef SQLITE_OMIT_DATETIME_FUNCS
    PURE_DATE(julianday,        -1, 0, 0, juliandayFunc ),
    PURE_DATE(unixepoch,        -1, 0, 0, unixepochFunc ),
    PURE_DATE(date,             -1, 0, 0, dateFunc      ),
    PURE_DATE(time,             -1, 0, 0, timeFunc      ),
    PURE_DATE(datetime,         -1, 0, 0, datetimeFunc  ),
    PURE_DATE(strftime,         -1, 0, 0, strftimeFunc  ),
    DFUNCTION(current_time,      0, 0, 0, ctimeFunc     ),
    DFUNCTION(current_timestamp, 0, 0, 0, ctimestampFunc),
    DFUNCTION(current_date,      0, 0, 0, cdateFunc     ),
24084
24085
24086
24087
24088
24089
24090

24091
24092
24093
24094

24095
24096

24097
24098
24099
24100
24101
24102
24103
  int rc;
  sqlite3_file *pFile;
  pFile = (sqlite3_file *)sqlite3MallocZero(pVfs->szOsFile);
  if( pFile ){
    rc = sqlite3OsOpen(pVfs, zFile, pFile, flags, pOutFlags);
    if( rc!=SQLITE_OK ){
      sqlite3_free(pFile);

    }else{
      *ppFile = pFile;
    }
  }else{

    rc = SQLITE_NOMEM_BKPT;
  }

  return rc;
}
SQLITE_PRIVATE void sqlite3OsCloseFree(sqlite3_file *pFile){
  assert( pFile );
  sqlite3OsClose(pFile);
  sqlite3_free(pFile);
}







>




>


>







24298
24299
24300
24301
24302
24303
24304
24305
24306
24307
24308
24309
24310
24311
24312
24313
24314
24315
24316
24317
24318
24319
24320
  int rc;
  sqlite3_file *pFile;
  pFile = (sqlite3_file *)sqlite3MallocZero(pVfs->szOsFile);
  if( pFile ){
    rc = sqlite3OsOpen(pVfs, zFile, pFile, flags, pOutFlags);
    if( rc!=SQLITE_OK ){
      sqlite3_free(pFile);
      *ppFile = 0;
    }else{
      *ppFile = pFile;
    }
  }else{
    *ppFile = 0;
    rc = SQLITE_NOMEM_BKPT;
  }
  assert( *ppFile!=0 || rc!=SQLITE_OK );
  return rc;
}
SQLITE_PRIVATE void sqlite3OsCloseFree(sqlite3_file *pFile){
  assert( pFile );
  sqlite3OsClose(pFile);
  sqlite3_free(pFile);
}
24807
24808
24809
24810
24811
24812
24813
24814
24815
24816
24817
24818
24819
24820
24821

/*
** Given an allocation, find the MemBlockHdr for that allocation.
**
** This routine checks the guards at either end of the allocation and
** if they are incorrect it asserts.
*/
static struct MemBlockHdr *sqlite3MemsysGetHeader(void *pAllocation){
  struct MemBlockHdr *p;
  int *pInt;
  u8 *pU8;
  int nReserve;

  p = (struct MemBlockHdr*)pAllocation;
  p--;







|







25024
25025
25026
25027
25028
25029
25030
25031
25032
25033
25034
25035
25036
25037
25038

/*
** Given an allocation, find the MemBlockHdr for that allocation.
**
** This routine checks the guards at either end of the allocation and
** if they are incorrect it asserts.
*/
static struct MemBlockHdr *sqlite3MemsysGetHeader(const void *pAllocation){
  struct MemBlockHdr *p;
  int *pInt;
  u8 *pU8;
  int nReserve;

  p = (struct MemBlockHdr*)pAllocation;
  p--;
25054
25055
25056
25057
25058
25059
25060
25061
25062
25063
25064
25065
25066
25067
25068
** allocation p.  Also return true if p==NULL.
**
** This routine is designed for use within an assert() statement, to
** verify the type of an allocation.  For example:
**
**     assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) );
*/
SQLITE_PRIVATE int sqlite3MemdebugHasType(void *p, u8 eType){
  int rc = 1;
  if( p && sqlite3GlobalConfig.m.xFree==sqlite3MemFree ){
    struct MemBlockHdr *pHdr;
    pHdr = sqlite3MemsysGetHeader(p);
    assert( pHdr->iForeGuard==FOREGUARD );         /* Allocation is valid */
    if( (pHdr->eType&eType)==0 ){
      rc = 0;







|







25271
25272
25273
25274
25275
25276
25277
25278
25279
25280
25281
25282
25283
25284
25285
** allocation p.  Also return true if p==NULL.
**
** This routine is designed for use within an assert() statement, to
** verify the type of an allocation.  For example:
**
**     assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) );
*/
SQLITE_PRIVATE int sqlite3MemdebugHasType(const void *p, u8 eType){
  int rc = 1;
  if( p && sqlite3GlobalConfig.m.xFree==sqlite3MemFree ){
    struct MemBlockHdr *pHdr;
    pHdr = sqlite3MemsysGetHeader(p);
    assert( pHdr->iForeGuard==FOREGUARD );         /* Allocation is valid */
    if( (pHdr->eType&eType)==0 ){
      rc = 0;
25076
25077
25078
25079
25080
25081
25082
25083
25084
25085
25086
25087
25088
25089
25090
** allocation p.  Also return true if p==NULL.
**
** This routine is designed for use within an assert() statement, to
** verify the type of an allocation.  For example:
**
**     assert( sqlite3MemdebugNoType(p, MEMTYPE_LOOKASIDE) );
*/
SQLITE_PRIVATE int sqlite3MemdebugNoType(void *p, u8 eType){
  int rc = 1;
  if( p && sqlite3GlobalConfig.m.xFree==sqlite3MemFree ){
    struct MemBlockHdr *pHdr;
    pHdr = sqlite3MemsysGetHeader(p);
    assert( pHdr->iForeGuard==FOREGUARD );         /* Allocation is valid */
    if( (pHdr->eType&eType)!=0 ){
      rc = 0;







|







25293
25294
25295
25296
25297
25298
25299
25300
25301
25302
25303
25304
25305
25306
25307
** allocation p.  Also return true if p==NULL.
**
** This routine is designed for use within an assert() statement, to
** verify the type of an allocation.  For example:
**
**     assert( sqlite3MemdebugNoType(p, MEMTYPE_LOOKASIDE) );
*/
SQLITE_PRIVATE int sqlite3MemdebugNoType(const void *p, u8 eType){
  int rc = 1;
  if( p && sqlite3GlobalConfig.m.xFree==sqlite3MemFree ){
    struct MemBlockHdr *pHdr;
    pHdr = sqlite3MemsysGetHeader(p);
    assert( pHdr->iForeGuard==FOREGUARD );         /* Allocation is valid */
    if( (pHdr->eType&eType)!=0 ){
      rc = 0;
30541
30542
30543
30544
30545
30546
30547

30548
30549
30550
30551
30552
30553
30554
30555
30556
30557
30558
30559
30560
30561
30562
30563
30564
30565
30566

30567
30568
30569
30570
30571

30572
30573
30574
30575
30576
30577
30578
30579
30580
30581
30582
30583
30584
30585

30586
30587
30588
30589
30590

30591
30592
30593
30594
30595
30596
30597
30598
30599

30600
30601
30602
30603
30604
30605

30606
30607
30608
30609
30610
30611
30612
          sqlite3_snprintf(sizeof(zOp2),zOp2," op2=0x%02x",pExpr->op2);
        }else{
          zOp2[0] = 0;
        }
        sqlite3TreeViewLine(pView, "COLUMN(%d)%s%s",
                                    pExpr->iColumn, zFlgs, zOp2);
      }else{

        sqlite3TreeViewLine(pView, "{%d:%d} pTab=%p%s",
                        pExpr->iTable, pExpr->iColumn,
                        pExpr->y.pTab, zFlgs);
      }
      if( ExprHasProperty(pExpr, EP_FixedCol) ){
        sqlite3TreeViewExpr(pView, pExpr->pLeft, 0);
      }
      break;
    }
    case TK_INTEGER: {
      if( pExpr->flags & EP_IntValue ){
        sqlite3TreeViewLine(pView, "%d", pExpr->u.iValue);
      }else{
        sqlite3TreeViewLine(pView, "%s", pExpr->u.zToken);
      }
      break;
    }
#ifndef SQLITE_OMIT_FLOATING_POINT
    case TK_FLOAT: {

      sqlite3TreeViewLine(pView,"%s", pExpr->u.zToken);
      break;
    }
#endif
    case TK_STRING: {

      sqlite3TreeViewLine(pView,"%Q", pExpr->u.zToken);
      break;
    }
    case TK_NULL: {
      sqlite3TreeViewLine(pView,"NULL");
      break;
    }
    case TK_TRUEFALSE: {
      sqlite3TreeViewLine(pView,"%s%s",
         sqlite3ExprTruthValue(pExpr) ? "TRUE" : "FALSE", zFlgs);
      break;
    }
#ifndef SQLITE_OMIT_BLOB_LITERAL
    case TK_BLOB: {

      sqlite3TreeViewLine(pView,"%s", pExpr->u.zToken);
      break;
    }
#endif
    case TK_VARIABLE: {

      sqlite3TreeViewLine(pView,"VARIABLE(%s,%d)",
                          pExpr->u.zToken, pExpr->iColumn);
      break;
    }
    case TK_REGISTER: {
      sqlite3TreeViewLine(pView,"REGISTER(%d)", pExpr->iTable);
      break;
    }
    case TK_ID: {

      sqlite3TreeViewLine(pView,"ID \"%w\"", pExpr->u.zToken);
      break;
    }
#ifndef SQLITE_OMIT_CAST
    case TK_CAST: {
      /* Expressions of the form:   CAST(pLeft AS token) */

      sqlite3TreeViewLine(pView,"CAST %Q", pExpr->u.zToken);
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 0);
      break;
    }
#endif /* SQLITE_OMIT_CAST */
    case TK_LT:      zBinOp = "LT";     break;
    case TK_LE:      zBinOp = "LE";     break;







>



















>





>














>





>









>






>







30758
30759
30760
30761
30762
30763
30764
30765
30766
30767
30768
30769
30770
30771
30772
30773
30774
30775
30776
30777
30778
30779
30780
30781
30782
30783
30784
30785
30786
30787
30788
30789
30790
30791
30792
30793
30794
30795
30796
30797
30798
30799
30800
30801
30802
30803
30804
30805
30806
30807
30808
30809
30810
30811
30812
30813
30814
30815
30816
30817
30818
30819
30820
30821
30822
30823
30824
30825
30826
30827
30828
30829
30830
30831
30832
30833
30834
30835
30836
          sqlite3_snprintf(sizeof(zOp2),zOp2," op2=0x%02x",pExpr->op2);
        }else{
          zOp2[0] = 0;
        }
        sqlite3TreeViewLine(pView, "COLUMN(%d)%s%s",
                                    pExpr->iColumn, zFlgs, zOp2);
      }else{
        assert( ExprUseYTab(pExpr) );
        sqlite3TreeViewLine(pView, "{%d:%d} pTab=%p%s",
                        pExpr->iTable, pExpr->iColumn,
                        pExpr->y.pTab, zFlgs);
      }
      if( ExprHasProperty(pExpr, EP_FixedCol) ){
        sqlite3TreeViewExpr(pView, pExpr->pLeft, 0);
      }
      break;
    }
    case TK_INTEGER: {
      if( pExpr->flags & EP_IntValue ){
        sqlite3TreeViewLine(pView, "%d", pExpr->u.iValue);
      }else{
        sqlite3TreeViewLine(pView, "%s", pExpr->u.zToken);
      }
      break;
    }
#ifndef SQLITE_OMIT_FLOATING_POINT
    case TK_FLOAT: {
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      sqlite3TreeViewLine(pView,"%s", pExpr->u.zToken);
      break;
    }
#endif
    case TK_STRING: {
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      sqlite3TreeViewLine(pView,"%Q", pExpr->u.zToken);
      break;
    }
    case TK_NULL: {
      sqlite3TreeViewLine(pView,"NULL");
      break;
    }
    case TK_TRUEFALSE: {
      sqlite3TreeViewLine(pView,"%s%s",
         sqlite3ExprTruthValue(pExpr) ? "TRUE" : "FALSE", zFlgs);
      break;
    }
#ifndef SQLITE_OMIT_BLOB_LITERAL
    case TK_BLOB: {
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      sqlite3TreeViewLine(pView,"%s", pExpr->u.zToken);
      break;
    }
#endif
    case TK_VARIABLE: {
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      sqlite3TreeViewLine(pView,"VARIABLE(%s,%d)",
                          pExpr->u.zToken, pExpr->iColumn);
      break;
    }
    case TK_REGISTER: {
      sqlite3TreeViewLine(pView,"REGISTER(%d)", pExpr->iTable);
      break;
    }
    case TK_ID: {
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      sqlite3TreeViewLine(pView,"ID \"%w\"", pExpr->u.zToken);
      break;
    }
#ifndef SQLITE_OMIT_CAST
    case TK_CAST: {
      /* Expressions of the form:   CAST(pLeft AS token) */
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      sqlite3TreeViewLine(pView,"CAST %Q", pExpr->u.zToken);
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 0);
      break;
    }
#endif /* SQLITE_OMIT_CAST */
    case TK_LT:      zBinOp = "LT";     break;
    case TK_LE:      zBinOp = "LE";     break;
30648
30649
30650
30651
30652
30653
30654

30655
30656
30657
30658
30659
30660
30661
30662
30663
30664
30665

30666
30667
30668
30669
30670
30671
30672
30673
30674
30675
30676
30677
30678
30679
30680

30681
30682
30683
30684
30685
30686
30687

30688
30689
30690
30691
30692
30693
30694
      assert( sqlite3ExprSkipCollate(pExpr->pRight)->op==TK_TRUEFALSE );
      x = (pExpr->op2==TK_ISNOT)*2 + sqlite3ExprTruthValue(pExpr->pRight);
      zUniOp = azOp[x];
      break;
    }

    case TK_SPAN: {

      sqlite3TreeViewLine(pView, "SPAN %Q", pExpr->u.zToken);
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 0);
      break;
    }

    case TK_COLLATE: {
      /* COLLATE operators without the EP_Collate flag are intended to
      ** emulate collation associated with a table column.  These show
      ** up in the treeview output as "SOFT-COLLATE".  Explicit COLLATE
      ** operators that appear in the original SQL always have the
      ** EP_Collate bit set and appear in treeview output as just "COLLATE" */

      sqlite3TreeViewLine(pView, "%sCOLLATE %Q%s",
        !ExprHasProperty(pExpr, EP_Collate) ? "SOFT-" : "",
        pExpr->u.zToken, zFlgs);
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 0);
      break;
    }

    case TK_AGG_FUNCTION:
    case TK_FUNCTION: {
      ExprList *pFarg;       /* List of function arguments */
      Window *pWin;
      if( ExprHasProperty(pExpr, EP_TokenOnly) ){
        pFarg = 0;
        pWin = 0;
      }else{

        pFarg = pExpr->x.pList;
#ifndef SQLITE_OMIT_WINDOWFUNC
        pWin = ExprHasProperty(pExpr, EP_WinFunc) ? pExpr->y.pWin : 0;
#else
        pWin = 0;
#endif
      }

      if( pExpr->op==TK_AGG_FUNCTION ){
        sqlite3TreeViewLine(pView, "AGG_FUNCTION%d %Q%s agg=%d[%d]/%p",
                             pExpr->op2, pExpr->u.zToken, zFlgs,
                             pExpr->pAggInfo ? pExpr->pAggInfo->selId : 0,
                             pExpr->iAgg, pExpr->pAggInfo);
      }else if( pExpr->op2!=0 ){
        const char *zOp2;







>











>















>







>







30872
30873
30874
30875
30876
30877
30878
30879
30880
30881
30882
30883
30884
30885
30886
30887
30888
30889
30890
30891
30892
30893
30894
30895
30896
30897
30898
30899
30900
30901
30902
30903
30904
30905
30906
30907
30908
30909
30910
30911
30912
30913
30914
30915
30916
30917
30918
30919
30920
30921
30922
      assert( sqlite3ExprSkipCollate(pExpr->pRight)->op==TK_TRUEFALSE );
      x = (pExpr->op2==TK_ISNOT)*2 + sqlite3ExprTruthValue(pExpr->pRight);
      zUniOp = azOp[x];
      break;
    }

    case TK_SPAN: {
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      sqlite3TreeViewLine(pView, "SPAN %Q", pExpr->u.zToken);
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 0);
      break;
    }

    case TK_COLLATE: {
      /* COLLATE operators without the EP_Collate flag are intended to
      ** emulate collation associated with a table column.  These show
      ** up in the treeview output as "SOFT-COLLATE".  Explicit COLLATE
      ** operators that appear in the original SQL always have the
      ** EP_Collate bit set and appear in treeview output as just "COLLATE" */
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      sqlite3TreeViewLine(pView, "%sCOLLATE %Q%s",
        !ExprHasProperty(pExpr, EP_Collate) ? "SOFT-" : "",
        pExpr->u.zToken, zFlgs);
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 0);
      break;
    }

    case TK_AGG_FUNCTION:
    case TK_FUNCTION: {
      ExprList *pFarg;       /* List of function arguments */
      Window *pWin;
      if( ExprHasProperty(pExpr, EP_TokenOnly) ){
        pFarg = 0;
        pWin = 0;
      }else{
        assert( ExprUseXList(pExpr) );
        pFarg = pExpr->x.pList;
#ifndef SQLITE_OMIT_WINDOWFUNC
        pWin = ExprHasProperty(pExpr, EP_WinFunc) ? pExpr->y.pWin : 0;
#else
        pWin = 0;
#endif
      }
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      if( pExpr->op==TK_AGG_FUNCTION ){
        sqlite3TreeViewLine(pView, "AGG_FUNCTION%d %Q%s agg=%d[%d]/%p",
                             pExpr->op2, pExpr->u.zToken, zFlgs,
                             pExpr->pAggInfo ? pExpr->pAggInfo->selId : 0,
                             pExpr->iAgg, pExpr->pAggInfo);
      }else if( pExpr->op2!=0 ){
        const char *zOp2;
30712
30713
30714
30715
30716
30717
30718

30719
30720
30721
30722
30723

30724
30725
30726
30727
30728
30729
30730
30731
30732
30733
30734
30735
30736
30737
30738
30739
30740
30741
30742
30743
30744
30745
30746
30747
30748
30749
30750
30751

30752


30753
30754
30755
30756
30757
30758
30759
30760
30761
        sqlite3TreeViewWindow(pView, pWin, 0);
      }
#endif
      break;
    }
#ifndef SQLITE_OMIT_SUBQUERY
    case TK_EXISTS: {

      sqlite3TreeViewLine(pView, "EXISTS-expr flags=0x%x", pExpr->flags);
      sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0);
      break;
    }
    case TK_SELECT: {

      sqlite3TreeViewLine(pView, "subquery-expr flags=0x%x", pExpr->flags);
      sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0);
      break;
    }
    case TK_IN: {
      sqlite3TreeViewLine(pView, "IN flags=0x%x", pExpr->flags);
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 1);
      if( ExprHasProperty(pExpr, EP_xIsSelect) ){
        sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0);
      }else{
        sqlite3TreeViewExprList(pView, pExpr->x.pList, 0, 0);
      }
      break;
    }
#endif /* SQLITE_OMIT_SUBQUERY */

    /*
    **    x BETWEEN y AND z
    **
    ** This is equivalent to
    **
    **    x>=y AND x<=z
    **
    ** X is stored in pExpr->pLeft.
    ** Y is stored in pExpr->pList->a[0].pExpr.
    ** Z is stored in pExpr->pList->a[1].pExpr.
    */
    case TK_BETWEEN: {

      Expr *pX = pExpr->pLeft;


      Expr *pY = pExpr->x.pList->a[0].pExpr;
      Expr *pZ = pExpr->x.pList->a[1].pExpr;
      sqlite3TreeViewLine(pView, "BETWEEN");
      sqlite3TreeViewExpr(pView, pX, 1);
      sqlite3TreeViewExpr(pView, pY, 1);
      sqlite3TreeViewExpr(pView, pZ, 0);
      break;
    }
    case TK_TRIGGER: {







>





>







|




















>
|
>
>
|
|







30940
30941
30942
30943
30944
30945
30946
30947
30948
30949
30950
30951
30952
30953
30954
30955
30956
30957
30958
30959
30960
30961
30962
30963
30964
30965
30966
30967
30968
30969
30970
30971
30972
30973
30974
30975
30976
30977
30978
30979
30980
30981
30982
30983
30984
30985
30986
30987
30988
30989
30990
30991
30992
30993
30994
        sqlite3TreeViewWindow(pView, pWin, 0);
      }
#endif
      break;
    }
#ifndef SQLITE_OMIT_SUBQUERY
    case TK_EXISTS: {
      assert( ExprUseXSelect(pExpr) );
      sqlite3TreeViewLine(pView, "EXISTS-expr flags=0x%x", pExpr->flags);
      sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0);
      break;
    }
    case TK_SELECT: {
      assert( ExprUseXSelect(pExpr) );
      sqlite3TreeViewLine(pView, "subquery-expr flags=0x%x", pExpr->flags);
      sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0);
      break;
    }
    case TK_IN: {
      sqlite3TreeViewLine(pView, "IN flags=0x%x", pExpr->flags);
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 1);
      if( ExprUseXSelect(pExpr) ){
        sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0);
      }else{
        sqlite3TreeViewExprList(pView, pExpr->x.pList, 0, 0);
      }
      break;
    }
#endif /* SQLITE_OMIT_SUBQUERY */

    /*
    **    x BETWEEN y AND z
    **
    ** This is equivalent to
    **
    **    x>=y AND x<=z
    **
    ** X is stored in pExpr->pLeft.
    ** Y is stored in pExpr->pList->a[0].pExpr.
    ** Z is stored in pExpr->pList->a[1].pExpr.
    */
    case TK_BETWEEN: {
      const Expr *pX, *pY, *pZ;
      pX = pExpr->pLeft;
      assert( ExprUseXList(pExpr) );
      assert( pExpr->x.pList->nExpr==2 );
      pY = pExpr->x.pList->a[0].pExpr;
      pZ = pExpr->x.pList->a[1].pExpr;
      sqlite3TreeViewLine(pView, "BETWEEN");
      sqlite3TreeViewExpr(pView, pX, 1);
      sqlite3TreeViewExpr(pView, pY, 1);
      sqlite3TreeViewExpr(pView, pZ, 0);
      break;
    }
    case TK_TRIGGER: {
30769
30770
30771
30772
30773
30774
30775

30776
30777
30778
30779
30780
30781
30782
30783
30784
30785
30786
30787

30788
30789
30790
30791
30792
30793
30794
30795
30796
30797
30798
30799

30800
30801
30802
30803
30804
30805
30806
30807

30808
30809
30810
30811
30812
30813
30814
      sqlite3TreeViewLine(pView, "%s(%d)",
          pExpr->iTable ? "NEW" : "OLD", pExpr->iColumn);
      break;
    }
    case TK_CASE: {
      sqlite3TreeViewLine(pView, "CASE");
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 1);

      sqlite3TreeViewExprList(pView, pExpr->x.pList, 0, 0);
      break;
    }
#ifndef SQLITE_OMIT_TRIGGER
    case TK_RAISE: {
      const char *zType = "unk";
      switch( pExpr->affExpr ){
        case OE_Rollback:   zType = "rollback";  break;
        case OE_Abort:      zType = "abort";     break;
        case OE_Fail:       zType = "fail";      break;
        case OE_Ignore:     zType = "ignore";    break;
      }

      sqlite3TreeViewLine(pView, "RAISE %s(%Q)", zType, pExpr->u.zToken);
      break;
    }
#endif
    case TK_MATCH: {
      sqlite3TreeViewLine(pView, "MATCH {%d:%d}%s",
                          pExpr->iTable, pExpr->iColumn, zFlgs);
      sqlite3TreeViewExpr(pView, pExpr->pRight, 0);
      break;
    }
    case TK_VECTOR: {
      char *z = sqlite3_mprintf("VECTOR%s",zFlgs);

      sqlite3TreeViewBareExprList(pView, pExpr->x.pList, z);
      sqlite3_free(z);
      break;
    }
    case TK_SELECT_COLUMN: {
      sqlite3TreeViewLine(pView, "SELECT-COLUMN %d of [0..%d]%s",
              pExpr->iColumn, pExpr->iTable-1,
              pExpr->pRight==pExpr->pLeft ? " (SELECT-owner)" : "");

      sqlite3TreeViewSelect(pView, pExpr->pLeft->x.pSelect, 0);
      break;
    }
    case TK_IF_NULL_ROW: {
      sqlite3TreeViewLine(pView, "IF-NULL-ROW %d", pExpr->iTable);
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 0);
      break;







>












>












>








>







31002
31003
31004
31005
31006
31007
31008
31009
31010
31011
31012
31013
31014
31015
31016
31017
31018
31019
31020
31021
31022
31023
31024
31025
31026
31027
31028
31029
31030
31031
31032
31033
31034
31035
31036
31037
31038
31039
31040
31041
31042
31043
31044
31045
31046
31047
31048
31049
31050
31051
      sqlite3TreeViewLine(pView, "%s(%d)",
          pExpr->iTable ? "NEW" : "OLD", pExpr->iColumn);
      break;
    }
    case TK_CASE: {
      sqlite3TreeViewLine(pView, "CASE");
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 1);
      assert( ExprUseXList(pExpr) );
      sqlite3TreeViewExprList(pView, pExpr->x.pList, 0, 0);
      break;
    }
#ifndef SQLITE_OMIT_TRIGGER
    case TK_RAISE: {
      const char *zType = "unk";
      switch( pExpr->affExpr ){
        case OE_Rollback:   zType = "rollback";  break;
        case OE_Abort:      zType = "abort";     break;
        case OE_Fail:       zType = "fail";      break;
        case OE_Ignore:     zType = "ignore";    break;
      }
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      sqlite3TreeViewLine(pView, "RAISE %s(%Q)", zType, pExpr->u.zToken);
      break;
    }
#endif
    case TK_MATCH: {
      sqlite3TreeViewLine(pView, "MATCH {%d:%d}%s",
                          pExpr->iTable, pExpr->iColumn, zFlgs);
      sqlite3TreeViewExpr(pView, pExpr->pRight, 0);
      break;
    }
    case TK_VECTOR: {
      char *z = sqlite3_mprintf("VECTOR%s",zFlgs);
      assert( ExprUseXList(pExpr) );
      sqlite3TreeViewBareExprList(pView, pExpr->x.pList, z);
      sqlite3_free(z);
      break;
    }
    case TK_SELECT_COLUMN: {
      sqlite3TreeViewLine(pView, "SELECT-COLUMN %d of [0..%d]%s",
              pExpr->iColumn, pExpr->iTable-1,
              pExpr->pRight==pExpr->pLeft ? " (SELECT-owner)" : "");
      assert( ExprUseXSelect(pExpr->pLeft) );
      sqlite3TreeViewSelect(pView, pExpr->pLeft->x.pSelect, 0);
      break;
    }
    case TK_IF_NULL_ROW: {
      sqlite3TreeViewLine(pView, "IF-NULL-ROW %d", pExpr->iTable);
      sqlite3TreeViewExpr(pView, pExpr->pLeft, 0);
      break;
31877
31878
31879
31880
31881
31882
31883
31884
31885
31886
31887
31888
31889
31890
31891
31892
31893
31894
31895
31896
31897
31898
31899
31900
*/
/* #include "sqliteInt.h" */
/* #include <stdarg.h> */
#ifndef SQLITE_OMIT_FLOATING_POINT
#include <math.h>
#endif

/*
** Routine needed to support the testcase() macro.
*/
#ifdef SQLITE_COVERAGE_TEST
SQLITE_PRIVATE void sqlite3Coverage(int x){
  static unsigned dummy = 0;
  dummy += (unsigned)x;
}
#endif

/*
** Calls to sqlite3FaultSim() are used to simulate a failure during testing,
** or to bypass normal error detection during testing in order to let
** execute proceed futher downstream.
**
** In deployment, sqlite3FaultSim() *always* return SQLITE_OK (0).  The
** sqlite3FaultSim() function only returns non-zero during testing.







<
<
<
<
<
<
<
<
<
<







32114
32115
32116
32117
32118
32119
32120










32121
32122
32123
32124
32125
32126
32127
*/
/* #include "sqliteInt.h" */
/* #include <stdarg.h> */
#ifndef SQLITE_OMIT_FLOATING_POINT
#include <math.h>
#endif











/*
** Calls to sqlite3FaultSim() are used to simulate a failure during testing,
** or to bypass normal error detection during testing in order to let
** execute proceed futher downstream.
**
** In deployment, sqlite3FaultSim() *always* return SQLITE_OK (0).  The
** sqlite3FaultSim() function only returns non-zero during testing.
32133
32134
32135
32136
32137
32138
32139

32140
32141
32142
32143
32144
32145
32146
    }else{
      z[j++] = z[i];
    }
  }
  z[j] = 0;
}
SQLITE_PRIVATE void sqlite3DequoteExpr(Expr *p){

  assert( sqlite3Isquote(p->u.zToken[0]) );
  p->flags |= p->u.zToken[0]=='"' ? EP_Quoted|EP_DblQuoted : EP_Quoted;
  sqlite3Dequote(p->u.zToken);
}

/*
** If the input token p is quoted, try to adjust the token to remove







>







32360
32361
32362
32363
32364
32365
32366
32367
32368
32369
32370
32371
32372
32373
32374
    }else{
      z[j++] = z[i];
    }
  }
  z[j] = 0;
}
SQLITE_PRIVATE void sqlite3DequoteExpr(Expr *p){
  assert( !ExprHasProperty(p, EP_IntValue) );
  assert( sqlite3Isquote(p->u.zToken[0]) );
  p->flags |= p->u.zToken[0]=='"' ? EP_Quoted|EP_DblQuoted : EP_Quoted;
  sqlite3Dequote(p->u.zToken);
}

/*
** If the input token p is quoted, try to adjust the token to remove
33451
33452
33453
33454
33455
33456
33457
33458
33459
33460
33461
33462
33463
33464
33465
33466
33467
33468
33469
33470
33471
33472
33473
33474
33475
33476
33477
33478
33479
33480
33481
33482
33483
33484
33485
33486
33487
33488
33489
33490
33491
33492
33493
33494
33495
33496
33497
33498
33499
33500
33501
33502
33503
33504
33505
33506
33507
    while( x>255 ){ y += 40; x >>= 4; }  /*OPTIMIZATION-IF-TRUE*/
    while( x>15 ){  y += 10; x >>= 1; }
#endif
  }
  return a[x&7] + y - 10;
}

#ifndef SQLITE_OMIT_VIRTUALTABLE
/*
** Convert a double into a LogEst
** In other words, compute an approximation for 10*log2(x).
*/
SQLITE_PRIVATE LogEst sqlite3LogEstFromDouble(double x){
  u64 a;
  LogEst e;
  assert( sizeof(x)==8 && sizeof(a)==8 );
  if( x<=1 ) return 0;
  if( x<=2000000000 ) return sqlite3LogEst((u64)x);
  memcpy(&a, &x, 8);
  e = (a>>52) - 1022;
  return e*10;
}
#endif /* SQLITE_OMIT_VIRTUALTABLE */

#if defined(SQLITE_ENABLE_STMT_SCANSTATUS) || \
    defined(SQLITE_ENABLE_STAT4) || \
    defined(SQLITE_EXPLAIN_ESTIMATED_ROWS)
/*
** Convert a LogEst into an integer.
**
** Note that this routine is only used when one or more of various
** non-standard compile-time options is enabled.
*/
SQLITE_PRIVATE u64 sqlite3LogEstToInt(LogEst x){
  u64 n;
  n = x%10;
  x /= 10;
  if( n>=5 ) n -= 2;
  else if( n>=1 ) n -= 1;
#if defined(SQLITE_ENABLE_STMT_SCANSTATUS) || \
    defined(SQLITE_EXPLAIN_ESTIMATED_ROWS)
  if( x>60 ) return (u64)LARGEST_INT64;
#else
  /* If only SQLITE_ENABLE_STAT4 is on, then the largest input
  ** possible to this routine is 310, resulting in a maximum x of 31 */
  assert( x<=60 );
#endif
  return x>=3 ? (n+8)<<(x-3) : (n+8)>>(3-x);
}
#endif /* defined SCANSTAT or STAT4 or ESTIMATED_ROWS */

/*
** Add a new name/number pair to a VList.  This might require that the
** VList object be reallocated, so return the new VList.  If an OOM
** error occurs, the original VList returned and the
** db->mallocFailed flag is set.
**







<














<

<
<
<


<
<
<







<
<

<
<
<
<
<


<







33679
33680
33681
33682
33683
33684
33685

33686
33687
33688
33689
33690
33691
33692
33693
33694
33695
33696
33697
33698
33699

33700



33701
33702



33703
33704
33705
33706
33707
33708
33709


33710





33711
33712

33713
33714
33715
33716
33717
33718
33719
    while( x>255 ){ y += 40; x >>= 4; }  /*OPTIMIZATION-IF-TRUE*/
    while( x>15 ){  y += 10; x >>= 1; }
#endif
  }
  return a[x&7] + y - 10;
}


/*
** Convert a double into a LogEst
** In other words, compute an approximation for 10*log2(x).
*/
SQLITE_PRIVATE LogEst sqlite3LogEstFromDouble(double x){
  u64 a;
  LogEst e;
  assert( sizeof(x)==8 && sizeof(a)==8 );
  if( x<=1 ) return 0;
  if( x<=2000000000 ) return sqlite3LogEst((u64)x);
  memcpy(&a, &x, 8);
  e = (a>>52) - 1022;
  return e*10;
}





/*
** Convert a LogEst into an integer.



*/
SQLITE_PRIVATE u64 sqlite3LogEstToInt(LogEst x){
  u64 n;
  n = x%10;
  x /= 10;
  if( n>=5 ) n -= 2;
  else if( n>=1 ) n -= 1;


  if( x>60 ) return (u64)LARGEST_INT64;





  return x>=3 ? (n+8)<<(x-3) : (n+8)>>(3-x);
}


/*
** Add a new name/number pair to a VList.  This might require that the
** VList object be reallocated, so return the new VList.  If an OOM
** error occurs, the original VList returned and the
** db->mallocFailed flag is set.
**
33947
33948
33949
33950
33951
33952
33953

33954
33955
33956
33957
33958
33959
33960
33961
33962
33963
33964
33965
33966
33967
33968
33969
33970
33971
33972
33973


33974
33975
33976
33977
33978
33979
33980
33981
33982
33983
33984
33985
33986
33987
33988
33989
33990
33991
33992
33993
33994
33995
33996
33997
33998
33999
34000
34001
34002
34003
34004

34005
34006
34007

34008
34009
34010
34011
34012
34013
34014
34015
34016
34017
34018
34019
34020
34021
34022
34023
34024
34025
34026
34027
34028
34029
34030
34031
34032
34033
34034
34035
34036
34037
34038
34039
34040
34041
34042
34043

34044
34045
34046
34047
34048
34049
34050
34051
34052
34053
34054
34055
34056
34057
34058
34059
34060
34061
34062
34063
34064
34065
34066

34067
34068
34069
34070
34071
34072
34073
34074
34075
34076
34077
34078
34079
    /*  56 */ "Lt"               OpHelp("IF r[P3]<r[P1]"),
    /*  57 */ "Ge"               OpHelp("IF r[P3]>=r[P1]"),
    /*  58 */ "ElseEq"           OpHelp(""),
    /*  59 */ "IfNotZero"        OpHelp("if r[P1]!=0 then r[P1]--, goto P2"),
    /*  60 */ "DecrJumpZero"     OpHelp("if (--r[P1])==0 goto P2"),
    /*  61 */ "IncrVacuum"       OpHelp(""),
    /*  62 */ "VNext"            OpHelp(""),

    /*  63 */ "Init"             OpHelp("Start at P2"),
    /*  64 */ "PureFunc"         OpHelp("r[P3]=func(r[P2@NP])"),
    /*  65 */ "Function"         OpHelp("r[P3]=func(r[P2@NP])"),
    /*  66 */ "Return"           OpHelp(""),
    /*  67 */ "EndCoroutine"     OpHelp(""),
    /*  68 */ "HaltIfNull"       OpHelp("if r[P3]=null halt"),
    /*  69 */ "Halt"             OpHelp(""),
    /*  70 */ "Integer"          OpHelp("r[P2]=P1"),
    /*  71 */ "Int64"            OpHelp("r[P2]=P4"),
    /*  72 */ "String"           OpHelp("r[P2]='P4' (len=P1)"),
    /*  73 */ "Null"             OpHelp("r[P2..P3]=NULL"),
    /*  74 */ "SoftNull"         OpHelp("r[P1]=NULL"),
    /*  75 */ "Blob"             OpHelp("r[P2]=P4 (len=P1)"),
    /*  76 */ "Variable"         OpHelp("r[P2]=parameter(P1,P4)"),
    /*  77 */ "Move"             OpHelp("r[P2@P3]=r[P1@P3]"),
    /*  78 */ "Copy"             OpHelp("r[P2@P3+1]=r[P1@P3+1]"),
    /*  79 */ "SCopy"            OpHelp("r[P2]=r[P1]"),
    /*  80 */ "IntCopy"          OpHelp("r[P2]=r[P1]"),
    /*  81 */ "ChngCntRow"       OpHelp("output=r[P1]"),
    /*  82 */ "ResultRow"        OpHelp("output=r[P1@P2]"),


    /*  83 */ "CollSeq"          OpHelp(""),
    /*  84 */ "AddImm"           OpHelp("r[P1]=r[P1]+P2"),
    /*  85 */ "RealAffinity"     OpHelp(""),
    /*  86 */ "Cast"             OpHelp("affinity(r[P1])"),
    /*  87 */ "Permutation"      OpHelp(""),
    /*  88 */ "Compare"          OpHelp("r[P1@P3] <-> r[P2@P3]"),
    /*  89 */ "IsTrue"           OpHelp("r[P2] = coalesce(r[P1]==TRUE,P3) ^ P4"),
    /*  90 */ "ZeroOrNull"       OpHelp("r[P2] = 0 OR NULL"),
    /*  91 */ "Offset"           OpHelp("r[P3] = sqlite_offset(P1)"),
    /*  92 */ "Column"           OpHelp("r[P3]=PX"),
    /*  93 */ "TypeCheck"        OpHelp("typecheck(r[P1@P2])"),
    /*  94 */ "Affinity"         OpHelp("affinity(r[P1@P2])"),
    /*  95 */ "MakeRecord"       OpHelp("r[P3]=mkrec(r[P1@P2])"),
    /*  96 */ "Count"            OpHelp("r[P2]=count()"),
    /*  97 */ "ReadCookie"       OpHelp(""),
    /*  98 */ "SetCookie"        OpHelp(""),
    /*  99 */ "ReopenIdx"        OpHelp("root=P2 iDb=P3"),
    /* 100 */ "OpenRead"         OpHelp("root=P2 iDb=P3"),
    /* 101 */ "OpenWrite"        OpHelp("root=P2 iDb=P3"),
    /* 102 */ "BitAnd"           OpHelp("r[P3]=r[P1]&r[P2]"),
    /* 103 */ "BitOr"            OpHelp("r[P3]=r[P1]|r[P2]"),
    /* 104 */ "ShiftLeft"        OpHelp("r[P3]=r[P2]<<r[P1]"),
    /* 105 */ "ShiftRight"       OpHelp("r[P3]=r[P2]>>r[P1]"),
    /* 106 */ "Add"              OpHelp("r[P3]=r[P1]+r[P2]"),
    /* 107 */ "Subtract"         OpHelp("r[P3]=r[P2]-r[P1]"),
    /* 108 */ "Multiply"         OpHelp("r[P3]=r[P1]*r[P2]"),
    /* 109 */ "Divide"           OpHelp("r[P3]=r[P2]/r[P1]"),
    /* 110 */ "Remainder"        OpHelp("r[P3]=r[P2]%r[P1]"),
    /* 111 */ "Concat"           OpHelp("r[P3]=r[P2]+r[P1]"),
    /* 112 */ "OpenDup"          OpHelp(""),
    /* 113 */ "BitNot"           OpHelp("r[P2]= ~r[P1]"),

    /* 114 */ "OpenAutoindex"    OpHelp("nColumn=P2"),
    /* 115 */ "OpenEphemeral"    OpHelp("nColumn=P2"),
    /* 116 */ "String8"          OpHelp("r[P2]='P4'"),

    /* 117 */ "SorterOpen"       OpHelp(""),
    /* 118 */ "SequenceTest"     OpHelp("if( cursor[P1].ctr++ ) pc = P2"),
    /* 119 */ "OpenPseudo"       OpHelp("P3 columns in r[P2]"),
    /* 120 */ "Close"            OpHelp(""),
    /* 121 */ "ColumnsUsed"      OpHelp(""),
    /* 122 */ "SeekScan"         OpHelp("Scan-ahead up to P1 rows"),
    /* 123 */ "SeekHit"          OpHelp("set P2<=seekHit<=P3"),
    /* 124 */ "Sequence"         OpHelp("r[P2]=cursor[P1].ctr++"),
    /* 125 */ "NewRowid"         OpHelp("r[P2]=rowid"),
    /* 126 */ "Insert"           OpHelp("intkey=r[P3] data=r[P2]"),
    /* 127 */ "RowCell"          OpHelp(""),
    /* 128 */ "Delete"           OpHelp(""),
    /* 129 */ "ResetCount"       OpHelp(""),
    /* 130 */ "SorterCompare"    OpHelp("if key(P1)!=trim(r[P3],P4) goto P2"),
    /* 131 */ "SorterData"       OpHelp("r[P2]=data"),
    /* 132 */ "RowData"          OpHelp("r[P2]=data"),
    /* 133 */ "Rowid"            OpHelp("r[P2]=rowid"),
    /* 134 */ "NullRow"          OpHelp(""),
    /* 135 */ "SeekEnd"          OpHelp(""),
    /* 136 */ "IdxInsert"        OpHelp("key=r[P2]"),
    /* 137 */ "SorterInsert"     OpHelp("key=r[P2]"),
    /* 138 */ "IdxDelete"        OpHelp("key=r[P2@P3]"),
    /* 139 */ "DeferredSeek"     OpHelp("Move P3 to P1.rowid if needed"),
    /* 140 */ "IdxRowid"         OpHelp("r[P2]=rowid"),
    /* 141 */ "FinishSeek"       OpHelp(""),
    /* 142 */ "Destroy"          OpHelp(""),
    /* 143 */ "Clear"            OpHelp(""),
    /* 144 */ "ResetSorter"      OpHelp(""),
    /* 145 */ "CreateBtree"      OpHelp("r[P2]=root iDb=P1 flags=P3"),
    /* 146 */ "SqlExec"          OpHelp(""),
    /* 147 */ "ParseSchema"      OpHelp(""),
    /* 148 */ "LoadAnalysis"     OpHelp(""),
    /* 149 */ "DropTable"        OpHelp(""),
    /* 150 */ "DropIndex"        OpHelp(""),
    /* 151 */ "DropTrigger"      OpHelp(""),
    /* 152 */ "Real"             OpHelp("r[P2]=P4"),

    /* 153 */ "IntegrityCk"      OpHelp(""),
    /* 154 */ "RowSetAdd"        OpHelp("rowset(P1)=r[P2]"),
    /* 155 */ "Param"            OpHelp(""),
    /* 156 */ "FkCounter"        OpHelp("fkctr[P1]+=P2"),
    /* 157 */ "MemMax"           OpHelp("r[P1]=max(r[P1],r[P2])"),
    /* 158 */ "OffsetLimit"      OpHelp("if r[P1]>0 then r[P2]=r[P1]+max(0,r[P3]) else r[P2]=(-1)"),
    /* 159 */ "AggInverse"       OpHelp("accum=r[P3] inverse(r[P2@P5])"),
    /* 160 */ "AggStep"          OpHelp("accum=r[P3] step(r[P2@P5])"),
    /* 161 */ "AggStep1"         OpHelp("accum=r[P3] step(r[P2@P5])"),
    /* 162 */ "AggValue"         OpHelp("r[P3]=value N=P2"),
    /* 163 */ "AggFinal"         OpHelp("accum=r[P1] N=P2"),
    /* 164 */ "Expire"           OpHelp(""),
    /* 165 */ "CursorLock"       OpHelp(""),
    /* 166 */ "CursorUnlock"     OpHelp(""),
    /* 167 */ "TableLock"        OpHelp("iDb=P1 root=P2 write=P3"),
    /* 168 */ "VBegin"           OpHelp(""),
    /* 169 */ "VCreate"          OpHelp(""),
    /* 170 */ "VDestroy"         OpHelp(""),
    /* 171 */ "VOpen"            OpHelp(""),
    /* 172 */ "VColumn"          OpHelp("r[P3]=vcolumn(P2)"),
    /* 173 */ "VRename"          OpHelp(""),
    /* 174 */ "Pagecount"        OpHelp(""),
    /* 175 */ "MaxPgcnt"         OpHelp(""),

    /* 176 */ "Trace"            OpHelp(""),
    /* 177 */ "CursorHint"       OpHelp(""),
    /* 178 */ "ReleaseReg"       OpHelp("release r[P1@P2] mask P3"),
    /* 179 */ "Noop"             OpHelp(""),
    /* 180 */ "Explain"          OpHelp(""),
    /* 181 */ "Abortable"        OpHelp(""),
  };
  return azName[i];
}
#endif

/************** End of opcodes.c *********************************************/
/************** Begin file os_unix.c *****************************************/







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










|

>
|
<

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

>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
>
|
|
|
|
|
|







34159
34160
34161
34162
34163
34164
34165
34166
34167
34168
34169
34170
34171
34172
34173
34174
34175
34176
34177
34178
34179
34180
34181
34182
34183
34184


34185
34186
34187
34188
34189
34190
34191
34192
34193
34194
34195
34196
34197
34198
34199
34200
34201
34202
34203
34204

34205
34206
34207
34208
34209
34210
34211
34212
34213
34214
34215
34216
34217
34218

34219
34220
34221
34222
34223
34224
34225
34226
34227
34228
34229
34230
34231
34232
34233
34234
34235
34236
34237
34238
34239
34240
34241
34242
34243
34244
34245
34246
34247
34248
34249
34250
34251
34252
34253
34254

34255
34256
34257
34258
34259
34260
34261
34262
34263
34264
34265
34266
34267
34268
34269
34270
34271
34272
34273
34274
34275
34276
34277
34278
34279
34280
34281
34282
34283
34284
34285
34286
34287
34288
34289
34290
34291
34292
34293
    /*  56 */ "Lt"               OpHelp("IF r[P3]<r[P1]"),
    /*  57 */ "Ge"               OpHelp("IF r[P3]>=r[P1]"),
    /*  58 */ "ElseEq"           OpHelp(""),
    /*  59 */ "IfNotZero"        OpHelp("if r[P1]!=0 then r[P1]--, goto P2"),
    /*  60 */ "DecrJumpZero"     OpHelp("if (--r[P1])==0 goto P2"),
    /*  61 */ "IncrVacuum"       OpHelp(""),
    /*  62 */ "VNext"            OpHelp(""),
    /*  63 */ "Filter"           OpHelp("if key(P3@P4) not in filter(P1) goto P2"),
    /*  64 */ "Init"             OpHelp("Start at P2"),
    /*  65 */ "PureFunc"         OpHelp("r[P3]=func(r[P2@NP])"),
    /*  66 */ "Function"         OpHelp("r[P3]=func(r[P2@NP])"),
    /*  67 */ "Return"           OpHelp(""),
    /*  68 */ "EndCoroutine"     OpHelp(""),
    /*  69 */ "HaltIfNull"       OpHelp("if r[P3]=null halt"),
    /*  70 */ "Halt"             OpHelp(""),
    /*  71 */ "Integer"          OpHelp("r[P2]=P1"),
    /*  72 */ "Int64"            OpHelp("r[P2]=P4"),
    /*  73 */ "String"           OpHelp("r[P2]='P4' (len=P1)"),
    /*  74 */ "Null"             OpHelp("r[P2..P3]=NULL"),
    /*  75 */ "SoftNull"         OpHelp("r[P1]=NULL"),
    /*  76 */ "Blob"             OpHelp("r[P2]=P4 (len=P1)"),
    /*  77 */ "Variable"         OpHelp("r[P2]=parameter(P1,P4)"),
    /*  78 */ "Move"             OpHelp("r[P2@P3]=r[P1@P3]"),
    /*  79 */ "Copy"             OpHelp("r[P2@P3+1]=r[P1@P3+1]"),
    /*  80 */ "SCopy"            OpHelp("r[P2]=r[P1]"),
    /*  81 */ "IntCopy"          OpHelp("r[P2]=r[P1]"),


    /*  82 */ "FkCheck"          OpHelp(""),
    /*  83 */ "ResultRow"        OpHelp("output=r[P1@P2]"),
    /*  84 */ "CollSeq"          OpHelp(""),
    /*  85 */ "AddImm"           OpHelp("r[P1]=r[P1]+P2"),
    /*  86 */ "RealAffinity"     OpHelp(""),
    /*  87 */ "Cast"             OpHelp("affinity(r[P1])"),
    /*  88 */ "Permutation"      OpHelp(""),
    /*  89 */ "Compare"          OpHelp("r[P1@P3] <-> r[P2@P3]"),
    /*  90 */ "IsTrue"           OpHelp("r[P2] = coalesce(r[P1]==TRUE,P3) ^ P4"),
    /*  91 */ "ZeroOrNull"       OpHelp("r[P2] = 0 OR NULL"),
    /*  92 */ "Offset"           OpHelp("r[P3] = sqlite_offset(P1)"),
    /*  93 */ "Column"           OpHelp("r[P3]=PX"),
    /*  94 */ "TypeCheck"        OpHelp("typecheck(r[P1@P2])"),
    /*  95 */ "Affinity"         OpHelp("affinity(r[P1@P2])"),
    /*  96 */ "MakeRecord"       OpHelp("r[P3]=mkrec(r[P1@P2])"),
    /*  97 */ "Count"            OpHelp("r[P2]=count()"),
    /*  98 */ "ReadCookie"       OpHelp(""),
    /*  99 */ "SetCookie"        OpHelp(""),
    /* 100 */ "ReopenIdx"        OpHelp("root=P2 iDb=P3"),
    /* 101 */ "OpenRead"         OpHelp("root=P2 iDb=P3"),

    /* 102 */ "BitAnd"           OpHelp("r[P3]=r[P1]&r[P2]"),
    /* 103 */ "BitOr"            OpHelp("r[P3]=r[P1]|r[P2]"),
    /* 104 */ "ShiftLeft"        OpHelp("r[P3]=r[P2]<<r[P1]"),
    /* 105 */ "ShiftRight"       OpHelp("r[P3]=r[P2]>>r[P1]"),
    /* 106 */ "Add"              OpHelp("r[P3]=r[P1]+r[P2]"),
    /* 107 */ "Subtract"         OpHelp("r[P3]=r[P2]-r[P1]"),
    /* 108 */ "Multiply"         OpHelp("r[P3]=r[P1]*r[P2]"),
    /* 109 */ "Divide"           OpHelp("r[P3]=r[P2]/r[P1]"),
    /* 110 */ "Remainder"        OpHelp("r[P3]=r[P2]%r[P1]"),
    /* 111 */ "Concat"           OpHelp("r[P3]=r[P2]+r[P1]"),
    /* 112 */ "OpenWrite"        OpHelp("root=P2 iDb=P3"),
    /* 113 */ "BitNot"           OpHelp("r[P2]= ~r[P1]"),
    /* 114 */ "OpenDup"          OpHelp(""),
    /* 115 */ "OpenAutoindex"    OpHelp("nColumn=P2"),

    /* 116 */ "String8"          OpHelp("r[P2]='P4'"),
    /* 117 */ "OpenEphemeral"    OpHelp("nColumn=P2"),
    /* 118 */ "SorterOpen"       OpHelp(""),
    /* 119 */ "SequenceTest"     OpHelp("if( cursor[P1].ctr++ ) pc = P2"),
    /* 120 */ "OpenPseudo"       OpHelp("P3 columns in r[P2]"),
    /* 121 */ "Close"            OpHelp(""),
    /* 122 */ "ColumnsUsed"      OpHelp(""),
    /* 123 */ "SeekScan"         OpHelp("Scan-ahead up to P1 rows"),
    /* 124 */ "SeekHit"          OpHelp("set P2<=seekHit<=P3"),
    /* 125 */ "Sequence"         OpHelp("r[P2]=cursor[P1].ctr++"),
    /* 126 */ "NewRowid"         OpHelp("r[P2]=rowid"),
    /* 127 */ "Insert"           OpHelp("intkey=r[P3] data=r[P2]"),
    /* 128 */ "RowCell"          OpHelp(""),
    /* 129 */ "Delete"           OpHelp(""),
    /* 130 */ "ResetCount"       OpHelp(""),
    /* 131 */ "SorterCompare"    OpHelp("if key(P1)!=trim(r[P3],P4) goto P2"),
    /* 132 */ "SorterData"       OpHelp("r[P2]=data"),
    /* 133 */ "RowData"          OpHelp("r[P2]=data"),
    /* 134 */ "Rowid"            OpHelp("r[P2]=rowid"),
    /* 135 */ "NullRow"          OpHelp(""),
    /* 136 */ "SeekEnd"          OpHelp(""),
    /* 137 */ "IdxInsert"        OpHelp("key=r[P2]"),
    /* 138 */ "SorterInsert"     OpHelp("key=r[P2]"),
    /* 139 */ "IdxDelete"        OpHelp("key=r[P2@P3]"),
    /* 140 */ "DeferredSeek"     OpHelp("Move P3 to P1.rowid if needed"),
    /* 141 */ "IdxRowid"         OpHelp("r[P2]=rowid"),
    /* 142 */ "FinishSeek"       OpHelp(""),
    /* 143 */ "Destroy"          OpHelp(""),
    /* 144 */ "Clear"            OpHelp(""),
    /* 145 */ "ResetSorter"      OpHelp(""),
    /* 146 */ "CreateBtree"      OpHelp("r[P2]=root iDb=P1 flags=P3"),
    /* 147 */ "SqlExec"          OpHelp(""),
    /* 148 */ "ParseSchema"      OpHelp(""),
    /* 149 */ "LoadAnalysis"     OpHelp(""),
    /* 150 */ "DropTable"        OpHelp(""),
    /* 151 */ "DropIndex"        OpHelp(""),

    /* 152 */ "Real"             OpHelp("r[P2]=P4"),
    /* 153 */ "DropTrigger"      OpHelp(""),
    /* 154 */ "IntegrityCk"      OpHelp(""),
    /* 155 */ "RowSetAdd"        OpHelp("rowset(P1)=r[P2]"),
    /* 156 */ "Param"            OpHelp(""),
    /* 157 */ "FkCounter"        OpHelp("fkctr[P1]+=P2"),
    /* 158 */ "MemMax"           OpHelp("r[P1]=max(r[P1],r[P2])"),
    /* 159 */ "OffsetLimit"      OpHelp("if r[P1]>0 then r[P2]=r[P1]+max(0,r[P3]) else r[P2]=(-1)"),
    /* 160 */ "AggInverse"       OpHelp("accum=r[P3] inverse(r[P2@P5])"),
    /* 161 */ "AggStep"          OpHelp("accum=r[P3] step(r[P2@P5])"),
    /* 162 */ "AggStep1"         OpHelp("accum=r[P3] step(r[P2@P5])"),
    /* 163 */ "AggValue"         OpHelp("r[P3]=value N=P2"),
    /* 164 */ "AggFinal"         OpHelp("accum=r[P1] N=P2"),
    /* 165 */ "Expire"           OpHelp(""),
    /* 166 */ "CursorLock"       OpHelp(""),
    /* 167 */ "CursorUnlock"     OpHelp(""),
    /* 168 */ "TableLock"        OpHelp("iDb=P1 root=P2 write=P3"),
    /* 169 */ "VBegin"           OpHelp(""),
    /* 170 */ "VCreate"          OpHelp(""),
    /* 171 */ "VDestroy"         OpHelp(""),
    /* 172 */ "VOpen"            OpHelp(""),
    /* 173 */ "VColumn"          OpHelp("r[P3]=vcolumn(P2)"),
    /* 174 */ "VRename"          OpHelp(""),
    /* 175 */ "Pagecount"        OpHelp(""),
    /* 176 */ "MaxPgcnt"         OpHelp(""),
    /* 177 */ "FilterAdd"        OpHelp("filter(P1) += key(P3@P4)"),
    /* 178 */ "Trace"            OpHelp(""),
    /* 179 */ "CursorHint"       OpHelp(""),
    /* 180 */ "ReleaseReg"       OpHelp("release r[P1@P2] mask P3"),
    /* 181 */ "Noop"             OpHelp(""),
    /* 182 */ "Explain"          OpHelp(""),
    /* 183 */ "Abortable"        OpHelp(""),
  };
  return azName[i];
}
#endif

/************** End of opcodes.c *********************************************/
/************** Begin file os_unix.c *****************************************/
38026
38027
38028
38029
38030
38031
38032

38033

38034
38035
38036
38037
38038
38039
38040
  }else{
    pFile->ctrlFlags |= mask;
  }
}

/* Forward declaration */
static int unixGetTempname(int nBuf, char *zBuf);

static int unixFcntlExternalReader(unixFile*, int*);


/*
** Information and control of an open file handle.
*/
static int unixFileControl(sqlite3_file *id, int op, void *pArg){
  unixFile *pFile = (unixFile*)id;
  switch( op ){







>
|
>







38240
38241
38242
38243
38244
38245
38246
38247
38248
38249
38250
38251
38252
38253
38254
38255
38256
  }else{
    pFile->ctrlFlags |= mask;
  }
}

/* Forward declaration */
static int unixGetTempname(int nBuf, char *zBuf);
#ifndef SQLITE_OMIT_WAL
 static int unixFcntlExternalReader(unixFile*, int*);
#endif

/*
** Information and control of an open file handle.
*/
static int unixFileControl(sqlite3_file *id, int op, void *pArg){
  unixFile *pFile = (unixFile*)id;
  switch( op ){
38145
38146
38147
38148
38149
38150
38151

38152




38153
38154
38155
38156
38157
38158
38159
    case SQLITE_FCNTL_SET_LOCKPROXYFILE:
    case SQLITE_FCNTL_GET_LOCKPROXYFILE: {
      return proxyFileControl(id,op,pArg);
    }
#endif /* SQLITE_ENABLE_LOCKING_STYLE && defined(__APPLE__) */

    case SQLITE_FCNTL_EXTERNAL_READER: {

      return unixFcntlExternalReader((unixFile*)id, (int*)pArg);




    }
  }
  return SQLITE_NOTFOUND;
}

/*
** If pFd->sectorSize is non-zero when this function is called, it is a







>

>
>
>
>







38361
38362
38363
38364
38365
38366
38367
38368
38369
38370
38371
38372
38373
38374
38375
38376
38377
38378
38379
38380
    case SQLITE_FCNTL_SET_LOCKPROXYFILE:
    case SQLITE_FCNTL_GET_LOCKPROXYFILE: {
      return proxyFileControl(id,op,pArg);
    }
#endif /* SQLITE_ENABLE_LOCKING_STYLE && defined(__APPLE__) */

    case SQLITE_FCNTL_EXTERNAL_READER: {
#ifndef SQLITE_OMIT_WAL
      return unixFcntlExternalReader((unixFile*)id, (int*)pArg);
#else
      *(int*)pArg = 0;
      return SQLITE_OK;
#endif
    }
  }
  return SQLITE_NOTFOUND;
}

/*
** If pFd->sectorSize is non-zero when this function is called, it is a
39865
39866
39867
39868
39869
39870
39871




















39872
39873
39874
39875
39876
39877
39878
39879
39880
39881
39882
39883
39884
39885
39886
39887
39888
39889
39890
39891
39892
39893
39894
39895
39896
39897
39898
39899
39900
39901
39902
39903
39904
39905
39906
39907
39908
  }else{
    pId->pMethods = pLockingStyle;
    OpenCounter(+1);
    verifyDbFile(pNew);
  }
  return rc;
}





















/*
** Return the name of a directory in which to put temporary files.
** If no suitable temporary file directory can be found, return NULL.
*/
static const char *unixTempFileDir(void){
  static const char *azDirs[] = {
     0,
     0,
     "/var/tmp",
     "/usr/tmp",
     "/tmp",
     "."
  };
  unsigned int i = 0;
  struct stat buf;
  const char *zDir = sqlite3_temp_directory;

  if( !azDirs[0] ) azDirs[0] = getenv("SQLITE_TMPDIR");
  if( !azDirs[1] ) azDirs[1] = getenv("TMPDIR");
  while(1){
    if( zDir!=0
     && osStat(zDir, &buf)==0
     && S_ISDIR(buf.st_mode)
     && osAccess(zDir, 03)==0
    ){
      return zDir;
    }
    if( i>=sizeof(azDirs)/sizeof(azDirs[0]) ) break;
    zDir = azDirs[i++];
  }
  return 0;
}

/*
** Create a temporary file name in zBuf.  zBuf must be allocated
** by the calling process and must be big enough to hold at least







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>






<
<
<
<
<
<
<
<




<
<








|
|







40086
40087
40088
40089
40090
40091
40092
40093
40094
40095
40096
40097
40098
40099
40100
40101
40102
40103
40104
40105
40106
40107
40108
40109
40110
40111
40112
40113
40114
40115
40116
40117
40118








40119
40120
40121
40122


40123
40124
40125
40126
40127
40128
40129
40130
40131
40132
40133
40134
40135
40136
40137
40138
40139
  }else{
    pId->pMethods = pLockingStyle;
    OpenCounter(+1);
    verifyDbFile(pNew);
  }
  return rc;
}

/*
** Directories to consider for temp files.
*/
static const char *azTempDirs[] = {
  0,
  0,
  "/var/tmp",
  "/usr/tmp",
  "/tmp",
  "."
};

/*
** Initialize first two members of azTempDirs[] array.
*/
static void unixTempFileInit(void){
  azTempDirs[0] = getenv("SQLITE_TMPDIR");
  azTempDirs[1] = getenv("TMPDIR");
}

/*
** Return the name of a directory in which to put temporary files.
** If no suitable temporary file directory can be found, return NULL.
*/
static const char *unixTempFileDir(void){








  unsigned int i = 0;
  struct stat buf;
  const char *zDir = sqlite3_temp_directory;



  while(1){
    if( zDir!=0
     && osStat(zDir, &buf)==0
     && S_ISDIR(buf.st_mode)
     && osAccess(zDir, 03)==0
    ){
      return zDir;
    }
    if( i>=sizeof(azTempDirs)/sizeof(azTempDirs[0]) ) break;
    zDir = azTempDirs[i++];
  }
  return 0;
}

/*
** Create a temporary file name in zBuf.  zBuf must be allocated
** by the calling process and must be big enough to hold at least
40199
40200
40201
40202
40203
40204
40205





40206
40207
40208
40209
40210
40211
40212
  ** are harmless.
  */
  if( randomnessPid!=osGetpid(0) ){
    randomnessPid = osGetpid(0);
    sqlite3_randomness(0,0);
  }
  memset(p, 0, sizeof(unixFile));






  if( eType==SQLITE_OPEN_MAIN_DB ){
    UnixUnusedFd *pUnused;
    pUnused = findReusableFd(zName, flags);
    if( pUnused ){
      fd = pUnused->fd;
    }else{







>
>
>
>
>







40430
40431
40432
40433
40434
40435
40436
40437
40438
40439
40440
40441
40442
40443
40444
40445
40446
40447
40448
  ** are harmless.
  */
  if( randomnessPid!=osGetpid(0) ){
    randomnessPid = osGetpid(0);
    sqlite3_randomness(0,0);
  }
  memset(p, 0, sizeof(unixFile));

#ifdef SQLITE_ASSERT_NO_FILES
  /* Applications that never read or write a persistent disk files */
  assert( zName==0 );
#endif

  if( eType==SQLITE_OPEN_MAIN_DB ){
    UnixUnusedFd *pUnused;
    pUnused = findReusableFd(zName, flags);
    if( pUnused ){
      fd = pUnused->fd;
    }else{
40260
40261
40262
40263
40264
40265
40266
40267
40268
40269
40270
40271
40272
40273
40274
40275
    OSTRACE(("OPENX   %-3d %s 0%o\n", fd, zName, openFlags));
    assert( !isExclusive || (openFlags & O_CREAT)!=0 );
    if( fd<0 ){
      if( isNewJrnl && errno==EACCES && osAccess(zName, F_OK) ){
        /* If unable to create a journal because the directory is not
        ** writable, change the error code to indicate that. */
        rc = SQLITE_READONLY_DIRECTORY;
      }else if( errno==EEXIST ){
        rc = SQLITE_CANTOPEN_EXISTS;
      }else if( errno!=EISDIR && isReadWrite ){
        /* Failed to open the file for read/write access. Try read-only. */
        flags &= ~(SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE);
        openFlags &= ~(O_RDWR|O_CREAT);
        flags |= SQLITE_OPEN_READONLY;
        openFlags |= O_RDONLY;
        isReadonly = 1;







<
<







40496
40497
40498
40499
40500
40501
40502


40503
40504
40505
40506
40507
40508
40509
    OSTRACE(("OPENX   %-3d %s 0%o\n", fd, zName, openFlags));
    assert( !isExclusive || (openFlags & O_CREAT)!=0 );
    if( fd<0 ){
      if( isNewJrnl && errno==EACCES && osAccess(zName, F_OK) ){
        /* If unable to create a journal because the directory is not
        ** writable, change the error code to indicate that. */
        rc = SQLITE_READONLY_DIRECTORY;


      }else if( errno!=EISDIR && isReadWrite ){
        /* Failed to open the file for read/write access. Try read-only. */
        flags &= ~(SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE);
        openFlags &= ~(O_RDWR|O_CREAT);
        flags |= SQLITE_OPEN_READONLY;
        openFlags |= O_RDONLY;
        isReadonly = 1;
42162
42163
42164
42165
42166
42167
42168



42169
42170
42171
42172
42173
42174
42175
  **    READ-2      UNIX_SHM_BASE+5    125
  **    READ-3      UNIX_SHM_BASE+6    126
  **    READ-4      UNIX_SHM_BASE+7    127
  **    DMS         UNIX_SHM_BASE+8    128
  */
  assert( UNIX_SHM_DMS==128   );  /* Byte offset of the deadman-switch */
#endif




  return SQLITE_OK;
}

/*
** Shutdown the operating system interface.
**







>
>
>







42396
42397
42398
42399
42400
42401
42402
42403
42404
42405
42406
42407
42408
42409
42410
42411
42412
  **    READ-2      UNIX_SHM_BASE+5    125
  **    READ-3      UNIX_SHM_BASE+6    126
  **    READ-4      UNIX_SHM_BASE+7    127
  **    DMS         UNIX_SHM_BASE+8    128
  */
  assert( UNIX_SHM_DMS==128   );  /* Byte offset of the deadman-switch */
#endif

  /* Initialize temp file dir array. */
  unixTempFileInit();

  return SQLITE_OK;
}

/*
** Shutdown the operating system interface.
**
48613
48614
48615
48616
48617
48618
48619
48620
48621
48622
48623
48624
48625
48626
48627
}

/*
** Try to enlarge the memory allocation to hold at least sz bytes
*/
static int memdbEnlarge(MemStore *p, sqlite3_int64 newSz){
  unsigned char *pNew;
  if( (p->mFlags & SQLITE_DESERIALIZE_RESIZEABLE)==0 || p->nMmap>0 ){
    return SQLITE_FULL;
  }
  if( newSz>p->szMax ){
    return SQLITE_FULL;
  }
  newSz *= 2;
  if( newSz>p->szMax ) newSz = p->szMax;







|







48850
48851
48852
48853
48854
48855
48856
48857
48858
48859
48860
48861
48862
48863
48864
}

/*
** Try to enlarge the memory allocation to hold at least sz bytes
*/
static int memdbEnlarge(MemStore *p, sqlite3_int64 newSz){
  unsigned char *pNew;
  if( (p->mFlags & SQLITE_DESERIALIZE_RESIZEABLE)==0 || NEVER(p->nMmap>0) ){
    return SQLITE_FULL;
  }
  if( newSz>p->szMax ){
    return SQLITE_FULL;
  }
  newSz *= 2;
  if( newSz>p->szMax ) newSz = p->szMax;
48672
48673
48674
48675
48676
48677
48678
48679

48680
48681
48682
48683
48684
48685
48686
48687
** support WAL mode) the truncate() method is only used to reduce
** the size of a file, never to increase the size.
*/
static int memdbTruncate(sqlite3_file *pFile, sqlite_int64 size){
  MemStore *p = ((MemFile*)pFile)->pStore;
  int rc = SQLITE_OK;
  memdbEnter(p);
  if( NEVER(size>p->sz) ){

    rc = SQLITE_FULL;
  }else{
    p->sz = size;
  }
  memdbLeave(p);
  return rc;
}








|
>
|







48909
48910
48911
48912
48913
48914
48915
48916
48917
48918
48919
48920
48921
48922
48923
48924
48925
** support WAL mode) the truncate() method is only used to reduce
** the size of a file, never to increase the size.
*/
static int memdbTruncate(sqlite3_file *pFile, sqlite_int64 size){
  MemStore *p = ((MemFile*)pFile)->pStore;
  int rc = SQLITE_OK;
  memdbEnter(p);
  if( size>p->sz ){
    /* This can only happen with a corrupt wal mode db */
    rc = SQLITE_CORRUPT;
  }else{
    p->sz = size;
  }
  memdbLeave(p);
  return rc;
}

48812
48813
48814
48815
48816
48817
48818
48819
48820
48821
48822
48823
48824
48825
48826
  sqlite3_file *pFile,
  sqlite3_int64 iOfst,
  int iAmt,
  void **pp
){
  MemStore *p = ((MemFile*)pFile)->pStore;
  memdbEnter(p);
  if( iOfst+iAmt>p->sz ){
    *pp = 0;
  }else{
    p->nMmap++;
    *pp = (void*)(p->aData + iOfst);
  }
  memdbLeave(p);
  return SQLITE_OK;







|







49050
49051
49052
49053
49054
49055
49056
49057
49058
49059
49060
49061
49062
49063
49064
  sqlite3_file *pFile,
  sqlite3_int64 iOfst,
  int iAmt,
  void **pp
){
  MemStore *p = ((MemFile*)pFile)->pStore;
  memdbEnter(p);
  if( iOfst+iAmt>p->sz || (p->mFlags & SQLITE_DESERIALIZE_RESIZEABLE)!=0 ){
    *pp = 0;
  }else{
    p->nMmap++;
    *pp = (void*)(p->aData + iOfst);
  }
  memdbLeave(p);
  return SQLITE_OK;
48846
48847
48848
48849
48850
48851
48852
48853
48854
48855
48856
48857
48858
48859
48860
48861
48862
  sqlite3_file *pFd,
  int flags,
  int *pOutFlags
){
  MemFile *pFile = (MemFile*)pFd;
  MemStore *p = 0;
  int szName;
  if( (flags & SQLITE_OPEN_MAIN_DB)==0 ){
    return ORIGVFS(pVfs)->xOpen(ORIGVFS(pVfs), zName, pFd, flags, pOutFlags);
  }
  memset(pFile, 0, sizeof(*pFile));
  szName = sqlite3Strlen30(zName);
  if( szName>1 && zName[0]=='/' ){
    int i;
#ifndef SQLITE_MUTEX_OMIT
    sqlite3_mutex *pVfsMutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1);
#endif







<
|
|







49084
49085
49086
49087
49088
49089
49090

49091
49092
49093
49094
49095
49096
49097
49098
49099
  sqlite3_file *pFd,
  int flags,
  int *pOutFlags
){
  MemFile *pFile = (MemFile*)pFd;
  MemStore *p = 0;
  int szName;

  UNUSED_PARAMETER(pVfs);

  memset(pFile, 0, sizeof(*pFile));
  szName = sqlite3Strlen30(zName);
  if( szName>1 && zName[0]=='/' ){
    int i;
#ifndef SQLITE_MUTEX_OMIT
    sqlite3_mutex *pVfsMutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1);
#endif
48908
48909
48910
48911
48912
48913
48914
48915
48916

48917
48918
48919
48920
48921
48922
48923
      return SQLITE_NOMEM;
    }
    memset(p, 0, sizeof(*p));
    p->mFlags = SQLITE_DESERIALIZE_RESIZEABLE | SQLITE_DESERIALIZE_FREEONCLOSE;
    p->szMax = sqlite3GlobalConfig.mxMemdbSize;
  }
  pFile->pStore = p;
  assert( pOutFlags!=0 );  /* True because flags==SQLITE_OPEN_MAIN_DB */
  *pOutFlags = flags | SQLITE_OPEN_MEMORY;

  pFd->pMethods = &memdb_io_methods;
  memdbLeave(p);
  return SQLITE_OK;
}

#if 0 /* Only used to delete rollback journals, super-journals, and WAL
      ** files, none of which exist in memdb.  So this routine is never used */







|
|
>







49145
49146
49147
49148
49149
49150
49151
49152
49153
49154
49155
49156
49157
49158
49159
49160
49161
      return SQLITE_NOMEM;
    }
    memset(p, 0, sizeof(*p));
    p->mFlags = SQLITE_DESERIALIZE_RESIZEABLE | SQLITE_DESERIALIZE_FREEONCLOSE;
    p->szMax = sqlite3GlobalConfig.mxMemdbSize;
  }
  pFile->pStore = p;
  if( pOutFlags!=0 ){
    *pOutFlags = flags | SQLITE_OPEN_MEMORY;
  }
  pFd->pMethods = &memdb_io_methods;
  memdbLeave(p);
  return SQLITE_OK;
}

#if 0 /* Only used to delete rollback journals, super-journals, and WAL
      ** files, none of which exist in memdb.  So this routine is never used */
49574
49575
49576
49577
49578
49579
49580
49581
49582
49583
49584
49585
49586
49587
49588
  if( pBitvec==0 || pV==0 || pTmpSpace==0  ) goto bitvec_end;

  /* NULL pBitvec tests */
  sqlite3BitvecSet(0, 1);
  sqlite3BitvecClear(0, 1, pTmpSpace);

  /* Run the program */
  pc = 0;
  while( (op = aOp[pc])!=0 ){
    switch( op ){
      case 1:
      case 2:
      case 5: {
        nx = 4;
        i = aOp[pc+2] - 1;







|







49812
49813
49814
49815
49816
49817
49818
49819
49820
49821
49822
49823
49824
49825
49826
  if( pBitvec==0 || pV==0 || pTmpSpace==0  ) goto bitvec_end;

  /* NULL pBitvec tests */
  sqlite3BitvecSet(0, 1);
  sqlite3BitvecClear(0, 1, pTmpSpace);

  /* Run the program */
  pc = i = 0;
  while( (op = aOp[pc])!=0 ){
    switch( op ){
      case 1:
      case 2:
      case 5: {
        nx = 4;
        i = aOp[pc+2] - 1;
53104
53105
53106
53107
53108
53109
53110

53111
53112
53113
53114
53115
53116
53117
  u8 extraSync;               /* sync directory after journal delete */
  u8 syncFlags;               /* SYNC_NORMAL or SYNC_FULL otherwise */
  u8 walSyncFlags;            /* See description above */
  u8 tempFile;                /* zFilename is a temporary or immutable file */
  u8 noLock;                  /* Do not lock (except in WAL mode) */
  u8 readOnly;                /* True for a read-only database */
  u8 memDb;                   /* True to inhibit all file I/O */


  /**************************************************************************
  ** The following block contains those class members that change during
  ** routine operation.  Class members not in this block are either fixed
  ** when the pager is first created or else only change when there is a
  ** significant mode change (such as changing the page_size, locking_mode,
  ** or the journal_mode).  From another view, these class members describe







>







53342
53343
53344
53345
53346
53347
53348
53349
53350
53351
53352
53353
53354
53355
53356
  u8 extraSync;               /* sync directory after journal delete */
  u8 syncFlags;               /* SYNC_NORMAL or SYNC_FULL otherwise */
  u8 walSyncFlags;            /* See description above */
  u8 tempFile;                /* zFilename is a temporary or immutable file */
  u8 noLock;                  /* Do not lock (except in WAL mode) */
  u8 readOnly;                /* True for a read-only database */
  u8 memDb;                   /* True to inhibit all file I/O */
  u8 memVfs;                  /* VFS-implemented memory database */

  /**************************************************************************
  ** The following block contains those class members that change during
  ** routine operation.  Class members not in this block are either fixed
  ** when the pager is first created or else only change when there is a
  ** significant mode change (such as changing the page_size, locking_mode,
  ** or the journal_mode).  From another view, these class members describe
55498
55499
55500
55501
55502
55503
55504

55505
55506
55507
55508
55509
55510
55511
**
** This is an unconditional update.  See also the pager_incr_changecounter()
** routine which only updates the change-counter if the update is actually
** needed, as determined by the pPager->changeCountDone state variable.
*/
static void pager_write_changecounter(PgHdr *pPg){
  u32 change_counter;


  /* Increment the value just read and write it back to byte 24. */
  change_counter = sqlite3Get4byte((u8*)pPg->pPager->dbFileVers)+1;
  put32bits(((char*)pPg->pData)+24, change_counter);

  /* Also store the SQLite version number in bytes 96..99 and in
  ** bytes 92..95 store the change counter for which the version number







>







55737
55738
55739
55740
55741
55742
55743
55744
55745
55746
55747
55748
55749
55750
55751
**
** This is an unconditional update.  See also the pager_incr_changecounter()
** routine which only updates the change-counter if the update is actually
** needed, as determined by the pPager->changeCountDone state variable.
*/
static void pager_write_changecounter(PgHdr *pPg){
  u32 change_counter;
  if( NEVER(pPg==0) ) return;

  /* Increment the value just read and write it back to byte 24. */
  change_counter = sqlite3Get4byte((u8*)pPg->pPager->dbFileVers)+1;
  put32bits(((char*)pPg->pData)+24, change_counter);

  /* Also store the SQLite version number in bytes 96..99 and in
  ** bytes 92..95 store the change counter for which the version number
57345
57346
57347
57348
57349
57350
57351
57352
57353
57354
57355
57356
57357
57358
57359
  /* Open the pager file.
  */
  if( zFilename && zFilename[0] ){
    int fout = 0;                    /* VFS flags returned by xOpen() */
    rc = sqlite3OsOpen(pVfs, pPager->zFilename, pPager->fd, vfsFlags, &fout);
    assert( !memDb );
#ifndef SQLITE_OMIT_DESERIALIZE
    memJM = (fout&SQLITE_OPEN_MEMORY)!=0;
#endif
    readOnly = (fout&SQLITE_OPEN_READONLY)!=0;

    /* If the file was successfully opened for read/write access,
    ** choose a default page size in case we have to create the
    ** database file. The default page size is the maximum of:
    **







|







57585
57586
57587
57588
57589
57590
57591
57592
57593
57594
57595
57596
57597
57598
57599
  /* Open the pager file.
  */
  if( zFilename && zFilename[0] ){
    int fout = 0;                    /* VFS flags returned by xOpen() */
    rc = sqlite3OsOpen(pVfs, pPager->zFilename, pPager->fd, vfsFlags, &fout);
    assert( !memDb );
#ifndef SQLITE_OMIT_DESERIALIZE
    pPager->memVfs = memJM = (fout&SQLITE_OPEN_MEMORY)!=0;
#endif
    readOnly = (fout&SQLITE_OPEN_READONLY)!=0;

    /* If the file was successfully opened for read/write access,
    ** choose a default page size in case we have to create the
    ** database file. The default page size is the maximum of:
    **
59282
59283
59284
59285
59286
59287
59288
59289
59290
59291
59292
59293
59294
59295
59296
  }
}

/*
** Return true if this is an in-memory or temp-file backed pager.
*/
SQLITE_PRIVATE int sqlite3PagerIsMemdb(Pager *pPager){
  return pPager->tempFile;
}

/*
** Check that there are at least nSavepoint savepoints open. If there are
** currently less than nSavepoints open, then open one or more savepoints
** to make up the difference. If the number of savepoints is already
** equal to nSavepoint, then this function is a no-op.







|







59522
59523
59524
59525
59526
59527
59528
59529
59530
59531
59532
59533
59534
59535
59536
  }
}

/*
** Return true if this is an in-memory or temp-file backed pager.
*/
SQLITE_PRIVATE int sqlite3PagerIsMemdb(Pager *pPager){
  return pPager->tempFile || pPager->memVfs;
}

/*
** Check that there are at least nSavepoint savepoints open. If there are
** currently less than nSavepoints open, then open one or more savepoints
** to make up the difference. If the number of savepoints is already
** equal to nSavepoint, then this function is a no-op.
59602
59603
59604
59605
59606
59607
59608
59609
59610
59611
59612
59613
59614
59615
59616
  ** page pgno before the 'move' operation, it needs to be retained
  ** for the page moved there.
  */
  pPg->flags &= ~PGHDR_NEED_SYNC;
  pPgOld = sqlite3PagerLookup(pPager, pgno);
  assert( !pPgOld || pPgOld->nRef==1 || CORRUPT_DB );
  if( pPgOld ){
    if( pPgOld->nRef>1 ){
      sqlite3PagerUnrefNotNull(pPgOld);
      return SQLITE_CORRUPT_BKPT;
    }
    pPg->flags |= (pPgOld->flags&PGHDR_NEED_SYNC);
    if( pPager->tempFile ){
      /* Do not discard pages from an in-memory database since we might
      ** need to rollback later.  Just move the page out of the way. */







|







59842
59843
59844
59845
59846
59847
59848
59849
59850
59851
59852
59853
59854
59855
59856
  ** page pgno before the 'move' operation, it needs to be retained
  ** for the page moved there.
  */
  pPg->flags &= ~PGHDR_NEED_SYNC;
  pPgOld = sqlite3PagerLookup(pPager, pgno);
  assert( !pPgOld || pPgOld->nRef==1 || CORRUPT_DB );
  if( pPgOld ){
    if( NEVER(pPgOld->nRef>1) ){
      sqlite3PagerUnrefNotNull(pPgOld);
      return SQLITE_CORRUPT_BKPT;
    }
    pPg->flags |= (pPgOld->flags&PGHDR_NEED_SYNC);
    if( pPager->tempFile ){
      /* Do not discard pages from an in-memory database since we might
      ** need to rollback later.  Just move the page out of the way. */
60807
60808
60809
60810
60811
60812
60813
60814

60815
60816



60817
60818
60819
60820
60821
60822
60823
** numbered from zero.
**
** If the wal-index is currently smaller the iPage pages then the size
** of the wal-index might be increased, but only if it is safe to do
** so.  It is safe to enlarge the wal-index if pWal->writeLock is true
** or pWal->exclusiveMode==WAL_HEAPMEMORY_MODE.
**
** If this call is successful, *ppPage is set to point to the wal-index

** page and SQLITE_OK is returned. If an error (an OOM or VFS error) occurs,
** then an SQLite error code is returned and *ppPage is set to 0.



*/
static SQLITE_NOINLINE int walIndexPageRealloc(
  Wal *pWal,               /* The WAL context */
  int iPage,               /* The page we seek */
  volatile u32 **ppPage    /* Write the page pointer here */
){
  int rc = SQLITE_OK;







|
>
|
|
>
>
>







61047
61048
61049
61050
61051
61052
61053
61054
61055
61056
61057
61058
61059
61060
61061
61062
61063
61064
61065
61066
61067
** numbered from zero.
**
** If the wal-index is currently smaller the iPage pages then the size
** of the wal-index might be increased, but only if it is safe to do
** so.  It is safe to enlarge the wal-index if pWal->writeLock is true
** or pWal->exclusiveMode==WAL_HEAPMEMORY_MODE.
**
** Three possible result scenarios:
**
**   (1)  rc==SQLITE_OK    and *ppPage==Requested-Wal-Index-Page
**   (2)  rc>=SQLITE_ERROR and *ppPage==NULL
**   (3)  rc==SQLITE_OK    and *ppPage==NULL  // only if iPage==0
**
** Scenario (3) can only occur when pWal->writeLock is false and iPage==0
*/
static SQLITE_NOINLINE int walIndexPageRealloc(
  Wal *pWal,               /* The WAL context */
  int iPage,               /* The page we seek */
  volatile u32 **ppPage    /* Write the page pointer here */
){
  int rc = SQLITE_OK;
60842
60843
60844
60845
60846
60847
60848
60849


60850
60851
60852
60853
60854
60855
60856
  if( pWal->exclusiveMode==WAL_HEAPMEMORY_MODE ){
    pWal->apWiData[iPage] = (u32 volatile *)sqlite3MallocZero(WALINDEX_PGSZ);
    if( !pWal->apWiData[iPage] ) rc = SQLITE_NOMEM_BKPT;
  }else{
    rc = sqlite3OsShmMap(pWal->pDbFd, iPage, WALINDEX_PGSZ,
        pWal->writeLock, (void volatile **)&pWal->apWiData[iPage]
    );
    assert( pWal->apWiData[iPage]!=0 || rc!=SQLITE_OK || pWal->writeLock==0 );


    testcase( pWal->apWiData[iPage]==0 && rc==SQLITE_OK );
    if( rc==SQLITE_OK ){
      if( iPage>0 && sqlite3FaultSim(600) ) rc = SQLITE_NOMEM;
    }else if( (rc&0xff)==SQLITE_READONLY ){
      pWal->readOnly |= WAL_SHM_RDONLY;
      if( rc==SQLITE_READONLY ){
        rc = SQLITE_OK;







|
>
>







61086
61087
61088
61089
61090
61091
61092
61093
61094
61095
61096
61097
61098
61099
61100
61101
61102
  if( pWal->exclusiveMode==WAL_HEAPMEMORY_MODE ){
    pWal->apWiData[iPage] = (u32 volatile *)sqlite3MallocZero(WALINDEX_PGSZ);
    if( !pWal->apWiData[iPage] ) rc = SQLITE_NOMEM_BKPT;
  }else{
    rc = sqlite3OsShmMap(pWal->pDbFd, iPage, WALINDEX_PGSZ,
        pWal->writeLock, (void volatile **)&pWal->apWiData[iPage]
    );
    assert( pWal->apWiData[iPage]!=0
         || rc!=SQLITE_OK
         || (pWal->writeLock==0 && iPage==0) );
    testcase( pWal->apWiData[iPage]==0 && rc==SQLITE_OK );
    if( rc==SQLITE_OK ){
      if( iPage>0 && sqlite3FaultSim(600) ) rc = SQLITE_NOMEM;
    }else if( (rc&0xff)==SQLITE_READONLY ){
      pWal->readOnly |= WAL_SHM_RDONLY;
      if( rc==SQLITE_READONLY ){
        rc = SQLITE_OK;
61181
61182
61183
61184
61185
61186
61187
61188
61189
61190
61191
61192
61193
61194
61195
61196
61197
61198
61199
61200
61201
61202
61203
61204
61205
61206
61207
61208

61209
61210
61211
61212
61213
61214
61215
61216
**
** Set output variable pLoc->aHash to point to the start of the hash table
** in the wal-index file. Set pLoc->iZero to one less than the frame
** number of the first frame indexed by this hash table. If a
** slot in the hash table is set to N, it refers to frame number
** (pLoc->iZero+N) in the log.
**
** Finally, set pLoc->aPgno so that pLoc->aPgno[1] is the page number of the
** first frame indexed by the hash table, frame (pLoc->iZero+1).
*/
static int walHashGet(
  Wal *pWal,                      /* WAL handle */
  int iHash,                      /* Find the iHash'th table */
  WalHashLoc *pLoc                /* OUT: Hash table location */
){
  int rc;                         /* Return code */

  rc = walIndexPage(pWal, iHash, &pLoc->aPgno);
  assert( rc==SQLITE_OK || iHash>0 );

  if( rc==SQLITE_OK ){
    pLoc->aHash = (volatile ht_slot *)&pLoc->aPgno[HASHTABLE_NPAGE];
    if( iHash==0 ){
      pLoc->aPgno = &pLoc->aPgno[WALINDEX_HDR_SIZE/sizeof(u32)];
      pLoc->iZero = 0;
    }else{
      pLoc->iZero = HASHTABLE_NPAGE_ONE + (iHash-1)*HASHTABLE_NPAGE;
    }

    pLoc->aPgno = &pLoc->aPgno[-1];
  }
  return rc;
}

/*
** Return the number of the wal-index page that contains the hash-table
** and page-number array that contain entries corresponding to WAL frame







|
|











|







>
|







61427
61428
61429
61430
61431
61432
61433
61434
61435
61436
61437
61438
61439
61440
61441
61442
61443
61444
61445
61446
61447
61448
61449
61450
61451
61452
61453
61454
61455
61456
61457
61458
61459
61460
61461
61462
61463
**
** Set output variable pLoc->aHash to point to the start of the hash table
** in the wal-index file. Set pLoc->iZero to one less than the frame
** number of the first frame indexed by this hash table. If a
** slot in the hash table is set to N, it refers to frame number
** (pLoc->iZero+N) in the log.
**
** Finally, set pLoc->aPgno so that pLoc->aPgno[0] is the page number of the
** first frame indexed by the hash table, frame (pLoc->iZero).
*/
static int walHashGet(
  Wal *pWal,                      /* WAL handle */
  int iHash,                      /* Find the iHash'th table */
  WalHashLoc *pLoc                /* OUT: Hash table location */
){
  int rc;                         /* Return code */

  rc = walIndexPage(pWal, iHash, &pLoc->aPgno);
  assert( rc==SQLITE_OK || iHash>0 );

  if( pLoc->aPgno ){
    pLoc->aHash = (volatile ht_slot *)&pLoc->aPgno[HASHTABLE_NPAGE];
    if( iHash==0 ){
      pLoc->aPgno = &pLoc->aPgno[WALINDEX_HDR_SIZE/sizeof(u32)];
      pLoc->iZero = 0;
    }else{
      pLoc->iZero = HASHTABLE_NPAGE_ONE + (iHash-1)*HASHTABLE_NPAGE;
    }
  }else if( NEVER(rc==SQLITE_OK) ){
    rc = SQLITE_ERROR;
  }
  return rc;
}

/*
** Return the number of the wal-index page that contains the hash-table
** and page-number array that contain entries corresponding to WAL frame
61284
61285
61286
61287
61288
61289
61290
61291

61292
61293
61294
61295
61296
61297
61298
61299
61300
61301
61302
61303
61304
61305
61306
61307
61308
61309
61310
61311
61312
      sLoc.aHash[i] = 0;
    }
  }

  /* Zero the entries in the aPgno array that correspond to frames with
  ** frame numbers greater than pWal->hdr.mxFrame.
  */
  nByte = (int)((char *)sLoc.aHash - (char *)&sLoc.aPgno[iLimit+1]);

  memset((void *)&sLoc.aPgno[iLimit+1], 0, nByte);

#ifdef SQLITE_ENABLE_EXPENSIVE_ASSERT
  /* Verify that the every entry in the mapping region is still reachable
  ** via the hash table even after the cleanup.
  */
  if( iLimit ){
    int j;           /* Loop counter */
    int iKey;        /* Hash key */
    for(j=1; j<=iLimit; j++){
      for(iKey=walHash(sLoc.aPgno[j]);sLoc.aHash[iKey];iKey=walNextHash(iKey)){
        if( sLoc.aHash[iKey]==j ) break;
      }
      assert( sLoc.aHash[iKey]==j );
    }
  }
#endif /* SQLITE_ENABLE_EXPENSIVE_ASSERT */
}


/*







|
>
|








|

|

|







61531
61532
61533
61534
61535
61536
61537
61538
61539
61540
61541
61542
61543
61544
61545
61546
61547
61548
61549
61550
61551
61552
61553
61554
61555
61556
61557
61558
61559
61560
      sLoc.aHash[i] = 0;
    }
  }

  /* Zero the entries in the aPgno array that correspond to frames with
  ** frame numbers greater than pWal->hdr.mxFrame.
  */
  nByte = (int)((char *)sLoc.aHash - (char *)&sLoc.aPgno[iLimit]);
  assert( nByte>=0 );
  memset((void *)&sLoc.aPgno[iLimit], 0, nByte);

#ifdef SQLITE_ENABLE_EXPENSIVE_ASSERT
  /* Verify that the every entry in the mapping region is still reachable
  ** via the hash table even after the cleanup.
  */
  if( iLimit ){
    int j;           /* Loop counter */
    int iKey;        /* Hash key */
    for(j=0; j<iLimit; j++){
      for(iKey=walHash(sLoc.aPgno[j]);sLoc.aHash[iKey];iKey=walNextHash(iKey)){
        if( sLoc.aHash[iKey]==j+1 ) break;
      }
      assert( sLoc.aHash[iKey]==j+1 );
    }
  }
#endif /* SQLITE_ENABLE_EXPENSIVE_ASSERT */
}


/*
61330
61331
61332
61333
61334
61335
61336
61337
61338
61339
61340
61341
61342
61343
61344
61345
61346
61347
61348
61349
61350
61351
61352
61353
61354
61355
61356
61357
61358
61359
61360
61361
61362
61363
61364
61365
61366
61367
61368
61369
61370
61371
61372
61373
61374
61375
61376
61377
61378
61379
61380
61381
61382
61383
61384
61385
61386
61387
61388
61389
61390
61391
61392
61393
61394
61395
61396
61397
    idx = iFrame - sLoc.iZero;
    assert( idx <= HASHTABLE_NSLOT/2 + 1 );

    /* If this is the first entry to be added to this hash-table, zero the
    ** entire hash table and aPgno[] array before proceeding.
    */
    if( idx==1 ){
      int nByte = (int)((u8 *)&sLoc.aHash[HASHTABLE_NSLOT]
                               - (u8 *)&sLoc.aPgno[1]);
      memset((void*)&sLoc.aPgno[1], 0, nByte);
    }

    /* If the entry in aPgno[] is already set, then the previous writer
    ** must have exited unexpectedly in the middle of a transaction (after
    ** writing one or more dirty pages to the WAL to free up memory).
    ** Remove the remnants of that writers uncommitted transaction from
    ** the hash-table before writing any new entries.
    */
    if( sLoc.aPgno[idx] ){
      walCleanupHash(pWal);
      assert( !sLoc.aPgno[idx] );
    }

    /* Write the aPgno[] array entry and the hash-table slot. */
    nCollide = idx;
    for(iKey=walHash(iPage); sLoc.aHash[iKey]; iKey=walNextHash(iKey)){
      if( (nCollide--)==0 ) return SQLITE_CORRUPT_BKPT;
    }
    sLoc.aPgno[idx] = iPage;
    AtomicStore(&sLoc.aHash[iKey], (ht_slot)idx);

#ifdef SQLITE_ENABLE_EXPENSIVE_ASSERT
    /* Verify that the number of entries in the hash table exactly equals
    ** the number of entries in the mapping region.
    */
    {
      int i;           /* Loop counter */
      int nEntry = 0;  /* Number of entries in the hash table */
      for(i=0; i<HASHTABLE_NSLOT; i++){ if( sLoc.aHash[i] ) nEntry++; }
      assert( nEntry==idx );
    }

    /* Verify that the every entry in the mapping region is reachable
    ** via the hash table.  This turns out to be a really, really expensive
    ** thing to check, so only do this occasionally - not on every
    ** iteration.
    */
    if( (idx&0x3ff)==0 ){
      int i;           /* Loop counter */
      for(i=1; i<=idx; i++){
        for(iKey=walHash(sLoc.aPgno[i]);
            sLoc.aHash[iKey];
            iKey=walNextHash(iKey)){
          if( sLoc.aHash[iKey]==i ) break;
        }
        assert( sLoc.aHash[iKey]==i );
      }
    }
#endif /* SQLITE_ENABLE_EXPENSIVE_ASSERT */
  }


  return rc;
}


/*
** Recover the wal-index by reading the write-ahead log file.







|
|
|








|

|







|




















|



|

|




<







61578
61579
61580
61581
61582
61583
61584
61585
61586
61587
61588
61589
61590
61591
61592
61593
61594
61595
61596
61597
61598
61599
61600
61601
61602
61603
61604
61605
61606
61607
61608
61609
61610
61611
61612
61613
61614
61615
61616
61617
61618
61619
61620
61621
61622
61623
61624
61625
61626
61627
61628
61629
61630
61631
61632
61633
61634
61635
61636
61637

61638
61639
61640
61641
61642
61643
61644
    idx = iFrame - sLoc.iZero;
    assert( idx <= HASHTABLE_NSLOT/2 + 1 );

    /* If this is the first entry to be added to this hash-table, zero the
    ** entire hash table and aPgno[] array before proceeding.
    */
    if( idx==1 ){
      int nByte = (int)((u8*)&sLoc.aHash[HASHTABLE_NSLOT] - (u8*)sLoc.aPgno);
      assert( nByte>=0 );
      memset((void*)sLoc.aPgno, 0, nByte);
    }

    /* If the entry in aPgno[] is already set, then the previous writer
    ** must have exited unexpectedly in the middle of a transaction (after
    ** writing one or more dirty pages to the WAL to free up memory).
    ** Remove the remnants of that writers uncommitted transaction from
    ** the hash-table before writing any new entries.
    */
    if( sLoc.aPgno[idx-1] ){
      walCleanupHash(pWal);
      assert( !sLoc.aPgno[idx-1] );
    }

    /* Write the aPgno[] array entry and the hash-table slot. */
    nCollide = idx;
    for(iKey=walHash(iPage); sLoc.aHash[iKey]; iKey=walNextHash(iKey)){
      if( (nCollide--)==0 ) return SQLITE_CORRUPT_BKPT;
    }
    sLoc.aPgno[idx-1] = iPage;
    AtomicStore(&sLoc.aHash[iKey], (ht_slot)idx);

#ifdef SQLITE_ENABLE_EXPENSIVE_ASSERT
    /* Verify that the number of entries in the hash table exactly equals
    ** the number of entries in the mapping region.
    */
    {
      int i;           /* Loop counter */
      int nEntry = 0;  /* Number of entries in the hash table */
      for(i=0; i<HASHTABLE_NSLOT; i++){ if( sLoc.aHash[i] ) nEntry++; }
      assert( nEntry==idx );
    }

    /* Verify that the every entry in the mapping region is reachable
    ** via the hash table.  This turns out to be a really, really expensive
    ** thing to check, so only do this occasionally - not on every
    ** iteration.
    */
    if( (idx&0x3ff)==0 ){
      int i;           /* Loop counter */
      for(i=0; i<idx; i++){
        for(iKey=walHash(sLoc.aPgno[i]);
            sLoc.aHash[iKey];
            iKey=walNextHash(iKey)){
          if( sLoc.aHash[iKey]==i+1 ) break;
        }
        assert( sLoc.aHash[iKey]==i+1 );
      }
    }
#endif /* SQLITE_ENABLE_EXPENSIVE_ASSERT */
  }


  return rc;
}


/*
** Recover the wal-index by reading the write-ahead log file.
61505
61506
61507
61508
61509
61510
61511

61512
61513
61514
61515
61516
61517
61518
61519
    for(iPg=0; iPg<=(u32)walFramePage(iLastFrame); iPg++){
      u32 *aShare;
      u32 iFrame;                 /* Index of last frame read */
      u32 iLast = MIN(iLastFrame, HASHTABLE_NPAGE_ONE+iPg*HASHTABLE_NPAGE);
      u32 iFirst = 1 + (iPg==0?0:HASHTABLE_NPAGE_ONE+(iPg-1)*HASHTABLE_NPAGE);
      u32 nHdr, nHdr32;
      rc = walIndexPage(pWal, iPg, (volatile u32**)&aShare);

      if( rc ) break;
      pWal->apWiData[iPg] = aPrivate;

      for(iFrame=iFirst; iFrame<=iLast; iFrame++){
        i64 iOffset = walFrameOffset(iFrame, szPage);
        u32 pgno;                 /* Database page number for frame */
        u32 nTruncate;            /* dbsize field from frame header */








>
|







61752
61753
61754
61755
61756
61757
61758
61759
61760
61761
61762
61763
61764
61765
61766
61767
    for(iPg=0; iPg<=(u32)walFramePage(iLastFrame); iPg++){
      u32 *aShare;
      u32 iFrame;                 /* Index of last frame read */
      u32 iLast = MIN(iLastFrame, HASHTABLE_NPAGE_ONE+iPg*HASHTABLE_NPAGE);
      u32 iFirst = 1 + (iPg==0?0:HASHTABLE_NPAGE_ONE+(iPg-1)*HASHTABLE_NPAGE);
      u32 nHdr, nHdr32;
      rc = walIndexPage(pWal, iPg, (volatile u32**)&aShare);
      assert( aShare!=0 || rc!=SQLITE_OK );
      if( aShare==0 ) break;
      pWal->apWiData[iPg] = aPrivate;

      for(iFrame=iFirst; iFrame<=iLast; iFrame++){
        i64 iOffset = walFrameOffset(iFrame, szPage);
        u32 pgno;                 /* Database page number for frame */
        u32 nTruncate;            /* dbsize field from frame header */

62002
62003
62004
62005
62006
62007
62008
62009
62010
62011
62012
62013
62014
62015
62016

    rc = walHashGet(pWal, i, &sLoc);
    if( rc==SQLITE_OK ){
      int j;                      /* Counter variable */
      int nEntry;                 /* Number of entries in this segment */
      ht_slot *aIndex;            /* Sorted index for this segment */

      sLoc.aPgno++;
      if( (i+1)==nSegment ){
        nEntry = (int)(iLast - sLoc.iZero);
      }else{
        nEntry = (int)((u32*)sLoc.aHash - (u32*)sLoc.aPgno);
      }
      aIndex = &((ht_slot *)&p->aSegment[p->nSegment])[sLoc.iZero];
      sLoc.iZero++;







<







62250
62251
62252
62253
62254
62255
62256

62257
62258
62259
62260
62261
62262
62263

    rc = walHashGet(pWal, i, &sLoc);
    if( rc==SQLITE_OK ){
      int j;                      /* Counter variable */
      int nEntry;                 /* Number of entries in this segment */
      ht_slot *aIndex;            /* Sorted index for this segment */


      if( (i+1)==nSegment ){
        nEntry = (int)(iLast - sLoc.iZero);
      }else{
        nEntry = (int)((u32*)sLoc.aHash - (u32*)sLoc.aPgno);
      }
      aIndex = &((ht_slot *)&p->aSegment[p->nSegment])[sLoc.iZero];
      sLoc.iZero++;
63141
63142
63143
63144
63145
63146
63147

63148
63149
63150
63151
63152
63153
63154
63155
          WalHashLoc sLoc;          /* Hash table location */
          u32 pgno;                 /* Page number in db file */
          i64 iDbOff;               /* Offset of db file entry */
          i64 iWalOff;              /* Offset of wal file entry */

          rc = walHashGet(pWal, walFramePage(i), &sLoc);
          if( rc!=SQLITE_OK ) break;

          pgno = sLoc.aPgno[i-sLoc.iZero];
          iDbOff = (i64)(pgno-1) * szPage;

          if( iDbOff+szPage<=szDb ){
            iWalOff = walFrameOffset(i, szPage) + WAL_FRAME_HDRSIZE;
            rc = sqlite3OsRead(pWal->pWalFd, pBuf1, szPage, iWalOff);

            if( rc==SQLITE_OK ){







>
|







63388
63389
63390
63391
63392
63393
63394
63395
63396
63397
63398
63399
63400
63401
63402
63403
          WalHashLoc sLoc;          /* Hash table location */
          u32 pgno;                 /* Page number in db file */
          i64 iDbOff;               /* Offset of db file entry */
          i64 iWalOff;              /* Offset of wal file entry */

          rc = walHashGet(pWal, walFramePage(i), &sLoc);
          if( rc!=SQLITE_OK ) break;
          assert( i - sLoc.iZero - 1 >=0 );
          pgno = sLoc.aPgno[i-sLoc.iZero-1];
          iDbOff = (i64)(pgno-1) * szPage;

          if( iDbOff+szPage<=szDb ){
            iWalOff = walFrameOffset(i, szPage) + WAL_FRAME_HDRSIZE;
            rc = sqlite3OsRead(pWal->pWalFd, pBuf1, szPage, iWalOff);

            if( rc==SQLITE_OK ){
63374
63375
63376
63377
63378
63379
63380
63381
63382
63383
63384
63385
63386
63387
63388
    if( rc!=SQLITE_OK ){
      return rc;
    }
    nCollide = HASHTABLE_NSLOT;
    iKey = walHash(pgno);
    while( (iH = AtomicLoad(&sLoc.aHash[iKey]))!=0 ){
      u32 iFrame = iH + sLoc.iZero;
      if( iFrame<=iLast && iFrame>=pWal->minFrame && sLoc.aPgno[iH]==pgno ){
        assert( iFrame>iRead || CORRUPT_DB );
        iRead = iFrame;
      }
      if( (nCollide--)==0 ){
        return SQLITE_CORRUPT_BKPT;
      }
      iKey = walNextHash(iKey);







|







63622
63623
63624
63625
63626
63627
63628
63629
63630
63631
63632
63633
63634
63635
63636
    if( rc!=SQLITE_OK ){
      return rc;
    }
    nCollide = HASHTABLE_NSLOT;
    iKey = walHash(pgno);
    while( (iH = AtomicLoad(&sLoc.aHash[iKey]))!=0 ){
      u32 iFrame = iH + sLoc.iZero;
      if( iFrame<=iLast && iFrame>=pWal->minFrame && sLoc.aPgno[iH-1]==pgno ){
        assert( iFrame>iRead || CORRUPT_DB );
        iRead = iFrame;
      }
      if( (nCollide--)==0 ){
        return SQLITE_CORRUPT_BKPT;
      }
      iKey = walNextHash(iKey);
64626
64627
64628
64629
64630
64631
64632
64633
64634
64635
64636
64637
64638
64639
64640
** "extra" information associated with each page of the pager.)
**
** Access to all fields of this structure is controlled by the mutex
** stored in MemPage.pBt->mutex.
*/
struct MemPage {
  u8 isInit;           /* True if previously initialized. MUST BE FIRST! */
  u8 bBusy;            /* Prevent endless loops on corrupt database files */
  u8 intKey;           /* True if table b-trees.  False for index b-trees */
  u8 intKeyLeaf;       /* True if the leaf of an intKey table */
  Pgno pgno;           /* Page number for this page */
  /* Only the first 8 bytes (above) are zeroed by pager.c when a new page
  ** is allocated. All fields that follow must be initialized before use */
  u8 leaf;             /* True if a leaf page */
  u8 hdrOffset;        /* 100 for page 1.  0 otherwise */







<







64874
64875
64876
64877
64878
64879
64880

64881
64882
64883
64884
64885
64886
64887
** "extra" information associated with each page of the pager.)
**
** Access to all fields of this structure is controlled by the mutex
** stored in MemPage.pBt->mutex.
*/
struct MemPage {
  u8 isInit;           /* True if previously initialized. MUST BE FIRST! */

  u8 intKey;           /* True if table b-trees.  False for index b-trees */
  u8 intKeyLeaf;       /* True if the leaf of an intKey table */
  Pgno pgno;           /* Page number for this page */
  /* Only the first 8 bytes (above) are zeroed by pager.c when a new page
  ** is allocated. All fields that follow must be initialized before use */
  u8 leaf;             /* True if a leaf page */
  u8 hdrOffset;        /* 100 for page 1.  0 otherwise */
66868
66869
66870
66871
66872
66873
66874
66875
66876
66877
66878
66879
66880
66881
66882
        }
        if( iFree2 ){
          if( iFree+sz>iFree2 ) return SQLITE_CORRUPT_PAGE(pPage);
          sz2 = get2byte(&data[iFree2+2]);
          if( iFree2+sz2 > usableSize ) return SQLITE_CORRUPT_PAGE(pPage);
          memmove(&data[iFree+sz+sz2], &data[iFree+sz], iFree2-(iFree+sz));
          sz += sz2;
        }else if( iFree+sz>usableSize ){
          return SQLITE_CORRUPT_PAGE(pPage);
        }

        cbrk = top+sz;
        assert( cbrk+(iFree-top) <= usableSize );
        memmove(&data[cbrk], &data[top], iFree-top);
        for(pAddr=&data[cellOffset]; pAddr<pEnd; pAddr+=2){







|







67115
67116
67117
67118
67119
67120
67121
67122
67123
67124
67125
67126
67127
67128
67129
        }
        if( iFree2 ){
          if( iFree+sz>iFree2 ) return SQLITE_CORRUPT_PAGE(pPage);
          sz2 = get2byte(&data[iFree2+2]);
          if( iFree2+sz2 > usableSize ) return SQLITE_CORRUPT_PAGE(pPage);
          memmove(&data[iFree+sz+sz2], &data[iFree+sz], iFree2-(iFree+sz));
          sz += sz2;
        }else if( NEVER(iFree+sz>usableSize) ){
          return SQLITE_CORRUPT_PAGE(pPage);
        }

        cbrk = top+sz;
        assert( cbrk+(iFree-top) <= usableSize );
        memmove(&data[cbrk], &data[top], iFree-top);
        for(pAddr=&data[cellOffset]; pAddr<pEnd; pAddr+=2){
68073
68074
68075
68076
68077
68078
68079
68080

68081



68082





68083

68084
68085
68086
68087
68088
68089
68090
68091
68092
68093
68094
68095
68096
68097
68098
68099
68100
68101
68102
68103

68104
68105
68106
68107
68108
68109
68110
}

/*
** Make sure pBt->pTmpSpace points to an allocation of
** MX_CELL_SIZE(pBt) bytes with a 4-byte prefix for a left-child
** pointer.
*/
static void allocateTempSpace(BtShared *pBt){

  if( !pBt->pTmpSpace ){



    pBt->pTmpSpace = sqlite3PageMalloc( pBt->pageSize );







    /* One of the uses of pBt->pTmpSpace is to format cells before
    ** inserting them into a leaf page (function fillInCell()). If
    ** a cell is less than 4 bytes in size, it is rounded up to 4 bytes
    ** by the various routines that manipulate binary cells. Which
    ** can mean that fillInCell() only initializes the first 2 or 3
    ** bytes of pTmpSpace, but that the first 4 bytes are copied from
    ** it into a database page. This is not actually a problem, but it
    ** does cause a valgrind error when the 1 or 2 bytes of unitialized
    ** data is passed to system call write(). So to avoid this error,
    ** zero the first 4 bytes of temp space here.
    **
    ** Also:  Provide four bytes of initialized space before the
    ** beginning of pTmpSpace as an area available to prepend the
    ** left-child pointer to the beginning of a cell.
    */
    if( pBt->pTmpSpace ){
      memset(pBt->pTmpSpace, 0, 8);
      pBt->pTmpSpace += 4;
    }
  }

}

/*
** Free the pBt->pTmpSpace allocation
*/
static void freeTempSpace(BtShared *pBt){
  if( pBt->pTmpSpace ){







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







68320
68321
68322
68323
68324
68325
68326
68327
68328
68329
68330
68331
68332
68333
68334
68335
68336
68337
68338
68339
68340
68341
68342
68343
68344
68345
68346
68347
68348
68349
68350
68351
68352
68353
68354
68355

68356
68357


68358
68359
68360
68361
68362
68363
68364
68365
}

/*
** Make sure pBt->pTmpSpace points to an allocation of
** MX_CELL_SIZE(pBt) bytes with a 4-byte prefix for a left-child
** pointer.
*/
static SQLITE_NOINLINE int allocateTempSpace(BtShared *pBt){
  assert( pBt!=0 );
  assert( pBt->pTmpSpace==0 );
  /* This routine is called only by btreeCursor() when allocating the
  ** first write cursor for the BtShared object */
  assert( pBt->pCursor!=0 && (pBt->pCursor->curFlags & BTCF_WriteFlag)!=0 );
  pBt->pTmpSpace = sqlite3PageMalloc( pBt->pageSize );
  if( pBt->pTmpSpace==0 ){
    BtCursor *pCur = pBt->pCursor;
    pBt->pCursor = pCur->pNext;  /* Unlink the cursor */
    memset(pCur, 0, sizeof(*pCur));
    return SQLITE_NOMEM_BKPT;
  }

  /* One of the uses of pBt->pTmpSpace is to format cells before
  ** inserting them into a leaf page (function fillInCell()). If
  ** a cell is less than 4 bytes in size, it is rounded up to 4 bytes
  ** by the various routines that manipulate binary cells. Which
  ** can mean that fillInCell() only initializes the first 2 or 3
  ** bytes of pTmpSpace, but that the first 4 bytes are copied from
  ** it into a database page. This is not actually a problem, but it
  ** does cause a valgrind error when the 1 or 2 bytes of unitialized
  ** data is passed to system call write(). So to avoid this error,
  ** zero the first 4 bytes of temp space here.
  **
  ** Also:  Provide four bytes of initialized space before the
  ** beginning of pTmpSpace as an area available to prepend the
  ** left-child pointer to the beginning of a cell.
  */

  memset(pBt->pTmpSpace, 0, 8);
  pBt->pTmpSpace += 4;


  return SQLITE_OK;
}

/*
** Free the pBt->pTmpSpace allocation
*/
static void freeTempSpace(BtShared *pBt){
  if( pBt->pTmpSpace ){
68475
68476
68477
68478
68479
68480
68481
68482
68483
68484
68485
68486
68487
68488
68489
68490
68491
68492
68493
68494
68495
68496
68497
68498
68499
68500
68501
** is returned if we run out of memory.
*/
static int lockBtree(BtShared *pBt){
  int rc;              /* Result code from subfunctions */
  MemPage *pPage1;     /* Page 1 of the database file */
  u32 nPage;           /* Number of pages in the database */
  u32 nPageFile = 0;   /* Number of pages in the database file */
  u32 nPageHeader;     /* Number of pages in the database according to hdr */

  assert( sqlite3_mutex_held(pBt->mutex) );
  assert( pBt->pPage1==0 );
  rc = sqlite3PagerSharedLock(pBt->pPager);
  if( rc!=SQLITE_OK ) return rc;
  rc = btreeGetPage(pBt, 1, &pPage1, 0);
  if( rc!=SQLITE_OK ) return rc;

  /* Do some checking to help insure the file we opened really is
  ** a valid database file.
  */
  nPage = nPageHeader = get4byte(28+(u8*)pPage1->aData);
  sqlite3PagerPagecount(pBt->pPager, (int*)&nPageFile);
  if( nPage==0 || memcmp(24+(u8*)pPage1->aData, 92+(u8*)pPage1->aData,4)!=0 ){
    nPage = nPageFile;
  }
  if( (pBt->db->flags & SQLITE_ResetDatabase)!=0 ){
    nPage = 0;
  }







<











|







68730
68731
68732
68733
68734
68735
68736

68737
68738
68739
68740
68741
68742
68743
68744
68745
68746
68747
68748
68749
68750
68751
68752
68753
68754
68755
** is returned if we run out of memory.
*/
static int lockBtree(BtShared *pBt){
  int rc;              /* Result code from subfunctions */
  MemPage *pPage1;     /* Page 1 of the database file */
  u32 nPage;           /* Number of pages in the database */
  u32 nPageFile = 0;   /* Number of pages in the database file */


  assert( sqlite3_mutex_held(pBt->mutex) );
  assert( pBt->pPage1==0 );
  rc = sqlite3PagerSharedLock(pBt->pPager);
  if( rc!=SQLITE_OK ) return rc;
  rc = btreeGetPage(pBt, 1, &pPage1, 0);
  if( rc!=SQLITE_OK ) return rc;

  /* Do some checking to help insure the file we opened really is
  ** a valid database file.
  */
  nPage = get4byte(28+(u8*)pPage1->aData);
  sqlite3PagerPagecount(pBt->pPager, (int*)&nPageFile);
  if( nPage==0 || memcmp(24+(u8*)pPage1->aData, 92+(u8*)pPage1->aData,4)!=0 ){
    nPage = nPageFile;
  }
  if( (pBt->db->flags & SQLITE_ResetDatabase)!=0 ){
    nPage = 0;
  }
69320
69321
69322
69323
69324
69325
69326
69327
69328
69329
69330
69331
69332
69333
69334
69335







69336
69337
69338
69339
69340
69341
69342
69343

69344
69345
69346
69347
69348
69349
69350
69351
69352
69353
69354
69355
69356






















69357
69358
69359
69360
69361
69362
69363
69364
69365
69366

69367
69368

69369
69370
69371
69372
69373
69374
69375
  sqlite3BtreeLeave(p);
  return rc;
}

/*
** This routine is called prior to sqlite3PagerCommit when a transaction
** is committed for an auto-vacuum database.
**
** If SQLITE_OK is returned, then *pnTrunc is set to the number of pages
** the database file should be truncated to during the commit process.
** i.e. the database has been reorganized so that only the first *pnTrunc
** pages are in use.
*/
static int autoVacuumCommit(BtShared *pBt){
  int rc = SQLITE_OK;
  Pager *pPager = pBt->pPager;







  VVA_ONLY( int nRef = sqlite3PagerRefcount(pPager); )

  assert( sqlite3_mutex_held(pBt->mutex) );
  invalidateAllOverflowCache(pBt);
  assert(pBt->autoVacuum);
  if( !pBt->incrVacuum ){
    Pgno nFin;         /* Number of pages in database after autovacuuming */
    Pgno nFree;        /* Number of pages on the freelist initially */

    Pgno iFree;        /* The next page to be freed */
    Pgno nOrig;        /* Database size before freeing */

    nOrig = btreePagecount(pBt);
    if( PTRMAP_ISPAGE(pBt, nOrig) || nOrig==PENDING_BYTE_PAGE(pBt) ){
      /* It is not possible to create a database for which the final page
      ** is either a pointer-map page or the pending-byte page. If one
      ** is encountered, this indicates corruption.
      */
      return SQLITE_CORRUPT_BKPT;
    }

    nFree = get4byte(&pBt->pPage1->aData[36]);






















    nFin = finalDbSize(pBt, nOrig, nFree);
    if( nFin>nOrig ) return SQLITE_CORRUPT_BKPT;
    if( nFin<nOrig ){
      rc = saveAllCursors(pBt, 0, 0);
    }
    for(iFree=nOrig; iFree>nFin && rc==SQLITE_OK; iFree--){
      rc = incrVacuumStep(pBt, nFin, iFree, 1);
    }
    if( (rc==SQLITE_DONE || rc==SQLITE_OK) && nFree>0 ){
      rc = sqlite3PagerWrite(pBt->pPage1->pDbPage);

      put4byte(&pBt->pPage1->aData[32], 0);
      put4byte(&pBt->pPage1->aData[36], 0);

      put4byte(&pBt->pPage1->aData[28], nFin);
      pBt->bDoTruncate = 1;
      pBt->nPage = nFin;
    }
    if( rc!=SQLITE_OK ){
      sqlite3PagerRollback(pPager);
    }







<
<
<
<
<

|

|
>
>
>
>
>
>
>
|







>













>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
|





|



>
|
|
>







69574
69575
69576
69577
69578
69579
69580





69581
69582
69583
69584
69585
69586
69587
69588
69589
69590
69591
69592
69593
69594
69595
69596
69597
69598
69599
69600
69601
69602
69603
69604
69605
69606
69607
69608
69609
69610
69611
69612
69613
69614
69615
69616
69617
69618
69619
69620
69621
69622
69623
69624
69625
69626
69627
69628
69629
69630
69631
69632
69633
69634
69635
69636
69637
69638
69639
69640
69641
69642
69643
69644
69645
69646
69647
69648
69649
69650
69651
69652
69653
69654
69655
69656
  sqlite3BtreeLeave(p);
  return rc;
}

/*
** This routine is called prior to sqlite3PagerCommit when a transaction
** is committed for an auto-vacuum database.





*/
static int autoVacuumCommit(Btree *p){
  int rc = SQLITE_OK;
  Pager *pPager;
  BtShared *pBt;
  sqlite3 *db;
  VVA_ONLY( int nRef );

  assert( p!=0 );
  pBt = p->pBt;
  pPager = pBt->pPager;
  VVA_ONLY( nRef = sqlite3PagerRefcount(pPager); )

  assert( sqlite3_mutex_held(pBt->mutex) );
  invalidateAllOverflowCache(pBt);
  assert(pBt->autoVacuum);
  if( !pBt->incrVacuum ){
    Pgno nFin;         /* Number of pages in database after autovacuuming */
    Pgno nFree;        /* Number of pages on the freelist initially */
    Pgno nVac;         /* Number of pages to vacuum */
    Pgno iFree;        /* The next page to be freed */
    Pgno nOrig;        /* Database size before freeing */

    nOrig = btreePagecount(pBt);
    if( PTRMAP_ISPAGE(pBt, nOrig) || nOrig==PENDING_BYTE_PAGE(pBt) ){
      /* It is not possible to create a database for which the final page
      ** is either a pointer-map page or the pending-byte page. If one
      ** is encountered, this indicates corruption.
      */
      return SQLITE_CORRUPT_BKPT;
    }

    nFree = get4byte(&pBt->pPage1->aData[36]);
    db = p->db;
    if( db->xAutovacPages ){
      int iDb;
      for(iDb=0; ALWAYS(iDb<db->nDb); iDb++){
        if( db->aDb[iDb].pBt==p ) break;
      }
      nVac = db->xAutovacPages(
        db->pAutovacPagesArg,
        db->aDb[iDb].zDbSName,
        nOrig,
        nFree,
        pBt->pageSize
      );
      if( nVac>nFree ){
        nVac = nFree;
      }
      if( nVac==0 ){
        return SQLITE_OK;
      }
    }else{
      nVac = nFree;
    }
    nFin = finalDbSize(pBt, nOrig, nVac);
    if( nFin>nOrig ) return SQLITE_CORRUPT_BKPT;
    if( nFin<nOrig ){
      rc = saveAllCursors(pBt, 0, 0);
    }
    for(iFree=nOrig; iFree>nFin && rc==SQLITE_OK; iFree--){
      rc = incrVacuumStep(pBt, nFin, iFree, nVac==nFree);
    }
    if( (rc==SQLITE_DONE || rc==SQLITE_OK) && nFree>0 ){
      rc = sqlite3PagerWrite(pBt->pPage1->pDbPage);
      if( nVac==nFree ){
        put4byte(&pBt->pPage1->aData[32], 0);
        put4byte(&pBt->pPage1->aData[36], 0);
      }
      put4byte(&pBt->pPage1->aData[28], nFin);
      pBt->bDoTruncate = 1;
      pBt->nPage = nFin;
    }
    if( rc!=SQLITE_OK ){
      sqlite3PagerRollback(pPager);
    }
69412
69413
69414
69415
69416
69417
69418
69419
69420
69421
69422
69423
69424
69425
69426
SQLITE_PRIVATE int sqlite3BtreeCommitPhaseOne(Btree *p, const char *zSuperJrnl){
  int rc = SQLITE_OK;
  if( p->inTrans==TRANS_WRITE ){
    BtShared *pBt = p->pBt;
    sqlite3BtreeEnter(p);
#ifndef SQLITE_OMIT_AUTOVACUUM
    if( pBt->autoVacuum ){
      rc = autoVacuumCommit(pBt);
      if( rc!=SQLITE_OK ){
        sqlite3BtreeLeave(p);
        return rc;
      }
    }
    if( pBt->bDoTruncate ){
      sqlite3PagerTruncateImage(pBt->pPager, pBt->nPage);







|







69693
69694
69695
69696
69697
69698
69699
69700
69701
69702
69703
69704
69705
69706
69707
SQLITE_PRIVATE int sqlite3BtreeCommitPhaseOne(Btree *p, const char *zSuperJrnl){
  int rc = SQLITE_OK;
  if( p->inTrans==TRANS_WRITE ){
    BtShared *pBt = p->pBt;
    sqlite3BtreeEnter(p);
#ifndef SQLITE_OMIT_AUTOVACUUM
    if( pBt->autoVacuum ){
      rc = autoVacuumCommit(p);
      if( rc!=SQLITE_OK ){
        sqlite3BtreeLeave(p);
        return rc;
      }
    }
    if( pBt->bDoTruncate ){
      sqlite3PagerTruncateImage(pBt->pPager, pBt->nPage);
69811
69812
69813
69814
69815
69816
69817
69818
69819
69820
69821
69822
69823
69824
69825
69826
69827
69828
69829
69830
69831
69832
69833
69834
69835
69836
69837
69838
69839
69840
69841
69842
69843
69844
69845
69846
69847

69848
69849


69850




69851
69852
69853
69854
69855
69856
69857

  /* Assert that the caller has opened the required transaction. */
  assert( p->inTrans>TRANS_NONE );
  assert( wrFlag==0 || p->inTrans==TRANS_WRITE );
  assert( pBt->pPage1 && pBt->pPage1->aData );
  assert( wrFlag==0 || (pBt->btsFlags & BTS_READ_ONLY)==0 );

  if( wrFlag ){
    allocateTempSpace(pBt);
    if( pBt->pTmpSpace==0 ) return SQLITE_NOMEM_BKPT;
  }
  if( iTable<=1 ){
    if( iTable<1 ){
      return SQLITE_CORRUPT_BKPT;
    }else if( btreePagecount(pBt)==0 ){
      assert( wrFlag==0 );
      iTable = 0;
    }
  }

  /* Now that no other errors can occur, finish filling in the BtCursor
  ** variables and link the cursor into the BtShared list.  */
  pCur->pgnoRoot = iTable;
  pCur->iPage = -1;
  pCur->pKeyInfo = pKeyInfo;
  pCur->pBtree = p;
  pCur->pBt = pBt;
  pCur->curFlags = wrFlag ? BTCF_WriteFlag : 0;
  pCur->curPagerFlags = wrFlag ? 0 : PAGER_GET_READONLY;
  /* If there are two or more cursors on the same btree, then all such
  ** cursors *must* have the BTCF_Multiple flag set. */
  for(pX=pBt->pCursor; pX; pX=pX->pNext){
    if( pX->pgnoRoot==iTable ){
      pX->curFlags |= BTCF_Multiple;
      pCur->curFlags |= BTCF_Multiple;
    }
  }

  pCur->pNext = pBt->pCursor;
  pBt->pCursor = pCur;


  pCur->eState = CURSOR_INVALID;




  return SQLITE_OK;
}
static int btreeCursorWithLock(
  Btree *p,                              /* The btree */
  Pgno iTable,                           /* Root page of table to open */
  int wrFlag,                            /* 1 to write. 0 read-only */
  struct KeyInfo *pKeyInfo,              /* First arg to comparison function */







<
<
<
<
















|
<





|


>


>
>
|
>
>
>
>







70092
70093
70094
70095
70096
70097
70098




70099
70100
70101
70102
70103
70104
70105
70106
70107
70108
70109
70110
70111
70112
70113
70114
70115

70116
70117
70118
70119
70120
70121
70122
70123
70124
70125
70126
70127
70128
70129
70130
70131
70132
70133
70134
70135
70136
70137
70138
70139
70140

  /* Assert that the caller has opened the required transaction. */
  assert( p->inTrans>TRANS_NONE );
  assert( wrFlag==0 || p->inTrans==TRANS_WRITE );
  assert( pBt->pPage1 && pBt->pPage1->aData );
  assert( wrFlag==0 || (pBt->btsFlags & BTS_READ_ONLY)==0 );





  if( iTable<=1 ){
    if( iTable<1 ){
      return SQLITE_CORRUPT_BKPT;
    }else if( btreePagecount(pBt)==0 ){
      assert( wrFlag==0 );
      iTable = 0;
    }
  }

  /* Now that no other errors can occur, finish filling in the BtCursor
  ** variables and link the cursor into the BtShared list.  */
  pCur->pgnoRoot = iTable;
  pCur->iPage = -1;
  pCur->pKeyInfo = pKeyInfo;
  pCur->pBtree = p;
  pCur->pBt = pBt;
  pCur->curFlags = 0;

  /* If there are two or more cursors on the same btree, then all such
  ** cursors *must* have the BTCF_Multiple flag set. */
  for(pX=pBt->pCursor; pX; pX=pX->pNext){
    if( pX->pgnoRoot==iTable ){
      pX->curFlags |= BTCF_Multiple;
      pCur->curFlags = BTCF_Multiple;
    }
  }
  pCur->eState = CURSOR_INVALID;
  pCur->pNext = pBt->pCursor;
  pBt->pCursor = pCur;
  if( wrFlag ){
    pCur->curFlags |= BTCF_WriteFlag;
    pCur->curPagerFlags = 0;
    if( pBt->pTmpSpace==0 ) return allocateTempSpace(pBt);
  }else{
    pCur->curPagerFlags = PAGER_GET_READONLY;
  }
  return SQLITE_OK;
}
static int btreeCursorWithLock(
  Btree *p,                              /* The btree */
  Pgno iTable,                           /* Root page of table to open */
  int wrFlag,                            /* 1 to write. 0 read-only */
  struct KeyInfo *pKeyInfo,              /* First arg to comparison function */
70217
70218
70219
70220
70221
70222
70223
70224


70225
70226
70227
70228
70229
70230
70231
#ifdef SQLITE_DIRECT_OVERFLOW_READ
  unsigned char * const pBufStart = pBuf;     /* Start of original out buffer */
#endif

  assert( pPage );
  assert( eOp==0 || eOp==1 );
  assert( pCur->eState==CURSOR_VALID );
  assert( pCur->ix<pPage->nCell );


  assert( cursorHoldsMutex(pCur) );

  getCellInfo(pCur);
  aPayload = pCur->info.pPayload;
  assert( offset+amt <= pCur->info.nPayload );

  assert( aPayload > pPage->aData );







|
>
>







70500
70501
70502
70503
70504
70505
70506
70507
70508
70509
70510
70511
70512
70513
70514
70515
70516
#ifdef SQLITE_DIRECT_OVERFLOW_READ
  unsigned char * const pBufStart = pBuf;     /* Start of original out buffer */
#endif

  assert( pPage );
  assert( eOp==0 || eOp==1 );
  assert( pCur->eState==CURSOR_VALID );
  if( pCur->ix>=pPage->nCell ){
    return SQLITE_CORRUPT_PAGE(pPage);
  }
  assert( cursorHoldsMutex(pCur) );

  getCellInfo(pCur);
  aPayload = pCur->info.pPayload;
  assert( offset+amt <= pCur->info.nPayload );

  assert( aPayload > pPage->aData );
70404
70405
70406
70407
70408
70409
70410
70411
70412
70413
70414
70415
70416
70417
70418
** wrong.  An error is returned if "offset+amt" is larger than
** the available payload.
*/
SQLITE_PRIVATE int sqlite3BtreePayload(BtCursor *pCur, u32 offset, u32 amt, void *pBuf){
  assert( cursorHoldsMutex(pCur) );
  assert( pCur->eState==CURSOR_VALID );
  assert( pCur->iPage>=0 && pCur->pPage );
  assert( pCur->ix<pCur->pPage->nCell );
  return accessPayload(pCur, offset, amt, (unsigned char*)pBuf, 0);
}

/*
** This variant of sqlite3BtreePayload() works even if the cursor has not
** in the CURSOR_VALID state.  It is only used by the sqlite3_blob_read()
** interface.







<







70689
70690
70691
70692
70693
70694
70695

70696
70697
70698
70699
70700
70701
70702
** wrong.  An error is returned if "offset+amt" is larger than
** the available payload.
*/
SQLITE_PRIVATE int sqlite3BtreePayload(BtCursor *pCur, u32 offset, u32 amt, void *pBuf){
  assert( cursorHoldsMutex(pCur) );
  assert( pCur->eState==CURSOR_VALID );
  assert( pCur->iPage>=0 && pCur->pPage );

  return accessPayload(pCur, offset, amt, (unsigned char*)pBuf, 0);
}

/*
** This variant of sqlite3BtreePayload() works even if the cursor has not
** in the CURSOR_VALID state.  It is only used by the sqlite3_blob_read()
** interface.
70466
70467
70468
70469
70470
70471
70472
70473
70474
70475
70476
70477
70478
70479
70480
  u32 *pAmt            /* Write the number of available bytes here */
){
  int amt;
  assert( pCur!=0 && pCur->iPage>=0 && pCur->pPage);
  assert( pCur->eState==CURSOR_VALID );
  assert( sqlite3_mutex_held(pCur->pBtree->db->mutex) );
  assert( cursorOwnsBtShared(pCur) );
  assert( pCur->ix<pCur->pPage->nCell );
  assert( pCur->info.nSize>0 );
  assert( pCur->info.pPayload>pCur->pPage->aData || CORRUPT_DB );
  assert( pCur->info.pPayload<pCur->pPage->aDataEnd ||CORRUPT_DB);
  amt = pCur->info.nLocal;
  if( amt>(int)(pCur->pPage->aDataEnd - pCur->info.pPayload) ){
    /* There is too little space on the page for the expected amount
    ** of local content. Database must be corrupt. */







|







70750
70751
70752
70753
70754
70755
70756
70757
70758
70759
70760
70761
70762
70763
70764
  u32 *pAmt            /* Write the number of available bytes here */
){
  int amt;
  assert( pCur!=0 && pCur->iPage>=0 && pCur->pPage);
  assert( pCur->eState==CURSOR_VALID );
  assert( sqlite3_mutex_held(pCur->pBtree->db->mutex) );
  assert( cursorOwnsBtShared(pCur) );
  assert( pCur->ix<pCur->pPage->nCell || CORRUPT_DB );
  assert( pCur->info.nSize>0 );
  assert( pCur->info.pPayload>pCur->pPage->aData || CORRUPT_DB );
  assert( pCur->info.pPayload<pCur->pPage->aDataEnd ||CORRUPT_DB);
  amt = pCur->info.nLocal;
  if( amt>(int)(pCur->pPage->aDataEnd - pCur->info.pPayload) ){
    /* There is too little space on the page for the expected amount
    ** of local content. Database must be corrupt. */
71252
71253
71254
71255
71256
71257
71258
71259
71260
71261
71262
71263
71264
71265
71266
71267
71268
71269
71270
71271
71272
71273
71274
71275
    ** in a corrupt database file where the table being DELETE-ed from
    ** has pages in common with the table being queried.  See TH3
    ** module cov1/btree78.test testcase 220 (2018-06-08) for an
    ** example. */
    return SQLITE_CORRUPT_BKPT;
  }

  /* If the database file is corrupt, it is possible for the value of idx
  ** to be invalid here. This can only occur if a second cursor modifies
  ** the page while cursor pCur is holding a reference to it. Which can
  ** only happen if the database is corrupt in such a way as to link the
  ** page into more than one b-tree structure.
  **
  ** Update 2019-12-23: appears to long longer be possible after the
  ** addition of anotherValidCursor() condition on balance_deeper().  */
  harmless( idx>pPage->nCell );

  if( idx>=pPage->nCell ){
    if( !pPage->leaf ){
      rc = moveToChild(pCur, get4byte(&pPage->aData[pPage->hdrOffset+8]));
      if( rc ) return rc;
      return moveToLeftmost(pCur);
    }
    do{







<
<
<
<
<
<
<
<
<
<







71536
71537
71538
71539
71540
71541
71542










71543
71544
71545
71546
71547
71548
71549
    ** in a corrupt database file where the table being DELETE-ed from
    ** has pages in common with the table being queried.  See TH3
    ** module cov1/btree78.test testcase 220 (2018-06-08) for an
    ** example. */
    return SQLITE_CORRUPT_BKPT;
  }











  if( idx>=pPage->nCell ){
    if( !pPage->leaf ){
      rc = moveToChild(pCur, get4byte(&pPage->aData[pPage->hdrOffset+8]));
      if( rc ) return rc;
      return moveToLeftmost(pCur);
    }
    do{
71749
71750
71751
71752
71753
71754
71755
71756
71757
71758
71759
71760
71761
71762
71763
  int rc;                             /* Return Code */
  u32 nFree;                          /* Initial number of pages on free-list */

  assert( sqlite3_mutex_held(pBt->mutex) );
  assert( CORRUPT_DB || iPage>1 );
  assert( !pMemPage || pMemPage->pgno==iPage );

  if( iPage<2 || iPage>pBt->nPage ){
    return SQLITE_CORRUPT_BKPT;
  }
  if( pMemPage ){
    pPage = pMemPage;
    sqlite3PagerRef(pPage->pDbPage);
  }else{
    pPage = btreePageLookup(pBt, iPage);







|







72023
72024
72025
72026
72027
72028
72029
72030
72031
72032
72033
72034
72035
72036
72037
  int rc;                             /* Return Code */
  u32 nFree;                          /* Initial number of pages on free-list */

  assert( sqlite3_mutex_held(pBt->mutex) );
  assert( CORRUPT_DB || iPage>1 );
  assert( !pMemPage || pMemPage->pgno==iPage );

  if( NEVER(iPage<2) || iPage>pBt->nPage ){
    return SQLITE_CORRUPT_BKPT;
  }
  if( pMemPage ){
    pPage = pMemPage;
    sqlite3PagerRef(pPage->pDbPage);
  }else{
    pPage = btreePageLookup(pBt, iPage);
73067
73068
73069
73070
73071
73072
73073
73074
73075
73076
73077
73078
73079
73080
73081
73082
73083
73084
73085
  int szNew[NB+2];             /* Combined size of cells placed on i-th page */
  u8 *aSpace1;                 /* Space for copies of dividers cells */
  Pgno pgno;                   /* Temp var to store a page number in */
  u8 abDone[NB+2];             /* True after i'th new page is populated */
  Pgno aPgno[NB+2];            /* Page numbers of new pages before shuffling */
  Pgno aPgOrder[NB+2];         /* Copy of aPgno[] used for sorting pages */
  u16 aPgFlags[NB+2];          /* flags field of new pages before shuffling */
  CellArray b;                  /* Parsed information on cells being balanced */

  memset(abDone, 0, sizeof(abDone));
  b.nCell = 0;
  b.apCell = 0;
  pBt = pParent->pBt;
  assert( sqlite3_mutex_held(pBt->mutex) );
  assert( sqlite3PagerIswriteable(pParent->pDbPage) );

  /* At this point pParent may have at most one overflow cell. And if
  ** this overflow cell is present, it must be the cell with
  ** index iParentIdx. This scenario comes about when this function







|


|
<







73341
73342
73343
73344
73345
73346
73347
73348
73349
73350
73351

73352
73353
73354
73355
73356
73357
73358
  int szNew[NB+2];             /* Combined size of cells placed on i-th page */
  u8 *aSpace1;                 /* Space for copies of dividers cells */
  Pgno pgno;                   /* Temp var to store a page number in */
  u8 abDone[NB+2];             /* True after i'th new page is populated */
  Pgno aPgno[NB+2];            /* Page numbers of new pages before shuffling */
  Pgno aPgOrder[NB+2];         /* Copy of aPgno[] used for sorting pages */
  u16 aPgFlags[NB+2];          /* flags field of new pages before shuffling */
  CellArray b;                 /* Parsed information on cells being balanced */

  memset(abDone, 0, sizeof(abDone));
  memset(&b, 0, sizeof(b));

  pBt = pParent->pBt;
  assert( sqlite3_mutex_held(pBt->mutex) );
  assert( sqlite3PagerIswriteable(pParent->pDbPage) );

  /* At this point pParent may have at most one overflow cell. And if
  ** this overflow cell is present, it must be the cell with
  ** index iParentIdx. This scenario comes about when this function
73882
73883
73884
73885
73886
73887
73888
73889
73890
73891
73892
73893
73894
73895
73896
  return SQLITE_OK;
}

/*
** Return SQLITE_CORRUPT if any cursor other than pCur is currently valid
** on the same B-tree as pCur.
**
** This can if a database is corrupt with two or more SQL tables
** pointing to the same b-tree.  If an insert occurs on one SQL table
** and causes a BEFORE TRIGGER to do a secondary insert on the other SQL
** table linked to the same b-tree.  If the secondary insert causes a
** rebalance, that can change content out from under the cursor on the
** first SQL table, violating invariants on the first insert.
*/
static int anotherValidCursor(BtCursor *pCur){







|







74155
74156
74157
74158
74159
74160
74161
74162
74163
74164
74165
74166
74167
74168
74169
  return SQLITE_OK;
}

/*
** Return SQLITE_CORRUPT if any cursor other than pCur is currently valid
** on the same B-tree as pCur.
**
** This can occur if a database is corrupt with two or more SQL tables
** pointing to the same b-tree.  If an insert occurs on one SQL table
** and causes a BEFORE TRIGGER to do a secondary insert on the other SQL
** table linked to the same b-tree.  If the secondary insert causes a
** rebalance, that can change content out from under the cursor on the
** first SQL table, violating invariants on the first insert.
*/
static int anotherValidCursor(BtCursor *pCur){
74351
74352
74353
74354
74355
74356
74357
74358



74359
74360
74361
74362
74363
74364
74365
  }
  if( rc ) goto end_insert;
  assert( szNew==pPage->xCellSize(pPage, newCell) );
  assert( szNew <= MX_CELL_SIZE(pBt) );
  idx = pCur->ix;
  if( loc==0 ){
    CellInfo info;
    assert( idx<pPage->nCell );



    rc = sqlite3PagerWrite(pPage->pDbPage);
    if( rc ){
      goto end_insert;
    }
    oldCell = findCell(pPage, idx);
    if( !pPage->leaf ){
      memcpy(newCell, oldCell, 4);







|
>
>
>







74624
74625
74626
74627
74628
74629
74630
74631
74632
74633
74634
74635
74636
74637
74638
74639
74640
74641
  }
  if( rc ) goto end_insert;
  assert( szNew==pPage->xCellSize(pPage, newCell) );
  assert( szNew <= MX_CELL_SIZE(pBt) );
  idx = pCur->ix;
  if( loc==0 ){
    CellInfo info;
    assert( idx>=0 );
    if( idx>=pPage->nCell ){
      return SQLITE_CORRUPT_BKPT;
    }
    rc = sqlite3PagerWrite(pPage->pDbPage);
    if( rc ){
      goto end_insert;
    }
    oldCell = findCell(pPage, idx);
    if( !pPage->leaf ){
      memcpy(newCell, oldCell, 4);
74937
74938
74939
74940
74941
74942
74943

74944

74945
74946
74947
74948
74949
74950
74951
74952
74953
74954
74955

  assert( sqlite3_mutex_held(pBt->mutex) );
  if( pgno>btreePagecount(pBt) ){
    return SQLITE_CORRUPT_BKPT;
  }
  rc = getAndInitPage(pBt, pgno, &pPage, 0, 0);
  if( rc ) return rc;

  if( pPage->bBusy ){

    rc = SQLITE_CORRUPT_BKPT;
    goto cleardatabasepage_out;
  }
  pPage->bBusy = 1;
  hdr = pPage->hdrOffset;
  for(i=0; i<pPage->nCell; i++){
    pCell = findCell(pPage, i);
    if( !pPage->leaf ){
      rc = clearDatabasePage(pBt, get4byte(pCell), 1, pnChange);
      if( rc ) goto cleardatabasepage_out;
    }







>
|
>



<







75213
75214
75215
75216
75217
75218
75219
75220
75221
75222
75223
75224
75225

75226
75227
75228
75229
75230
75231
75232

  assert( sqlite3_mutex_held(pBt->mutex) );
  if( pgno>btreePagecount(pBt) ){
    return SQLITE_CORRUPT_BKPT;
  }
  rc = getAndInitPage(pBt, pgno, &pPage, 0, 0);
  if( rc ) return rc;
  if( (pBt->openFlags & BTREE_SINGLE)==0
   && sqlite3PagerPageRefcount(pPage->pDbPage)!=1
  ){
    rc = SQLITE_CORRUPT_BKPT;
    goto cleardatabasepage_out;
  }

  hdr = pPage->hdrOffset;
  for(i=0; i<pPage->nCell; i++){
    pCell = findCell(pPage, i);
    if( !pPage->leaf ){
      rc = clearDatabasePage(pBt, get4byte(pCell), 1, pnChange);
      if( rc ) goto cleardatabasepage_out;
    }
74968
74969
74970
74971
74972
74973
74974
74975
74976
74977
74978
74979
74980
74981
74982
  if( freePageFlag ){
    freePage(pPage, &rc);
  }else if( (rc = sqlite3PagerWrite(pPage->pDbPage))==0 ){
    zeroPage(pPage, pPage->aData[hdr] | PTF_LEAF);
  }

cleardatabasepage_out:
  pPage->bBusy = 0;
  releasePage(pPage);
  return rc;
}

/*
** Delete all information from a single table in the database.  iTable is
** the page number of the root of the table.  After this routine returns,







<







75245
75246
75247
75248
75249
75250
75251

75252
75253
75254
75255
75256
75257
75258
  if( freePageFlag ){
    freePage(pPage, &rc);
  }else if( (rc = sqlite3PagerWrite(pPage->pDbPage))==0 ){
    zeroPage(pPage, pPage->aData[hdr] | PTF_LEAF);
  }

cleardatabasepage_out:

  releasePage(pPage);
  return rc;
}

/*
** Delete all information from a single table in the database.  iTable is
** the page number of the root of the table.  After this routine returns,
75047
75048
75049
75050
75051
75052
75053
75054
75055
75056
75057


75058
75059
75060
75061
75062
75063
75064
  assert( sqlite3BtreeHoldsMutex(p) );
  assert( p->inTrans==TRANS_WRITE );
  assert( iTable>=2 );
  if( iTable>btreePagecount(pBt) ){
    return SQLITE_CORRUPT_BKPT;
  }

  rc = btreeGetPage(pBt, (Pgno)iTable, &pPage, 0);
  if( rc ) return rc;
  rc = sqlite3BtreeClearTable(p, iTable, 0);
  if( rc ){


    releasePage(pPage);
    return rc;
  }

  *piMoved = 0;

#ifdef SQLITE_OMIT_AUTOVACUUM







<
<

|
>
>







75323
75324
75325
75326
75327
75328
75329


75330
75331
75332
75333
75334
75335
75336
75337
75338
75339
75340
  assert( sqlite3BtreeHoldsMutex(p) );
  assert( p->inTrans==TRANS_WRITE );
  assert( iTable>=2 );
  if( iTable>btreePagecount(pBt) ){
    return SQLITE_CORRUPT_BKPT;
  }



  rc = sqlite3BtreeClearTable(p, iTable, 0);
  if( rc ) return rc;
  rc = btreeGetPage(pBt, (Pgno)iTable, &pPage, 0);
  if( NEVER(rc) ){
    releasePage(pPage);
    return rc;
  }

  *piMoved = 0;

#ifdef SQLITE_OMIT_AUTOVACUUM
77207
77208
77209
77210
77211
77212
77213

77214
77215
77216
77217
77218
77219
77220
** SQLITE_NOMEM may be returned if a malloc() fails during conversion
** between formats.
*/
SQLITE_PRIVATE int sqlite3VdbeChangeEncoding(Mem *pMem, int desiredEnc){
#ifndef SQLITE_OMIT_UTF16
  int rc;
#endif

  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  assert( desiredEnc==SQLITE_UTF8 || desiredEnc==SQLITE_UTF16LE
           || desiredEnc==SQLITE_UTF16BE );
  if( !(pMem->flags&MEM_Str) || pMem->enc==desiredEnc ){
    return SQLITE_OK;
  }
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );







>







77483
77484
77485
77486
77487
77488
77489
77490
77491
77492
77493
77494
77495
77496
77497
** SQLITE_NOMEM may be returned if a malloc() fails during conversion
** between formats.
*/
SQLITE_PRIVATE int sqlite3VdbeChangeEncoding(Mem *pMem, int desiredEnc){
#ifndef SQLITE_OMIT_UTF16
  int rc;
#endif
  assert( pMem!=0 );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  assert( desiredEnc==SQLITE_UTF8 || desiredEnc==SQLITE_UTF16LE
           || desiredEnc==SQLITE_UTF16BE );
  if( !(pMem->flags&MEM_Str) || pMem->enc==desiredEnc ){
    return SQLITE_OK;
  }
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
77339
77340
77341
77342
77343
77344
77345

77346
77347
77348
77349
77350
77351
77352
/*
** Change pMem so that its MEM_Str or MEM_Blob value is stored in
** MEM.zMalloc, where it can be safely written.
**
** Return SQLITE_OK on success or SQLITE_NOMEM if malloc fails.
*/
SQLITE_PRIVATE int sqlite3VdbeMemMakeWriteable(Mem *pMem){

  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  if( (pMem->flags & (MEM_Str|MEM_Blob))!=0 ){
    if( ExpandBlob(pMem) ) return SQLITE_NOMEM;
    if( pMem->szMalloc==0 || pMem->z!=pMem->zMalloc ){
      int rc = vdbeMemAddTerminator(pMem);
      if( rc ) return rc;







>







77616
77617
77618
77619
77620
77621
77622
77623
77624
77625
77626
77627
77628
77629
77630
/*
** Change pMem so that its MEM_Str or MEM_Blob value is stored in
** MEM.zMalloc, where it can be safely written.
**
** Return SQLITE_OK on success or SQLITE_NOMEM if malloc fails.
*/
SQLITE_PRIVATE int sqlite3VdbeMemMakeWriteable(Mem *pMem){
  assert( pMem!=0 );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  if( (pMem->flags & (MEM_Str|MEM_Blob))!=0 ){
    if( ExpandBlob(pMem) ) return SQLITE_NOMEM;
    if( pMem->szMalloc==0 || pMem->z!=pMem->zMalloc ){
      int rc = vdbeMemAddTerminator(pMem);
      if( rc ) return rc;
77363
77364
77365
77366
77367
77368
77369

77370
77371
77372
77373
77374
77375
77376
77377
77378
77379
77380
77381
77382
77383
77384


77385
77386
77387
77388
77389
77390
77391
77392
77393
77394
77395
77396

77397
77398
77399
77400
77401
77402
77403
/*
** If the given Mem* has a zero-filled tail, turn it into an ordinary
** blob stored in dynamically allocated space.
*/
#ifndef SQLITE_OMIT_INCRBLOB
SQLITE_PRIVATE int sqlite3VdbeMemExpandBlob(Mem *pMem){
  int nByte;

  assert( pMem->flags & MEM_Zero );
  assert( (pMem->flags&MEM_Blob)!=0 || MemNullNochng(pMem) );
  testcase( sqlite3_value_nochange(pMem) );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );

  /* Set nByte to the number of bytes required to store the expanded blob. */
  nByte = pMem->n + pMem->u.nZero;
  if( nByte<=0 ){
    if( (pMem->flags & MEM_Blob)==0 ) return SQLITE_OK;
    nByte = 1;
  }
  if( sqlite3VdbeMemGrow(pMem, nByte, 1) ){
    return SQLITE_NOMEM_BKPT;
  }



  memset(&pMem->z[pMem->n], 0, pMem->u.nZero);
  pMem->n += pMem->u.nZero;
  pMem->flags &= ~(MEM_Zero|MEM_Term);
  return SQLITE_OK;
}
#endif

/*
** Make sure the given Mem is \u0000 terminated.
*/
SQLITE_PRIVATE int sqlite3VdbeMemNulTerminate(Mem *pMem){

  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  testcase( (pMem->flags & (MEM_Term|MEM_Str))==(MEM_Term|MEM_Str) );
  testcase( (pMem->flags & (MEM_Term|MEM_Str))==0 );
  if( (pMem->flags & (MEM_Term|MEM_Str))!=MEM_Str ){
    return SQLITE_OK;   /* Nothing to do */
  }else{
    return vdbeMemAddTerminator(pMem);







>















>
>












>







77641
77642
77643
77644
77645
77646
77647
77648
77649
77650
77651
77652
77653
77654
77655
77656
77657
77658
77659
77660
77661
77662
77663
77664
77665
77666
77667
77668
77669
77670
77671
77672
77673
77674
77675
77676
77677
77678
77679
77680
77681
77682
77683
77684
77685
/*
** If the given Mem* has a zero-filled tail, turn it into an ordinary
** blob stored in dynamically allocated space.
*/
#ifndef SQLITE_OMIT_INCRBLOB
SQLITE_PRIVATE int sqlite3VdbeMemExpandBlob(Mem *pMem){
  int nByte;
  assert( pMem!=0 );
  assert( pMem->flags & MEM_Zero );
  assert( (pMem->flags&MEM_Blob)!=0 || MemNullNochng(pMem) );
  testcase( sqlite3_value_nochange(pMem) );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );

  /* Set nByte to the number of bytes required to store the expanded blob. */
  nByte = pMem->n + pMem->u.nZero;
  if( nByte<=0 ){
    if( (pMem->flags & MEM_Blob)==0 ) return SQLITE_OK;
    nByte = 1;
  }
  if( sqlite3VdbeMemGrow(pMem, nByte, 1) ){
    return SQLITE_NOMEM_BKPT;
  }
  assert( pMem->z!=0 );
  assert( sqlite3DbMallocSize(pMem->db,pMem->z) >= nByte );

  memset(&pMem->z[pMem->n], 0, pMem->u.nZero);
  pMem->n += pMem->u.nZero;
  pMem->flags &= ~(MEM_Zero|MEM_Term);
  return SQLITE_OK;
}
#endif

/*
** Make sure the given Mem is \u0000 terminated.
*/
SQLITE_PRIVATE int sqlite3VdbeMemNulTerminate(Mem *pMem){
  assert( pMem!=0 );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  testcase( (pMem->flags & (MEM_Term|MEM_Str))==(MEM_Term|MEM_Str) );
  testcase( (pMem->flags & (MEM_Term|MEM_Str))==0 );
  if( (pMem->flags & (MEM_Term|MEM_Str))!=MEM_Str ){
    return SQLITE_OK;   /* Nothing to do */
  }else{
    return vdbeMemAddTerminator(pMem);
77417
77418
77419
77420
77421
77422
77423

77424
77425
77426
77427
77428
77429
77430
** sqlite3_value_text()), or for ensuring that values to be used as btree
** keys are strings. In the former case a NULL pointer is returned the
** user and the latter is an internal programming error.
*/
SQLITE_PRIVATE int sqlite3VdbeMemStringify(Mem *pMem, u8 enc, u8 bForce){
  const int nByte = 32;


  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( !(pMem->flags&MEM_Zero) );
  assert( !(pMem->flags&(MEM_Str|MEM_Blob)) );
  assert( pMem->flags&(MEM_Int|MEM_Real|MEM_IntReal) );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );








>







77699
77700
77701
77702
77703
77704
77705
77706
77707
77708
77709
77710
77711
77712
77713
** sqlite3_value_text()), or for ensuring that values to be used as btree
** keys are strings. In the former case a NULL pointer is returned the
** user and the latter is an internal programming error.
*/
SQLITE_PRIVATE int sqlite3VdbeMemStringify(Mem *pMem, u8 enc, u8 bForce){
  const int nByte = 32;

  assert( pMem!=0 );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( !(pMem->flags&MEM_Zero) );
  assert( !(pMem->flags&(MEM_Str|MEM_Blob)) );
  assert( pMem->flags&(MEM_Int|MEM_Real|MEM_IntReal) );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );

77452
77453
77454
77455
77456
77457
77458

77459
77460
77461
77462
77463
77464
77465
** Return SQLITE_ERROR if the finalizer reports an error.  SQLITE_OK
** otherwise.
*/
SQLITE_PRIVATE int sqlite3VdbeMemFinalize(Mem *pMem, FuncDef *pFunc){
  sqlite3_context ctx;
  Mem t;
  assert( pFunc!=0 );

  assert( pFunc->xFinalize!=0 );
  assert( (pMem->flags & MEM_Null)!=0 || pFunc==pMem->u.pDef );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  memset(&ctx, 0, sizeof(ctx));
  memset(&t, 0, sizeof(t));
  t.flags = MEM_Null;
  t.db = pMem->db;







>







77735
77736
77737
77738
77739
77740
77741
77742
77743
77744
77745
77746
77747
77748
77749
** Return SQLITE_ERROR if the finalizer reports an error.  SQLITE_OK
** otherwise.
*/
SQLITE_PRIVATE int sqlite3VdbeMemFinalize(Mem *pMem, FuncDef *pFunc){
  sqlite3_context ctx;
  Mem t;
  assert( pFunc!=0 );
  assert( pMem!=0 );
  assert( pFunc->xFinalize!=0 );
  assert( (pMem->flags & MEM_Null)!=0 || pFunc==pMem->u.pDef );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  memset(&ctx, 0, sizeof(ctx));
  memset(&t, 0, sizeof(t));
  t.flags = MEM_Null;
  t.db = pMem->db;
77595
77596
77597
77598
77599
77600
77601
77602
77603
77604
77605
77606
77607
77608

77609
77610
77611
77612
77613
77614
77615
** a floating-point then the value returned is the integer part.
** If pMem is a string or blob, then we make an attempt to convert
** it into an integer and return that.  If pMem represents an
** an SQL-NULL value, return 0.
**
** If pMem represents a string value, its encoding might be changed.
*/
static SQLITE_NOINLINE i64 memIntValue(Mem *pMem){
  i64 value = 0;
  sqlite3Atoi64(pMem->z, &value, pMem->n, pMem->enc);
  return value;
}
SQLITE_PRIVATE i64 sqlite3VdbeIntValue(Mem *pMem){
  int flags;

  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );
  flags = pMem->flags;
  if( flags & (MEM_Int|MEM_IntReal) ){
    testcase( flags & MEM_IntReal );
    return pMem->u.i;
  }else if( flags & MEM_Real ){







|




|

>







77879
77880
77881
77882
77883
77884
77885
77886
77887
77888
77889
77890
77891
77892
77893
77894
77895
77896
77897
77898
77899
77900
** a floating-point then the value returned is the integer part.
** If pMem is a string or blob, then we make an attempt to convert
** it into an integer and return that.  If pMem represents an
** an SQL-NULL value, return 0.
**
** If pMem represents a string value, its encoding might be changed.
*/
static SQLITE_NOINLINE i64 memIntValue(const Mem *pMem){
  i64 value = 0;
  sqlite3Atoi64(pMem->z, &value, pMem->n, pMem->enc);
  return value;
}
SQLITE_PRIVATE i64 sqlite3VdbeIntValue(const Mem *pMem){
  int flags;
  assert( pMem!=0 );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );
  flags = pMem->flags;
  if( flags & (MEM_Int|MEM_IntReal) ){
    testcase( flags & MEM_IntReal );
    return pMem->u.i;
  }else if( flags & MEM_Real ){
77630
77631
77632
77633
77634
77635
77636

77637
77638
77639
77640
77641
77642
77643
static SQLITE_NOINLINE double memRealValue(Mem *pMem){
  /* (double)0 In case of SQLITE_OMIT_FLOATING_POINT... */
  double val = (double)0;
  sqlite3AtoF(pMem->z, &val, pMem->n, pMem->enc);
  return val;
}
SQLITE_PRIVATE double sqlite3VdbeRealValue(Mem *pMem){

  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );
  if( pMem->flags & MEM_Real ){
    return pMem->u.r;
  }else if( pMem->flags & (MEM_Int|MEM_IntReal) ){
    testcase( pMem->flags & MEM_IntReal );
    return (double)pMem->u.i;







>







77915
77916
77917
77918
77919
77920
77921
77922
77923
77924
77925
77926
77927
77928
77929
static SQLITE_NOINLINE double memRealValue(Mem *pMem){
  /* (double)0 In case of SQLITE_OMIT_FLOATING_POINT... */
  double val = (double)0;
  sqlite3AtoF(pMem->z, &val, pMem->n, pMem->enc);
  return val;
}
SQLITE_PRIVATE double sqlite3VdbeRealValue(Mem *pMem){
  assert( pMem!=0 );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );
  if( pMem->flags & MEM_Real ){
    return pMem->u.r;
  }else if( pMem->flags & (MEM_Int|MEM_IntReal) ){
    testcase( pMem->flags & MEM_IntReal );
    return (double)pMem->u.i;
77662
77663
77664
77665
77666
77667
77668

77669
77670
77671
77672
77673
77674
77675

/*
** The MEM structure is already a MEM_Real.  Try to also make it a
** MEM_Int if we can.
*/
SQLITE_PRIVATE void sqlite3VdbeIntegerAffinity(Mem *pMem){
  i64 ix;

  assert( pMem->flags & MEM_Real );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );

  ix = doubleToInt64(pMem->u.r);








>







77948
77949
77950
77951
77952
77953
77954
77955
77956
77957
77958
77959
77960
77961
77962

/*
** The MEM structure is already a MEM_Real.  Try to also make it a
** MEM_Int if we can.
*/
SQLITE_PRIVATE void sqlite3VdbeIntegerAffinity(Mem *pMem){
  i64 ix;
  assert( pMem!=0 );
  assert( pMem->flags & MEM_Real );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );

  ix = doubleToInt64(pMem->u.r);

77689
77690
77691
77692
77693
77694
77695

77696
77697
77698
77699
77700
77701
77702
77703
77704
77705
77706
77707
77708
77709

77710
77711
77712
77713
77714
77715
77716
  }
}

/*
** Convert pMem to type integer.  Invalidate any prior representations.
*/
SQLITE_PRIVATE int sqlite3VdbeMemIntegerify(Mem *pMem){

  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );

  pMem->u.i = sqlite3VdbeIntValue(pMem);
  MemSetTypeFlag(pMem, MEM_Int);
  return SQLITE_OK;
}

/*
** Convert pMem so that it is of type MEM_Real.
** Invalidate any prior representations.
*/
SQLITE_PRIVATE int sqlite3VdbeMemRealify(Mem *pMem){

  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );

  pMem->u.r = sqlite3VdbeRealValue(pMem);
  MemSetTypeFlag(pMem, MEM_Real);
  return SQLITE_OK;
}







>














>







77976
77977
77978
77979
77980
77981
77982
77983
77984
77985
77986
77987
77988
77989
77990
77991
77992
77993
77994
77995
77996
77997
77998
77999
78000
78001
78002
78003
78004
78005
  }
}

/*
** Convert pMem to type integer.  Invalidate any prior representations.
*/
SQLITE_PRIVATE int sqlite3VdbeMemIntegerify(Mem *pMem){
  assert( pMem!=0 );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );

  pMem->u.i = sqlite3VdbeIntValue(pMem);
  MemSetTypeFlag(pMem, MEM_Int);
  return SQLITE_OK;
}

/*
** Convert pMem so that it is of type MEM_Real.
** Invalidate any prior representations.
*/
SQLITE_PRIVATE int sqlite3VdbeMemRealify(Mem *pMem){
  assert( pMem!=0 );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( EIGHT_BYTE_ALIGNMENT(pMem) );

  pMem->u.r = sqlite3VdbeRealValue(pMem);
  MemSetTypeFlag(pMem, MEM_Real);
  return SQLITE_OK;
}
77736
77737
77738
77739
77740
77741
77742

77743
77744
77745
77746
77747
77748
77749
** Invalidate any prior representations.
**
** Every effort is made to force the conversion, even if the input
** is a string that does not look completely like a number.  Convert
** as much of the string as we can and ignore the rest.
*/
SQLITE_PRIVATE int sqlite3VdbeMemNumerify(Mem *pMem){

  testcase( pMem->flags & MEM_Int );
  testcase( pMem->flags & MEM_Real );
  testcase( pMem->flags & MEM_IntReal );
  testcase( pMem->flags & MEM_Null );
  if( (pMem->flags & (MEM_Int|MEM_Real|MEM_IntReal|MEM_Null))==0 ){
    int rc;
    sqlite3_int64 ix;







>







78025
78026
78027
78028
78029
78030
78031
78032
78033
78034
78035
78036
78037
78038
78039
** Invalidate any prior representations.
**
** Every effort is made to force the conversion, even if the input
** is a string that does not look completely like a number.  Convert
** as much of the string as we can and ignore the rest.
*/
SQLITE_PRIVATE int sqlite3VdbeMemNumerify(Mem *pMem){
  assert( pMem!=0 );
  testcase( pMem->flags & MEM_Int );
  testcase( pMem->flags & MEM_Real );
  testcase( pMem->flags & MEM_IntReal );
  testcase( pMem->flags & MEM_Null );
  if( (pMem->flags & (MEM_Int|MEM_Real|MEM_IntReal|MEM_Null))==0 ){
    int rc;
    sqlite3_int64 ix;
77845
77846
77847
77848
77849
77850
77851

77852
77853
77854
77855
77856
77857
77858
77859
77860















77861
77862
77863
77864
77865
77866
77867
  sqlite3VdbeMemSetNull((Mem*)p);
}

/*
** Delete any previous value and set the value to be a BLOB of length
** n containing all zeros.
*/

SQLITE_PRIVATE void sqlite3VdbeMemSetZeroBlob(Mem *pMem, int n){
  sqlite3VdbeMemRelease(pMem);
  pMem->flags = MEM_Blob|MEM_Zero;
  pMem->n = 0;
  if( n<0 ) n = 0;
  pMem->u.nZero = n;
  pMem->enc = SQLITE_UTF8;
  pMem->z = 0;
}
















/*
** The pMem is known to contain content that needs to be destroyed prior
** to a value change.  So invoke the destructor, then set the value to
** a 64-bit integer.
*/
static SQLITE_NOINLINE void vdbeReleaseAndSetInt64(Mem *pMem, i64 val){







>









>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







78135
78136
78137
78138
78139
78140
78141
78142
78143
78144
78145
78146
78147
78148
78149
78150
78151
78152
78153
78154
78155
78156
78157
78158
78159
78160
78161
78162
78163
78164
78165
78166
78167
78168
78169
78170
78171
78172
78173
  sqlite3VdbeMemSetNull((Mem*)p);
}

/*
** Delete any previous value and set the value to be a BLOB of length
** n containing all zeros.
*/
#ifndef SQLITE_OMIT_INCRBLOB
SQLITE_PRIVATE void sqlite3VdbeMemSetZeroBlob(Mem *pMem, int n){
  sqlite3VdbeMemRelease(pMem);
  pMem->flags = MEM_Blob|MEM_Zero;
  pMem->n = 0;
  if( n<0 ) n = 0;
  pMem->u.nZero = n;
  pMem->enc = SQLITE_UTF8;
  pMem->z = 0;
}
#else
SQLITE_PRIVATE int sqlite3VdbeMemSetZeroBlob(Mem *pMem, int n){
  int nByte = n>0?n:1;
  if( sqlite3VdbeMemGrow(pMem, nByte, 0) ){
    return SQLITE_NOMEM_BKPT;
  }
  assert( pMem->z!=0 );
  assert( sqlite3DbMallocSize(pMem->db, pMem->z)>=nByte );
  memset(pMem->z, 0, nByte);
  pMem->n = n>0?n:0;
  pMem->flags = MEM_Blob;
  pMem->enc = SQLITE_UTF8;
  return SQLITE_OK;
}
#endif

/*
** The pMem is known to contain content that needs to be destroyed prior
** to a value change.  So invoke the destructor, then set the value to
** a 64-bit integer.
*/
static SQLITE_NOINLINE void vdbeReleaseAndSetInt64(Mem *pMem, i64 val){
78087
78088
78089
78090
78091
78092
78093

78094
78095
78096
78097
78098
78099
78100
  u8 enc,             /* Encoding of z.  0 for BLOBs */
  void (*xDel)(void*) /* Destructor function */
){
  i64 nByte = n;      /* New value for pMem->n */
  int iLimit;         /* Maximum allowed string or blob size */
  u16 flags = 0;      /* New value for pMem->flags */


  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );

  /* If z is a NULL pointer, set pMem to contain an SQL NULL. */
  if( !z ){
    sqlite3VdbeMemSetNull(pMem);
    return SQLITE_OK;







>







78393
78394
78395
78396
78397
78398
78399
78400
78401
78402
78403
78404
78405
78406
78407
  u8 enc,             /* Encoding of z.  0 for BLOBs */
  void (*xDel)(void*) /* Destructor function */
){
  i64 nByte = n;      /* New value for pMem->n */
  int iLimit;         /* Maximum allowed string or blob size */
  u16 flags = 0;      /* New value for pMem->flags */

  assert( pMem!=0 );
  assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) );
  assert( !sqlite3VdbeMemIsRowSet(pMem) );

  /* If z is a NULL pointer, set pMem to contain an SQL NULL. */
  if( !z ){
    sqlite3VdbeMemSetNull(pMem);
    return SQLITE_OK;
78412
78413
78414
78415
78416
78417
78418

78419
78420

78421
78422
78423
78424
78425
78426
78427
  sqlite3_value *pVal = 0;        /* New value */
  int rc = SQLITE_OK;             /* Return code */
  ExprList *pList = 0;            /* Function arguments */
  int i;                          /* Iterator variable */

  assert( pCtx!=0 );
  assert( (p->flags & EP_TokenOnly)==0 );

  pList = p->x.pList;
  if( pList ) nVal = pList->nExpr;

  pFunc = sqlite3FindFunction(db, p->u.zToken, nVal, enc, 0);
  assert( pFunc );
  if( (pFunc->funcFlags & (SQLITE_FUNC_CONSTANT|SQLITE_FUNC_SLOCHNG))==0
   || (pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL)
  ){
    return SQLITE_OK;
  }







>


>







78719
78720
78721
78722
78723
78724
78725
78726
78727
78728
78729
78730
78731
78732
78733
78734
78735
78736
  sqlite3_value *pVal = 0;        /* New value */
  int rc = SQLITE_OK;             /* Return code */
  ExprList *pList = 0;            /* Function arguments */
  int i;                          /* Iterator variable */

  assert( pCtx!=0 );
  assert( (p->flags & EP_TokenOnly)==0 );
  assert( ExprUseXList(p) );
  pList = p->x.pList;
  if( pList ) nVal = pList->nExpr;
  assert( !ExprHasProperty(p, EP_IntValue) );
  pFunc = sqlite3FindFunction(db, p->u.zToken, nVal, enc, 0);
  assert( pFunc );
  if( (pFunc->funcFlags & (SQLITE_FUNC_CONSTANT|SQLITE_FUNC_SLOCHNG))==0
   || (pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL)
  ){
    return SQLITE_OK;
  }
78517
78518
78519
78520
78521
78522
78523


78524
78525
78526
78527
78528
78529
78530
78531
  /* Compressed expressions only appear when parsing the DEFAULT clause
  ** on a table column definition, and hence only when pCtx==0.  This
  ** check ensures that an EP_TokenOnly expression is never passed down
  ** into valueFromFunction(). */
  assert( (pExpr->flags & EP_TokenOnly)==0 || pCtx==0 );

  if( op==TK_CAST ){


    u8 aff = sqlite3AffinityType(pExpr->u.zToken,0);
    rc = valueFromExpr(db, pExpr->pLeft, enc, aff, ppVal, pCtx);
    testcase( rc!=SQLITE_OK );
    if( *ppVal ){
      sqlite3VdbeMemCast(*ppVal, aff, SQLITE_UTF8);
      sqlite3ValueApplyAffinity(*ppVal, affinity, SQLITE_UTF8);
    }
    return rc;







>
>
|







78826
78827
78828
78829
78830
78831
78832
78833
78834
78835
78836
78837
78838
78839
78840
78841
78842
  /* Compressed expressions only appear when parsing the DEFAULT clause
  ** on a table column definition, and hence only when pCtx==0.  This
  ** check ensures that an EP_TokenOnly expression is never passed down
  ** into valueFromFunction(). */
  assert( (pExpr->flags & EP_TokenOnly)==0 || pCtx==0 );

  if( op==TK_CAST ){
    u8 aff;
    assert( !ExprHasProperty(pExpr, EP_IntValue) );
    aff = sqlite3AffinityType(pExpr->u.zToken,0);
    rc = valueFromExpr(db, pExpr->pLeft, enc, aff, ppVal, pCtx);
    testcase( rc!=SQLITE_OK );
    if( *ppVal ){
      sqlite3VdbeMemCast(*ppVal, aff, SQLITE_UTF8);
      sqlite3ValueApplyAffinity(*ppVal, affinity, SQLITE_UTF8);
    }
    return rc;
78590
78591
78592
78593
78594
78595
78596

78597
78598
78599
78600
78601
78602
78603
78604
78605
78606
78607
78608
78609
78610
78611
78612
78613

78614
78615
78616
78617
78618
78619
78620
    pVal = valueNew(db, pCtx);
    if( pVal==0 ) goto no_mem;
    sqlite3VdbeMemSetNull(pVal);
  }
#ifndef SQLITE_OMIT_BLOB_LITERAL
  else if( op==TK_BLOB ){
    int nVal;

    assert( pExpr->u.zToken[0]=='x' || pExpr->u.zToken[0]=='X' );
    assert( pExpr->u.zToken[1]=='\'' );
    pVal = valueNew(db, pCtx);
    if( !pVal ) goto no_mem;
    zVal = &pExpr->u.zToken[2];
    nVal = sqlite3Strlen30(zVal)-1;
    assert( zVal[nVal]=='\'' );
    sqlite3VdbeMemSetStr(pVal, sqlite3HexToBlob(db, zVal, nVal), nVal/2,
                         0, SQLITE_DYNAMIC);
  }
#endif
#ifdef SQLITE_ENABLE_STAT4
  else if( op==TK_FUNCTION && pCtx!=0 ){
    rc = valueFromFunction(db, pExpr, enc, affinity, &pVal, pCtx);
  }
#endif
  else if( op==TK_TRUEFALSE ){

    pVal = valueNew(db, pCtx);
    if( pVal ){
      pVal->flags = MEM_Int;
      pVal->u.i = pExpr->u.zToken[4]==0;
    }
  }








>

















>







78901
78902
78903
78904
78905
78906
78907
78908
78909
78910
78911
78912
78913
78914
78915
78916
78917
78918
78919
78920
78921
78922
78923
78924
78925
78926
78927
78928
78929
78930
78931
78932
78933
    pVal = valueNew(db, pCtx);
    if( pVal==0 ) goto no_mem;
    sqlite3VdbeMemSetNull(pVal);
  }
#ifndef SQLITE_OMIT_BLOB_LITERAL
  else if( op==TK_BLOB ){
    int nVal;
    assert( !ExprHasProperty(pExpr, EP_IntValue) );
    assert( pExpr->u.zToken[0]=='x' || pExpr->u.zToken[0]=='X' );
    assert( pExpr->u.zToken[1]=='\'' );
    pVal = valueNew(db, pCtx);
    if( !pVal ) goto no_mem;
    zVal = &pExpr->u.zToken[2];
    nVal = sqlite3Strlen30(zVal)-1;
    assert( zVal[nVal]=='\'' );
    sqlite3VdbeMemSetStr(pVal, sqlite3HexToBlob(db, zVal, nVal), nVal/2,
                         0, SQLITE_DYNAMIC);
  }
#endif
#ifdef SQLITE_ENABLE_STAT4
  else if( op==TK_FUNCTION && pCtx!=0 ){
    rc = valueFromFunction(db, pExpr, enc, affinity, &pVal, pCtx);
  }
#endif
  else if( op==TK_TRUEFALSE ){
    assert( !ExprHasProperty(pExpr, EP_IntValue) );
    pVal = valueNew(db, pCtx);
    if( pVal ){
      pVal->flags = MEM_Int;
      pVal->u.i = pExpr->u.zToken[4]==0;
    }
  }

79160
79161
79162
79163
79164
79165
79166

79167
79168

79169
79170
79171
79172
79173
79174
79175

  i = p->nOp;
  assert( p->iVdbeMagic==VDBE_MAGIC_INIT );
  assert( op>=0 && op<0xff );
  if( p->nOpAlloc<=i ){
    return growOp3(p, op, p1, p2, p3);
  }

  p->nOp++;
  pOp = &p->aOp[i];

  pOp->opcode = (u8)op;
  pOp->p5 = 0;
  pOp->p1 = p1;
  pOp->p2 = p2;
  pOp->p3 = p3;
  pOp->p4.p = 0;
  pOp->p4type = P4_NOTUSED;







>


>







79473
79474
79475
79476
79477
79478
79479
79480
79481
79482
79483
79484
79485
79486
79487
79488
79489
79490

  i = p->nOp;
  assert( p->iVdbeMagic==VDBE_MAGIC_INIT );
  assert( op>=0 && op<0xff );
  if( p->nOpAlloc<=i ){
    return growOp3(p, op, p1, p2, p3);
  }
  assert( p->aOp!=0 );
  p->nOp++;
  pOp = &p->aOp[i];
  assert( pOp!=0 );
  pOp->opcode = (u8)op;
  pOp->p5 = 0;
  pOp->p1 = p1;
  pOp->p2 = p2;
  pOp->p3 = p3;
  pOp->p4.p = 0;
  pOp->p4type = P4_NOTUSED;
80404
80405
80406
80407
80408
80409
80410
80411
80412
80413
80414
80415
80416
80417
80418

  sqlite3StrAccumInit(&x, 0, 0, 0, SQLITE_MAX_LENGTH);
  zOpName = sqlite3OpcodeName(pOp->opcode);
  nOpName = sqlite3Strlen30(zOpName);
  if( zOpName[nOpName+1] ){
    int seenCom = 0;
    char c;
    zSynopsis = zOpName += nOpName + 1;
    if( strncmp(zSynopsis,"IF ",3)==0 ){
      sqlite3_snprintf(sizeof(zAlt), zAlt, "if %s goto P2", zSynopsis+3);
      zSynopsis = zAlt;
    }
    for(ii=0; (c = zSynopsis[ii])!=0; ii++){
      if( c=='P' ){
        c = zSynopsis[++ii];







|







80719
80720
80721
80722
80723
80724
80725
80726
80727
80728
80729
80730
80731
80732
80733

  sqlite3StrAccumInit(&x, 0, 0, 0, SQLITE_MAX_LENGTH);
  zOpName = sqlite3OpcodeName(pOp->opcode);
  nOpName = sqlite3Strlen30(zOpName);
  if( zOpName[nOpName+1] ){
    int seenCom = 0;
    char c;
    zSynopsis = zOpName + nOpName + 1;
    if( strncmp(zSynopsis,"IF ",3)==0 ){
      sqlite3_snprintf(sizeof(zAlt), zAlt, "if %s goto P2", zSynopsis+3);
      zSynopsis = zAlt;
    }
    for(ii=0; (c = zSynopsis[ii])!=0; ii++){
      if( c=='P' ){
        c = zSynopsis[++ii];
80477
80478
80479
80480
80481
80482
80483

80484
80485
80486
80487
80488
80489
80490
** Translate the P4.pExpr value for an OP_CursorHint opcode into text
** that can be displayed in the P4 column of EXPLAIN output.
*/
static void displayP4Expr(StrAccum *p, Expr *pExpr){
  const char *zOp = 0;
  switch( pExpr->op ){
    case TK_STRING:

      sqlite3_str_appendf(p, "%Q", pExpr->u.zToken);
      break;
    case TK_INTEGER:
      sqlite3_str_appendf(p, "%d", pExpr->u.iValue);
      break;
    case TK_NULL:
      sqlite3_str_appendf(p, "NULL");







>







80792
80793
80794
80795
80796
80797
80798
80799
80800
80801
80802
80803
80804
80805
80806
** Translate the P4.pExpr value for an OP_CursorHint opcode into text
** that can be displayed in the P4 column of EXPLAIN output.
*/
static void displayP4Expr(StrAccum *p, Expr *pExpr){
  const char *zOp = 0;
  switch( pExpr->op ){
    case TK_STRING:
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      sqlite3_str_appendf(p, "%Q", pExpr->u.zToken);
      break;
    case TK_INTEGER:
      sqlite3_str_appendf(p, "%d", pExpr->u.iValue);
      break;
    case TK_NULL:
      sqlite3_str_appendf(p, "NULL");
80823
80824
80825
80826
80827
80828
80829
80830
80831

80832
80833
80834
80835
80836
80837
80838
      ** sqlite3MemRelease() were called from here. With -O2, this jumps
      ** to 6.6 percent. The test case is inserting 1000 rows into a table
      ** with no indexes using a single prepared INSERT statement, bind()
      ** and reset(). Inserts are grouped into a transaction.
      */
      testcase( p->flags & MEM_Agg );
      testcase( p->flags & MEM_Dyn );
      testcase( p->xDel==sqlite3VdbeFrameMemDel );
      if( p->flags&(MEM_Agg|MEM_Dyn) ){

        sqlite3VdbeMemRelease(p);
      }else if( p->szMalloc ){
        sqlite3DbFreeNN(db, p->zMalloc);
        p->szMalloc = 0;
      }

      p->flags = MEM_Undefined;







<

>







81139
81140
81141
81142
81143
81144
81145

81146
81147
81148
81149
81150
81151
81152
81153
81154
      ** sqlite3MemRelease() were called from here. With -O2, this jumps
      ** to 6.6 percent. The test case is inserting 1000 rows into a table
      ** with no indexes using a single prepared INSERT statement, bind()
      ** and reset(). Inserts are grouped into a transaction.
      */
      testcase( p->flags & MEM_Agg );
      testcase( p->flags & MEM_Dyn );

      if( p->flags&(MEM_Agg|MEM_Dyn) ){
        testcase( (p->flags & MEM_Dyn)!=0 && p->xDel==sqlite3VdbeFrameMemDel );
        sqlite3VdbeMemRelease(p);
      }else if( p->szMalloc ){
        sqlite3DbFreeNN(db, p->zMalloc);
        p->szMalloc = 0;
      }

      p->flags = MEM_Undefined;
81972
81973
81974
81975
81976
81977
81978

81979
81980

81981




81982
81983
81984
81985
81986
81987
81988
    int eStatementOp = 0;
    int isSpecialError;            /* Set to true if a 'special' error */

    /* Lock all btrees used by the statement */
    sqlite3VdbeEnter(p);

    /* Check for one of the special errors */

    mrc = p->rc & 0xff;
    isSpecialError = mrc==SQLITE_NOMEM || mrc==SQLITE_IOERR

                     || mrc==SQLITE_INTERRUPT || mrc==SQLITE_FULL;




    if( isSpecialError ){
      /* If the query was read-only and the error code is SQLITE_INTERRUPT,
      ** no rollback is necessary. Otherwise, at least a savepoint
      ** transaction must be rolled back to restore the database to a
      ** consistent state.
      **
      ** Even if the statement is read-only, it is important to perform







>
|
|
>
|
>
>
>
>







82288
82289
82290
82291
82292
82293
82294
82295
82296
82297
82298
82299
82300
82301
82302
82303
82304
82305
82306
82307
82308
82309
82310
    int eStatementOp = 0;
    int isSpecialError;            /* Set to true if a 'special' error */

    /* Lock all btrees used by the statement */
    sqlite3VdbeEnter(p);

    /* Check for one of the special errors */
    if( p->rc ){
      mrc = p->rc & 0xff;
      isSpecialError = mrc==SQLITE_NOMEM
                    || mrc==SQLITE_IOERR
                    || mrc==SQLITE_INTERRUPT
                    || mrc==SQLITE_FULL;
    }else{
      mrc = isSpecialError = 0;
    }
    if( isSpecialError ){
      /* If the query was read-only and the error code is SQLITE_INTERRUPT,
      ** no rollback is necessary. Otherwise, at least a savepoint
      ** transaction must be rolled back to restore the database to a
      ** consistent state.
      **
      ** Even if the statement is read-only, it is important to perform
82026
82027
82028
82029
82030
82031
82032



82033
82034
82035
82036
82037
82038
82039
        rc = sqlite3VdbeCheckFk(p, 1);
        if( rc!=SQLITE_OK ){
          if( NEVER(p->readOnly) ){
            sqlite3VdbeLeave(p);
            return SQLITE_ERROR;
          }
          rc = SQLITE_CONSTRAINT_FOREIGNKEY;



        }else{
          /* The auto-commit flag is true, the vdbe program was successful
          ** or hit an 'OR FAIL' constraint and there are no deferred foreign
          ** key constraints to hold up the transaction. This means a commit
          ** is required. */
          rc = vdbeCommit(db, p);
        }







>
>
>







82348
82349
82350
82351
82352
82353
82354
82355
82356
82357
82358
82359
82360
82361
82362
82363
82364
        rc = sqlite3VdbeCheckFk(p, 1);
        if( rc!=SQLITE_OK ){
          if( NEVER(p->readOnly) ){
            sqlite3VdbeLeave(p);
            return SQLITE_ERROR;
          }
          rc = SQLITE_CONSTRAINT_FOREIGNKEY;
        }else if( db->flags & SQLITE_CorruptRdOnly ){
          rc = SQLITE_CORRUPT;
          db->flags &= ~SQLITE_CorruptRdOnly;
        }else{
          /* The auto-commit flag is true, the vdbe program was successful
          ** or hit an 'OR FAIL' constraint and there are no deferred foreign
          ** key constraints to hold up the transaction. This means a commit
          ** is required. */
          rc = vdbeCommit(db, p);
        }
84130
84131
84132
84133
84134
84135
84136


84137
84138
84139
84140
84141
84142
84143
    if( op==SQLITE_UPDATE ){
      iKey2 = v->aMem[iReg].u.i;
    }else{
      iKey2 = iKey1;
    }
  }



  assert( pCsr->nField==pTab->nCol
       || (pCsr->nField==pTab->nCol+1 && op==SQLITE_DELETE && iReg==-1)
  );

  preupdate.v = v;
  preupdate.pCsr = pCsr;
  preupdate.op = op;







>
>







84455
84456
84457
84458
84459
84460
84461
84462
84463
84464
84465
84466
84467
84468
84469
84470
    if( op==SQLITE_UPDATE ){
      iKey2 = v->aMem[iReg].u.i;
    }else{
      iKey2 = iKey1;
    }
  }

  assert( pCsr!=0 );
  assert( pCsr->eCurType==CURTYPE_BTREE );
  assert( pCsr->nField==pTab->nCol
       || (pCsr->nField==pTab->nCol+1 && op==SQLITE_DELETE && iReg==-1)
  );

  preupdate.v = v;
  preupdate.pCsr = pCsr;
  preupdate.op = op;
84529
84530
84531
84532
84533
84534
84535
84536
84537
84538
84539
84540
84541
84542
84543
84544
84545
84546
84547
84548
84549


84550






84551
84552
84553
84554
84555
84556
84557


/**************************** sqlite3_result_  *******************************
** The following routines are used by user-defined functions to specify
** the function result.
**
** The setStrOrError() function calls sqlite3VdbeMemSetStr() to store the
** result as a string or blob but if the string or blob is too large, it
** then sets the error code to SQLITE_TOOBIG
**
** The invokeValueDestructor(P,X) routine invokes destructor function X()
** on value P is not going to be used and need to be destroyed.
*/
static void setResultStrOrError(
  sqlite3_context *pCtx,  /* Function context */
  const char *z,          /* String pointer */
  int n,                  /* Bytes in string, or negative */
  u8 enc,                 /* Encoding of z.  0 for BLOBs */
  void (*xDel)(void*)     /* Destructor function */
){
  if( sqlite3VdbeMemSetStr(pCtx->pOut, z, n, enc, xDel)==SQLITE_TOOBIG ){


    sqlite3_result_error_toobig(pCtx);






  }
}
static int invokeValueDestructor(
  const void *p,             /* Value to destroy */
  void (*xDel)(void*),       /* The destructor */
  sqlite3_context *pCtx      /* Set a SQLITE_TOOBIG error if no NULL */
){







|
|











|
>
>
|
>
>
>
>
>
>







84856
84857
84858
84859
84860
84861
84862
84863
84864
84865
84866
84867
84868
84869
84870
84871
84872
84873
84874
84875
84876
84877
84878
84879
84880
84881
84882
84883
84884
84885
84886
84887
84888
84889
84890
84891
84892


/**************************** sqlite3_result_  *******************************
** The following routines are used by user-defined functions to specify
** the function result.
**
** The setStrOrError() function calls sqlite3VdbeMemSetStr() to store the
** result as a string or blob.  Appropriate errors are set if the string/blob
** is too big or if an OOM occurs.
**
** The invokeValueDestructor(P,X) routine invokes destructor function X()
** on value P is not going to be used and need to be destroyed.
*/
static void setResultStrOrError(
  sqlite3_context *pCtx,  /* Function context */
  const char *z,          /* String pointer */
  int n,                  /* Bytes in string, or negative */
  u8 enc,                 /* Encoding of z.  0 for BLOBs */
  void (*xDel)(void*)     /* Destructor function */
){
  int rc = sqlite3VdbeMemSetStr(pCtx->pOut, z, n, enc, xDel);
  if( rc ){
    if( rc==SQLITE_TOOBIG ){
      sqlite3_result_error_toobig(pCtx);
    }else{
      /* The only errors possible from sqlite3VdbeMemSetStr are
      ** SQLITE_TOOBIG and SQLITE_NOMEM */
      assert( rc==SQLITE_NOMEM );
      sqlite3_result_error_nomem(pCtx);
    }
  }
}
static int invokeValueDestructor(
  const void *p,             /* Value to destroy */
  void (*xDel)(void*),       /* The destructor */
  sqlite3_context *pCtx      /* Set a SQLITE_TOOBIG error if no NULL */
){
84700
84701
84702
84703
84704
84705
84706

84707
84708



84709
84710
84711
84712
84713
84714
84715
}
SQLITE_API int sqlite3_result_zeroblob64(sqlite3_context *pCtx, u64 n){
  Mem *pOut = pCtx->pOut;
  assert( sqlite3_mutex_held(pOut->db->mutex) );
  if( n>(u64)pOut->db->aLimit[SQLITE_LIMIT_LENGTH] ){
    return SQLITE_TOOBIG;
  }

  sqlite3VdbeMemSetZeroBlob(pCtx->pOut, (int)n);
  return SQLITE_OK;



}
SQLITE_API void sqlite3_result_error_code(sqlite3_context *pCtx, int errCode){
  pCtx->isError = errCode ? errCode : -1;
#ifdef SQLITE_DEBUG
  if( pCtx->pVdbe ) pCtx->pVdbe->rcApp = errCode;
#endif
  if( pCtx->pOut->flags & MEM_Null ){







>


>
>
>







85035
85036
85037
85038
85039
85040
85041
85042
85043
85044
85045
85046
85047
85048
85049
85050
85051
85052
85053
85054
}
SQLITE_API int sqlite3_result_zeroblob64(sqlite3_context *pCtx, u64 n){
  Mem *pOut = pCtx->pOut;
  assert( sqlite3_mutex_held(pOut->db->mutex) );
  if( n>(u64)pOut->db->aLimit[SQLITE_LIMIT_LENGTH] ){
    return SQLITE_TOOBIG;
  }
#ifndef SQLITE_OMIT_INCRBLOB
  sqlite3VdbeMemSetZeroBlob(pCtx->pOut, (int)n);
  return SQLITE_OK;
#else
  return sqlite3VdbeMemSetZeroBlob(pCtx->pOut, (int)n);
#endif
}
SQLITE_API void sqlite3_result_error_code(sqlite3_context *pCtx, int errCode){
  pCtx->isError = errCode ? errCode : -1;
#ifdef SQLITE_DEBUG
  if( pCtx->pVdbe ) pCtx->pVdbe->rcApp = errCode;
#endif
  if( pCtx->pOut->flags & MEM_Null ){
85713
85714
85715
85716
85717
85718
85719

85720



85721
85722
85723
85724
85725
85726
85727
  return rc;
}
SQLITE_API int sqlite3_bind_zeroblob(sqlite3_stmt *pStmt, int i, int n){
  int rc;
  Vdbe *p = (Vdbe *)pStmt;
  rc = vdbeUnbind(p, i);
  if( rc==SQLITE_OK ){

    sqlite3VdbeMemSetZeroBlob(&p->aVar[i-1], n);



    sqlite3_mutex_leave(p->db->mutex);
  }
  return rc;
}
SQLITE_API int sqlite3_bind_zeroblob64(sqlite3_stmt *pStmt, int i, sqlite3_uint64 n){
  int rc;
  Vdbe *p = (Vdbe *)pStmt;







>

>
>
>







86052
86053
86054
86055
86056
86057
86058
86059
86060
86061
86062
86063
86064
86065
86066
86067
86068
86069
86070
  return rc;
}
SQLITE_API int sqlite3_bind_zeroblob(sqlite3_stmt *pStmt, int i, int n){
  int rc;
  Vdbe *p = (Vdbe *)pStmt;
  rc = vdbeUnbind(p, i);
  if( rc==SQLITE_OK ){
#ifndef SQLITE_OMIT_INCRBLOB
    sqlite3VdbeMemSetZeroBlob(&p->aVar[i-1], n);
#else
    rc = sqlite3VdbeMemSetZeroBlob(&p->aVar[i-1], n);
#endif
    sqlite3_mutex_leave(p->db->mutex);
  }
  return rc;
}
SQLITE_API int sqlite3_bind_zeroblob64(sqlite3_stmt *pStmt, int i, sqlite3_uint64 n){
  int rc;
  Vdbe *p = (Vdbe *)pStmt;
86001
86002
86003
86004
86005
86006
86007

86008
86009
86010
86011
86012
86013
86014
  }

  /* If the old.* record has not yet been loaded into memory, do so now. */
  if( p->pUnpacked==0 ){
    u32 nRec;
    u8 *aRec;


    nRec = sqlite3BtreePayloadSize(p->pCsr->uc.pCursor);
    aRec = sqlite3DbMallocRaw(db, nRec);
    if( !aRec ) goto preupdate_old_out;
    rc = sqlite3BtreePayload(p->pCsr->uc.pCursor, 0, nRec, aRec);
    if( rc==SQLITE_OK ){
      p->pUnpacked = vdbeUnpackRecord(&p->keyinfo, nRec, aRec);
      if( !p->pUnpacked ) rc = SQLITE_NOMEM;







>







86344
86345
86346
86347
86348
86349
86350
86351
86352
86353
86354
86355
86356
86357
86358
  }

  /* If the old.* record has not yet been loaded into memory, do so now. */
  if( p->pUnpacked==0 ){
    u32 nRec;
    u8 *aRec;

    assert( p->pCsr->eCurType==CURTYPE_BTREE );
    nRec = sqlite3BtreePayloadSize(p->pCsr->uc.pCursor);
    aRec = sqlite3DbMallocRaw(db, nRec);
    if( !aRec ) goto preupdate_old_out;
    rc = sqlite3BtreePayload(p->pCsr->uc.pCursor, 0, nRec, aRec);
    if( rc==SQLITE_OK ){
      p->pUnpacked = vdbeUnpackRecord(&p->keyinfo, nRec, aRec);
      if( !p->pUnpacked ) rc = SQLITE_NOMEM;
87089
87090
87091
87092
87093
87094
87095

























87096
87097
87098
87099
87100
87101
87102
  if( VdbeMemDynamic(pOut) ){ /*OPTIMIZATION-IF-FALSE*/
    return out2PrereleaseWithClear(pOut);
  }else{
    pOut->flags = MEM_Int;
    return pOut;
  }
}


























/*
** Return the symbolic name for the data type of a pMem
*/
static const char *vdbeMemTypeName(Mem *pMem){
  static const char *azTypes[] = {
      /* SQLITE_INTEGER */ "INT",







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







87433
87434
87435
87436
87437
87438
87439
87440
87441
87442
87443
87444
87445
87446
87447
87448
87449
87450
87451
87452
87453
87454
87455
87456
87457
87458
87459
87460
87461
87462
87463
87464
87465
87466
87467
87468
87469
87470
87471
  if( VdbeMemDynamic(pOut) ){ /*OPTIMIZATION-IF-FALSE*/
    return out2PrereleaseWithClear(pOut);
  }else{
    pOut->flags = MEM_Int;
    return pOut;
  }
}

/*
** Compute a bloom filter hash using pOp->p4.i registers from aMem[] beginning
** with pOp->p3.  Return the hash.
*/
static u64 filterHash(const Mem *aMem, const Op *pOp){
  int i, mx;
  u64 h = 0;

  i = pOp->p3;
  assert( pOp->p4type==P4_INT32 );
  mx = i + pOp->p4.i;
  for(i=pOp->p3, mx=i+pOp->p4.i; i<mx; i++){
    const Mem *p = &aMem[i];
    if( p->flags & (MEM_Int|MEM_IntReal) ){
      h += p->u.i;
    }else if( p->flags & MEM_Real ){
      h += sqlite3VdbeIntValue(p);
    }else if( p->flags & (MEM_Str|MEM_Blob) ){
      h += p->n;
      if( p->flags & MEM_Zero ) h += p->u.nZero;
    }
  }
  return h;
}

/*
** Return the symbolic name for the data type of a pMem
*/
static const char *vdbeMemTypeName(Mem *pMem){
  static const char *azTypes[] = {
      /* SQLITE_INTEGER */ "INT",
87744
87745
87746
87747
87748
87749
87750
87751

87752
87753
87754
87755




87756

87757
87758
87759
87760
87761
87762
87763
  break;
}

/* Opcode: Blob P1 P2 * P4 *
** Synopsis: r[P2]=P4 (len=P1)
**
** P4 points to a blob of data P1 bytes long.  Store this
** blob in register P2.

*/
case OP_Blob: {                /* out2 */
  assert( pOp->p1 <= SQLITE_MAX_LENGTH );
  pOut = out2Prerelease(p, pOp);




  sqlite3VdbeMemSetStr(pOut, pOp->p4.z, pOp->p1, 0, 0);

  pOut->enc = encoding;
  UPDATE_MAX_BLOBSIZE(pOut);
  break;
}

/* Opcode: Variable P1 P2 * P4 *
** Synopsis: r[P2]=parameter(P1,P4)







|
>




>
>
>
>
|
>







88113
88114
88115
88116
88117
88118
88119
88120
88121
88122
88123
88124
88125
88126
88127
88128
88129
88130
88131
88132
88133
88134
88135
88136
88137
88138
  break;
}

/* Opcode: Blob P1 P2 * P4 *
** Synopsis: r[P2]=P4 (len=P1)
**
** P4 points to a blob of data P1 bytes long.  Store this
** blob in register P2.  If P4 is a NULL pointer, then construct
** a zero-filled blob that is P1 bytes long in P2.
*/
case OP_Blob: {                /* out2 */
  assert( pOp->p1 <= SQLITE_MAX_LENGTH );
  pOut = out2Prerelease(p, pOp);
  if( pOp->p4.z==0 ){
    sqlite3VdbeMemSetZeroBlob(pOut, pOp->p1);
    if( sqlite3VdbeMemExpandBlob(pOut) ) goto no_mem;
  }else{
    sqlite3VdbeMemSetStr(pOut, pOp->p4.z, pOp->p1, 0, 0);
  }
  pOut->enc = encoding;
  UPDATE_MAX_BLOBSIZE(pOut);
  break;
}

/* Opcode: Variable P1 P2 * P4 *
** Synopsis: r[P2]=parameter(P1,P4)
87898
87899
87900
87901
87902
87903
87904
87905
87906
87907
87908
87909
87910

87911

87912
87913
87914
87915
87916
87917
87918
87919
87920
87921
87922
87923
87924
87925
87926
87927
87928
87929
  pIn1 = &aMem[pOp->p1];
  assert( (pIn1->flags & MEM_Int)!=0 );
  pOut = &aMem[pOp->p2];
  sqlite3VdbeMemSetInt64(pOut, pIn1->u.i);
  break;
}

/* Opcode: ChngCntRow P1 P2 * * *
** Synopsis: output=r[P1]
**
** Output value in register P1 as the chance count for a DML statement,
** due to the "PRAGMA count_changes=ON" setting.  Or, if there was a
** foreign key error in the statement, trigger the error now.

**

** This opcode is a variant of OP_ResultRow that checks the foreign key
** immediate constraint count and throws an error if the count is
** non-zero.  The P2 opcode must be 1.
*/
case OP_ChngCntRow: {
  assert( pOp->p2==1 );
  if( (rc = sqlite3VdbeCheckFk(p,0))!=SQLITE_OK ){
    goto abort_due_to_error;
  }
  /* Fall through to the next case, OP_ResultRow */
  /* no break */ deliberate_fall_through
}

/* Opcode: ResultRow P1 P2 * * *
** Synopsis: output=r[P1@P2]
**
** The registers P1 through P1+P2-1 contain a single row of
** results. This opcode causes the sqlite3_step() call to terminate







|
<

<
|
|
>

>
|
|
|

|
<



<
|







88273
88274
88275
88276
88277
88278
88279
88280

88281

88282
88283
88284
88285
88286
88287
88288
88289
88290
88291

88292
88293
88294

88295
88296
88297
88298
88299
88300
88301
88302
  pIn1 = &aMem[pOp->p1];
  assert( (pIn1->flags & MEM_Int)!=0 );
  pOut = &aMem[pOp->p2];
  sqlite3VdbeMemSetInt64(pOut, pIn1->u.i);
  break;
}

/* Opcode: FkCheck * * * * *

**

** Halt with an SQLITE_CONSTRAINT error if there are any unresolved
** foreign key constraint violations.  If there are no foreign key
** constraint violations, this is a no-op.
**
** FK constraint violations are also checked when the prepared statement
** exits.  This opcode is used to raise foreign key constraint errors prior
** to returning results such as a row change count or the result of a
** RETURNING clause.
*/
case OP_FkCheck: {

  if( (rc = sqlite3VdbeCheckFk(p,0))!=SQLITE_OK ){
    goto abort_due_to_error;
  }

  break;
}

/* Opcode: ResultRow P1 P2 * * *
** Synopsis: output=r[P1@P2]
**
** The registers P1 through P1+P2-1 contain a single row of
** results. This opcode causes the sqlite3_step() call to terminate
89318
89319
89320
89321
89322
89323
89324
89325
89326
89327
89328
89329
89330
89331
89332
89333
89334





89335
89336
89337
89338
89339
89340
89341
    break;
  }else{
    rc = SQLITE_CORRUPT_BKPT;
    goto abort_due_to_error;
  }
}

/* Opcode: TypeCheck P1 P2 * P4 *
** Synopsis: typecheck(r[P1@P2])
**
** Apply affinities to the range of P2 registers beginning with P1.
** Take the affinities from the Table object in P4.  If any value
** cannot be coerced into the correct type, then raise an error.
**
** This opcode is similar to OP_Affinity except that this opcode
** forces the register type to the Table column type.  This is used
** to implement "strict affinity".





**
** Preconditions:
**
** <ul>
** <li> P2 should be the number of non-virtual columns in the
**      table of P4.
** <li> Table P4 should be a STRICT table.







|









>
>
>
>
>







89691
89692
89693
89694
89695
89696
89697
89698
89699
89700
89701
89702
89703
89704
89705
89706
89707
89708
89709
89710
89711
89712
89713
89714
89715
89716
89717
89718
89719
    break;
  }else{
    rc = SQLITE_CORRUPT_BKPT;
    goto abort_due_to_error;
  }
}

/* Opcode: TypeCheck P1 P2 P3 P4 *
** Synopsis: typecheck(r[P1@P2])
**
** Apply affinities to the range of P2 registers beginning with P1.
** Take the affinities from the Table object in P4.  If any value
** cannot be coerced into the correct type, then raise an error.
**
** This opcode is similar to OP_Affinity except that this opcode
** forces the register type to the Table column type.  This is used
** to implement "strict affinity".
**
** GENERATED ALWAYS AS ... STATIC columns are only checked if P3
** is zero.  When P3 is non-zero, no type checking occurs for
** static generated columns.  Virtual columns are computed at query time
** and so they are never checked.
**
** Preconditions:
**
** <ul>
** <li> P2 should be the number of non-virtual columns in the
**      table of P4.
** <li> Table P4 should be a STRICT table.
89351
89352
89353
89354
89355
89356
89357

89358


89359
89360
89361
89362
89363
89364
89365
  assert( pOp->p4type==P4_TABLE );
  pTab = pOp->p4.pTab;
  assert( pTab->tabFlags & TF_Strict );
  assert( pTab->nNVCol==pOp->p2 );
  aCol = pTab->aCol;
  pIn1 = &aMem[pOp->p1];
  for(i=0; i<pTab->nCol; i++){

    if( aCol[i].colFlags & COLFLAG_VIRTUAL ) continue;


    assert( pIn1 < &aMem[pOp->p1+pOp->p2] );
    applyAffinity(pIn1, aCol[i].affinity, encoding);
    if( (pIn1->flags & MEM_Null)==0 ){
      switch( aCol[i].eCType ){
        case COLTYPE_BLOB: {
          if( (pIn1->flags & MEM_Blob)==0 ) goto vdbe_type_error;
          break;







>
|
>
>







89729
89730
89731
89732
89733
89734
89735
89736
89737
89738
89739
89740
89741
89742
89743
89744
89745
89746
  assert( pOp->p4type==P4_TABLE );
  pTab = pOp->p4.pTab;
  assert( pTab->tabFlags & TF_Strict );
  assert( pTab->nNVCol==pOp->p2 );
  aCol = pTab->aCol;
  pIn1 = &aMem[pOp->p1];
  for(i=0; i<pTab->nCol; i++){
    if( aCol[i].colFlags & COLFLAG_GENERATED ){
      if( aCol[i].colFlags & COLFLAG_VIRTUAL ) continue;
      if( pOp->p3 ){ pIn1++; continue; }
    }
    assert( pIn1 < &aMem[pOp->p1+pOp->p2] );
    applyAffinity(pIn1, aCol[i].affinity, encoding);
    if( (pIn1->flags & MEM_Null)==0 ){
      switch( aCol[i].eCType ){
        case COLTYPE_BLOB: {
          if( (pIn1->flags & MEM_Blob)==0 ) goto vdbe_type_error;
          break;
89754
89755
89756
89757
89758
89759
89760
89761
89762
89763
89764
89765
89766
89767
89768
  assert( nByte==(int)(zPayload - (u8*)pOut->z) );

  assert( pOp->p3>0 && pOp->p3<=(p->nMem+1 - p->nCursor) );
  REGISTER_TRACE(pOp->p3, pOut);
  break;
}

/* Opcode: Count P1 P2 p3 * *
** Synopsis: r[P2]=count()
**
** Store the number of entries (an integer value) in the table or index
** opened by cursor P1 in register P2.
**
** If P3==0, then an exact count is obtained, which involves visiting
** every btree page of the table.  But if P3 is non-zero, an estimate







|







90135
90136
90137
90138
90139
90140
90141
90142
90143
90144
90145
90146
90147
90148
90149
  assert( nByte==(int)(zPayload - (u8*)pOut->z) );

  assert( pOp->p3>0 && pOp->p3<=(p->nMem+1 - p->nCursor) );
  REGISTER_TRACE(pOp->p3, pOut);
  break;
}

/* Opcode: Count P1 P2 P3 * *
** Synopsis: r[P2]=count()
**
** Store the number of entries (an integer value) in the table or index
** opened by cursor P1 in register P2.
**
** If P3==0, then an exact count is obtained, which involves visiting
** every btree page of the table.  But if P3 is non-zero, an estimate
90075
90076
90077
90078
90079
90080
90081

90082


90083





90084
90085
90086
90087
90088
90089
90090
  int iMeta = 0;

  assert( p->bIsReader );
  assert( p->readOnly==0 || pOp->p2==0 );
  assert( pOp->p2>=0 && pOp->p2<=2 );
  assert( pOp->p1>=0 && pOp->p1<db->nDb );
  assert( DbMaskTest(p->btreeMask, pOp->p1) );

  if( pOp->p2 && (db->flags & SQLITE_QueryOnly)!=0 ){


    rc = SQLITE_READONLY;





    goto abort_due_to_error;
  }
  pBt = db->aDb[pOp->p1].pBt;

  if( pBt ){
    rc = sqlite3BtreeBeginTrans(pBt, pOp->p2, &iMeta);
    testcase( rc==SQLITE_BUSY_SNAPSHOT );







>
|
>
>
|
>
>
>
>
>







90456
90457
90458
90459
90460
90461
90462
90463
90464
90465
90466
90467
90468
90469
90470
90471
90472
90473
90474
90475
90476
90477
90478
90479
  int iMeta = 0;

  assert( p->bIsReader );
  assert( p->readOnly==0 || pOp->p2==0 );
  assert( pOp->p2>=0 && pOp->p2<=2 );
  assert( pOp->p1>=0 && pOp->p1<db->nDb );
  assert( DbMaskTest(p->btreeMask, pOp->p1) );
  assert( rc==SQLITE_OK );
  if( pOp->p2 && (db->flags & (SQLITE_QueryOnly|SQLITE_CorruptRdOnly))!=0 ){
    if( db->flags & SQLITE_QueryOnly ){
      /* Writes prohibited by the "PRAGMA query_only=TRUE" statement */
      rc = SQLITE_READONLY;
    }else{
      /* Writes prohibited due to a prior SQLITE_CORRUPT in the current
      ** transaction */
      rc = SQLITE_CORRUPT;
    }
    goto abort_due_to_error;
  }
  pBt = db->aDb[pOp->p1].pBt;

  if( pBt ){
    rc = sqlite3BtreeBeginTrans(pBt, pOp->p2, &iMeta);
    testcase( rc==SQLITE_BUSY_SNAPSHOT );
90118
90119
90120
90121
90122
90123
90124

90125
90126
90127
90128
90129
90130
90131
90132
      ** counter. If the statement transaction needs to be rolled back,
      ** the value of this counter needs to be restored too.  */
      p->nStmtDefCons = db->nDeferredCons;
      p->nStmtDefImmCons = db->nDeferredImmCons;
    }
  }
  assert( pOp->p5==0 || pOp->p4type==P4_INT32 );

  if( pOp->p5
   && (iMeta!=pOp->p3
      || db->aDb[pOp->p1].pSchema->iGeneration!=pOp->p4.i)
  ){
    /*
    ** IMPLEMENTATION-OF: R-03189-51135 As each SQL statement runs, the schema
    ** version is checked to ensure that the schema has not changed since the
    ** SQL statement was prepared.







>
|







90507
90508
90509
90510
90511
90512
90513
90514
90515
90516
90517
90518
90519
90520
90521
90522
      ** counter. If the statement transaction needs to be rolled back,
      ** the value of this counter needs to be restored too.  */
      p->nStmtDefCons = db->nDeferredCons;
      p->nStmtDefImmCons = db->nDeferredImmCons;
    }
  }
  assert( pOp->p5==0 || pOp->p4type==P4_INT32 );
  if( rc==SQLITE_OK
   && pOp->p5
   && (iMeta!=pOp->p3
      || db->aDb[pOp->p1].pSchema->iGeneration!=pOp->p4.i)
  ){
    /*
    ** IMPLEMENTATION-OF: R-03189-51135 As each SQL statement runs, the schema
    ** version is checked to ensure that the schema has not changed since the
    ** SQL statement was prepared.
90512
90513
90514
90515
90516
90517
90518
90519
90520
90521
90522
90523
90524
90525
90526
    assert( pOp->p2==0 ); /* Only used when number of columns is zero */
    assert( pOp->opcode==OP_OpenEphemeral );
    assert( aMem[pOp->p3].flags & MEM_Null );
    aMem[pOp->p3].n = 0;
    aMem[pOp->p3].z = "";
  }
  pCx = p->apCsr[pOp->p1];
  if( pCx && !pCx->hasBeenDuped ){
    /* If the ephermeral table is already open and has no duplicates from
    ** OP_OpenDup, then erase all existing content so that the table is
    ** empty again, rather than creating a new table. */
    assert( pCx->isEphemeral );
    pCx->seqCount = 0;
    pCx->cacheStatus = CACHE_STALE;
    rc = sqlite3BtreeClearTable(pCx->pBtx, pCx->pgnoRoot, 0);







|







90902
90903
90904
90905
90906
90907
90908
90909
90910
90911
90912
90913
90914
90915
90916
    assert( pOp->p2==0 ); /* Only used when number of columns is zero */
    assert( pOp->opcode==OP_OpenEphemeral );
    assert( aMem[pOp->p3].flags & MEM_Null );
    aMem[pOp->p3].n = 0;
    aMem[pOp->p3].z = "";
  }
  pCx = p->apCsr[pOp->p1];
  if( pCx && !pCx->hasBeenDuped &&  ALWAYS(pOp->p2<=pCx->nField) ){
    /* If the ephermeral table is already open and has no duplicates from
    ** OP_OpenDup, then erase all existing content so that the table is
    ** empty again, rather than creating a new table. */
    assert( pCx->isEphemeral );
    pCx->seqCount = 0;
    pCx->cacheStatus = CACHE_STALE;
    rc = sqlite3BtreeClearTable(pCx->pBtx, pCx->pgnoRoot, 0);
91675
91676
91677
91678
91679
91680
91681
91682
91683
91684
91685
91686
91687
91688
91689
  if( pOp->p4type==P4_TABLE && HAS_UPDATE_HOOK(db) ){
    assert( pC->iDb>=0 );
    zDb = db->aDb[pC->iDb].zDbSName;
    pTab = pOp->p4.pTab;
    assert( (pOp->p5 & OPFLAG_ISNOOP) || HasRowid(pTab) );
  }else{
    pTab = 0;
    zDb = 0;  /* Not needed.  Silence a compiler warning. */
  }

#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
  /* Invoke the pre-update hook, if any */
  if( pTab ){
    if( db->xPreUpdateCallback && !(pOp->p5 & OPFLAG_ISUPDATE) ){
      sqlite3VdbePreUpdateHook(p,pC,SQLITE_INSERT,zDb,pTab,x.nKey,pOp->p2,-1);







|







92065
92066
92067
92068
92069
92070
92071
92072
92073
92074
92075
92076
92077
92078
92079
  if( pOp->p4type==P4_TABLE && HAS_UPDATE_HOOK(db) ){
    assert( pC->iDb>=0 );
    zDb = db->aDb[pC->iDb].zDbSName;
    pTab = pOp->p4.pTab;
    assert( (pOp->p5 & OPFLAG_ISNOOP) || HasRowid(pTab) );
  }else{
    pTab = 0;
    zDb = 0;
  }

#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
  /* Invoke the pre-update hook, if any */
  if( pTab ){
    if( db->xPreUpdateCallback && !(pOp->p5 & OPFLAG_ISUPDATE) ){
      sqlite3VdbePreUpdateHook(p,pC,SQLITE_INSERT,zDb,pTab,x.nKey,pOp->p2,-1);
91828
91829
91830
91831
91832
91833
91834
91835
91836
91837
91838
91839
91840

91841
91842
91843
91844
91845
91846
91847
91848
    assert( pOp->p4.pTab!=0 );
    zDb = db->aDb[pC->iDb].zDbSName;
    pTab = pOp->p4.pTab;
    if( (pOp->p5 & OPFLAG_SAVEPOSITION)!=0 && pC->isTable ){
      pC->movetoTarget = sqlite3BtreeIntegerKey(pC->uc.pCursor);
    }
  }else{
    zDb = 0;   /* Not needed.  Silence a compiler warning. */
    pTab = 0;  /* Not needed.  Silence a compiler warning. */
  }

#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
  /* Invoke the pre-update-hook if required. */

  if( db->xPreUpdateCallback && pOp->p4.pTab ){
    assert( !(opflags & OPFLAG_ISUPDATE)
         || HasRowid(pTab)==0
         || (aMem[pOp->p3].flags & MEM_Int)
    );
    sqlite3VdbePreUpdateHook(p, pC,
        (opflags & OPFLAG_ISUPDATE) ? SQLITE_UPDATE : SQLITE_DELETE,
        zDb, pTab, pC->movetoTarget,







|
|




>
|







92218
92219
92220
92221
92222
92223
92224
92225
92226
92227
92228
92229
92230
92231
92232
92233
92234
92235
92236
92237
92238
92239
    assert( pOp->p4.pTab!=0 );
    zDb = db->aDb[pC->iDb].zDbSName;
    pTab = pOp->p4.pTab;
    if( (pOp->p5 & OPFLAG_SAVEPOSITION)!=0 && pC->isTable ){
      pC->movetoTarget = sqlite3BtreeIntegerKey(pC->uc.pCursor);
    }
  }else{
    zDb = 0;
    pTab = 0;
  }

#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
  /* Invoke the pre-update-hook if required. */
  assert( db->xPreUpdateCallback==0 || pTab==pOp->p4.pTab );
  if( db->xPreUpdateCallback && pTab ){
    assert( !(opflags & OPFLAG_ISUPDATE)
         || HasRowid(pTab)==0
         || (aMem[pOp->p3].flags & MEM_Int)
    );
    sqlite3VdbePreUpdateHook(p, pC,
        (opflags & OPFLAG_ISUPDATE) ? SQLITE_UPDATE : SQLITE_DELETE,
        zDb, pTab, pC->movetoTarget,
91875
91876
91877
91878
91879
91880
91881
91882
91883
91884
91885
91886
91887
91888
91889
  pC->cacheStatus = CACHE_STALE;
  pC->seekResult = 0;
  if( rc ) goto abort_due_to_error;

  /* Invoke the update-hook if required. */
  if( opflags & OPFLAG_NCHANGE ){
    p->nChange++;
    if( db->xUpdateCallback && HasRowid(pTab) ){
      db->xUpdateCallback(db->pUpdateArg, SQLITE_DELETE, zDb, pTab->zName,
          pC->movetoTarget);
      assert( pC->iDb>=0 );
    }
  }

  break;







|







92266
92267
92268
92269
92270
92271
92272
92273
92274
92275
92276
92277
92278
92279
92280
  pC->cacheStatus = CACHE_STALE;
  pC->seekResult = 0;
  if( rc ) goto abort_due_to_error;

  /* Invoke the update-hook if required. */
  if( opflags & OPFLAG_NCHANGE ){
    p->nChange++;
    if( db->xUpdateCallback && ALWAYS(pTab!=0) && HasRowid(pTab) ){
      db->xUpdateCallback(db->pUpdateArg, SQLITE_DELETE, zDb, pTab->zName,
          pC->movetoTarget);
      assert( pC->iDb>=0 );
    }
  }

  break;
92923
92924
92925
92926
92927
92928
92929
92930
92931
92932
92933
92934
92935
92936
92937
    db->mDbFlags &= ~DBFLAG_SchemaKnownOk;
    rc = sqlite3InitOne(db, iDb, &p->zErrMsg, pOp->p5);
    db->mDbFlags |= DBFLAG_SchemaChange;
    p->expired = 0;
  }else
#endif
  {
    zSchema = DFLT_SCHEMA_TABLE;
    initData.db = db;
    initData.iDb = iDb;
    initData.pzErrMsg = &p->zErrMsg;
    initData.mInitFlags = 0;
    initData.mxPage = sqlite3BtreeLastPage(db->aDb[iDb].pBt);
    zSql = sqlite3MPrintf(db,
       "SELECT*FROM\"%w\".%s WHERE %s ORDER BY rowid",







|







93314
93315
93316
93317
93318
93319
93320
93321
93322
93323
93324
93325
93326
93327
93328
    db->mDbFlags &= ~DBFLAG_SchemaKnownOk;
    rc = sqlite3InitOne(db, iDb, &p->zErrMsg, pOp->p5);
    db->mDbFlags |= DBFLAG_SchemaChange;
    p->expired = 0;
  }else
#endif
  {
    zSchema = LEGACY_SCHEMA_TABLE;
    initData.db = db;
    initData.iDb = iDb;
    initData.pzErrMsg = &p->zErrMsg;
    initData.mInitFlags = 0;
    initData.mxPage = sqlite3BtreeLastPage(db->aDb[iDb].pBt);
    zSql = sqlite3MPrintf(db,
       "SELECT*FROM\"%w\".%s WHERE %s ORDER BY rowid",
94143
94144
94145
94146
94147
94148
94149

94150
94151
94152
94153
94154
94155
94156
  Mem **apArg;

  pQuery = &aMem[pOp->p3];
  pArgc = &pQuery[1];
  pCur = p->apCsr[pOp->p1];
  assert( memIsValid(pQuery) );
  REGISTER_TRACE(pOp->p3, pQuery);

  assert( pCur->eCurType==CURTYPE_VTAB );
  pVCur = pCur->uc.pVCur;
  pVtab = pVCur->pVtab;
  pModule = pVtab->pModule;

  /* Grab the index number and argc parameters */
  assert( (pQuery->flags&MEM_Int)!=0 && pArgc->flags==MEM_Int );







>







94534
94535
94536
94537
94538
94539
94540
94541
94542
94543
94544
94545
94546
94547
94548
  Mem **apArg;

  pQuery = &aMem[pOp->p3];
  pArgc = &pQuery[1];
  pCur = p->apCsr[pOp->p1];
  assert( memIsValid(pQuery) );
  REGISTER_TRACE(pOp->p3, pQuery);
  assert( pCur!=0 );
  assert( pCur->eCurType==CURTYPE_VTAB );
  pVCur = pCur->uc.pVCur;
  pVtab = pVCur->pVtab;
  pModule = pVtab->pModule;

  /* Grab the index number and argc parameters */
  assert( (pQuery->flags&MEM_Int)!=0 && pArgc->flags==MEM_Int );
94191
94192
94193
94194
94195
94196
94197

94198
94199
94200
94201
94202
94203
94204
case OP_VColumn: {
  sqlite3_vtab *pVtab;
  const sqlite3_module *pModule;
  Mem *pDest;
  sqlite3_context sContext;

  VdbeCursor *pCur = p->apCsr[pOp->p1];

  assert( pCur->eCurType==CURTYPE_VTAB );
  assert( pOp->p3>0 && pOp->p3<=(p->nMem+1 - p->nCursor) );
  pDest = &aMem[pOp->p3];
  memAboutToChange(p, pDest);
  if( pCur->nullRow ){
    sqlite3VdbeMemSetNull(pDest);
    break;







>







94583
94584
94585
94586
94587
94588
94589
94590
94591
94592
94593
94594
94595
94596
94597
case OP_VColumn: {
  sqlite3_vtab *pVtab;
  const sqlite3_module *pModule;
  Mem *pDest;
  sqlite3_context sContext;

  VdbeCursor *pCur = p->apCsr[pOp->p1];
  assert( pCur!=0 );
  assert( pCur->eCurType==CURTYPE_VTAB );
  assert( pOp->p3>0 && pOp->p3<=(p->nMem+1 - p->nCursor) );
  pDest = &aMem[pOp->p3];
  memAboutToChange(p, pDest);
  if( pCur->nullRow ){
    sqlite3VdbeMemSetNull(pDest);
    break;
94244
94245
94246
94247
94248
94249
94250

94251
94252
94253
94254
94255
94256
94257
case OP_VNext: {   /* jump */
  sqlite3_vtab *pVtab;
  const sqlite3_module *pModule;
  int res;
  VdbeCursor *pCur;

  pCur = p->apCsr[pOp->p1];

  assert( pCur->eCurType==CURTYPE_VTAB );
  if( pCur->nullRow ){
    break;
  }
  pVtab = pCur->uc.pVCur->pVtab;
  pModule = pVtab->pModule;
  assert( pModule->xNext );







>







94637
94638
94639
94640
94641
94642
94643
94644
94645
94646
94647
94648
94649
94650
94651
case OP_VNext: {   /* jump */
  sqlite3_vtab *pVtab;
  const sqlite3_module *pModule;
  int res;
  VdbeCursor *pCur;

  pCur = p->apCsr[pOp->p1];
  assert( pCur!=0 );
  assert( pCur->eCurType==CURTYPE_VTAB );
  if( pCur->nullRow ){
    break;
  }
  pVtab = pCur->uc.pVCur->pVtab;
  pModule = pVtab->pModule;
  assert( pModule->xNext );
94339
94340
94341
94342
94343
94344
94345
94346
94347
94348
94349
94350
94351
94352
94353
** apply in the case of a constraint failure on an insert or update.
*/
case OP_VUpdate: {
  sqlite3_vtab *pVtab;
  const sqlite3_module *pModule;
  int nArg;
  int i;
  sqlite_int64 rowid;
  Mem **apArg;
  Mem *pX;

  assert( pOp->p2==1        || pOp->p5==OE_Fail   || pOp->p5==OE_Rollback
       || pOp->p5==OE_Abort || pOp->p5==OE_Ignore || pOp->p5==OE_Replace
  );
  assert( p->readOnly==0 );







|







94733
94734
94735
94736
94737
94738
94739
94740
94741
94742
94743
94744
94745
94746
94747
** apply in the case of a constraint failure on an insert or update.
*/
case OP_VUpdate: {
  sqlite3_vtab *pVtab;
  const sqlite3_module *pModule;
  int nArg;
  int i;
  sqlite_int64 rowid = 0;
  Mem **apArg;
  Mem *pX;

  assert( pOp->p2==1        || pOp->p5==OE_Fail   || pOp->p5==OE_Rollback
       || pOp->p5==OE_Abort || pOp->p5==OE_Ignore || pOp->p5==OE_Replace
  );
  assert( p->readOnly==0 );
94526
94527
94528
94529
94530
94531
94532







































































94533
94534
94535
94536
94537
94538
94539
    if( sqlite3VdbeMemTooBig(pOut) ) goto too_big;
  }

  REGISTER_TRACE(pOp->p3, pOut);
  UPDATE_MAX_BLOBSIZE(pOut);
  break;
}








































































/* Opcode: Trace P1 P2 * P4 *
**
** Write P4 on the statement trace output if statement tracing is
** enabled.
**
** Operand P1 must be 0x7fffffff and P2 must positive.







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







94920
94921
94922
94923
94924
94925
94926
94927
94928
94929
94930
94931
94932
94933
94934
94935
94936
94937
94938
94939
94940
94941
94942
94943
94944
94945
94946
94947
94948
94949
94950
94951
94952
94953
94954
94955
94956
94957
94958
94959
94960
94961
94962
94963
94964
94965
94966
94967
94968
94969
94970
94971
94972
94973
94974
94975
94976
94977
94978
94979
94980
94981
94982
94983
94984
94985
94986
94987
94988
94989
94990
94991
94992
94993
94994
94995
94996
94997
94998
94999
95000
95001
95002
95003
95004
    if( sqlite3VdbeMemTooBig(pOut) ) goto too_big;
  }

  REGISTER_TRACE(pOp->p3, pOut);
  UPDATE_MAX_BLOBSIZE(pOut);
  break;
}

/* Opcode: FilterAdd P1 * P3 P4 *
** Synopsis: filter(P1) += key(P3@P4)
**
** Compute a hash on the P4 registers starting with r[P3] and
** add that hash to the bloom filter contained in r[P1].
*/
case OP_FilterAdd: {
  u64 h;

  assert( pOp->p1>0 && pOp->p1<=(p->nMem+1 - p->nCursor) );
  pIn1 = &aMem[pOp->p1];
  assert( pIn1->flags & MEM_Blob );
  assert( pIn1->n>0 );
  h = filterHash(aMem, pOp);
#ifdef SQLITE_DEBUG
  if( db->flags&SQLITE_VdbeTrace ){
    int ii;
    for(ii=pOp->p3; ii<pOp->p3+pOp->p4.i; ii++){
      registerTrace(ii, &aMem[ii]);
    }
    printf("hash: %llu modulo %d -> %u\n", h, pIn1->n, (int)(h%pIn1->n));
  }
#endif
  h %= pIn1->n;
  pIn1->z[h/8] |= 1<<(h&7);
  break;
}

/* Opcode: Filter P1 P2 P3 P4 *
** Synopsis: if key(P3@P4) not in filter(P1) goto P2
**
** Compute a hash on the key contained in the P4 registers starting
** with r[P3].  Check to see if that hash is found in the
** bloom filter hosted by register P1.  If it is not present then
** maybe jump to P2.  Otherwise fall through.
**
** False negatives are harmless.  It is always safe to fall through,
** even if the value is in the bloom filter.  A false negative causes
** more CPU cycles to be used, but it should still yield the correct
** answer.  However, an incorrect answer may well arise from a
** false positive - if the jump is taken when it should fall through.
*/
case OP_Filter: {          /* jump */
  u64 h;

  assert( pOp->p1>0 && pOp->p1<=(p->nMem+1 - p->nCursor) );
  pIn1 = &aMem[pOp->p1];
  assert( (pIn1->flags & MEM_Blob)!=0 );
  assert( pIn1->n >= 1 );
  h = filterHash(aMem, pOp);
#ifdef SQLITE_DEBUG
  if( db->flags&SQLITE_VdbeTrace ){
    int ii;
    for(ii=pOp->p3; ii<pOp->p3+pOp->p4.i; ii++){
      registerTrace(ii, &aMem[ii]);
    }
    printf("hash: %llu modulo %d -> %u\n", h, pIn1->n, (int)(h%pIn1->n));
  }
#endif
  h %= pIn1->n;
  if( (pIn1->z[h/8] & (1<<(h&7)))==0 ){
    VdbeBranchTaken(1, 2);
    p->aCounter[SQLITE_STMTSTATUS_FILTER_HIT]++;
    goto jump_to_p2;
  }else{
    p->aCounter[SQLITE_STMTSTATUS_FILTER_MISS]++;
    VdbeBranchTaken(0, 2);
  }
  break;
}

/* Opcode: Trace P1 P2 * P4 *
**
** Write P4 on the statement trace output if statement tracing is
** enabled.
**
** Operand P1 must be 0x7fffffff and P2 must positive.
94786
94787
94788
94789
94790
94791
94792







94793
94794
94795
94796
94797
94798
94799
94800
94801
94802
94803
94804
94805



94806
94807
94808
94809
94810
94811
94812
    rc = SQLITE_NOMEM_BKPT;
  }else if( rc==SQLITE_IOERR_CORRUPTFS ){
    rc = SQLITE_CORRUPT_BKPT;
  }
  assert( rc );
#ifdef SQLITE_DEBUG
  if( db->flags & SQLITE_VdbeTrace ){







     printf("ABORT-due-to-error.  rc=%d\n", rc);
  }
#endif
  if( p->zErrMsg==0 && rc!=SQLITE_IOERR_NOMEM ){
    sqlite3VdbeError(p, "%s", sqlite3ErrStr(rc));
  }
  p->rc = rc;
  sqlite3SystemError(db, rc);
  testcase( sqlite3GlobalConfig.xLog!=0 );
  sqlite3_log(rc, "statement aborts at %d: [%s] %s",
                   (int)(pOp - aOp), p->zSql, p->zErrMsg);
  sqlite3VdbeHalt(p);
  if( rc==SQLITE_IOERR_NOMEM ) sqlite3OomFault(db);



  rc = SQLITE_ERROR;
  if( resetSchemaOnFault>0 ){
    sqlite3ResetOneSchema(db, resetSchemaOnFault-1);
  }

  /* This is the only way out of this procedure.  We have to
  ** release the mutexes on btrees that were acquired at the







>
>
>
>
>
>
>
|












>
>
>







95251
95252
95253
95254
95255
95256
95257
95258
95259
95260
95261
95262
95263
95264
95265
95266
95267
95268
95269
95270
95271
95272
95273
95274
95275
95276
95277
95278
95279
95280
95281
95282
95283
95284
95285
95286
95287
    rc = SQLITE_NOMEM_BKPT;
  }else if( rc==SQLITE_IOERR_CORRUPTFS ){
    rc = SQLITE_CORRUPT_BKPT;
  }
  assert( rc );
#ifdef SQLITE_DEBUG
  if( db->flags & SQLITE_VdbeTrace ){
    const char *zTrace = p->zSql;
    if( zTrace==0 ){
      if( aOp[0].opcode==OP_Trace ){
        zTrace = aOp[0].p4.z;
      }
      if( zTrace==0 ) zTrace = "???";
    }
    printf("ABORT-due-to-error (rc=%d): %s\n", rc, zTrace);
  }
#endif
  if( p->zErrMsg==0 && rc!=SQLITE_IOERR_NOMEM ){
    sqlite3VdbeError(p, "%s", sqlite3ErrStr(rc));
  }
  p->rc = rc;
  sqlite3SystemError(db, rc);
  testcase( sqlite3GlobalConfig.xLog!=0 );
  sqlite3_log(rc, "statement aborts at %d: [%s] %s",
                   (int)(pOp - aOp), p->zSql, p->zErrMsg);
  sqlite3VdbeHalt(p);
  if( rc==SQLITE_IOERR_NOMEM ) sqlite3OomFault(db);
  if( rc==SQLITE_CORRUPT && db->autoCommit==0 ){
    db->flags |= SQLITE_CorruptRdOnly;
  }
  rc = SQLITE_ERROR;
  if( resetSchemaOnFault>0 ){
    sqlite3ResetOneSchema(db, resetSchemaOnFault-1);
  }

  /* This is the only way out of this procedure.  We have to
  ** release the mutexes on btrees that were acquired at the
94930
94931
94932
94933
94934
94935
94936



94937
94938
94939
94940
94941
94942
94943
94944
    assert( v->aOp[v->pc].opcode==OP_NotExists );
    rc = sqlite3VdbeExec(v);
  }else{
    rc = sqlite3_step(p->pStmt);
  }
  if( rc==SQLITE_ROW ){
    VdbeCursor *pC = v->apCsr[0];



    u32 type = pC->nHdrParsed>p->iCol ? pC->aType[p->iCol] : 0;
    testcase( pC->nHdrParsed==p->iCol );
    testcase( pC->nHdrParsed==p->iCol+1 );
    if( type<12 ){
      zErr = sqlite3MPrintf(p->db, "cannot open value of type %s",
          type==0?"null": type==7?"real": "integer"
      );
      rc = SQLITE_ERROR;







>
>
>
|







95405
95406
95407
95408
95409
95410
95411
95412
95413
95414
95415
95416
95417
95418
95419
95420
95421
95422
    assert( v->aOp[v->pc].opcode==OP_NotExists );
    rc = sqlite3VdbeExec(v);
  }else{
    rc = sqlite3_step(p->pStmt);
  }
  if( rc==SQLITE_ROW ){
    VdbeCursor *pC = v->apCsr[0];
    u32 type;
    assert( pC!=0 );
    assert( pC->eCurType==CURTYPE_BTREE );
    type = pC->nHdrParsed>p->iCol ? pC->aType[p->iCol] : 0;
    testcase( pC->nHdrParsed==p->iCol );
    testcase( pC->nHdrParsed==p->iCol+1 );
    if( type<12 ){
      zErr = sqlite3MPrintf(p->db, "cannot open value of type %s",
          type==0?"null": type==7?"real": "integer"
      );
      rc = SQLITE_ERROR;
95067
95068
95069
95070
95071
95072
95073
95074
95075
95076
95077
95078
95079
95080
95081
#ifndef SQLITE_OMIT_FOREIGN_KEY
      if( db->flags&SQLITE_ForeignKeys ){
        /* Check that the column is not part of an FK child key definition. It
        ** is not necessary to check if it is part of a parent key, as parent
        ** key columns must be indexed. The check below will pick up this
        ** case.  */
        FKey *pFKey;
        assert( !IsVirtual(pTab) );
        for(pFKey=pTab->u.tab.pFKey; pFKey; pFKey=pFKey->pNextFrom){
          int j;
          for(j=0; j<pFKey->nCol; j++){
            if( pFKey->aCol[j].iFrom==iCol ){
              zFault = "foreign key";
            }
          }







|







95545
95546
95547
95548
95549
95550
95551
95552
95553
95554
95555
95556
95557
95558
95559
#ifndef SQLITE_OMIT_FOREIGN_KEY
      if( db->flags&SQLITE_ForeignKeys ){
        /* Check that the column is not part of an FK child key definition. It
        ** is not necessary to check if it is part of a parent key, as parent
        ** key columns must be indexed. The check below will pick up this
        ** case.  */
        FKey *pFKey;
        assert( IsOrdinaryTable(pTab) );
        for(pFKey=pTab->u.tab.pFKey; pFKey; pFKey=pFKey->pNextFrom){
          int j;
          for(j=0; j<pFKey->nCol; j++){
            if( pFKey->aCol[j].iFrom==iCol ){
              zFault = "foreign key";
            }
          }
95275
95276
95277
95278
95279
95280
95281


95282
95283
95284
95285
95286
95287
95288
      ** same way as an SQLITE_DELETE (the SQLITE_DELETE code is actually
      ** slightly more efficient). Since you cannot write to a PK column
      ** using the incremental-blob API, this works. For the sessions module
      ** anyhow.
      */
      sqlite3_int64 iKey;
      iKey = sqlite3BtreeIntegerKey(p->pCsr);


      sqlite3VdbePreUpdateHook(
          v, v->apCsr[0], SQLITE_DELETE, p->zDb, p->pTab, iKey, -1, p->iCol
      );
    }
#endif

    rc = xCall(p->pCsr, iOffset+p->iOffset, n, z);







>
>







95753
95754
95755
95756
95757
95758
95759
95760
95761
95762
95763
95764
95765
95766
95767
95768
      ** same way as an SQLITE_DELETE (the SQLITE_DELETE code is actually
      ** slightly more efficient). Since you cannot write to a PK column
      ** using the incremental-blob API, this works. For the sessions module
      ** anyhow.
      */
      sqlite3_int64 iKey;
      iKey = sqlite3BtreeIntegerKey(p->pCsr);
      assert( v->apCsr[0]!=0 );
      assert( v->apCsr[0]->eCurType==CURTYPE_BTREE );
      sqlite3VdbePreUpdateHook(
          v, v->apCsr[0], SQLITE_DELETE, p->zDb, p->pTab, iKey, -1, p->iCol
      );
    }
#endif

    rc = xCall(p->pCsr, iOffset+p->iOffset, n, z);
96657
96658
96659
96660
96661
96662
96663
96664
96665
96666
96667
96668
96669
96670
96671
static void vdbeSorterExtendFile(sqlite3 *db, sqlite3_file *pFd, i64 nByte){
  if( nByte<=(i64)(db->nMaxSorterMmap) && pFd->pMethods->iVersion>=3 ){
    void *p = 0;
    int chunksize = 4*1024;
    sqlite3OsFileControlHint(pFd, SQLITE_FCNTL_CHUNK_SIZE, &chunksize);
    sqlite3OsFileControlHint(pFd, SQLITE_FCNTL_SIZE_HINT, &nByte);
    sqlite3OsFetch(pFd, 0, (int)nByte, &p);
    sqlite3OsUnfetch(pFd, 0, p);
  }
}
#else
# define vdbeSorterExtendFile(x,y,z)
#endif

/*







|







97137
97138
97139
97140
97141
97142
97143
97144
97145
97146
97147
97148
97149
97150
97151
static void vdbeSorterExtendFile(sqlite3 *db, sqlite3_file *pFd, i64 nByte){
  if( nByte<=(i64)(db->nMaxSorterMmap) && pFd->pMethods->iVersion>=3 ){
    void *p = 0;
    int chunksize = 4*1024;
    sqlite3OsFileControlHint(pFd, SQLITE_FCNTL_CHUNK_SIZE, &chunksize);
    sqlite3OsFileControlHint(pFd, SQLITE_FCNTL_SIZE_HINT, &nByte);
    sqlite3OsFetch(pFd, 0, (int)nByte, &p);
    if( p ) sqlite3OsUnfetch(pFd, 0, p);
  }
}
#else
# define vdbeSorterExtendFile(x,y,z)
#endif

/*
97375
97376
97377
97378
97379
97380
97381

97382
97383
97384
97385
97386
97387
97388
    pIncr->pTask = pTask;
    pIncr->mxSz = MAX(pTask->pSorter->mxKeysize+9,pTask->pSorter->mxPmaSize/2);
    pTask->file2.iEof += pIncr->mxSz;
  }else{
    vdbeMergeEngineFree(pMerger);
    rc = SQLITE_NOMEM_BKPT;
  }

  return rc;
}

#if SQLITE_MAX_WORKER_THREADS>0
/*
** Set the "use-threads" flag on object pIncr.
*/







>







97855
97856
97857
97858
97859
97860
97861
97862
97863
97864
97865
97866
97867
97868
97869
    pIncr->pTask = pTask;
    pIncr->mxSz = MAX(pTask->pSorter->mxKeysize+9,pTask->pSorter->mxPmaSize/2);
    pTask->file2.iEof += pIncr->mxSz;
  }else{
    vdbeMergeEngineFree(pMerger);
    rc = SQLITE_NOMEM_BKPT;
  }
  assert( *ppOut!=0 || rc!=SQLITE_OK );
  return rc;
}

#if SQLITE_MAX_WORKER_THREADS>0
/*
** Set the "use-threads" flag on object pIncr.
*/
99076
99077
99078
99079
99080
99081
99082
99083
99084
99085
99086
99087
99088
99089
99090
    if( !ExprHasProperty(pExpr,(EP_TokenOnly|EP_Leaf)) ){
      assert( pExpr->x.pList==0 || pExpr->pRight==0 );
      if( pExpr->pLeft && walkExpr(pWalker, pExpr->pLeft) ) return WRC_Abort;
      if( pExpr->pRight ){
        assert( !ExprHasProperty(pExpr, EP_WinFunc) );
        pExpr = pExpr->pRight;
        continue;
      }else if( ExprHasProperty(pExpr, EP_xIsSelect) ){
        assert( !ExprHasProperty(pExpr, EP_WinFunc) );
        if( sqlite3WalkSelect(pWalker, pExpr->x.pSelect) ) return WRC_Abort;
      }else{
        if( pExpr->x.pList ){
          if( sqlite3WalkExprList(pWalker, pExpr->x.pList) ) return WRC_Abort;
        }
#ifndef SQLITE_OMIT_WINDOWFUNC







|







99557
99558
99559
99560
99561
99562
99563
99564
99565
99566
99567
99568
99569
99570
99571
    if( !ExprHasProperty(pExpr,(EP_TokenOnly|EP_Leaf)) ){
      assert( pExpr->x.pList==0 || pExpr->pRight==0 );
      if( pExpr->pLeft && walkExpr(pWalker, pExpr->pLeft) ) return WRC_Abort;
      if( pExpr->pRight ){
        assert( !ExprHasProperty(pExpr, EP_WinFunc) );
        pExpr = pExpr->pRight;
        continue;
      }else if( ExprUseXSelect(pExpr) ){
        assert( !ExprHasProperty(pExpr, EP_WinFunc) );
        if( sqlite3WalkSelect(pWalker, pExpr->x.pSelect) ) return WRC_Abort;
      }else{
        if( pExpr->x.pList ){
          if( sqlite3WalkExprList(pWalker, pExpr->x.pList) ) return WRC_Abort;
        }
#ifndef SQLITE_OMIT_WINDOWFUNC
99348
99349
99350
99351
99352
99353
99354

99355
99356
99357
99358
99359
99360
99361
  pDup = sqlite3ExprDup(db, pOrig, 0);
  if( db->mallocFailed ){
    sqlite3ExprDelete(db, pDup);
    pDup = 0;
  }else{
    incrAggFunctionDepth(pDup, nSubquery);
    if( pExpr->op==TK_COLLATE ){

      pDup = sqlite3ExprAddCollateString(pParse, pDup, pExpr->u.zToken);
    }

    /* Before calling sqlite3ExprDelete(), set the EP_Static flag. This
    ** prevents ExprDelete() from deleting the Expr structure itself,
    ** allowing it to be repopulated by the memcpy() on the following line.
    ** The pExpr->u.zToken might point into memory that will be freed by the







>







99829
99830
99831
99832
99833
99834
99835
99836
99837
99838
99839
99840
99841
99842
99843
  pDup = sqlite3ExprDup(db, pOrig, 0);
  if( db->mallocFailed ){
    sqlite3ExprDelete(db, pDup);
    pDup = 0;
  }else{
    incrAggFunctionDepth(pDup, nSubquery);
    if( pExpr->op==TK_COLLATE ){
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      pDup = sqlite3ExprAddCollateString(pParse, pDup, pExpr->u.zToken);
    }

    /* Before calling sqlite3ExprDelete(), set the EP_Static flag. This
    ** prevents ExprDelete() from deleting the Expr structure itself,
    ** allowing it to be repopulated by the memcpy() on the following line.
    ** The pExpr->u.zToken might point into memory that will be freed by the
99451
99452
99453
99454
99455
99456
99457

99458
99459
99460
99461
99462
99463
99464
** return the appropriate colUsed mask.
*/
SQLITE_PRIVATE Bitmask sqlite3ExprColUsed(Expr *pExpr){
  int n;
  Table *pExTab;

  n = pExpr->iColumn;

  pExTab = pExpr->y.pTab;
  assert( pExTab!=0 );
  if( (pExTab->tabFlags & TF_HasGenerated)!=0
   && (pExTab->aCol[n].colFlags & COLFLAG_GENERATED)!=0
  ){
    testcase( pExTab->nCol==BMS-1 );
    testcase( pExTab->nCol==BMS );







>







99933
99934
99935
99936
99937
99938
99939
99940
99941
99942
99943
99944
99945
99946
99947
** return the appropriate colUsed mask.
*/
SQLITE_PRIVATE Bitmask sqlite3ExprColUsed(Expr *pExpr){
  int n;
  Table *pExTab;

  n = pExpr->iColumn;
  assert( ExprUseYTab(pExpr) );
  pExTab = pExpr->y.pTab;
  assert( pExTab!=0 );
  if( (pExTab->tabFlags & TF_HasGenerated)!=0
   && (pExTab->aCol[n].colFlags & COLFLAG_GENERATED)!=0
  ){
    testcase( pExTab->nCol==BMS-1 );
    testcase( pExTab->nCol==BMS );
99588
99589
99590
99591
99592
99593
99594

99595
99596
99597
99598
99599
99600
99601
        }
        if( zTab ){
          const char *zTabName = pItem->zAlias ? pItem->zAlias : pTab->zName;
          assert( zTabName!=0 );
          if( sqlite3StrICmp(zTabName, zTab)!=0 ){
            continue;
          }

          if( IN_RENAME_OBJECT && pItem->zAlias ){
            sqlite3RenameTokenRemap(pParse, 0, (void*)&pExpr->y.pTab);
          }
        }
        hCol = sqlite3StrIHash(zCol);
        for(j=0, pCol=pTab->aCol; j<pTab->nCol; j++, pCol++){
          if( pCol->hName==hCol







>







100071
100072
100073
100074
100075
100076
100077
100078
100079
100080
100081
100082
100083
100084
100085
        }
        if( zTab ){
          const char *zTabName = pItem->zAlias ? pItem->zAlias : pTab->zName;
          assert( zTabName!=0 );
          if( sqlite3StrICmp(zTabName, zTab)!=0 ){
            continue;
          }
          assert( ExprUseYTab(pExpr) );
          if( IN_RENAME_OBJECT && pItem->zAlias ){
            sqlite3RenameTokenRemap(pParse, 0, (void*)&pExpr->y.pTab);
          }
        }
        hCol = sqlite3StrIHash(zCol);
        for(j=0, pCol=pTab->aCol; j<pTab->nCol; j++, pCol++){
          if( pCol->hName==hCol
99619
99620
99621
99622
99623
99624
99625

99626
99627
99628
99629
99630
99631
99632
        if( 0==cnt && VisibleRowid(pTab) ){
          cntTab++;
          pMatch = pItem;
        }
      }
      if( pMatch ){
        pExpr->iTable = pMatch->iCursor;

        pExpr->y.pTab = pMatch->pTab;
        /* RIGHT JOIN not (yet) supported */
        assert( (pMatch->fg.jointype & JT_RIGHT)==0 );
        if( (pMatch->fg.jointype & JT_LEFT)!=0 ){
          ExprSetProperty(pExpr, EP_CanBeNull);
        }
        pSchema = pExpr->y.pTab->pSchema;







>







100103
100104
100105
100106
100107
100108
100109
100110
100111
100112
100113
100114
100115
100116
100117
        if( 0==cnt && VisibleRowid(pTab) ){
          cntTab++;
          pMatch = pItem;
        }
      }
      if( pMatch ){
        pExpr->iTable = pMatch->iCursor;
        assert( ExprUseYTab(pExpr) );
        pExpr->y.pTab = pMatch->pTab;
        /* RIGHT JOIN not (yet) supported */
        assert( (pMatch->fg.jointype & JT_RIGHT)==0 );
        if( (pMatch->fg.jointype & JT_LEFT)!=0 ){
          ExprSetProperty(pExpr, EP_CanBeNull);
        }
        pSchema = pExpr->y.pTab->pSchema;
99692
99693
99694
99695
99696
99697
99698

99699
99700
99701
99702
99703
99704
99705
99706
99707
99708
99709
99710

99711
99712
99713
99714
99715
99716
99717
        }
        if( iCol<pTab->nCol ){
          cnt++;
          pMatch = 0;
#ifndef SQLITE_OMIT_UPSERT
          if( pExpr->iTable==EXCLUDED_TABLE_NUMBER ){
            testcase( iCol==(-1) );

            if( IN_RENAME_OBJECT ){
              pExpr->iColumn = iCol;
              pExpr->y.pTab = pTab;
              eNewExprOp = TK_COLUMN;
            }else{
              pExpr->iTable = pNC->uNC.pUpsert->regData +
                 sqlite3TableColumnToStorage(pTab, iCol);
              eNewExprOp = TK_REGISTER;
            }
          }else
#endif /* SQLITE_OMIT_UPSERT */
          {

            pExpr->y.pTab = pTab;
            if( pParse->bReturning ){
              eNewExprOp = TK_REGISTER;
              pExpr->iTable = pNC->uNC.iBaseReg + (pTab->nCol+1)*pExpr->iTable +
                 sqlite3TableColumnToStorage(pTab, iCol) + 1;
            }else{
              pExpr->iColumn = (i16)iCol;







>












>







100177
100178
100179
100180
100181
100182
100183
100184
100185
100186
100187
100188
100189
100190
100191
100192
100193
100194
100195
100196
100197
100198
100199
100200
100201
100202
100203
100204
        }
        if( iCol<pTab->nCol ){
          cnt++;
          pMatch = 0;
#ifndef SQLITE_OMIT_UPSERT
          if( pExpr->iTable==EXCLUDED_TABLE_NUMBER ){
            testcase( iCol==(-1) );
            assert( ExprUseYTab(pExpr) );
            if( IN_RENAME_OBJECT ){
              pExpr->iColumn = iCol;
              pExpr->y.pTab = pTab;
              eNewExprOp = TK_COLUMN;
            }else{
              pExpr->iTable = pNC->uNC.pUpsert->regData +
                 sqlite3TableColumnToStorage(pTab, iCol);
              eNewExprOp = TK_REGISTER;
            }
          }else
#endif /* SQLITE_OMIT_UPSERT */
          {
            assert( ExprUseYTab(pExpr) );
            pExpr->y.pTab = pTab;
            if( pParse->bReturning ){
              eNewExprOp = TK_REGISTER;
              pExpr->iTable = pNC->uNC.iBaseReg + (pTab->nCol+1)*pExpr->iTable +
                 sqlite3TableColumnToStorage(pTab, iCol) + 1;
            }else{
              pExpr->iColumn = (i16)iCol;
99778
99779
99780
99781
99782
99783
99784
99785
99786
99787
99788
99789
99790
99791
99792
99793
      for(j=0; j<pEList->nExpr; j++){
        char *zAs = pEList->a[j].zEName;
        if( pEList->a[j].eEName==ENAME_NAME
         && sqlite3_stricmp(zAs, zCol)==0
        ){
          Expr *pOrig;
          assert( pExpr->pLeft==0 && pExpr->pRight==0 );
          assert( pExpr->x.pList==0 );
          assert( pExpr->x.pSelect==0 );
          pOrig = pEList->a[j].pExpr;
          if( (pNC->ncFlags&NC_AllowAgg)==0 && ExprHasProperty(pOrig, EP_Agg) ){
            sqlite3ErrorMsg(pParse, "misuse of aliased aggregate %s", zAs);
            return WRC_Abort;
          }
          if( ExprHasProperty(pOrig, EP_Win)
           && ((pNC->ncFlags&NC_AllowWin)==0 || pNC!=pTopNC )







|
|







100265
100266
100267
100268
100269
100270
100271
100272
100273
100274
100275
100276
100277
100278
100279
100280
      for(j=0; j<pEList->nExpr; j++){
        char *zAs = pEList->a[j].zEName;
        if( pEList->a[j].eEName==ENAME_NAME
         && sqlite3_stricmp(zAs, zCol)==0
        ){
          Expr *pOrig;
          assert( pExpr->pLeft==0 && pExpr->pRight==0 );
          assert( ExprUseXList(pExpr)==0 || pExpr->x.pList==0 );
          assert( ExprUseXSelect(pExpr)==0 || pExpr->x.pSelect==0 );
          pOrig = pEList->a[j].pExpr;
          if( (pNC->ncFlags&NC_AllowAgg)==0 && ExprHasProperty(pOrig, EP_Agg) ){
            sqlite3ErrorMsg(pParse, "misuse of aliased aggregate %s", zAs);
            return WRC_Abort;
          }
          if( ExprHasProperty(pOrig, EP_Win)
           && ((pNC->ncFlags&NC_AllowWin)==0 || pNC!=pTopNC )
99851
99852
99853
99854
99855
99856
99857
99858
99859
99860
99861
99862
99863
99864
99865
      */
      sqlite3_log(SQLITE_WARNING,
        "double-quoted string literal: \"%w\"", zCol);
#ifdef SQLITE_ENABLE_NORMALIZE
      sqlite3VdbeAddDblquoteStr(db, pParse->pVdbe, zCol);
#endif
      pExpr->op = TK_STRING;
      pExpr->y.pTab = 0;
      return WRC_Prune;
    }
    if( sqlite3ExprIdToTrueFalse(pExpr) ){
      return WRC_Prune;
    }
  }








|







100338
100339
100340
100341
100342
100343
100344
100345
100346
100347
100348
100349
100350
100351
100352
      */
      sqlite3_log(SQLITE_WARNING,
        "double-quoted string literal: \"%w\"", zCol);
#ifdef SQLITE_ENABLE_NORMALIZE
      sqlite3VdbeAddDblquoteStr(db, pParse->pVdbe, zCol);
#endif
      pExpr->op = TK_STRING;
      memset(&pExpr->y, 0, sizeof(pExpr->y));
      return WRC_Prune;
    }
    if( sqlite3ExprIdToTrueFalse(pExpr) ){
      return WRC_Prune;
    }
  }

99937
99938
99939
99940
99941
99942
99943


99944
99945
99946
99947
99948
99949
99950
99951
** Allocate and return a pointer to an expression to load the column iCol
** from datasource iSrc in SrcList pSrc.
*/
SQLITE_PRIVATE Expr *sqlite3CreateColumnExpr(sqlite3 *db, SrcList *pSrc, int iSrc, int iCol){
  Expr *p = sqlite3ExprAlloc(db, TK_COLUMN, 0, 0);
  if( p ){
    SrcItem *pItem = &pSrc->a[iSrc];


    Table *pTab = p->y.pTab = pItem->pTab;
    p->iTable = pItem->iCursor;
    if( p->y.pTab->iPKey==iCol ){
      p->iColumn = -1;
    }else{
      p->iColumn = (ynVar)iCol;
      if( (pTab->tabFlags & TF_HasGenerated)!=0
       && (pTab->aCol[iCol].colFlags & COLFLAG_GENERATED)!=0







>
>
|







100424
100425
100426
100427
100428
100429
100430
100431
100432
100433
100434
100435
100436
100437
100438
100439
100440
** Allocate and return a pointer to an expression to load the column iCol
** from datasource iSrc in SrcList pSrc.
*/
SQLITE_PRIVATE Expr *sqlite3CreateColumnExpr(sqlite3 *db, SrcList *pSrc, int iSrc, int iCol){
  Expr *p = sqlite3ExprAlloc(db, TK_COLUMN, 0, 0);
  if( p ){
    SrcItem *pItem = &pSrc->a[iSrc];
    Table *pTab;
    assert( ExprUseYTab(p) );
    pTab = p->y.pTab = pItem->pTab;
    p->iTable = pItem->iCursor;
    if( p->y.pTab->iPKey==iCol ){
      p->iColumn = -1;
    }else{
      p->iColumn = (ynVar)iCol;
      if( (pTab->tabFlags & TF_HasGenerated)!=0
       && (pTab->aCol[iCol].colFlags & COLFLAG_GENERATED)!=0
100004
100005
100006
100007
100008
100009
100010

100011
100012
100013
100014
100015
100016
100017
** Expression p should encode a floating point value between 1.0 and 0.0.
** Return 1024 times this value.  Or return -1 if p is not a floating point
** value between 1.0 and 0.0.
*/
static int exprProbability(Expr *p){
  double r = -1.0;
  if( p->op!=TK_FLOAT ) return -1;

  sqlite3AtoF(p->u.zToken, &r, sqlite3Strlen30(p->u.zToken), SQLITE_UTF8);
  assert( r>=0.0 );
  if( r>1.0 ) return -1;
  return (int)(r*134217728.0);
}

/*







>







100493
100494
100495
100496
100497
100498
100499
100500
100501
100502
100503
100504
100505
100506
100507
** Expression p should encode a floating point value between 1.0 and 0.0.
** Return 1024 times this value.  Or return -1 if p is not a floating point
** value between 1.0 and 0.0.
*/
static int exprProbability(Expr *p){
  double r = -1.0;
  if( p->op!=TK_FLOAT ) return -1;
  assert( !ExprHasProperty(p, EP_IntValue) );
  sqlite3AtoF(p->u.zToken, &r, sqlite3Strlen30(p->u.zToken), SQLITE_UTF8);
  assert( r>=0.0 );
  if( r>1.0 ) return -1;
  return (int)(r*134217728.0);
}

/*
100052
100053
100054
100055
100056
100057
100058

100059
100060
100061
100062
100063
100064
100065
    */
    case TK_ROW: {
      SrcList *pSrcList = pNC->pSrcList;
      SrcItem *pItem;
      assert( pSrcList && pSrcList->nSrc>=1 );
      pItem = pSrcList->a;
      pExpr->op = TK_COLUMN;

      pExpr->y.pTab = pItem->pTab;
      pExpr->iTable = pItem->iCursor;
      pExpr->iColumn--;
      pExpr->affExpr = SQLITE_AFF_INTEGER;
      break;
    }








>







100542
100543
100544
100545
100546
100547
100548
100549
100550
100551
100552
100553
100554
100555
100556
    */
    case TK_ROW: {
      SrcList *pSrcList = pNC->pSrcList;
      SrcItem *pItem;
      assert( pSrcList && pSrcList->nSrc>=1 );
      pItem = pSrcList->a;
      pExpr->op = TK_COLUMN;
      assert( ExprUseYTab(pExpr) );
      pExpr->y.pTab = pItem->pTab;
      pExpr->iTable = pItem->iCursor;
      pExpr->iColumn--;
      pExpr->affExpr = SQLITE_AFF_INTEGER;
      break;
    }

100084
100085
100086
100087
100088
100089
100090

100091
100092
100093
100094
100095
100096
100097
      int i;
      for(i=0, p=pNC; p && i<ArraySize(anRef); p=p->pNext, i++){
        anRef[i] = p->nRef;
      }
      sqlite3WalkExpr(pWalker, pExpr->pLeft);
      if( 0==sqlite3ExprCanBeNull(pExpr->pLeft) && !IN_RENAME_OBJECT ){
        testcase( ExprHasProperty(pExpr, EP_FromJoin) );

        if( pExpr->op==TK_NOTNULL ){
          pExpr->u.zToken = "true";
          ExprSetProperty(pExpr, EP_IsTrue);
        }else{
          pExpr->u.zToken = "false";
          ExprSetProperty(pExpr, EP_IsFalse);
        }







>







100575
100576
100577
100578
100579
100580
100581
100582
100583
100584
100585
100586
100587
100588
100589
      int i;
      for(i=0, p=pNC; p && i<ArraySize(anRef); p=p->pNext, i++){
        anRef[i] = p->nRef;
      }
      sqlite3WalkExpr(pWalker, pExpr->pLeft);
      if( 0==sqlite3ExprCanBeNull(pExpr->pLeft) && !IN_RENAME_OBJECT ){
        testcase( ExprHasProperty(pExpr, EP_FromJoin) );
        assert( !ExprHasProperty(pExpr, EP_IntValue) );
        if( pExpr->op==TK_NOTNULL ){
          pExpr->u.zToken = "true";
          ExprSetProperty(pExpr, EP_IsTrue);
        }else{
          pExpr->u.zToken = "false";
          ExprSetProperty(pExpr, EP_IsFalse);
        }
100119
100120
100121
100122
100123
100124
100125

100126
100127
100128
100129
100130
100131
100132
100133
100134
100135
100136
100137

100138
100139
100140
100141

100142
100143

100144
100145
100146
100147
100148
100149
100150
      const char *zTable;
      const char *zDb;
      Expr *pRight;

      if( pExpr->op==TK_ID ){
        zDb = 0;
        zTable = 0;

        zColumn = pExpr->u.zToken;
      }else{
        Expr *pLeft = pExpr->pLeft;
        testcase( pNC->ncFlags & NC_IdxExpr );
        testcase( pNC->ncFlags & NC_GenCol );
        sqlite3ResolveNotValid(pParse, pNC, "the \".\" operator",
                               NC_IdxExpr|NC_GenCol, 0);
        pRight = pExpr->pRight;
        if( pRight->op==TK_ID ){
          zDb = 0;
        }else{
          assert( pRight->op==TK_DOT );

          zDb = pLeft->u.zToken;
          pLeft = pRight->pLeft;
          pRight = pRight->pRight;
        }

        zTable = pLeft->u.zToken;
        zColumn = pRight->u.zToken;

        if( IN_RENAME_OBJECT ){
          sqlite3RenameTokenRemap(pParse, (void*)pExpr, (void*)pRight);
          sqlite3RenameTokenRemap(pParse, (void*)&pExpr->y.pTab, (void*)pLeft);
        }
      }
      return lookupName(pParse, zDb, zTable, zColumn, pNC, pExpr);
    }







>












>




>


>







100611
100612
100613
100614
100615
100616
100617
100618
100619
100620
100621
100622
100623
100624
100625
100626
100627
100628
100629
100630
100631
100632
100633
100634
100635
100636
100637
100638
100639
100640
100641
100642
100643
100644
100645
100646
      const char *zTable;
      const char *zDb;
      Expr *pRight;

      if( pExpr->op==TK_ID ){
        zDb = 0;
        zTable = 0;
        assert( !ExprHasProperty(pExpr, EP_IntValue) );
        zColumn = pExpr->u.zToken;
      }else{
        Expr *pLeft = pExpr->pLeft;
        testcase( pNC->ncFlags & NC_IdxExpr );
        testcase( pNC->ncFlags & NC_GenCol );
        sqlite3ResolveNotValid(pParse, pNC, "the \".\" operator",
                               NC_IdxExpr|NC_GenCol, 0);
        pRight = pExpr->pRight;
        if( pRight->op==TK_ID ){
          zDb = 0;
        }else{
          assert( pRight->op==TK_DOT );
          assert( !ExprHasProperty(pRight, EP_IntValue) );
          zDb = pLeft->u.zToken;
          pLeft = pRight->pLeft;
          pRight = pRight->pRight;
        }
        assert( ExprUseUToken(pLeft) && ExprUseUToken(pRight) );
        zTable = pLeft->u.zToken;
        zColumn = pRight->u.zToken;
        assert( ExprUseYTab(pExpr) );
        if( IN_RENAME_OBJECT ){
          sqlite3RenameTokenRemap(pParse, (void*)pExpr, (void*)pRight);
          sqlite3RenameTokenRemap(pParse, (void*)&pExpr->y.pTab, (void*)pLeft);
        }
      }
      return lookupName(pParse, zDb, zTable, zColumn, pNC, pExpr);
    }
100161
100162
100163
100164
100165
100166
100167
100168
100169
100170
100171
100172
100173
100174
100175
      const char *zId;            /* The function name. */
      FuncDef *pDef;              /* Information about the function */
      u8 enc = ENC(pParse->db);   /* The database encoding */
      int savedAllowFlags = (pNC->ncFlags & (NC_AllowAgg | NC_AllowWin));
#ifndef SQLITE_OMIT_WINDOWFUNC
      Window *pWin = (IsWindowFunc(pExpr) ? pExpr->y.pWin : 0);
#endif
      assert( !ExprHasProperty(pExpr, EP_xIsSelect) );
      zId = pExpr->u.zToken;
      nId = sqlite3Strlen30(zId);
      pDef = sqlite3FindFunction(pParse->db, zId, n, enc, 0);
      if( pDef==0 ){
        pDef = sqlite3FindFunction(pParse->db, zId, -2, enc, 0);
        if( pDef==0 ){
          no_such_func = 1;







|







100657
100658
100659
100660
100661
100662
100663
100664
100665
100666
100667
100668
100669
100670
100671
      const char *zId;            /* The function name. */
      FuncDef *pDef;              /* Information about the function */
      u8 enc = ENC(pParse->db);   /* The database encoding */
      int savedAllowFlags = (pNC->ncFlags & (NC_AllowAgg | NC_AllowWin));
#ifndef SQLITE_OMIT_WINDOWFUNC
      Window *pWin = (IsWindowFunc(pExpr) ? pExpr->y.pWin : 0);
#endif
      assert( !ExprHasProperty(pExpr, EP_xIsSelect|EP_IntValue) );
      zId = pExpr->u.zToken;
      nId = sqlite3Strlen30(zId);
      pDef = sqlite3FindFunction(pParse->db, zId, n, enc, 0);
      if( pDef==0 ){
        pDef = sqlite3FindFunction(pParse->db, zId, -2, enc, 0);
        if( pDef==0 ){
          no_such_func = 1;
100325
100326
100327
100328
100329
100330
100331
100332
100333
100334
100335
100336
100337
100338
100339
100340
100341
100342
100343
100344
100345
100346
100347
100348
100349
100350
100351
100352

100353


100354
100355
100356
100357
100358
100359
100360
      }
#endif
      sqlite3WalkExprList(pWalker, pList);
      if( is_agg ){
#ifndef SQLITE_OMIT_WINDOWFUNC
        if( pWin ){
          Select *pSel = pNC->pWinSelect;
          assert( pWin==pExpr->y.pWin );
          if( IN_RENAME_OBJECT==0 ){
            sqlite3WindowUpdate(pParse, pSel ? pSel->pWinDefn : 0, pWin, pDef);
            if( pParse->db->mallocFailed ) break;
          }
          sqlite3WalkExprList(pWalker, pWin->pPartition);
          sqlite3WalkExprList(pWalker, pWin->pOrderBy);
          sqlite3WalkExpr(pWalker, pWin->pFilter);
          sqlite3WindowLink(pSel, pWin);
          pNC->ncFlags |= NC_HasWin;
        }else
#endif /* SQLITE_OMIT_WINDOWFUNC */
        {
          NameContext *pNC2 = pNC;
          pExpr->op = TK_AGG_FUNCTION;
          pExpr->op2 = 0;
#ifndef SQLITE_OMIT_WINDOWFUNC
          if( ExprHasProperty(pExpr, EP_WinFunc) ){
            sqlite3WalkExpr(pWalker, pExpr->y.pWin->pFilter);
          }
#endif

          while( pNC2 && !sqlite3FunctionUsesThisSrc(pExpr, pNC2->pSrcList) ){


            pExpr->op2++;
            pNC2 = pNC2->pNext;
          }
          assert( pDef!=0 || IN_RENAME_OBJECT );
          if( pNC2 && pDef ){
            assert( SQLITE_FUNC_MINMAX==NC_MinMaxAgg );
            assert( SQLITE_FUNC_ANYORDER==NC_OrderAgg );







|












|







>
|
>
>







100821
100822
100823
100824
100825
100826
100827
100828
100829
100830
100831
100832
100833
100834
100835
100836
100837
100838
100839
100840
100841
100842
100843
100844
100845
100846
100847
100848
100849
100850
100851
100852
100853
100854
100855
100856
100857
100858
100859
      }
#endif
      sqlite3WalkExprList(pWalker, pList);
      if( is_agg ){
#ifndef SQLITE_OMIT_WINDOWFUNC
        if( pWin ){
          Select *pSel = pNC->pWinSelect;
          assert( pWin==0 || (ExprUseYWin(pExpr) && pWin==pExpr->y.pWin) );
          if( IN_RENAME_OBJECT==0 ){
            sqlite3WindowUpdate(pParse, pSel ? pSel->pWinDefn : 0, pWin, pDef);
            if( pParse->db->mallocFailed ) break;
          }
          sqlite3WalkExprList(pWalker, pWin->pPartition);
          sqlite3WalkExprList(pWalker, pWin->pOrderBy);
          sqlite3WalkExpr(pWalker, pWin->pFilter);
          sqlite3WindowLink(pSel, pWin);
          pNC->ncFlags |= NC_HasWin;
        }else
#endif /* SQLITE_OMIT_WINDOWFUNC */
        {
          NameContext *pNC2;          /* For looping up thru outer contexts */
          pExpr->op = TK_AGG_FUNCTION;
          pExpr->op2 = 0;
#ifndef SQLITE_OMIT_WINDOWFUNC
          if( ExprHasProperty(pExpr, EP_WinFunc) ){
            sqlite3WalkExpr(pWalker, pExpr->y.pWin->pFilter);
          }
#endif
          pNC2 = pNC;
          while( pNC2
              && sqlite3ReferencesSrcList(pParse, pExpr, pNC2->pSrcList)==0
          ){
            pExpr->op2++;
            pNC2 = pNC2->pNext;
          }
          assert( pDef!=0 || IN_RENAME_OBJECT );
          if( pNC2 && pDef ){
            assert( SQLITE_FUNC_MINMAX==NC_MinMaxAgg );
            assert( SQLITE_FUNC_ANYORDER==NC_OrderAgg );
100374
100375
100376
100377
100378
100379
100380
100381
100382
100383
100384
100385
100386
100387
100388
    }
#ifndef SQLITE_OMIT_SUBQUERY
    case TK_SELECT:
    case TK_EXISTS:  testcase( pExpr->op==TK_EXISTS );
#endif
    case TK_IN: {
      testcase( pExpr->op==TK_IN );
      if( ExprHasProperty(pExpr, EP_xIsSelect) ){
        int nRef = pNC->nRef;
        testcase( pNC->ncFlags & NC_IsCheck );
        testcase( pNC->ncFlags & NC_PartIdx );
        testcase( pNC->ncFlags & NC_IdxExpr );
        testcase( pNC->ncFlags & NC_GenCol );
        if( pNC->ncFlags & NC_SelfRef ){
          notValidImpl(pParse, pNC, "subqueries", pExpr);







|







100873
100874
100875
100876
100877
100878
100879
100880
100881
100882
100883
100884
100885
100886
100887
    }
#ifndef SQLITE_OMIT_SUBQUERY
    case TK_SELECT:
    case TK_EXISTS:  testcase( pExpr->op==TK_EXISTS );
#endif
    case TK_IN: {
      testcase( pExpr->op==TK_IN );
      if( ExprUseXSelect(pExpr) ){
        int nRef = pNC->nRef;
        testcase( pNC->ncFlags & NC_IsCheck );
        testcase( pNC->ncFlags & NC_PartIdx );
        testcase( pNC->ncFlags & NC_IdxExpr );
        testcase( pNC->ncFlags & NC_GenCol );
        if( pNC->ncFlags & NC_SelfRef ){
          notValidImpl(pParse, pNC, "subqueries", pExpr);
100431
100432
100433
100434
100435
100436
100437

100438
100439
100440
100441
100442
100443
100444
    case TK_GT:
    case TK_GE: {
      int nLeft, nRight;
      if( pParse->db->mallocFailed ) break;
      assert( pExpr->pLeft!=0 );
      nLeft = sqlite3ExprVectorSize(pExpr->pLeft);
      if( pExpr->op==TK_BETWEEN ){

        nRight = sqlite3ExprVectorSize(pExpr->x.pList->a[0].pExpr);
        if( nRight==nLeft ){
          nRight = sqlite3ExprVectorSize(pExpr->x.pList->a[1].pExpr);
        }
      }else{
        assert( pExpr->pRight!=0 );
        nRight = sqlite3ExprVectorSize(pExpr->pRight);







>







100930
100931
100932
100933
100934
100935
100936
100937
100938
100939
100940
100941
100942
100943
100944
    case TK_GT:
    case TK_GE: {
      int nLeft, nRight;
      if( pParse->db->mallocFailed ) break;
      assert( pExpr->pLeft!=0 );
      nLeft = sqlite3ExprVectorSize(pExpr->pLeft);
      if( pExpr->op==TK_BETWEEN ){
        assert( ExprUseXList(pExpr) );
        nRight = sqlite3ExprVectorSize(pExpr->x.pList->a[0].pExpr);
        if( nRight==nLeft ){
          nRight = sqlite3ExprVectorSize(pExpr->x.pList->a[1].pExpr);
        }
      }else{
        assert( pExpr->pRight!=0 );
        nRight = sqlite3ExprVectorSize(pExpr->pRight);
100479
100480
100481
100482
100483
100484
100485


100486
100487
100488
100489
100490
100491
100492
100493
  Expr *pE           /* Expression we are trying to match */
){
  int i;             /* Loop counter */

  UNUSED_PARAMETER(pParse);

  if( pE->op==TK_ID ){


    char *zCol = pE->u.zToken;
    for(i=0; i<pEList->nExpr; i++){
      if( pEList->a[i].eEName==ENAME_NAME
       && sqlite3_stricmp(pEList->a[i].zEName, zCol)==0
      ){
        return i+1;
      }
    }







>
>
|







100979
100980
100981
100982
100983
100984
100985
100986
100987
100988
100989
100990
100991
100992
100993
100994
100995
  Expr *pE           /* Expression we are trying to match */
){
  int i;             /* Loop counter */

  UNUSED_PARAMETER(pParse);

  if( pE->op==TK_ID ){
    const char *zCol;
    assert( !ExprHasProperty(pE, EP_IntValue) );
    zCol = pE->u.zToken;
    for(i=0; i<pEList->nExpr; i++){
      if( pEList->a[i].eEName==ENAME_NAME
       && sqlite3_stricmp(pEList->a[i].zEName, zCol)==0
      ){
        return i+1;
      }
    }
101313
101314
101315
101316
101317
101318
101319
101320
101321
101322
101323
101324
101325
101326
101327
101328
static void exprCodeBetween(Parse*,Expr*,int,void(*)(Parse*,Expr*,int,int),int);
static int exprCodeVector(Parse *pParse, Expr *p, int *piToFree);

/*
** Return the affinity character for a single column of a table.
*/
SQLITE_PRIVATE char sqlite3TableColumnAffinity(const Table *pTab, int iCol){
  assert( iCol<pTab->nCol );
  return iCol>=0 ? pTab->aCol[iCol].affinity : SQLITE_AFF_INTEGER;
}

/*
** Return the 'affinity' of the expression pExpr if any.
**
** If pExpr is a column, a reference to a column via an 'AS' alias,
** or a sub-select with a column as the return value, then the







|
|







101815
101816
101817
101818
101819
101820
101821
101822
101823
101824
101825
101826
101827
101828
101829
101830
static void exprCodeBetween(Parse*,Expr*,int,void(*)(Parse*,Expr*,int,int),int);
static int exprCodeVector(Parse *pParse, Expr *p, int *piToFree);

/*
** Return the affinity character for a single column of a table.
*/
SQLITE_PRIVATE char sqlite3TableColumnAffinity(const Table *pTab, int iCol){
  if( iCol<0 || NEVER(iCol>=pTab->nCol) ) return SQLITE_AFF_INTEGER;
  return pTab->aCol[iCol].affinity;
}

/*
** Return the 'affinity' of the expression pExpr if any.
**
** If pExpr is a column, a reference to a column via an 'AS' alias,
** or a sub-select with a column as the return value, then the
101344
101345
101346
101347
101348
101349
101350
101351


101352
101353

101354
101355
101356
101357
101358
101359
101360
101361
101362
101363
101364
101365
101366
101367
101368
101369
101370
101371
101372
101373
101374
101375

101376
101377
101378
101379
101380
101381
101382
         || pExpr->op==TK_IF_NULL_ROW
         || (pExpr->op==TK_REGISTER && pExpr->op2==TK_IF_NULL_ROW) );
    pExpr = pExpr->pLeft;
    assert( pExpr!=0 );
  }
  op = pExpr->op;
  if( op==TK_REGISTER ) op = pExpr->op2;
  if( (op==TK_COLUMN || op==TK_AGG_COLUMN) && pExpr->y.pTab ){


    return sqlite3TableColumnAffinity(pExpr->y.pTab, pExpr->iColumn);
  }

  if( op==TK_SELECT ){
    assert( pExpr->flags&EP_xIsSelect );
    assert( pExpr->x.pSelect!=0 );
    assert( pExpr->x.pSelect->pEList!=0 );
    assert( pExpr->x.pSelect->pEList->a[0].pExpr!=0 );
    return sqlite3ExprAffinity(pExpr->x.pSelect->pEList->a[0].pExpr);
  }
#ifndef SQLITE_OMIT_CAST
  if( op==TK_CAST ){
    assert( !ExprHasProperty(pExpr, EP_IntValue) );
    return sqlite3AffinityType(pExpr->u.zToken, 0);
  }
#endif
  if( op==TK_SELECT_COLUMN ){
    assert( pExpr->pLeft->flags&EP_xIsSelect );
    assert( pExpr->iColumn < pExpr->iTable );
    assert( pExpr->iTable==pExpr->pLeft->x.pSelect->pEList->nExpr );
    return sqlite3ExprAffinity(
        pExpr->pLeft->x.pSelect->pEList->a[pExpr->iColumn].pExpr
    );
  }
  if( op==TK_VECTOR ){

    return sqlite3ExprAffinity(pExpr->x.pList->a[0].pExpr);
  }
  return pExpr->affExpr;
}

/*
** Set the collating sequence for expression pExpr to be the collating







|
>
>
|
|
>

|












|







>







101846
101847
101848
101849
101850
101851
101852
101853
101854
101855
101856
101857
101858
101859
101860
101861
101862
101863
101864
101865
101866
101867
101868
101869
101870
101871
101872
101873
101874
101875
101876
101877
101878
101879
101880
101881
101882
101883
101884
101885
101886
101887
101888
         || pExpr->op==TK_IF_NULL_ROW
         || (pExpr->op==TK_REGISTER && pExpr->op2==TK_IF_NULL_ROW) );
    pExpr = pExpr->pLeft;
    assert( pExpr!=0 );
  }
  op = pExpr->op;
  if( op==TK_REGISTER ) op = pExpr->op2;
  if( op==TK_COLUMN || op==TK_AGG_COLUMN ){
    assert( ExprUseYTab(pExpr) );
    if( pExpr->y.pTab ){
      return sqlite3TableColumnAffinity(pExpr->y.pTab, pExpr->iColumn);
    }
  }
  if( op==TK_SELECT ){
    assert( ExprUseXSelect(pExpr) );
    assert( pExpr->x.pSelect!=0 );
    assert( pExpr->x.pSelect->pEList!=0 );
    assert( pExpr->x.pSelect->pEList->a[0].pExpr!=0 );
    return sqlite3ExprAffinity(pExpr->x.pSelect->pEList->a[0].pExpr);
  }
#ifndef SQLITE_OMIT_CAST
  if( op==TK_CAST ){
    assert( !ExprHasProperty(pExpr, EP_IntValue) );
    return sqlite3AffinityType(pExpr->u.zToken, 0);
  }
#endif
  if( op==TK_SELECT_COLUMN ){
    assert( pExpr->pLeft!=0 && ExprUseXSelect(pExpr->pLeft) );
    assert( pExpr->iColumn < pExpr->iTable );
    assert( pExpr->iTable==pExpr->pLeft->x.pSelect->pEList->nExpr );
    return sqlite3ExprAffinity(
        pExpr->pLeft->x.pSelect->pEList->a[pExpr->iColumn].pExpr
    );
  }
  if( op==TK_VECTOR ){
    assert( ExprUseXList(pExpr) );
    return sqlite3ExprAffinity(pExpr->x.pList->a[0].pExpr);
  }
  return pExpr->affExpr;
}

/*
** Set the collating sequence for expression pExpr to be the collating
101428
101429
101430
101431
101432
101433
101434
101435
101436
101437
101438
101439
101440
101441
101442
** Skip over any TK_COLLATE operators and/or any unlikely()
** or likelihood() or likely() functions at the root of an
** expression.
*/
SQLITE_PRIVATE Expr *sqlite3ExprSkipCollateAndLikely(Expr *pExpr){
  while( pExpr && ExprHasProperty(pExpr, EP_Skip|EP_Unlikely) ){
    if( ExprHasProperty(pExpr, EP_Unlikely) ){
      assert( !ExprHasProperty(pExpr, EP_xIsSelect) );
      assert( pExpr->x.pList->nExpr>0 );
      assert( pExpr->op==TK_FUNCTION );
      pExpr = pExpr->x.pList->a[0].pExpr;
    }else{
      assert( pExpr->op==TK_COLLATE );
      pExpr = pExpr->pLeft;
    }







|







101934
101935
101936
101937
101938
101939
101940
101941
101942
101943
101944
101945
101946
101947
101948
** Skip over any TK_COLLATE operators and/or any unlikely()
** or likelihood() or likely() functions at the root of an
** expression.
*/
SQLITE_PRIVATE Expr *sqlite3ExprSkipCollateAndLikely(Expr *pExpr){
  while( pExpr && ExprHasProperty(pExpr, EP_Skip|EP_Unlikely) ){
    if( ExprHasProperty(pExpr, EP_Unlikely) ){
      assert( ExprUseXList(pExpr) );
      assert( pExpr->x.pList->nExpr>0 );
      assert( pExpr->op==TK_FUNCTION );
      pExpr = pExpr->x.pList->a[0].pExpr;
    }else{
      assert( pExpr->op==TK_COLLATE );
      pExpr = pExpr->pLeft;
    }
101461
101462
101463
101464
101465
101466
101467
101468

101469
101470
101471
101472
101473
101474
101475
101476
101477
101478

101479
101480
101481
101482
101483
101484

101485
101486
101487
101488

101489
101490
101491
101492
101493
101494
101495
101496
101497

101498
101499
101500
101501
101502
101503
101504
101505
101506
101507
101508
101509
SQLITE_PRIVATE CollSeq *sqlite3ExprCollSeq(Parse *pParse, const Expr *pExpr){
  sqlite3 *db = pParse->db;
  CollSeq *pColl = 0;
  const Expr *p = pExpr;
  while( p ){
    int op = p->op;
    if( op==TK_REGISTER ) op = p->op2;
    if( (op==TK_AGG_COLUMN || op==TK_COLUMN || op==TK_TRIGGER)

     && p->y.pTab!=0
    ){
      /* op==TK_REGISTER && p->y.pTab!=0 happens when pExpr was originally
      ** a TK_COLUMN but was previously evaluated and cached in a register */
      int j = p->iColumn;
      if( j>=0 ){
        const char *zColl = sqlite3ColumnColl(&p->y.pTab->aCol[j]);
        pColl = sqlite3FindCollSeq(db, ENC(db), zColl, 0);
      }
      break;

    }
    if( op==TK_CAST || op==TK_UPLUS ){
      p = p->pLeft;
      continue;
    }
    if( op==TK_VECTOR ){

      p = p->x.pList->a[0].pExpr;
      continue;
    }
    if( op==TK_COLLATE ){

      pColl = sqlite3GetCollSeq(pParse, ENC(db), 0, p->u.zToken);
      break;
    }
    if( p->flags & EP_Collate ){
      if( p->pLeft && (p->pLeft->flags & EP_Collate)!=0 ){
        p = p->pLeft;
      }else{
        Expr *pNext  = p->pRight;
        /* The Expr.x union is never used at the same time as Expr.pRight */

        assert( p->x.pList==0 || p->pRight==0 );
        if( p->x.pList!=0
         && !db->mallocFailed
         && ALWAYS(!ExprHasProperty(p, EP_xIsSelect))
        ){
          int i;
          for(i=0; ALWAYS(i<p->x.pList->nExpr); i++){
            if( ExprHasProperty(p->x.pList->a[i].pExpr, EP_Collate) ){
              pNext = p->x.pList->a[i].pExpr;
              break;
            }
          }







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






>




>









>

|
<
<
<







101967
101968
101969
101970
101971
101972
101973
101974
101975
101976

101977
101978
101979
101980
101981
101982
101983
101984
101985
101986
101987
101988
101989
101990
101991
101992
101993
101994
101995
101996
101997
101998
101999
102000
102001
102002
102003
102004
102005
102006
102007
102008
102009



102010
102011
102012
102013
102014
102015
102016
SQLITE_PRIVATE CollSeq *sqlite3ExprCollSeq(Parse *pParse, const Expr *pExpr){
  sqlite3 *db = pParse->db;
  CollSeq *pColl = 0;
  const Expr *p = pExpr;
  while( p ){
    int op = p->op;
    if( op==TK_REGISTER ) op = p->op2;
    if( op==TK_AGG_COLUMN || op==TK_COLUMN || op==TK_TRIGGER ){
      assert( ExprUseYTab(p) );
      if( p->y.pTab!=0 ){

        /* op==TK_REGISTER && p->y.pTab!=0 happens when pExpr was originally
        ** a TK_COLUMN but was previously evaluated and cached in a register */
        int j = p->iColumn;
        if( j>=0 ){
          const char *zColl = sqlite3ColumnColl(&p->y.pTab->aCol[j]);
          pColl = sqlite3FindCollSeq(db, ENC(db), zColl, 0);
        }
        break;
      }
    }
    if( op==TK_CAST || op==TK_UPLUS ){
      p = p->pLeft;
      continue;
    }
    if( op==TK_VECTOR ){
      assert( ExprUseXList(p) );
      p = p->x.pList->a[0].pExpr;
      continue;
    }
    if( op==TK_COLLATE ){
      assert( !ExprHasProperty(p, EP_IntValue) );
      pColl = sqlite3GetCollSeq(pParse, ENC(db), 0, p->u.zToken);
      break;
    }
    if( p->flags & EP_Collate ){
      if( p->pLeft && (p->pLeft->flags & EP_Collate)!=0 ){
        p = p->pLeft;
      }else{
        Expr *pNext  = p->pRight;
        /* The Expr.x union is never used at the same time as Expr.pRight */
        assert( ExprUseXList(p) );
        assert( p->x.pList==0 || p->pRight==0 );
        if( p->x.pList!=0 && !db->mallocFailed ){



          int i;
          for(i=0; ALWAYS(i<p->x.pList->nExpr); i++){
            if( ExprHasProperty(p->x.pList->a[i].pExpr, EP_Collate) ){
              pNext = p->x.pList->a[i].pExpr;
              break;
            }
          }
101578
101579
101580
101581
101582
101583
101584
101585
101586
101587
101588
101589
101590
101591
101592
  assert( pExpr->op==TK_EQ || pExpr->op==TK_IN || pExpr->op==TK_LT ||
          pExpr->op==TK_GT || pExpr->op==TK_GE || pExpr->op==TK_LE ||
          pExpr->op==TK_NE || pExpr->op==TK_IS || pExpr->op==TK_ISNOT );
  assert( pExpr->pLeft );
  aff = sqlite3ExprAffinity(pExpr->pLeft);
  if( pExpr->pRight ){
    aff = sqlite3CompareAffinity(pExpr->pRight, aff);
  }else if( ExprHasProperty(pExpr, EP_xIsSelect) ){
    aff = sqlite3CompareAffinity(pExpr->x.pSelect->pEList->a[0].pExpr, aff);
  }else if( aff==0 ){
    aff = SQLITE_AFF_BLOB;
  }
  return aff;
}








|







102085
102086
102087
102088
102089
102090
102091
102092
102093
102094
102095
102096
102097
102098
102099
  assert( pExpr->op==TK_EQ || pExpr->op==TK_IN || pExpr->op==TK_LT ||
          pExpr->op==TK_GT || pExpr->op==TK_GE || pExpr->op==TK_LE ||
          pExpr->op==TK_NE || pExpr->op==TK_IS || pExpr->op==TK_ISNOT );
  assert( pExpr->pLeft );
  aff = sqlite3ExprAffinity(pExpr->pLeft);
  if( pExpr->pRight ){
    aff = sqlite3CompareAffinity(pExpr->pRight, aff);
  }else if( ExprUseXSelect(pExpr) ){
    aff = sqlite3CompareAffinity(pExpr->x.pSelect->pEList->a[0].pExpr, aff);
  }else if( aff==0 ){
    aff = SQLITE_AFF_BLOB;
  }
  return aff;
}

101718
101719
101720
101721
101722
101723
101724

101725
101726

101727
101728
101729
101730
101731
101732
101733
** is a sub-select, return the number of columns in the sub-select. For
** any other type of expression, return 1.
*/
SQLITE_PRIVATE int sqlite3ExprVectorSize(const Expr *pExpr){
  u8 op = pExpr->op;
  if( op==TK_REGISTER ) op = pExpr->op2;
  if( op==TK_VECTOR ){

    return pExpr->x.pList->nExpr;
  }else if( op==TK_SELECT ){

    return pExpr->x.pSelect->pEList->nExpr;
  }else{
    return 1;
  }
}

/*







>


>







102225
102226
102227
102228
102229
102230
102231
102232
102233
102234
102235
102236
102237
102238
102239
102240
102241
102242
** is a sub-select, return the number of columns in the sub-select. For
** any other type of expression, return 1.
*/
SQLITE_PRIVATE int sqlite3ExprVectorSize(const Expr *pExpr){
  u8 op = pExpr->op;
  if( op==TK_REGISTER ) op = pExpr->op2;
  if( op==TK_VECTOR ){
    assert( ExprUseXList(pExpr) );
    return pExpr->x.pList->nExpr;
  }else if( op==TK_SELECT ){
    assert( ExprUseXSelect(pExpr) );
    return pExpr->x.pSelect->pEList->nExpr;
  }else{
    return 1;
  }
}

/*
101746
101747
101748
101749
101750
101751
101752

101753
101754

101755
101756
101757
101758
101759
101760
101761
** been positioned.
*/
SQLITE_PRIVATE Expr *sqlite3VectorFieldSubexpr(Expr *pVector, int i){
  assert( i<sqlite3ExprVectorSize(pVector) || pVector->op==TK_ERROR );
  if( sqlite3ExprIsVector(pVector) ){
    assert( pVector->op2==0 || pVector->op==TK_REGISTER );
    if( pVector->op==TK_SELECT || pVector->op2==TK_SELECT ){

      return pVector->x.pSelect->pEList->a[i].pExpr;
    }else{

      return pVector->x.pList->a[i].pExpr;
    }
  }
  return pVector;
}

/*







>


>







102255
102256
102257
102258
102259
102260
102261
102262
102263
102264
102265
102266
102267
102268
102269
102270
102271
102272
** been positioned.
*/
SQLITE_PRIVATE Expr *sqlite3VectorFieldSubexpr(Expr *pVector, int i){
  assert( i<sqlite3ExprVectorSize(pVector) || pVector->op==TK_ERROR );
  if( sqlite3ExprIsVector(pVector) ){
    assert( pVector->op2==0 || pVector->op==TK_REGISTER );
    if( pVector->op==TK_SELECT || pVector->op2==TK_SELECT ){
      assert( ExprUseXSelect(pVector) );
      return pVector->x.pSelect->pEList->a[i].pExpr;
    }else{
      assert( ExprUseXList(pVector) );
      return pVector->x.pList->a[i].pExpr;
    }
  }
  return pVector;
}

/*
101783
101784
101785
101786
101787
101788
101789
101790
101791
101792
101793
101794
101795
101796
101797
  Parse *pParse,       /* Parsing context */
  Expr *pVector,       /* The vector.  List of expressions or a sub-SELECT */
  int iField,          /* Which column of the vector to return */
  int nField           /* Total number of columns in the vector */
){
  Expr *pRet;
  if( pVector->op==TK_SELECT ){
    assert( pVector->flags & EP_xIsSelect );
    /* The TK_SELECT_COLUMN Expr node:
    **
    ** pLeft:           pVector containing TK_SELECT.  Not deleted.
    ** pRight:          not used.  But recursively deleted.
    ** iColumn:         Index of a column in pVector
    ** iTable:          0 or the number of columns on the LHS of an assignment
    ** pLeft->iTable:   First in an array of register holding result, or 0







|







102294
102295
102296
102297
102298
102299
102300
102301
102302
102303
102304
102305
102306
102307
102308
  Parse *pParse,       /* Parsing context */
  Expr *pVector,       /* The vector.  List of expressions or a sub-SELECT */
  int iField,          /* Which column of the vector to return */
  int nField           /* Total number of columns in the vector */
){
  Expr *pRet;
  if( pVector->op==TK_SELECT ){
    assert( ExprUseXSelect(pVector) );
    /* The TK_SELECT_COLUMN Expr node:
    **
    ** pLeft:           pVector containing TK_SELECT.  Not deleted.
    ** pRight:          not used.  But recursively deleted.
    ** iColumn:         Index of a column in pVector
    ** iTable:          0 or the number of columns on the LHS of an assignment
    ** pLeft->iTable:   First in an array of register holding result, or 0
101808
101809
101810
101811
101812
101813
101814


101815
101816
101817
101818
101819
101820
101821
101822
    if( pRet ){
      pRet->iTable = nField;
      pRet->iColumn = iField;
      pRet->pLeft = pVector;
    }
  }else{
    if( pVector->op==TK_VECTOR ){


      Expr **ppVector = &pVector->x.pList->a[iField].pExpr;
      pVector = *ppVector;
      if( IN_RENAME_OBJECT ){
        /* This must be a vector UPDATE inside a trigger */
        *ppVector = 0;
        return pVector;
      }
    }







>
>
|







102319
102320
102321
102322
102323
102324
102325
102326
102327
102328
102329
102330
102331
102332
102333
102334
102335
    if( pRet ){
      pRet->iTable = nField;
      pRet->iColumn = iField;
      pRet->pLeft = pVector;
    }
  }else{
    if( pVector->op==TK_VECTOR ){
      Expr **ppVector;
      assert( ExprUseXList(pVector) );
      ppVector = &pVector->x.pList->a[iField].pExpr;
      pVector = *ppVector;
      if( IN_RENAME_OBJECT ){
        /* This must be a vector UPDATE inside a trigger */
        *ppVector = 0;
        return pVector;
      }
    }
101872
101873
101874
101875
101876
101877
101878

101879
101880
101881
101882

101883
101884
101885
101886
101887
101888
101889
  u8 op = pVector->op;
  assert( op==TK_VECTOR || op==TK_REGISTER || op==TK_SELECT || op==TK_ERROR );
  if( op==TK_REGISTER ){
    *ppExpr = sqlite3VectorFieldSubexpr(pVector, iField);
    return pVector->iTable+iField;
  }
  if( op==TK_SELECT ){

    *ppExpr = pVector->x.pSelect->pEList->a[iField].pExpr;
     return regSelect+iField;
  }
  if( op==TK_VECTOR ){

    *ppExpr = pVector->x.pList->a[iField].pExpr;
    return sqlite3ExprCodeTemp(pParse, *ppExpr, pRegFree);
  }
  return 0;
}

/*







>




>







102385
102386
102387
102388
102389
102390
102391
102392
102393
102394
102395
102396
102397
102398
102399
102400
102401
102402
102403
102404
  u8 op = pVector->op;
  assert( op==TK_VECTOR || op==TK_REGISTER || op==TK_SELECT || op==TK_ERROR );
  if( op==TK_REGISTER ){
    *ppExpr = sqlite3VectorFieldSubexpr(pVector, iField);
    return pVector->iTable+iField;
  }
  if( op==TK_SELECT ){
    assert( ExprUseXSelect(pVector) );
    *ppExpr = pVector->x.pSelect->pEList->a[iField].pExpr;
     return regSelect+iField;
  }
  if( op==TK_VECTOR ){
    assert( ExprUseXList(pVector) );
    *ppExpr = pVector->x.pList->a[iField].pExpr;
    return sqlite3ExprCodeTemp(pParse, *ppExpr, pRegFree);
  }
  return 0;
}

/*
102050
102051
102052
102053
102054
102055
102056
102057
102058
102059
102060
102061
102062
102063
102064
** Also propagate EP_Propagate flags up from Expr.x.pList to Expr.flags,
** if appropriate.
*/
static void exprSetHeight(Expr *p){
  int nHeight = 0;
  heightOfExpr(p->pLeft, &nHeight);
  heightOfExpr(p->pRight, &nHeight);
  if( ExprHasProperty(p, EP_xIsSelect) ){
    heightOfSelect(p->x.pSelect, &nHeight);
  }else if( p->x.pList ){
    heightOfExprList(p->x.pList, &nHeight);
    p->flags |= EP_Propagate & sqlite3ExprListFlags(p->x.pList);
  }
  p->nHeight = nHeight + 1;
}







|







102565
102566
102567
102568
102569
102570
102571
102572
102573
102574
102575
102576
102577
102578
102579
** Also propagate EP_Propagate flags up from Expr.x.pList to Expr.flags,
** if appropriate.
*/
static void exprSetHeight(Expr *p){
  int nHeight = 0;
  heightOfExpr(p->pLeft, &nHeight);
  heightOfExpr(p->pRight, &nHeight);
  if( ExprUseXSelect(p) ){
    heightOfSelect(p->x.pSelect, &nHeight);
  }else if( p->x.pList ){
    heightOfExprList(p->x.pList, &nHeight);
    p->flags |= EP_Propagate & sqlite3ExprListFlags(p->x.pList);
  }
  p->nHeight = nHeight + 1;
}
102089
102090
102091
102092
102093
102094
102095
102096
102097
102098
102099
102100
102101
102102
102103
#else /* ABOVE:  Height enforcement enabled.  BELOW: Height enforcement off */
/*
** Propagate all EP_Propagate flags from the Expr.x.pList into
** Expr.flags.
*/
SQLITE_PRIVATE void sqlite3ExprSetHeightAndFlags(Parse *pParse, Expr *p){
  if( pParse->nErr ) return;
  if( p && p->x.pList && !ExprHasProperty(p, EP_xIsSelect) ){
    p->flags |= EP_Propagate & sqlite3ExprListFlags(p->x.pList);
  }
}
#define exprSetHeight(y)
#endif /* SQLITE_MAX_EXPR_DEPTH>0 */

/*







|







102604
102605
102606
102607
102608
102609
102610
102611
102612
102613
102614
102615
102616
102617
102618
#else /* ABOVE:  Height enforcement enabled.  BELOW: Height enforcement off */
/*
** Propagate all EP_Propagate flags from the Expr.x.pList into
** Expr.flags.
*/
SQLITE_PRIVATE void sqlite3ExprSetHeightAndFlags(Parse *pParse, Expr *p){
  if( pParse->nErr ) return;
  if( p && ExprUseXList(p) && p->x.pList ){
    p->flags |= EP_Propagate & sqlite3ExprListFlags(p->x.pList);
  }
}
#define exprSetHeight(y)
#endif /* SQLITE_MAX_EXPR_DEPTH>0 */

/*
102273
102274
102275
102276
102277
102278
102279
102280






102281
102282
102283
102284
102285
102286

102287
102288
102289
102290
102291
102292
102293
SQLITE_PRIVATE Select *sqlite3ExprListToValues(Parse *pParse, int nElem, ExprList *pEList){
  int ii;
  Select *pRet = 0;
  assert( nElem>1 );
  for(ii=0; ii<pEList->nExpr; ii++){
    Select *pSel;
    Expr *pExpr = pEList->a[ii].pExpr;
    int nExprElem = (pExpr->op==TK_VECTOR ? pExpr->x.pList->nExpr : 1);






    if( nExprElem!=nElem ){
      sqlite3ErrorMsg(pParse, "IN(...) element has %d term%s - expected %d",
          nExprElem, nExprElem>1?"s":"", nElem
      );
      break;
    }

    pSel = sqlite3SelectNew(pParse, pExpr->x.pList, 0, 0, 0, 0, 0, SF_Values,0);
    pExpr->x.pList = 0;
    if( pSel ){
      if( pRet ){
        pSel->op = TK_ALL;
        pSel->pPrior = pRet;
      }







|
>
>
>
>
>
>






>







102788
102789
102790
102791
102792
102793
102794
102795
102796
102797
102798
102799
102800
102801
102802
102803
102804
102805
102806
102807
102808
102809
102810
102811
102812
102813
102814
102815
SQLITE_PRIVATE Select *sqlite3ExprListToValues(Parse *pParse, int nElem, ExprList *pEList){
  int ii;
  Select *pRet = 0;
  assert( nElem>1 );
  for(ii=0; ii<pEList->nExpr; ii++){
    Select *pSel;
    Expr *pExpr = pEList->a[ii].pExpr;
    int nExprElem;
    if( pExpr->op==TK_VECTOR ){
      assert( ExprUseXList(pExpr) );
      nExprElem = pExpr->x.pList->nExpr;
    }else{
      nExprElem = 1;
    }
    if( nExprElem!=nElem ){
      sqlite3ErrorMsg(pParse, "IN(...) element has %d term%s - expected %d",
          nExprElem, nExprElem>1?"s":"", nElem
      );
      break;
    }
    assert( ExprUseXList(pExpr) );
    pSel = sqlite3SelectNew(pParse, pExpr->x.pList, 0, 0, 0, 0, 0, SF_Values,0);
    pExpr->x.pList = 0;
    if( pSel ){
      if( pRet ){
        pSel->op = TK_ALL;
        pSel->pPrior = pRet;
      }
102349
102350
102351
102352
102353
102354
102355
102356
102357
102358
102359
102360
102361
102362
102363
   && pList->nExpr > pParse->db->aLimit[SQLITE_LIMIT_FUNCTION_ARG]
   && !pParse->nested
  ){
    sqlite3ErrorMsg(pParse, "too many arguments on function %T", pToken);
  }
  pNew->x.pList = pList;
  ExprSetProperty(pNew, EP_HasFunc);
  assert( !ExprHasProperty(pNew, EP_xIsSelect) );
  sqlite3ExprSetHeightAndFlags(pParse, pNew);
  if( eDistinct==SF_Distinct ) ExprSetProperty(pNew, EP_Distinct);
  return pNew;
}

/*
** Check to see if a function is usable according to current access







|







102871
102872
102873
102874
102875
102876
102877
102878
102879
102880
102881
102882
102883
102884
102885
   && pList->nExpr > pParse->db->aLimit[SQLITE_LIMIT_FUNCTION_ARG]
   && !pParse->nested
  ){
    sqlite3ErrorMsg(pParse, "too many arguments on function %T", pToken);
  }
  pNew->x.pList = pList;
  ExprSetProperty(pNew, EP_HasFunc);
  assert( ExprUseXList(pNew) );
  sqlite3ExprSetHeightAndFlags(pParse, pNew);
  if( eDistinct==SF_Distinct ) ExprSetProperty(pNew, EP_Distinct);
  return pNew;
}

/*
** Check to see if a function is usable according to current access
102475
102476
102477
102478
102479
102480
102481
102482
102483
102484
102485
102486
102487
102488
102489
102490
102491
102492

102493
102494
102495
102496
102497
102498
102499
102500
102501
102502
102503
102504
102505
102506
102507
102508
102509
102510
102511
102512
102513
102514



102515
102516
102517
102518
102519
102520
102521
}

/*
** Recursively delete an expression tree.
*/
static SQLITE_NOINLINE void sqlite3ExprDeleteNN(sqlite3 *db, Expr *p){
  assert( p!=0 );
  /* Sanity check: Assert that the IntValue is non-negative if it exists */
  assert( !ExprHasProperty(p, EP_IntValue) || p->u.iValue>=0 );

  assert( !ExprHasProperty(p, EP_WinFunc) || p->y.pWin!=0 || db->mallocFailed );
  assert( p->op!=TK_FUNCTION || ExprHasProperty(p, EP_TokenOnly|EP_Reduced)
          || p->y.pWin==0 || ExprHasProperty(p, EP_WinFunc) );
#ifdef SQLITE_DEBUG
  if( ExprHasProperty(p, EP_Leaf) && !ExprHasProperty(p, EP_TokenOnly) ){
    assert( p->pLeft==0 );
    assert( p->pRight==0 );
    assert( p->x.pSelect==0 );

  }
#endif
  if( !ExprHasProperty(p, (EP_TokenOnly|EP_Leaf)) ){
    /* The Expr.x union is never used at the same time as Expr.pRight */
    assert( p->x.pList==0 || p->pRight==0 );
    if( p->pLeft && p->op!=TK_SELECT_COLUMN ) sqlite3ExprDeleteNN(db, p->pLeft);
    if( p->pRight ){
      assert( !ExprHasProperty(p, EP_WinFunc) );
      sqlite3ExprDeleteNN(db, p->pRight);
    }else if( ExprHasProperty(p, EP_xIsSelect) ){
      assert( !ExprHasProperty(p, EP_WinFunc) );
      sqlite3SelectDelete(db, p->x.pSelect);
    }else{
      sqlite3ExprListDelete(db, p->x.pList);
#ifndef SQLITE_OMIT_WINDOWFUNC
      if( ExprHasProperty(p, EP_WinFunc) ){
        sqlite3WindowDelete(db, p->y.pWin);
      }
#endif
    }
  }
  if( ExprHasProperty(p, EP_MemToken) ) sqlite3DbFree(db, p->u.zToken);



  if( !ExprHasProperty(p, EP_Static) ){
    sqlite3DbFreeNN(db, p);
  }
}
SQLITE_PRIVATE void sqlite3ExprDelete(sqlite3 *db, Expr *p){
  if( p ) sqlite3ExprDeleteNN(db, p);
}







<
|
|
|
|
<




|
>




|




|











|
>
>
>







102997
102998
102999
103000
103001
103002
103003

103004
103005
103006
103007

103008
103009
103010
103011
103012
103013
103014
103015
103016
103017
103018
103019
103020
103021
103022
103023
103024
103025
103026
103027
103028
103029
103030
103031
103032
103033
103034
103035
103036
103037
103038
103039
103040
103041
103042
103043
103044
103045
}

/*
** Recursively delete an expression tree.
*/
static SQLITE_NOINLINE void sqlite3ExprDeleteNN(sqlite3 *db, Expr *p){
  assert( p!=0 );

  assert( !ExprUseUValue(p) || p->u.iValue>=0 );
  assert( !ExprUseYWin(p) || !ExprUseYSub(p) );
  assert( !ExprUseYWin(p) || p->y.pWin!=0 || db->mallocFailed );
  assert( p->op!=TK_FUNCTION || !ExprUseYSub(p) );

#ifdef SQLITE_DEBUG
  if( ExprHasProperty(p, EP_Leaf) && !ExprHasProperty(p, EP_TokenOnly) ){
    assert( p->pLeft==0 );
    assert( p->pRight==0 );
    assert( !ExprUseXSelect(p) || p->x.pSelect==0 );
    assert( !ExprUseXList(p) || p->x.pList==0 );
  }
#endif
  if( !ExprHasProperty(p, (EP_TokenOnly|EP_Leaf)) ){
    /* The Expr.x union is never used at the same time as Expr.pRight */
    assert( (ExprUseXList(p) && p->x.pList==0) || p->pRight==0 );
    if( p->pLeft && p->op!=TK_SELECT_COLUMN ) sqlite3ExprDeleteNN(db, p->pLeft);
    if( p->pRight ){
      assert( !ExprHasProperty(p, EP_WinFunc) );
      sqlite3ExprDeleteNN(db, p->pRight);
    }else if( ExprUseXSelect(p) ){
      assert( !ExprHasProperty(p, EP_WinFunc) );
      sqlite3SelectDelete(db, p->x.pSelect);
    }else{
      sqlite3ExprListDelete(db, p->x.pList);
#ifndef SQLITE_OMIT_WINDOWFUNC
      if( ExprHasProperty(p, EP_WinFunc) ){
        sqlite3WindowDelete(db, p->y.pWin);
      }
#endif
    }
  }
  if( ExprHasProperty(p, EP_MemToken) ){
    assert( !ExprHasProperty(p, EP_IntValue) );
    sqlite3DbFree(db, p->u.zToken);
  }
  if( !ExprHasProperty(p, EP_Static) ){
    sqlite3DbFreeNN(db, p);
  }
}
SQLITE_PRIVATE void sqlite3ExprDelete(sqlite3 *db, Expr *p){
  if( p ) sqlite3ExprDeleteNN(db, p);
}
102723
102724
102725
102726
102727
102728
102729
102730
102731
102732
102733
102734
102735
102736
102737
    if( nToken ){
      char *zToken = pNew->u.zToken = (char*)&zAlloc[nNewSize];
      memcpy(zToken, p->u.zToken, nToken);
    }

    if( 0==((p->flags|pNew->flags) & (EP_TokenOnly|EP_Leaf)) ){
      /* Fill in the pNew->x.pSelect or pNew->x.pList member. */
      if( ExprHasProperty(p, EP_xIsSelect) ){
        pNew->x.pSelect = sqlite3SelectDup(db, p->x.pSelect, dupFlags);
      }else{
        pNew->x.pList = sqlite3ExprListDup(db, p->x.pList, dupFlags);
      }
    }

    /* Fill in pNew->pLeft and pNew->pRight. */







|







103247
103248
103249
103250
103251
103252
103253
103254
103255
103256
103257
103258
103259
103260
103261
    if( nToken ){
      char *zToken = pNew->u.zToken = (char*)&zAlloc[nNewSize];
      memcpy(zToken, p->u.zToken, nToken);
    }

    if( 0==((p->flags|pNew->flags) & (EP_TokenOnly|EP_Leaf)) ){
      /* Fill in the pNew->x.pSelect or pNew->x.pList member. */
      if( ExprUseXSelect(p) ){
        pNew->x.pSelect = sqlite3SelectDup(db, p->x.pSelect, dupFlags);
      }else{
        pNew->x.pList = sqlite3ExprListDup(db, p->x.pList, dupFlags);
      }
    }

    /* Fill in pNew->pLeft and pNew->pRight. */
103017
103018
103019
103020
103021
103022
103023
103024
103025
103026
103027
103028
103029
103030
103031
    pp = &pNew->pPrior;
    pNext = pNew;
  }

  return pRet;
}
#else
SQLITE_PRIVATE Select *sqlite3SelectDup(sqlite3 *db, Select *p, int flags){
  assert( p==0 );
  return 0;
}
#endif


/*







|







103541
103542
103543
103544
103545
103546
103547
103548
103549
103550
103551
103552
103553
103554
103555
    pp = &pNew->pPrior;
    pNext = pNew;
  }

  return pRet;
}
#else
SQLITE_PRIVATE Select *sqlite3SelectDup(sqlite3 *db, const Select *p, int flags){
  assert( p==0 );
  return 0;
}
#endif


/*
103350
103351
103352
103353
103354
103355
103356
103357
103358
103359
103360
103361
103362
103363
103364
103365
103366
103367
103368
103369
103370
103371
103372
103373

103374
103375
103376
103377
103378
103379
103380
** If the input expression is an ID with the name "true" or "false"
** then convert it into an TK_TRUEFALSE term.  Return non-zero if
** the conversion happened, and zero if the expression is unaltered.
*/
SQLITE_PRIVATE int sqlite3ExprIdToTrueFalse(Expr *pExpr){
  u32 v;
  assert( pExpr->op==TK_ID || pExpr->op==TK_STRING );
  if( !ExprHasProperty(pExpr, EP_Quoted)
   && (v = sqlite3IsTrueOrFalse(pExpr->u.zToken))!=0
  ){
    pExpr->op = TK_TRUEFALSE;
    ExprSetProperty(pExpr, v);
    return 1;
  }
  return 0;
}

/*
** The argument must be a TK_TRUEFALSE Expr node.  Return 1 if it is TRUE
** and 0 if it is FALSE.
*/
SQLITE_PRIVATE int sqlite3ExprTruthValue(const Expr *pExpr){
  pExpr = sqlite3ExprSkipCollate((Expr*)pExpr);
  assert( pExpr->op==TK_TRUEFALSE );

  assert( sqlite3StrICmp(pExpr->u.zToken,"true")==0
       || sqlite3StrICmp(pExpr->u.zToken,"false")==0 );
  return pExpr->u.zToken[4]==0;
}

/*
** If pExpr is an AND or OR expression, try to simplify it by eliminating







|
















>







103874
103875
103876
103877
103878
103879
103880
103881
103882
103883
103884
103885
103886
103887
103888
103889
103890
103891
103892
103893
103894
103895
103896
103897
103898
103899
103900
103901
103902
103903
103904
103905
** If the input expression is an ID with the name "true" or "false"
** then convert it into an TK_TRUEFALSE term.  Return non-zero if
** the conversion happened, and zero if the expression is unaltered.
*/
SQLITE_PRIVATE int sqlite3ExprIdToTrueFalse(Expr *pExpr){
  u32 v;
  assert( pExpr->op==TK_ID || pExpr->op==TK_STRING );
  if( !ExprHasProperty(pExpr, EP_Quoted|EP_IntValue)
   && (v = sqlite3IsTrueOrFalse(pExpr->u.zToken))!=0
  ){
    pExpr->op = TK_TRUEFALSE;
    ExprSetProperty(pExpr, v);
    return 1;
  }
  return 0;
}

/*
** The argument must be a TK_TRUEFALSE Expr node.  Return 1 if it is TRUE
** and 0 if it is FALSE.
*/
SQLITE_PRIVATE int sqlite3ExprTruthValue(const Expr *pExpr){
  pExpr = sqlite3ExprSkipCollate((Expr*)pExpr);
  assert( pExpr->op==TK_TRUEFALSE );
  assert( !ExprHasProperty(pExpr, EP_IntValue) );
  assert( sqlite3StrICmp(pExpr->u.zToken,"true")==0
       || sqlite3StrICmp(pExpr->u.zToken,"false")==0 );
  return pExpr->u.zToken[4]==0;
}

/*
** If pExpr is an AND or OR expression, try to simplify it by eliminating
103571
103572
103573
103574
103575
103576
103577
103578
103579
103580
103581
103582
103583
103584
103585
      if( sqlite3IsBinary(pColl) ){
        return WRC_Prune;
      }
    }
  }

  /* Check if pExpr is a sub-select. If so, consider it variable. */
  if( ExprHasProperty(pExpr, EP_xIsSelect) ){
    pWalker->eCode = 0;
    return WRC_Abort;
  }

  return exprNodeIsConstant(pWalker, pExpr);
}








|







104096
104097
104098
104099
104100
104101
104102
104103
104104
104105
104106
104107
104108
104109
104110
      if( sqlite3IsBinary(pColl) ){
        return WRC_Prune;
      }
    }
  }

  /* Check if pExpr is a sub-select. If so, consider it variable. */
  if( ExprUseXSelect(pExpr) ){
    pWalker->eCode = 0;
    return WRC_Abort;
  }

  return exprNodeIsConstant(pWalker, pExpr);
}

103678
103679
103680
103681
103682
103683
103684
103685
103686
103687
103688
103689
103690
103691
103692
103693
103694
  }
  switch( p->op ){
    case TK_UPLUS: {
      rc = sqlite3ExprIsInteger(p->pLeft, pValue);
      break;
    }
    case TK_UMINUS: {
      int v;
      if( sqlite3ExprIsInteger(p->pLeft, &v) ){
        assert( v!=(-2147483647-1) );
        *pValue = -v;
        rc = 1;
      }
      break;
    }
    default: break;
  }







|

|







104203
104204
104205
104206
104207
104208
104209
104210
104211
104212
104213
104214
104215
104216
104217
104218
104219
  }
  switch( p->op ){
    case TK_UPLUS: {
      rc = sqlite3ExprIsInteger(p->pLeft, pValue);
      break;
    }
    case TK_UMINUS: {
      int v = 0;
      if( sqlite3ExprIsInteger(p->pLeft, &v) ){
        assert( ((unsigned int)v)!=0x80000000 );
        *pValue = -v;
        rc = 1;
      }
      break;
    }
    default: break;
  }
103721
103722
103723
103724
103725
103726
103727

103728
103729
103730
103731
103732
103733
103734
103735
103736
103737
103738
  switch( op ){
    case TK_INTEGER:
    case TK_STRING:
    case TK_FLOAT:
    case TK_BLOB:
      return 0;
    case TK_COLUMN:

      return ExprHasProperty(p, EP_CanBeNull) ||
             p->y.pTab==0 ||  /* Reference to column of index on expression */
             (p->iColumn>=0
              && ALWAYS(p->y.pTab->aCol!=0) /* Defense against OOM problems */
              && p->y.pTab->aCol[p->iColumn].notNull==0);
    default:
      return 1;
  }
}

/*







>



|







104246
104247
104248
104249
104250
104251
104252
104253
104254
104255
104256
104257
104258
104259
104260
104261
104262
104263
104264
  switch( op ){
    case TK_INTEGER:
    case TK_STRING:
    case TK_FLOAT:
    case TK_BLOB:
      return 0;
    case TK_COLUMN:
      assert( ExprUseYTab(p) );
      return ExprHasProperty(p, EP_CanBeNull) ||
             p->y.pTab==0 ||  /* Reference to column of index on expression */
             (p->iColumn>=0
              && p->y.pTab->aCol!=0 /* Possible due to prior error */
              && p->y.pTab->aCol[p->iColumn].notNull==0);
    default:
      return 1;
  }
}

/*
103798
103799
103800
103801
103802
103803
103804
103805
103806
103807
103808
103809
103810
103811
103812
#ifndef SQLITE_OMIT_SUBQUERY
static Select *isCandidateForInOpt(const Expr *pX){
  Select *p;
  SrcList *pSrc;
  ExprList *pEList;
  Table *pTab;
  int i;
  if( !ExprHasProperty(pX, EP_xIsSelect) ) return 0;  /* Not a subquery */
  if( ExprHasProperty(pX, EP_VarSelect)  ) return 0;  /* Correlated subq */
  p = pX->x.pSelect;
  if( p->pPrior ) return 0;              /* Not a compound SELECT */
  if( p->selFlags & (SF_Distinct|SF_Aggregate) ){
    testcase( (p->selFlags & (SF_Distinct|SF_Aggregate))==SF_Distinct );
    testcase( (p->selFlags & (SF_Distinct|SF_Aggregate))==SF_Aggregate );
    return 0; /* No DISTINCT keyword and no aggregate functions */







|







104324
104325
104326
104327
104328
104329
104330
104331
104332
104333
104334
104335
104336
104337
104338
#ifndef SQLITE_OMIT_SUBQUERY
static Select *isCandidateForInOpt(const Expr *pX){
  Select *p;
  SrcList *pSrc;
  ExprList *pEList;
  Table *pTab;
  int i;
  if( !ExprUseXSelect(pX) ) return 0;                 /* Not a subquery */
  if( ExprHasProperty(pX, EP_VarSelect)  ) return 0;  /* Correlated subq */
  p = pX->x.pSelect;
  if( p->pPrior ) return 0;              /* Not a compound SELECT */
  if( p->selFlags & (SF_Distinct|SF_Aggregate) ){
    testcase( (p->selFlags & (SF_Distinct|SF_Aggregate))==SF_Distinct );
    testcase( (p->selFlags & (SF_Distinct|SF_Aggregate))==SF_Aggregate );
    return 0; /* No DISTINCT keyword and no aggregate functions */
103969
103970
103971
103972
103973
103974
103975
103976
103977
103978
103979
103980
103981
103982
103983
  mustBeUnique = (inFlags & IN_INDEX_LOOP)!=0;

  /* If the RHS of this IN(...) operator is a SELECT, and if it matters
  ** whether or not the SELECT result contains NULL values, check whether
  ** or not NULL is actually possible (it may not be, for example, due
  ** to NOT NULL constraints in the schema). If no NULL values are possible,
  ** set prRhsHasNull to 0 before continuing.  */
  if( prRhsHasNull && (pX->flags & EP_xIsSelect) ){
    int i;
    ExprList *pEList = pX->x.pSelect->pEList;
    for(i=0; i<pEList->nExpr; i++){
      if( sqlite3ExprCanBeNull(pEList->a[i].pExpr) ) break;
    }
    if( i==pEList->nExpr ){
      prRhsHasNull = 0;







|







104495
104496
104497
104498
104499
104500
104501
104502
104503
104504
104505
104506
104507
104508
104509
  mustBeUnique = (inFlags & IN_INDEX_LOOP)!=0;

  /* If the RHS of this IN(...) operator is a SELECT, and if it matters
  ** whether or not the SELECT result contains NULL values, check whether
  ** or not NULL is actually possible (it may not be, for example, due
  ** to NOT NULL constraints in the schema). If no NULL values are possible,
  ** set prRhsHasNull to 0 before continuing.  */
  if( prRhsHasNull && ExprUseXSelect(pX) ){
    int i;
    ExprList *pEList = pX->x.pSelect->pEList;
    for(i=0; i<pEList->nExpr; i++){
      if( sqlite3ExprCanBeNull(pEList->a[i].pExpr) ) break;
    }
    if( i==pEList->nExpr ){
      prRhsHasNull = 0;
104070
104071
104072
104073
104074
104075
104076
104077

104078
104079
104080
104081
104082
104083
104084
          colUsed = 0;   /* Columns of index used so far */
          for(i=0; i<nExpr; i++){
            Expr *pLhs = sqlite3VectorFieldSubexpr(pX->pLeft, i);
            Expr *pRhs = pEList->a[i].pExpr;
            CollSeq *pReq = sqlite3BinaryCompareCollSeq(pParse, pLhs, pRhs);
            int j;

            assert( pReq!=0 || pRhs->iColumn==XN_ROWID || pParse->nErr );

            for(j=0; j<nExpr; j++){
              if( pIdx->aiColumn[j]!=pRhs->iColumn ) continue;
              assert( pIdx->azColl[j] );
              if( pReq!=0 && sqlite3StrICmp(pReq->zName, pIdx->azColl[j])!=0 ){
                continue;
              }
              break;







|
>







104596
104597
104598
104599
104600
104601
104602
104603
104604
104605
104606
104607
104608
104609
104610
104611
          colUsed = 0;   /* Columns of index used so far */
          for(i=0; i<nExpr; i++){
            Expr *pLhs = sqlite3VectorFieldSubexpr(pX->pLeft, i);
            Expr *pRhs = pEList->a[i].pExpr;
            CollSeq *pReq = sqlite3BinaryCompareCollSeq(pParse, pLhs, pRhs);
            int j;

            assert( pReq!=0 || pRhs->iColumn==XN_ROWID
                   || pParse->nErr || db->mallocFailed );
            for(j=0; j<nExpr; j++){
              if( pIdx->aiColumn[j]!=pRhs->iColumn ) continue;
              assert( pIdx->azColl[j] );
              if( pReq!=0 && sqlite3StrICmp(pReq->zName, pIdx->azColl[j])!=0 ){
                continue;
              }
              break;
104125
104126
104127
104128
104129
104130
104131
104132
104133
104134
104135
104136
104137
104138
104139
  ** and the RHS of the IN operator is a list, not a subquery
  ** and the RHS is not constant or has two or fewer terms,
  ** then it is not worth creating an ephemeral table to evaluate
  ** the IN operator so return IN_INDEX_NOOP.
  */
  if( eType==0
   && (inFlags & IN_INDEX_NOOP_OK)
   && !ExprHasProperty(pX, EP_xIsSelect)
   && (!sqlite3InRhsIsConstant(pX) || pX->x.pList->nExpr<=2)
  ){
    eType = IN_INDEX_NOOP;
  }

  if( eType==0 ){
    /* Could not find an existing table or index to use as the RHS b-tree.







|







104652
104653
104654
104655
104656
104657
104658
104659
104660
104661
104662
104663
104664
104665
104666
  ** and the RHS of the IN operator is a list, not a subquery
  ** and the RHS is not constant or has two or fewer terms,
  ** then it is not worth creating an ephemeral table to evaluate
  ** the IN operator so return IN_INDEX_NOOP.
  */
  if( eType==0
   && (inFlags & IN_INDEX_NOOP_OK)
   && ExprUseXList(pX)
   && (!sqlite3InRhsIsConstant(pX) || pX->x.pList->nExpr<=2)
  ){
    eType = IN_INDEX_NOOP;
  }

  if( eType==0 ){
    /* Could not find an existing table or index to use as the RHS b-tree.
104173
104174
104175
104176
104177
104178
104179
104180
104181
104182
104183
104184
104185
104186
104187
**
** It is the responsibility of the caller to ensure that the returned
** string is eventually freed using sqlite3DbFree().
*/
static char *exprINAffinity(Parse *pParse, const Expr *pExpr){
  Expr *pLeft = pExpr->pLeft;
  int nVal = sqlite3ExprVectorSize(pLeft);
  Select *pSelect = (pExpr->flags & EP_xIsSelect) ? pExpr->x.pSelect : 0;
  char *zRet;

  assert( pExpr->op==TK_IN );
  zRet = sqlite3DbMallocRaw(pParse->db, nVal+1);
  if( zRet ){
    int i;
    for(i=0; i<nVal; i++){







|







104700
104701
104702
104703
104704
104705
104706
104707
104708
104709
104710
104711
104712
104713
104714
**
** It is the responsibility of the caller to ensure that the returned
** string is eventually freed using sqlite3DbFree().
*/
static char *exprINAffinity(Parse *pParse, const Expr *pExpr){
  Expr *pLeft = pExpr->pLeft;
  int nVal = sqlite3ExprVectorSize(pLeft);
  Select *pSelect = ExprUseXSelect(pExpr) ? pExpr->x.pSelect : 0;
  char *zRet;

  assert( pExpr->op==TK_IN );
  zRet = sqlite3DbMallocRaw(pParse->db, nVal+1);
  if( zRet ){
    int i;
    for(i=0; i<nVal; i++){
104223
104224
104225
104226
104227
104228
104229
104230
104231
104232
104233
104234
104235
104236
104237
**
** Or, if it is a regular scalar vector:
**
**   "row value misused"
*/
SQLITE_PRIVATE void sqlite3VectorErrorMsg(Parse *pParse, Expr *pExpr){
#ifndef SQLITE_OMIT_SUBQUERY
  if( pExpr->flags & EP_xIsSelect ){
    sqlite3SubselectError(pParse, pExpr->x.pSelect->pEList->nExpr, 1);
  }else
#endif
  {
    sqlite3ErrorMsg(pParse, "row value misused");
  }
}







|







104750
104751
104752
104753
104754
104755
104756
104757
104758
104759
104760
104761
104762
104763
104764
**
** Or, if it is a regular scalar vector:
**
**   "row value misused"
*/
SQLITE_PRIVATE void sqlite3VectorErrorMsg(Parse *pParse, Expr *pExpr){
#ifndef SQLITE_OMIT_SUBQUERY
  if( ExprUseXSelect(pExpr) ){
    sqlite3SubselectError(pParse, pExpr->x.pSelect->pEList->nExpr, 1);
  }else
#endif
  {
    sqlite3ErrorMsg(pParse, "row value misused");
  }
}
104287
104288
104289
104290
104291
104292
104293
104294
104295
104296
104297

104298
104299
104300
104301
104302
104303
104304
104305

104306
104307
104308
104309
104310
104311
104312
104313
104314
104315
104316
104317
104318
104319
104320
104321
104322
104323
104324
104325
104326
104327
104328
104329
104330
104331
104332
104333
104334
104335
104336
104337
104338
104339
104340
104341
  if( !ExprHasProperty(pExpr, EP_VarSelect) && pParse->iSelfTab==0 ){
    /* Reuse of the RHS is allowed */
    /* If this routine has already been coded, but the previous code
    ** might not have been invoked yet, so invoke it now as a subroutine.
    */
    if( ExprHasProperty(pExpr, EP_Subrtn) ){
      addrOnce = sqlite3VdbeAddOp0(v, OP_Once); VdbeCoverage(v);
      if( ExprHasProperty(pExpr, EP_xIsSelect) ){
        ExplainQueryPlan((pParse, 0, "REUSE LIST SUBQUERY %d",
              pExpr->x.pSelect->selId));
      }

      sqlite3VdbeAddOp2(v, OP_Gosub, pExpr->y.sub.regReturn,
                        pExpr->y.sub.iAddr);
      sqlite3VdbeAddOp2(v, OP_OpenDup, iTab, pExpr->iTable);
      sqlite3VdbeJumpHere(v, addrOnce);
      return;
    }

    /* Begin coding the subroutine */

    ExprSetProperty(pExpr, EP_Subrtn);
    assert( !ExprHasProperty(pExpr, EP_TokenOnly|EP_Reduced) );
    pExpr->y.sub.regReturn = ++pParse->nMem;
    pExpr->y.sub.iAddr =
      sqlite3VdbeAddOp2(v, OP_Integer, 0, pExpr->y.sub.regReturn) + 1;
    VdbeComment((v, "return address"));

    addrOnce = sqlite3VdbeAddOp0(v, OP_Once); VdbeCoverage(v);
  }

  /* Check to see if this is a vector IN operator */
  pLeft = pExpr->pLeft;
  nVal = sqlite3ExprVectorSize(pLeft);

  /* Construct the ephemeral table that will contain the content of
  ** RHS of the IN operator.
  */
  pExpr->iTable = iTab;
  addr = sqlite3VdbeAddOp2(v, OP_OpenEphemeral, pExpr->iTable, nVal);
#ifdef SQLITE_ENABLE_EXPLAIN_COMMENTS
  if( ExprHasProperty(pExpr, EP_xIsSelect) ){
    VdbeComment((v, "Result of SELECT %u", pExpr->x.pSelect->selId));
  }else{
    VdbeComment((v, "RHS of IN operator"));
  }
#endif
  pKeyInfo = sqlite3KeyInfoAlloc(pParse->db, nVal, 1);

  if( ExprHasProperty(pExpr, EP_xIsSelect) ){
    /* Case 1:     expr IN (SELECT ...)
    **
    ** Generate code to write the results of the select into the temporary
    ** table allocated and opened above.
    */
    Select *pSelect = pExpr->x.pSelect;
    ExprList *pEList = pSelect->pEList;







|



>








>




















|







|







104814
104815
104816
104817
104818
104819
104820
104821
104822
104823
104824
104825
104826
104827
104828
104829
104830
104831
104832
104833
104834
104835
104836
104837
104838
104839
104840
104841
104842
104843
104844
104845
104846
104847
104848
104849
104850
104851
104852
104853
104854
104855
104856
104857
104858
104859
104860
104861
104862
104863
104864
104865
104866
104867
104868
104869
104870
  if( !ExprHasProperty(pExpr, EP_VarSelect) && pParse->iSelfTab==0 ){
    /* Reuse of the RHS is allowed */
    /* If this routine has already been coded, but the previous code
    ** might not have been invoked yet, so invoke it now as a subroutine.
    */
    if( ExprHasProperty(pExpr, EP_Subrtn) ){
      addrOnce = sqlite3VdbeAddOp0(v, OP_Once); VdbeCoverage(v);
      if( ExprUseXSelect(pExpr) ){
        ExplainQueryPlan((pParse, 0, "REUSE LIST SUBQUERY %d",
              pExpr->x.pSelect->selId));
      }
      assert( ExprUseYSub(pExpr) );
      sqlite3VdbeAddOp2(v, OP_Gosub, pExpr->y.sub.regReturn,
                        pExpr->y.sub.iAddr);
      sqlite3VdbeAddOp2(v, OP_OpenDup, iTab, pExpr->iTable);
      sqlite3VdbeJumpHere(v, addrOnce);
      return;
    }

    /* Begin coding the subroutine */
    assert( !ExprUseYWin(pExpr) );
    ExprSetProperty(pExpr, EP_Subrtn);
    assert( !ExprHasProperty(pExpr, EP_TokenOnly|EP_Reduced) );
    pExpr->y.sub.regReturn = ++pParse->nMem;
    pExpr->y.sub.iAddr =
      sqlite3VdbeAddOp2(v, OP_Integer, 0, pExpr->y.sub.regReturn) + 1;
    VdbeComment((v, "return address"));

    addrOnce = sqlite3VdbeAddOp0(v, OP_Once); VdbeCoverage(v);
  }

  /* Check to see if this is a vector IN operator */
  pLeft = pExpr->pLeft;
  nVal = sqlite3ExprVectorSize(pLeft);

  /* Construct the ephemeral table that will contain the content of
  ** RHS of the IN operator.
  */
  pExpr->iTable = iTab;
  addr = sqlite3VdbeAddOp2(v, OP_OpenEphemeral, pExpr->iTable, nVal);
#ifdef SQLITE_ENABLE_EXPLAIN_COMMENTS
  if( ExprUseXSelect(pExpr) ){
    VdbeComment((v, "Result of SELECT %u", pExpr->x.pSelect->selId));
  }else{
    VdbeComment((v, "RHS of IN operator"));
  }
#endif
  pKeyInfo = sqlite3KeyInfoAlloc(pParse->db, nVal, 1);

  if( ExprUseXSelect(pExpr) ){
    /* Case 1:     expr IN (SELECT ...)
    **
    ** Generate code to write the results of the select into the temporary
    ** table allocated and opened above.
    */
    Select *pSelect = pExpr->x.pSelect;
    ExprList *pEList = pSelect->pEList;
104425
104426
104427
104428
104429
104430
104431

104432
104433
104434
104435
104436
104437
104438
  }
  if( pKeyInfo ){
    sqlite3VdbeChangeP4(v, addr, (void *)pKeyInfo, P4_KEYINFO);
  }
  if( addrOnce ){
    sqlite3VdbeJumpHere(v, addrOnce);
    /* Subroutine return */

    sqlite3VdbeAddOp1(v, OP_Return, pExpr->y.sub.regReturn);
    sqlite3VdbeChangeP1(v, pExpr->y.sub.iAddr-1, sqlite3VdbeCurrentAddr(v)-1);
    sqlite3ClearTempRegCache(pParse);
  }
}
#endif /* SQLITE_OMIT_SUBQUERY */








>







104954
104955
104956
104957
104958
104959
104960
104961
104962
104963
104964
104965
104966
104967
104968
  }
  if( pKeyInfo ){
    sqlite3VdbeChangeP4(v, addr, (void *)pKeyInfo, P4_KEYINFO);
  }
  if( addrOnce ){
    sqlite3VdbeJumpHere(v, addrOnce);
    /* Subroutine return */
    assert( ExprUseYSub(pExpr) );
    sqlite3VdbeAddOp1(v, OP_Return, pExpr->y.sub.regReturn);
    sqlite3VdbeChangeP1(v, pExpr->y.sub.iAddr-1, sqlite3VdbeCurrentAddr(v)-1);
    sqlite3ClearTempRegCache(pParse);
  }
}
#endif /* SQLITE_OMIT_SUBQUERY */

104461
104462
104463
104464
104465
104466
104467
104468
104469
104470
104471
104472
104473
104474

104475
104476
104477
104478
104479
104480


104481
104482
104483
104484
104485
104486
104487

  Vdbe *v = pParse->pVdbe;
  assert( v!=0 );
  if( pParse->nErr ) return 0;
  testcase( pExpr->op==TK_EXISTS );
  testcase( pExpr->op==TK_SELECT );
  assert( pExpr->op==TK_EXISTS || pExpr->op==TK_SELECT );
  assert( ExprHasProperty(pExpr, EP_xIsSelect) );
  pSel = pExpr->x.pSelect;

  /* If this routine has already been coded, then invoke it as a
  ** subroutine. */
  if( ExprHasProperty(pExpr, EP_Subrtn) ){
    ExplainQueryPlan((pParse, 0, "REUSE SUBQUERY %d", pSel->selId));

    sqlite3VdbeAddOp2(v, OP_Gosub, pExpr->y.sub.regReturn,
                      pExpr->y.sub.iAddr);
    return pExpr->iTable;
  }

  /* Begin coding the subroutine */


  ExprSetProperty(pExpr, EP_Subrtn);
  pExpr->y.sub.regReturn = ++pParse->nMem;
  pExpr->y.sub.iAddr =
    sqlite3VdbeAddOp2(v, OP_Integer, 0, pExpr->y.sub.regReturn) + 1;
  VdbeComment((v, "return address"));









|






>






>
>







104991
104992
104993
104994
104995
104996
104997
104998
104999
105000
105001
105002
105003
105004
105005
105006
105007
105008
105009
105010
105011
105012
105013
105014
105015
105016
105017
105018
105019
105020

  Vdbe *v = pParse->pVdbe;
  assert( v!=0 );
  if( pParse->nErr ) return 0;
  testcase( pExpr->op==TK_EXISTS );
  testcase( pExpr->op==TK_SELECT );
  assert( pExpr->op==TK_EXISTS || pExpr->op==TK_SELECT );
  assert( ExprUseXSelect(pExpr) );
  pSel = pExpr->x.pSelect;

  /* If this routine has already been coded, then invoke it as a
  ** subroutine. */
  if( ExprHasProperty(pExpr, EP_Subrtn) ){
    ExplainQueryPlan((pParse, 0, "REUSE SUBQUERY %d", pSel->selId));
    assert( ExprUseYSub(pExpr) );
    sqlite3VdbeAddOp2(v, OP_Gosub, pExpr->y.sub.regReturn,
                      pExpr->y.sub.iAddr);
    return pExpr->iTable;
  }

  /* Begin coding the subroutine */
  assert( !ExprUseYWin(pExpr) );
  assert( !ExprHasProperty(pExpr, EP_Reduced|EP_TokenOnly) );
  ExprSetProperty(pExpr, EP_Subrtn);
  pExpr->y.sub.regReturn = ++pParse->nMem;
  pExpr->y.sub.iAddr =
    sqlite3VdbeAddOp2(v, OP_Integer, 0, pExpr->y.sub.regReturn) + 1;
  VdbeComment((v, "return address"));


104553
104554
104555
104556
104557
104558
104559

104560
104561
104562
104563
104564
104565
104566
104567
104568
104569
104570
104571
104572
104573
104574
104575
104576
104577
104578
104579
104580
104581
104582
104583
  pExpr->iTable = rReg = dest.iSDParm;
  ExprSetVVAProperty(pExpr, EP_NoReduce);
  if( addrOnce ){
    sqlite3VdbeJumpHere(v, addrOnce);
  }

  /* Subroutine return */

  sqlite3VdbeAddOp1(v, OP_Return, pExpr->y.sub.regReturn);
  sqlite3VdbeChangeP1(v, pExpr->y.sub.iAddr-1, sqlite3VdbeCurrentAddr(v)-1);
  sqlite3ClearTempRegCache(pParse);
  return rReg;
}
#endif /* SQLITE_OMIT_SUBQUERY */

#ifndef SQLITE_OMIT_SUBQUERY
/*
** Expr pIn is an IN(...) expression. This function checks that the
** sub-select on the RHS of the IN() operator has the same number of
** columns as the vector on the LHS. Or, if the RHS of the IN() is not
** a sub-query, that the LHS is a vector of size 1.
*/
SQLITE_PRIVATE int sqlite3ExprCheckIN(Parse *pParse, Expr *pIn){
  int nVector = sqlite3ExprVectorSize(pIn->pLeft);
  if( (pIn->flags & EP_xIsSelect)!=0 && !pParse->db->mallocFailed ){
    if( nVector!=pIn->x.pSelect->pEList->nExpr ){
      sqlite3SubselectError(pParse, pIn->x.pSelect->pEList->nExpr, nVector);
      return 1;
    }
  }else if( nVector!=1 ){
    sqlite3VectorErrorMsg(pParse, pIn->pLeft);
    return 1;







>
















|







105086
105087
105088
105089
105090
105091
105092
105093
105094
105095
105096
105097
105098
105099
105100
105101
105102
105103
105104
105105
105106
105107
105108
105109
105110
105111
105112
105113
105114
105115
105116
105117
  pExpr->iTable = rReg = dest.iSDParm;
  ExprSetVVAProperty(pExpr, EP_NoReduce);
  if( addrOnce ){
    sqlite3VdbeJumpHere(v, addrOnce);
  }

  /* Subroutine return */
  assert( ExprUseYSub(pExpr) );
  sqlite3VdbeAddOp1(v, OP_Return, pExpr->y.sub.regReturn);
  sqlite3VdbeChangeP1(v, pExpr->y.sub.iAddr-1, sqlite3VdbeCurrentAddr(v)-1);
  sqlite3ClearTempRegCache(pParse);
  return rReg;
}
#endif /* SQLITE_OMIT_SUBQUERY */

#ifndef SQLITE_OMIT_SUBQUERY
/*
** Expr pIn is an IN(...) expression. This function checks that the
** sub-select on the RHS of the IN() operator has the same number of
** columns as the vector on the LHS. Or, if the RHS of the IN() is not
** a sub-query, that the LHS is a vector of size 1.
*/
SQLITE_PRIVATE int sqlite3ExprCheckIN(Parse *pParse, Expr *pIn){
  int nVector = sqlite3ExprVectorSize(pIn->pLeft);
  if( ExprUseXSelect(pIn) && !pParse->db->mallocFailed ){
    if( nVector!=pIn->x.pSelect->pEList->nExpr ){
      sqlite3SubselectError(pParse, pIn->x.pSelect->pEList->nExpr, nVector);
      return 1;
    }
  }else if( nVector!=1 ){
    sqlite3VectorErrorMsg(pParse, pIn->pLeft);
    return 1;
104703
104704
104705
104706
104707
104708
104709
104710
104711
104712
104713
104714
104715
104716


104717
104718
104719
104720
104721
104722
104723
  /* If sqlite3FindInIndex() did not find or create an index that is
  ** suitable for evaluating the IN operator, then evaluate using a
  ** sequence of comparisons.
  **
  ** This is step (1) in the in-operator.md optimized algorithm.
  */
  if( eType==IN_INDEX_NOOP ){
    ExprList *pList = pExpr->x.pList;
    CollSeq *pColl = sqlite3ExprCollSeq(pParse, pExpr->pLeft);
    int labelOk = sqlite3VdbeMakeLabel(pParse);
    int r2, regToFree;
    int regCkNull = 0;
    int ii;
    assert( !ExprHasProperty(pExpr, EP_xIsSelect) );


    if( destIfNull!=destIfFalse ){
      regCkNull = sqlite3GetTempReg(pParse);
      sqlite3VdbeAddOp3(v, OP_BitAnd, rLhs, rLhs, regCkNull);
    }
    for(ii=0; ii<pList->nExpr; ii++){
      r2 = sqlite3ExprCodeTemp(pParse, pList->a[ii].pExpr, &regToFree);
      if( regCkNull && sqlite3ExprCanBeNull(pList->a[ii].pExpr) ){







|
|




|
>
>







105237
105238
105239
105240
105241
105242
105243
105244
105245
105246
105247
105248
105249
105250
105251
105252
105253
105254
105255
105256
105257
105258
105259
  /* If sqlite3FindInIndex() did not find or create an index that is
  ** suitable for evaluating the IN operator, then evaluate using a
  ** sequence of comparisons.
  **
  ** This is step (1) in the in-operator.md optimized algorithm.
  */
  if( eType==IN_INDEX_NOOP ){
    ExprList *pList;
    CollSeq *pColl;
    int labelOk = sqlite3VdbeMakeLabel(pParse);
    int r2, regToFree;
    int regCkNull = 0;
    int ii;
    assert( ExprUseXList(pExpr) );
    pList = pExpr->x.pList;
    pColl = sqlite3ExprCollSeq(pParse, pExpr->pLeft);
    if( destIfNull!=destIfFalse ){
      regCkNull = sqlite3GetTempReg(pParse);
      sqlite3VdbeAddOp3(v, OP_BitAnd, rLhs, rLhs, regCkNull);
    }
    for(ii=0; ii<pList->nExpr; ii++){
      r2 = sqlite3ExprCodeTemp(pParse, pList->a[ii].pExpr, &regToFree);
      if( regCkNull && sqlite3ExprCanBeNull(pList->a[ii].pExpr) ){
105095
105096
105097
105098
105099
105100
105101

105102
105103
105104
105105
105106
105107
105108
#else
      iResult = sqlite3CodeSubselect(pParse, p);
#endif
    }else{
      int i;
      iResult = pParse->nMem+1;
      pParse->nMem += nResult;

      for(i=0; i<nResult; i++){
        sqlite3ExprCodeFactorable(pParse, p->x.pList->a[i].pExpr, i+iResult);
      }
    }
  }
  return iResult;
}







>







105631
105632
105633
105634
105635
105636
105637
105638
105639
105640
105641
105642
105643
105644
105645
#else
      iResult = sqlite3CodeSubselect(pParse, p);
#endif
    }else{
      int i;
      iResult = pParse->nMem+1;
      pParse->nMem += nResult;
      assert( ExprUseXList(p) );
      for(i=0; i<nResult; i++){
        sqlite3ExprCodeFactorable(pParse, p->x.pList->a[i].pExpr, i+iResult);
      }
    }
  }
  return iResult;
}
105293
105294
105295
105296
105297
105298
105299

105300
105301
105302
105303
105304
105305
105306
        ** constraints, and that constant is coded by the pExpr->pLeft
        ** expresssion.  However, make sure the constant has the correct
        ** datatype by applying the Affinity of the table column to the
        ** constant.
        */
        int aff;
        iReg = sqlite3ExprCodeTarget(pParse, pExpr->pLeft,target);

        if( pExpr->y.pTab ){
          aff = sqlite3TableColumnAffinity(pExpr->y.pTab, pExpr->iColumn);
        }else{
          aff = pExpr->affExpr;
        }
        if( aff>SQLITE_AFF_BLOB ){
          static const char zAff[] = "B\000C\000D\000E";







>







105830
105831
105832
105833
105834
105835
105836
105837
105838
105839
105840
105841
105842
105843
105844
        ** constraints, and that constant is coded by the pExpr->pLeft
        ** expresssion.  However, make sure the constant has the correct
        ** datatype by applying the Affinity of the table column to the
        ** constant.
        */
        int aff;
        iReg = sqlite3ExprCodeTarget(pParse, pExpr->pLeft,target);
        assert( ExprUseYTab(pExpr) );
        if( pExpr->y.pTab ){
          aff = sqlite3TableColumnAffinity(pExpr->y.pTab, pExpr->iColumn);
        }else{
          aff = pExpr->affExpr;
        }
        if( aff>SQLITE_AFF_BLOB ){
          static const char zAff[] = "B\000C\000D\000E";
105316
105317
105318
105319
105320
105321
105322
105323
105324
105325


105326
105327
105328
105329
105330
105331
105332
          /* Other columns in the same row for CHECK constraints or
          ** generated columns or for inserting into partial index.
          ** The row is unpacked into registers beginning at
          ** 0-(pParse->iSelfTab).  The rowid (if any) is in a register
          ** immediately prior to the first column.
          */
          Column *pCol;
          Table *pTab = pExpr->y.pTab;
          int iSrc;
          int iCol = pExpr->iColumn;


          assert( pTab!=0 );
          assert( iCol>=XN_ROWID );
          assert( iCol<pTab->nCol );
          if( iCol<0 ){
            return -1-pParse->iSelfTab;
          }
          pCol = pTab->aCol + iCol;







|


>
>







105854
105855
105856
105857
105858
105859
105860
105861
105862
105863
105864
105865
105866
105867
105868
105869
105870
105871
105872
          /* Other columns in the same row for CHECK constraints or
          ** generated columns or for inserting into partial index.
          ** The row is unpacked into registers beginning at
          ** 0-(pParse->iSelfTab).  The rowid (if any) is in a register
          ** immediately prior to the first column.
          */
          Column *pCol;
          Table *pTab;
          int iSrc;
          int iCol = pExpr->iColumn;
          assert( ExprUseYTab(pExpr) );
          pTab = pExpr->y.pTab;
          assert( pTab!=0 );
          assert( iCol>=XN_ROWID );
          assert( iCol<pTab->nCol );
          if( iCol<0 ){
            return -1-pParse->iSelfTab;
          }
          pCol = pTab->aCol + iCol;
105356
105357
105358
105359
105360
105361
105362

105363
105364
105365
105366
105367
105368
105369
          }
        }else{
          /* Coding an expression that is part of an index where column names
          ** in the index refer to the table to which the index belongs */
          iTab = pParse->iSelfTab - 1;
        }
      }

      iReg = sqlite3ExprCodeGetColumn(pParse, pExpr->y.pTab,
                               pExpr->iColumn, iTab, target,
                               pExpr->op2);
      if( pExpr->y.pTab==0 && pExpr->affExpr==SQLITE_AFF_REAL ){
        sqlite3VdbeAddOp1(v, OP_RealAffinity, iReg);
      }
      return iReg;







>







105896
105897
105898
105899
105900
105901
105902
105903
105904
105905
105906
105907
105908
105909
105910
          }
        }else{
          /* Coding an expression that is part of an index where column names
          ** in the index refer to the table to which the index belongs */
          iTab = pParse->iSelfTab - 1;
        }
      }
      assert( ExprUseYTab(pExpr) );
      iReg = sqlite3ExprCodeGetColumn(pParse, pExpr->y.pTab,
                               pExpr->iColumn, iTab, target,
                               pExpr->op2);
      if( pExpr->y.pTab==0 && pExpr->affExpr==SQLITE_AFF_REAL ){
        sqlite3VdbeAddOp1(v, OP_RealAffinity, iReg);
      }
      return iReg;
105433
105434
105435
105436
105437
105438
105439

105440
105441
105442
105443
105444
105445
105446
    case TK_CAST: {
      /* Expressions of the form:   CAST(pLeft AS token) */
      inReg = sqlite3ExprCodeTarget(pParse, pExpr->pLeft, target);
      if( inReg!=target ){
        sqlite3VdbeAddOp2(v, OP_SCopy, inReg, target);
        inReg = target;
      }

      sqlite3VdbeAddOp2(v, OP_Cast, target,
                        sqlite3AffinityType(pExpr->u.zToken, 0));
      return inReg;
    }
#endif /* SQLITE_OMIT_CAST */
    case TK_IS:
    case TK_ISNOT:







>







105974
105975
105976
105977
105978
105979
105980
105981
105982
105983
105984
105985
105986
105987
105988
    case TK_CAST: {
      /* Expressions of the form:   CAST(pLeft AS token) */
      inReg = sqlite3ExprCodeTarget(pParse, pExpr->pLeft, target);
      if( inReg!=target ){
        sqlite3VdbeAddOp2(v, OP_SCopy, inReg, target);
        inReg = target;
      }
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      sqlite3VdbeAddOp2(v, OP_Cast, target,
                        sqlite3AffinityType(pExpr->u.zToken, 0));
      return inReg;
    }
#endif /* SQLITE_OMIT_CAST */
    case TK_IS:
    case TK_ISNOT:
105600
105601
105602
105603
105604
105605
105606
105607
105608
105609
105610
105611
105612
105613
105614
105615
#endif

      if( ConstFactorOk(pParse) && sqlite3ExprIsConstantNotJoin(pExpr) ){
        /* SQL functions can be expensive. So try to avoid running them
        ** multiple times if we know they always give the same result */
        return sqlite3ExprCodeRunJustOnce(pParse, pExpr, -1);
      }
      assert( !ExprHasProperty(pExpr, EP_xIsSelect) );
      assert( !ExprHasProperty(pExpr, EP_TokenOnly) );
      pFarg = pExpr->x.pList;
      nFarg = pFarg ? pFarg->nExpr : 0;
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      zId = pExpr->u.zToken;
      pDef = sqlite3FindFunction(db, zId, nFarg, enc, 0);
#ifdef SQLITE_ENABLE_UNKNOWN_SQL_FUNCTION
      if( pDef==0 && pParse->explain ){







|
|







106142
106143
106144
106145
106146
106147
106148
106149
106150
106151
106152
106153
106154
106155
106156
106157
#endif

      if( ConstFactorOk(pParse) && sqlite3ExprIsConstantNotJoin(pExpr) ){
        /* SQL functions can be expensive. So try to avoid running them
        ** multiple times if we know they always give the same result */
        return sqlite3ExprCodeRunJustOnce(pParse, pExpr, -1);
      }
      assert( !ExprHasProperty(pExpr, EP_TokenOnly) );
      assert( ExprUseXList(pExpr) );
      pFarg = pExpr->x.pList;
      nFarg = pFarg ? pFarg->nExpr : 0;
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      zId = pExpr->u.zToken;
      pDef = sqlite3FindFunction(db, zId, nFarg, enc, 0);
#ifdef SQLITE_ENABLE_UNKNOWN_SQL_FUNCTION
      if( pDef==0 && pParse->explain ){
105690
105691
105692
105693
105694
105695
105696
105697
105698
105699
105700
105701
105702
105703
105704
      }
#endif
      if( pDef->funcFlags & SQLITE_FUNC_NEEDCOLL ){
        if( !pColl ) pColl = db->pDfltColl;
        sqlite3VdbeAddOp4(v, OP_CollSeq, 0, 0, 0, (char *)pColl, P4_COLLSEQ);
      }
#ifdef SQLITE_ENABLE_OFFSET_SQL_FUNC
      if( pDef->funcFlags & SQLITE_FUNC_OFFSET ){
        Expr *pArg = pFarg->a[0].pExpr;
        if( pArg->op==TK_COLUMN ){
          sqlite3VdbeAddOp3(v, OP_Offset, pArg->iTable, pArg->iColumn, target);
        }else{
          sqlite3VdbeAddOp2(v, OP_Null, 0, target);
        }
      }else







|







106232
106233
106234
106235
106236
106237
106238
106239
106240
106241
106242
106243
106244
106245
106246
      }
#endif
      if( pDef->funcFlags & SQLITE_FUNC_NEEDCOLL ){
        if( !pColl ) pColl = db->pDfltColl;
        sqlite3VdbeAddOp4(v, OP_CollSeq, 0, 0, 0, (char *)pColl, P4_COLLSEQ);
      }
#ifdef SQLITE_ENABLE_OFFSET_SQL_FUNC
      if( (pDef->funcFlags & SQLITE_FUNC_OFFSET)!=0 && ALWAYS(pFarg!=0) ){
        Expr *pArg = pFarg->a[0].pExpr;
        if( pArg->op==TK_COLUMN ){
          sqlite3VdbeAddOp3(v, OP_Offset, pArg->iTable, pArg->iColumn, target);
        }else{
          sqlite3VdbeAddOp2(v, OP_Null, 0, target);
        }
      }else
105720
105721
105722
105723
105724
105725
105726


105727

105728
105729
105730
105731
105732
105733
105734
    case TK_EXISTS:
    case TK_SELECT: {
      int nCol;
      testcase( op==TK_EXISTS );
      testcase( op==TK_SELECT );
      if( pParse->db->mallocFailed ){
        return 0;


      }else if( op==TK_SELECT && (nCol = pExpr->x.pSelect->pEList->nExpr)!=1 ){

        sqlite3SubselectError(pParse, nCol, 1);
      }else{
        return sqlite3CodeSubselect(pParse, pExpr);
      }
      break;
    }
    case TK_SELECT_COLUMN: {







>
>
|
>







106262
106263
106264
106265
106266
106267
106268
106269
106270
106271
106272
106273
106274
106275
106276
106277
106278
106279
    case TK_EXISTS:
    case TK_SELECT: {
      int nCol;
      testcase( op==TK_EXISTS );
      testcase( op==TK_SELECT );
      if( pParse->db->mallocFailed ){
        return 0;
      }else if( op==TK_SELECT
             && ALWAYS( ExprUseXSelect(pExpr) )
             && (nCol = pExpr->x.pSelect->pEList->nExpr)!=1
      ){
        sqlite3SubselectError(pParse, nCol, 1);
      }else{
        return sqlite3CodeSubselect(pParse, pExpr);
      }
      break;
    }
    case TK_SELECT_COLUMN: {
105802
105803
105804
105805
105806
105807
105808





105809
105810
105811
105812
105813
105814
105815
105816
105817
105818
      **
      ** Then p1 is interpreted as follows:
      **
      **   p1==0   ->    old.rowid     p1==3   ->    new.rowid
      **   p1==1   ->    old.a         p1==4   ->    new.a
      **   p1==2   ->    old.b         p1==5   ->    new.b
      */





      Table *pTab = pExpr->y.pTab;
      int iCol = pExpr->iColumn;
      int p1 = pExpr->iTable * (pTab->nCol+1) + 1
                     + sqlite3TableColumnToStorage(pTab, iCol);

      assert( pExpr->iTable==0 || pExpr->iTable==1 );
      assert( iCol>=-1 && iCol<pTab->nCol );
      assert( pTab->iPKey<0 || iCol!=pTab->iPKey );
      assert( p1>=0 && p1<(pTab->nCol*2+2) );








>
>
>
>
>
|
|
|







106347
106348
106349
106350
106351
106352
106353
106354
106355
106356
106357
106358
106359
106360
106361
106362
106363
106364
106365
106366
106367
106368
      **
      ** Then p1 is interpreted as follows:
      **
      **   p1==0   ->    old.rowid     p1==3   ->    new.rowid
      **   p1==1   ->    old.a         p1==4   ->    new.a
      **   p1==2   ->    old.b         p1==5   ->    new.b
      */
      Table *pTab;
      int iCol;
      int p1;

      assert( ExprUseYTab(pExpr) );
      pTab = pExpr->y.pTab;
      iCol = pExpr->iColumn;
      p1 = pExpr->iTable * (pTab->nCol+1) + 1
                     + sqlite3TableColumnToStorage(pTab, iCol);

      assert( pExpr->iTable==0 || pExpr->iTable==1 );
      assert( iCol>=-1 && iCol<pTab->nCol );
      assert( pTab->iPKey<0 || iCol!=pTab->iPKey );
      assert( p1>=0 && p1<(pTab->nCol*2+2) );

105892
105893
105894
105895
105896
105897
105898
105899
105900
105901
105902
105903
105904
105905
105906
      struct ExprList_item *aListelem;  /* Array of WHEN terms */
      Expr opCompare;                   /* The X==Ei expression */
      Expr *pX;                         /* The X expression */
      Expr *pTest = 0;                  /* X==Ei (form A) or just Ei (form B) */
      Expr *pDel = 0;
      sqlite3 *db = pParse->db;

      assert( !ExprHasProperty(pExpr, EP_xIsSelect) && pExpr->x.pList );
      assert(pExpr->x.pList->nExpr > 0);
      pEList = pExpr->x.pList;
      aListelem = pEList->a;
      nExpr = pEList->nExpr;
      endLabel = sqlite3VdbeMakeLabel(pParse);
      if( (pX = pExpr->pLeft)!=0 ){
        pDel = sqlite3ExprDup(db, pX, 0);







|







106442
106443
106444
106445
106446
106447
106448
106449
106450
106451
106452
106453
106454
106455
106456
      struct ExprList_item *aListelem;  /* Array of WHEN terms */
      Expr opCompare;                   /* The X==Ei expression */
      Expr *pX;                         /* The X expression */
      Expr *pTest = 0;                  /* X==Ei (form A) or just Ei (form B) */
      Expr *pDel = 0;
      sqlite3 *db = pParse->db;

      assert( ExprUseXList(pExpr) && pExpr->x.pList!=0 );
      assert(pExpr->x.pList->nExpr > 0);
      pEList = pExpr->x.pList;
      aListelem = pEList->a;
      nExpr = pEList->nExpr;
      endLabel = sqlite3VdbeMakeLabel(pParse);
      if( (pX = pExpr->pLeft)!=0 ){
        pDel = sqlite3ExprDup(db, pX, 0);
106237
106238
106239
106240
106241
106242
106243
106244
106245
106246
106247
106248
106249
106250
106251
  Expr *pDel = 0;
  sqlite3 *db = pParse->db;

  memset(&compLeft, 0, sizeof(Expr));
  memset(&compRight, 0, sizeof(Expr));
  memset(&exprAnd, 0, sizeof(Expr));

  assert( !ExprHasProperty(pExpr, EP_xIsSelect) );
  pDel = sqlite3ExprDup(db, pExpr->pLeft, 0);
  if( db->mallocFailed==0 ){
    exprAnd.op = TK_AND;
    exprAnd.pLeft = &compLeft;
    exprAnd.pRight = &compRight;
    compLeft.op = TK_GE;
    compLeft.pLeft = pDel;







|







106787
106788
106789
106790
106791
106792
106793
106794
106795
106796
106797
106798
106799
106800
106801
  Expr *pDel = 0;
  sqlite3 *db = pParse->db;

  memset(&compLeft, 0, sizeof(Expr));
  memset(&compRight, 0, sizeof(Expr));
  memset(&exprAnd, 0, sizeof(Expr));

  assert( ExprUseXList(pExpr) );
  pDel = sqlite3ExprDup(db, pExpr->pLeft, 0);
  if( db->mallocFailed==0 ){
    exprAnd.op = TK_AND;
    exprAnd.pLeft = &compLeft;
    exprAnd.pRight = &compRight;
    compLeft.op = TK_GE;
    compLeft.pLeft = pDel;
106712
106713
106714
106715
106716
106717
106718


106719
106720
106721
106722
106723
106724
106725
106726
106727
106728
106729
106730
106731
106732
106733
106734
106735
106736




106737

106738
106739
106740
106741
106742
106743
106744
      return 1;
    }
    if( pB->op==TK_COLLATE && sqlite3ExprCompare(pParse, pA,pB->pLeft,iTab)<2 ){
      return 1;
    }
    return 2;
  }


  if( pA->op!=TK_COLUMN && pA->op!=TK_AGG_COLUMN && pA->u.zToken ){
    if( pA->op==TK_FUNCTION || pA->op==TK_AGG_FUNCTION ){
      if( sqlite3StrICmp(pA->u.zToken,pB->u.zToken)!=0 ) return 2;
#ifndef SQLITE_OMIT_WINDOWFUNC
      assert( pA->op==pB->op );
      if( ExprHasProperty(pA,EP_WinFunc)!=ExprHasProperty(pB,EP_WinFunc) ){
        return 2;
      }
      if( ExprHasProperty(pA,EP_WinFunc) ){
        if( sqlite3WindowCompare(pParse, pA->y.pWin, pB->y.pWin, 1)!=0 ){
          return 2;
        }
      }
#endif
    }else if( pA->op==TK_NULL ){
      return 0;
    }else if( pA->op==TK_COLLATE ){
      if( sqlite3_stricmp(pA->u.zToken,pB->u.zToken)!=0 ) return 2;




    }else if( ALWAYS(pB->u.zToken!=0) && strcmp(pA->u.zToken,pB->u.zToken)!=0 ){

      return 2;
    }
  }
  if( (pA->flags & (EP_Distinct|EP_Commuted))
     != (pB->flags & (EP_Distinct|EP_Commuted)) ) return 2;
  if( ALWAYS((combinedFlags & EP_TokenOnly)==0) ){
    if( combinedFlags & EP_xIsSelect ) return 2;







>
>
|

















>
>
>
>
|
>







107262
107263
107264
107265
107266
107267
107268
107269
107270
107271
107272
107273
107274
107275
107276
107277
107278
107279
107280
107281
107282
107283
107284
107285
107286
107287
107288
107289
107290
107291
107292
107293
107294
107295
107296
107297
107298
107299
107300
107301
      return 1;
    }
    if( pB->op==TK_COLLATE && sqlite3ExprCompare(pParse, pA,pB->pLeft,iTab)<2 ){
      return 1;
    }
    return 2;
  }
  assert( !ExprHasProperty(pA, EP_IntValue) );
  assert( !ExprHasProperty(pB, EP_IntValue) );
  if( pA->u.zToken ){
    if( pA->op==TK_FUNCTION || pA->op==TK_AGG_FUNCTION ){
      if( sqlite3StrICmp(pA->u.zToken,pB->u.zToken)!=0 ) return 2;
#ifndef SQLITE_OMIT_WINDOWFUNC
      assert( pA->op==pB->op );
      if( ExprHasProperty(pA,EP_WinFunc)!=ExprHasProperty(pB,EP_WinFunc) ){
        return 2;
      }
      if( ExprHasProperty(pA,EP_WinFunc) ){
        if( sqlite3WindowCompare(pParse, pA->y.pWin, pB->y.pWin, 1)!=0 ){
          return 2;
        }
      }
#endif
    }else if( pA->op==TK_NULL ){
      return 0;
    }else if( pA->op==TK_COLLATE ){
      if( sqlite3_stricmp(pA->u.zToken,pB->u.zToken)!=0 ) return 2;
    }else
    if( pB->u.zToken!=0
     && pA->op!=TK_COLUMN
     && pA->op!=TK_AGG_COLUMN
     && strcmp(pA->u.zToken,pB->u.zToken)!=0
    ){
      return 2;
    }
  }
  if( (pA->flags & (EP_Distinct|EP_Commuted))
     != (pB->flags & (EP_Distinct|EP_Commuted)) ) return 2;
  if( ALWAYS((combinedFlags & EP_TokenOnly)==0) ){
    if( combinedFlags & EP_xIsSelect ) return 2;
106819
106820
106821
106822
106823
106824
106825
106826
106827
106828
106829
106830
106831


106832
106833
106834
106835
106836
106837
106838
  assert( pNN );
  if( sqlite3ExprCompare(pParse, p, pNN, iTab)==0 ){
    return pNN->op!=TK_NULL;
  }
  switch( p->op ){
    case TK_IN: {
      if( seenNot && ExprHasProperty(p, EP_xIsSelect) ) return 0;
      assert( ExprHasProperty(p,EP_xIsSelect)
           || (p->x.pList!=0 && p->x.pList->nExpr>0) );
      return exprImpliesNotNull(pParse, p->pLeft, pNN, iTab, 1);
    }
    case TK_BETWEEN: {
      ExprList *pList = p->x.pList;


      assert( pList!=0 );
      assert( pList->nExpr==2 );
      if( seenNot ) return 0;
      if( exprImpliesNotNull(pParse, pList->a[0].pExpr, pNN, iTab, 1)
       || exprImpliesNotNull(pParse, pList->a[1].pExpr, pNN, iTab, 1)
      ){
        return 1;







<
|



|
>
>







107376
107377
107378
107379
107380
107381
107382

107383
107384
107385
107386
107387
107388
107389
107390
107391
107392
107393
107394
107395
107396
  assert( pNN );
  if( sqlite3ExprCompare(pParse, p, pNN, iTab)==0 ){
    return pNN->op!=TK_NULL;
  }
  switch( p->op ){
    case TK_IN: {
      if( seenNot && ExprHasProperty(p, EP_xIsSelect) ) return 0;

      assert( ExprUseXSelect(p) || (p->x.pList!=0 && p->x.pList->nExpr>0) );
      return exprImpliesNotNull(pParse, p->pLeft, pNN, iTab, 1);
    }
    case TK_BETWEEN: {
      ExprList *pList;
      assert( ExprUseXList(p) );
      pList = p->x.pList;
      assert( pList!=0 );
      assert( pList->nExpr==2 );
      if( seenNot ) return 0;
      if( exprImpliesNotNull(pParse, pList->a[0].pExpr, pNN, iTab, 1)
       || exprImpliesNotNull(pParse, pList->a[1].pExpr, pNN, iTab, 1)
      ){
        return 1;
107001
107002
107003
107004
107005
107006
107007


107008

107009
107010

107011
107012
107013
107014
107015
107016
107017
107018
      testcase( pExpr->op==TK_NE );
      testcase( pExpr->op==TK_LT );
      testcase( pExpr->op==TK_LE );
      testcase( pExpr->op==TK_GT );
      testcase( pExpr->op==TK_GE );
      /* The y.pTab=0 assignment in wherecode.c always happens after the
      ** impliesNotNullRow() test */


      if( (pLeft->op==TK_COLUMN && pLeft->y.pTab!=0

                               && IsVirtual(pLeft->y.pTab))
       || (pRight->op==TK_COLUMN && pRight->y.pTab!=0

                               && IsVirtual(pRight->y.pTab))
      ){
        return WRC_Prune;
      }
      /* no break */ deliberate_fall_through
    }
    default:
      return WRC_Continue;







>
>
|
>
|
|
>
|







107559
107560
107561
107562
107563
107564
107565
107566
107567
107568
107569
107570
107571
107572
107573
107574
107575
107576
107577
107578
107579
107580
      testcase( pExpr->op==TK_NE );
      testcase( pExpr->op==TK_LT );
      testcase( pExpr->op==TK_LE );
      testcase( pExpr->op==TK_GT );
      testcase( pExpr->op==TK_GE );
      /* The y.pTab=0 assignment in wherecode.c always happens after the
      ** impliesNotNullRow() test */
      assert( pLeft->op!=TK_COLUMN || ExprUseYTab(pLeft) );
      assert( pRight->op!=TK_COLUMN || ExprUseYTab(pRight) );
      if( (pLeft->op==TK_COLUMN
           && pLeft->y.pTab!=0
           && IsVirtual(pLeft->y.pTab))
       || (pRight->op==TK_COLUMN
           && pRight->y.pTab!=0
           && IsVirtual(pRight->y.pTab))
      ){
        return WRC_Prune;
      }
      /* no break */ deliberate_fall_through
    }
    default:
      return WRC_Continue;
107113
107114
107115
107116
107117
107118
107119
107120
107121
107122
107123
107124
107125
107126

107127
107128
107129
107130
107131
107132
107133
107134

107135
107136

107137

107138
107139
107140





107141








107142
107143
107144
107145






107146



107147
107148




107149
107150
107151
107152
107153
107154
107155
107156
107157


107158
107159
107160
107161
107162
107163


107164
107165
107166

107167
107168
107169
107170
107171

107172
107173
107174
107175
107176
107177
107178
107179




107180


107181



107182
107183
107184
107185
107186
107187

107188
107189

107190

107191
107192
107193
107194


107195
107196
107197
107198
107199
107200


107201





107202
107203
107204
107205
107206
107207
107208
  w.xExprCallback = exprIdxCover;
  w.u.pIdxCover = &xcov;
  sqlite3WalkExpr(&w, pExpr);
  return !w.eCode;
}


/*
** An instance of the following structure is used by the tree walker
** to count references to table columns in the arguments of an
** aggregate function, in order to implement the
** sqlite3FunctionThisSrc() routine.
*/
struct SrcCount {

  SrcList *pSrc;   /* One particular FROM clause in a nested query */
  int iSrcInner;   /* Smallest cursor number in this context */
  int nThis;       /* Number of references to columns in pSrcList */
  int nOther;      /* Number of references to columns in other FROM clauses */
};

/*
** xSelect callback for sqlite3FunctionUsesThisSrc(). If this is the first

** SELECT with a FROM clause encountered during this iteration, set
** SrcCount.iSrcInner to the cursor number of the leftmost object in

** the FROM cause.

*/
static int selectSrcCount(Walker *pWalker, Select *pSel){
  struct SrcCount *p = pWalker->u.pSrcCount;





  if( p->iSrcInner==0x7FFFFFFF && ALWAYS(pSel->pSrc) && pSel->pSrc->nSrc ){








    pWalker->u.pSrcCount->iSrcInner = pSel->pSrc->a[0].iCursor;
  }
  return WRC_Continue;
}










/*
** Count the number of references to columns.




*/
static int exprSrcCount(Walker *pWalker, Expr *pExpr){
  /* There was once a NEVER() on the second term on the grounds that
  ** sqlite3FunctionUsesThisSrc() was always called before
  ** sqlite3ExprAnalyzeAggregates() and so the TK_COLUMNs have not yet
  ** been converted into TK_AGG_COLUMN. But this is no longer true due
  ** to window functions - sqlite3WindowRewrite() may now indirectly call
  ** FunctionUsesThisSrc() when creating a new sub-select. */
  if( pExpr->op==TK_COLUMN || pExpr->op==TK_AGG_COLUMN ){


    int i;
    struct SrcCount *p = pWalker->u.pSrcCount;
    SrcList *pSrc = p->pSrc;
    int nSrc = pSrc ? pSrc->nSrc : 0;
    for(i=0; i<nSrc; i++){
      if( pExpr->iTable==pSrc->a[i].iCursor ) break;


    }
    if( i<nSrc ){
      p->nThis++;

    }else if( pExpr->iTable<p->iSrcInner ){
      /* In a well-formed parse tree (no name resolution errors),
      ** TK_COLUMN nodes with smaller Expr.iTable values are in an
      ** outer context.  Those are the only ones to count as "other" */
      p->nOther++;

    }
  }
  return WRC_Continue;
}

/*
** Determine if any of the arguments to the pExpr Function reference
** pSrcList.  Return true if they do.  Also return true if the function




** has no arguments or has only constant arguments.  Return false if pExpr


** references columns but not columns of tables found in pSrcList.



*/
SQLITE_PRIVATE int sqlite3FunctionUsesThisSrc(Expr *pExpr, SrcList *pSrcList){
  Walker w;
  struct SrcCount cnt;
  assert( pExpr->op==TK_AGG_FUNCTION );
  memset(&w, 0, sizeof(w));

  w.xExprCallback = exprSrcCount;
  w.xSelectCallback = selectSrcCount;

  w.u.pSrcCount = &cnt;

  cnt.pSrc = pSrcList;
  cnt.iSrcInner = (pSrcList&&pSrcList->nSrc)?pSrcList->a[0].iCursor:0x7FFFFFFF;
  cnt.nThis = 0;
  cnt.nOther = 0;


  sqlite3WalkExprList(&w, pExpr->x.pList);
#ifndef SQLITE_OMIT_WINDOWFUNC
  if( ExprHasProperty(pExpr, EP_WinFunc) ){
    sqlite3WalkExpr(&w, pExpr->y.pWin->pFilter);
  }
#endif


  return cnt.nThis>0 || cnt.nOther==0;





}

/*
** This is a Walker expression node callback.
**
** For Expr nodes that contain pAggInfo pointers, make sure the AggInfo
** object that is referenced does not refer directly to the Expr.  If







<
|
<
|
<

|
>
|
<
|
|



|
>
|
<
>
|
>

|
|
>
>
>
>
>
|
>
>
>
>
>
>
>
>
|



>
>
>
>
>
>
|
>
>
>
|
|
>
>
>
>

|
<
<
<
<
<
<
|
>
>

|
|


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






|
|
>
>
>
>
|
>
>
|
>
>
>

|

|
<

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






>
>
|
>
>
>
>
>







107675
107676
107677
107678
107679
107680
107681

107682

107683

107684
107685
107686
107687

107688
107689
107690
107691
107692
107693
107694
107695

107696
107697
107698
107699
107700
107701
107702
107703
107704
107705
107706
107707
107708
107709
107710
107711
107712
107713
107714
107715
107716
107717
107718
107719
107720
107721
107722
107723
107724
107725
107726
107727
107728
107729
107730
107731
107732
107733
107734
107735
107736
107737






107738
107739
107740
107741
107742
107743
107744
107745
107746
107747
107748
107749


107750
107751



107752
107753
107754
107755
107756
107757
107758
107759
107760
107761
107762
107763
107764
107765
107766
107767
107768
107769
107770
107771
107772
107773
107774
107775
107776

107777
107778
107779
107780
107781
107782
107783
107784



107785
107786
107787
107788
107789
107790
107791
107792
107793
107794
107795
107796
107797
107798
107799
107800
107801
107802
107803
107804
107805
107806
107807
  w.xExprCallback = exprIdxCover;
  w.u.pIdxCover = &xcov;
  sqlite3WalkExpr(&w, pExpr);
  return !w.eCode;
}



/* Structure used to pass information throught the Walker in order to

** implement sqlite3ReferencesSrcList().

*/
struct RefSrcList {
  sqlite3 *db;         /* Database connection used for sqlite3DbRealloc() */
  SrcList *pRef;       /* Looking for references to these tables */

  i64 nExclude;        /* Number of tables to exclude from the search */
  int *aiExclude;      /* Cursor IDs for tables to exclude from the search */
};

/*
** Walker SELECT callbacks for sqlite3ReferencesSrcList().
**
** When entering a new subquery on the pExpr argument, add all FROM clause

** entries for that subquery to the exclude list.
**
** When leaving the subquery, remove those entries from the exclude list.
*/
static int selectRefEnter(Walker *pWalker, Select *pSelect){
  struct RefSrcList *p = pWalker->u.pRefSrcList;
  SrcList *pSrc = pSelect->pSrc;
  i64 i, j;
  int *piNew;
  if( pSrc->nSrc==0 ) return WRC_Continue;
  j = p->nExclude;
  p->nExclude += pSrc->nSrc;
  piNew = sqlite3DbRealloc(p->db, p->aiExclude, p->nExclude*sizeof(int));
  if( piNew==0 ){
    p->nExclude = 0;
    return WRC_Abort;
  }else{
    p->aiExclude = piNew;
  }
  for(i=0; i<pSrc->nSrc; i++, j++){
     p->aiExclude[j] = pSrc->a[i].iCursor;
  }
  return WRC_Continue;
}
static void selectRefLeave(Walker *pWalker, Select *pSelect){
  struct RefSrcList *p = pWalker->u.pRefSrcList;
  SrcList *pSrc = pSelect->pSrc;
  if( p->nExclude ){
    assert( p->nExclude>=pSrc->nSrc );
    p->nExclude -= pSrc->nSrc;
  }
}

/* This is the Walker EXPR callback for sqlite3ReferencesSrcList().
**
** Set the 0x01 bit of pWalker->eCode if there is a reference to any
** of the tables shown in RefSrcList.pRef.
**
** Set the 0x02 bit of pWalker->eCode if there is a reference to a
** table is in neither RefSrcList.pRef nor RefSrcList.aiExclude.
*/
static int exprRefToSrcList(Walker *pWalker, Expr *pExpr){






  if( pExpr->op==TK_COLUMN
   || pExpr->op==TK_AGG_COLUMN
  ){
    int i;
    struct RefSrcList *p = pWalker->u.pRefSrcList;
    SrcList *pSrc = p->pRef;
    int nSrc = pSrc ? pSrc->nSrc : 0;
    for(i=0; i<nSrc; i++){
      if( pExpr->iTable==pSrc->a[i].iCursor ){
        pWalker->eCode |= 1;
        return WRC_Continue;
      }


    }
    for(i=0; i<p->nExclude && p->aiExclude[i]!=pExpr->iTable; i++){}



    if( i>=p->nExclude ){
      pWalker->eCode |= 2;
    }
  }
  return WRC_Continue;
}

/*
** Check to see if pExpr references any tables in pSrcList.
** Possible return values:
**
**    1         pExpr does references a table in pSrcList.
**
**    0         pExpr references some table that is not defined in either
**              pSrcList or in subqueries of pExpr itself.
**
**   -1         pExpr only references no tables at all, or it only
**              references tables defined in subqueries of pExpr itself.
**
** As currently used, pExpr is always an aggregate function call.  That
** fact is exploited for efficiency.
*/
SQLITE_PRIVATE int sqlite3ReferencesSrcList(Parse *pParse, Expr *pExpr, SrcList *pSrcList){
  Walker w;
  struct RefSrcList x;

  memset(&w, 0, sizeof(w));
  memset(&x, 0, sizeof(x));
  w.xExprCallback = exprRefToSrcList;
  w.xSelectCallback = selectRefEnter;
  w.xSelectCallback2 = selectRefLeave;
  w.u.pRefSrcList = &x;
  x.db = pParse->db;
  x.pRef = pSrcList;



  assert( pExpr->op==TK_AGG_FUNCTION );
  assert( ExprUseXList(pExpr) );
  sqlite3WalkExprList(&w, pExpr->x.pList);
#ifndef SQLITE_OMIT_WINDOWFUNC
  if( ExprHasProperty(pExpr, EP_WinFunc) ){
    sqlite3WalkExpr(&w, pExpr->y.pWin->pFilter);
  }
#endif
  sqlite3DbFree(pParse->db, x.aiExclude);
  if( w.eCode & 0x01 ){
    return 1;
  }else if( w.eCode ){
    return 0;
  }else{
    return -1;
  }
}

/*
** This is a Walker expression node callback.
**
** For Expr nodes that contain pAggInfo pointers, make sure the AggInfo
** object that is referenced does not refer directly to the Expr.  If
107329
107330
107331
107332
107333
107334
107335

107336
107337
107338
107339
107340
107341
107342
                break;
              }
            }
            if( (k>=pAggInfo->nColumn)
             && (k = addAggInfoColumn(pParse->db, pAggInfo))>=0
            ){
              pCol = &pAggInfo->aCol[k];

              pCol->pTab = pExpr->y.pTab;
              pCol->iTable = pExpr->iTable;
              pCol->iColumn = pExpr->iColumn;
              pCol->iMem = ++pParse->nMem;
              pCol->iSorterColumn = -1;
              pCol->pCExpr = pExpr;
              if( pAggInfo->pGroupBy ){







>







107928
107929
107930
107931
107932
107933
107934
107935
107936
107937
107938
107939
107940
107941
107942
                break;
              }
            }
            if( (k>=pAggInfo->nColumn)
             && (k = addAggInfoColumn(pParse->db, pAggInfo))>=0
            ){
              pCol = &pAggInfo->aCol[k];
              assert( ExprUseYTab(pExpr) );
              pCol->pTab = pExpr->y.pTab;
              pCol->iTable = pExpr->iTable;
              pCol->iColumn = pExpr->iColumn;
              pCol->iMem = ++pParse->nMem;
              pCol->iSorterColumn = -1;
              pCol->pCExpr = pExpr;
              if( pAggInfo->pGroupBy ){
107392
107393
107394
107395
107396
107397
107398
107399
107400
107401
107402
107403
107404
107405
107406
          u8 enc = ENC(pParse->db);
          i = addAggInfoFunc(pParse->db, pAggInfo);
          if( i>=0 ){
            assert( !ExprHasProperty(pExpr, EP_xIsSelect) );
            pItem = &pAggInfo->aFunc[i];
            pItem->pFExpr = pExpr;
            pItem->iMem = ++pParse->nMem;
            assert( !ExprHasProperty(pExpr, EP_IntValue) );
            pItem->pFunc = sqlite3FindFunction(pParse->db,
                   pExpr->u.zToken,
                   pExpr->x.pList ? pExpr->x.pList->nExpr : 0, enc, 0);
            if( pExpr->flags & EP_Distinct ){
              pItem->iDistinct = pParse->nTab++;
            }else{
              pItem->iDistinct = -1;







|







107992
107993
107994
107995
107996
107997
107998
107999
108000
108001
108002
108003
108004
108005
108006
          u8 enc = ENC(pParse->db);
          i = addAggInfoFunc(pParse->db, pAggInfo);
          if( i>=0 ){
            assert( !ExprHasProperty(pExpr, EP_xIsSelect) );
            pItem = &pAggInfo->aFunc[i];
            pItem->pFExpr = pExpr;
            pItem->iMem = ++pParse->nMem;
            assert( ExprUseUToken(pExpr) );
            pItem->pFunc = sqlite3FindFunction(pParse->db,
                   pExpr->u.zToken,
                   pExpr->x.pList ? pExpr->x.pList->nExpr : 0, enc, 0);
            if( pExpr->flags & EP_Distinct ){
              pItem->iDistinct = pParse->nTab++;
            }else{
              pItem->iDistinct = -1;
107607
107608
107609
107610
107611
107612
107613
107614
107615
107616
107617
107618
107619
107620
107621
107622
107623
107624
107625
107626
107627
107628
107629
107630
107631
107632
107633
107634
107635
107636
107637
107638
107639
107640
107641
107642
107643
107644
107645
107646
107647
107648
107649
107650
107651
107652
107653
107654
107655
107656
107657
  int bTemp,                      /* True if this is the temp db */
  const char *zWhen,              /* "when" part of error message */
  int bNoDQS                      /* Do not allow DQS in the schema */
){
  pParse->colNamesSet = 1;
  sqlite3NestedParse(pParse,
      "SELECT 1 "
      "FROM \"%w\"." DFLT_SCHEMA_TABLE " "
      "WHERE name NOT LIKE 'sqliteX_%%' ESCAPE 'X'"
      " AND sql NOT LIKE 'create virtual%%'"
      " AND sqlite_rename_test(%Q, sql, type, name, %d, %Q, %d)=NULL ",
      zDb,
      zDb, bTemp, zWhen, bNoDQS
  );

  if( bTemp==0 ){
    sqlite3NestedParse(pParse,
        "SELECT 1 "
        "FROM temp." DFLT_SCHEMA_TABLE " "
        "WHERE name NOT LIKE 'sqliteX_%%' ESCAPE 'X'"
        " AND sql NOT LIKE 'create virtual%%'"
        " AND sqlite_rename_test(%Q, sql, type, name, 1, %Q, %d)=NULL ",
        zDb, zWhen, bNoDQS
    );
  }
}

/*
** Generate VM code to replace any double-quoted strings (but not double-quoted
** identifiers) within the "sql" column of the sqlite_schema table in
** database zDb with their single-quoted equivalents. If argument bTemp is
** not true, similarly update all SQL statements in the sqlite_schema table
** of the temp db.
*/
static void renameFixQuotes(Parse *pParse, const char *zDb, int bTemp){
  sqlite3NestedParse(pParse,
      "UPDATE \"%w\"." DFLT_SCHEMA_TABLE
      " SET sql = sqlite_rename_quotefix(%Q, sql)"
      "WHERE name NOT LIKE 'sqliteX_%%' ESCAPE 'X'"
      " AND sql NOT LIKE 'create virtual%%'" , zDb, zDb
  );
  if( bTemp==0 ){
    sqlite3NestedParse(pParse,
      "UPDATE temp." DFLT_SCHEMA_TABLE
      " SET sql = sqlite_rename_quotefix('temp', sql)"
      "WHERE name NOT LIKE 'sqliteX_%%' ESCAPE 'X'"
      " AND sql NOT LIKE 'create virtual%%'"
    );
  }
}








|










|

















|






|







108207
108208
108209
108210
108211
108212
108213
108214
108215
108216
108217
108218
108219
108220
108221
108222
108223
108224
108225
108226
108227
108228
108229
108230
108231
108232
108233
108234
108235
108236
108237
108238
108239
108240
108241
108242
108243
108244
108245
108246
108247
108248
108249
108250
108251
108252
108253
108254
108255
108256
108257
  int bTemp,                      /* True if this is the temp db */
  const char *zWhen,              /* "when" part of error message */
  int bNoDQS                      /* Do not allow DQS in the schema */
){
  pParse->colNamesSet = 1;
  sqlite3NestedParse(pParse,
      "SELECT 1 "
      "FROM \"%w\"." LEGACY_SCHEMA_TABLE " "
      "WHERE name NOT LIKE 'sqliteX_%%' ESCAPE 'X'"
      " AND sql NOT LIKE 'create virtual%%'"
      " AND sqlite_rename_test(%Q, sql, type, name, %d, %Q, %d)=NULL ",
      zDb,
      zDb, bTemp, zWhen, bNoDQS
  );

  if( bTemp==0 ){
    sqlite3NestedParse(pParse,
        "SELECT 1 "
        "FROM temp." LEGACY_SCHEMA_TABLE " "
        "WHERE name NOT LIKE 'sqliteX_%%' ESCAPE 'X'"
        " AND sql NOT LIKE 'create virtual%%'"
        " AND sqlite_rename_test(%Q, sql, type, name, 1, %Q, %d)=NULL ",
        zDb, zWhen, bNoDQS
    );
  }
}

/*
** Generate VM code to replace any double-quoted strings (but not double-quoted
** identifiers) within the "sql" column of the sqlite_schema table in
** database zDb with their single-quoted equivalents. If argument bTemp is
** not true, similarly update all SQL statements in the sqlite_schema table
** of the temp db.
*/
static void renameFixQuotes(Parse *pParse, const char *zDb, int bTemp){
  sqlite3NestedParse(pParse,
      "UPDATE \"%w\"." LEGACY_SCHEMA_TABLE
      " SET sql = sqlite_rename_quotefix(%Q, sql)"
      "WHERE name NOT LIKE 'sqliteX_%%' ESCAPE 'X'"
      " AND sql NOT LIKE 'create virtual%%'" , zDb, zDb
  );
  if( bTemp==0 ){
    sqlite3NestedParse(pParse,
      "UPDATE temp." LEGACY_SCHEMA_TABLE
      " SET sql = sqlite_rename_quotefix('temp', sql)"
      "WHERE name NOT LIKE 'sqliteX_%%' ESCAPE 'X'"
      " AND sql NOT LIKE 'create virtual%%'"
    );
  }
}

107761
107762
107763
107764
107765
107766
107767
107768
107769
107770
107771
107772
107773
107774
107775
107776
107777
107778
107779
107780
107781
107782
107783
107784
107785
  /* figure out how many UTF-8 characters are in zName */
  zTabName = pTab->zName;
  nTabName = sqlite3Utf8CharLen(zTabName, -1);

  /* Rewrite all CREATE TABLE, INDEX, TRIGGER or VIEW statements in
  ** the schema to use the new table name.  */
  sqlite3NestedParse(pParse,
      "UPDATE \"%w\"." DFLT_SCHEMA_TABLE " SET "
      "sql = sqlite_rename_table(%Q, type, name, sql, %Q, %Q, %d) "
      "WHERE (type!='index' OR tbl_name=%Q COLLATE nocase)"
      "AND   name NOT LIKE 'sqliteX_%%' ESCAPE 'X'"
      , zDb, zDb, zTabName, zName, (iDb==1), zTabName
  );

  /* Update the tbl_name and name columns of the sqlite_schema table
  ** as required.  */
  sqlite3NestedParse(pParse,
      "UPDATE %Q." DFLT_SCHEMA_TABLE " SET "
          "tbl_name = %Q, "
          "name = CASE "
            "WHEN type='table' THEN %Q "
            "WHEN name LIKE 'sqliteX_autoindex%%' ESCAPE 'X' "
            "     AND type='index' THEN "
             "'sqlite_autoindex_' || %Q || substr(name,%d+18) "
            "ELSE name END "







|









|







108361
108362
108363
108364
108365
108366
108367
108368
108369
108370
108371
108372
108373
108374
108375
108376
108377
108378
108379
108380
108381
108382
108383
108384
108385
  /* figure out how many UTF-8 characters are in zName */
  zTabName = pTab->zName;
  nTabName = sqlite3Utf8CharLen(zTabName, -1);

  /* Rewrite all CREATE TABLE, INDEX, TRIGGER or VIEW statements in
  ** the schema to use the new table name.  */
  sqlite3NestedParse(pParse,
      "UPDATE \"%w\"." LEGACY_SCHEMA_TABLE " SET "
      "sql = sqlite_rename_table(%Q, type, name, sql, %Q, %Q, %d) "
      "WHERE (type!='index' OR tbl_name=%Q COLLATE nocase)"
      "AND   name NOT LIKE 'sqliteX_%%' ESCAPE 'X'"
      , zDb, zDb, zTabName, zName, (iDb==1), zTabName
  );

  /* Update the tbl_name and name columns of the sqlite_schema table
  ** as required.  */
  sqlite3NestedParse(pParse,
      "UPDATE %Q." LEGACY_SCHEMA_TABLE " SET "
          "tbl_name = %Q, "
          "name = CASE "
            "WHEN type='table' THEN %Q "
            "WHEN name LIKE 'sqliteX_autoindex%%' ESCAPE 'X' "
            "     AND type='index' THEN "
             "'sqlite_autoindex_' || %Q || substr(name,%d+18) "
            "ELSE name END "
107914
107915
107916
107917
107918
107919
107920

107921
107922
107923
107924
107925
107926
107927
    ** literal NULL, then set pDflt to 0. This simplifies checking
    ** for an SQL NULL default below.
    */
    assert( pDflt==0 || pDflt->op==TK_SPAN );
    if( pDflt && pDflt->pLeft->op==TK_NULL ){
      pDflt = 0;
    }

    if( (db->flags&SQLITE_ForeignKeys) && pNew->u.tab.pFKey && pDflt ){
      sqlite3ErrorIfNotEmpty(pParse, zDb, zTab,
          "Cannot add a REFERENCES column with non-NULL default value");
    }
    if( pCol->notNull && !pDflt ){
      sqlite3ErrorIfNotEmpty(pParse, zDb, zTab,
          "Cannot add a NOT NULL column with default value NULL");







>







108514
108515
108516
108517
108518
108519
108520
108521
108522
108523
108524
108525
108526
108527
108528
    ** literal NULL, then set pDflt to 0. This simplifies checking
    ** for an SQL NULL default below.
    */
    assert( pDflt==0 || pDflt->op==TK_SPAN );
    if( pDflt && pDflt->pLeft->op==TK_NULL ){
      pDflt = 0;
    }
    assert( IsOrdinaryTable(pNew) );
    if( (db->flags&SQLITE_ForeignKeys) && pNew->u.tab.pFKey && pDflt ){
      sqlite3ErrorIfNotEmpty(pParse, zDb, zTab,
          "Cannot add a REFERENCES column with non-NULL default value");
    }
    if( pCol->notNull && !pDflt ){
      sqlite3ErrorIfNotEmpty(pParse, zDb, zTab,
          "Cannot add a NOT NULL column with default value NULL");
107956
107957
107958
107959
107960
107961
107962
107963

107964
107965
107966
107967
107968
107969
107970
107971
107972
  if( zCol ){
    char *zEnd = &zCol[pColDef->n-1];
    while( zEnd>zCol && (*zEnd==';' || sqlite3Isspace(*zEnd)) ){
      *zEnd-- = '\0';
    }
    /* substr() operations on characters, but addColOffset is in bytes. So we
    ** have to use printf() to translate between these units: */
    assert( !IsVirtual(pTab) );

    sqlite3NestedParse(pParse,
        "UPDATE \"%w\"." DFLT_SCHEMA_TABLE " SET "
          "sql = printf('%%.%ds, ',sql) || %Q"
          " || substr(sql,1+length(printf('%%.%ds',sql))) "
        "WHERE type = 'table' AND name = %Q",
      zDb, pNew->u.tab.addColOffset, zCol, pNew->u.tab.addColOffset,
      zTab
    );
    sqlite3DbFree(db, zCol);







|
>

|







108557
108558
108559
108560
108561
108562
108563
108564
108565
108566
108567
108568
108569
108570
108571
108572
108573
108574
  if( zCol ){
    char *zEnd = &zCol[pColDef->n-1];
    while( zEnd>zCol && (*zEnd==';' || sqlite3Isspace(*zEnd)) ){
      *zEnd-- = '\0';
    }
    /* substr() operations on characters, but addColOffset is in bytes. So we
    ** have to use printf() to translate between these units: */
    assert( IsOrdinaryTable(pTab) );
    assert( IsOrdinaryTable(pNew) );
    sqlite3NestedParse(pParse,
        "UPDATE \"%w\"." LEGACY_SCHEMA_TABLE " SET "
          "sql = printf('%%.%ds, ',sql) || %Q"
          " || substr(sql,1+length(printf('%%.%ds',sql))) "
        "WHERE type = 'table' AND name = %Q",
      zDb, pNew->u.tab.addColOffset, zCol, pNew->u.tab.addColOffset,
      zTab
    );
    sqlite3DbFree(db, zCol);
107984
107985
107986
107987
107988
107989
107990
107991
107992
107993
107994
107995
107996
107997
107998
    sqlite3VdbeAddOp2(v, OP_AddImm, r1, -2);
    sqlite3VdbeAddOp2(v, OP_IfPos, r1, sqlite3VdbeCurrentAddr(v)+2);
    VdbeCoverage(v);
    sqlite3VdbeAddOp3(v, OP_SetCookie, iDb, BTREE_FILE_FORMAT, 3);
    sqlite3ReleaseTempReg(pParse, r1);

    /* Reload the table definition */
    renameReloadSchema(pParse, iDb, INITFLAG_AlterRename);

    /* Verify that constraints are still satisfied */
    if( pNew->pCheck!=0
     || (pCol->notNull && (pCol->colFlags & COLFLAG_GENERATED)!=0)
    ){
      sqlite3NestedParse(pParse,
        "SELECT CASE WHEN quick_check GLOB 'CHECK*'"







|







108586
108587
108588
108589
108590
108591
108592
108593
108594
108595
108596
108597
108598
108599
108600
    sqlite3VdbeAddOp2(v, OP_AddImm, r1, -2);
    sqlite3VdbeAddOp2(v, OP_IfPos, r1, sqlite3VdbeCurrentAddr(v)+2);
    VdbeCoverage(v);
    sqlite3VdbeAddOp3(v, OP_SetCookie, iDb, BTREE_FILE_FORMAT, 3);
    sqlite3ReleaseTempReg(pParse, r1);

    /* Reload the table definition */
    renameReloadSchema(pParse, iDb, INITFLAG_AlterAdd);

    /* Verify that constraints are still satisfied */
    if( pNew->pCheck!=0
     || (pCol->notNull && (pCol->colFlags & COLFLAG_GENERATED)!=0)
    ){
      sqlite3NestedParse(pParse,
        "SELECT CASE WHEN quick_check GLOB 'CHECK*'"
108050
108051
108052
108053
108054
108055
108056

108057
108058
108059
108060
108061
108062
108063
    goto exit_begin_add_column;
  }
  if( SQLITE_OK!=isAlterableTable(pParse, pTab) ){
    goto exit_begin_add_column;
  }

  sqlite3MayAbort(pParse);

  assert( pTab->u.tab.addColOffset>0 );
  iDb = sqlite3SchemaToIndex(db, pTab->pSchema);

  /* Put a copy of the Table struct in Parse.pNewTable for the
  ** sqlite3AddColumn() function and friends to modify.  But modify
  ** the name by adding an "sqlite_altertab_" prefix.  By adding this
  ** prefix, we insure that the name will not collide with an existing







>







108652
108653
108654
108655
108656
108657
108658
108659
108660
108661
108662
108663
108664
108665
108666
    goto exit_begin_add_column;
  }
  if( SQLITE_OK!=isAlterableTable(pParse, pTab) ){
    goto exit_begin_add_column;
  }

  sqlite3MayAbort(pParse);
  assert( IsOrdinaryTable(pTab) );
  assert( pTab->u.tab.addColOffset>0 );
  iDb = sqlite3SchemaToIndex(db, pTab->pSchema);

  /* Put a copy of the Table struct in Parse.pNewTable for the
  ** sqlite3AddColumn() function and friends to modify.  But modify
  ** the name by adding an "sqlite_altertab_" prefix.  By adding this
  ** prefix, we insure that the name will not collide with an existing
108080
108081
108082
108083
108084
108085
108086
108087
108088
108089
108090
108091
108092
108093
108094
  }
  memcpy(pNew->aCol, pTab->aCol, sizeof(Column)*pNew->nCol);
  for(i=0; i<pNew->nCol; i++){
    Column *pCol = &pNew->aCol[i];
    pCol->zCnName = sqlite3DbStrDup(db, pCol->zCnName);
    pCol->hName = sqlite3StrIHash(pCol->zCnName);
  }
  assert( !IsVirtual(pNew) );
  pNew->u.tab.pDfltList = sqlite3ExprListDup(db, pTab->u.tab.pDfltList, 0);
  pNew->pSchema = db->aDb[iDb].pSchema;
  pNew->u.tab.addColOffset = pTab->u.tab.addColOffset;
  pNew->nTabRef = 1;

exit_begin_add_column:
  sqlite3SrcListDelete(db, pSrc);







|







108683
108684
108685
108686
108687
108688
108689
108690
108691
108692
108693
108694
108695
108696
108697
  }
  memcpy(pNew->aCol, pTab->aCol, sizeof(Column)*pNew->nCol);
  for(i=0; i<pNew->nCol; i++){
    Column *pCol = &pNew->aCol[i];
    pCol->zCnName = sqlite3DbStrDup(db, pCol->zCnName);
    pCol->hName = sqlite3StrIHash(pCol->zCnName);
  }
  assert( IsOrdinaryTable(pNew) );
  pNew->u.tab.pDfltList = sqlite3ExprListDup(db, pTab->u.tab.pDfltList, 0);
  pNew->pSchema = db->aDb[iDb].pSchema;
  pNew->u.tab.addColOffset = pTab->u.tab.addColOffset;
  pNew->nTabRef = 1;

exit_begin_add_column:
  sqlite3SrcListDelete(db, pSrc);
108191
108192
108193
108194
108195
108196
108197
108198
108199
108200
108201
108202
108203
108204
108205
108206
108207
108208
108209
108210
108211
108212
108213
108214
108215
  */
  sqlite3MayAbort(pParse);
  zNew = sqlite3NameFromToken(db, pNew);
  if( !zNew ) goto exit_rename_column;
  assert( pNew->n>0 );
  bQuote = sqlite3Isquote(pNew->z[0]);
  sqlite3NestedParse(pParse,
      "UPDATE \"%w\"." DFLT_SCHEMA_TABLE " SET "
      "sql = sqlite_rename_column(sql, type, name, %Q, %Q, %d, %Q, %d, %d) "
      "WHERE name NOT LIKE 'sqliteX_%%' ESCAPE 'X' "
      " AND (type != 'index' OR tbl_name = %Q)",
      zDb,
      zDb, pTab->zName, iCol, zNew, bQuote, iSchema==1,
      pTab->zName
  );

  sqlite3NestedParse(pParse,
      "UPDATE temp." DFLT_SCHEMA_TABLE " SET "
      "sql = sqlite_rename_column(sql, type, name, %Q, %Q, %d, %Q, %d, 1) "
      "WHERE type IN ('trigger', 'view')",
      zDb, pTab->zName, iCol, zNew, bQuote
  );

  /* Drop and reload the database schema. */
  renameReloadSchema(pParse, iSchema, INITFLAG_AlterRename);







|









|







108794
108795
108796
108797
108798
108799
108800
108801
108802
108803
108804
108805
108806
108807
108808
108809
108810
108811
108812
108813
108814
108815
108816
108817
108818
  */
  sqlite3MayAbort(pParse);
  zNew = sqlite3NameFromToken(db, pNew);
  if( !zNew ) goto exit_rename_column;
  assert( pNew->n>0 );
  bQuote = sqlite3Isquote(pNew->z[0]);
  sqlite3NestedParse(pParse,
      "UPDATE \"%w\"." LEGACY_SCHEMA_TABLE " SET "
      "sql = sqlite_rename_column(sql, type, name, %Q, %Q, %d, %Q, %d, %d) "
      "WHERE name NOT LIKE 'sqliteX_%%' ESCAPE 'X' "
      " AND (type != 'index' OR tbl_name = %Q)",
      zDb,
      zDb, pTab->zName, iCol, zNew, bQuote, iSchema==1,
      pTab->zName
  );

  sqlite3NestedParse(pParse,
      "UPDATE temp." LEGACY_SCHEMA_TABLE " SET "
      "sql = sqlite_rename_column(sql, type, name, %Q, %Q, %d, %Q, %d, 1) "
      "WHERE type IN ('trigger', 'view')",
      zDb, pTab->zName, iCol, zNew, bQuote
  );

  /* Drop and reload the database schema. */
  renameReloadSchema(pParse, iSchema, INITFLAG_AlterRename);
108349
108350
108351
108352
108353
108354
108355

108356

108357
108358
108359
108360
108361
108362
108363

/*
** Walker callback used by sqlite3RenameExprUnmap().
*/
static int renameUnmapExprCb(Walker *pWalker, Expr *pExpr){
  Parse *pParse = pWalker->pParse;
  sqlite3RenameTokenRemap(pParse, 0, (const void*)pExpr);

  sqlite3RenameTokenRemap(pParse, 0, (const void*)&pExpr->y.pTab);

  return WRC_Continue;
}

/*
** Iterate through the Select objects that are part of WITH clauses attached
** to select statement pSelect.
*/







>
|
>







108952
108953
108954
108955
108956
108957
108958
108959
108960
108961
108962
108963
108964
108965
108966
108967
108968

/*
** Walker callback used by sqlite3RenameExprUnmap().
*/
static int renameUnmapExprCb(Walker *pWalker, Expr *pExpr){
  Parse *pParse = pWalker->pParse;
  sqlite3RenameTokenRemap(pParse, 0, (const void*)pExpr);
  if( ExprUseYTab(pExpr) ){
    sqlite3RenameTokenRemap(pParse, 0, (const void*)&pExpr->y.pTab);
  }
  return WRC_Continue;
}

/*
** Iterate through the Select objects that are part of WITH clauses attached
** to select statement pSelect.
*/
108411
108412
108413
108414
108415
108416
108417


108418
108419
108420
108421
108422
108423
108424
108425
/*
** Walker callback used by sqlite3RenameExprUnmap().
*/
static int renameUnmapSelectCb(Walker *pWalker, Select *p){
  Parse *pParse = pWalker->pParse;
  int i;
  if( pParse->nErr ) return WRC_Abort;


  if( NEVER(p->selFlags & (SF_View|SF_CopyCte)) ){
    return WRC_Prune;
  }
  if( ALWAYS(p->pEList) ){
    ExprList *pList = p->pEList;
    for(i=0; i<pList->nExpr; i++){
      if( pList->a[i].zEName && pList->a[i].eEName==ENAME_NAME ){
        sqlite3RenameTokenRemap(pParse, 0, (void*)pList->a[i].zEName);







>
>
|







109016
109017
109018
109019
109020
109021
109022
109023
109024
109025
109026
109027
109028
109029
109030
109031
109032
/*
** Walker callback used by sqlite3RenameExprUnmap().
*/
static int renameUnmapSelectCb(Walker *pWalker, Select *p){
  Parse *pParse = pWalker->pParse;
  int i;
  if( pParse->nErr ) return WRC_Abort;
  testcase( p->selFlags & SF_View );
  testcase( p->selFlags & SF_CopyCte );
  if( p->selFlags & (SF_View|SF_CopyCte) ){
    return WRC_Prune;
  }
  if( ALWAYS(p->pEList) ){
    ExprList *pList = p->pEList;
    for(i=0; i<pList->nExpr; i++){
      if( pList->a[i].zEName && pList->a[i].eEName==ENAME_NAME ){
        sqlite3RenameTokenRemap(pParse, 0, (void*)pList->a[i].zEName);
108548
108549
108550
108551
108552
108553
108554

108555
108556
108557
108558
108559
108560
108561
  if( pExpr->op==TK_TRIGGER
   && pExpr->iColumn==p->iCol
   && pWalker->pParse->pTriggerTab==p->pTab
  ){
    renameTokenFind(pWalker->pParse, p, (void*)pExpr);
  }else if( pExpr->op==TK_COLUMN
   && pExpr->iColumn==p->iCol

   && p->pTab==pExpr->y.pTab
  ){
    renameTokenFind(pWalker->pParse, p, (void*)pExpr);
  }
  return WRC_Continue;
}








>







109155
109156
109157
109158
109159
109160
109161
109162
109163
109164
109165
109166
109167
109168
109169
  if( pExpr->op==TK_TRIGGER
   && pExpr->iColumn==p->iCol
   && pWalker->pParse->pTriggerTab==p->pTab
  ){
    renameTokenFind(pWalker->pParse, p, (void*)pExpr);
  }else if( pExpr->op==TK_COLUMN
   && pExpr->iColumn==p->iCol
   && ALWAYS(ExprUseYTab(pExpr))
   && p->pTab==pExpr->y.pTab
  ){
    renameTokenFind(pWalker->pParse, p, (void*)pExpr);
  }
  return WRC_Continue;
}

108872
108873
108874
108875
108876
108877
108878



108879
108880
108881
108882
108883
108884
108885
              rc = SQLITE_ERROR;
            }else{
              p->pTab->nTabRef++;
              rc = sqlite3ViewGetColumnNames(pParse, p->pTab);
            }
          }
        }



        sNC.pSrcList = pSrc;
        if( rc==SQLITE_OK && pStep->pWhere ){
          rc = sqlite3ResolveExprNames(&sNC, pStep->pWhere);
        }
        if( rc==SQLITE_OK ){
          rc = sqlite3ResolveExprListNames(&sNC, pStep->pExprList);
        }







>
>
>







109480
109481
109482
109483
109484
109485
109486
109487
109488
109489
109490
109491
109492
109493
109494
109495
109496
              rc = SQLITE_ERROR;
            }else{
              p->pTab->nTabRef++;
              rc = sqlite3ViewGetColumnNames(pParse, p->pTab);
            }
          }
        }
        if( rc==SQLITE_OK && db->mallocFailed ){
          rc = SQLITE_NOMEM;
        }
        sNC.pSrcList = pSrc;
        if( rc==SQLITE_OK && pStep->pWhere ){
          rc = sqlite3ResolveExprNames(&sNC, pStep->pWhere);
        }
        if( rc==SQLITE_OK ){
          rc = sqlite3ResolveExprListNames(&sNC, pStep->pExprList);
        }
109078
109079
109080
109081
109082
109083
109084
109085
109086
109087
109088
109089
109090
109091
109092
          Expr *pExpr = sqlite3ColumnExpr(sParse.pNewTable,
                                                  &sParse.pNewTable->aCol[i]);
          sqlite3WalkExpr(&sWalker, pExpr);
        }
#endif
      }

      assert( !IsVirtual(sParse.pNewTable) );
      for(pFKey=sParse.pNewTable->u.tab.pFKey; pFKey; pFKey=pFKey->pNextFrom){
        for(i=0; i<pFKey->nCol; i++){
          if( bFKOnly==0 && pFKey->aCol[i].iFrom==iCol ){
            renameTokenFind(&sParse, &sCtx, (void*)&pFKey->aCol[i]);
          }
          if( 0==sqlite3_stricmp(pFKey->zTo, zTable)
           && 0==sqlite3_stricmp(pFKey->aCol[i].zCol, zOld)







|







109689
109690
109691
109692
109693
109694
109695
109696
109697
109698
109699
109700
109701
109702
109703
          Expr *pExpr = sqlite3ColumnExpr(sParse.pNewTable,
                                                  &sParse.pNewTable->aCol[i]);
          sqlite3WalkExpr(&sWalker, pExpr);
        }
#endif
      }

      assert( IsOrdinaryTable(sParse.pNewTable) );
      for(pFKey=sParse.pNewTable->u.tab.pFKey; pFKey; pFKey=pFKey->pNextFrom){
        for(i=0; i<pFKey->nCol; i++){
          if( bFKOnly==0 && pFKey->aCol[i].iFrom==iCol ){
            renameTokenFind(&sParse, &sCtx, (void*)&pFKey->aCol[i]);
          }
          if( 0==sqlite3_stricmp(pFKey->zTo, zTable)
           && 0==sqlite3_stricmp(pFKey->aCol[i].zCol, zOld)
109150
109151
109152
109153
109154
109155
109156
109157



109158
109159
109160
109161
109162
109163
109164
}

/*
** Walker expression callback used by "RENAME TABLE".
*/
static int renameTableExprCb(Walker *pWalker, Expr *pExpr){
  RenameCtx *p = pWalker->u.pRename;
  if( pExpr->op==TK_COLUMN && p->pTab==pExpr->y.pTab ){



    renameTokenFind(pWalker->pParse, p, (void*)&pExpr->y.pTab);
  }
  return WRC_Continue;
}

/*
** Walker select callback used by "RENAME TABLE".







|
>
>
>







109761
109762
109763
109764
109765
109766
109767
109768
109769
109770
109771
109772
109773
109774
109775
109776
109777
109778
}

/*
** Walker expression callback used by "RENAME TABLE".
*/
static int renameTableExprCb(Walker *pWalker, Expr *pExpr){
  RenameCtx *p = pWalker->u.pRename;
  if( pExpr->op==TK_COLUMN
   && ALWAYS(ExprUseYTab(pExpr))
   && p->pTab==pExpr->y.pTab
  ){
    renameTokenFind(pWalker->pParse, p, (void*)&pExpr->y.pTab);
  }
  return WRC_Continue;
}

/*
** Walker select callback used by "RENAME TABLE".
109268
109269
109270
109271
109272
109273
109274
109275
109276
109277
109278
109279
109280
109281
109282
        }else{
          /* Modify any FK definitions to point to the new table. */
#ifndef SQLITE_OMIT_FOREIGN_KEY
          if( (isLegacy==0 || (db->flags & SQLITE_ForeignKeys))
           && !IsVirtual(pTab)
          ){
            FKey *pFKey;
            assert( !IsVirtual(pTab) );
            for(pFKey=pTab->u.tab.pFKey; pFKey; pFKey=pFKey->pNextFrom){
              if( sqlite3_stricmp(pFKey->zTo, zOld)==0 ){
                renameTokenFind(&sParse, &sCtx, (void*)pFKey->zTo);
              }
            }
          }
#endif







|







109882
109883
109884
109885
109886
109887
109888
109889
109890
109891
109892
109893
109894
109895
109896
        }else{
          /* Modify any FK definitions to point to the new table. */
#ifndef SQLITE_OMIT_FOREIGN_KEY
          if( (isLegacy==0 || (db->flags & SQLITE_ForeignKeys))
           && !IsVirtual(pTab)
          ){
            FKey *pFKey;
            assert( IsOrdinaryTable(pTab) );
            for(pFKey=pTab->u.tab.pFKey; pFKey; pFKey=pFKey->pNextFrom){
              if( sqlite3_stricmp(pFKey->zTo, zOld)==0 ){
                renameTokenFind(&sParse, &sCtx, (void*)pFKey->zTo);
              }
            }
          }
#endif
109589
109590
109591
109592
109593
109594
109595
109596
109597
109598
109599
109600
109601
109602
109603

  pCol = renameTokenFind(&sParse, 0, (void*)pTab->aCol[iCol].zCnName);
  if( iCol<pTab->nCol-1 ){
    RenameToken *pEnd;
    pEnd = renameTokenFind(&sParse, 0, (void*)pTab->aCol[iCol+1].zCnName);
    zEnd = (const char*)pEnd->t.z;
  }else{
    assert( !IsVirtual(pTab) );
    zEnd = (const char*)&zSql[pTab->u.tab.addColOffset];
    while( ALWAYS(pCol->t.z[0]!=0) && pCol->t.z[0]!=',' ) pCol->t.z--;
  }

  zNew = sqlite3MPrintf(db, "%.*s%s", pCol->t.z-zSql, zSql, zEnd);
  sqlite3_result_text(context, zNew, -1, SQLITE_TRANSIENT);
  sqlite3_free(zNew);







|







110203
110204
110205
110206
110207
110208
110209
110210
110211
110212
110213
110214
110215
110216
110217

  pCol = renameTokenFind(&sParse, 0, (void*)pTab->aCol[iCol].zCnName);
  if( iCol<pTab->nCol-1 ){
    RenameToken *pEnd;
    pEnd = renameTokenFind(&sParse, 0, (void*)pTab->aCol[iCol+1].zCnName);
    zEnd = (const char*)pEnd->t.z;
  }else{
    assert( IsOrdinaryTable(pTab) );
    zEnd = (const char*)&zSql[pTab->u.tab.addColOffset];
    while( ALWAYS(pCol->t.z[0]!=0) && pCol->t.z[0]!=',' ) pCol->t.z--;
  }

  zNew = sqlite3MPrintf(db, "%.*s%s", pCol->t.z-zSql, zSql, zEnd);
  sqlite3_result_text(context, zNew, -1, SQLITE_TRANSIENT);
  sqlite3_free(zNew);
109671
109672
109673
109674
109675
109676
109677
109678
109679
109680
109681
109682
109683
109684
109685
  /* Edit the sqlite_schema table */
  iDb = sqlite3SchemaToIndex(db, pTab->pSchema);
  assert( iDb>=0 );
  zDb = db->aDb[iDb].zDbSName;
  renameTestSchema(pParse, zDb, iDb==1, "", 0);
  renameFixQuotes(pParse, zDb, iDb==1);
  sqlite3NestedParse(pParse,
      "UPDATE \"%w\"." DFLT_SCHEMA_TABLE " SET "
      "sql = sqlite_drop_column(%d, sql, %d) "
      "WHERE (type=='table' AND tbl_name=%Q COLLATE nocase)"
      , zDb, iDb, iCol, pTab->zName
  );

  /* Drop and reload the database schema. */
  renameReloadSchema(pParse, iDb, INITFLAG_AlterDrop);







|







110285
110286
110287
110288
110289
110290
110291
110292
110293
110294
110295
110296
110297
110298
110299
  /* Edit the sqlite_schema table */
  iDb = sqlite3SchemaToIndex(db, pTab->pSchema);
  assert( iDb>=0 );
  zDb = db->aDb[iDb].zDbSName;
  renameTestSchema(pParse, zDb, iDb==1, "", 0);
  renameFixQuotes(pParse, zDb, iDb==1);
  sqlite3NestedParse(pParse,
      "UPDATE \"%w\"." LEGACY_SCHEMA_TABLE " SET "
      "sql = sqlite_drop_column(%d, sql, %d) "
      "WHERE (type=='table' AND tbl_name=%Q COLLATE nocase)"
      , zDb, iDb, iCol, pTab->zName
  );

  /* Drop and reload the database schema. */
  renameReloadSchema(pParse, iDb, INITFLAG_AlterDrop);
110764
110765
110766
110767
110768
110769
110770
110771
110772
110773
110774
110775
110776
110777
110778
#endif

  pParse->nMem = MAX(pParse->nMem, iMem);
  v = sqlite3GetVdbe(pParse);
  if( v==0 || NEVER(pTab==0) ){
    return;
  }
  if( pTab->tnum==0 ){
    /* Do not gather statistics on views or virtual tables */
    return;
  }
  if( sqlite3_strlike("sqlite\\_%", pTab->zName, '\\')==0 ){
    /* Do not gather statistics on system tables */
    return;
  }







|







111378
111379
111380
111381
111382
111383
111384
111385
111386
111387
111388
111389
111390
111391
111392
#endif

  pParse->nMem = MAX(pParse->nMem, iMem);
  v = sqlite3GetVdbe(pParse);
  if( v==0 || NEVER(pTab==0) ){
    return;
  }
  if( !IsOrdinaryTable(pTab) ){
    /* Do not gather statistics on views or virtual tables */
    return;
  }
  if( sqlite3_strlike("sqlite\\_%", pTab->zName, '\\')==0 ){
    /* Do not gather statistics on system tables */
    return;
  }
112047
112048
112049
112050
112051
112052
112053
112054
112055
112056
112057
112058
112059
112060
112061
112062
112063
112064

112065
112066
112067
112068
112069
112070
112071
  int regArgs;

  if( pParse->nErr ) goto attach_end;
  memset(&sName, 0, sizeof(NameContext));
  sName.pParse = pParse;

  if(
      SQLITE_OK!=(rc = resolveAttachExpr(&sName, pFilename)) ||
      SQLITE_OK!=(rc = resolveAttachExpr(&sName, pDbname)) ||
      SQLITE_OK!=(rc = resolveAttachExpr(&sName, pKey))
  ){
    goto attach_end;
  }

#ifndef SQLITE_OMIT_AUTHORIZATION
  if( pAuthArg ){
    char *zAuthArg;
    if( pAuthArg->op==TK_STRING ){

      zAuthArg = pAuthArg->u.zToken;
    }else{
      zAuthArg = 0;
    }
    rc = sqlite3AuthCheck(pParse, type, zAuthArg, 0, 0);
    if(rc!=SQLITE_OK ){
      goto attach_end;







|
|
|








>







112661
112662
112663
112664
112665
112666
112667
112668
112669
112670
112671
112672
112673
112674
112675
112676
112677
112678
112679
112680
112681
112682
112683
112684
112685
112686
  int regArgs;

  if( pParse->nErr ) goto attach_end;
  memset(&sName, 0, sizeof(NameContext));
  sName.pParse = pParse;

  if(
      SQLITE_OK!=resolveAttachExpr(&sName, pFilename) ||
      SQLITE_OK!=resolveAttachExpr(&sName, pDbname) ||
      SQLITE_OK!=resolveAttachExpr(&sName, pKey)
  ){
    goto attach_end;
  }

#ifndef SQLITE_OMIT_AUTHORIZATION
  if( pAuthArg ){
    char *zAuthArg;
    if( pAuthArg->op==TK_STRING ){
      assert( !ExprHasProperty(pAuthArg, EP_IntValue) );
      zAuthArg = pAuthArg->u.zToken;
    }else{
      zAuthArg = 0;
    }
    rc = sqlite3AuthCheck(pParse, type, zAuthArg, 0, 0);
    if(rc!=SQLITE_OK ){
      goto attach_end;
112742
112743
112744
112745
112746
112747
112748




112749
112750
112751
112752
112753
112754
112755
112756
112757
112758
112759

112760
112761
112762
112763
112764
112765
112766
  if( v ){
    if( pParse->bReturning ){
      Returning *pReturning = pParse->u1.pReturning;
      int addrRewind;
      int i;
      int reg;





      addrRewind =
         sqlite3VdbeAddOp1(v, OP_Rewind, pReturning->iRetCur);
      VdbeCoverage(v);
      reg = pReturning->iRetReg;
      for(i=0; i<pReturning->nRetCol; i++){
        sqlite3VdbeAddOp3(v, OP_Column, pReturning->iRetCur, i, reg+i);
      }
      sqlite3VdbeAddOp2(v, OP_ResultRow, reg, i);
      sqlite3VdbeAddOp2(v, OP_Next, pReturning->iRetCur, addrRewind+1);
      VdbeCoverage(v);
      sqlite3VdbeJumpHere(v, addrRewind);

    }
    sqlite3VdbeAddOp0(v, OP_Halt);

#if SQLITE_USER_AUTHENTICATION
    if( pParse->nTableLock>0 && db->init.busy==0 ){
      sqlite3UserAuthInit(db);
      if( db->auth.authLevel<UAUTH_User ){







>
>
>
>
|
|
|
|
|
|
|
|
|
|
|
>







113357
113358
113359
113360
113361
113362
113363
113364
113365
113366
113367
113368
113369
113370
113371
113372
113373
113374
113375
113376
113377
113378
113379
113380
113381
113382
113383
113384
113385
113386
  if( v ){
    if( pParse->bReturning ){
      Returning *pReturning = pParse->u1.pReturning;
      int addrRewind;
      int i;
      int reg;

      if( pReturning->nRetCol==0 ){
        assert( CORRUPT_DB );
      }else{
        sqlite3VdbeAddOp0(v, OP_FkCheck);
        addrRewind =
           sqlite3VdbeAddOp1(v, OP_Rewind, pReturning->iRetCur);
        VdbeCoverage(v);
        reg = pReturning->iRetReg;
        for(i=0; i<pReturning->nRetCol; i++){
          sqlite3VdbeAddOp3(v, OP_Column, pReturning->iRetCur, i, reg+i);
        }
        sqlite3VdbeAddOp2(v, OP_ResultRow, reg, i);
        sqlite3VdbeAddOp2(v, OP_Next, pReturning->iRetCur, addrRewind+1);
        VdbeCoverage(v);
        sqlite3VdbeJumpHere(v, addrRewind);
      }
    }
    sqlite3VdbeAddOp0(v, OP_Halt);

#if SQLITE_USER_AUTHENTICATION
    if( pParse->nTableLock>0 && db->init.busy==0 ){
      sqlite3UserAuthInit(db);
      if( db->auth.authLevel<UAUTH_User ){
112833
112834
112835
112836
112837
112838
112839



112840

112841
112842
112843
112844
112845
112846
112847
            sqlite3ExprCode(pParse, pEL->a[i].pExpr, iReg);
          }
        }
      }

      if( pParse->bReturning ){
        Returning *pRet = pParse->u1.pReturning;



        sqlite3VdbeAddOp2(v, OP_OpenEphemeral, pRet->iRetCur, pRet->nRetCol);

      }

      /* Finally, jump back to the beginning of the executable code. */
      sqlite3VdbeGoto(v, 1);
    }
  }








>
>
>
|
>







113453
113454
113455
113456
113457
113458
113459
113460
113461
113462
113463
113464
113465
113466
113467
113468
113469
113470
113471
            sqlite3ExprCode(pParse, pEL->a[i].pExpr, iReg);
          }
        }
      }

      if( pParse->bReturning ){
        Returning *pRet = pParse->u1.pReturning;
        if( pRet->nRetCol==0 ){
          assert( CORRUPT_DB );
        }else{
          sqlite3VdbeAddOp2(v, OP_OpenEphemeral, pRet->iRetCur, pRet->nRetCol);
        }
      }

      /* Finally, jump back to the beginning of the executable code. */
      sqlite3VdbeGoto(v, 1);
    }
  }

112951
112952
112953
112954
112955
112956
112957
112958
112959
112960
112961
112962
112963
112964
112965
112966
112967
112968
112969
112970
112971
112972
112973
112974
112975
112976
112977
112978
112979
112980
112981
112982
112983
112984
112985
112986
112987
112988
112989
112990
112991
112992
112993
112994
112995
112996
112997
      }else{
        return 0;
      }
    }
    p = sqlite3HashFind(&db->aDb[i].pSchema->tblHash, zName);
    if( p==0 && sqlite3StrNICmp(zName, "sqlite_", 7)==0 ){
      if( i==1 ){
        if( sqlite3StrICmp(zName+7, &ALT_TEMP_SCHEMA_TABLE[7])==0
         || sqlite3StrICmp(zName+7, &ALT_SCHEMA_TABLE[7])==0
         || sqlite3StrICmp(zName+7, &DFLT_SCHEMA_TABLE[7])==0
        ){
          p = sqlite3HashFind(&db->aDb[1].pSchema->tblHash,
                              DFLT_TEMP_SCHEMA_TABLE);
        }
      }else{
        if( sqlite3StrICmp(zName+7, &ALT_SCHEMA_TABLE[7])==0 ){
          p = sqlite3HashFind(&db->aDb[i].pSchema->tblHash,
                              DFLT_SCHEMA_TABLE);
        }
      }
    }
  }else{
    /* Match against TEMP first */
    p = sqlite3HashFind(&db->aDb[1].pSchema->tblHash, zName);
    if( p ) return p;
    /* The main database is second */
    p = sqlite3HashFind(&db->aDb[0].pSchema->tblHash, zName);
    if( p ) return p;
    /* Attached databases are in order of attachment */
    for(i=2; i<db->nDb; i++){
      assert( sqlite3SchemaMutexHeld(db, i, 0) );
      p = sqlite3HashFind(&db->aDb[i].pSchema->tblHash, zName);
      if( p ) break;
    }
    if( p==0 && sqlite3StrNICmp(zName, "sqlite_", 7)==0 ){
      if( sqlite3StrICmp(zName+7, &ALT_SCHEMA_TABLE[7])==0 ){
        p = sqlite3HashFind(&db->aDb[0].pSchema->tblHash, DFLT_SCHEMA_TABLE);
      }else if( sqlite3StrICmp(zName+7, &ALT_TEMP_SCHEMA_TABLE[7])==0 ){
        p = sqlite3HashFind(&db->aDb[1].pSchema->tblHash,
                            DFLT_TEMP_SCHEMA_TABLE);
      }
    }
  }
  return p;
}

/*







|
|
|


|


|

|

















|
|
|

|







113575
113576
113577
113578
113579
113580
113581
113582
113583
113584
113585
113586
113587
113588
113589
113590
113591
113592
113593
113594
113595
113596
113597
113598
113599
113600
113601
113602
113603
113604
113605
113606
113607
113608
113609
113610
113611
113612
113613
113614
113615
113616
113617
113618
113619
113620
113621
      }else{
        return 0;
      }
    }
    p = sqlite3HashFind(&db->aDb[i].pSchema->tblHash, zName);
    if( p==0 && sqlite3StrNICmp(zName, "sqlite_", 7)==0 ){
      if( i==1 ){
        if( sqlite3StrICmp(zName+7, &PREFERRED_TEMP_SCHEMA_TABLE[7])==0
         || sqlite3StrICmp(zName+7, &PREFERRED_SCHEMA_TABLE[7])==0
         || sqlite3StrICmp(zName+7, &LEGACY_SCHEMA_TABLE[7])==0
        ){
          p = sqlite3HashFind(&db->aDb[1].pSchema->tblHash,
                              LEGACY_TEMP_SCHEMA_TABLE);
        }
      }else{
        if( sqlite3StrICmp(zName+7, &PREFERRED_SCHEMA_TABLE[7])==0 ){
          p = sqlite3HashFind(&db->aDb[i].pSchema->tblHash,
                              LEGACY_SCHEMA_TABLE);
        }
      }
    }
  }else{
    /* Match against TEMP first */
    p = sqlite3HashFind(&db->aDb[1].pSchema->tblHash, zName);
    if( p ) return p;
    /* The main database is second */
    p = sqlite3HashFind(&db->aDb[0].pSchema->tblHash, zName);
    if( p ) return p;
    /* Attached databases are in order of attachment */
    for(i=2; i<db->nDb; i++){
      assert( sqlite3SchemaMutexHeld(db, i, 0) );
      p = sqlite3HashFind(&db->aDb[i].pSchema->tblHash, zName);
      if( p ) break;
    }
    if( p==0 && sqlite3StrNICmp(zName, "sqlite_", 7)==0 ){
      if( sqlite3StrICmp(zName+7, &PREFERRED_SCHEMA_TABLE[7])==0 ){
        p = sqlite3HashFind(&db->aDb[0].pSchema->tblHash, LEGACY_SCHEMA_TABLE);
      }else if( sqlite3StrICmp(zName+7, &PREFERRED_TEMP_SCHEMA_TABLE[7])==0 ){
        p = sqlite3HashFind(&db->aDb[1].pSchema->tblHash,
                            LEGACY_TEMP_SCHEMA_TABLE);
      }
    }
  }
  return p;
}

/*
113078
113079
113080
113081
113082
113083
113084
















113085
113086
113087
113088
113089
113090
113091
    int iDb = sqlite3SchemaToIndex(pParse->db, p->pSchema);
    zDb = pParse->db->aDb[iDb].zDbSName;
  }else{
    zDb = p->zDatabase;
  }
  return sqlite3LocateTable(pParse, flags, p->zName, zDb);
}

















/*
** Locate the in-memory structure that describes
** a particular index given the name of that index
** and the name of the database that contains the index.
** Return NULL if not found.
**







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







113702
113703
113704
113705
113706
113707
113708
113709
113710
113711
113712
113713
113714
113715
113716
113717
113718
113719
113720
113721
113722
113723
113724
113725
113726
113727
113728
113729
113730
113731
    int iDb = sqlite3SchemaToIndex(pParse->db, p->pSchema);
    zDb = pParse->db->aDb[iDb].zDbSName;
  }else{
    zDb = p->zDatabase;
  }
  return sqlite3LocateTable(pParse, flags, p->zName, zDb);
}

/*
** Return the preferred table name for system tables.  Translate legacy
** names into the new preferred names, as appropriate.
*/
SQLITE_PRIVATE const char *sqlite3PreferredTableName(const char *zName){
  if( sqlite3StrNICmp(zName, "sqlite_", 7)==0 ){
    if( sqlite3StrICmp(zName+7, &LEGACY_SCHEMA_TABLE[7])==0 ){
      return PREFERRED_SCHEMA_TABLE;
    }
    if( sqlite3StrICmp(zName+7, &LEGACY_TEMP_SCHEMA_TABLE[7])==0 ){
      return PREFERRED_TEMP_SCHEMA_TABLE;
    }
  }
  return zName;
}

/*
** Locate the in-memory structure that describes
** a particular index given the name of that index
** and the name of the database that contains the index.
** Return NULL if not found.
**
113255
113256
113257
113258
113259
113260
113261
113262
113263
113264
113265
113266
113267
113268
113269
113270
113271
113272
113273
113274
113275
113276
113277
113278
113279
113280
113281
113282
113283
113284
113285
113286
113287
113288
113289
113290
113291
113292
113293
113294
113295
113296
113297
113298
113299
113300
113301
113302
113303
113304
113305
SQLITE_PRIVATE void sqlite3ColumnSetExpr(
  Parse *pParse,    /* Parsing context */
  Table *pTab,      /* The table containing the column */
  Column *pCol,     /* The column to receive the new DEFAULT expression */
  Expr *pExpr       /* The new default expression */
){
  ExprList *pList;
  assert( !IsVirtual(pTab) );
  pList = pTab->u.tab.pDfltList;
  if( pCol->iDflt==0
   || NEVER(pList==0)
   || NEVER(pList->nExpr<pCol->iDflt)
  ){
    pCol->iDflt = pList==0 ? 1 : pList->nExpr+1;
    pTab->u.tab.pDfltList = sqlite3ExprListAppend(pParse, pList, pExpr);
  }else{
    sqlite3ExprDelete(pParse->db, pList->a[pCol->iDflt-1].pExpr);
    pList->a[pCol->iDflt-1].pExpr = pExpr;
  }
}

/*
** Return the expression associated with a column.  The expression might be
** the DEFAULT clause or the AS clause of a generated column.
** Return NULL if the column has no associated expression.
*/
SQLITE_PRIVATE Expr *sqlite3ColumnExpr(Table *pTab, Column *pCol){
  if( pCol->iDflt==0 ) return 0;
  if( NEVER(IsVirtual(pTab)) ) return 0;
  if( NEVER(pTab->u.tab.pDfltList==0) ) return 0;
  if( NEVER(pTab->u.tab.pDfltList->nExpr<pCol->iDflt) ) return 0;
  return pTab->u.tab.pDfltList->a[pCol->iDflt-1].pExpr;
}

/*
** Set the collating sequence name for a column.
*/
SQLITE_PRIVATE void sqlite3ColumnSetColl(
  sqlite3 *db,
  Column *pCol,
  const char *zColl
){
  int nColl;
  int n;
  char *zNew;
  assert( zColl!=0 );
  n = sqlite3Strlen30(pCol->zCnName) + 1;
  if( pCol->colFlags & COLFLAG_HASTYPE ){
    n += sqlite3Strlen30(pCol->zCnName+n) + 1;
  }
  nColl = sqlite3Strlen30(zColl) + 1;







|




















|













|
|







113895
113896
113897
113898
113899
113900
113901
113902
113903
113904
113905
113906
113907
113908
113909
113910
113911
113912
113913
113914
113915
113916
113917
113918
113919
113920
113921
113922
113923
113924
113925
113926
113927
113928
113929
113930
113931
113932
113933
113934
113935
113936
113937
113938
113939
113940
113941
113942
113943
113944
113945
SQLITE_PRIVATE void sqlite3ColumnSetExpr(
  Parse *pParse,    /* Parsing context */
  Table *pTab,      /* The table containing the column */
  Column *pCol,     /* The column to receive the new DEFAULT expression */
  Expr *pExpr       /* The new default expression */
){
  ExprList *pList;
  assert( IsOrdinaryTable(pTab) );
  pList = pTab->u.tab.pDfltList;
  if( pCol->iDflt==0
   || NEVER(pList==0)
   || NEVER(pList->nExpr<pCol->iDflt)
  ){
    pCol->iDflt = pList==0 ? 1 : pList->nExpr+1;
    pTab->u.tab.pDfltList = sqlite3ExprListAppend(pParse, pList, pExpr);
  }else{
    sqlite3ExprDelete(pParse->db, pList->a[pCol->iDflt-1].pExpr);
    pList->a[pCol->iDflt-1].pExpr = pExpr;
  }
}

/*
** Return the expression associated with a column.  The expression might be
** the DEFAULT clause or the AS clause of a generated column.
** Return NULL if the column has no associated expression.
*/
SQLITE_PRIVATE Expr *sqlite3ColumnExpr(Table *pTab, Column *pCol){
  if( pCol->iDflt==0 ) return 0;
  if( NEVER(!IsOrdinaryTable(pTab)) ) return 0;
  if( NEVER(pTab->u.tab.pDfltList==0) ) return 0;
  if( NEVER(pTab->u.tab.pDfltList->nExpr<pCol->iDflt) ) return 0;
  return pTab->u.tab.pDfltList->a[pCol->iDflt-1].pExpr;
}

/*
** Set the collating sequence name for a column.
*/
SQLITE_PRIVATE void sqlite3ColumnSetColl(
  sqlite3 *db,
  Column *pCol,
  const char *zColl
){
  i64 nColl;
  i64 n;
  char *zNew;
  assert( zColl!=0 );
  n = sqlite3Strlen30(pCol->zCnName) + 1;
  if( pCol->colFlags & COLFLAG_HASTYPE ){
    n += sqlite3Strlen30(pCol->zCnName+n) + 1;
  }
  nColl = sqlite3Strlen30(zColl) + 1;
113335
113336
113337
113338
113339
113340
113341
113342
113343
113344
113345
113346
113347
113348
113349
113350
113351
113352
113353
113354
113355
  assert( pTable!=0 );
  if( (pCol = pTable->aCol)!=0 ){
    for(i=0; i<pTable->nCol; i++, pCol++){
      assert( pCol->zCnName==0 || pCol->hName==sqlite3StrIHash(pCol->zCnName) );
      sqlite3DbFree(db, pCol->zCnName);
    }
    sqlite3DbFree(db, pTable->aCol);
    if( !IsVirtual(pTable) ){
      sqlite3ExprListDelete(db, pTable->u.tab.pDfltList);
    }
    if( db==0 || db->pnBytesFreed==0 ){
      pTable->aCol = 0;
      pTable->nCol = 0;
      if( !IsVirtual(pTable) ){
        pTable->u.tab.pDfltList = 0;
      }
    }
  }
}

/*







|





|







113975
113976
113977
113978
113979
113980
113981
113982
113983
113984
113985
113986
113987
113988
113989
113990
113991
113992
113993
113994
113995
  assert( pTable!=0 );
  if( (pCol = pTable->aCol)!=0 ){
    for(i=0; i<pTable->nCol; i++, pCol++){
      assert( pCol->zCnName==0 || pCol->hName==sqlite3StrIHash(pCol->zCnName) );
      sqlite3DbFree(db, pCol->zCnName);
    }
    sqlite3DbFree(db, pTable->aCol);
    if( IsOrdinaryTable(pTable) ){
      sqlite3ExprListDelete(db, pTable->u.tab.pDfltList);
    }
    if( db==0 || db->pnBytesFreed==0 ){
      pTable->aCol = 0;
      pTable->nCol = 0;
      if( IsOrdinaryTable(pTable) ){
        pTable->u.tab.pDfltList = 0;
      }
    }
  }
}

/*
113477
113478
113479
113480
113481
113482
113483
113484
113485
113486
113487
113488
113489
113490
113491

/*
** Open the sqlite_schema table stored in database number iDb for
** writing. The table is opened using cursor 0.
*/
SQLITE_PRIVATE void sqlite3OpenSchemaTable(Parse *p, int iDb){
  Vdbe *v = sqlite3GetVdbe(p);
  sqlite3TableLock(p, iDb, SCHEMA_ROOT, 1, DFLT_SCHEMA_TABLE);
  sqlite3VdbeAddOp4Int(v, OP_OpenWrite, 0, SCHEMA_ROOT, iDb, 5);
  if( p->nTab==0 ){
    p->nTab = 1;
  }
}

/*







|







114117
114118
114119
114120
114121
114122
114123
114124
114125
114126
114127
114128
114129
114130
114131

/*
** Open the sqlite_schema table stored in database number iDb for
** writing. The table is opened using cursor 0.
*/
SQLITE_PRIVATE void sqlite3OpenSchemaTable(Parse *p, int iDb){
  Vdbe *v = sqlite3GetVdbe(p);
  sqlite3TableLock(p, iDb, SCHEMA_ROOT, 1, LEGACY_SCHEMA_TABLE);
  sqlite3VdbeAddOp4Int(v, OP_OpenWrite, 0, SCHEMA_ROOT, iDb, 5);
  if( p->nTab==0 ){
    p->nTab = 1;
  }
}

/*
114096
114097
114098
114099
114100
114101
114102
114103
114104
114105
114106
114107
114108
114109
114110
114111
114112
114113
114114
114115
114116
114117
114118
114119
114120
114121
114122
114123
114124
         affinity = sqlite3StdTypeAffinity[i];
         if( affinity<=SQLITE_AFF_TEXT ) szEst = 5;
         break;
       }
    }
  }

  z = sqlite3DbMallocRaw(db, sName.n + 1 + sType.n + (sType.n>0) );
  if( z==0 ) return;
  if( IN_RENAME_OBJECT ) sqlite3RenameTokenMap(pParse, (void*)z, &sName);
  memcpy(z, sName.z, sName.n);
  z[sName.n] = 0;
  sqlite3Dequote(z);
  hName = sqlite3StrIHash(z);
  for(i=0; i<p->nCol; i++){
    if( p->aCol[i].hName==hName && sqlite3StrICmp(z, p->aCol[i].zCnName)==0 ){
      sqlite3ErrorMsg(pParse, "duplicate column name: %s", z);
      sqlite3DbFree(db, z);
      return;
    }
  }
  aNew = sqlite3DbRealloc(db,p->aCol,(p->nCol+1)*sizeof(p->aCol[0]));
  if( aNew==0 ){
    sqlite3DbFree(db, z);
    return;
  }
  p->aCol = aNew;
  pCol = &p->aCol[p->nCol];
  memset(pCol, 0, sizeof(p->aCol[0]));







|













|







114736
114737
114738
114739
114740
114741
114742
114743
114744
114745
114746
114747
114748
114749
114750
114751
114752
114753
114754
114755
114756
114757
114758
114759
114760
114761
114762
114763
114764
         affinity = sqlite3StdTypeAffinity[i];
         if( affinity<=SQLITE_AFF_TEXT ) szEst = 5;
         break;
       }
    }
  }

  z = sqlite3DbMallocRaw(db, (i64)sName.n + 1 + (i64)sType.n + (sType.n>0) );
  if( z==0 ) return;
  if( IN_RENAME_OBJECT ) sqlite3RenameTokenMap(pParse, (void*)z, &sName);
  memcpy(z, sName.z, sName.n);
  z[sName.n] = 0;
  sqlite3Dequote(z);
  hName = sqlite3StrIHash(z);
  for(i=0; i<p->nCol; i++){
    if( p->aCol[i].hName==hName && sqlite3StrICmp(z, p->aCol[i].zCnName)==0 ){
      sqlite3ErrorMsg(pParse, "duplicate column name: %s", z);
      sqlite3DbFree(db, z);
      return;
    }
  }
  aNew = sqlite3DbRealloc(db,p->aCol,((i64)p->nCol+1)*sizeof(p->aCol[0]));
  if( aNew==0 ){
    sqlite3DbFree(db, z);
    return;
  }
  p->aCol = aNew;
  pCol = &p->aCol[p->nCol];
  memset(pCol, 0, sizeof(p->aCol[0]));
114408
114409
114410
114411
114412
114413
114414
114415


114416
114417
114418
114419
114420
114421
114422
  }else{
    nTerm = pList->nExpr;
    for(i=0; i<nTerm; i++){
      Expr *pCExpr = sqlite3ExprSkipCollate(pList->a[i].pExpr);
      assert( pCExpr!=0 );
      sqlite3StringToId(pCExpr);
      if( pCExpr->op==TK_ID ){
        const char *zCName = pCExpr->u.zToken;


        for(iCol=0; iCol<pTab->nCol; iCol++){
          if( sqlite3StrICmp(zCName, pTab->aCol[iCol].zCnName)==0 ){
            pCol = &pTab->aCol[iCol];
            makeColumnPartOfPrimaryKey(pParse, pCol);
            break;
          }
        }







|
>
>







115048
115049
115050
115051
115052
115053
115054
115055
115056
115057
115058
115059
115060
115061
115062
115063
115064
  }else{
    nTerm = pList->nExpr;
    for(i=0; i<nTerm; i++){
      Expr *pCExpr = sqlite3ExprSkipCollate(pList->a[i].pExpr);
      assert( pCExpr!=0 );
      sqlite3StringToId(pCExpr);
      if( pCExpr->op==TK_ID ){
        const char *zCName;
        assert( !ExprHasProperty(pCExpr, EP_IntValue) );
        zCName = pCExpr->u.zToken;
        for(iCol=0; iCol<pTab->nCol; iCol++){
          if( sqlite3StrICmp(zCName, pTab->aCol[iCol].zCnName)==0 ){
            pCol = &pTab->aCol[iCol];
            makeColumnPartOfPrimaryKey(pParse, pCol);
            break;
          }
        }
114780
114781
114782
114783
114784
114785
114786
114787
114788
114789
114790
114791
114792
114793
114794

/* Return true if column number x is any of the first nCol entries of aiCol[].
** This is used to determine if the column number x appears in any of the
** first nCol entries of an index.
*/
static int hasColumn(const i16 *aiCol, int nCol, int x){
  while( nCol-- > 0 ){
    assert( aiCol[0]>=0 );
    if( x==*(aiCol++) ){
      return 1;
    }
  }
  return 0;
}








<







115422
115423
115424
115425
115426
115427
115428

115429
115430
115431
115432
115433
115434
115435

/* Return true if column number x is any of the first nCol entries of aiCol[].
** This is used to determine if the column number x appears in any of the
** first nCol entries of an index.
*/
static int hasColumn(const i16 *aiCol, int nCol, int x){
  while( nCol-- > 0 ){

    if( x==*(aiCol++) ){
      return 1;
    }
  }
  return 0;
}

115055
115056
115057
115058
115059
115060
115061



































115062
115063
115064
115065
115066
115067
115068
  if( pMod==0 ) return 0;
  if( pMod->pModule->iVersion<3 ) return 0;
  if( pMod->pModule->xShadowName==0 ) return 0;
  return pMod->pModule->xShadowName(zName+nName+1);
}
#endif /* ifndef SQLITE_OMIT_VIRTUALTABLE */




































#ifndef SQLITE_OMIT_VIRTUALTABLE
/*
** Return true if zName is a shadow table name in the current database
** connection.
**
** zName is temporarily modified while this routine is running, but is
** restored to its original value prior to this routine returning.







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







115696
115697
115698
115699
115700
115701
115702
115703
115704
115705
115706
115707
115708
115709
115710
115711
115712
115713
115714
115715
115716
115717
115718
115719
115720
115721
115722
115723
115724
115725
115726
115727
115728
115729
115730
115731
115732
115733
115734
115735
115736
115737
115738
115739
115740
115741
115742
115743
115744
  if( pMod==0 ) return 0;
  if( pMod->pModule->iVersion<3 ) return 0;
  if( pMod->pModule->xShadowName==0 ) return 0;
  return pMod->pModule->xShadowName(zName+nName+1);
}
#endif /* ifndef SQLITE_OMIT_VIRTUALTABLE */

#ifndef SQLITE_OMIT_VIRTUALTABLE
/*
** Table pTab is a virtual table.  If it the virtual table implementation
** exists and has an xShadowName method, then loop over all other ordinary
** tables within the same schema looking for shadow tables of pTab, and mark
** any shadow tables seen using the TF_Shadow flag.
*/
SQLITE_PRIVATE void sqlite3MarkAllShadowTablesOf(sqlite3 *db, Table *pTab){
  int nName;                    /* Length of pTab->zName */
  Module *pMod;                 /* Module for the virtual table */
  HashElem *k;                  /* For looping through the symbol table */

  assert( IsVirtual(pTab) );
  pMod = (Module*)sqlite3HashFind(&db->aModule, pTab->u.vtab.azArg[0]);
  if( pMod==0 ) return;
  if( NEVER(pMod->pModule==0) ) return;
  if( pMod->pModule->iVersion<3 ) return;
  if( pMod->pModule->xShadowName==0 ) return;
  assert( pTab->zName!=0 );
  nName = sqlite3Strlen30(pTab->zName);
  for(k=sqliteHashFirst(&pTab->pSchema->tblHash); k; k=sqliteHashNext(k)){
    Table *pOther = sqliteHashData(k);
    assert( pOther->zName!=0 );
    if( !IsOrdinaryTable(pOther) ) continue;
    if( pOther->tabFlags & TF_Shadow ) continue;
    if( sqlite3StrNICmp(pOther->zName, pTab->zName, nName)==0
     && pOther->zName[nName]=='_'
     && pMod->pModule->xShadowName(pOther->zName+nName+1)
    ){
      pOther->tabFlags |= TF_Shadow;
    }
  }
}
#endif /* ifndef SQLITE_OMIT_VIRTUALTABLE */

#ifndef SQLITE_OMIT_VIRTUALTABLE
/*
** Return true if zName is a shadow table name in the current database
** connection.
**
** zName is temporarily modified while this routine is running, but is
** restored to its original value prior to this routine returning.
115156
115157
115158
115159
115160
115161
115162
115163
115164
115165
115166
115167
115168
115169
115170
  ** for the table from the db->init.newTnum field.  (The page number
  ** should have been put there by the sqliteOpenCb routine.)
  **
  ** If the root page number is 1, that means this is the sqlite_schema
  ** table itself.  So mark it read-only.
  */
  if( db->init.busy ){
    if( pSelect ){
      sqlite3ErrorMsg(pParse, "");
      return;
    }
    p->tnum = db->init.newTnum;
    if( p->tnum==1 ) p->tabFlags |= TF_Readonly;
  }








|







115832
115833
115834
115835
115836
115837
115838
115839
115840
115841
115842
115843
115844
115845
115846
  ** for the table from the db->init.newTnum field.  (The page number
  ** should have been put there by the sqliteOpenCb routine.)
  **
  ** If the root page number is 1, that means this is the sqlite_schema
  ** table itself.  So mark it read-only.
  */
  if( db->init.busy ){
    if( pSelect || (!IsOrdinaryTable(p) && db->init.newTnum) ){
      sqlite3ErrorMsg(pParse, "");
      return;
    }
    p->tnum = db->init.newTnum;
    if( p->tnum==1 ) p->tabFlags |= TF_Readonly;
  }

115383
115384
115385
115386
115387
115388
115389
115390
115391
115392
115393
115394
115395
115396
115397
    }

    /* A slot for the record has already been allocated in the
    ** schema table.  We just need to update that slot with all
    ** the information we've collected.
    */
    sqlite3NestedParse(pParse,
      "UPDATE %Q." DFLT_SCHEMA_TABLE
      " SET type='%s', name=%Q, tbl_name=%Q, rootpage=#%d, sql=%Q"
      " WHERE rowid=#%d",
      db->aDb[iDb].zDbSName,
      zType,
      p->zName,
      p->zName,
      pParse->regRoot,







|







116059
116060
116061
116062
116063
116064
116065
116066
116067
116068
116069
116070
116071
116072
116073
    }

    /* A slot for the record has already been allocated in the
    ** schema table.  We just need to update that slot with all
    ** the information we've collected.
    */
    sqlite3NestedParse(pParse,
      "UPDATE %Q." LEGACY_SCHEMA_TABLE
      " SET type='%s', name=%Q, tbl_name=%Q, rootpage=#%d, sql=%Q"
      " WHERE rowid=#%d",
      db->aDb[iDb].zDbSName,
      zType,
      p->zName,
      p->zName,
      pParse->regRoot,
115569
115570
115571
115572
115573
115574
115575

115576
115577
115578
115579
115580
115581
115582
115583
115584
115585
115586
115587
115588
115589
#ifndef SQLITE_OMIT_AUTHORIZATION
  sqlite3_xauth xAuth;       /* Saved xAuth pointer */
#endif

  assert( pTable );

#ifndef SQLITE_OMIT_VIRTUALTABLE

  db->nSchemaLock++;
  rc = sqlite3VtabCallConnect(pParse, pTable);
  db->nSchemaLock--;
  if( rc ){
    return 1;
  }
  if( IsVirtual(pTable) ) return 0;
#endif

#ifndef SQLITE_OMIT_VIEW
  /* A positive nCol means the columns names for this view are
  ** already known.
  */
  if( pTable->nCol>0 ) return 0;







>
|
|
|
<
|

<







116245
116246
116247
116248
116249
116250
116251
116252
116253
116254
116255

116256
116257

116258
116259
116260
116261
116262
116263
116264
#ifndef SQLITE_OMIT_AUTHORIZATION
  sqlite3_xauth xAuth;       /* Saved xAuth pointer */
#endif

  assert( pTable );

#ifndef SQLITE_OMIT_VIRTUALTABLE
  if( IsVirtual(pTable) ){
    db->nSchemaLock++;
    rc = sqlite3VtabCallConnect(pParse, pTable);
    db->nSchemaLock--;

    return rc;
  }

#endif

#ifndef SQLITE_OMIT_VIEW
  /* A positive nCol means the columns names for this view are
  ** already known.
  */
  if( pTable->nCol>0 ) return 0;
115763
115764
115765
115766
115767
115768
115769
115770
115771
115772
115773
115774
115775
115776
115777
  ** reflect this.
  **
  ** The "#NNN" in the SQL is a special constant that means whatever value
  ** is in register NNN.  See grammar rules associated with the TK_REGISTER
  ** token for additional information.
  */
  sqlite3NestedParse(pParse,
     "UPDATE %Q." DFLT_SCHEMA_TABLE
     " SET rootpage=%d WHERE #%d AND rootpage=#%d",
     pParse->db->aDb[iDb].zDbSName, iTable, r1, r1);
#endif
  sqlite3ReleaseTempReg(pParse, r1);
}

/*







|







116438
116439
116440
116441
116442
116443
116444
116445
116446
116447
116448
116449
116450
116451
116452
  ** reflect this.
  **
  ** The "#NNN" in the SQL is a special constant that means whatever value
  ** is in register NNN.  See grammar rules associated with the TK_REGISTER
  ** token for additional information.
  */
  sqlite3NestedParse(pParse,
     "UPDATE %Q." LEGACY_SCHEMA_TABLE
     " SET rootpage=%d WHERE #%d AND rootpage=#%d",
     pParse->db->aDb[iDb].zDbSName, iTable, r1, r1);
#endif
  sqlite3ReleaseTempReg(pParse, r1);
}

/*
115898
115899
115900
115901
115902
115903
115904
115905
115906
115907
115908
115909
115910
115911
115912
  ** table. The program name loops through the schema table and deletes
  ** every row that refers to a table of the same name as the one being
  ** dropped. Triggers are handled separately because a trigger can be
  ** created in the temp database that refers to a table in another
  ** database.
  */
  sqlite3NestedParse(pParse,
      "DELETE FROM %Q." DFLT_SCHEMA_TABLE
      " WHERE tbl_name=%Q and type!='trigger'",
      pDb->zDbSName, pTab->zName);
  if( !isView && !IsVirtual(pTab) ){
    destroyTable(pParse, pTab);
  }

  /* Remove the table entry from SQLite's internal schema and modify







|







116573
116574
116575
116576
116577
116578
116579
116580
116581
116582
116583
116584
116585
116586
116587
  ** table. The program name loops through the schema table and deletes
  ** every row that refers to a table of the same name as the one being
  ** dropped. Triggers are handled separately because a trigger can be
  ** created in the temp database that refers to a table in another
  ** database.
  */
  sqlite3NestedParse(pParse,
      "DELETE FROM %Q." LEGACY_SCHEMA_TABLE
      " WHERE tbl_name=%Q and type!='trigger'",
      pDb->zDbSName, pTab->zName);
  if( !isView && !IsVirtual(pTab) ){
    destroyTable(pParse, pTab);
  }

  /* Remove the table entry from SQLite's internal schema and modify
115945
115946
115947
115948
115949
115950
115951



115952
115953
115954
115955
115956
115957
115958
  if( sqlite3StrNICmp(pTab->zName, "sqlite_", 7)==0 ){
    if( sqlite3StrNICmp(pTab->zName+7, "stat", 4)==0 ) return 0;
    if( sqlite3StrNICmp(pTab->zName+7, "parameters", 10)==0 ) return 0;
    return 1;
  }
  if( (pTab->tabFlags & TF_Shadow)!=0 && sqlite3ReadOnlyShadowTables(db) ){
    return 1;



  }
  return 0;
}

/*
** This routine is called to do the work of a DROP TABLE statement.
** pName is the name of the table to be dropped.







>
>
>







116620
116621
116622
116623
116624
116625
116626
116627
116628
116629
116630
116631
116632
116633
116634
116635
116636
  if( sqlite3StrNICmp(pTab->zName, "sqlite_", 7)==0 ){
    if( sqlite3StrNICmp(pTab->zName+7, "stat", 4)==0 ) return 0;
    if( sqlite3StrNICmp(pTab->zName+7, "parameters", 10)==0 ) return 0;
    return 1;
  }
  if( (pTab->tabFlags & TF_Shadow)!=0 && sqlite3ReadOnlyShadowTables(db) ){
    return 1;
  }
  if( pTab->tabFlags & TF_Eponymous ){
    return 1;
  }
  return 0;
}

/*
** This routine is called to do the work of a DROP TABLE statement.
** pName is the name of the table to be dropped.
116085
116086
116087
116088
116089
116090
116091
116092
116093
116094
116095
116096
116097
116098
116099
  int flags            /* Conflict resolution algorithms. */
){
  sqlite3 *db = pParse->db;
#ifndef SQLITE_OMIT_FOREIGN_KEY
  FKey *pFKey = 0;
  FKey *pNextTo;
  Table *p = pParse->pNewTable;
  int nByte;
  int i;
  int nCol;
  char *z;

  assert( pTo!=0 );
  if( p==0 || IN_DECLARE_VTAB ) goto fk_end;
  if( pFromCol==0 ){







|







116763
116764
116765
116766
116767
116768
116769
116770
116771
116772
116773
116774
116775
116776
116777
  int flags            /* Conflict resolution algorithms. */
){
  sqlite3 *db = pParse->db;
#ifndef SQLITE_OMIT_FOREIGN_KEY
  FKey *pFKey = 0;
  FKey *pNextTo;
  Table *p = pParse->pNewTable;
  i64 nByte;
  int i;
  int nCol;
  char *z;

  assert( pTo!=0 );
  if( p==0 || IN_DECLARE_VTAB ) goto fk_end;
  if( pFromCol==0 ){
116121
116122
116123
116124
116125
116126
116127

116128
116129
116130
116131
116132
116133
116134
    }
  }
  pFKey = sqlite3DbMallocZero(db, nByte );
  if( pFKey==0 ){
    goto fk_end;
  }
  pFKey->pFrom = p;

  pFKey->pNextFrom = p->u.tab.pFKey;
  z = (char*)&pFKey->aCol[nCol];
  pFKey->zTo = z;
  if( IN_RENAME_OBJECT ){
    sqlite3RenameTokenMap(pParse, (void*)z, pTo);
  }
  memcpy(z, pTo->z, pTo->n);







>







116799
116800
116801
116802
116803
116804
116805
116806
116807
116808
116809
116810
116811
116812
116813
    }
  }
  pFKey = sqlite3DbMallocZero(db, nByte );
  if( pFKey==0 ){
    goto fk_end;
  }
  pFKey->pFrom = p;
  assert( IsOrdinaryTable(p) );
  pFKey->pNextFrom = p->u.tab.pFKey;
  z = (char*)&pFKey->aCol[nCol];
  pFKey->zTo = z;
  if( IN_RENAME_OBJECT ){
    sqlite3RenameTokenMap(pParse, (void*)z, pTo);
  }
  memcpy(z, pTo->z, pTo->n);
116186
116187
116188
116189
116190
116191
116192
116193
116194
116195
116196
116197
116198
116199
116200
    assert( pNextTo->pPrevTo==0 );
    pFKey->pNextTo = pNextTo;
    pNextTo->pPrevTo = pFKey;
  }

  /* Link the foreign key to the table as the last step.
  */
  assert( !IsVirtual(p) );
  p->u.tab.pFKey = pFKey;
  pFKey = 0;

fk_end:
  sqlite3DbFree(db, pFKey);
#endif /* !defined(SQLITE_OMIT_FOREIGN_KEY) */
  sqlite3ExprListDelete(db, pFromCol);







|







116865
116866
116867
116868
116869
116870
116871
116872
116873
116874
116875
116876
116877
116878
116879
    assert( pNextTo->pPrevTo==0 );
    pFKey->pNextTo = pNextTo;
    pNextTo->pPrevTo = pFKey;
  }

  /* Link the foreign key to the table as the last step.
  */
  assert( IsOrdinaryTable(p) );
  p->u.tab.pFKey = pFKey;
  pFKey = 0;

fk_end:
  sqlite3DbFree(db, pFKey);
#endif /* !defined(SQLITE_OMIT_FOREIGN_KEY) */
  sqlite3ExprListDelete(db, pFromCol);
116209
116210
116211
116212
116213
116214
116215
116216
116217
116218
116219
116220
116221
116222
116223
** accordingly.
*/
SQLITE_PRIVATE void sqlite3DeferForeignKey(Parse *pParse, int isDeferred){
#ifndef SQLITE_OMIT_FOREIGN_KEY
  Table *pTab;
  FKey *pFKey;
  if( (pTab = pParse->pNewTable)==0 ) return;
  if( NEVER(IsVirtual(pTab)) ) return;
  if( (pFKey = pTab->u.tab.pFKey)==0 ) return;
  assert( isDeferred==0 || isDeferred==1 ); /* EV: R-30323-21917 */
  pFKey->isDeferred = (u8)isDeferred;
#endif
}

/*







|







116888
116889
116890
116891
116892
116893
116894
116895
116896
116897
116898
116899
116900
116901
116902
** accordingly.
*/
SQLITE_PRIVATE void sqlite3DeferForeignKey(Parse *pParse, int isDeferred){
#ifndef SQLITE_OMIT_FOREIGN_KEY
  Table *pTab;
  FKey *pFKey;
  if( (pTab = pParse->pNewTable)==0 ) return;
  if( NEVER(!IsOrdinaryTable(pTab)) ) return;
  if( (pFKey = pTab->u.tab.pFKey)==0 ) return;
  assert( isDeferred==0 || isDeferred==1 ); /* EV: R-30323-21917 */
  pFKey->isDeferred = (u8)isDeferred;
#endif
}

/*
116611
116612
116613
116614
116615
116616
116617

116618
116619
116620
116621
116622
116623
116624
  /* Figure out how many bytes of space are required to store explicitly
  ** specified collation sequence names.
  */
  for(i=0; i<pList->nExpr; i++){
    Expr *pExpr = pList->a[i].pExpr;
    assert( pExpr!=0 );
    if( pExpr->op==TK_COLLATE ){

      nExtra += (1 + sqlite3Strlen30(pExpr->u.zToken));
    }
  }

  /*
  ** Allocate the index structure.
  */







>







117290
117291
117292
117293
117294
117295
117296
117297
117298
117299
117300
117301
117302
117303
117304
  /* Figure out how many bytes of space are required to store explicitly
  ** specified collation sequence names.
  */
  for(i=0; i<pList->nExpr; i++){
    Expr *pExpr = pList->a[i].pExpr;
    assert( pExpr!=0 );
    if( pExpr->op==TK_COLLATE ){
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      nExtra += (1 + sqlite3Strlen30(pExpr->u.zToken));
    }
  }

  /*
  ** Allocate the index structure.
  */
116706
116707
116708
116709
116710
116711
116712

116713
116714
116715
116716
116717
116718
116719
        }
      }
      pIndex->aiColumn[i] = (i16)j;
    }
    zColl = 0;
    if( pListItem->pExpr->op==TK_COLLATE ){
      int nColl;

      zColl = pListItem->pExpr->u.zToken;
      nColl = sqlite3Strlen30(zColl) + 1;
      assert( nExtra>=nColl );
      memcpy(zExtra, zColl, nColl);
      zColl = zExtra;
      zExtra += nColl;
      nExtra -= nColl;







>







117386
117387
117388
117389
117390
117391
117392
117393
117394
117395
117396
117397
117398
117399
117400
        }
      }
      pIndex->aiColumn[i] = (i16)j;
    }
    zColl = 0;
    if( pListItem->pExpr->op==TK_COLLATE ){
      int nColl;
      assert( !ExprHasProperty(pListItem->pExpr, EP_IntValue) );
      zColl = pListItem->pExpr->u.zToken;
      nColl = sqlite3Strlen30(zColl) + 1;
      assert( nExtra>=nColl );
      memcpy(zExtra, zColl, nColl);
      zColl = zExtra;
      zExtra += nColl;
      nExtra -= nColl;
116912
116913
116914
116915
116916
116917
116918
116919
116920
116921
116922
116923
116924
116925
116926
116927
116928
116929
116930
116931
116932
        /* zStmt = sqlite3MPrintf(""); */
        zStmt = 0;
      }

      /* Add an entry in sqlite_schema for this index
      */
      sqlite3NestedParse(pParse,
          "INSERT INTO %Q." DFLT_SCHEMA_TABLE " VALUES('index',%Q,%Q,#%d,%Q);",
          db->aDb[iDb].zDbSName,
          pIndex->zName,
          pTab->zName,
          iMem,
          zStmt
          );
      sqlite3DbFree(db, zStmt);

      /* Fill the index with data and reparse the schema. Code an OP_Expire
      ** to invalidate all pre-compiled statements.
      */
      if( pTblName ){
        sqlite3RefillIndex(pParse, pIndex, iMem);







|
|
|
|
|
|
|







117593
117594
117595
117596
117597
117598
117599
117600
117601
117602
117603
117604
117605
117606
117607
117608
117609
117610
117611
117612
117613
        /* zStmt = sqlite3MPrintf(""); */
        zStmt = 0;
      }

      /* Add an entry in sqlite_schema for this index
      */
      sqlite3NestedParse(pParse,
         "INSERT INTO %Q." LEGACY_SCHEMA_TABLE " VALUES('index',%Q,%Q,#%d,%Q);",
         db->aDb[iDb].zDbSName,
         pIndex->zName,
         pTab->zName,
         iMem,
         zStmt
      );
      sqlite3DbFree(db, zStmt);

      /* Fill the index with data and reparse the schema. Code an OP_Expire
      ** to invalidate all pre-compiled statements.
      */
      if( pTblName ){
        sqlite3RefillIndex(pParse, pIndex, iMem);
117098
117099
117100
117101
117102
117103
117104
117105
117106
117107
117108
117109
117110
117111
117112
#endif

  /* Generate code to remove the index and from the schema table */
  v = sqlite3GetVdbe(pParse);
  if( v ){
    sqlite3BeginWriteOperation(pParse, 1, iDb);
    sqlite3NestedParse(pParse,
       "DELETE FROM %Q." DFLT_SCHEMA_TABLE " WHERE name=%Q AND type='index'",
       db->aDb[iDb].zDbSName, pIndex->zName
    );
    sqlite3ClearStatTables(pParse, iDb, "idx", pIndex->zName);
    sqlite3ChangeCookie(pParse, iDb);
    destroyRootPage(pParse, pIndex->tnum, iDb);
    sqlite3VdbeAddOp4(v, OP_DropIndex, iDb, 0, 0, pIndex->zName, 0);
  }







|







117779
117780
117781
117782
117783
117784
117785
117786
117787
117788
117789
117790
117791
117792
117793
#endif

  /* Generate code to remove the index and from the schema table */
  v = sqlite3GetVdbe(pParse);
  if( v ){
    sqlite3BeginWriteOperation(pParse, 1, iDb);
    sqlite3NestedParse(pParse,
       "DELETE FROM %Q." LEGACY_SCHEMA_TABLE " WHERE name=%Q AND type='index'",
       db->aDb[iDb].zDbSName, pIndex->zName
    );
    sqlite3ClearStatTables(pParse, iDb, "idx", pIndex->zName);
    sqlite3ChangeCookie(pParse, iDb);
    destroyRootPage(pParse, pIndex->tnum, iDb);
    sqlite3VdbeAddOp4(v, OP_DropIndex, iDb, 0, 0, pIndex->zName, 0);
  }
117466
117467
117468
117469
117470
117471
117472
117473
117474
117475
117476
117477
117478
117479
117480
    pItem->zAlias = sqlite3NameFromToken(db, pAlias);
  }
  pItem->pSelect = pSubquery;
  pItem->pOn = pOn;
  pItem->pUsing = pUsing;
  return p;

 append_from_error:
  assert( p==0 );
  sqlite3ExprDelete(db, pOn);
  sqlite3IdListDelete(db, pUsing);
  sqlite3SelectDelete(db, pSubquery);
  return 0;
}








|







118147
118148
118149
118150
118151
118152
118153
118154
118155
118156
118157
118158
118159
118160
118161
    pItem->zAlias = sqlite3NameFromToken(db, pAlias);
  }
  pItem->pSelect = pSubquery;
  pItem->pOn = pOn;
  pItem->pUsing = pUsing;
  return p;

append_from_error:
  assert( p==0 );
  sqlite3ExprDelete(db, pOn);
  sqlite3IdListDelete(db, pUsing);
  sqlite3SelectDelete(db, pSubquery);
  return 0;
}

117494
117495
117496
117497
117498
117499
117500

117501
117502
117503
117504
117505
117506
117507
    if( pIndexedBy->n==1 && !pIndexedBy->z ){
      /* A "NOT INDEXED" clause was supplied. See parse.y
      ** construct "indexed_opt" for details. */
      pItem->fg.notIndexed = 1;
    }else{
      pItem->u1.zIndexedBy = sqlite3NameFromToken(pParse->db, pIndexedBy);
      pItem->fg.isIndexedBy = 1;

    }
  }
}

/*
** Append the contents of SrcList p2 to SrcList p1 and return the resulting
** SrcList. Or, if an error occurs, return NULL. In all cases, p1 and p2







>







118175
118176
118177
118178
118179
118180
118181
118182
118183
118184
118185
118186
118187
118188
118189
    if( pIndexedBy->n==1 && !pIndexedBy->z ){
      /* A "NOT INDEXED" clause was supplied. See parse.y
      ** construct "indexed_opt" for details. */
      pItem->fg.notIndexed = 1;
    }else{
      pItem->u1.zIndexedBy = sqlite3NameFromToken(pParse->db, pIndexedBy);
      pItem->fg.isIndexedBy = 1;
      assert( pItem->fg.isCte==0 );  /* No collision on union u2 */
    }
  }
}

/*
** Append the contents of SrcList p2 to SrcList p1 and return the resulting
** SrcList. Or, if an error occurs, return NULL. In all cases, p1 and p2
118474
118475
118476
118477
118478
118479
118480

118481
118482
118483
118484
118485
118486
118487
*/
SQLITE_PRIVATE FuncDef *sqlite3FunctionSearch(
  int h,               /* Hash of the name */
  const char *zFunc    /* Name of function */
){
  FuncDef *p;
  for(p=sqlite3BuiltinFunctions.a[h]; p; p=p->u.pHash){

    if( sqlite3StrICmp(p->zName, zFunc)==0 ){
      return p;
    }
  }
  return 0;
}








>







119156
119157
119158
119159
119160
119161
119162
119163
119164
119165
119166
119167
119168
119169
119170
*/
SQLITE_PRIVATE FuncDef *sqlite3FunctionSearch(
  int h,               /* Hash of the name */
  const char *zFunc    /* Name of function */
){
  FuncDef *p;
  for(p=sqlite3BuiltinFunctions.a[h]; p; p=p->u.pHash){
    assert( p->funcFlags & SQLITE_FUNC_BUILTIN );
    if( sqlite3StrICmp(p->zName, zFunc)==0 ){
      return p;
    }
  }
  return 0;
}

118495
118496
118497
118498
118499
118500
118501

118502
118503
118504
118505
118506
118507
118508
  int i;
  for(i=0; i<nDef; i++){
    FuncDef *pOther;
    const char *zName = aDef[i].zName;
    int nName = sqlite3Strlen30(zName);
    int h = SQLITE_FUNC_HASH(zName[0], nName);
    assert( zName[0]>='a' && zName[0]<='z' );

    pOther = sqlite3FunctionSearch(h, zName);
    if( pOther ){
      assert( pOther!=&aDef[i] && pOther->pNext!=&aDef[i] );
      aDef[i].pNext = pOther->pNext;
      pOther->pNext = &aDef[i];
    }else{
      aDef[i].pNext = 0;







>







119178
119179
119180
119181
119182
119183
119184
119185
119186
119187
119188
119189
119190
119191
119192
  int i;
  for(i=0; i<nDef; i++){
    FuncDef *pOther;
    const char *zName = aDef[i].zName;
    int nName = sqlite3Strlen30(zName);
    int h = SQLITE_FUNC_HASH(zName[0], nName);
    assert( zName[0]>='a' && zName[0]<='z' );
    assert( aDef[i].funcFlags & SQLITE_FUNC_BUILTIN );
    pOther = sqlite3FunctionSearch(h, zName);
    if( pOther ){
      assert( pOther!=&aDef[i] && pOther->pNext!=&aDef[i] );
      aDef[i].pNext = pOther->pNext;
      pOther->pNext = &aDef[i];
    }else{
      aDef[i].pNext = 0;
118719
118720
118721
118722
118723
118724
118725










118726
118727
118728
118729
118730
118731
118732
    pTab->nTabRef++;
    if( pItem->fg.isIndexedBy && sqlite3IndexedByLookup(pParse, pItem) ){
      pTab = 0;
    }
  }
  return pTab;
}











/* Return true if table pTab is read-only.
**
** A table is read-only if any of the following are true:
**
**   1) It is a virtual table and no implementation of the xUpdate method
**      has been provided







>
>
>
>
>
>
>
>
>
>







119403
119404
119405
119406
119407
119408
119409
119410
119411
119412
119413
119414
119415
119416
119417
119418
119419
119420
119421
119422
119423
119424
119425
119426
    pTab->nTabRef++;
    if( pItem->fg.isIndexedBy && sqlite3IndexedByLookup(pParse, pItem) ){
      pTab = 0;
    }
  }
  return pTab;
}

/* Generate byte-code that will report the number of rows modified
** by a DELETE, INSERT, or UPDATE statement.
*/
SQLITE_PRIVATE void sqlite3CodeChangeCount(Vdbe *v, int regCounter, const char *zColName){
  sqlite3VdbeAddOp0(v, OP_FkCheck);
  sqlite3VdbeAddOp2(v, OP_ResultRow, regCounter, 1);
  sqlite3VdbeSetNumCols(v, 1);
  sqlite3VdbeSetColName(v, 0, COLNAME_NAME, zColName, SQLITE_STATIC);
}

/* Return true if table pTab is read-only.
**
** A table is read-only if any of the following are true:
**
**   1) It is a virtual table and no implementation of the xUpdate method
**      has been provided
118886
118887
118888
118889
118890
118891
118892

118893
118894
118895
118896
118897
118898
118899

  /* duplicate the FROM clause as it is needed by both the DELETE/UPDATE tree
  ** and the SELECT subtree. */
  pSrc->a[0].pTab = 0;
  pSelectSrc = sqlite3SrcListDup(db, pSrc, 0);
  pSrc->a[0].pTab = pTab;
  if( pSrc->a[0].fg.isIndexedBy ){

    pSrc->a[0].u2.pIBIndex = 0;
    pSrc->a[0].fg.isIndexedBy = 0;
    sqlite3DbFree(db, pSrc->a[0].u1.zIndexedBy);
  }else if( pSrc->a[0].fg.isCte ){
    pSrc->a[0].u2.pCteUse->nUse++;
  }








>







119580
119581
119582
119583
119584
119585
119586
119587
119588
119589
119590
119591
119592
119593
119594

  /* duplicate the FROM clause as it is needed by both the DELETE/UPDATE tree
  ** and the SELECT subtree. */
  pSrc->a[0].pTab = 0;
  pSelectSrc = sqlite3SrcListDup(db, pSrc, 0);
  pSrc->a[0].pTab = pTab;
  if( pSrc->a[0].fg.isIndexedBy ){
    assert( pSrc->a[0].fg.isCte==0 );
    pSrc->a[0].u2.pIBIndex = 0;
    pSrc->a[0].fg.isIndexedBy = 0;
    sqlite3DbFree(db, pSrc->a[0].u1.zIndexedBy);
  }else if( pSrc->a[0].fg.isCte ){
    pSrc->a[0].u2.pCteUse->nUse++;
  }

119294
119295
119296
119297
119298
119299
119300
119301
119302
119303
119304
119305
119306
119307
119308
119309
119310
  }

  /* Return the number of rows that were deleted. If this routine is
  ** generating code because of a call to sqlite3NestedParse(), do not
  ** invoke the callback function.
  */
  if( memCnt ){
    sqlite3VdbeAddOp2(v, OP_ChngCntRow, memCnt, 1);
    sqlite3VdbeSetNumCols(v, 1);
    sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "rows deleted", SQLITE_STATIC);
  }

delete_from_cleanup:
  sqlite3AuthContextPop(&sContext);
  sqlite3SrcListDelete(db, pTabList);
  sqlite3ExprDelete(db, pWhere);
#if defined(SQLITE_ENABLE_UPDATE_DELETE_LIMIT)







<
<
|







119989
119990
119991
119992
119993
119994
119995


119996
119997
119998
119999
120000
120001
120002
120003
  }

  /* Return the number of rows that were deleted. If this routine is
  ** generating code because of a call to sqlite3NestedParse(), do not
  ** invoke the callback function.
  */
  if( memCnt ){


    sqlite3CodeChangeCount(v, memCnt, "rows deleted");
  }

delete_from_cleanup:
  sqlite3AuthContextPop(&sContext);
  sqlite3SrcListDelete(db, pTabList);
  sqlite3ExprDelete(db, pWhere);
#if defined(SQLITE_ENABLE_UPDATE_DELETE_LIMIT)
121470
121471
121472
121473
121474
121475
121476




121477
121478
121479
121480
121481
121482
121483
121484
  assert( argc==1 || argc==2 );
  (void)argc;  /* Suppress unused parameter warning */
  if( sqlite3_value_type(argv[0])==SQLITE_NULL ) return;
  pGCC = (GroupConcatCtx*)sqlite3_aggregate_context(context, sizeof(*pGCC));
  /* pGCC is always non-NULL since groupConcatStep() will have always
  ** run frist to initialize it */
  if( ALWAYS(pGCC) ){




    int nVS = sqlite3_value_bytes(argv[0]);
    pGCC->nAccum -= 1;
    if( pGCC->pnSepLengths!=0 ){
      assert(pGCC->nAccum >= 0);
      if( pGCC->nAccum>0 ){
        nVS += *pGCC->pnSepLengths;
        memmove(pGCC->pnSepLengths, pGCC->pnSepLengths+1,
               (pGCC->nAccum-1)*sizeof(int));







>
>
>
>
|







122163
122164
122165
122166
122167
122168
122169
122170
122171
122172
122173
122174
122175
122176
122177
122178
122179
122180
122181
  assert( argc==1 || argc==2 );
  (void)argc;  /* Suppress unused parameter warning */
  if( sqlite3_value_type(argv[0])==SQLITE_NULL ) return;
  pGCC = (GroupConcatCtx*)sqlite3_aggregate_context(context, sizeof(*pGCC));
  /* pGCC is always non-NULL since groupConcatStep() will have always
  ** run frist to initialize it */
  if( ALWAYS(pGCC) ){
    int nVS;
    /* Must call sqlite3_value_text() to convert the argument into text prior
    ** to invoking sqlite3_value_bytes(), in case the text encoding is UTF16 */
    (void)sqlite3_value_text(argv[0]);
    nVS = sqlite3_value_bytes(argv[0]);
    pGCC->nAccum -= 1;
    if( pGCC->pnSepLengths!=0 ){
      assert(pGCC->nAccum >= 0);
      if( pGCC->nAccum>0 ){
        nVS += *pGCC->pnSepLengths;
        memmove(pGCC->pnSepLengths, pGCC->pnSepLengths+1,
               (pGCC->nAccum-1)*sizeof(int));
121585
121586
121587
121588
121589
121590
121591

121592
121593
121594
121595
121596

121597
121598
121599
121600
121601
121602
121603
** false.
*/
SQLITE_PRIVATE int sqlite3IsLikeFunction(sqlite3 *db, Expr *pExpr, int *pIsNocase, char *aWc){
  FuncDef *pDef;
  int nExpr;
  assert( pExpr!=0 );
  assert( pExpr->op==TK_FUNCTION );

  if( !pExpr->x.pList ){
    return 0;
  }
  assert( !ExprHasProperty(pExpr, EP_xIsSelect) );
  nExpr = pExpr->x.pList->nExpr;

  pDef = sqlite3FindFunction(db, pExpr->u.zToken, nExpr, SQLITE_UTF8, 0);
#ifdef SQLITE_ENABLE_UNKNOWN_SQL_FUNCTION
  if( pDef==0 ) return 0;
#endif
  if( NEVER(pDef==0) || (pDef->funcFlags & SQLITE_FUNC_LIKE)==0 ){
    return 0;
  }







>



<

>







122282
122283
122284
122285
122286
122287
122288
122289
122290
122291
122292

122293
122294
122295
122296
122297
122298
122299
122300
122301
** false.
*/
SQLITE_PRIVATE int sqlite3IsLikeFunction(sqlite3 *db, Expr *pExpr, int *pIsNocase, char *aWc){
  FuncDef *pDef;
  int nExpr;
  assert( pExpr!=0 );
  assert( pExpr->op==TK_FUNCTION );
  assert( ExprUseXList(pExpr) );
  if( !pExpr->x.pList ){
    return 0;
  }

  nExpr = pExpr->x.pList->nExpr;
  assert( !ExprHasProperty(pExpr, EP_IntValue) );
  pDef = sqlite3FindFunction(db, pExpr->u.zToken, nExpr, SQLITE_UTF8, 0);
#ifdef SQLITE_ENABLE_UNKNOWN_SQL_FUNCTION
  if( pDef==0 ) return 0;
#endif
  if( NEVER(pDef==0) || (pDef->funcFlags & SQLITE_FUNC_LIKE)==0 ){
    return 0;
  }
121613
121614
121615
121616
121617
121618
121619

121620
121621
121622
121623
121624
121625
121626

  if( nExpr<3 ){
    aWc[3] = 0;
  }else{
    Expr *pEscape = pExpr->x.pList->a[2].pExpr;
    char *zEscape;
    if( pEscape->op!=TK_STRING ) return 0;

    zEscape = pEscape->u.zToken;
    if( zEscape[0]==0 || zEscape[1]!=0 ) return 0;
    if( zEscape[0]==aWc[0] ) return 0;
    if( zEscape[0]==aWc[1] ) return 0;
    aWc[3] = zEscape[0];
  }








>







122311
122312
122313
122314
122315
122316
122317
122318
122319
122320
122321
122322
122323
122324
122325

  if( nExpr<3 ){
    aWc[3] = 0;
  }else{
    Expr *pEscape = pExpr->x.pList->a[2].pExpr;
    char *zEscape;
    if( pEscape->op!=TK_STRING ) return 0;
    assert( !ExprHasProperty(pEscape, EP_IntValue) );
    zEscape = pEscape->u.zToken;
    if( zEscape[0]==0 || zEscape[1]!=0 ) return 0;
    if( zEscape[0]==aWc[0] ) return 0;
    if( zEscape[0]==aWc[1] ) return 0;
    aWc[3] = zEscape[0];
  }

121994
121995
121996
121997
121998
121999
122000

122001
122002
122003
122004
122005
122006
122007
    int i;
    FuncDef *p;
    for(i=0; i<SQLITE_FUNC_HASH_SZ; i++){
      printf("FUNC-HASH %02d:", i);
      for(p=sqlite3BuiltinFunctions.a[i]; p; p=p->u.pHash){
        int n = sqlite3Strlen30(p->zName);
        int h = p->zName[0] + n;

        printf(" %s(%d)", p->zName, h);
      }
      printf("\n");
    }
  }
#endif
}







>







122693
122694
122695
122696
122697
122698
122699
122700
122701
122702
122703
122704
122705
122706
122707
    int i;
    FuncDef *p;
    for(i=0; i<SQLITE_FUNC_HASH_SZ; i++){
      printf("FUNC-HASH %02d:", i);
      for(p=sqlite3BuiltinFunctions.a[i]; p; p=p->u.pHash){
        int n = sqlite3Strlen30(p->zName);
        int h = p->zName[0] + n;
        assert( p->funcFlags & SQLITE_FUNC_BUILTIN );
        printf(" %s(%d)", p->zName, h);
      }
      printf("\n");
    }
  }
#endif
}
122516
122517
122518
122519
122520
122521
122522

122523
122524
122525
122526
122527
122528
122529
  sqlite3 *db,      /* The database connection */
  Table *pTab,      /* The table whose column is desired */
  int iCursor,      /* The open cursor on the table */
  i16 iCol          /* The column that is wanted */
){
  Expr *pExpr = sqlite3Expr(db, TK_COLUMN, 0);
  if( pExpr ){

    pExpr->y.pTab = pTab;
    pExpr->iTable = iCursor;
    pExpr->iColumn = iCol;
  }
  return pExpr;
}








>







123216
123217
123218
123219
123220
123221
123222
123223
123224
123225
123226
123227
123228
123229
123230
  sqlite3 *db,      /* The database connection */
  Table *pTab,      /* The table whose column is desired */
  int iCursor,      /* The open cursor on the table */
  i16 iCol          /* The column that is wanted */
){
  Expr *pExpr = sqlite3Expr(db, TK_COLUMN, 0);
  if( pExpr ){
    assert( ExprUseYTab(pExpr) );
    pExpr->y.pTab = pTab;
    pExpr->iTable = iCursor;
    pExpr->iColumn = iCol;
  }
  return pExpr;
}

122726
122727
122728
122729
122730
122731
122732
122733
122734
122735
122736
122737
122738
122739
122740
122741
122742
122743
122744
122745
122746
**
** then the equivalent of "DELETE FROM <tbl>" is executed before dropping
** the table from the database. Triggers are disabled while running this
** DELETE, but foreign key actions are not.
*/
SQLITE_PRIVATE void sqlite3FkDropTable(Parse *pParse, SrcList *pName, Table *pTab){
  sqlite3 *db = pParse->db;
  if( (db->flags&SQLITE_ForeignKeys) && !IsVirtual(pTab) ){
    int iSkip = 0;
    Vdbe *v = sqlite3GetVdbe(pParse);

    assert( v );                  /* VDBE has already been allocated */
    assert( !IsView(pTab) );      /* Not a view */
    assert( !IsVirtual(pTab) );
    if( sqlite3FkReferences(pTab)==0 ){
      /* Search for a deferred foreign key constraint for which this table
      ** is the child table. If one cannot be found, return without
      ** generating any VDBE code. If one can be found, then jump over
      ** the entire DELETE if there are no outstanding deferred constraints
      ** when this statement is run.  */
      FKey *p;







|




<
|







123427
123428
123429
123430
123431
123432
123433
123434
123435
123436
123437
123438

123439
123440
123441
123442
123443
123444
123445
123446
**
** then the equivalent of "DELETE FROM <tbl>" is executed before dropping
** the table from the database. Triggers are disabled while running this
** DELETE, but foreign key actions are not.
*/
SQLITE_PRIVATE void sqlite3FkDropTable(Parse *pParse, SrcList *pName, Table *pTab){
  sqlite3 *db = pParse->db;
  if( (db->flags&SQLITE_ForeignKeys) && IsOrdinaryTable(pTab) ){
    int iSkip = 0;
    Vdbe *v = sqlite3GetVdbe(pParse);

    assert( v );                  /* VDBE has already been allocated */

    assert( IsOrdinaryTable(pTab) );
    if( sqlite3FkReferences(pTab)==0 ){
      /* Search for a deferred foreign key constraint for which this table
      ** is the child table. If one cannot be found, return without
      ** generating any VDBE code. If one can be found, then jump over
      ** the entire DELETE if there are no outstanding deferred constraints
      ** when this statement is run.  */
      FKey *p;
122896
122897
122898
122899
122900
122901
122902

122903
122904
122905
122906
122907
122908
122909
122910
122911
122912
122913
122914
122915
122916
  int isIgnoreErrors = pParse->disableTriggers;

  /* Exactly one of regOld and regNew should be non-zero. */
  assert( (regOld==0)!=(regNew==0) );

  /* If foreign-keys are disabled, this function is a no-op. */
  if( (db->flags&SQLITE_ForeignKeys)==0 ) return;


  iDb = sqlite3SchemaToIndex(db, pTab->pSchema);
  zDb = db->aDb[iDb].zDbSName;

  /* Loop through all the foreign key constraints for which pTab is the
  ** child table (the table that the foreign key definition is part of).  */
  assert( !IsVirtual(pTab) );
  for(pFKey=pTab->u.tab.pFKey; pFKey; pFKey=pFKey->pNextFrom){
    Table *pTo;                   /* Parent table of foreign key pFKey */
    Index *pIdx = 0;              /* Index on key columns in pTo */
    int *aiFree = 0;
    int *aiCol;
    int iCol;
    int i;







>






<







123596
123597
123598
123599
123600
123601
123602
123603
123604
123605
123606
123607
123608
123609

123610
123611
123612
123613
123614
123615
123616
  int isIgnoreErrors = pParse->disableTriggers;

  /* Exactly one of regOld and regNew should be non-zero. */
  assert( (regOld==0)!=(regNew==0) );

  /* If foreign-keys are disabled, this function is a no-op. */
  if( (db->flags&SQLITE_ForeignKeys)==0 ) return;
  if( !IsOrdinaryTable(pTab) ) return;

  iDb = sqlite3SchemaToIndex(db, pTab->pSchema);
  zDb = db->aDb[iDb].zDbSName;

  /* Loop through all the foreign key constraints for which pTab is the
  ** child table (the table that the foreign key definition is part of).  */

  for(pFKey=pTab->u.tab.pFKey; pFKey; pFKey=pFKey->pNextFrom){
    Table *pTo;                   /* Parent table of foreign key pFKey */
    Index *pIdx = 0;              /* Index on key columns in pTo */
    int *aiFree = 0;
    int *aiCol;
    int iCol;
    int i;
123085
123086
123087
123088
123089
123090
123091
123092
123093
123094
123095
123096
123097
123098
123099
123100
123101
123102
** row contained in table pTab.
*/
SQLITE_PRIVATE u32 sqlite3FkOldmask(
  Parse *pParse,                  /* Parse context */
  Table *pTab                     /* Table being modified */
){
  u32 mask = 0;
  if( pParse->db->flags&SQLITE_ForeignKeys ){
    FKey *p;
    int i;
    assert( !IsVirtual(pTab) );
    for(p=pTab->u.tab.pFKey; p; p=p->pNextFrom){
      for(i=0; i<p->nCol; i++) mask |= COLUMN_MASK(p->aCol[i].iFrom);
    }
    for(p=sqlite3FkReferences(pTab); p; p=p->pNextTo){
      Index *pIdx = 0;
      sqlite3FkLocateIndex(pParse, pTab, p, &pIdx, 0);
      if( pIdx ){







|


<







123785
123786
123787
123788
123789
123790
123791
123792
123793
123794

123795
123796
123797
123798
123799
123800
123801
** row contained in table pTab.
*/
SQLITE_PRIVATE u32 sqlite3FkOldmask(
  Parse *pParse,                  /* Parse context */
  Table *pTab                     /* Table being modified */
){
  u32 mask = 0;
  if( pParse->db->flags&SQLITE_ForeignKeys && IsOrdinaryTable(pTab) ){
    FKey *p;
    int i;

    for(p=pTab->u.tab.pFKey; p; p=p->pNextFrom){
      for(i=0; i<p->nCol; i++) mask |= COLUMN_MASK(p->aCol[i].iFrom);
    }
    for(p=sqlite3FkReferences(pTab); p; p=p->pNextTo){
      Index *pIdx = 0;
      sqlite3FkLocateIndex(pParse, pTab, p, &pIdx, 0);
      if( pIdx ){
123139
123140
123141
123142
123143
123144
123145
123146
123147
123148
123149
123150
123151
123152
123153
  Parse *pParse,                  /* Parse context */
  Table *pTab,                    /* Table being modified */
  int *aChange,                   /* Non-NULL for UPDATE operations */
  int chngRowid                   /* True for UPDATE that affects rowid */
){
  int eRet = 1;                   /* Value to return if bHaveFK is true */
  int bHaveFK = 0;                /* If FK processing is required */
  if( pParse->db->flags&SQLITE_ForeignKeys && !IsVirtual(pTab) ){
    if( !aChange ){
      /* A DELETE operation. Foreign key processing is required if the
      ** table in question is either the child or parent table for any
      ** foreign key constraint.  */
      bHaveFK = (sqlite3FkReferences(pTab) || pTab->u.tab.pFKey);
    }else{
      /* This is an UPDATE. Foreign key processing is only required if the







|







123838
123839
123840
123841
123842
123843
123844
123845
123846
123847
123848
123849
123850
123851
123852
  Parse *pParse,                  /* Parse context */
  Table *pTab,                    /* Table being modified */
  int *aChange,                   /* Non-NULL for UPDATE operations */
  int chngRowid                   /* True for UPDATE that affects rowid */
){
  int eRet = 1;                   /* Value to return if bHaveFK is true */
  int bHaveFK = 0;                /* If FK processing is required */
  if( pParse->db->flags&SQLITE_ForeignKeys && IsOrdinaryTable(pTab) ){
    if( !aChange ){
      /* A DELETE operation. Foreign key processing is required if the
      ** table in question is either the child or parent table for any
      ** foreign key constraint.  */
      bHaveFK = (sqlite3FkReferences(pTab) || pTab->u.tab.pFKey);
    }else{
      /* This is an UPDATE. Foreign key processing is only required if the
123427
123428
123429
123430
123431
123432
123433
123434
123435
123436
123437
123438
123439
123440
123441
** table pTab. Remove the deleted foreign keys from the Schema.fkeyHash
** hash table.
*/
SQLITE_PRIVATE void sqlite3FkDelete(sqlite3 *db, Table *pTab){
  FKey *pFKey;                    /* Iterator variable */
  FKey *pNext;                    /* Copy of pFKey->pNextFrom */

  assert( !IsVirtual(pTab) );
  for(pFKey=pTab->u.tab.pFKey; pFKey; pFKey=pNext){
    assert( db==0 || sqlite3SchemaMutexHeld(db, 0, pTab->pSchema) );

    /* Remove the FK from the fkeyHash hash table. */
    if( !db || db->pnBytesFreed==0 ){
      if( pFKey->pPrevTo ){
        pFKey->pPrevTo->pNextTo = pFKey->pNextTo;







|







124126
124127
124128
124129
124130
124131
124132
124133
124134
124135
124136
124137
124138
124139
124140
** table pTab. Remove the deleted foreign keys from the Schema.fkeyHash
** hash table.
*/
SQLITE_PRIVATE void sqlite3FkDelete(sqlite3 *db, Table *pTab){
  FKey *pFKey;                    /* Iterator variable */
  FKey *pNext;                    /* Copy of pFKey->pNextFrom */

  assert( IsOrdinaryTable(pTab) );
  for(pFKey=pTab->u.tab.pFKey; pFKey; pFKey=pNext){
    assert( db==0 || sqlite3SchemaMutexHeld(db, 0, pTab->pSchema) );

    /* Remove the FK from the fkeyHash hash table. */
    if( !db || db->pnBytesFreed==0 ){
      if( pFKey->pPrevTo ){
        pFKey->pPrevTo->pNextTo = pFKey->pNextTo;
123748
123749
123750
123751
123752
123753
123754
123755
123756
123757
123758
123759
123760
123761
123762
123763
123764
123765
123766
123767
123768
123769
123770
123771
123772






123773
123774
123775
123776
123777
123778
123779
  testcase( pTab->tabFlags & TF_HasVirtual );
  testcase( pTab->tabFlags & TF_HasStored );

  /* Before computing generated columns, first go through and make sure
  ** that appropriate affinity has been applied to the regular columns
  */
  sqlite3TableAffinity(pParse->pVdbe, pTab, iRegStore);
  if( (pTab->tabFlags & TF_HasStored)!=0
   && (pOp = sqlite3VdbeGetOp(pParse->pVdbe,-1))->opcode==OP_Affinity
  ){
    /* Change the OP_Affinity argument to '@' (NONE) for all stored
    ** columns.  '@' is the no-op affinity and those columns have not
    ** yet been computed. */
    int ii, jj;
    char *zP4 = pOp->p4.z;
    assert( zP4!=0 );
    assert( pOp->p4type==P4_DYNAMIC );
    for(ii=jj=0; zP4[jj]; ii++){
      if( pTab->aCol[ii].colFlags & COLFLAG_VIRTUAL ){
        continue;
      }
      if( pTab->aCol[ii].colFlags & COLFLAG_STORED ){
        zP4[jj] = SQLITE_AFF_NONE;
      }
      jj++;






    }
  }

  /* Because there can be multiple generated columns that refer to one another,
  ** this is a two-pass algorithm.  On the first pass, mark all generated
  ** columns as "not available".
  */







|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
>
>
>
>
>
>







124447
124448
124449
124450
124451
124452
124453
124454
124455
124456
124457
124458
124459
124460
124461
124462
124463
124464
124465
124466
124467
124468
124469
124470
124471
124472
124473
124474
124475
124476
124477
124478
124479
124480
124481
124482
124483
124484
  testcase( pTab->tabFlags & TF_HasVirtual );
  testcase( pTab->tabFlags & TF_HasStored );

  /* Before computing generated columns, first go through and make sure
  ** that appropriate affinity has been applied to the regular columns
  */
  sqlite3TableAffinity(pParse->pVdbe, pTab, iRegStore);
  if( (pTab->tabFlags & TF_HasStored)!=0 ){
    pOp = sqlite3VdbeGetOp(pParse->pVdbe,-1);
    if( pOp->opcode==OP_Affinity ){
      /* Change the OP_Affinity argument to '@' (NONE) for all stored
      ** columns.  '@' is the no-op affinity and those columns have not
      ** yet been computed. */
      int ii, jj;
      char *zP4 = pOp->p4.z;
      assert( zP4!=0 );
      assert( pOp->p4type==P4_DYNAMIC );
      for(ii=jj=0; zP4[jj]; ii++){
        if( pTab->aCol[ii].colFlags & COLFLAG_VIRTUAL ){
          continue;
        }
        if( pTab->aCol[ii].colFlags & COLFLAG_STORED ){
          zP4[jj] = SQLITE_AFF_NONE;
        }
        jj++;
      }
    }else if( pOp->opcode==OP_TypeCheck ){
      /* If an OP_TypeCheck was generated because the table is STRICT,
      ** then set the P3 operand to indicate that generated columns should
      ** not be checked */
      pOp->p3 = 1;
    }
  }

  /* Because there can be multiple generated columns that refer to one another,
  ** this is a two-pass algorithm.  On the first pass, mark all generated
  ** columns as "not available".
  */
124842
124843
124844
124845
124846
124847
124848
124849
124850
124851
124852
124853
124854
124855
124856
124857
124858

  /*
  ** Return the number of rows inserted. If this routine is
  ** generating code because of a call to sqlite3NestedParse(), do not
  ** invoke the callback function.
  */
  if( regRowCount ){
    sqlite3VdbeAddOp2(v, OP_ChngCntRow, regRowCount, 1);
    sqlite3VdbeSetNumCols(v, 1);
    sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "rows inserted", SQLITE_STATIC);
  }

insert_cleanup:
  sqlite3SrcListDelete(db, pTabList);
  sqlite3ExprListDelete(db, pList);
  sqlite3UpsertDelete(db, pUpsert);
  sqlite3SelectDelete(db, pSelect);







|
<
<







125547
125548
125549
125550
125551
125552
125553
125554


125555
125556
125557
125558
125559
125560
125561

  /*
  ** Return the number of rows inserted. If this routine is
  ** generating code because of a call to sqlite3NestedParse(), do not
  ** invoke the callback function.
  */
  if( regRowCount ){
    sqlite3CodeChangeCount(v, regRowCount, "rows inserted");


  }

insert_cleanup:
  sqlite3SrcListDelete(db, pTabList);
  sqlite3ExprListDelete(db, pList);
  sqlite3UpsertDelete(db, pUpsert);
  sqlite3SelectDelete(db, pSelect);
125686
125687
125688
125689
125690
125691
125692

125693
125694
125695
125696
125697
125698
125699
    **   (3) There are no secondary indexes on the table
    **   (4) No delete triggers need to be fired if there is a conflict
    **   (5) No FK constraint counters need to be updated if a conflict occurs.
    **
    ** This is not possible for ENABLE_PREUPDATE_HOOK builds, as the row
    ** must be explicitly deleted in order to ensure any pre-update hook
    ** is invoked.  */

#ifndef SQLITE_ENABLE_PREUPDATE_HOOK
    if( (ix==0 && pIdx->pNext==0)                   /* Condition 3 */
     && pPk==pIdx                                   /* Condition 2 */
     && onError==OE_Replace                         /* Condition 1 */
     && ( 0==(db->flags&SQLITE_RecTriggers) ||      /* Condition 4 */
          0==sqlite3TriggersExist(pParse, pTab, TK_DELETE, 0, 0))
     && ( 0==(db->flags&SQLITE_ForeignKeys) ||      /* Condition 5 */







>







126389
126390
126391
126392
126393
126394
126395
126396
126397
126398
126399
126400
126401
126402
126403
    **   (3) There are no secondary indexes on the table
    **   (4) No delete triggers need to be fired if there is a conflict
    **   (5) No FK constraint counters need to be updated if a conflict occurs.
    **
    ** This is not possible for ENABLE_PREUPDATE_HOOK builds, as the row
    ** must be explicitly deleted in order to ensure any pre-update hook
    ** is invoked.  */
    assert( IsOrdinaryTable(pTab) );
#ifndef SQLITE_ENABLE_PREUPDATE_HOOK
    if( (ix==0 && pIdx->pNext==0)                   /* Condition 3 */
     && pPk==pIdx                                   /* Condition 2 */
     && onError==OE_Replace                         /* Condition 1 */
     && ( 0==(db->flags&SQLITE_RecTriggers) ||      /* Condition 4 */
          0==sqlite3TriggersExist(pParse, pTab, TK_DELETE, 0, 0))
     && ( 0==(db->flags&SQLITE_ForeignKeys) ||      /* Condition 5 */
125792
125793
125794
125795
125796
125797
125798
125799

125800
125801
125802
125803
125804
125805
125806
        break;
      }
      default: {
        int nConflictCk;   /* Number of opcodes in conflict check logic */

        assert( onError==OE_Replace );
        nConflictCk = sqlite3VdbeCurrentAddr(v) - addrConflictCk;
        assert( nConflictCk>0 );

        testcase( nConflictCk>1 );
        if( regTrigCnt ){
          sqlite3MultiWrite(pParse);
          nReplaceTrig++;
        }
        if( pTrigger && isUpdate ){
          sqlite3VdbeAddOp1(v, OP_CursorLock, iDataCur);







|
>







126496
126497
126498
126499
126500
126501
126502
126503
126504
126505
126506
126507
126508
126509
126510
126511
        break;
      }
      default: {
        int nConflictCk;   /* Number of opcodes in conflict check logic */

        assert( onError==OE_Replace );
        nConflictCk = sqlite3VdbeCurrentAddr(v) - addrConflictCk;
        assert( nConflictCk>0 || db->mallocFailed );
        testcase( nConflictCk<=0 );
        testcase( nConflictCk>1 );
        if( regTrigCnt ){
          sqlite3MultiWrite(pParse);
          nReplaceTrig++;
        }
        if( pTrigger && isUpdate ){
          sqlite3VdbeAddOp1(v, OP_CursorLock, iDataCur);
126078
126079
126080
126081
126082
126083
126084
126085
126086

126087
126088
126089
126090
126091
126092
126093
  Index *pIdx;
  Vdbe *v;

  assert( op==OP_OpenRead || op==OP_OpenWrite );
  assert( op==OP_OpenWrite || p5==0 );
  if( IsVirtual(pTab) ){
    /* This routine is a no-op for virtual tables. Leave the output
    ** variables *piDataCur and *piIdxCur uninitialized so that valgrind
    ** can detect if they are used by mistake in the caller. */

    return 0;
  }
  iDb = sqlite3SchemaToIndex(pParse->db, pTab->pSchema);
  v = pParse->pVdbe;
  assert( v!=0 );
  if( iBase<0 ) iBase = pParse->nTab;
  iDataCur = iBase++;







|
|
>







126783
126784
126785
126786
126787
126788
126789
126790
126791
126792
126793
126794
126795
126796
126797
126798
126799
  Index *pIdx;
  Vdbe *v;

  assert( op==OP_OpenRead || op==OP_OpenWrite );
  assert( op==OP_OpenWrite || p5==0 );
  if( IsVirtual(pTab) ){
    /* This routine is a no-op for virtual tables. Leave the output
    ** variables *piDataCur and *piIdxCur set to illegal cursor numbers
    ** for improved error detection. */
    *piDataCur = *piIdxCur = -999;
    return 0;
  }
  iDb = sqlite3SchemaToIndex(pParse->db, pTab->pSchema);
  v = pParse->pVdbe;
  assert( v!=0 );
  if( iBase<0 ) iBase = pParse->nTab;
  iDataCur = iBase++;
126366
126367
126368
126369
126370
126371
126372

126373

126374
126375
126376
126377
126378
126379
126380
      return 0;    /* tab2 must be NOT NULL if tab1 is */
    }
    /* Default values for second and subsequent columns need to match. */
    if( (pDestCol->colFlags & COLFLAG_GENERATED)==0 && i>0 ){
      Expr *pDestExpr = sqlite3ColumnExpr(pDest, pDestCol);
      Expr *pSrcExpr = sqlite3ColumnExpr(pSrc, pSrcCol);
      assert( pDestExpr==0 || pDestExpr->op==TK_SPAN );

      assert( pSrcExpr==0 || pSrcExpr->op==TK_SPAN );

      if( (pDestExpr==0)!=(pSrcExpr==0)
       || (pDestExpr!=0 && strcmp(pDestExpr->u.zToken,
                                       pSrcExpr->u.zToken)!=0)
      ){
        return 0;    /* Default values must be the same for all columns */
      }
    }







>

>







127072
127073
127074
127075
127076
127077
127078
127079
127080
127081
127082
127083
127084
127085
127086
127087
127088
      return 0;    /* tab2 must be NOT NULL if tab1 is */
    }
    /* Default values for second and subsequent columns need to match. */
    if( (pDestCol->colFlags & COLFLAG_GENERATED)==0 && i>0 ){
      Expr *pDestExpr = sqlite3ColumnExpr(pDest, pDestCol);
      Expr *pSrcExpr = sqlite3ColumnExpr(pSrc, pSrcCol);
      assert( pDestExpr==0 || pDestExpr->op==TK_SPAN );
      assert( pDestExpr==0 || !ExprHasProperty(pDestExpr, EP_IntValue) );
      assert( pSrcExpr==0 || pSrcExpr->op==TK_SPAN );
      assert( pSrcExpr==0 || !ExprHasProperty(pSrcExpr, EP_IntValue) );
      if( (pDestExpr==0)!=(pSrcExpr==0)
       || (pDestExpr!=0 && strcmp(pDestExpr->u.zToken,
                                       pSrcExpr->u.zToken)!=0)
      ){
        return 0;    /* Default values must be the same for all columns */
      }
    }
126406
126407
126408
126409
126410
126411
126412

126413
126414
126415
126416
126417
126418
126419
  /* Disallow the transfer optimization if the destination table constains
  ** any foreign key constraints.  This is more restrictive than necessary.
  ** But the main beneficiary of the transfer optimization is the VACUUM
  ** command, and the VACUUM command disables foreign key constraints.  So
  ** the extra complication to make this rule less restrictive is probably
  ** not worth the effort.  Ticket [6284df89debdfa61db8073e062908af0c9b6118e]
  */

  if( (db->flags & SQLITE_ForeignKeys)!=0 && pDest->u.tab.pFKey!=0 ){
    return 0;
  }
#endif
  if( (db->flags & SQLITE_CountRows)!=0 ){
    return 0;  /* xfer opt does not play well with PRAGMA count_changes */
  }







>







127114
127115
127116
127117
127118
127119
127120
127121
127122
127123
127124
127125
127126
127127
127128
  /* Disallow the transfer optimization if the destination table constains
  ** any foreign key constraints.  This is more restrictive than necessary.
  ** But the main beneficiary of the transfer optimization is the VACUUM
  ** command, and the VACUUM command disables foreign key constraints.  So
  ** the extra complication to make this rule less restrictive is probably
  ** not worth the effort.  Ticket [6284df89debdfa61db8073e062908af0c9b6118e]
  */
  assert( IsOrdinaryTable(pDest) );
  if( (db->flags & SQLITE_ForeignKeys)!=0 && pDest->u.tab.pFKey!=0 ){
    return 0;
  }
#endif
  if( (db->flags & SQLITE_CountRows)!=0 ){
    return 0;  /* xfer opt does not play well with PRAGMA count_changes */
  }
127087
127088
127089
127090
127091
127092
127093




127094
127095
127096
127097
127098
127099
127100
  void (*free_filename)(char*);
  sqlite3_file *(*database_file_object)(const char*);
  /* Version 3.34.0 and later */
  int (*txn_state)(sqlite3*,const char*);
  /* Version 3.36.1 and later */
  sqlite3_int64 (*changes64)(sqlite3*);
  sqlite3_int64 (*total_changes64)(sqlite3*);




};

/*
** This is the function signature used for all extension entry points.  It
** is also defined in the file "loadext.c".
*/
typedef int (*sqlite3_loadext_entry)(







>
>
>
>







127796
127797
127798
127799
127800
127801
127802
127803
127804
127805
127806
127807
127808
127809
127810
127811
127812
127813
  void (*free_filename)(char*);
  sqlite3_file *(*database_file_object)(const char*);
  /* Version 3.34.0 and later */
  int (*txn_state)(sqlite3*,const char*);
  /* Version 3.36.1 and later */
  sqlite3_int64 (*changes64)(sqlite3*);
  sqlite3_int64 (*total_changes64)(sqlite3*);
  /* Version 3.37.0 and later */
  int (*autovacuum_pages)(sqlite3*,
     unsigned int(*)(void*,const char*,unsigned int,unsigned int,unsigned int),
     void*, void(*)(void*));
};

/*
** This is the function signature used for all extension entry points.  It
** is also defined in the file "loadext.c".
*/
typedef int (*sqlite3_loadext_entry)(
127393
127394
127395
127396
127397
127398
127399





127400
127401
127402
127403
127404
127405
127406
#define sqlite3_filename_wal           sqlite3_api->filename_wal
/* Version 3.32.0 and later */
#define sqlite3_create_filename        sqlite3_api->create_filename
#define sqlite3_free_filename          sqlite3_api->free_filename
#define sqlite3_database_file_object   sqlite3_api->database_file_object
/* Version 3.34.0 and later */
#define sqlite3_txn_state              sqlite3_api->txn_state





#endif /* !defined(SQLITE_CORE) && !defined(SQLITE_OMIT_LOAD_EXTENSION) */

#if !defined(SQLITE_CORE) && !defined(SQLITE_OMIT_LOAD_EXTENSION)
  /* This case when the file really is being compiled as a loadable
  ** extension */
# define SQLITE_EXTENSION_INIT1     const sqlite3_api_routines *sqlite3_api=0;
# define SQLITE_EXTENSION_INIT2(v)  sqlite3_api=v;







>
>
>
>
>







128106
128107
128108
128109
128110
128111
128112
128113
128114
128115
128116
128117
128118
128119
128120
128121
128122
128123
128124
#define sqlite3_filename_wal           sqlite3_api->filename_wal
/* Version 3.32.0 and later */
#define sqlite3_create_filename        sqlite3_api->create_filename
#define sqlite3_free_filename          sqlite3_api->free_filename
#define sqlite3_database_file_object   sqlite3_api->database_file_object
/* Version 3.34.0 and later */
#define sqlite3_txn_state              sqlite3_api->txn_state
/* Version 3.36.1 and later */
#define sqlite3_changes64              sqlite3_api->changes64
#define sqlite3_total_changes64        sqlite3_api->total_changes64
/* Version 3.37.0 and later */
#define sqlite3_autovacuum_pages       sqlite3_api->autovacuum_pages
#endif /* !defined(SQLITE_CORE) && !defined(SQLITE_OMIT_LOAD_EXTENSION) */

#if !defined(SQLITE_CORE) && !defined(SQLITE_OMIT_LOAD_EXTENSION)
  /* This case when the file really is being compiled as a loadable
  ** extension */
# define SQLITE_EXTENSION_INIT1     const sqlite3_api_routines *sqlite3_api=0;
# define SQLITE_EXTENSION_INIT2(v)  sqlite3_api=v;
127880
127881
127882
127883
127884
127885
127886


127887
127888
127889
127890
127891
127892
127893
  sqlite3_free_filename,
  sqlite3_database_file_object,
  /* Version 3.34.0 and later */
  sqlite3_txn_state,
  /* Version 3.36.1 and later */
  sqlite3_changes64,
  sqlite3_total_changes64,


};

/* True if x is the directory separator character
*/
#if SQLITE_OS_WIN
# define DirSep(X)  ((X)=='/'||(X)=='\\')
#else







>
>







128598
128599
128600
128601
128602
128603
128604
128605
128606
128607
128608
128609
128610
128611
128612
128613
  sqlite3_free_filename,
  sqlite3_database_file_object,
  /* Version 3.34.0 and later */
  sqlite3_txn_state,
  /* Version 3.36.1 and later */
  sqlite3_changes64,
  sqlite3_total_changes64,
  /* Version 3.37.0 and later */
  sqlite3_autovacuum_pages,
};

/* True if x is the directory separator character
*/
#if SQLITE_OS_WIN
# define DirSep(X)  ((X)=='/'||(X)=='\\')
#else
128869
128870
128871
128872
128873
128874
128875
128876
128877
128878
128879
128880
128881
128882
128883
  /* ePragFlg:  */ PragFlg_NeedSchema|PragFlg_Result1|PragFlg_SchemaOpt,
  /* ColNames:  */ 8, 6,
  /* iArg:      */ 0 },
 {/* zName:     */ "table_list",
  /* ePragTyp:  */ PragTyp_TABLE_LIST,
  /* ePragFlg:  */ PragFlg_NeedSchema|PragFlg_Result1,
  /* ColNames:  */ 15, 6,
  /* iArg:      */ 1 },
 {/* zName:     */ "table_xinfo",
  /* ePragTyp:  */ PragTyp_TABLE_INFO,
  /* ePragFlg:  */ PragFlg_NeedSchema|PragFlg_Result1|PragFlg_SchemaOpt,
  /* ColNames:  */ 8, 7,
  /* iArg:      */ 1 },
#endif
#if !defined(SQLITE_OMIT_PAGER_PRAGMAS)







|







129589
129590
129591
129592
129593
129594
129595
129596
129597
129598
129599
129600
129601
129602
129603
  /* ePragFlg:  */ PragFlg_NeedSchema|PragFlg_Result1|PragFlg_SchemaOpt,
  /* ColNames:  */ 8, 6,
  /* iArg:      */ 0 },
 {/* zName:     */ "table_list",
  /* ePragTyp:  */ PragTyp_TABLE_LIST,
  /* ePragFlg:  */ PragFlg_NeedSchema|PragFlg_Result1,
  /* ColNames:  */ 15, 6,
  /* iArg:      */ 0 },
 {/* zName:     */ "table_xinfo",
  /* ePragTyp:  */ PragTyp_TABLE_INFO,
  /* ePragFlg:  */ PragFlg_NeedSchema|PragFlg_Result1|PragFlg_SchemaOpt,
  /* ColNames:  */ 8, 7,
  /* iArg:      */ 1 },
#endif
#if !defined(SQLITE_OMIT_PAGER_PRAGMAS)
129398
129399
129400
129401
129402
129403
129404
129405




129406
129407
129408
129409
129410
129411
129412
    pParse->nErr++;
    pParse->rc = rc;
    goto pragma_out;
  }

  /* Locate the pragma in the lookup table */
  pPragma = pragmaLocate(zLeft);
  if( pPragma==0 ) goto pragma_out;





  /* Make sure the database schema is loaded if the pragma requires that */
  if( (pPragma->mPragFlg & PragFlg_NeedSchema)!=0 ){
    if( sqlite3ReadSchema(pParse) ) goto pragma_out;
  }

  /* Register the result column names for pragmas that return results */







|
>
>
>
>







130118
130119
130120
130121
130122
130123
130124
130125
130126
130127
130128
130129
130130
130131
130132
130133
130134
130135
130136
    pParse->nErr++;
    pParse->rc = rc;
    goto pragma_out;
  }

  /* Locate the pragma in the lookup table */
  pPragma = pragmaLocate(zLeft);
  if( pPragma==0 ){
    /* IMP: R-43042-22504 No error messages are generated if an
    ** unknown pragma is issued. */
    goto pragma_out;
  }

  /* Make sure the database schema is loaded if the pragma requires that */
  if( (pPragma->mPragFlg & PragFlg_NeedSchema)!=0 ){
    if( sqlite3ReadSchema(pParse) ) goto pragma_out;
  }

  /* Register the result column names for pragmas that return results */
130048
130049
130050
130051
130052
130053
130054








130055
130056
130057
130058
130059
130060
130061
#endif

      if( sqlite3GetBoolean(zRight, 0) ){
        db->flags |= mask;
      }else{
        db->flags &= ~mask;
        if( mask==SQLITE_DeferFKs ) db->nDeferredImmCons = 0;








      }

      /* Many of the flag-pragmas modify the code generated by the SQL
      ** compiler (eg. count_changes). So add an opcode to expire all
      ** compiled SQL statements after modifying a pragma value.
      */
      sqlite3VdbeAddOp0(v, OP_Expire);







>
>
>
>
>
>
>
>







130772
130773
130774
130775
130776
130777
130778
130779
130780
130781
130782
130783
130784
130785
130786
130787
130788
130789
130790
130791
130792
130793
#endif

      if( sqlite3GetBoolean(zRight, 0) ){
        db->flags |= mask;
      }else{
        db->flags &= ~mask;
        if( mask==SQLITE_DeferFKs ) db->nDeferredImmCons = 0;
        if( (mask & SQLITE_WriteSchema)!=0
         && sqlite3_stricmp(zRight, "reset")==0
        ){
          /* IMP: R-60817-01178 If the argument is "RESET" then schema
          ** writing is disabled (as with "PRAGMA writable_schema=OFF") and,
          ** in addition, the schema is reloaded. */
          sqlite3ResetAllSchemasOfConnection(db);
        }
      }

      /* Many of the flag-pragmas modify the code generated by the SQL
      ** compiler (eg. count_changes). So add an opcode to expire all
      ** compiled SQL statements after modifying a pragma value.
      */
      sqlite3VdbeAddOp0(v, OP_Expire);
130088
130089
130090
130091
130092
130093
130094

130095
130096
130097
130098
130099
130100
130101
130102
130103
130104
130105
130106
130107
130108
130109
130110
130111
130112
130113
130114
130115
130116

130117
130118
130119
130120
130121
130122
130123
130124
130125
130126
130127
130128
130129
130130
130131
      int nHidden = 0;
      Column *pCol;
      Index *pPk = sqlite3PrimaryKeyIndex(pTab);
      pParse->nMem = 7;
      sqlite3ViewGetColumnNames(pParse, pTab);
      for(i=0, pCol=pTab->aCol; i<pTab->nCol; i++, pCol++){
        int isHidden = 0;

        if( pCol->colFlags & COLFLAG_NOINSERT ){
          if( pPragma->iArg==0 ){
            nHidden++;
            continue;
          }
          if( pCol->colFlags & COLFLAG_VIRTUAL ){
            isHidden = 2;  /* GENERATED ALWAYS AS ... VIRTUAL */
          }else if( pCol->colFlags & COLFLAG_STORED ){
            isHidden = 3;  /* GENERATED ALWAYS AS ... STORED */
          }else{ assert( pCol->colFlags & COLFLAG_HIDDEN );
            isHidden = 1;  /* HIDDEN */
          }
        }
        if( (pCol->colFlags & COLFLAG_PRIMKEY)==0 ){
          k = 0;
        }else if( pPk==0 ){
          k = 1;
        }else{
          for(k=1; k<=pTab->nCol && pPk->aiColumn[k-1]!=i; k++){}
        }
        assert( sqlite3ColumnExpr(pTab,pCol)==0
             || sqlite3ColumnExpr(pTab,pCol)->op==TK_SPAN

             || isHidden>=2 );
        sqlite3VdbeMultiLoad(v, 1, pPragma->iArg ? "issisii" : "issisi",
               i-nHidden,
               pCol->zCnName,
               sqlite3ColumnType(pCol,""),
               pCol->notNull ? 1 : 0,
               isHidden>=2 || sqlite3ColumnExpr(pTab,pCol)==0 ? 0 :
                          sqlite3ColumnExpr(pTab,pCol)->u.zToken,
               k,
               isHidden);
      }
    }
  }
  break;








>




















|
|
>
|





|
<







130820
130821
130822
130823
130824
130825
130826
130827
130828
130829
130830
130831
130832
130833
130834
130835
130836
130837
130838
130839
130840
130841
130842
130843
130844
130845
130846
130847
130848
130849
130850
130851
130852
130853
130854
130855
130856
130857

130858
130859
130860
130861
130862
130863
130864
      int nHidden = 0;
      Column *pCol;
      Index *pPk = sqlite3PrimaryKeyIndex(pTab);
      pParse->nMem = 7;
      sqlite3ViewGetColumnNames(pParse, pTab);
      for(i=0, pCol=pTab->aCol; i<pTab->nCol; i++, pCol++){
        int isHidden = 0;
        const Expr *pColExpr;
        if( pCol->colFlags & COLFLAG_NOINSERT ){
          if( pPragma->iArg==0 ){
            nHidden++;
            continue;
          }
          if( pCol->colFlags & COLFLAG_VIRTUAL ){
            isHidden = 2;  /* GENERATED ALWAYS AS ... VIRTUAL */
          }else if( pCol->colFlags & COLFLAG_STORED ){
            isHidden = 3;  /* GENERATED ALWAYS AS ... STORED */
          }else{ assert( pCol->colFlags & COLFLAG_HIDDEN );
            isHidden = 1;  /* HIDDEN */
          }
        }
        if( (pCol->colFlags & COLFLAG_PRIMKEY)==0 ){
          k = 0;
        }else if( pPk==0 ){
          k = 1;
        }else{
          for(k=1; k<=pTab->nCol && pPk->aiColumn[k-1]!=i; k++){}
        }
        pColExpr = sqlite3ColumnExpr(pTab,pCol);
        assert( pColExpr==0 || pColExpr->op==TK_SPAN || isHidden>=2 );
        assert( pColExpr==0 || !ExprHasProperty(pColExpr, EP_IntValue)
                  || isHidden>=2 );
        sqlite3VdbeMultiLoad(v, 1, pPragma->iArg ? "issisii" : "issisi",
               i-nHidden,
               pCol->zCnName,
               sqlite3ColumnType(pCol,""),
               pCol->notNull ? 1 : 0,
               (isHidden>=2 || pColExpr==0) ? 0 : pColExpr->u.zToken,

               k,
               isHidden);
      }
    }
  }
  break;

130145
130146
130147
130148
130149
130150
130151

130152






130153




















130154
130155
130156
130157
130158
130159
130160
130161
130162
130163
130164
130165
130166
130167
130168
130169
130170
130171
130172
130173
130174
130175
130176
130177
130178
130179
130180
130181
130182
130183
130184
130185
130186
130187
130188
130189
130190
130191
130192
130193
130194
130195
130196
  case PragTyp_TABLE_LIST: {
    int ii;
    pParse->nMem = 6;
    sqlite3CodeVerifyNamedSchema(pParse, zDb);
    for(ii=0; ii<db->nDb; ii++){
      HashElem *k;
      Hash *pHash;

      if( zDb && sqlite3_stricmp(zDb, db->aDb[ii].zDbSName)!=0 ) continue;






      pHash = &db->aDb[ii].pSchema->tblHash;




















      for(k=sqliteHashFirst(pHash); k; k=sqliteHashNext(k) ){
        Table *pTab = sqliteHashData(k);
        const char *zType;
        if( zRight && sqlite3_stricmp(zRight, pTab->zName)!=0 ) continue;
        if( IsView(pTab) ){
          zType = "view";
        }else if( IsVirtual(pTab) ){
          zType = "virtual";
        }else if( pTab->tabFlags & TF_Shadow ){
          zType = "shadow";
        }else{
          zType = "table";
        }
        sqlite3VdbeMultiLoad(v, 1, "sssiii",
           db->aDb[ii].zDbSName,
           pTab->zName,
           zType,
           pTab->nCol,
           (pTab->tabFlags & TF_WithoutRowid)!=0,
           (pTab->tabFlags & TF_Strict)!=0
        );
      }
    }
  }
  break;

#ifdef SQLITE_DEBUG
  case PragTyp_STATS: {
    Index *pIdx;
    HashElem *i;
    pParse->nMem = 5;
    sqlite3CodeVerifySchema(pParse, iDb);
    for(i=sqliteHashFirst(&pDb->pSchema->tblHash); i; i=sqliteHashNext(i)){
      Table *pTab = sqliteHashData(i);
      sqlite3VdbeMultiLoad(v, 1, "ssiii",
           pTab->zName,
           0,
           pTab->szTabRow,
           pTab->nRowLogEst,
           pTab->tabFlags);
      for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){
        sqlite3VdbeMultiLoad(v, 2, "siiiX",
           pIdx->zName,







>

>
>
>
>
>
>

>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>















|



















|







130878
130879
130880
130881
130882
130883
130884
130885
130886
130887
130888
130889
130890
130891
130892
130893
130894
130895
130896
130897
130898
130899
130900
130901
130902
130903
130904
130905
130906
130907
130908
130909
130910
130911
130912
130913
130914
130915
130916
130917
130918
130919
130920
130921
130922
130923
130924
130925
130926
130927
130928
130929
130930
130931
130932
130933
130934
130935
130936
130937
130938
130939
130940
130941
130942
130943
130944
130945
130946
130947
130948
130949
130950
130951
130952
130953
130954
130955
130956
  case PragTyp_TABLE_LIST: {
    int ii;
    pParse->nMem = 6;
    sqlite3CodeVerifyNamedSchema(pParse, zDb);
    for(ii=0; ii<db->nDb; ii++){
      HashElem *k;
      Hash *pHash;
      int initNCol;
      if( zDb && sqlite3_stricmp(zDb, db->aDb[ii].zDbSName)!=0 ) continue;

      /* Ensure that the Table.nCol field is initialized for all views
      ** and virtual tables.  Each time we initialize a Table.nCol value
      ** for a table, that can potentially disrupt the hash table, so restart
      ** the initialization scan.
      */
      pHash = &db->aDb[ii].pSchema->tblHash;
      initNCol = sqliteHashCount(pHash);
      while( initNCol-- ){
        for(k=sqliteHashFirst(pHash); 1; k=sqliteHashNext(k) ){
          Table *pTab;
          if( k==0 ){ initNCol = 0; break; }
          pTab = sqliteHashData(k);
          if( pTab->nCol==0 ){
            char *zSql = sqlite3MPrintf(db, "SELECT*FROM\"%w\"", pTab->zName);
            if( zSql ){
              sqlite3_stmt *pDummy = 0;
              (void)sqlite3_prepare(db, zSql, -1, &pDummy, 0);
              (void)sqlite3_finalize(pDummy);
              sqlite3DbFree(db, zSql);
            }
            pHash = &db->aDb[ii].pSchema->tblHash;
            break;
          }
        }
      }

      for(k=sqliteHashFirst(pHash); k; k=sqliteHashNext(k) ){
        Table *pTab = sqliteHashData(k);
        const char *zType;
        if( zRight && sqlite3_stricmp(zRight, pTab->zName)!=0 ) continue;
        if( IsView(pTab) ){
          zType = "view";
        }else if( IsVirtual(pTab) ){
          zType = "virtual";
        }else if( pTab->tabFlags & TF_Shadow ){
          zType = "shadow";
        }else{
          zType = "table";
        }
        sqlite3VdbeMultiLoad(v, 1, "sssiii",
           db->aDb[ii].zDbSName,
           sqlite3PreferredTableName(pTab->zName),
           zType,
           pTab->nCol,
           (pTab->tabFlags & TF_WithoutRowid)!=0,
           (pTab->tabFlags & TF_Strict)!=0
        );
      }
    }
  }
  break;

#ifdef SQLITE_DEBUG
  case PragTyp_STATS: {
    Index *pIdx;
    HashElem *i;
    pParse->nMem = 5;
    sqlite3CodeVerifySchema(pParse, iDb);
    for(i=sqliteHashFirst(&pDb->pSchema->tblHash); i; i=sqliteHashNext(i)){
      Table *pTab = sqliteHashData(i);
      sqlite3VdbeMultiLoad(v, 1, "ssiii",
           sqlite3PreferredTableName(pTab->zName),
           0,
           pTab->szTabRow,
           pTab->nRowLogEst,
           pTab->tabFlags);
      for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){
        sqlite3VdbeMultiLoad(v, 2, "siiiX",
           pIdx->zName,
130301
130302
130303
130304
130305
130306
130307

130308
130309
130310
130311
130312

130313
130314
130315
130316
130317
130318
130319
    int i;
    HashElem *j;
    FuncDef *p;
    int showInternFunc = (db->mDbFlags & DBFLAG_InternalFunc)!=0;
    pParse->nMem = 6;
    for(i=0; i<SQLITE_FUNC_HASH_SZ; i++){
      for(p=sqlite3BuiltinFunctions.a[i]; p; p=p->u.pHash ){

        pragmaFunclistLine(v, p, 1, showInternFunc);
      }
    }
    for(j=sqliteHashFirst(&db->aFunc); j; j=sqliteHashNext(j)){
      p = (FuncDef*)sqliteHashData(j);

      pragmaFunclistLine(v, p, 0, showInternFunc);
    }
  }
  break;

#ifndef SQLITE_OMIT_VIRTUALTABLE
  case PragTyp_MODULE_LIST: {







>





>







131061
131062
131063
131064
131065
131066
131067
131068
131069
131070
131071
131072
131073
131074
131075
131076
131077
131078
131079
131080
131081
    int i;
    HashElem *j;
    FuncDef *p;
    int showInternFunc = (db->mDbFlags & DBFLAG_InternalFunc)!=0;
    pParse->nMem = 6;
    for(i=0; i<SQLITE_FUNC_HASH_SZ; i++){
      for(p=sqlite3BuiltinFunctions.a[i]; p; p=p->u.pHash ){
        assert( p->funcFlags & SQLITE_FUNC_BUILTIN );
        pragmaFunclistLine(v, p, 1, showInternFunc);
      }
    }
    for(j=sqliteHashFirst(&db->aFunc); j; j=sqliteHashNext(j)){
      p = (FuncDef*)sqliteHashData(j);
      assert( (p->funcFlags & SQLITE_FUNC_BUILTIN)==0 );
      pragmaFunclistLine(v, p, 0, showInternFunc);
    }
  }
  break;

#ifndef SQLITE_OMIT_VIRTUALTABLE
  case PragTyp_MODULE_LIST: {
130339
130340
130341
130342
130343
130344
130345
130346
130347
130348
130349
130350
130351
130352
130353
#endif /* SQLITE_OMIT_SCHEMA_PRAGMAS */

#ifndef SQLITE_OMIT_FOREIGN_KEY
  case PragTyp_FOREIGN_KEY_LIST: if( zRight ){
    FKey *pFK;
    Table *pTab;
    pTab = sqlite3FindTable(db, zRight, zDb);
    if( pTab && !IsVirtual(pTab) ){
      pFK = pTab->u.tab.pFKey;
      if( pFK ){
        int iTabDb = sqlite3SchemaToIndex(db, pTab->pSchema);
        int i = 0;
        pParse->nMem = 8;
        sqlite3CodeVerifySchema(pParse, iTabDb);
        while(pFK){







|







131101
131102
131103
131104
131105
131106
131107
131108
131109
131110
131111
131112
131113
131114
131115
#endif /* SQLITE_OMIT_SCHEMA_PRAGMAS */

#ifndef SQLITE_OMIT_FOREIGN_KEY
  case PragTyp_FOREIGN_KEY_LIST: if( zRight ){
    FKey *pFK;
    Table *pTab;
    pTab = sqlite3FindTable(db, zRight, zDb);
    if( pTab && IsOrdinaryTable(pTab) ){
      pFK = pTab->u.tab.pFKey;
      if( pFK ){
        int iTabDb = sqlite3SchemaToIndex(db, pTab->pSchema);
        int i = 0;
        pParse->nMem = 8;
        sqlite3CodeVerifySchema(pParse, iTabDb);
        while(pFK){
130399
130400
130401
130402
130403
130404
130405
130406
130407
130408
130409
130410
130411
130412
130413
130414
130415
130416
130417
130418
130419
130420
130421
      if( zRight ){
        pTab = sqlite3LocateTable(pParse, 0, zRight, zDb);
        k = 0;
      }else{
        pTab = (Table*)sqliteHashData(k);
        k = sqliteHashNext(k);
      }
      if( pTab==0 || IsVirtual(pTab) || pTab->u.tab.pFKey==0 ) continue;
      iDb = sqlite3SchemaToIndex(db, pTab->pSchema);
      zDb = db->aDb[iDb].zDbSName;
      sqlite3CodeVerifySchema(pParse, iDb);
      sqlite3TableLock(pParse, iDb, pTab->tnum, 0, pTab->zName);
      if( pTab->nCol+regRow>pParse->nMem ) pParse->nMem = pTab->nCol + regRow;
      sqlite3OpenTable(pParse, 0, iDb, pTab, OP_OpenRead);
      sqlite3VdbeLoadString(v, regResult, pTab->zName);
      assert( !IsVirtual(pTab) );
      for(i=1, pFK=pTab->u.tab.pFKey; pFK; i++, pFK=pFK->pNextFrom){
        pParent = sqlite3FindTable(db, pFK->zTo, zDb);
        if( pParent==0 ) continue;
        pIdx = 0;
        sqlite3TableLock(pParse, iDb, pParent->tnum, 0, pParent->zName);
        x = sqlite3FkLocateIndex(pParse, pParent, pFK, &pIdx, 0);
        if( x==0 ){







|







|







131161
131162
131163
131164
131165
131166
131167
131168
131169
131170
131171
131172
131173
131174
131175
131176
131177
131178
131179
131180
131181
131182
131183
      if( zRight ){
        pTab = sqlite3LocateTable(pParse, 0, zRight, zDb);
        k = 0;
      }else{
        pTab = (Table*)sqliteHashData(k);
        k = sqliteHashNext(k);
      }
      if( pTab==0 || !IsOrdinaryTable(pTab) || pTab->u.tab.pFKey==0 ) continue;
      iDb = sqlite3SchemaToIndex(db, pTab->pSchema);
      zDb = db->aDb[iDb].zDbSName;
      sqlite3CodeVerifySchema(pParse, iDb);
      sqlite3TableLock(pParse, iDb, pTab->tnum, 0, pTab->zName);
      if( pTab->nCol+regRow>pParse->nMem ) pParse->nMem = pTab->nCol + regRow;
      sqlite3OpenTable(pParse, 0, iDb, pTab, OP_OpenRead);
      sqlite3VdbeLoadString(v, regResult, pTab->zName);
      assert( IsOrdinaryTable(pTab) );
      for(i=1, pFK=pTab->u.tab.pFKey; pFK; i++, pFK=pFK->pNextFrom){
        pParent = sqlite3FindTable(db, pFK->zTo, zDb);
        if( pParent==0 ) continue;
        pIdx = 0;
        sqlite3TableLock(pParse, iDb, pParent->tnum, 0, pParent->zName);
        x = sqlite3FkLocateIndex(pParse, pParent, pFK, &pIdx, 0);
        if( x==0 ){
130430
130431
130432
130433
130434
130435
130436
130437
130438
130439
130440
130441
130442
130443
130444
          break;
        }
      }
      assert( pParse->nErr>0 || pFK==0 );
      if( pFK ) break;
      if( pParse->nTab<i ) pParse->nTab = i;
      addrTop = sqlite3VdbeAddOp1(v, OP_Rewind, 0); VdbeCoverage(v);
      assert( !IsVirtual(pTab) );
      for(i=1, pFK=pTab->u.tab.pFKey; pFK; i++, pFK=pFK->pNextFrom){
        pParent = sqlite3FindTable(db, pFK->zTo, zDb);
        pIdx = 0;
        aiCols = 0;
        if( pParent ){
          x = sqlite3FkLocateIndex(pParse, pParent, pFK, &pIdx, &aiCols);
          assert( x==0 || db->mallocFailed );







|







131192
131193
131194
131195
131196
131197
131198
131199
131200
131201
131202
131203
131204
131205
131206
          break;
        }
      }
      assert( pParse->nErr>0 || pFK==0 );
      if( pFK ) break;
      if( pParse->nTab<i ) pParse->nTab = i;
      addrTop = sqlite3VdbeAddOp1(v, OP_Rewind, 0); VdbeCoverage(v);
      assert( IsOrdinaryTable(pTab) );
      for(i=1, pFK=pTab->u.tab.pFKey; pFK; i++, pFK=pFK->pNextFrom){
        pParent = sqlite3FindTable(db, pFK->zTo, zDb);
        pIdx = 0;
        aiCols = 0;
        if( pParent ){
          x = sqlite3FkLocateIndex(pParse, pParent, pFK, &pIdx, &aiCols);
          assert( x==0 || db->mallocFailed );
130634
130635
130636
130637
130638
130639
130640
130641
130642
130643
130644
130645
130646
130647
130648
        Index *pIdx, *pPk;
        Index *pPrior = 0;
        int loopTop;
        int iDataCur, iIdxCur;
        int r1 = -1;
        int bStrict;

        if( pTab->tnum<1 ) continue;  /* Skip VIEWs or VIRTUAL TABLEs */
        if( pObjTab && pObjTab!=pTab ) continue;
        pPk = HasRowid(pTab) ? 0 : sqlite3PrimaryKeyIndex(pTab);
        sqlite3OpenTableAndIndices(pParse, pTab, OP_OpenRead, 0,
                                   1, 0, &iDataCur, &iIdxCur);
        /* reg[7] counts the number of entries in the table.
        ** reg[8+i] counts the number of entries in the i-th index
        */







|







131396
131397
131398
131399
131400
131401
131402
131403
131404
131405
131406
131407
131408
131409
131410
        Index *pIdx, *pPk;
        Index *pPrior = 0;
        int loopTop;
        int iDataCur, iIdxCur;
        int r1 = -1;
        int bStrict;

        if( !IsOrdinaryTable(pTab) ) continue;
        if( pObjTab && pObjTab!=pTab ) continue;
        pPk = HasRowid(pTab) ? 0 : sqlite3PrimaryKeyIndex(pTab);
        sqlite3OpenTableAndIndices(pParse, pTab, OP_OpenRead, 0,
                                   1, 0, &iDataCur, &iIdxCur);
        /* reg[7] counts the number of entries in the table.
        ** reg[8+i] counts the number of entries in the i-th index
        */
130675
130676
130677
130678
130679
130680
130681
130682
130683
130684
130685
130686
130687
130688
130689
            sqlite3VdbeChangeP5(v, OPFLAG_TYPEOFARG);
          }
          if( pCol->notNull ){
            jmp2 = sqlite3VdbeAddOp1(v, OP_NotNull, 3); VdbeCoverage(v);
            zErr = sqlite3MPrintf(db, "NULL value in %s.%s", pTab->zName,
                                pCol->zCnName);
            sqlite3VdbeAddOp4(v, OP_String8, 0, 3, 0, zErr, P4_DYNAMIC);
            if( bStrict ){
              sqlite3VdbeGoto(v, doError);
            }else{
              integrityCheckResultRow(v);
            }
            sqlite3VdbeJumpHere(v, jmp2);
          }
          if( (pTab->tabFlags & TF_Strict)!=0







|







131437
131438
131439
131440
131441
131442
131443
131444
131445
131446
131447
131448
131449
131450
131451
            sqlite3VdbeChangeP5(v, OPFLAG_TYPEOFARG);
          }
          if( pCol->notNull ){
            jmp2 = sqlite3VdbeAddOp1(v, OP_NotNull, 3); VdbeCoverage(v);
            zErr = sqlite3MPrintf(db, "NULL value in %s.%s", pTab->zName,
                                pCol->zCnName);
            sqlite3VdbeAddOp4(v, OP_String8, 0, 3, 0, zErr, P4_DYNAMIC);
            if( bStrict && pCol->eCType!=COLTYPE_ANY ){
              sqlite3VdbeGoto(v, doError);
            }else{
              integrityCheckResultRow(v);
            }
            sqlite3VdbeJumpHere(v, jmp2);
          }
          if( (pTab->tabFlags & TF_Strict)!=0
131229
131230
131231
131232
131233
131234
131235
131236
131237
131238
131239
131240
131241
131242
131243
131244
131245
131246
131247
131248
  **
  ** Configure the maximum number of rows that ANALYZE will examine
  ** in each index that it looks at.  Return the new limit.
  */
  case PragTyp_ANALYSIS_LIMIT: {
    sqlite3_int64 N;
    if( zRight
     && sqlite3DecOrHexToI64(zRight, &N)==SQLITE_OK
     && N>=0
    ){
      db->nAnalysisLimit = (int)(N&0x7fffffff);
    }
    returnSingleInt(v, db->nAnalysisLimit);
    break;
  }

#if defined(SQLITE_DEBUG) || defined(SQLITE_TEST)
  /*
  ** Report the current state of file logs for all databases
  */







|




|







131991
131992
131993
131994
131995
131996
131997
131998
131999
132000
132001
132002
132003
132004
132005
132006
132007
132008
132009
132010
  **
  ** Configure the maximum number of rows that ANALYZE will examine
  ** in each index that it looks at.  Return the new limit.
  */
  case PragTyp_ANALYSIS_LIMIT: {
    sqlite3_int64 N;
    if( zRight
     && sqlite3DecOrHexToI64(zRight, &N)==SQLITE_OK /* IMP: R-40975-20399 */
     && N>=0
    ){
      db->nAnalysisLimit = (int)(N&0x7fffffff);
    }
    returnSingleInt(v, db->nAnalysisLimit); /* IMP: R-57594-65522 */
    break;
  }

#if defined(SQLITE_DEBUG) || defined(SQLITE_TEST)
  /*
  ** Report the current state of file logs for all databases
  */
131636
131637
131638
131639
131640
131641
131642
131643





131644
131645
131646
131647
131648
131649
131650
131651
131652
131653
  const char *zExtra   /* Error information */
){
  sqlite3 *db = pData->db;
  if( db->mallocFailed ){
    pData->rc = SQLITE_NOMEM_BKPT;
  }else if( pData->pzErrMsg[0]!=0 ){
    /* A error message has already been generated.  Do not overwrite it */
  }else if( pData->mInitFlags & (INITFLAG_AlterRename|INITFLAG_AlterDrop) ){





    *pData->pzErrMsg = sqlite3MPrintf(db,
        "error in %s %s after %s: %s", azObj[0], azObj[1],
        (pData->mInitFlags & INITFLAG_AlterRename) ? "rename" : "drop column",
        zExtra
    );
    pData->rc = SQLITE_ERROR;
  }else if( db->flags & SQLITE_WriteSchema ){
    pData->rc = SQLITE_CORRUPT_BKPT;
  }else{
    char *z;







|
>
>
>
>
>


|







132398
132399
132400
132401
132402
132403
132404
132405
132406
132407
132408
132409
132410
132411
132412
132413
132414
132415
132416
132417
132418
132419
132420
  const char *zExtra   /* Error information */
){
  sqlite3 *db = pData->db;
  if( db->mallocFailed ){
    pData->rc = SQLITE_NOMEM_BKPT;
  }else if( pData->pzErrMsg[0]!=0 ){
    /* A error message has already been generated.  Do not overwrite it */
  }else if( pData->mInitFlags & (INITFLAG_AlterMask) ){
    static const char *azAlterType[] = {
       "rename",
       "drop column",
       "add column"
    };
    *pData->pzErrMsg = sqlite3MPrintf(db,
        "error in %s %s after %s: %s", azObj[0], azObj[1],
        azAlterType[(pData->mInitFlags&INITFLAG_AlterMask)-1],
        zExtra
    );
    pData->rc = SQLITE_ERROR;
  }else if( db->flags & SQLITE_WriteSchema ){
    pData->rc = SQLITE_CORRUPT_BKPT;
  }else{
    char *z;
132410
132411
132412
132413
132414
132415
132416

132417
132418
132419
132420
132421
132422
132423
  sqlite3BtreeEnterAll(db);
  do{
    /* Make multiple attempts to compile the SQL, until it either succeeds
    ** or encounters a permanent error.  A schema problem after one schema
    ** reset is considered a permanent error. */
    rc = sqlite3Prepare(db, zSql, nBytes, prepFlags, pOld, ppStmt, pzTail);
    assert( rc==SQLITE_OK || *ppStmt==0 );

  }while( rc==SQLITE_ERROR_RETRY
       || (rc==SQLITE_SCHEMA && (sqlite3ResetOneSchema(db,-1), cnt++)==0) );
  sqlite3BtreeLeaveAll(db);
  rc = sqlite3ApiExit(db, rc);
  assert( (rc&db->errMask)==rc );
  db->busyHandler.nBusy = 0;
  sqlite3_mutex_leave(db->mutex);







>







133177
133178
133179
133180
133181
133182
133183
133184
133185
133186
133187
133188
133189
133190
133191
  sqlite3BtreeEnterAll(db);
  do{
    /* Make multiple attempts to compile the SQL, until it either succeeds
    ** or encounters a permanent error.  A schema problem after one schema
    ** reset is considered a permanent error. */
    rc = sqlite3Prepare(db, zSql, nBytes, prepFlags, pOld, ppStmt, pzTail);
    assert( rc==SQLITE_OK || *ppStmt==0 );
    if( rc==SQLITE_OK || db->mallocFailed ) break;
  }while( rc==SQLITE_ERROR_RETRY
       || (rc==SQLITE_SCHEMA && (sqlite3ResetOneSchema(db,-1), cnt++)==0) );
  sqlite3BtreeLeaveAll(db);
  rc = sqlite3ApiExit(db, rc);
  assert( (rc&db->errMask)==rc );
  db->busyHandler.nBusy = 0;
  sqlite3_mutex_leave(db->mutex);
133021
133022
133023
133024
133025
133026
133027
133028


133029
133030
133031

133032
133033
133034
133035
133036
133037
133038
*/
SQLITE_PRIVATE void sqlite3SetJoinExpr(Expr *p, int iTable){
  while( p ){
    ExprSetProperty(p, EP_FromJoin);
    assert( !ExprHasProperty(p, EP_TokenOnly|EP_Reduced) );
    ExprSetVVAProperty(p, EP_NoReduce);
    p->iRightJoinTable = iTable;
    if( p->op==TK_FUNCTION && p->x.pList ){


      int i;
      for(i=0; i<p->x.pList->nExpr; i++){
        sqlite3SetJoinExpr(p->x.pList->a[i].pExpr, iTable);

      }
    }
    sqlite3SetJoinExpr(p->pLeft, iTable);
    p = p->pRight;
  }
}








|
>
>
|
|
|
>







133789
133790
133791
133792
133793
133794
133795
133796
133797
133798
133799
133800
133801
133802
133803
133804
133805
133806
133807
133808
133809
*/
SQLITE_PRIVATE void sqlite3SetJoinExpr(Expr *p, int iTable){
  while( p ){
    ExprSetProperty(p, EP_FromJoin);
    assert( !ExprHasProperty(p, EP_TokenOnly|EP_Reduced) );
    ExprSetVVAProperty(p, EP_NoReduce);
    p->iRightJoinTable = iTable;
    if( p->op==TK_FUNCTION ){
      assert( ExprUseXList(p) );
      if( p->x.pList ){
        int i;
        for(i=0; i<p->x.pList->nExpr; i++){
          sqlite3SetJoinExpr(p->x.pList->a[i].pExpr, iTable);
        }
      }
    }
    sqlite3SetJoinExpr(p->pLeft, iTable);
    p = p->pRight;
  }
}

133047
133048
133049
133050
133051
133052
133053
133054


133055
133056
133057

133058
133059
133060
133061
133062
133063
133064
    if( ExprHasProperty(p, EP_FromJoin)
     && (iTable<0 || p->iRightJoinTable==iTable) ){
      ExprClearProperty(p, EP_FromJoin);
    }
    if( p->op==TK_COLUMN && p->iTable==iTable ){
      ExprClearProperty(p, EP_CanBeNull);
    }
    if( p->op==TK_FUNCTION && p->x.pList ){


      int i;
      for(i=0; i<p->x.pList->nExpr; i++){
        unsetJoinExpr(p->x.pList->a[i].pExpr, iTable);

      }
    }
    unsetJoinExpr(p->pLeft, iTable);
    p = p->pRight;
  }
}








|
>
>
|
|
|
>







133818
133819
133820
133821
133822
133823
133824
133825
133826
133827
133828
133829
133830
133831
133832
133833
133834
133835
133836
133837
133838
    if( ExprHasProperty(p, EP_FromJoin)
     && (iTable<0 || p->iRightJoinTable==iTable) ){
      ExprClearProperty(p, EP_FromJoin);
    }
    if( p->op==TK_COLUMN && p->iTable==iTable ){
      ExprClearProperty(p, EP_CanBeNull);
    }
    if( p->op==TK_FUNCTION ){
      assert( ExprUseXList(p) );
      if( p->x.pList ){
        int i;
        for(i=0; i<p->x.pList->nExpr; i++){
          unsetJoinExpr(p->x.pList->a[i].pExpr, iTable);
        }
      }
    }
    unsetJoinExpr(p->pLeft, iTable);
    p = p->pRight;
  }
}

133565
133566
133567
133568
133569
133570
133571
133572
133573




133574
133575
133576
133577
133578
133579
133580
133581
133582
133583
133584
133585
133586
133587
133588
133589
133590
133591
133592
133593
133594

133595
133596
133597
133598
133599
133600
133601
  int i;
  int nDefer = 0;
  ExprList *pExtra = 0;
  for(i=0; i<pEList->nExpr; i++){
    struct ExprList_item *pItem = &pEList->a[i];
    if( pItem->u.x.iOrderByCol==0 ){
      Expr *pExpr = pItem->pExpr;
      Table *pTab = pExpr->y.pTab;
      if( pExpr->op==TK_COLUMN && pExpr->iColumn>=0 && pTab && !IsVirtual(pTab)




       && (pTab->aCol[pExpr->iColumn].colFlags & COLFLAG_SORTERREF)
      ){
        int j;
        for(j=0; j<nDefer; j++){
          if( pSort->aDefer[j].iCsr==pExpr->iTable ) break;
        }
        if( j==nDefer ){
          if( nDefer==ArraySize(pSort->aDefer) ){
            continue;
          }else{
            int nKey = 1;
            int k;
            Index *pPk = 0;
            if( !HasRowid(pTab) ){
              pPk = sqlite3PrimaryKeyIndex(pTab);
              nKey = pPk->nKeyCol;
            }
            for(k=0; k<nKey; k++){
              Expr *pNew = sqlite3PExpr(pParse, TK_COLUMN, 0, 0);
              if( pNew ){
                pNew->iTable = pExpr->iTable;

                pNew->y.pTab = pExpr->y.pTab;
                pNew->iColumn = pPk ? pPk->aiColumn[k] : -1;
                pExtra = sqlite3ExprListAppend(pParse, pExtra, pNew);
              }
            }
            pSort->aDefer[nDefer].pTab = pExpr->y.pTab;
            pSort->aDefer[nDefer].iCsr = pExpr->iTable;







|
|
>
>
>
>
|




















>







134339
134340
134341
134342
134343
134344
134345
134346
134347
134348
134349
134350
134351
134352
134353
134354
134355
134356
134357
134358
134359
134360
134361
134362
134363
134364
134365
134366
134367
134368
134369
134370
134371
134372
134373
134374
134375
134376
134377
134378
134379
134380
  int i;
  int nDefer = 0;
  ExprList *pExtra = 0;
  for(i=0; i<pEList->nExpr; i++){
    struct ExprList_item *pItem = &pEList->a[i];
    if( pItem->u.x.iOrderByCol==0 ){
      Expr *pExpr = pItem->pExpr;
      Table *pTab;
      if( pExpr->op==TK_COLUMN
       && pExpr->iColumn>=0
       && ALWAYS( ExprUseYTab(pExpr) )
       && (pTab = pExpr->y.pTab)!=0
       && IsOrdinaryTable(pTab)
       && (pTab->aCol[pExpr->iColumn].colFlags & COLFLAG_SORTERREF)!=0
      ){
        int j;
        for(j=0; j<nDefer; j++){
          if( pSort->aDefer[j].iCsr==pExpr->iTable ) break;
        }
        if( j==nDefer ){
          if( nDefer==ArraySize(pSort->aDefer) ){
            continue;
          }else{
            int nKey = 1;
            int k;
            Index *pPk = 0;
            if( !HasRowid(pTab) ){
              pPk = sqlite3PrimaryKeyIndex(pTab);
              nKey = pPk->nKeyCol;
            }
            for(k=0; k<nKey; k++){
              Expr *pNew = sqlite3PExpr(pParse, TK_COLUMN, 0, 0);
              if( pNew ){
                pNew->iTable = pExpr->iTable;
                assert( ExprUseYTab(pNew) );
                pNew->y.pTab = pExpr->y.pTab;
                pNew->iColumn = pPk ? pPk->aiColumn[k] : -1;
                pExtra = sqlite3ExprListAppend(pParse, pExtra, pNew);
              }
            }
            pSort->aDefer[nDefer].pTab = pExpr->y.pTab;
            pSort->aDefer[nDefer].iCsr = pExpr->iTable;
134436
134437
134438
134439
134440
134441
134442
134443
134444
134445
134446
134447
134448
134449
134450
        ** This is not a problem, as the column type of "t1.col" is never
        ** used. When columnType() is called on the expression
        ** "(SELECT t1.col)", the correct type is returned (see the TK_SELECT
        ** branch below.  */
        break;
      }

      assert( pTab && pExpr->y.pTab==pTab );
      if( pS ){
        /* The "table" is actually a sub-select or a view in the FROM clause
        ** of the SELECT statement. Return the declaration type and origin
        ** data for the result-set column of the sub-select.
        */
        if( iCol<pS->pEList->nExpr
#ifdef SQLITE_ALLOW_ROWID_IN_VIEW







|







135215
135216
135217
135218
135219
135220
135221
135222
135223
135224
135225
135226
135227
135228
135229
        ** This is not a problem, as the column type of "t1.col" is never
        ** used. When columnType() is called on the expression
        ** "(SELECT t1.col)", the correct type is returned (see the TK_SELECT
        ** branch below.  */
        break;
      }

      assert( pTab && ExprUseYTab(pExpr) && pExpr->y.pTab==pTab );
      if( pS ){
        /* The "table" is actually a sub-select or a view in the FROM clause
        ** of the SELECT statement. Return the declaration type and origin
        ** data for the result-set column of the sub-select.
        */
        if( iCol<pS->pEList->nExpr
#ifdef SQLITE_ALLOW_ROWID_IN_VIEW
134496
134497
134498
134499
134500
134501
134502



134503
134504
134505
134506
134507
134508
134509
134510
134511
134512
#ifndef SQLITE_OMIT_SUBQUERY
    case TK_SELECT: {
      /* The expression is a sub-select. Return the declaration type and
      ** origin info for the single column in the result set of the SELECT
      ** statement.
      */
      NameContext sNC;



      Select *pS = pExpr->x.pSelect;
      Expr *p = pS->pEList->a[0].pExpr;
      assert( ExprHasProperty(pExpr, EP_xIsSelect) );
      sNC.pSrcList = pS->pSrc;
      sNC.pNext = pNC;
      sNC.pParse = pNC->pParse;
      zType = columnType(&sNC, p, &zOrigDb, &zOrigTab, &zOrigCol);
      break;
    }
#endif







>
>
>
|
|
<







135275
135276
135277
135278
135279
135280
135281
135282
135283
135284
135285
135286

135287
135288
135289
135290
135291
135292
135293
#ifndef SQLITE_OMIT_SUBQUERY
    case TK_SELECT: {
      /* The expression is a sub-select. Return the declaration type and
      ** origin info for the single column in the result set of the SELECT
      ** statement.
      */
      NameContext sNC;
      Select *pS;
      Expr *p;
      assert( ExprUseXSelect(pExpr) );
      pS = pExpr->x.pSelect;
      p = pS->pEList->a[0].pExpr;

      sNC.pSrcList = pS->pSrc;
      sNC.pNext = pNC;
      sNC.pParse = pNC->pParse;
      zType = columnType(&sNC, p, &zOrigDb, &zOrigTab, &zOrigCol);
      break;
    }
#endif
134627
134628
134629
134630
134631
134632
134633
134634

134635
134636
134637
134638
134639
134640
134641
  srcName = (db->flags & SQLITE_ShortColNames)!=0 || fullName;
  sqlite3VdbeSetNumCols(v, pEList->nExpr);
  for(i=0; i<pEList->nExpr; i++){
    Expr *p = pEList->a[i].pExpr;

    assert( p!=0 );
    assert( p->op!=TK_AGG_COLUMN );  /* Agg processing has not run yet */
    assert( p->op!=TK_COLUMN || p->y.pTab!=0 ); /* Covering idx not yet coded */

    if( pEList->a[i].zEName && pEList->a[i].eEName==ENAME_NAME ){
      /* An AS clause always takes first priority */
      char *zName = pEList->a[i].zEName;
      sqlite3VdbeSetColName(v, i, COLNAME_NAME, zName, SQLITE_TRANSIENT);
    }else if( srcName && p->op==TK_COLUMN ){
      char *zCol;
      int iCol = p->iColumn;







|
>







135408
135409
135410
135411
135412
135413
135414
135415
135416
135417
135418
135419
135420
135421
135422
135423
  srcName = (db->flags & SQLITE_ShortColNames)!=0 || fullName;
  sqlite3VdbeSetNumCols(v, pEList->nExpr);
  for(i=0; i<pEList->nExpr; i++){
    Expr *p = pEList->a[i].pExpr;

    assert( p!=0 );
    assert( p->op!=TK_AGG_COLUMN );  /* Agg processing has not run yet */
    assert( p->op!=TK_COLUMN
        || (ExprUseYTab(p) && p->y.pTab!=0) ); /* Covering idx not yet coded */
    if( pEList->a[i].zEName && pEList->a[i].eEName==ENAME_NAME ){
      /* An AS clause always takes first priority */
      char *zName = pEList->a[i].zEName;
      sqlite3VdbeSetColName(v, i, COLNAME_NAME, zName, SQLITE_TRANSIENT);
    }else if( srcName && p->op==TK_COLUMN ){
      char *zCol;
      int iCol = p->iColumn;
134723
134724
134725
134726
134727
134728
134729
134730



134731
134732
134733
134734
134735
134736
134737
      /* If the column contains an "AS <name>" phrase, use <name> as the name */
    }else{
      Expr *pColExpr = sqlite3ExprSkipCollateAndLikely(pEList->a[i].pExpr);
      while( ALWAYS(pColExpr!=0) && pColExpr->op==TK_DOT ){
        pColExpr = pColExpr->pRight;
        assert( pColExpr!=0 );
      }
      if( pColExpr->op==TK_COLUMN && (pTab = pColExpr->y.pTab)!=0 ){



        /* For columns use the column name name */
        int iCol = pColExpr->iColumn;
        if( iCol<0 ) iCol = pTab->iPKey;
        zName = iCol>=0 ? pTab->aCol[iCol].zCnName : "rowid";
      }else if( pColExpr->op==TK_ID ){
        assert( !ExprHasProperty(pColExpr, EP_IntValue) );
        zName = pColExpr->u.zToken;







|
>
>
>







135505
135506
135507
135508
135509
135510
135511
135512
135513
135514
135515
135516
135517
135518
135519
135520
135521
135522
      /* If the column contains an "AS <name>" phrase, use <name> as the name */
    }else{
      Expr *pColExpr = sqlite3ExprSkipCollateAndLikely(pEList->a[i].pExpr);
      while( ALWAYS(pColExpr!=0) && pColExpr->op==TK_DOT ){
        pColExpr = pColExpr->pRight;
        assert( pColExpr!=0 );
      }
      if( pColExpr->op==TK_COLUMN
       && ALWAYS( ExprUseYTab(pColExpr) )
       && (pTab = pColExpr->y.pTab)!=0
      ){
        /* For columns use the column name name */
        int iCol = pColExpr->iColumn;
        if( iCol<0 ) iCol = pTab->iPKey;
        zName = iCol>=0 ? pTab->aCol[iCol].zCnName : "rowid";
      }else if( pColExpr->op==TK_ID ){
        assert( !ExprHasProperty(pColExpr, EP_IntValue) );
        zName = pColExpr->u.zToken;
134809
134810
134811
134812
134813
134814
134815
134816
134817
134818
134819
134820
134821
134822
134823
134824
134825
134826
134827
134828



134829
134830
134831
134832
134833
134834
134835
  assert( pTab->nCol==pSelect->pEList->nExpr || db->mallocFailed );
  if( db->mallocFailed ) return;
  memset(&sNC, 0, sizeof(sNC));
  sNC.pSrcList = pSelect->pSrc;
  a = pSelect->pEList->a;
  for(i=0, pCol=pTab->aCol; i<pTab->nCol; i++, pCol++){
    const char *zType;
    int n, m;
    pTab->tabFlags |= (pCol->colFlags & COLFLAG_NOINSERT);
    p = a[i].pExpr;
    zType = columnType(&sNC, p, 0, 0, 0);
    /* pCol->szEst = ... // Column size est for SELECT tables never used */
    pCol->affinity = sqlite3ExprAffinity(p);
    if( zType ){
      m = sqlite3Strlen30(zType);
      n = sqlite3Strlen30(pCol->zCnName);
      pCol->zCnName = sqlite3DbReallocOrFree(db, pCol->zCnName, n+m+2);
      if( pCol->zCnName ){
        memcpy(&pCol->zCnName[n+1], zType, m+1);
        pCol->colFlags |= COLFLAG_HASTYPE;



      }
    }
    if( pCol->affinity<=SQLITE_AFF_NONE ) pCol->affinity = aff;
    pColl = sqlite3ExprCollSeq(pParse, p);
    if( pColl ){
      assert( pTab->pIndex==0 );
      sqlite3ColumnSetColl(db, pCol, pColl->zName);







|












>
>
>







135594
135595
135596
135597
135598
135599
135600
135601
135602
135603
135604
135605
135606
135607
135608
135609
135610
135611
135612
135613
135614
135615
135616
135617
135618
135619
135620
135621
135622
135623
  assert( pTab->nCol==pSelect->pEList->nExpr || db->mallocFailed );
  if( db->mallocFailed ) return;
  memset(&sNC, 0, sizeof(sNC));
  sNC.pSrcList = pSelect->pSrc;
  a = pSelect->pEList->a;
  for(i=0, pCol=pTab->aCol; i<pTab->nCol; i++, pCol++){
    const char *zType;
    i64 n, m;
    pTab->tabFlags |= (pCol->colFlags & COLFLAG_NOINSERT);
    p = a[i].pExpr;
    zType = columnType(&sNC, p, 0, 0, 0);
    /* pCol->szEst = ... // Column size est for SELECT tables never used */
    pCol->affinity = sqlite3ExprAffinity(p);
    if( zType ){
      m = sqlite3Strlen30(zType);
      n = sqlite3Strlen30(pCol->zCnName);
      pCol->zCnName = sqlite3DbReallocOrFree(db, pCol->zCnName, n+m+2);
      if( pCol->zCnName ){
        memcpy(&pCol->zCnName[n+1], zType, m+1);
        pCol->colFlags |= COLFLAG_HASTYPE;
      }else{
        testcase( pCol->colFlags & COLFLAG_HASTYPE );
        pCol->colFlags &= ~(COLFLAG_HASTYPE|COLFLAG_HASCOLL);
      }
    }
    if( pCol->affinity<=SQLITE_AFF_NONE ) pCol->affinity = aff;
    pColl = sqlite3ExprCollSeq(pParse, p);
    if( pColl ){
      assert( pTab->pIndex==0 );
      sqlite3ColumnSetColl(db, pCol, pColl->zName);
134992
134993
134994
134995
134996
134997
134998
134999
135000
135001
135002
135003
135004
135005
135006
**
** Space to hold the KeyInfo structure is obtained from malloc. The calling
** function is responsible for ensuring that this structure is eventually
** freed.
*/
static KeyInfo *multiSelectOrderByKeyInfo(Parse *pParse, Select *p, int nExtra){
  ExprList *pOrderBy = p->pOrderBy;
  int nOrderBy = p->pOrderBy->nExpr;
  sqlite3 *db = pParse->db;
  KeyInfo *pRet = sqlite3KeyInfoAlloc(db, nOrderBy+nExtra, 1);
  if( pRet ){
    int i;
    for(i=0; i<nOrderBy; i++){
      struct ExprList_item *pItem = &pOrderBy->a[i];
      Expr *pTerm = pItem->pExpr;







|







135780
135781
135782
135783
135784
135785
135786
135787
135788
135789
135790
135791
135792
135793
135794
**
** Space to hold the KeyInfo structure is obtained from malloc. The calling
** function is responsible for ensuring that this structure is eventually
** freed.
*/
static KeyInfo *multiSelectOrderByKeyInfo(Parse *pParse, Select *p, int nExtra){
  ExprList *pOrderBy = p->pOrderBy;
  int nOrderBy = ALWAYS(pOrderBy!=0) ? pOrderBy->nExpr : 0;
  sqlite3 *db = pParse->db;
  KeyInfo *pRet = sqlite3KeyInfoAlloc(db, nOrderBy+nExtra, 1);
  if( pRet ){
    int i;
    for(i=0; i<nOrderBy; i++){
      struct ExprList_item *pItem = &pOrderBy->a[i];
      Expr *pTerm = pItem->pExpr;
135613
135614
135615
135616
135617
135618
135619

135620
135621
135622
135623
135624
135625
135626
    int i;                        /* Loop counter */
    KeyInfo *pKeyInfo;            /* Collating sequence for the result set */
    Select *pLoop;                /* For looping through SELECT statements */
    CollSeq **apColl;             /* For looping through pKeyInfo->aColl[] */
    int nCol;                     /* Number of columns in result set */

    assert( p->pNext==0 );

    nCol = p->pEList->nExpr;
    pKeyInfo = sqlite3KeyInfoAlloc(db, nCol, 1);
    if( !pKeyInfo ){
      rc = SQLITE_NOMEM_BKPT;
      goto multi_select_end;
    }
    for(i=0, apColl=pKeyInfo->aColl; i<nCol; i++, apColl++){







>







136401
136402
136403
136404
136405
136406
136407
136408
136409
136410
136411
136412
136413
136414
136415
    int i;                        /* Loop counter */
    KeyInfo *pKeyInfo;            /* Collating sequence for the result set */
    Select *pLoop;                /* For looping through SELECT statements */
    CollSeq **apColl;             /* For looping through pKeyInfo->aColl[] */
    int nCol;                     /* Number of columns in result set */

    assert( p->pNext==0 );
    assert( p->pEList!=0 );
    nCol = p->pEList->nExpr;
    pKeyInfo = sqlite3KeyInfoAlloc(db, nCol, 1);
    if( !pKeyInfo ){
      rc = SQLITE_NOMEM_BKPT;
      goto multi_select_end;
    }
    for(i=0, apColl=pKeyInfo->aColl; i<nCol; i++, apColl++){
135964
135965
135966
135967
135968
135969
135970

135971
135972
135973
135974
135975
135976
135977
  ** the ORDER BY clause covers every term of the result set.  Add
  ** terms to the ORDER BY clause as necessary.
  */
  if( op!=TK_ALL ){
    for(i=1; db->mallocFailed==0 && i<=p->pEList->nExpr; i++){
      struct ExprList_item *pItem;
      for(j=0, pItem=pOrderBy->a; j<nOrderBy; j++, pItem++){

        assert( pItem->u.x.iOrderByCol>0 );
        if( pItem->u.x.iOrderByCol==i ) break;
      }
      if( j==nOrderBy ){
        Expr *pNew = sqlite3Expr(db, TK_INTEGER, 0);
        if( pNew==0 ) return SQLITE_NOMEM_BKPT;
        pNew->flags |= EP_IntValue;







>







136753
136754
136755
136756
136757
136758
136759
136760
136761
136762
136763
136764
136765
136766
136767
  ** the ORDER BY clause covers every term of the result set.  Add
  ** terms to the ORDER BY clause as necessary.
  */
  if( op!=TK_ALL ){
    for(i=1; db->mallocFailed==0 && i<=p->pEList->nExpr; i++){
      struct ExprList_item *pItem;
      for(j=0, pItem=pOrderBy->a; j<nOrderBy; j++, pItem++){
        assert( pItem!=0 );
        assert( pItem->u.x.iOrderByCol>0 );
        if( pItem->u.x.iOrderByCol==i ) break;
      }
      if( j==nOrderBy ){
        Expr *pNew = sqlite3Expr(db, TK_INTEGER, 0);
        if( pNew==0 ) return SQLITE_NOMEM_BKPT;
        pNew->flags |= EP_IntValue;
135990
135991
135992
135993
135994
135995
135996

135997
135998
135999
136000
136001
136002
136003
  ** collation.
  */
  aPermute = sqlite3DbMallocRawNN(db, sizeof(u32)*(nOrderBy + 1));
  if( aPermute ){
    struct ExprList_item *pItem;
    aPermute[0] = nOrderBy;
    for(i=1, pItem=pOrderBy->a; i<=nOrderBy; i++, pItem++){

      assert( pItem->u.x.iOrderByCol>0 );
      assert( pItem->u.x.iOrderByCol<=p->pEList->nExpr );
      aPermute[i] = pItem->u.x.iOrderByCol - 1;
    }
    pKeyMerge = multiSelectOrderByKeyInfo(pParse, p, 1);
  }else{
    pKeyMerge = 0;







>







136780
136781
136782
136783
136784
136785
136786
136787
136788
136789
136790
136791
136792
136793
136794
  ** collation.
  */
  aPermute = sqlite3DbMallocRawNN(db, sizeof(u32)*(nOrderBy + 1));
  if( aPermute ){
    struct ExprList_item *pItem;
    aPermute[0] = nOrderBy;
    for(i=1, pItem=pOrderBy->a; i<=nOrderBy; i++, pItem++){
      assert( pItem!=0 );
      assert( pItem->u.x.iOrderByCol>0 );
      assert( pItem->u.x.iOrderByCol<=p->pEList->nExpr );
      aPermute[i] = pItem->u.x.iOrderByCol - 1;
    }
    pKeyMerge = multiSelectOrderByKeyInfo(pParse, p, 1);
  }else{
    pKeyMerge = 0;
136302
136303
136304
136305
136306
136307
136308
136309
136310
136311
136312
136313
136314
136315
136316
    }
  }else{
    if( pExpr->op==TK_IF_NULL_ROW && pExpr->iTable==pSubst->iTable ){
      pExpr->iTable = pSubst->iNewTable;
    }
    pExpr->pLeft = substExpr(pSubst, pExpr->pLeft);
    pExpr->pRight = substExpr(pSubst, pExpr->pRight);
    if( ExprHasProperty(pExpr, EP_xIsSelect) ){
      substSelect(pSubst, pExpr->x.pSelect, 1);
    }else{
      substExprList(pSubst, pExpr->x.pList);
    }
#ifndef SQLITE_OMIT_WINDOWFUNC
    if( ExprHasProperty(pExpr, EP_WinFunc) ){
      Window *pWin = pExpr->y.pWin;







|







137093
137094
137095
137096
137097
137098
137099
137100
137101
137102
137103
137104
137105
137106
137107
    }
  }else{
    if( pExpr->op==TK_IF_NULL_ROW && pExpr->iTable==pSubst->iTable ){
      pExpr->iTable = pSubst->iNewTable;
    }
    pExpr->pLeft = substExpr(pSubst, pExpr->pLeft);
    pExpr->pRight = substExpr(pSubst, pExpr->pRight);
    if( ExprUseXSelect(pExpr) ){
      substSelect(pSubst, pExpr->x.pSelect, 1);
    }else{
      substExprList(pSubst, pExpr->x.pList);
    }
#ifndef SQLITE_OMIT_WINDOWFUNC
    if( ExprHasProperty(pExpr, EP_WinFunc) ){
      Window *pWin = pExpr->y.pWin;
136789
136790
136791
136792
136793
136794
136795
136796
136797
136798
136799
136800
136801
136802
136803
    }

    /* Restriction (23) */
    if( (p->selFlags & SF_Recursive) ) return 0;

    if( pSrc->nSrc>1 ){
      if( pParse->nSelect>500 ) return 0;
      aCsrMap = sqlite3DbMallocZero(db, (pParse->nTab+1)*sizeof(int));
      if( aCsrMap ) aCsrMap[0] = pParse->nTab;
    }
  }

  /***** If we reach this point, flattening is permitted. *****/
  SELECTTRACE(1,pParse,p,("flatten %u.%p from term %d\n",
                   pSub->selId, pSub, iFrom));







|







137580
137581
137582
137583
137584
137585
137586
137587
137588
137589
137590
137591
137592
137593
137594
    }

    /* Restriction (23) */
    if( (p->selFlags & SF_Recursive) ) return 0;

    if( pSrc->nSrc>1 ){
      if( pParse->nSelect>500 ) return 0;
      aCsrMap = sqlite3DbMallocZero(db, ((i64)pParse->nTab+1)*sizeof(int));
      if( aCsrMap ) aCsrMap[0] = pParse->nTab;
    }
  }

  /***** If we reach this point, flattening is permitted. *****/
  SELECTTRACE(1,pParse,p,("flatten %u.%p from term %d\n",
                   pSub->selId, pSub, iFrom));
137513
137514
137515
137516
137517
137518
137519
137520
137521
137522
137523
137524
137525
137526
137527


137528
137529
137530
137531
137532
137533
137534

137535
137536
137537
137538
137539
137540
137541
**
** This routine must be called after aggregate functions have been
** located but before their arguments have been subjected to aggregate
** analysis.
*/
static u8 minMaxQuery(sqlite3 *db, Expr *pFunc, ExprList **ppMinMax){
  int eRet = WHERE_ORDERBY_NORMAL;      /* Return value */
  ExprList *pEList = pFunc->x.pList;    /* Arguments to agg function */
  const char *zFunc;                    /* Name of aggregate function pFunc */
  ExprList *pOrderBy;
  u8 sortFlags = 0;

  assert( *ppMinMax==0 );
  assert( pFunc->op==TK_AGG_FUNCTION );
  assert( !IsWindowFunc(pFunc) );


  if( pEList==0
   || pEList->nExpr!=1
   || ExprHasProperty(pFunc, EP_WinFunc)
   || OptimizationDisabled(db, SQLITE_MinMaxOpt)
  ){
    return eRet;
  }

  zFunc = pFunc->u.zToken;
  if( sqlite3StrICmp(zFunc, "min")==0 ){
    eRet = WHERE_ORDERBY_MIN;
    if( sqlite3ExprCanBeNull(pEList->a[0].pExpr) ){
      sortFlags = KEYINFO_ORDER_BIGNULL;
    }
  }else if( sqlite3StrICmp(zFunc, "max")==0 ){







|







>
>







>







138304
138305
138306
138307
138308
138309
138310
138311
138312
138313
138314
138315
138316
138317
138318
138319
138320
138321
138322
138323
138324
138325
138326
138327
138328
138329
138330
138331
138332
138333
138334
138335
**
** This routine must be called after aggregate functions have been
** located but before their arguments have been subjected to aggregate
** analysis.
*/
static u8 minMaxQuery(sqlite3 *db, Expr *pFunc, ExprList **ppMinMax){
  int eRet = WHERE_ORDERBY_NORMAL;      /* Return value */
  ExprList *pEList;                     /* Arguments to agg function */
  const char *zFunc;                    /* Name of aggregate function pFunc */
  ExprList *pOrderBy;
  u8 sortFlags = 0;

  assert( *ppMinMax==0 );
  assert( pFunc->op==TK_AGG_FUNCTION );
  assert( !IsWindowFunc(pFunc) );
  assert( ExprUseXList(pFunc) );
  pEList = pFunc->x.pList;
  if( pEList==0
   || pEList->nExpr!=1
   || ExprHasProperty(pFunc, EP_WinFunc)
   || OptimizationDisabled(db, SQLITE_MinMaxOpt)
  ){
    return eRet;
  }
  assert( !ExprHasProperty(pFunc, EP_IntValue) );
  zFunc = pFunc->u.zToken;
  if( sqlite3StrICmp(zFunc, "min")==0 ){
    eRet = WHERE_ORDERBY_MIN;
    if( sqlite3ExprCanBeNull(pEList->a[0].pExpr) ){
      sortFlags = KEYINFO_ORDER_BIGNULL;
    }
  }else if( sqlite3StrICmp(zFunc, "max")==0 ){
137555
137556
137557
137558
137559
137560
137561
137562






137563
137564
137565
137566
137567
137568
137569
137570

137571


137572
137573
137574
137575
137576
137577
137578
137579


137580
137581
137582



137583
137584
137585
137586
137587
137588
137589
** The second argument is the associated aggregate-info object. This
** function tests if the SELECT is of the form:
**
**   SELECT count(*) FROM <tbl>
**
** where table is a database table, not a sub-select or view. If the query
** does match this pattern, then a pointer to the Table object representing
** <tbl> is returned. Otherwise, 0 is returned.






*/
static Table *isSimpleCount(Select *p, AggInfo *pAggInfo){
  Table *pTab;
  Expr *pExpr;

  assert( !p->pGroupBy );

  if( p->pWhere || p->pEList->nExpr!=1

   || p->pSrc->nSrc!=1 || p->pSrc->a[0].pSelect


  ){
    return 0;
  }
  pTab = p->pSrc->a[0].pTab;
  pExpr = p->pEList->a[0].pExpr;
  assert( pTab && !IsView(pTab) && pExpr );

  if( IsVirtual(pTab) ) return 0;


  if( pExpr->op!=TK_AGG_FUNCTION ) return 0;
  if( NEVER(pAggInfo->nFunc==0) ) return 0;
  if( (pAggInfo->aFunc[0].pFunc->funcFlags&SQLITE_FUNC_COUNT)==0 ) return 0;



  if( ExprHasProperty(pExpr, EP_Distinct|EP_WinFunc) ) return 0;

  return pTab;
}

/*
** If the source-list item passed as an argument was augmented with an







|
>
>
>
>
>
>







|
>
|
>
>




<
|
|
|
>
>

|

>
>
>







138349
138350
138351
138352
138353
138354
138355
138356
138357
138358
138359
138360
138361
138362
138363
138364
138365
138366
138367
138368
138369
138370
138371
138372
138373
138374
138375
138376
138377
138378

138379
138380
138381
138382
138383
138384
138385
138386
138387
138388
138389
138390
138391
138392
138393
138394
138395
138396
** The second argument is the associated aggregate-info object. This
** function tests if the SELECT is of the form:
**
**   SELECT count(*) FROM <tbl>
**
** where table is a database table, not a sub-select or view. If the query
** does match this pattern, then a pointer to the Table object representing
** <tbl> is returned. Otherwise, NULL is returned.
**
** This routine checks to see if it is safe to use the count optimization.
** A correct answer is still obtained (though perhaps more slowly) if
** this routine returns NULL when it could have returned a table pointer.
** But returning the pointer when NULL should have been returned can
** result in incorrect answers and/or crashes.  So, when in doubt, return NULL.
*/
static Table *isSimpleCount(Select *p, AggInfo *pAggInfo){
  Table *pTab;
  Expr *pExpr;

  assert( !p->pGroupBy );

  if( p->pWhere
   || p->pEList->nExpr!=1
   || p->pSrc->nSrc!=1
   || p->pSrc->a[0].pSelect
   || pAggInfo->nFunc!=1
  ){
    return 0;
  }
  pTab = p->pSrc->a[0].pTab;

  assert( pTab!=0 );
  assert( !IsView(pTab) );
  if( !IsOrdinaryTable(pTab) ) return 0;
  pExpr = p->pEList->a[0].pExpr;
  assert( pExpr!=0 );
  if( pExpr->op!=TK_AGG_FUNCTION ) return 0;
  if( pExpr->pAggInfo!=pAggInfo ) return 0;
  if( (pAggInfo->aFunc[0].pFunc->funcFlags&SQLITE_FUNC_COUNT)==0 ) return 0;
  assert( pAggInfo->aFunc[0].pFExpr==pExpr );
  testcase( ExprHasProperty(pExpr, EP_Distinct) );
  testcase( ExprHasProperty(pExpr, EP_WinFunc) );
  if( ExprHasProperty(pExpr, EP_Distinct|EP_WinFunc) ) return 0;

  return pTab;
}

/*
** If the source-list item passed as an argument was augmented with an
137604
137605
137606
137607
137608
137609
137610

137611
137612
137613
137614
137615
137616
137617
      pIdx=pIdx->pNext
  );
  if( !pIdx ){
    sqlite3ErrorMsg(pParse, "no such index: %s", zIndexedBy, 0);
    pParse->checkSchema = 1;
    return SQLITE_ERROR;
  }

  pFrom->u2.pIBIndex = pIdx;
  return SQLITE_OK;
}

/*
** Detect compound SELECT statements that use an ORDER BY clause with
** an alternative collating sequence.







>







138411
138412
138413
138414
138415
138416
138417
138418
138419
138420
138421
138422
138423
138424
138425
      pIdx=pIdx->pNext
  );
  if( !pIdx ){
    sqlite3ErrorMsg(pParse, "no such index: %s", zIndexedBy, 0);
    pParse->checkSchema = 1;
    return SQLITE_ERROR;
  }
  assert( pFrom->fg.isCte==0 );
  pFrom->u2.pIBIndex = pIdx;
  return SQLITE_OK;
}

/*
** Detect compound SELECT statements that use an ORDER BY clause with
** an alternative collating sequence.
137861
137862
137863
137864
137865
137866
137867




137868
137869
137870
137871
137872
137873
137874
    pTab->iPKey = -1;
    pTab->nRowLogEst = 200; assert( 200==sqlite3LogEst(1048576) );
    pTab->tabFlags |= TF_Ephemeral | TF_NoVisibleRowid;
    pFrom->pSelect = sqlite3SelectDup(db, pCte->pSelect, 0);
    if( db->mallocFailed ) return 2;
    pFrom->pSelect->selFlags |= SF_CopyCte;
    assert( pFrom->pSelect );




    pFrom->fg.isCte = 1;
    pFrom->u2.pCteUse = pCteUse;
    pCteUse->nUse++;
    if( pCteUse->nUse>=2 && pCteUse->eM10d==M10d_Any ){
      pCteUse->eM10d = M10d_Yes;
    }








>
>
>
>







138669
138670
138671
138672
138673
138674
138675
138676
138677
138678
138679
138680
138681
138682
138683
138684
138685
138686
    pTab->iPKey = -1;
    pTab->nRowLogEst = 200; assert( 200==sqlite3LogEst(1048576) );
    pTab->tabFlags |= TF_Ephemeral | TF_NoVisibleRowid;
    pFrom->pSelect = sqlite3SelectDup(db, pCte->pSelect, 0);
    if( db->mallocFailed ) return 2;
    pFrom->pSelect->selFlags |= SF_CopyCte;
    assert( pFrom->pSelect );
    if( pFrom->fg.isIndexedBy ){
      sqlite3ErrorMsg(pParse, "no such index: \"%s\"", pFrom->u1.zIndexedBy);
      return 2;
    }
    pFrom->fg.isCte = 1;
    pFrom->u2.pCteUse = pCteUse;
    pCteUse->nUse++;
    if( pCteUse->nUse>=2 && pCteUse->eM10d==M10d_Any ){
      pCteUse->eM10d = M10d_Yes;
    }

138496
138497
138498
138499
138500
138501
138502
138503
138504
138505
138506
138507
138508
138509
138510
         && pAggInfo->aFunc[i].iMem<=pAggInfo->mxReg );
  }
#endif
  sqlite3VdbeAddOp3(v, OP_Null, 0, pAggInfo->mnReg, pAggInfo->mxReg);
  for(pFunc=pAggInfo->aFunc, i=0; i<pAggInfo->nFunc; i++, pFunc++){
    if( pFunc->iDistinct>=0 ){
      Expr *pE = pFunc->pFExpr;
      assert( !ExprHasProperty(pE, EP_xIsSelect) );
      if( pE->x.pList==0 || pE->x.pList->nExpr!=1 ){
        sqlite3ErrorMsg(pParse, "DISTINCT aggregates must have exactly one "
           "argument");
        pFunc->iDistinct = -1;
      }else{
        KeyInfo *pKeyInfo = sqlite3KeyInfoFromExprList(pParse, pE->x.pList,0,0);
        pFunc->iDistAddr = sqlite3VdbeAddOp4(v, OP_OpenEphemeral,







|







139308
139309
139310
139311
139312
139313
139314
139315
139316
139317
139318
139319
139320
139321
139322
         && pAggInfo->aFunc[i].iMem<=pAggInfo->mxReg );
  }
#endif
  sqlite3VdbeAddOp3(v, OP_Null, 0, pAggInfo->mnReg, pAggInfo->mxReg);
  for(pFunc=pAggInfo->aFunc, i=0; i<pAggInfo->nFunc; i++, pFunc++){
    if( pFunc->iDistinct>=0 ){
      Expr *pE = pFunc->pFExpr;
      assert( ExprUseXList(pE) );
      if( pE->x.pList==0 || pE->x.pList->nExpr!=1 ){
        sqlite3ErrorMsg(pParse, "DISTINCT aggregates must have exactly one "
           "argument");
        pFunc->iDistinct = -1;
      }else{
        KeyInfo *pKeyInfo = sqlite3KeyInfoFromExprList(pParse, pE->x.pList,0,0);
        pFunc->iDistAddr = sqlite3VdbeAddOp4(v, OP_OpenEphemeral,
138521
138522
138523
138524
138525
138526
138527
138528

138529
138530
138531
138532
138533
138534
138535
138536
** in the AggInfo structure.
*/
static void finalizeAggFunctions(Parse *pParse, AggInfo *pAggInfo){
  Vdbe *v = pParse->pVdbe;
  int i;
  struct AggInfo_func *pF;
  for(i=0, pF=pAggInfo->aFunc; i<pAggInfo->nFunc; i++, pF++){
    ExprList *pList = pF->pFExpr->x.pList;

    assert( !ExprHasProperty(pF->pFExpr, EP_xIsSelect) );
    sqlite3VdbeAddOp2(v, OP_AggFinal, pF->iMem, pList ? pList->nExpr : 0);
    sqlite3VdbeAppendP4(v, pF->pFunc, P4_FUNCDEF);
  }
}


/*







|
>
|







139333
139334
139335
139336
139337
139338
139339
139340
139341
139342
139343
139344
139345
139346
139347
139348
139349
** in the AggInfo structure.
*/
static void finalizeAggFunctions(Parse *pParse, AggInfo *pAggInfo){
  Vdbe *v = pParse->pVdbe;
  int i;
  struct AggInfo_func *pF;
  for(i=0, pF=pAggInfo->aFunc; i<pAggInfo->nFunc; i++, pF++){
    ExprList *pList;
    assert( ExprUseXList(pF->pFExpr) );
    pList = pF->pFExpr->x.pList;
    sqlite3VdbeAddOp2(v, OP_AggFinal, pF->iMem, pList ? pList->nExpr : 0);
    sqlite3VdbeAppendP4(v, pF->pFunc, P4_FUNCDEF);
  }
}


/*
138556
138557
138558
138559
138560
138561
138562
138563
138564
138565

138566
138567
138568
138569
138570
138571
138572
  struct AggInfo_col *pC;

  pAggInfo->directMode = 1;
  for(i=0, pF=pAggInfo->aFunc; i<pAggInfo->nFunc; i++, pF++){
    int nArg;
    int addrNext = 0;
    int regAgg;
    ExprList *pList = pF->pFExpr->x.pList;
    assert( !ExprHasProperty(pF->pFExpr, EP_xIsSelect) );
    assert( !IsWindowFunc(pF->pFExpr) );

    if( ExprHasProperty(pF->pFExpr, EP_WinFunc) ){
      Expr *pFilter = pF->pFExpr->y.pWin->pFilter;
      if( pAggInfo->nAccumulator
       && (pF->pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL)
       && regAcc
      ){
        /* If regAcc==0, there there exists some min() or max() function







|
|

>







139369
139370
139371
139372
139373
139374
139375
139376
139377
139378
139379
139380
139381
139382
139383
139384
139385
139386
  struct AggInfo_col *pC;

  pAggInfo->directMode = 1;
  for(i=0, pF=pAggInfo->aFunc; i<pAggInfo->nFunc; i++, pF++){
    int nArg;
    int addrNext = 0;
    int regAgg;
    ExprList *pList;
    assert( ExprUseXList(pF->pFExpr) );
    assert( !IsWindowFunc(pF->pFExpr) );
    pList = pF->pFExpr->x.pList;
    if( ExprHasProperty(pF->pFExpr, EP_WinFunc) ){
      Expr *pFilter = pF->pFExpr->y.pWin->pFilter;
      if( pAggInfo->nAccumulator
       && (pF->pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL)
       && regAcc
      ){
        /* If regAcc==0, there there exists some min() or max() function
138804
138805
138806
138807
138808
138809
138810

138811

138812
138813
138814
138815
138816
138817
138818
  sqlite3 *db;
  if( (p->selFlags & SF_Aggregate)==0 ) return 0;   /* This is an aggregate */
  if( p->pEList->nExpr!=1 ) return 0;               /* Single result column */
  if( p->pWhere ) return 0;
  if( p->pGroupBy ) return 0;
  pExpr = p->pEList->a[0].pExpr;
  if( pExpr->op!=TK_AGG_FUNCTION ) return 0;        /* Result is an aggregate */

  if( sqlite3_stricmp(pExpr->u.zToken,"count") ) return 0;  /* Is count() */

  if( pExpr->x.pList!=0 ) return 0;                 /* Must be count(*) */
  if( p->pSrc->nSrc!=1 ) return 0;                  /* One table in FROM  */
  pSub = p->pSrc->a[0].pSelect;
  if( pSub==0 ) return 0;                           /* The FROM is a subquery */
  if( pSub->pPrior==0 ) return 0;                   /* Must be a compound ry */
  do{
    if( pSub->op!=TK_ALL && pSub->pPrior ) return 0;  /* Must be UNION ALL */







>

>







139618
139619
139620
139621
139622
139623
139624
139625
139626
139627
139628
139629
139630
139631
139632
139633
139634
  sqlite3 *db;
  if( (p->selFlags & SF_Aggregate)==0 ) return 0;   /* This is an aggregate */
  if( p->pEList->nExpr!=1 ) return 0;               /* Single result column */
  if( p->pWhere ) return 0;
  if( p->pGroupBy ) return 0;
  pExpr = p->pEList->a[0].pExpr;
  if( pExpr->op!=TK_AGG_FUNCTION ) return 0;        /* Result is an aggregate */
  assert( ExprUseUToken(pExpr) );
  if( sqlite3_stricmp(pExpr->u.zToken,"count") ) return 0;  /* Is count() */
  assert( ExprUseXList(pExpr) );
  if( pExpr->x.pList!=0 ) return 0;                 /* Must be count(*) */
  if( p->pSrc->nSrc!=1 ) return 0;                  /* One table in FROM  */
  pSub = p->pSrc->a[0].pSelect;
  if( pSub==0 ) return 0;                           /* The FROM is a subquery */
  if( pSub->pPrior==0 ) return 0;                   /* Must be a compound ry */
  do{
    if( pSub->op!=TK_ALL && pSub->pPrior ) return 0;  /* Must be UNION ALL */
139619
139620
139621
139622
139623
139624
139625
139626
139627
139628
139629
139630
139631
139632
139633
    if( p->pGroupBy==0 && p->pHaving==0 && pAggInfo->nFunc==1 ){
      minMaxFlag = minMaxQuery(db, pAggInfo->aFunc[0].pFExpr, &pMinMaxOrderBy);
    }else{
      minMaxFlag = WHERE_ORDERBY_NORMAL;
    }
    for(i=0; i<pAggInfo->nFunc; i++){
      Expr *pExpr = pAggInfo->aFunc[i].pFExpr;
      assert( !ExprHasProperty(pExpr, EP_xIsSelect) );
      sNC.ncFlags |= NC_InAggFunc;
      sqlite3ExprAnalyzeAggList(&sNC, pExpr->x.pList);
#ifndef SQLITE_OMIT_WINDOWFUNC
      assert( !IsWindowFunc(pExpr) );
      if( ExprHasProperty(pExpr, EP_WinFunc) ){
        sqlite3ExprAnalyzeAggregates(&sNC, pExpr->y.pWin->pFilter);
      }







|







140435
140436
140437
140438
140439
140440
140441
140442
140443
140444
140445
140446
140447
140448
140449
    if( p->pGroupBy==0 && p->pHaving==0 && pAggInfo->nFunc==1 ){
      minMaxFlag = minMaxQuery(db, pAggInfo->aFunc[0].pFExpr, &pMinMaxOrderBy);
    }else{
      minMaxFlag = WHERE_ORDERBY_NORMAL;
    }
    for(i=0; i<pAggInfo->nFunc; i++){
      Expr *pExpr = pAggInfo->aFunc[i].pFExpr;
      assert( ExprUseXList(pExpr) );
      sNC.ncFlags |= NC_InAggFunc;
      sqlite3ExprAnalyzeAggList(&sNC, pExpr->x.pList);
#ifndef SQLITE_OMIT_WINDOWFUNC
      assert( !IsWindowFunc(pExpr) );
      if( ExprHasProperty(pExpr, EP_WinFunc) ){
        sqlite3ExprAnalyzeAggregates(&sNC, pExpr->y.pWin->pFilter);
      }
139674
139675
139676
139677
139678
139679
139680


139681
139682
139683
139684
139685
139686
139687
139688
      int regReset;       /* Return address register for reset subroutine */
      ExprList *pDistinct = 0;
      u16 distFlag = 0;
      int eDist = WHERE_DISTINCT_NOOP;

      if( pAggInfo->nFunc==1
       && pAggInfo->aFunc[0].iDistinct>=0


       && pAggInfo->aFunc[0].pFExpr->x.pList
      ){
        Expr *pExpr = pAggInfo->aFunc[0].pFExpr->x.pList->a[0].pExpr;
        pExpr = sqlite3ExprDup(db, pExpr, 0);
        pDistinct = sqlite3ExprListDup(db, pGroupBy, 0);
        pDistinct = sqlite3ExprListAppend(pParse, pDistinct, pExpr);
        distFlag = pDistinct ? (WHERE_WANT_DISTINCT|WHERE_AGG_DISTINCT) : 0;
      }







>
>
|







140490
140491
140492
140493
140494
140495
140496
140497
140498
140499
140500
140501
140502
140503
140504
140505
140506
      int regReset;       /* Return address register for reset subroutine */
      ExprList *pDistinct = 0;
      u16 distFlag = 0;
      int eDist = WHERE_DISTINCT_NOOP;

      if( pAggInfo->nFunc==1
       && pAggInfo->aFunc[0].iDistinct>=0
       && ALWAYS(pAggInfo->aFunc[0].pFExpr!=0)
       && ALWAYS(ExprUseXList(pAggInfo->aFunc[0].pFExpr))
       && pAggInfo->aFunc[0].pFExpr->x.pList!=0
      ){
        Expr *pExpr = pAggInfo->aFunc[0].pFExpr->x.pList->a[0].pExpr;
        pExpr = sqlite3ExprDup(db, pExpr, 0);
        pDistinct = sqlite3ExprListDup(db, pGroupBy, 0);
        pDistinct = sqlite3ExprListAppend(pParse, pDistinct, pExpr);
        distFlag = pDistinct ? (WHERE_WANT_DISTINCT|WHERE_AGG_DISTINCT) : 0;
      }
139995
139996
139997
139998
139999
140000
140001

140002
140003
140004
140005
140006
140007
140008
            }
          }
          if( i==pAggInfo->nFunc ){
            regAcc = ++pParse->nMem;
            sqlite3VdbeAddOp2(v, OP_Integer, 0, regAcc);
          }
        }else if( pAggInfo->nFunc==1 && pAggInfo->aFunc[0].iDistinct>=0 ){

          pDistinct = pAggInfo->aFunc[0].pFExpr->x.pList;
          distFlag = pDistinct ? (WHERE_WANT_DISTINCT|WHERE_AGG_DISTINCT) : 0;
        }

        /* This case runs if the aggregate has no GROUP BY clause.  The
        ** processing is much simpler since there is only a single row
        ** of output.







>







140813
140814
140815
140816
140817
140818
140819
140820
140821
140822
140823
140824
140825
140826
140827
            }
          }
          if( i==pAggInfo->nFunc ){
            regAcc = ++pParse->nMem;
            sqlite3VdbeAddOp2(v, OP_Integer, 0, regAcc);
          }
        }else if( pAggInfo->nFunc==1 && pAggInfo->aFunc[0].iDistinct>=0 ){
          assert( ExprUseXList(pAggInfo->aFunc[0].pFExpr) );
          pDistinct = pAggInfo->aFunc[0].pFExpr->x.pList;
          distFlag = pDistinct ? (WHERE_WANT_DISTINCT|WHERE_AGG_DISTINCT) : 0;
        }

        /* This case runs if the aggregate has no GROUP BY clause.  The
        ** processing is much simpler since there is only a single row
        ** of output.
140668
140669
140670
140671
140672
140673
140674
140675
140676
140677
140678
140679
140680
140681
140682
    /* Make an entry in the sqlite_schema table */
    v = sqlite3GetVdbe(pParse);
    if( v==0 ) goto triggerfinish_cleanup;
    sqlite3BeginWriteOperation(pParse, 0, iDb);
    z = sqlite3DbStrNDup(db, (char*)pAll->z, pAll->n);
    testcase( z==0 );
    sqlite3NestedParse(pParse,
       "INSERT INTO %Q." DFLT_SCHEMA_TABLE
       " VALUES('trigger',%Q,%Q,0,'CREATE TRIGGER %q')",
       db->aDb[iDb].zDbSName, zName,
       pTrig->table, z);
    sqlite3DbFree(db, z);
    sqlite3ChangeCookie(pParse, iDb);
    sqlite3VdbeAddParseSchemaOp(v, iDb,
        sqlite3MPrintf(db, "type='trigger' AND name='%q'", zName), 0);







|







141487
141488
141489
141490
141491
141492
141493
141494
141495
141496
141497
141498
141499
141500
141501
    /* Make an entry in the sqlite_schema table */
    v = sqlite3GetVdbe(pParse);
    if( v==0 ) goto triggerfinish_cleanup;
    sqlite3BeginWriteOperation(pParse, 0, iDb);
    z = sqlite3DbStrNDup(db, (char*)pAll->z, pAll->n);
    testcase( z==0 );
    sqlite3NestedParse(pParse,
       "INSERT INTO %Q." LEGACY_SCHEMA_TABLE
       " VALUES('trigger',%Q,%Q,0,'CREATE TRIGGER %q')",
       db->aDb[iDb].zDbSName, zName,
       pTrig->table, z);
    sqlite3DbFree(db, z);
    sqlite3ChangeCookie(pParse, iDb);
    sqlite3VdbeAddParseSchemaOp(v, iDb,
        sqlite3MPrintf(db, "type='trigger' AND name='%q'", zName), 0);
140982
140983
140984
140985
140986
140987
140988
140989
140990
140991
140992
140993
140994
140995
140996
  }
#endif

  /* Generate code to destroy the database record of the trigger.
  */
  if( (v = sqlite3GetVdbe(pParse))!=0 ){
    sqlite3NestedParse(pParse,
       "DELETE FROM %Q." DFLT_SCHEMA_TABLE " WHERE name=%Q AND type='trigger'",
       db->aDb[iDb].zDbSName, pTrigger->zName
    );
    sqlite3ChangeCookie(pParse, iDb);
    sqlite3VdbeAddOp4(v, OP_DropTrigger, iDb, 0, 0, pTrigger->zName, 0);
  }
}








|







141801
141802
141803
141804
141805
141806
141807
141808
141809
141810
141811
141812
141813
141814
141815
  }
#endif

  /* Generate code to destroy the database record of the trigger.
  */
  if( (v = sqlite3GetVdbe(pParse))!=0 ){
    sqlite3NestedParse(pParse,
       "DELETE FROM %Q." LEGACY_SCHEMA_TABLE " WHERE name=%Q AND type='trigger'",
       db->aDb[iDb].zDbSName, pTrigger->zName
    );
    sqlite3ChangeCookie(pParse, iDb);
    sqlite3VdbeAddOp4(v, OP_DropTrigger, iDb, 0, 0, pTrigger->zName, 0);
  }
}

142850
142851
142852
142853
142854
142855
142856
142857
142858
142859
142860
142861
142862
142863
142864
142865
142866
  }

  /*
  ** Return the number of rows that were changed, if we are tracking
  ** that information.
  */
  if( regRowCount ){
    sqlite3VdbeAddOp2(v, OP_ChngCntRow, regRowCount, 1);
    sqlite3VdbeSetNumCols(v, 1);
    sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "rows updated", SQLITE_STATIC);
  }

update_cleanup:
  sqlite3AuthContextPop(&sContext);
  sqlite3DbFree(db, aXRef); /* Also frees aRegIdx[] and aToOpen[] */
  sqlite3SrcListDelete(db, pTabList);
  sqlite3ExprListDelete(db, pChanges);







|
<
<







143669
143670
143671
143672
143673
143674
143675
143676


143677
143678
143679
143680
143681
143682
143683
  }

  /*
  ** Return the number of rows that were changed, if we are tracking
  ** that information.
  */
  if( regRowCount ){
    sqlite3CodeChangeCount(v, regRowCount, "rows updated");


  }

update_cleanup:
  sqlite3AuthContextPop(&sContext);
  sqlite3DbFree(db, aXRef); /* Also frees aRegIdx[] and aToOpen[] */
  sqlite3SrcListDelete(db, pTabList);
  sqlite3ExprListDelete(db, pChanges);
143635
143636
143637
143638
143639
143640
143641
143642


143643
143644
143645
143646
143647
143648
143649
  rc = execSql(db, pzErrMsg, "BEGIN");
  if( rc!=SQLITE_OK ) goto end_of_vacuum;
  rc = sqlite3BtreeBeginTrans(pMain, pOut==0 ? 2 : 0, 0);
  if( rc!=SQLITE_OK ) goto end_of_vacuum;

  /* Do not attempt to change the page size for a WAL database */
  if( sqlite3PagerGetJournalMode(sqlite3BtreePager(pMain))
                                               ==PAGER_JOURNALMODE_WAL ){


    db->nextPagesize = 0;
  }

  if( sqlite3BtreeSetPageSize(pTemp, sqlite3BtreeGetPageSize(pMain), nRes, 0)
   || (!isMemDb && sqlite3BtreeSetPageSize(pTemp, db->nextPagesize, nRes, 0))
   || NEVER(db->mallocFailed)
  ){







|
>
>







144452
144453
144454
144455
144456
144457
144458
144459
144460
144461
144462
144463
144464
144465
144466
144467
144468
  rc = execSql(db, pzErrMsg, "BEGIN");
  if( rc!=SQLITE_OK ) goto end_of_vacuum;
  rc = sqlite3BtreeBeginTrans(pMain, pOut==0 ? 2 : 0, 0);
  if( rc!=SQLITE_OK ) goto end_of_vacuum;

  /* Do not attempt to change the page size for a WAL database */
  if( sqlite3PagerGetJournalMode(sqlite3BtreePager(pMain))
                                               ==PAGER_JOURNALMODE_WAL
   && pOut==0
  ){
    db->nextPagesize = 0;
  }

  if( sqlite3BtreeSetPageSize(pTemp, sqlite3BtreeGetPageSize(pMain), nRes, 0)
   || (!isMemDb && sqlite3BtreeSetPageSize(pTemp, db->nextPagesize, nRes, 0))
   || NEVER(db->mallocFailed)
  ){
144020
144021
144022
144023
144024
144025
144026
144027



144028
144029
144030
144031
144032
144033
144034
** p->u.vtab.p list to the sqlite3.pDisconnect lists of their associated
** database connections to be disconnected at the next opportunity.
** Except, if argument db is not NULL, then the entry associated with
** connection db is left in the p->u.vtab.p list.
*/
static VTable *vtabDisconnectAll(sqlite3 *db, Table *p){
  VTable *pRet = 0;
  VTable *pVTable = p->u.vtab.p;



  p->u.vtab.p = 0;

  /* Assert that the mutex (if any) associated with the BtShared database
  ** that contains table p is held by the caller. See header comments
  ** above function sqlite3VtabUnlockList() for an explanation of why
  ** this makes it safe to access the sqlite3.pDisconnect list of any
  ** database connection that may have an entry in the p->u.vtab.p list.







|
>
>
>







144839
144840
144841
144842
144843
144844
144845
144846
144847
144848
144849
144850
144851
144852
144853
144854
144855
144856
** p->u.vtab.p list to the sqlite3.pDisconnect lists of their associated
** database connections to be disconnected at the next opportunity.
** Except, if argument db is not NULL, then the entry associated with
** connection db is left in the p->u.vtab.p list.
*/
static VTable *vtabDisconnectAll(sqlite3 *db, Table *p){
  VTable *pRet = 0;
  VTable *pVTable;

  assert( IsVirtual(p) );
  pVTable = p->u.vtab.p;
  p->u.vtab.p = 0;

  /* Assert that the mutex (if any) associated with the BtShared database
  ** that contains table p is held by the caller. See header comments
  ** above function sqlite3VtabUnlockList() for an explanation of why
  ** this makes it safe to access the sqlite3.pDisconnect list of any
  ** database connection that may have an entry in the p->u.vtab.p list.
144128
144129
144130
144131
144132
144133
144134

144135
144136
144137
144138
144139
144140
144141
144142
144143
144144
144145
144146
144147
144148
144149
144150
144151
144152
144153
144154



144155
144156
144157
144158
144159
144160
144161
** The reference count of the VTable structure associated with database
** connection db is decremented immediately (which may lead to the
** structure being xDisconnected and free). Any other VTable structures
** in the list are moved to the sqlite3.pDisconnect list of the associated
** database connection.
*/
SQLITE_PRIVATE void sqlite3VtabClear(sqlite3 *db, Table *p){

  if( !db || db->pnBytesFreed==0 ) vtabDisconnectAll(0, p);
  if( p->u.vtab.azArg ){
    int i;
    for(i=0; i<p->u.vtab.nArg; i++){
      if( i!=1 ) sqlite3DbFree(db, p->u.vtab.azArg[i]);
    }
    sqlite3DbFree(db, p->u.vtab.azArg);
  }
}

/*
** Add a new module argument to pTable->u.vtab.azArg[].
** The string is not copied - the pointer is stored.  The
** string will be freed automatically when the table is
** deleted.
*/
static void addModuleArgument(Parse *pParse, Table *pTable, char *zArg){
  sqlite3_int64 nBytes = sizeof(char *)*(2+pTable->u.vtab.nArg);
  char **azModuleArg;
  sqlite3 *db = pParse->db;



  if( pTable->u.vtab.nArg+3>=db->aLimit[SQLITE_LIMIT_COLUMN] ){
    sqlite3ErrorMsg(pParse, "too many columns on %s", pTable->zName);
  }
  azModuleArg = sqlite3DbRealloc(db, pTable->u.vtab.azArg, nBytes);
  if( azModuleArg==0 ){
    sqlite3DbFree(db, zArg);
  }else{







>

















|


>
>
>







144950
144951
144952
144953
144954
144955
144956
144957
144958
144959
144960
144961
144962
144963
144964
144965
144966
144967
144968
144969
144970
144971
144972
144973
144974
144975
144976
144977
144978
144979
144980
144981
144982
144983
144984
144985
144986
144987
** The reference count of the VTable structure associated with database
** connection db is decremented immediately (which may lead to the
** structure being xDisconnected and free). Any other VTable structures
** in the list are moved to the sqlite3.pDisconnect list of the associated
** database connection.
*/
SQLITE_PRIVATE void sqlite3VtabClear(sqlite3 *db, Table *p){
  assert( IsVirtual(p) );
  if( !db || db->pnBytesFreed==0 ) vtabDisconnectAll(0, p);
  if( p->u.vtab.azArg ){
    int i;
    for(i=0; i<p->u.vtab.nArg; i++){
      if( i!=1 ) sqlite3DbFree(db, p->u.vtab.azArg[i]);
    }
    sqlite3DbFree(db, p->u.vtab.azArg);
  }
}

/*
** Add a new module argument to pTable->u.vtab.azArg[].
** The string is not copied - the pointer is stored.  The
** string will be freed automatically when the table is
** deleted.
*/
static void addModuleArgument(Parse *pParse, Table *pTable, char *zArg){
  sqlite3_int64 nBytes;
  char **azModuleArg;
  sqlite3 *db = pParse->db;

  assert( IsVirtual(pTable) );
  nBytes = sizeof(char *)*(2+pTable->u.vtab.nArg);
  if( pTable->u.vtab.nArg+3>=db->aLimit[SQLITE_LIMIT_COLUMN] ){
    sqlite3ErrorMsg(pParse, "too many columns on %s", pTable->zName);
  }
  azModuleArg = sqlite3DbRealloc(db, pTable->u.vtab.azArg, nBytes);
  if( azModuleArg==0 ){
    sqlite3DbFree(db, zArg);
  }else{
144234
144235
144236
144237
144238
144239
144240

144241
144242
144243
144244
144245
144246
144247
** has been completely parsed.
*/
SQLITE_PRIVATE void sqlite3VtabFinishParse(Parse *pParse, Token *pEnd){
  Table *pTab = pParse->pNewTable;  /* The table being constructed */
  sqlite3 *db = pParse->db;         /* The database connection */

  if( pTab==0 ) return;

  addArgumentToVtab(pParse);
  pParse->sArg.z = 0;
  if( pTab->u.vtab.nArg<1 ) return;

  /* If the CREATE VIRTUAL TABLE statement is being entered for the
  ** first time (in other words if the virtual table is actually being
  ** created now instead of just being read out of sqlite_schema) then







>







145060
145061
145062
145063
145064
145065
145066
145067
145068
145069
145070
145071
145072
145073
145074
** has been completely parsed.
*/
SQLITE_PRIVATE void sqlite3VtabFinishParse(Parse *pParse, Token *pEnd){
  Table *pTab = pParse->pNewTable;  /* The table being constructed */
  sqlite3 *db = pParse->db;         /* The database connection */

  if( pTab==0 ) return;
  assert( IsVirtual(pTab) );
  addArgumentToVtab(pParse);
  pParse->sArg.z = 0;
  if( pTab->u.vtab.nArg<1 ) return;

  /* If the CREATE VIRTUAL TABLE statement is being entered for the
  ** first time (in other words if the virtual table is actually being
  ** created now instead of just being read out of sqlite_schema) then
144269
144270
144271
144272
144273
144274
144275
144276
144277
144278
144279
144280
144281
144282
144283
144284
144285
144286
144287
144288
144289
144290
144291
144292
144293
144294
144295
144296
144297
144298
144299
144300
144301
144302
144303
144304
144305
144306
144307

144308
144309
144310
144311
144312
144313
144314
    **
    ** The VM register number pParse->regRowid holds the rowid of an
    ** entry in the sqlite_schema table tht was created for this vtab
    ** by sqlite3StartTable().
    */
    iDb = sqlite3SchemaToIndex(db, pTab->pSchema);
    sqlite3NestedParse(pParse,
      "UPDATE %Q." DFLT_SCHEMA_TABLE " "
         "SET type='table', name=%Q, tbl_name=%Q, rootpage=0, sql=%Q "
       "WHERE rowid=#%d",
      db->aDb[iDb].zDbSName,
      pTab->zName,
      pTab->zName,
      zStmt,
      pParse->regRowid
    );
    v = sqlite3GetVdbe(pParse);
    sqlite3ChangeCookie(pParse, iDb);

    sqlite3VdbeAddOp0(v, OP_Expire);
    zWhere = sqlite3MPrintf(db, "name=%Q AND sql=%Q", pTab->zName, zStmt);
    sqlite3VdbeAddParseSchemaOp(v, iDb, zWhere, 0);
    sqlite3DbFree(db, zStmt);

    iReg = ++pParse->nMem;
    sqlite3VdbeLoadString(v, iReg, pTab->zName);
    sqlite3VdbeAddOp2(v, OP_VCreate, iDb, iReg);
  }

  /* If we are rereading the sqlite_schema table create the in-memory
  ** record of the table. The xConnect() method is not called until
  ** the first time the virtual table is used in an SQL statement. This
  ** allows a schema that contains virtual tables to be loaded before
  ** the required virtual table implementations are registered.  */
  else {
    Table *pOld;
    Schema *pSchema = pTab->pSchema;
    const char *zName = pTab->zName;
    assert( sqlite3SchemaMutexHeld(db, 0, pSchema) );

    pOld = sqlite3HashInsert(&pSchema->tblHash, zName, pTab);
    if( pOld ){
      sqlite3OomFault(db);
      assert( pTab==pOld );  /* Malloc must have failed inside HashInsert() */
      return;
    }
    pParse->pNewTable = 0;







|



















|
<
|
|
<
<
<
<



|
>







145096
145097
145098
145099
145100
145101
145102
145103
145104
145105
145106
145107
145108
145109
145110
145111
145112
145113
145114
145115
145116
145117
145118
145119
145120
145121
145122
145123

145124
145125




145126
145127
145128
145129
145130
145131
145132
145133
145134
145135
145136
145137
    **
    ** The VM register number pParse->regRowid holds the rowid of an
    ** entry in the sqlite_schema table tht was created for this vtab
    ** by sqlite3StartTable().
    */
    iDb = sqlite3SchemaToIndex(db, pTab->pSchema);
    sqlite3NestedParse(pParse,
      "UPDATE %Q." LEGACY_SCHEMA_TABLE " "
         "SET type='table', name=%Q, tbl_name=%Q, rootpage=0, sql=%Q "
       "WHERE rowid=#%d",
      db->aDb[iDb].zDbSName,
      pTab->zName,
      pTab->zName,
      zStmt,
      pParse->regRowid
    );
    v = sqlite3GetVdbe(pParse);
    sqlite3ChangeCookie(pParse, iDb);

    sqlite3VdbeAddOp0(v, OP_Expire);
    zWhere = sqlite3MPrintf(db, "name=%Q AND sql=%Q", pTab->zName, zStmt);
    sqlite3VdbeAddParseSchemaOp(v, iDb, zWhere, 0);
    sqlite3DbFree(db, zStmt);

    iReg = ++pParse->nMem;
    sqlite3VdbeLoadString(v, iReg, pTab->zName);
    sqlite3VdbeAddOp2(v, OP_VCreate, iDb, iReg);
  }else{

    /* If we are rereading the sqlite_schema table create the in-memory
    ** record of the table. */




    Table *pOld;
    Schema *pSchema = pTab->pSchema;
    const char *zName = pTab->zName;
    assert( zName!=0 );
    sqlite3MarkAllShadowTablesOf(db, pTab);
    pOld = sqlite3HashInsert(&pSchema->tblHash, zName, pTab);
    if( pOld ){
      sqlite3OomFault(db);
      assert( pTab==pOld );  /* Malloc must have failed inside HashInsert() */
      return;
    }
    pParse->pNewTable = 0;
144351
144352
144353
144354
144355
144356
144357
144358
144359
144360
144361
144362
144363
144364



144365
144366
144367
144368
144369
144370
144371
  Module *pMod,
  int (*xConstruct)(sqlite3*,void*,int,const char*const*,sqlite3_vtab**,char**),
  char **pzErr
){
  VtabCtx sCtx;
  VTable *pVTable;
  int rc;
  const char *const*azArg = (const char *const*)pTab->u.vtab.azArg;
  int nArg = pTab->u.vtab.nArg;
  char *zErr = 0;
  char *zModuleName;
  int iDb;
  VtabCtx *pCtx;




  /* Check that the virtual-table is not already being initialized */
  for(pCtx=db->pVtabCtx; pCtx; pCtx=pCtx->pPrior){
    if( pCtx->pTab==pTab ){
      *pzErr = sqlite3MPrintf(db,
          "vtable constructor called recursively: %s", pTab->zName
      );
      return SQLITE_LOCKED;







|






>
>
>







145174
145175
145176
145177
145178
145179
145180
145181
145182
145183
145184
145185
145186
145187
145188
145189
145190
145191
145192
145193
145194
145195
145196
145197
  Module *pMod,
  int (*xConstruct)(sqlite3*,void*,int,const char*const*,sqlite3_vtab**,char**),
  char **pzErr
){
  VtabCtx sCtx;
  VTable *pVTable;
  int rc;
  const char *const*azArg;
  int nArg = pTab->u.vtab.nArg;
  char *zErr = 0;
  char *zModuleName;
  int iDb;
  VtabCtx *pCtx;

  assert( IsVirtual(pTab) );
  azArg = (const char *const*)pTab->u.vtab.azArg;

  /* Check that the virtual-table is not already being initialized */
  for(pCtx=db->pVtabCtx; pCtx; pCtx=pCtx->pPrior){
    if( pCtx->pTab==pTab ){
      *pzErr = sqlite3MPrintf(db,
          "vtable constructor called recursively: %s", pTab->zName
      );
      return SQLITE_LOCKED;
144481
144482
144483
144484
144485
144486
144487

144488
144489
144490
144491
144492
144493
144494
144495
SQLITE_PRIVATE int sqlite3VtabCallConnect(Parse *pParse, Table *pTab){
  sqlite3 *db = pParse->db;
  const char *zMod;
  Module *pMod;
  int rc;

  assert( pTab );

  if( !IsVirtual(pTab) || sqlite3GetVTable(db, pTab) ){
    return SQLITE_OK;
  }

  /* Locate the required virtual table module */
  zMod = pTab->u.vtab.azArg[0];
  pMod = (Module*)sqlite3HashFind(&db->aModule, zMod);








>
|







145307
145308
145309
145310
145311
145312
145313
145314
145315
145316
145317
145318
145319
145320
145321
145322
SQLITE_PRIVATE int sqlite3VtabCallConnect(Parse *pParse, Table *pTab){
  sqlite3 *db = pParse->db;
  const char *zMod;
  Module *pMod;
  int rc;

  assert( pTab );
  assert( IsVirtual(pTab) );
  if( sqlite3GetVTable(db, pTab) ){
    return SQLITE_OK;
  }

  /* Locate the required virtual table module */
  zMod = pTab->u.vtab.azArg[0];
  pMod = (Module*)sqlite3HashFind(&db->aModule, zMod);

144685
144686
144687
144688
144689
144690
144691


144692

144693
144694
144695
144696
144697
144698
144699
** This call is a no-op if zTab is not a virtual table.
*/
SQLITE_PRIVATE int sqlite3VtabCallDestroy(sqlite3 *db, int iDb, const char *zTab){
  int rc = SQLITE_OK;
  Table *pTab;

  pTab = sqlite3FindTable(db, zTab, db->aDb[iDb].zDbSName);


  if( pTab!=0 && ALWAYS(pTab->u.vtab.p!=0) ){

    VTable *p;
    int (*xDestroy)(sqlite3_vtab *);
    for(p=pTab->u.vtab.p; p; p=p->pNext){
      assert( p->pVtab );
      if( p->pVtab->nRef>0 ){
        return SQLITE_LOCKED;
      }







>
>
|
>







145512
145513
145514
145515
145516
145517
145518
145519
145520
145521
145522
145523
145524
145525
145526
145527
145528
145529
** This call is a no-op if zTab is not a virtual table.
*/
SQLITE_PRIVATE int sqlite3VtabCallDestroy(sqlite3 *db, int iDb, const char *zTab){
  int rc = SQLITE_OK;
  Table *pTab;

  pTab = sqlite3FindTable(db, zTab, db->aDb[iDb].zDbSName);
  if( ALWAYS(pTab!=0)
   && ALWAYS(IsVirtual(pTab))
   && ALWAYS(pTab->u.vtab.p!=0)
  ){
    VTable *p;
    int (*xDestroy)(sqlite3_vtab *);
    for(p=pTab->u.vtab.p; p; p=p->pNext){
      assert( p->pVtab );
      if( p->pVtab->nRef>0 ){
        return SQLITE_LOCKED;
      }
144918
144919
144920
144921
144922
144923
144924

144925
144926
144927
144928
144929
144930
144931
  void *pArg = 0;
  FuncDef *pNew;
  int rc = 0;

  /* Check to see the left operand is a column in a virtual table */
  if( NEVER(pExpr==0) ) return pDef;
  if( pExpr->op!=TK_COLUMN ) return pDef;

  pTab = pExpr->y.pTab;
  if( pTab==0 ) return pDef;
  if( !IsVirtual(pTab) ) return pDef;
  pVtab = sqlite3GetVTable(db, pTab)->pVtab;
  assert( pVtab!=0 );
  assert( pVtab->pModule!=0 );
  pMod = (sqlite3_module *)pVtab->pModule;







>







145748
145749
145750
145751
145752
145753
145754
145755
145756
145757
145758
145759
145760
145761
145762
  void *pArg = 0;
  FuncDef *pNew;
  int rc = 0;

  /* Check to see the left operand is a column in a virtual table */
  if( NEVER(pExpr==0) ) return pDef;
  if( pExpr->op!=TK_COLUMN ) return pDef;
  assert( ExprUseYTab(pExpr) );
  pTab = pExpr->y.pTab;
  if( pTab==0 ) return pDef;
  if( !IsVirtual(pTab) ) return pDef;
  pVtab = sqlite3GetVTable(db, pTab)->pVtab;
  assert( pVtab!=0 );
  assert( pVtab->pModule!=0 );
  pMod = (sqlite3_module *)pVtab->pModule;
145212
145213
145214
145215
145216
145217
145218

145219
145220
145221
145222
145223
145224
145225
145226
145227
145228
145229
145230
145231
145232
145233
145234
145235
145236
145237
145238
145239
145240
  int addrBody;         /* Beginning of the body of this loop */
  int regBignull;       /* big-null flag reg. True if a NULL-scan is needed */
  int addrBignull;      /* Jump here for next part of big-null scan */
#ifndef SQLITE_LIKE_DOESNT_MATCH_BLOBS
  u32 iLikeRepCntr;     /* LIKE range processing counter register (times 2) */
  int addrLikeRep;      /* LIKE range processing address */
#endif

  u8 iFrom;             /* Which entry in the FROM clause */
  u8 op, p3, p5;        /* Opcode, P3 & P5 of the opcode that ends the loop */
  int p1, p2;           /* Operands of the opcode used to end the loop */
  union {               /* Information that depends on pWLoop->wsFlags */
    struct {
      int nIn;              /* Number of entries in aInLoop[] */
      struct InLoop {
        int iCur;              /* The VDBE cursor used by this IN operator */
        int addrInTop;         /* Top of the IN loop */
        int iBase;             /* Base register of multi-key index record */
        int nPrefix;           /* Number of prior entires in the key */
        u8 eEndLoopOp;         /* IN Loop terminator. OP_Next or OP_Prev */
      } *aInLoop;           /* Information about each nested IN operator */
    } in;                 /* Used when pWLoop->wsFlags&WHERE_IN_ABLE */
    Index *pCovidx;       /* Possible covering index for WHERE_MULTI_OR */
  } u;
  struct WhereLoop *pWLoop;  /* The selected WhereLoop object */
  Bitmask notReady;          /* FROM entries not usable at this level */
#ifdef SQLITE_ENABLE_STMT_SCANSTATUS
  int addrVisit;        /* Address at which row is visited */
#endif
};







>














|







146043
146044
146045
146046
146047
146048
146049
146050
146051
146052
146053
146054
146055
146056
146057
146058
146059
146060
146061
146062
146063
146064
146065
146066
146067
146068
146069
146070
146071
146072
  int addrBody;         /* Beginning of the body of this loop */
  int regBignull;       /* big-null flag reg. True if a NULL-scan is needed */
  int addrBignull;      /* Jump here for next part of big-null scan */
#ifndef SQLITE_LIKE_DOESNT_MATCH_BLOBS
  u32 iLikeRepCntr;     /* LIKE range processing counter register (times 2) */
  int addrLikeRep;      /* LIKE range processing address */
#endif
  int regFilter;        /* Bloom filter */
  u8 iFrom;             /* Which entry in the FROM clause */
  u8 op, p3, p5;        /* Opcode, P3 & P5 of the opcode that ends the loop */
  int p1, p2;           /* Operands of the opcode used to end the loop */
  union {               /* Information that depends on pWLoop->wsFlags */
    struct {
      int nIn;              /* Number of entries in aInLoop[] */
      struct InLoop {
        int iCur;              /* The VDBE cursor used by this IN operator */
        int addrInTop;         /* Top of the IN loop */
        int iBase;             /* Base register of multi-key index record */
        int nPrefix;           /* Number of prior entires in the key */
        u8 eEndLoopOp;         /* IN Loop terminator. OP_Next or OP_Prev */
      } *aInLoop;           /* Information about each nested IN operator */
    } in;                 /* Used when pWLoop->wsFlags&WHERE_IN_ABLE */
    Index *pCoveringIdx;  /* Possible covering index for WHERE_MULTI_OR */
  } u;
  struct WhereLoop *pWLoop;  /* The selected WhereLoop object */
  Bitmask notReady;          /* FROM entries not usable at this level */
#ifdef SQLITE_ENABLE_STMT_SCANSTATUS
  int addrVisit;        /* Address at which row is visited */
#endif
};
145440
145441
145442
145443
145444
145445
145446


145447

145448
145449
145450
145451
145452
145453
145454
145455
145456
145457
145458
** terms in the WHERE clause that are useful to the query planner.
*/
struct WhereScan {
  WhereClause *pOrigWC;      /* Original, innermost WhereClause */
  WhereClause *pWC;          /* WhereClause currently being scanned */
  const char *zCollName;     /* Required collating sequence, if not NULL */
  Expr *pIdxExpr;            /* Search for this index expression */


  char idxaff;               /* Must match this affinity, if zCollName!=NULL */

  unsigned char nEquiv;      /* Number of entries in aiCur[] and aiColumn[] */
  unsigned char iEquiv;      /* Next unused slot in aiCur[] and aiColumn[] */
  u32 opMask;                /* Acceptable operators */
  int k;                     /* Resume scanning at this->pWC->a[this->k] */
  int aiCur[11];             /* Cursors in the equivalence class */
  i16 aiColumn[11];          /* Corresponding column number in the eq-class */
};

/*
** An instance of the following structure holds all information about a
** WHERE clause.  Mostly this is a container for one or more WhereTerms.







>
>

>

<
<
<







146272
146273
146274
146275
146276
146277
146278
146279
146280
146281
146282
146283



146284
146285
146286
146287
146288
146289
146290
** terms in the WHERE clause that are useful to the query planner.
*/
struct WhereScan {
  WhereClause *pOrigWC;      /* Original, innermost WhereClause */
  WhereClause *pWC;          /* WhereClause currently being scanned */
  const char *zCollName;     /* Required collating sequence, if not NULL */
  Expr *pIdxExpr;            /* Search for this index expression */
  int k;                     /* Resume scanning at this->pWC->a[this->k] */
  u32 opMask;                /* Acceptable operators */
  char idxaff;               /* Must match this affinity, if zCollName!=NULL */
  unsigned char iEquiv;      /* Current slot in aiCur[] and aiColumn[] */
  unsigned char nEquiv;      /* Number of entries in aiCur[] and aiColumn[] */



  int aiCur[11];             /* Cursors in the equivalence class */
  i16 aiColumn[11];          /* Corresponding column number in the eq-class */
};

/*
** An instance of the following structure holds all information about a
** WHERE clause.  Mostly this is a container for one or more WhereTerms.
145468
145469
145470
145471
145472
145473
145474

145475
145476
145477
145478
145479
145480
145481
struct WhereClause {
  WhereInfo *pWInfo;       /* WHERE clause processing context */
  WhereClause *pOuter;     /* Outer conjunction */
  u8 op;                   /* Split operator.  TK_AND or TK_OR */
  u8 hasOr;                /* True if any a[].eOperator is WO_OR */
  int nTerm;               /* Number of terms */
  int nSlot;               /* Number of entries in a[] */

  WhereTerm *a;            /* Each a[] describes a term of the WHERE cluase */
#if defined(SQLITE_SMALL_STACK)
  WhereTerm aStatic[1];    /* Initial static space for a[] */
#else
  WhereTerm aStatic[8];    /* Initial static space for a[] */
#endif
};







>







146300
146301
146302
146303
146304
146305
146306
146307
146308
146309
146310
146311
146312
146313
146314
struct WhereClause {
  WhereInfo *pWInfo;       /* WHERE clause processing context */
  WhereClause *pOuter;     /* Outer conjunction */
  u8 op;                   /* Split operator.  TK_AND or TK_OR */
  u8 hasOr;                /* True if any a[].eOperator is WO_OR */
  int nTerm;               /* Number of terms */
  int nSlot;               /* Number of entries in a[] */
  int nBase;               /* Number of terms through the last non-Virtual */
  WhereTerm *a;            /* Each a[] describes a term of the WHERE cluase */
#if defined(SQLITE_SMALL_STACK)
  WhereTerm aStatic[1];    /* Initial static space for a[] */
#else
  WhereTerm aStatic[8];    /* Initial static space for a[] */
#endif
};
145525
145526
145527
145528
145529
145530
145531
145532
145533
145534
145535
145536
145537
145538
145539
145540
145541
145542
145543
*/
struct WhereMaskSet {
  int bVarSelect;               /* Used by sqlite3WhereExprUsage() */
  int n;                        /* Number of assigned cursor values */
  int ix[BMS];                  /* Cursor assigned to each bit */
};

/*
** Initialize a WhereMaskSet object
*/
#define initMaskSet(P)  (P)->n=0

/*
** This object is a convenience wrapper holding all information needed
** to construct WhereLoop objects for a particular query.
*/
struct WhereLoopBuilder {
  WhereInfo *pWInfo;        /* Information about this WHERE */
  WhereClause *pWC;         /* WHERE clause terms */







<
<
<
<
<







146358
146359
146360
146361
146362
146363
146364





146365
146366
146367
146368
146369
146370
146371
*/
struct WhereMaskSet {
  int bVarSelect;               /* Used by sqlite3WhereExprUsage() */
  int n;                        /* Number of assigned cursor values */
  int ix[BMS];                  /* Cursor assigned to each bit */
};






/*
** This object is a convenience wrapper holding all information needed
** to construct WhereLoop objects for a particular query.
*/
struct WhereLoopBuilder {
  WhereInfo *pWInfo;        /* Information about this WHERE */
  WhereClause *pWC;         /* WHERE clause terms */
145658
145659
145660
145661
145662
145663
145664





145665
145666

145667
145668
145669
145670
145671
145672
145673
#ifndef SQLITE_OMIT_EXPLAIN
SQLITE_PRIVATE int sqlite3WhereExplainOneScan(
  Parse *pParse,                  /* Parse context */
  SrcList *pTabList,              /* Table list this loop refers to */
  WhereLevel *pLevel,             /* Scan to write OP_Explain opcode for */
  u16 wctrlFlags                  /* Flags passed to sqlite3WhereBegin() */
);





#else
# define sqlite3WhereExplainOneScan(u,v,w,x) 0

#endif /* SQLITE_OMIT_EXPLAIN */
#ifdef SQLITE_ENABLE_STMT_SCANSTATUS
SQLITE_PRIVATE void sqlite3WhereAddScanStatus(
  Vdbe *v,                        /* Vdbe to add scanstatus entry to */
  SrcList *pSrclist,              /* FROM clause pLvl reads data from */
  WhereLevel *pLvl,               /* Level to add scanstatus() entry for */
  int addrExplain                 /* Address of OP_Explain (or 0) */







>
>
>
>
>


>







146486
146487
146488
146489
146490
146491
146492
146493
146494
146495
146496
146497
146498
146499
146500
146501
146502
146503
146504
146505
146506
146507
#ifndef SQLITE_OMIT_EXPLAIN
SQLITE_PRIVATE int sqlite3WhereExplainOneScan(
  Parse *pParse,                  /* Parse context */
  SrcList *pTabList,              /* Table list this loop refers to */
  WhereLevel *pLevel,             /* Scan to write OP_Explain opcode for */
  u16 wctrlFlags                  /* Flags passed to sqlite3WhereBegin() */
);
SQLITE_PRIVATE int sqlite3WhereExplainBloomFilter(
  const Parse *pParse,            /* Parse context */
  const WhereInfo *pWInfo,        /* WHERE clause */
  const WhereLevel *pLevel        /* Bloom filter on this level */
);
#else
# define sqlite3WhereExplainOneScan(u,v,w,x) 0
# define sqlite3WhereExplainBloomFilter(u,v,w) 0
#endif /* SQLITE_OMIT_EXPLAIN */
#ifdef SQLITE_ENABLE_STMT_SCANSTATUS
SQLITE_PRIVATE void sqlite3WhereAddScanStatus(
  Vdbe *v,                        /* Vdbe to add scanstatus entry to */
  SrcList *pSrclist,              /* FROM clause pLvl reads data from */
  WhereLevel *pLvl,               /* Level to add scanstatus() entry for */
  int addrExplain                 /* Address of OP_Explain (or 0) */
145752
145753
145754
145755
145756
145757
145758


145759
145760
145761
145762
145763
145764
145765
#define WHERE_SKIPSCAN     0x00008000  /* Uses the skip-scan algorithm */
#define WHERE_UNQ_WANTED   0x00010000  /* WHERE_ONEROW would have been helpful*/
#define WHERE_PARTIALIDX   0x00020000  /* The automatic index is partial */
#define WHERE_IN_EARLYOUT  0x00040000  /* Perhaps quit IN loops early */
#define WHERE_BIGNULL_SORT 0x00080000  /* Column nEq of index is BIGNULL */
#define WHERE_IN_SEEKSCAN  0x00100000  /* Seek-scan optimization for IN */
#define WHERE_TRANSCONS    0x00200000  /* Uses a transitive constraint */



#endif /* !defined(SQLITE_WHEREINT_H) */

/************** End of whereInt.h ********************************************/
/************** Continuing where we left off in wherecode.c ******************/

#ifndef SQLITE_OMIT_EXPLAIN







>
>







146586
146587
146588
146589
146590
146591
146592
146593
146594
146595
146596
146597
146598
146599
146600
146601
#define WHERE_SKIPSCAN     0x00008000  /* Uses the skip-scan algorithm */
#define WHERE_UNQ_WANTED   0x00010000  /* WHERE_ONEROW would have been helpful*/
#define WHERE_PARTIALIDX   0x00020000  /* The automatic index is partial */
#define WHERE_IN_EARLYOUT  0x00040000  /* Perhaps quit IN loops early */
#define WHERE_BIGNULL_SORT 0x00080000  /* Column nEq of index is BIGNULL */
#define WHERE_IN_SEEKSCAN  0x00100000  /* Seek-scan optimization for IN */
#define WHERE_TRANSCONS    0x00200000  /* Uses a transitive constraint */
#define WHERE_BLOOMFILTER  0x00400000  /* Consider using a Bloom-filter */
#define WHERE_SELFCULL     0x00800000  /* nOut reduced by extra WHERE terms */

#endif /* !defined(SQLITE_WHEREINT_H) */

/************** End of whereInt.h ********************************************/
/************** Continuing where we left off in wherecode.c ******************/

#ifndef SQLITE_OMIT_EXPLAIN
145914
145915
145916
145917
145918
145919
145920






145921


145922
145923
145924

145925
145926
145927
145928
145929
145930
145931
145932
145933
145934
145935
145936
145937
145938
145939
145940
      }
      if( zFmt ){
        sqlite3_str_append(&str, " USING ", 7);
        sqlite3_str_appendf(&str, zFmt, pIdx->zName);
        explainIndexRange(&str, pLoop);
      }
    }else if( (flags & WHERE_IPK)!=0 && (flags & WHERE_CONSTRAINT)!=0 ){






      const char *zRangeOp;


      if( flags&(WHERE_COLUMN_EQ|WHERE_COLUMN_IN) ){
        zRangeOp = "=";
      }else if( (flags&WHERE_BOTH_LIMIT)==WHERE_BOTH_LIMIT ){

        zRangeOp = ">? AND rowid<";
      }else if( flags&WHERE_BTM_LIMIT ){
        zRangeOp = ">";
      }else{
        assert( flags&WHERE_TOP_LIMIT);
        zRangeOp = "<";
      }
      sqlite3_str_appendf(&str,
          " USING INTEGER PRIMARY KEY (rowid%s?)",zRangeOp);
    }
#ifndef SQLITE_OMIT_VIRTUALTABLE
    else if( (flags & WHERE_VIRTUALTABLE)!=0 ){
      sqlite3_str_appendf(&str, " VIRTUAL TABLE INDEX %d:%s",
                  pLoop->u.vtab.idxNum, pLoop->u.vtab.idxStr);
    }
#endif







>
>
>
>
>
>
|
>
>

|

>
|

|


|

|
<







146750
146751
146752
146753
146754
146755
146756
146757
146758
146759
146760
146761
146762
146763
146764
146765
146766
146767
146768
146769
146770
146771
146772
146773
146774
146775
146776
146777

146778
146779
146780
146781
146782
146783
146784
      }
      if( zFmt ){
        sqlite3_str_append(&str, " USING ", 7);
        sqlite3_str_appendf(&str, zFmt, pIdx->zName);
        explainIndexRange(&str, pLoop);
      }
    }else if( (flags & WHERE_IPK)!=0 && (flags & WHERE_CONSTRAINT)!=0 ){
      char cRangeOp;
#if 0  /* Better output, but breaks many tests */
      const Table *pTab = pItem->pTab;
      const char *zRowid = pTab->iPKey>=0 ? pTab->aCol[pTab->iPKey].zCnName:
                              "rowid";
#else
      const char *zRowid = "rowid";
#endif
      sqlite3_str_appendf(&str, " USING INTEGER PRIMARY KEY (%s", zRowid);
      if( flags&(WHERE_COLUMN_EQ|WHERE_COLUMN_IN) ){
        cRangeOp = '=';
      }else if( (flags&WHERE_BOTH_LIMIT)==WHERE_BOTH_LIMIT ){
        sqlite3_str_appendf(&str, ">? AND %s", zRowid);
        cRangeOp = '<';
      }else if( flags&WHERE_BTM_LIMIT ){
        cRangeOp = '>';
      }else{
        assert( flags&WHERE_TOP_LIMIT);
        cRangeOp = '<';
      }
      sqlite3_str_appendf(&str, "%c?)", cRangeOp);

    }
#ifndef SQLITE_OMIT_VIRTUALTABLE
    else if( (flags & WHERE_VIRTUALTABLE)!=0 ){
      sqlite3_str_appendf(&str, " VIRTUAL TABLE INDEX %d:%s",
                  pLoop->u.vtab.idxNum, pLoop->u.vtab.idxStr);
    }
#endif
145949
145950
145951
145952
145953
145954
145955


















































145956
145957
145958
145959
145960
145961
145962
    zMsg = sqlite3StrAccumFinish(&str);
    sqlite3ExplainBreakpoint("",zMsg);
    ret = sqlite3VdbeAddOp4(v, OP_Explain, sqlite3VdbeCurrentAddr(v),
                            pParse->addrExplain, 0, zMsg,P4_DYNAMIC);
  }
  return ret;
}


















































#endif /* SQLITE_OMIT_EXPLAIN */

#ifdef SQLITE_ENABLE_STMT_SCANSTATUS
/*
** Configure the VM passed as the first argument with an
** sqlite3_stmt_scanstatus() entry corresponding to the scan used to
** implement level pLvl. Argument pSrclist is a pointer to the FROM







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







146793
146794
146795
146796
146797
146798
146799
146800
146801
146802
146803
146804
146805
146806
146807
146808
146809
146810
146811
146812
146813
146814
146815
146816
146817
146818
146819
146820
146821
146822
146823
146824
146825
146826
146827
146828
146829
146830
146831
146832
146833
146834
146835
146836
146837
146838
146839
146840
146841
146842
146843
146844
146845
146846
146847
146848
146849
146850
146851
146852
146853
146854
146855
146856
    zMsg = sqlite3StrAccumFinish(&str);
    sqlite3ExplainBreakpoint("",zMsg);
    ret = sqlite3VdbeAddOp4(v, OP_Explain, sqlite3VdbeCurrentAddr(v),
                            pParse->addrExplain, 0, zMsg,P4_DYNAMIC);
  }
  return ret;
}

/*
** Add a single OP_Explain opcode that describes a Bloom filter.
**
** Or if not processing EXPLAIN QUERY PLAN and not in a SQLITE_DEBUG and/or
** SQLITE_ENABLE_STMT_SCANSTATUS build, then OP_Explain opcodes are not
** required and this routine is a no-op.
**
** If an OP_Explain opcode is added to the VM, its address is returned.
** Otherwise, if no OP_Explain is coded, zero is returned.
*/
SQLITE_PRIVATE int sqlite3WhereExplainBloomFilter(
  const Parse *pParse,               /* Parse context */
  const WhereInfo *pWInfo,           /* WHERE clause */
  const WhereLevel *pLevel           /* Bloom filter on this level */
){
  int ret = 0;
  SrcItem *pItem = &pWInfo->pTabList->a[pLevel->iFrom];
  Vdbe *v = pParse->pVdbe;      /* VM being constructed */
  sqlite3 *db = pParse->db;     /* Database handle */
  char *zMsg;                   /* Text to add to EQP output */
  int i;                        /* Loop counter */
  WhereLoop *pLoop;             /* The where loop */
  StrAccum str;                 /* EQP output string */
  char zBuf[100];               /* Initial space for EQP output string */

  sqlite3StrAccumInit(&str, db, zBuf, sizeof(zBuf), SQLITE_MAX_LENGTH);
  str.printfFlags = SQLITE_PRINTF_INTERNAL;
  sqlite3_str_appendf(&str, "BLOOM FILTER ON %S (", pItem);
  pLoop = pLevel->pWLoop;
  if( pLoop->wsFlags & WHERE_IPK ){
    const Table *pTab = pItem->pTab;
    if( pTab->iPKey>=0 ){
      sqlite3_str_appendf(&str, "%s=?", pTab->aCol[pTab->iPKey].zCnName);
    }else{
      sqlite3_str_appendf(&str, "rowid=?");
    }
  }else{
    for(i=pLoop->nSkip; i<pLoop->u.btree.nEq; i++){
      const char *z = explainIndexColumnName(pLoop->u.btree.pIndex, i);
      if( i>pLoop->nSkip ) sqlite3_str_append(&str, " AND ", 5);
      sqlite3_str_appendf(&str, "%s=?", z);
    }
  }
  sqlite3_str_append(&str, ")", 1);
  zMsg = sqlite3StrAccumFinish(&str);
  ret = sqlite3VdbeAddOp4(v, OP_Explain, sqlite3VdbeCurrentAddr(v),
                          pParse->addrExplain, 0, zMsg,P4_DYNAMIC);
  return ret;
}
#endif /* SQLITE_OMIT_EXPLAIN */

#ifdef SQLITE_ENABLE_STMT_SCANSTATUS
/*
** Configure the VM passed as the first argument with an
** sqlite3_stmt_scanstatus() entry corresponding to the scan used to
** implement level pLvl. Argument pSrclist is a pointer to the FROM
146154
146155
146156
146157
146158
146159
146160
146161
146162
146163
146164
146165
146166
146167





146168
146169


146170
146171
146172
146173
146174
146175
146176
146177
  WhereLoop *pLoop,     /* The current loop */
  Expr *pX              /* The IN expression to be reduced */
){
  sqlite3 *db = pParse->db;
  Expr *pNew;
  pNew = sqlite3ExprDup(db, pX, 0);
  if( db->mallocFailed==0 ){
    ExprList *pOrigRhs = pNew->x.pSelect->pEList;  /* Original unmodified RHS */
    ExprList *pOrigLhs = pNew->pLeft->x.pList;     /* Original unmodified LHS */
    ExprList *pRhs = 0;         /* New RHS after modifications */
    ExprList *pLhs = 0;         /* New LHS after mods */
    int i;                      /* Loop counter */
    Select *pSelect;            /* Pointer to the SELECT on the RHS */






    for(i=iEq; i<pLoop->nLTerm; i++){
      if( pLoop->aLTerm[i]->pExpr==pX ){


        int iField = pLoop->aLTerm[i]->u.x.iField - 1;
        if( pOrigRhs->a[iField].pExpr==0 ) continue; /* Duplicate PK column */
        pRhs = sqlite3ExprListAppend(pParse, pRhs, pOrigRhs->a[iField].pExpr);
        pOrigRhs->a[iField].pExpr = 0;
        assert( pOrigLhs->a[iField].pExpr!=0 );
        pLhs = sqlite3ExprListAppend(pParse, pLhs, pOrigLhs->a[iField].pExpr);
        pOrigLhs->a[iField].pExpr = 0;
      }







|
|





>
>
>
>
>


>
>
|







147048
147049
147050
147051
147052
147053
147054
147055
147056
147057
147058
147059
147060
147061
147062
147063
147064
147065
147066
147067
147068
147069
147070
147071
147072
147073
147074
147075
147076
147077
147078
  WhereLoop *pLoop,     /* The current loop */
  Expr *pX              /* The IN expression to be reduced */
){
  sqlite3 *db = pParse->db;
  Expr *pNew;
  pNew = sqlite3ExprDup(db, pX, 0);
  if( db->mallocFailed==0 ){
    ExprList *pOrigRhs;         /* Original unmodified RHS */
    ExprList *pOrigLhs;         /* Original unmodified LHS */
    ExprList *pRhs = 0;         /* New RHS after modifications */
    ExprList *pLhs = 0;         /* New LHS after mods */
    int i;                      /* Loop counter */
    Select *pSelect;            /* Pointer to the SELECT on the RHS */

    assert( ExprUseXSelect(pNew) );
    pOrigRhs = pNew->x.pSelect->pEList;
    assert( pNew->pLeft!=0 );
    assert( ExprUseXList(pNew->pLeft) );
    pOrigLhs = pNew->pLeft->x.pList;
    for(i=iEq; i<pLoop->nLTerm; i++){
      if( pLoop->aLTerm[i]->pExpr==pX ){
        int iField;
        assert( (pLoop->aLTerm[i]->eOperator & (WO_OR|WO_AND))==0 );
        iField = pLoop->aLTerm[i]->u.x.iField - 1;
        if( pOrigRhs->a[iField].pExpr==0 ) continue; /* Duplicate PK column */
        pRhs = sqlite3ExprListAppend(pParse, pRhs, pOrigRhs->a[iField].pExpr);
        pOrigRhs->a[iField].pExpr = 0;
        assert( pOrigLhs->a[iField].pExpr!=0 );
        pLhs = sqlite3ExprListAppend(pParse, pLhs, pOrigLhs->a[iField].pExpr);
        pOrigLhs->a[iField].pExpr = 0;
      }
146278
146279
146280
146281
146282
146283
146284
146285
146286
146287
146288
146289
146290
146291
146292
    }
    for(i=iEq;i<pLoop->nLTerm; i++){
      assert( pLoop->aLTerm[i]!=0 );
      if( pLoop->aLTerm[i]->pExpr==pX ) nEq++;
    }

    iTab = 0;
    if( (pX->flags & EP_xIsSelect)==0 || pX->x.pSelect->pEList->nExpr==1 ){
      eType = sqlite3FindInIndex(pParse, pX, IN_INDEX_LOOP, 0, 0, &iTab);
    }else{
      sqlite3 *db = pParse->db;
      pX = removeUnindexableInClauseTerms(pParse, iEq, pLoop, pX);

      if( !db->mallocFailed ){
        aiMap = (int*)sqlite3DbMallocZero(pParse->db, sizeof(int)*nEq);







|







147179
147180
147181
147182
147183
147184
147185
147186
147187
147188
147189
147190
147191
147192
147193
    }
    for(i=iEq;i<pLoop->nLTerm; i++){
      assert( pLoop->aLTerm[i]!=0 );
      if( pLoop->aLTerm[i]->pExpr==pX ) nEq++;
    }

    iTab = 0;
    if( !ExprUseXSelect(pX) || pX->x.pSelect->pEList->nExpr==1 ){
      eType = sqlite3FindInIndex(pParse, pX, IN_INDEX_LOOP, 0, 0, &iTab);
    }else{
      sqlite3 *db = pParse->db;
      pX = removeUnindexableInClauseTerms(pParse, iEq, pLoop, pX);

      if( !db->mallocFailed ){
        aiMap = (int*)sqlite3DbMallocZero(pParse->db, sizeof(int)*nEq);
146300
146301
146302
146303
146304
146305
146306
146307
146308

146309
146310
146311
146312
146313
146314
146315
    if( eType==IN_INDEX_INDEX_DESC ){
      testcase( bRev );
      bRev = !bRev;
    }
    sqlite3VdbeAddOp2(v, bRev ? OP_Last : OP_Rewind, iTab, 0);
    VdbeCoverageIf(v, bRev);
    VdbeCoverageIf(v, !bRev);
    assert( (pLoop->wsFlags & WHERE_MULTI_OR)==0 );


    pLoop->wsFlags |= WHERE_IN_ABLE;
    if( pLevel->u.in.nIn==0 ){
      pLevel->addrNxt = sqlite3VdbeMakeLabel(pParse);
    }
    if( iEq>0 && (pLoop->wsFlags & WHERE_IN_SEEKSCAN)==0 ){
      pLoop->wsFlags |= WHERE_IN_EARLYOUT;
    }







<

>







147201
147202
147203
147204
147205
147206
147207

147208
147209
147210
147211
147212
147213
147214
147215
147216
    if( eType==IN_INDEX_INDEX_DESC ){
      testcase( bRev );
      bRev = !bRev;
    }
    sqlite3VdbeAddOp2(v, bRev ? OP_Last : OP_Rewind, iTab, 0);
    VdbeCoverageIf(v, bRev);
    VdbeCoverageIf(v, !bRev);


    assert( (pLoop->wsFlags & WHERE_MULTI_OR)==0 );
    pLoop->wsFlags |= WHERE_IN_ABLE;
    if( pLevel->u.in.nIn==0 ){
      pLevel->addrNxt = sqlite3VdbeMakeLabel(pParse);
    }
    if( iEq>0 && (pLoop->wsFlags & WHERE_IN_SEEKSCAN)==0 ){
      pLoop->wsFlags |= WHERE_IN_EARLYOUT;
    }
146701
146702
146703
146704
146705
146706
146707
146708
146709
146710
146711
146712
146713
146714
146715
  sHint.iTabCur = iCur;
  sHint.iIdxCur = pLevel->iIdxCur;
  sHint.pIdx = pLoop->u.btree.pIndex;
  memset(&sWalker, 0, sizeof(sWalker));
  sWalker.pParse = pParse;
  sWalker.u.pCCurHint = &sHint;
  pWC = &pWInfo->sWC;
  for(i=0; i<pWC->nTerm; i++){
    pTerm = &pWC->a[i];
    if( pTerm->wtFlags & (TERM_VIRTUAL|TERM_CODED) ) continue;
    if( pTerm->prereqAll & pLevel->notReady ) continue;

    /* Any terms specified as part of the ON(...) clause for any LEFT
    ** JOIN for which the current table is not the rhs are omitted
    ** from the cursor-hint.







|







147602
147603
147604
147605
147606
147607
147608
147609
147610
147611
147612
147613
147614
147615
147616
  sHint.iTabCur = iCur;
  sHint.iIdxCur = pLevel->iIdxCur;
  sHint.pIdx = pLoop->u.btree.pIndex;
  memset(&sWalker, 0, sizeof(sWalker));
  sWalker.pParse = pParse;
  sWalker.u.pCCurHint = &sHint;
  pWC = &pWInfo->sWC;
  for(i=0; i<pWC->nBase; i++){
    pTerm = &pWC->a[i];
    if( pTerm->wtFlags & (TERM_VIRTUAL|TERM_CODED) ) continue;
    if( pTerm->prereqAll & pLevel->notReady ) continue;

    /* Any terms specified as part of the ON(...) clause for any LEFT
    ** JOIN for which the current table is not the rhs are omitted
    ** from the cursor-hint.
146843
146844
146845
146846
146847
146848
146849
146850
146851
146852
146853
146854
146855
146856
146857
146858
146859


146860
146861
146862
146863
146864
146865
146866
146867
** this case, generate code to evaluate the expression and leave the
** result in register iReg.
*/
static void codeExprOrVector(Parse *pParse, Expr *p, int iReg, int nReg){
  assert( nReg>0 );
  if( p && sqlite3ExprIsVector(p) ){
#ifndef SQLITE_OMIT_SUBQUERY
    if( (p->flags & EP_xIsSelect) ){
      Vdbe *v = pParse->pVdbe;
      int iSelect;
      assert( p->op==TK_SELECT );
      iSelect = sqlite3CodeSubselect(pParse, p);
      sqlite3VdbeAddOp3(v, OP_Copy, iSelect, iReg, nReg-1);
    }else
#endif
    {
      int i;


      ExprList *pList = p->x.pList;
      assert( nReg<=pList->nExpr );
      for(i=0; i<nReg; i++){
        sqlite3ExprCode(pParse, pList->a[i].pExpr, iReg+i);
      }
    }
  }else{
    assert( nReg==1 || pParse->nErr );







|









>
>
|







147744
147745
147746
147747
147748
147749
147750
147751
147752
147753
147754
147755
147756
147757
147758
147759
147760
147761
147762
147763
147764
147765
147766
147767
147768
147769
147770
** this case, generate code to evaluate the expression and leave the
** result in register iReg.
*/
static void codeExprOrVector(Parse *pParse, Expr *p, int iReg, int nReg){
  assert( nReg>0 );
  if( p && sqlite3ExprIsVector(p) ){
#ifndef SQLITE_OMIT_SUBQUERY
    if( ExprUseXSelect(p) ){
      Vdbe *v = pParse->pVdbe;
      int iSelect;
      assert( p->op==TK_SELECT );
      iSelect = sqlite3CodeSubselect(pParse, p);
      sqlite3VdbeAddOp3(v, OP_Copy, iSelect, iReg, nReg-1);
    }else
#endif
    {
      int i;
      const ExprList *pList;
      assert( ExprUseXList(p) );
      pList = p->x.pList;
      assert( nReg<=pList->nExpr );
      for(i=0; i<nReg; i++){
        sqlite3ExprCode(pParse, pList->a[i].pExpr, iReg+i);
      }
    }
  }else{
    assert( nReg==1 || pParse->nErr );
146906
146907
146908
146909
146910
146911
146912
146913
146914
146915
146916

146917
146918
146919
146920
146921
146922
146923
146924
146925
146926
146927
146928
146929
146930
146931
146932
146933
146934
146935
146936
146937
146938
  IdxExprTrans *pX = p->u.pIdxTrans;
  if( sqlite3ExprCompare(0, pExpr, pX->pIdxExpr, pX->iTabCur)==0 ){
    preserveExpr(pX, pExpr);
    pExpr->affExpr = sqlite3ExprAffinity(pExpr);
    pExpr->op = TK_COLUMN;
    pExpr->iTable = pX->iIdxCur;
    pExpr->iColumn = pX->iIdxCol;
    pExpr->y.pTab = 0;
    testcase( ExprHasProperty(pExpr, EP_Skip) );
    testcase( ExprHasProperty(pExpr, EP_Unlikely) );
    ExprClearProperty(pExpr, EP_Skip|EP_Unlikely);

    return WRC_Prune;
  }else{
    return WRC_Continue;
  }
}

#ifndef SQLITE_OMIT_GENERATED_COLUMNS
/* A walker node callback that translates a column reference to a table
** into a corresponding column reference of an index.
*/
static int whereIndexExprTransColumn(Walker *p, Expr *pExpr){
  if( pExpr->op==TK_COLUMN ){
    IdxExprTrans *pX = p->u.pIdxTrans;
    if( pExpr->iTable==pX->iTabCur && pExpr->iColumn==pX->iTabCol ){
      assert( pExpr->y.pTab!=0 );
      preserveExpr(pX, pExpr);
      pExpr->affExpr = sqlite3TableColumnAffinity(pExpr->y.pTab,pExpr->iColumn);
      pExpr->iTable = pX->iIdxCur;
      pExpr->iColumn = pX->iIdxCol;
      pExpr->y.pTab = 0;
    }
  }







<


|
>














|







147809
147810
147811
147812
147813
147814
147815

147816
147817
147818
147819
147820
147821
147822
147823
147824
147825
147826
147827
147828
147829
147830
147831
147832
147833
147834
147835
147836
147837
147838
147839
147840
147841
  IdxExprTrans *pX = p->u.pIdxTrans;
  if( sqlite3ExprCompare(0, pExpr, pX->pIdxExpr, pX->iTabCur)==0 ){
    preserveExpr(pX, pExpr);
    pExpr->affExpr = sqlite3ExprAffinity(pExpr);
    pExpr->op = TK_COLUMN;
    pExpr->iTable = pX->iIdxCur;
    pExpr->iColumn = pX->iIdxCol;

    testcase( ExprHasProperty(pExpr, EP_Skip) );
    testcase( ExprHasProperty(pExpr, EP_Unlikely) );
    ExprClearProperty(pExpr, EP_Skip|EP_Unlikely|EP_WinFunc|EP_Subrtn);
    pExpr->y.pTab = 0;
    return WRC_Prune;
  }else{
    return WRC_Continue;
  }
}

#ifndef SQLITE_OMIT_GENERATED_COLUMNS
/* A walker node callback that translates a column reference to a table
** into a corresponding column reference of an index.
*/
static int whereIndexExprTransColumn(Walker *p, Expr *pExpr){
  if( pExpr->op==TK_COLUMN ){
    IdxExprTrans *pX = p->u.pIdxTrans;
    if( pExpr->iTable==pX->iTabCur && pExpr->iColumn==pX->iTabCol ){
      assert( ExprUseYTab(pExpr) && pExpr->y.pTab!=0 );
      preserveExpr(pX, pExpr);
      pExpr->affExpr = sqlite3TableColumnAffinity(pExpr->y.pTab,pExpr->iColumn);
      pExpr->iTable = pX->iIdxCur;
      pExpr->iColumn = pX->iIdxCol;
      pExpr->y.pTab = 0;
    }
  }
146972
146973
146974
146975
146976
146977
146978
146979
146980
146981
146982
146983
146984
146985
146986
  x.iTabCur = iTabCur;
  x.iIdxCur = iIdxCur;
  x.pWInfo = pWInfo;
  x.db = pWInfo->pParse->db;
  for(iIdxCol=0; iIdxCol<pIdx->nColumn; iIdxCol++){
    i16 iRef = pIdx->aiColumn[iIdxCol];
    if( iRef==XN_EXPR ){
      assert( aColExpr->a[iIdxCol].pExpr!=0 );
      x.pIdxExpr = aColExpr->a[iIdxCol].pExpr;
      if( sqlite3ExprIsConstant(x.pIdxExpr) ) continue;
      w.xExprCallback = whereIndexExprTransNode;
#ifndef SQLITE_OMIT_GENERATED_COLUMNS
    }else if( iRef>=0
       && (pTab->aCol[iRef].colFlags & COLFLAG_VIRTUAL)!=0
       && ((pTab->aCol[iRef].colFlags & COLFLAG_HASCOLL)==0







|







147875
147876
147877
147878
147879
147880
147881
147882
147883
147884
147885
147886
147887
147888
147889
  x.iTabCur = iTabCur;
  x.iIdxCur = iIdxCur;
  x.pWInfo = pWInfo;
  x.db = pWInfo->pParse->db;
  for(iIdxCol=0; iIdxCol<pIdx->nColumn; iIdxCol++){
    i16 iRef = pIdx->aiColumn[iIdxCol];
    if( iRef==XN_EXPR ){
      assert( aColExpr!=0 && aColExpr->a[iIdxCol].pExpr!=0 );
      x.pIdxExpr = aColExpr->a[iIdxCol].pExpr;
      if( sqlite3ExprIsConstant(x.pIdxExpr) ) continue;
      w.xExprCallback = whereIndexExprTransNode;
#ifndef SQLITE_OMIT_GENERATED_COLUMNS
    }else if( iRef>=0
       && (pTab->aCol[iRef].colFlags & COLFLAG_VIRTUAL)!=0
       && ((pTab->aCol[iRef].colFlags & COLFLAG_HASCOLL)==0
147029
147030
147031
147032
147033
147034
147035

























































147036
147037
147038
147039
147040
147041
147042
    if( pTerm->wtFlags & TERM_CODED ) continue;
    pExpr = pTerm->pExpr;
    if( sqlite3ExprCompare(0, pExpr, pTruth, iTabCur)==0 ){
      pTerm->wtFlags |= TERM_CODED;
    }
  }
}


























































/*
** Generate code for the start of the iLevel-th loop in the WHERE clause
** implementation described by pWInfo.
*/
SQLITE_PRIVATE Bitmask sqlite3WhereCodeOneLoopStart(
  Parse *pParse,       /* Parsing context */







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







147932
147933
147934
147935
147936
147937
147938
147939
147940
147941
147942
147943
147944
147945
147946
147947
147948
147949
147950
147951
147952
147953
147954
147955
147956
147957
147958
147959
147960
147961
147962
147963
147964
147965
147966
147967
147968
147969
147970
147971
147972
147973
147974
147975
147976
147977
147978
147979
147980
147981
147982
147983
147984
147985
147986
147987
147988
147989
147990
147991
147992
147993
147994
147995
147996
147997
147998
147999
148000
148001
148002
    if( pTerm->wtFlags & TERM_CODED ) continue;
    pExpr = pTerm->pExpr;
    if( sqlite3ExprCompare(0, pExpr, pTruth, iTabCur)==0 ){
      pTerm->wtFlags |= TERM_CODED;
    }
  }
}

/*
** This routine is called right after An OP_Filter has been generated and
** before the corresponding index search has been performed.  This routine
** checks to see if there are additional Bloom filters in inner loops that
** can be checked prior to doing the index lookup.  If there are available
** inner-loop Bloom filters, then evaluate those filters now, before the
** index lookup.  The idea is that a Bloom filter check is way faster than
** an index lookup, and the Bloom filter might return false, meaning that
** the index lookup can be skipped.
**
** We know that an inner loop uses a Bloom filter because it has the
** WhereLevel.regFilter set.  If an inner-loop Bloom filter is checked,
** then clear the WhereLevel.regFilter value to prevent the Bloom filter
** from being checked a second time when the inner loop is evaluated.
*/
static SQLITE_NOINLINE void filterPullDown(
  Parse *pParse,       /* Parsing context */
  WhereInfo *pWInfo,   /* Complete information about the WHERE clause */
  int iLevel,          /* Which level of pWInfo->a[] should be coded */
  int addrNxt,         /* Jump here to bypass inner loops */
  Bitmask notReady     /* Loops that are not ready */
){
  while( ++iLevel < pWInfo->nLevel ){
    WhereLevel *pLevel = &pWInfo->a[iLevel];
    WhereLoop *pLoop = pLevel->pWLoop;
    if( pLevel->regFilter==0 ) continue;
    /*         ,--- Because constructBloomFilter() has will not have set
    **  vvvvv--'    pLevel->regFilter if this were true. */
    if( NEVER(pLoop->prereq & notReady) ) continue;
    if( pLoop->wsFlags & WHERE_IPK ){
      WhereTerm *pTerm = pLoop->aLTerm[0];
      int regRowid;
      assert( pTerm!=0 );
      assert( pTerm->pExpr!=0 );
      testcase( pTerm->wtFlags & TERM_VIRTUAL );
      regRowid = sqlite3GetTempReg(pParse);
      regRowid = codeEqualityTerm(pParse, pTerm, pLevel, 0, 0, regRowid);
      sqlite3VdbeAddOp4Int(pParse->pVdbe, OP_Filter, pLevel->regFilter,
                           addrNxt, regRowid, 1);
      VdbeCoverage(pParse->pVdbe);
    }else{
      u16 nEq = pLoop->u.btree.nEq;
      int r1;
      char *zStartAff;

      assert( pLoop->wsFlags & WHERE_INDEXED );
      r1 = codeAllEqualityTerms(pParse,pLevel,0,0,&zStartAff);
      codeApplyAffinity(pParse, r1, nEq, zStartAff);
      sqlite3DbFree(pParse->db, zStartAff);
      sqlite3VdbeAddOp4Int(pParse->pVdbe, OP_Filter, pLevel->regFilter,
                           addrNxt, r1, nEq);
      VdbeCoverage(pParse->pVdbe);
    }
    pLevel->regFilter = 0;
  }
}

/*
** Generate code for the start of the iLevel-th loop in the WHERE clause
** implementation described by pWInfo.
*/
SQLITE_PRIVATE Bitmask sqlite3WhereCodeOneLoopStart(
  Parse *pParse,       /* Parsing context */
147161
147162
147163
147164
147165
147166
147167


147168



147169
147170
147171
147172
147173
147174
147175
    pLoop->u.vtab.needFree = 0;
    /* An OOM inside of AddOp4(OP_VFilter) instruction above might have freed
    ** the u.vtab.idxStr.  NULL it out to prevent a use-after-free */
    if( db->mallocFailed ) pLoop->u.vtab.idxStr = 0;
    pLevel->p1 = iCur;
    pLevel->op = pWInfo->eOnePass ? OP_Noop : OP_VNext;
    pLevel->p2 = sqlite3VdbeCurrentAddr(v);


    iIn = pLevel->u.in.nIn;



    for(j=nConstraint-1; j>=0; j--){
      pTerm = pLoop->aLTerm[j];
      if( (pTerm->eOperator & WO_IN)!=0 ) iIn--;
      if( j<16 && (pLoop->u.vtab.omitMask>>j)&1 ){
        disableTerm(pLevel, pTerm);
      }else if( (pTerm->eOperator & WO_IN)!=0
        && sqlite3ExprVectorSize(pTerm->pExpr->pLeft)==1







>
>
|
>
>
>







148121
148122
148123
148124
148125
148126
148127
148128
148129
148130
148131
148132
148133
148134
148135
148136
148137
148138
148139
148140
    pLoop->u.vtab.needFree = 0;
    /* An OOM inside of AddOp4(OP_VFilter) instruction above might have freed
    ** the u.vtab.idxStr.  NULL it out to prevent a use-after-free */
    if( db->mallocFailed ) pLoop->u.vtab.idxStr = 0;
    pLevel->p1 = iCur;
    pLevel->op = pWInfo->eOnePass ? OP_Noop : OP_VNext;
    pLevel->p2 = sqlite3VdbeCurrentAddr(v);
    assert( (pLoop->wsFlags & WHERE_MULTI_OR)==0 );
    if( pLoop->wsFlags & WHERE_IN_ABLE ){
      iIn = pLevel->u.in.nIn;
    }else{
      iIn = 0;
    }
    for(j=nConstraint-1; j>=0; j--){
      pTerm = pLoop->aLTerm[j];
      if( (pTerm->eOperator & WO_IN)!=0 ) iIn--;
      if( j<16 && (pLoop->u.vtab.omitMask>>j)&1 ){
        disableTerm(pLevel, pTerm);
      }else if( (pTerm->eOperator & WO_IN)!=0
        && sqlite3ExprVectorSize(pTerm->pExpr->pLeft)==1
147235
147236
147237
147238
147239
147240
147241






147242
147243
147244
147245
147246
147247
147248
    assert( pTerm!=0 );
    assert( pTerm->pExpr!=0 );
    testcase( pTerm->wtFlags & TERM_VIRTUAL );
    iReleaseReg = ++pParse->nMem;
    iRowidReg = codeEqualityTerm(pParse, pTerm, pLevel, 0, bRev, iReleaseReg);
    if( iRowidReg!=iReleaseReg ) sqlite3ReleaseTempReg(pParse, iReleaseReg);
    addrNxt = pLevel->addrNxt;






    sqlite3VdbeAddOp3(v, OP_SeekRowid, iCur, addrNxt, iRowidReg);
    VdbeCoverage(v);
    pLevel->op = OP_Noop;
  }else if( (pLoop->wsFlags & WHERE_IPK)!=0
         && (pLoop->wsFlags & WHERE_COLUMN_RANGE)!=0
  ){
    /* Case 3:  We have an inequality comparison against the ROWID field.







>
>
>
>
>
>







148200
148201
148202
148203
148204
148205
148206
148207
148208
148209
148210
148211
148212
148213
148214
148215
148216
148217
148218
148219
    assert( pTerm!=0 );
    assert( pTerm->pExpr!=0 );
    testcase( pTerm->wtFlags & TERM_VIRTUAL );
    iReleaseReg = ++pParse->nMem;
    iRowidReg = codeEqualityTerm(pParse, pTerm, pLevel, 0, bRev, iReleaseReg);
    if( iRowidReg!=iReleaseReg ) sqlite3ReleaseTempReg(pParse, iReleaseReg);
    addrNxt = pLevel->addrNxt;
    if( pLevel->regFilter ){
      sqlite3VdbeAddOp4Int(v, OP_Filter, pLevel->regFilter, addrNxt,
                           iRowidReg, 1);
      VdbeCoverage(v);
      filterPullDown(pParse, pWInfo, iLevel, addrNxt, notReady);
    }
    sqlite3VdbeAddOp3(v, OP_SeekRowid, iCur, addrNxt, iRowidReg);
    VdbeCoverage(v);
    pLevel->op = OP_Noop;
  }else if( (pLoop->wsFlags & WHERE_IPK)!=0
         && (pLoop->wsFlags & WHERE_COLUMN_RANGE)!=0
  ){
    /* Case 3:  We have an inequality comparison against the ROWID field.
147560
147561
147562
147563
147564
147565
147566






147567
147568
147569
147570
147571
147572
147573
      ** above has already left the cursor sitting on the correct row,
      ** so no further seeking is needed */
    }else{
      if( regBignull ){
        sqlite3VdbeAddOp2(v, OP_Integer, 1, regBignull);
        VdbeComment((v, "NULL-scan pass ctr"));
      }







      op = aStartOp[(start_constraints<<2) + (startEq<<1) + bRev];
      assert( op!=0 );
      if( (pLoop->wsFlags & WHERE_IN_SEEKSCAN)!=0 && op==OP_SeekGE ){
        assert( regBignull==0 );
        /* TUNING:  The OP_SeekScan opcode seeks to reduce the number
        ** of expensive seek operations by replacing a single seek with







>
>
>
>
>
>







148531
148532
148533
148534
148535
148536
148537
148538
148539
148540
148541
148542
148543
148544
148545
148546
148547
148548
148549
148550
      ** above has already left the cursor sitting on the correct row,
      ** so no further seeking is needed */
    }else{
      if( regBignull ){
        sqlite3VdbeAddOp2(v, OP_Integer, 1, regBignull);
        VdbeComment((v, "NULL-scan pass ctr"));
      }
      if( pLevel->regFilter ){
        sqlite3VdbeAddOp4Int(v, OP_Filter, pLevel->regFilter, addrNxt,
                             regBase, nEq);
        VdbeCoverage(v);
        filterPullDown(pParse, pWInfo, iLevel, addrNxt, notReady);
      }

      op = aStartOp[(start_constraints<<2) + (startEq<<1) + bRev];
      assert( op!=0 );
      if( (pLoop->wsFlags & WHERE_IN_SEEKSCAN)!=0 && op==OP_SeekGE ){
        assert( regBignull==0 );
        /* TUNING:  The OP_SeekScan opcode seeks to reduce the number
        ** of expensive seek operations by replacing a single seek with
147608
147609
147610
147611
147612
147613
147614

147615
147616










147617
147618
147619
147620
147621
147622
147623
      }
    }

    /* Load the value for the inequality constraint at the end of the
    ** range (if any).
    */
    nConstraint = nEq;

    if( pRangeEnd ){
      Expr *pRight = pRangeEnd->pExpr->pRight;










      codeExprOrVector(pParse, pRight, regBase+nEq, nTop);
      whereLikeOptimizationStringFixup(v, pLevel, pRangeEnd);
      if( (pRangeEnd->wtFlags & TERM_VNULL)==0
       && sqlite3ExprCanBeNull(pRight)
      ){
        sqlite3VdbeAddOp2(v, OP_IsNull, regBase+nEq, addrNxt);
        VdbeCoverage(v);







>


>
>
>
>
>
>
>
>
>
>







148585
148586
148587
148588
148589
148590
148591
148592
148593
148594
148595
148596
148597
148598
148599
148600
148601
148602
148603
148604
148605
148606
148607
148608
148609
148610
148611
      }
    }

    /* Load the value for the inequality constraint at the end of the
    ** range (if any).
    */
    nConstraint = nEq;
    assert( pLevel->p2==0 );
    if( pRangeEnd ){
      Expr *pRight = pRangeEnd->pExpr->pRight;
      if( addrSeekScan ){
        /* For a seek-scan that has a range on the lowest term of the index,
        ** we have to make the top of the loop be code that sets the end
        ** condition of the range.  Otherwise, the OP_SeekScan might jump
        ** over that initialization, leaving the range-end value set to the
        ** range-start value, resulting in a wrong answer.
        ** See ticket 5981a8c041a3c2f3 (2021-11-02).
        */
        pLevel->p2 = sqlite3VdbeCurrentAddr(v);
      }
      codeExprOrVector(pParse, pRight, regBase+nEq, nTop);
      whereLikeOptimizationStringFixup(v, pLevel, pRangeEnd);
      if( (pRangeEnd->wtFlags & TERM_VNULL)==0
       && sqlite3ExprCanBeNull(pRight)
      ){
        sqlite3VdbeAddOp2(v, OP_IsNull, regBase+nEq, addrNxt);
        VdbeCoverage(v);
147643
147644
147645
147646
147647
147648
147649
147650
147651
147652
147653
147654
147655
147656
147657
      }
      nConstraint++;
    }
    sqlite3DbFree(db, zStartAff);
    sqlite3DbFree(db, zEndAff);

    /* Top of the loop body */
    pLevel->p2 = sqlite3VdbeCurrentAddr(v);

    /* Check if the index cursor is past the end of the range. */
    if( nConstraint ){
      if( regBignull ){
        /* Except, skip the end-of-range check while doing the NULL-scan */
        sqlite3VdbeAddOp2(v, OP_IfNot, regBignull, sqlite3VdbeCurrentAddr(v)+3);
        VdbeComment((v, "If NULL-scan 2nd pass"));







|







148631
148632
148633
148634
148635
148636
148637
148638
148639
148640
148641
148642
148643
148644
148645
      }
      nConstraint++;
    }
    sqlite3DbFree(db, zStartAff);
    sqlite3DbFree(db, zEndAff);

    /* Top of the loop body */
    if( pLevel->p2==0 ) pLevel->p2 = sqlite3VdbeCurrentAddr(v);

    /* Check if the index cursor is past the end of the range. */
    if( nConstraint ){
      if( regBignull ){
        /* Except, skip the end-of-range check while doing the NULL-scan */
        sqlite3VdbeAddOp2(v, OP_IfNot, regBignull, sqlite3VdbeCurrentAddr(v)+3);
        VdbeComment((v, "If NULL-scan 2nd pass"));
148050
148051
148052
148053
148054
148055
148056



148057
148058
148059
148060
148061
148062
148063
148064
          sqlite3WhereEnd(pSubWInfo);
          ExplainQueryPlanPop(pParse);
        }
        sqlite3ExprDelete(db, pDelete);
      }
    }
    ExplainQueryPlanPop(pParse);



    pLevel->u.pCovidx = pCov;
    if( pCov ) pLevel->iIdxCur = iCovCur;
    if( pAndExpr ){
      pAndExpr->pLeft = 0;
      sqlite3ExprDelete(db, pAndExpr);
    }
    sqlite3VdbeChangeP1(v, iRetInit, sqlite3VdbeCurrentAddr(v));
    sqlite3VdbeGoto(v, pLevel->addrBrk);







>
>
>
|







149038
149039
149040
149041
149042
149043
149044
149045
149046
149047
149048
149049
149050
149051
149052
149053
149054
149055
          sqlite3WhereEnd(pSubWInfo);
          ExplainQueryPlanPop(pParse);
        }
        sqlite3ExprDelete(db, pDelete);
      }
    }
    ExplainQueryPlanPop(pParse);
    assert( pLevel->pWLoop==pLoop );
    assert( (pLoop->wsFlags & WHERE_MULTI_OR)!=0 );
    assert( (pLoop->wsFlags & WHERE_IN_ABLE)==0 );
    pLevel->u.pCoveringIdx = pCov;
    if( pCov ) pLevel->iIdxCur = iCovCur;
    if( pAndExpr ){
      pAndExpr->pLeft = 0;
      sqlite3ExprDelete(db, pAndExpr);
    }
    sqlite3VdbeChangeP1(v, iRetInit, sqlite3VdbeCurrentAddr(v));
    sqlite3VdbeGoto(v, pLevel->addrBrk);
148177
148178
148179
148180
148181
148182
148183
148184
148185
148186
148187
148188
148189
148190
148191
148192
148193
148194
148195
148196
148197
148198
148199
148200

148201
148202
148203
148204
148205
148206
148207
148208
148209
148210
148211
148212
148213
  ** of the "==" operator.
  **
  ** Example: If the WHERE clause contains "t1.a=t2.b" and "t2.b=123"
  ** and we are coding the t1 loop and the t2 loop has not yet coded,
  ** then we cannot use the "t1.a=t2.b" constraint, but we can code
  ** the implied "t1.a=123" constraint.
  */
  for(pTerm=pWC->a, j=pWC->nTerm; j>0; j--, pTerm++){
    Expr *pE, sEAlt;
    WhereTerm *pAlt;
    if( pTerm->wtFlags & (TERM_VIRTUAL|TERM_CODED) ) continue;
    if( (pTerm->eOperator & (WO_EQ|WO_IS))==0 ) continue;
    if( (pTerm->eOperator & WO_EQUIV)==0 ) continue;
    if( pTerm->leftCursor!=iCur ) continue;
    if( pTabItem->fg.jointype & JT_LEFT ) continue;
    pE = pTerm->pExpr;
#ifdef WHERETRACE_ENABLED /* 0x800 */
    if( sqlite3WhereTrace & 0x800 ){
      sqlite3DebugPrintf("Coding transitive constraint:\n");
      sqlite3WhereTermPrint(pTerm, pWC->nTerm-j);
    }
#endif
    assert( !ExprHasProperty(pE, EP_FromJoin) );
    assert( (pTerm->prereqRight & pLevel->notReady)!=0 );

    pAlt = sqlite3WhereFindTerm(pWC, iCur, pTerm->u.x.leftColumn, notReady,
                    WO_EQ|WO_IN|WO_IS, 0);
    if( pAlt==0 ) continue;
    if( pAlt->wtFlags & (TERM_CODED) ) continue;
    if( (pAlt->eOperator & WO_IN)
     && (pAlt->pExpr->flags & EP_xIsSelect)
     && (pAlt->pExpr->x.pSelect->pEList->nExpr>1)
    ){
      continue;
    }
    testcase( pAlt->eOperator & WO_EQ );
    testcase( pAlt->eOperator & WO_IS );
    testcase( pAlt->eOperator & WO_IN );







|
















>





|







149168
149169
149170
149171
149172
149173
149174
149175
149176
149177
149178
149179
149180
149181
149182
149183
149184
149185
149186
149187
149188
149189
149190
149191
149192
149193
149194
149195
149196
149197
149198
149199
149200
149201
149202
149203
149204
149205
  ** of the "==" operator.
  **
  ** Example: If the WHERE clause contains "t1.a=t2.b" and "t2.b=123"
  ** and we are coding the t1 loop and the t2 loop has not yet coded,
  ** then we cannot use the "t1.a=t2.b" constraint, but we can code
  ** the implied "t1.a=123" constraint.
  */
  for(pTerm=pWC->a, j=pWC->nBase; j>0; j--, pTerm++){
    Expr *pE, sEAlt;
    WhereTerm *pAlt;
    if( pTerm->wtFlags & (TERM_VIRTUAL|TERM_CODED) ) continue;
    if( (pTerm->eOperator & (WO_EQ|WO_IS))==0 ) continue;
    if( (pTerm->eOperator & WO_EQUIV)==0 ) continue;
    if( pTerm->leftCursor!=iCur ) continue;
    if( pTabItem->fg.jointype & JT_LEFT ) continue;
    pE = pTerm->pExpr;
#ifdef WHERETRACE_ENABLED /* 0x800 */
    if( sqlite3WhereTrace & 0x800 ){
      sqlite3DebugPrintf("Coding transitive constraint:\n");
      sqlite3WhereTermPrint(pTerm, pWC->nTerm-j);
    }
#endif
    assert( !ExprHasProperty(pE, EP_FromJoin) );
    assert( (pTerm->prereqRight & pLevel->notReady)!=0 );
    assert( (pTerm->eOperator & (WO_OR|WO_AND))==0 );
    pAlt = sqlite3WhereFindTerm(pWC, iCur, pTerm->u.x.leftColumn, notReady,
                    WO_EQ|WO_IN|WO_IS, 0);
    if( pAlt==0 ) continue;
    if( pAlt->wtFlags & (TERM_CODED) ) continue;
    if( (pAlt->eOperator & WO_IN)
     && ExprUseXSelect(pAlt->pExpr)
     && (pAlt->pExpr->x.pSelect->pEList->nExpr>1)
    ){
      continue;
    }
    testcase( pAlt->eOperator & WO_EQ );
    testcase( pAlt->eOperator & WO_IS );
    testcase( pAlt->eOperator & WO_IN );
148221
148222
148223
148224
148225
148226
148227
148228
148229
148230
148231
148232
148233
148234
148235
  /* For a LEFT OUTER JOIN, generate code that will record the fact that
  ** at least one row of the right table has matched the left table.
  */
  if( pLevel->iLeftJoin ){
    pLevel->addrFirst = sqlite3VdbeCurrentAddr(v);
    sqlite3VdbeAddOp2(v, OP_Integer, 1, pLevel->iLeftJoin);
    VdbeComment((v, "record LEFT JOIN hit"));
    for(pTerm=pWC->a, j=0; j<pWC->nTerm; j++, pTerm++){
      testcase( pTerm->wtFlags & TERM_VIRTUAL );
      testcase( pTerm->wtFlags & TERM_CODED );
      if( pTerm->wtFlags & (TERM_VIRTUAL|TERM_CODED) ) continue;
      if( (pTerm->prereqAll & pLevel->notReady)!=0 ){
        assert( pWInfo->untestedTerms );
        continue;
      }







|







149213
149214
149215
149216
149217
149218
149219
149220
149221
149222
149223
149224
149225
149226
149227
  /* For a LEFT OUTER JOIN, generate code that will record the fact that
  ** at least one row of the right table has matched the left table.
  */
  if( pLevel->iLeftJoin ){
    pLevel->addrFirst = sqlite3VdbeCurrentAddr(v);
    sqlite3VdbeAddOp2(v, OP_Integer, 1, pLevel->iLeftJoin);
    VdbeComment((v, "record LEFT JOIN hit"));
    for(pTerm=pWC->a, j=0; j<pWC->nBase; j++, pTerm++){
      testcase( pTerm->wtFlags & TERM_VIRTUAL );
      testcase( pTerm->wtFlags & TERM_CODED );
      if( pTerm->wtFlags & (TERM_VIRTUAL|TERM_CODED) ) continue;
      if( (pTerm->prereqAll & pLevel->notReady)!=0 ){
        assert( pWInfo->untestedTerms );
        continue;
      }
148332
148333
148334
148335
148336
148337
148338

148339
148340
148341
148342
148343
148344
148345
    memcpy(pWC->a, pOld, sizeof(pWC->a[0])*pWC->nTerm);
    if( pOld!=pWC->aStatic ){
      sqlite3DbFree(db, pOld);
    }
    pWC->nSlot = sqlite3DbMallocSize(db, pWC->a)/sizeof(pWC->a[0]);
  }
  pTerm = &pWC->a[idx = pWC->nTerm++];

  if( p && ExprHasProperty(p, EP_Unlikely) ){
    pTerm->truthProb = sqlite3LogEst(p->iTable) - 270;
  }else{
    pTerm->truthProb = 1;
  }
  pTerm->pExpr = sqlite3ExprSkipCollateAndLikely(p);
  pTerm->wtFlags = wtFlags;







>







149324
149325
149326
149327
149328
149329
149330
149331
149332
149333
149334
149335
149336
149337
149338
    memcpy(pWC->a, pOld, sizeof(pWC->a[0])*pWC->nTerm);
    if( pOld!=pWC->aStatic ){
      sqlite3DbFree(db, pOld);
    }
    pWC->nSlot = sqlite3DbMallocSize(db, pWC->a)/sizeof(pWC->a[0]);
  }
  pTerm = &pWC->a[idx = pWC->nTerm++];
  if( (wtFlags & TERM_VIRTUAL)==0 ) pWC->nBase = pWC->nTerm;
  if( p && ExprHasProperty(p, EP_Unlikely) ){
    pTerm->truthProb = sqlite3LogEst(p->iTable) - 270;
  }else{
    pTerm->truthProb = 1;
  }
  pTerm->pExpr = sqlite3ExprSkipCollateAndLikely(p);
  pTerm->wtFlags = wtFlags;
148448
148449
148450
148451
148452
148453
148454

148455
148456
148457
148458
148459
148460
148461
148462
148463
148464
148465
148466
148467
148468
148469

148470
148471
148472
148473
148474
148475
148476
148477

  if( !sqlite3IsLikeFunction(db, pExpr, pnoCase, (char*)wc) ){
    return 0;
  }
#ifdef SQLITE_EBCDIC
  if( *pnoCase ) return 0;
#endif

  pList = pExpr->x.pList;
  pLeft = pList->a[1].pExpr;

  pRight = sqlite3ExprSkipCollate(pList->a[0].pExpr);
  op = pRight->op;
  if( op==TK_VARIABLE && (db->flags & SQLITE_EnableQPSG)==0 ){
    Vdbe *pReprepare = pParse->pReprepare;
    int iCol = pRight->iColumn;
    pVal = sqlite3VdbeGetBoundValue(pReprepare, iCol, SQLITE_AFF_BLOB);
    if( pVal && sqlite3_value_type(pVal)==SQLITE_TEXT ){
      z = sqlite3_value_text(pVal);
    }
    sqlite3VdbeSetVarmask(pParse->pVdbe, iCol);
    assert( pRight->op==TK_VARIABLE || pRight->op==TK_REGISTER );
  }else if( op==TK_STRING ){

    z = (u8*)pRight->u.zToken;
  }
  if( z ){

    /* Count the number of prefix characters prior to the first wildcard */
    cnt = 0;
    while( (c=z[cnt])!=0 && c!=wc[0] && c!=wc[1] && c!=wc[2] ){
      cnt++;







>















>
|







149441
149442
149443
149444
149445
149446
149447
149448
149449
149450
149451
149452
149453
149454
149455
149456
149457
149458
149459
149460
149461
149462
149463
149464
149465
149466
149467
149468
149469
149470
149471
149472

  if( !sqlite3IsLikeFunction(db, pExpr, pnoCase, (char*)wc) ){
    return 0;
  }
#ifdef SQLITE_EBCDIC
  if( *pnoCase ) return 0;
#endif
  assert( ExprUseXList(pExpr) );
  pList = pExpr->x.pList;
  pLeft = pList->a[1].pExpr;

  pRight = sqlite3ExprSkipCollate(pList->a[0].pExpr);
  op = pRight->op;
  if( op==TK_VARIABLE && (db->flags & SQLITE_EnableQPSG)==0 ){
    Vdbe *pReprepare = pParse->pReprepare;
    int iCol = pRight->iColumn;
    pVal = sqlite3VdbeGetBoundValue(pReprepare, iCol, SQLITE_AFF_BLOB);
    if( pVal && sqlite3_value_type(pVal)==SQLITE_TEXT ){
      z = sqlite3_value_text(pVal);
    }
    sqlite3VdbeSetVarmask(pParse->pVdbe, iCol);
    assert( pRight->op==TK_VARIABLE || pRight->op==TK_REGISTER );
  }else if( op==TK_STRING ){
    assert( !ExprHasProperty(pRight, EP_IntValue) );
     z = (u8*)pRight->u.zToken;
  }
  if( z ){

    /* Count the number of prefix characters prior to the first wildcard */
    cnt = 0;
    while( (c=z[cnt])!=0 && c!=wc[0] && c!=wc[1] && c!=wc[2] ){
      cnt++;
148492
148493
148494
148495
148496
148497
148498


148499
148500
148501
148502
148503
148504
148505
148506
      /* A "complete" match if the pattern ends with "*" or "%" */
      *pisComplete = c==wc[0] && z[cnt+1]==0;

      /* Get the pattern prefix.  Remove all escapes from the prefix. */
      pPrefix = sqlite3Expr(db, TK_STRING, (char*)z);
      if( pPrefix ){
        int iFrom, iTo;


        char *zNew = pPrefix->u.zToken;
        zNew[cnt] = 0;
        for(iFrom=iTo=0; iFrom<cnt; iFrom++){
          if( zNew[iFrom]==wc[3] ) iFrom++;
          zNew[iTo++] = zNew[iFrom];
        }
        zNew[iTo] = 0;
        assert( iTo>0 );







>
>
|







149487
149488
149489
149490
149491
149492
149493
149494
149495
149496
149497
149498
149499
149500
149501
149502
149503
      /* A "complete" match if the pattern ends with "*" or "%" */
      *pisComplete = c==wc[0] && z[cnt+1]==0;

      /* Get the pattern prefix.  Remove all escapes from the prefix. */
      pPrefix = sqlite3Expr(db, TK_STRING, (char*)z);
      if( pPrefix ){
        int iFrom, iTo;
        char *zNew;
        assert( !ExprHasProperty(pPrefix, EP_IntValue) );
        zNew = pPrefix->u.zToken;
        zNew[cnt] = 0;
        for(iFrom=iTo=0; iFrom<cnt; iFrom++){
          if( zNew[iFrom]==wc[3] ) iFrom++;
          zNew[iTo++] = zNew[iFrom];
        }
        zNew[iTo] = 0;
        assert( iTo>0 );
148516
148517
148518
148519
148520
148521
148522


148523
148524
148525
148526
148527
148528
148529
148530
        **    2019-05-02 https://sqlite.org/src/info/b043a54c3de54b28
        **    2019-06-10 https://sqlite.org/src/info/fd76310a5e843e07
        **    2019-06-14 https://sqlite.org/src/info/ce8717f0885af975
        **    2019-09-03 https://sqlite.org/src/info/0f0428096f17252a
        */
        if( pLeft->op!=TK_COLUMN
         || sqlite3ExprAffinity(pLeft)!=SQLITE_AFF_TEXT


         || (pLeft->y.pTab && IsVirtual(pLeft->y.pTab))  /* Might be numeric */
        ){
          int isNum;
          double rDummy;
          isNum = sqlite3AtoF(zNew, &rDummy, iTo, SQLITE_UTF8);
          if( isNum<=0 ){
            if( iTo==1 && zNew[0]=='-' ){
              isNum = +1;







>
>
|







149513
149514
149515
149516
149517
149518
149519
149520
149521
149522
149523
149524
149525
149526
149527
149528
149529
        **    2019-05-02 https://sqlite.org/src/info/b043a54c3de54b28
        **    2019-06-10 https://sqlite.org/src/info/fd76310a5e843e07
        **    2019-06-14 https://sqlite.org/src/info/ce8717f0885af975
        **    2019-09-03 https://sqlite.org/src/info/0f0428096f17252a
        */
        if( pLeft->op!=TK_COLUMN
         || sqlite3ExprAffinity(pLeft)!=SQLITE_AFF_TEXT
         || (ALWAYS( ExprUseYTab(pLeft) )
             && pLeft->y.pTab
             && IsVirtual(pLeft->y.pTab))  /* Might be numeric */
        ){
          int isNum;
          double rDummy;
          isNum = sqlite3AtoF(zNew, &rDummy, iTo, SQLITE_UTF8);
          if( isNum<=0 ){
            if( iTo==1 && zNew[0]=='-' ){
              isNum = +1;
148544
148545
148546
148547
148548
148549
148550

148551
148552
148553
148554
148555
148556
148557
      *ppPrefix = pPrefix;

      /* If the RHS pattern is a bound parameter, make arrangements to
      ** reprepare the statement when that parameter is rebound */
      if( op==TK_VARIABLE ){
        Vdbe *v = pParse->pVdbe;
        sqlite3VdbeSetVarmask(v, pRight->iColumn);

        if( *pisComplete && pRight->u.zToken[1] ){
          /* If the rhs of the LIKE expression is a variable, and the current
          ** value of the variable means there is no need to invoke the LIKE
          ** function, then no OP_Variable will be added to the program.
          ** This causes problems for the sqlite3_bind_parameter_name()
          ** API. To work around them, add a dummy OP_Variable here.
          */







>







149543
149544
149545
149546
149547
149548
149549
149550
149551
149552
149553
149554
149555
149556
149557
      *ppPrefix = pPrefix;

      /* If the RHS pattern is a bound parameter, make arrangements to
      ** reprepare the statement when that parameter is rebound */
      if( op==TK_VARIABLE ){
        Vdbe *v = pParse->pVdbe;
        sqlite3VdbeSetVarmask(v, pRight->iColumn);
        assert( !ExprHasProperty(pRight, EP_IntValue) );
        if( *pisComplete && pRight->u.zToken[1] ){
          /* If the rhs of the LIKE expression is a variable, and the current
          ** value of the variable means there is no need to invoke the LIKE
          ** function, then no OP_Variable will be added to the program.
          ** This causes problems for the sqlite3_bind_parameter_name()
          ** API. To work around them, add a dummy OP_Variable here.
          */
148617
148618
148619
148620
148621
148622
148623

148624
148625
148626
148627
148628
148629
148630
148631
148632
148633
148634
148635
148636

148637
148638
148639

148640
148641
148642
148643
148644
148645
148646
148647
148648
148649
148650
148651
148652
148653
148654
148655
148656
148657
148658
148659

148660
148661
148662
148663
148664
148665
148666
148667
148668

148669
148670
148671
148672
148673
148674
148675
148676
148677
148678
148679
148680
148681
148682
148683

148684
148685
148686
148687

148688
148689
148690
148691
148692
148693
148694
      { "like",   SQLITE_INDEX_CONSTRAINT_LIKE },
      { "regexp", SQLITE_INDEX_CONSTRAINT_REGEXP }
    };
    ExprList *pList;
    Expr *pCol;                     /* Column reference */
    int i;


    pList = pExpr->x.pList;
    if( pList==0 || pList->nExpr!=2 ){
      return 0;
    }

    /* Built-in operators MATCH, GLOB, LIKE, and REGEXP attach to a
    ** virtual table on their second argument, which is the same as
    ** the left-hand side operand in their in-fix form.
    **
    **       vtab_column MATCH expression
    **       MATCH(expression,vtab_column)
    */
    pCol = pList->a[1].pExpr;

    testcase( pCol->op==TK_COLUMN && pCol->y.pTab==0 );
    if( ExprIsVtab(pCol) ){
      for(i=0; i<ArraySize(aOp); i++){

        if( sqlite3StrICmp(pExpr->u.zToken, aOp[i].zOp)==0 ){
          *peOp2 = aOp[i].eOp2;
          *ppRight = pList->a[0].pExpr;
          *ppLeft = pCol;
          return 1;
        }
      }
    }

    /* We can also match against the first column of overloaded
    ** functions where xFindFunction returns a value of at least
    ** SQLITE_INDEX_CONSTRAINT_FUNCTION.
    **
    **      OVERLOADED(vtab_column,expression)
    **
    ** Historically, xFindFunction expected to see lower-case function
    ** names.  But for this use case, xFindFunction is expected to deal
    ** with function names in an arbitrary case.
    */
    pCol = pList->a[0].pExpr;

    testcase( pCol->op==TK_COLUMN && pCol->y.pTab==0 );
    if( ExprIsVtab(pCol) ){
      sqlite3_vtab *pVtab;
      sqlite3_module *pMod;
      void (*xNotUsed)(sqlite3_context*,int,sqlite3_value**);
      void *pNotUsed;
      pVtab = sqlite3GetVTable(db, pCol->y.pTab)->pVtab;
      assert( pVtab!=0 );
      assert( pVtab->pModule!=0 );

      pMod = (sqlite3_module *)pVtab->pModule;
      if( pMod->xFindFunction!=0 ){
        i = pMod->xFindFunction(pVtab,2, pExpr->u.zToken, &xNotUsed, &pNotUsed);
        if( i>=SQLITE_INDEX_CONSTRAINT_FUNCTION ){
          *peOp2 = i;
          *ppRight = pList->a[1].pExpr;
          *ppLeft = pCol;
          return 1;
        }
      }
    }
  }else if( pExpr->op==TK_NE || pExpr->op==TK_ISNOT || pExpr->op==TK_NOTNULL ){
    int res = 0;
    Expr *pLeft = pExpr->pLeft;
    Expr *pRight = pExpr->pRight;

    testcase( pLeft->op==TK_COLUMN && pLeft->y.pTab==0 );
    if( ExprIsVtab(pLeft) ){
      res++;
    }

    testcase( pRight && pRight->op==TK_COLUMN && pRight->y.pTab==0 );
    if( pRight && ExprIsVtab(pRight) ){
      res++;
      SWAP(Expr*, pLeft, pRight);
    }
    *ppLeft = pLeft;
    *ppRight = pRight;







>













>



>




















>









>
|














>




>







149617
149618
149619
149620
149621
149622
149623
149624
149625
149626
149627
149628
149629
149630
149631
149632
149633
149634
149635
149636
149637
149638
149639
149640
149641
149642
149643
149644
149645
149646
149647
149648
149649
149650
149651
149652
149653
149654
149655
149656
149657
149658
149659
149660
149661
149662
149663
149664
149665
149666
149667
149668
149669
149670
149671
149672
149673
149674
149675
149676
149677
149678
149679
149680
149681
149682
149683
149684
149685
149686
149687
149688
149689
149690
149691
149692
149693
149694
149695
149696
149697
149698
149699
149700
149701
      { "like",   SQLITE_INDEX_CONSTRAINT_LIKE },
      { "regexp", SQLITE_INDEX_CONSTRAINT_REGEXP }
    };
    ExprList *pList;
    Expr *pCol;                     /* Column reference */
    int i;

    assert( ExprUseXList(pExpr) );
    pList = pExpr->x.pList;
    if( pList==0 || pList->nExpr!=2 ){
      return 0;
    }

    /* Built-in operators MATCH, GLOB, LIKE, and REGEXP attach to a
    ** virtual table on their second argument, which is the same as
    ** the left-hand side operand in their in-fix form.
    **
    **       vtab_column MATCH expression
    **       MATCH(expression,vtab_column)
    */
    pCol = pList->a[1].pExpr;
    assert( pCol->op!=TK_COLUMN || ExprUseYTab(pCol) );
    testcase( pCol->op==TK_COLUMN && pCol->y.pTab==0 );
    if( ExprIsVtab(pCol) ){
      for(i=0; i<ArraySize(aOp); i++){
        assert( !ExprHasProperty(pExpr, EP_IntValue) );
        if( sqlite3StrICmp(pExpr->u.zToken, aOp[i].zOp)==0 ){
          *peOp2 = aOp[i].eOp2;
          *ppRight = pList->a[0].pExpr;
          *ppLeft = pCol;
          return 1;
        }
      }
    }

    /* We can also match against the first column of overloaded
    ** functions where xFindFunction returns a value of at least
    ** SQLITE_INDEX_CONSTRAINT_FUNCTION.
    **
    **      OVERLOADED(vtab_column,expression)
    **
    ** Historically, xFindFunction expected to see lower-case function
    ** names.  But for this use case, xFindFunction is expected to deal
    ** with function names in an arbitrary case.
    */
    pCol = pList->a[0].pExpr;
    assert( pCol->op!=TK_COLUMN || ExprUseYTab(pCol) );
    testcase( pCol->op==TK_COLUMN && pCol->y.pTab==0 );
    if( ExprIsVtab(pCol) ){
      sqlite3_vtab *pVtab;
      sqlite3_module *pMod;
      void (*xNotUsed)(sqlite3_context*,int,sqlite3_value**);
      void *pNotUsed;
      pVtab = sqlite3GetVTable(db, pCol->y.pTab)->pVtab;
      assert( pVtab!=0 );
      assert( pVtab->pModule!=0 );
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
       pMod = (sqlite3_module *)pVtab->pModule;
      if( pMod->xFindFunction!=0 ){
        i = pMod->xFindFunction(pVtab,2, pExpr->u.zToken, &xNotUsed, &pNotUsed);
        if( i>=SQLITE_INDEX_CONSTRAINT_FUNCTION ){
          *peOp2 = i;
          *ppRight = pList->a[1].pExpr;
          *ppLeft = pCol;
          return 1;
        }
      }
    }
  }else if( pExpr->op==TK_NE || pExpr->op==TK_ISNOT || pExpr->op==TK_NOTNULL ){
    int res = 0;
    Expr *pLeft = pExpr->pLeft;
    Expr *pRight = pExpr->pRight;
    assert( pLeft->op!=TK_COLUMN || ExprUseYTab(pLeft) );
    testcase( pLeft->op==TK_COLUMN && pLeft->y.pTab==0 );
    if( ExprIsVtab(pLeft) ){
      res++;
    }
    assert( pRight==0 || pRight->op!=TK_COLUMN || ExprUseYTab(pRight) );
    testcase( pRight && pRight->op==TK_COLUMN && pRight->y.pTab==0 );
    if( pRight && ExprIsVtab(pRight) ){
      res++;
      SWAP(Expr*, pLeft, pRight);
    }
    *ppLeft = pLeft;
    *ppRight = pRight;
148933
148934
148935
148936
148937
148938
148939

148940
148941
148942
148943
148944
148945
148946
        WhereClause *pAndWC;
        WhereTerm *pAndTerm;
        int j;
        Bitmask b = 0;
        pOrTerm->u.pAndInfo = pAndInfo;
        pOrTerm->wtFlags |= TERM_ANDINFO;
        pOrTerm->eOperator = WO_AND;

        pAndWC = &pAndInfo->wc;
        memset(pAndWC->aStatic, 0, sizeof(pAndWC->aStatic));
        sqlite3WhereClauseInit(pAndWC, pWC->pWInfo);
        sqlite3WhereSplit(pAndWC, pOrTerm->pExpr, TK_AND);
        sqlite3WhereExprAnalyze(pSrc, pAndWC);
        pAndWC->pOuter = pWC;
        if( !db->mallocFailed ){







>







149940
149941
149942
149943
149944
149945
149946
149947
149948
149949
149950
149951
149952
149953
149954
        WhereClause *pAndWC;
        WhereTerm *pAndTerm;
        int j;
        Bitmask b = 0;
        pOrTerm->u.pAndInfo = pAndInfo;
        pOrTerm->wtFlags |= TERM_ANDINFO;
        pOrTerm->eOperator = WO_AND;
        pOrTerm->leftCursor = -1;
        pAndWC = &pAndInfo->wc;
        memset(pAndWC->aStatic, 0, sizeof(pAndWC->aStatic));
        sqlite3WhereClauseInit(pAndWC, pWC->pWInfo);
        sqlite3WhereSplit(pAndWC, pOrTerm->pExpr, TK_AND);
        sqlite3WhereExprAnalyze(pSrc, pAndWC);
        pAndWC->pOuter = pWC;
        if( !db->mallocFailed ){
148975
148976
148977
148978
148979
148980
148981
148982
148983


148984
148985
148986
148987
148988
148989
148990
148991
148992
148993
  }

  /*
  ** Record the set of tables that satisfy case 3.  The set might be
  ** empty.
  */
  pOrInfo->indexable = indexable;
  if( indexable ){
    pTerm->eOperator = WO_OR;


    pWC->hasOr = 1;
  }else{
    pTerm->eOperator = WO_OR;
  }

  /* For a two-way OR, attempt to implementation case 2.
  */
  if( indexable && pOrWc->nTerm==2 ){
    int iOne = 0;
    WhereTerm *pOne;







<
|
>
>

<
<







149983
149984
149985
149986
149987
149988
149989

149990
149991
149992
149993


149994
149995
149996
149997
149998
149999
150000
  }

  /*
  ** Record the set of tables that satisfy case 3.  The set might be
  ** empty.
  */
  pOrInfo->indexable = indexable;

  pTerm->eOperator = WO_OR;
  pTerm->leftCursor = -1;
  if( indexable ){
    pWC->hasOr = 1;


  }

  /* For a two-way OR, attempt to implementation case 2.
  */
  if( indexable && pOrWc->nTerm==2 ){
    int iOne = 0;
    WhereTerm *pOne;
149052
149053
149054
149055
149056
149057
149058

149059
149060
149061
149062
149063
149064
149065
149066
149067
149068
149069
149070
149071
149072
149073
149074
149075
149076
149077
149078

149079
149080
149081
149082
149083
149084
149085
          ** or follwed by an inverted copy (t2.b==t1.a).  Skip this term
          ** and use its inversion. */
          testcase( pOrTerm->wtFlags & TERM_COPIED );
          testcase( pOrTerm->wtFlags & TERM_VIRTUAL );
          assert( pOrTerm->wtFlags & (TERM_COPIED|TERM_VIRTUAL) );
          continue;
        }

        iColumn = pOrTerm->u.x.leftColumn;
        iCursor = pOrTerm->leftCursor;
        pLeft = pOrTerm->pExpr->pLeft;
        break;
      }
      if( i<0 ){
        /* No candidate table+column was found.  This can only occur
        ** on the second iteration */
        assert( j==1 );
        assert( IsPowerOfTwo(chngToIN) );
        assert( chngToIN==sqlite3WhereGetMask(&pWInfo->sMaskSet, iCursor) );
        break;
      }
      testcase( j==1 );

      /* We have found a candidate table and column.  Check to see if that
      ** table and column is common to every term in the OR clause */
      okToChngToIN = 1;
      for(; i>=0 && okToChngToIN; i--, pOrTerm++){
        assert( pOrTerm->eOperator & WO_EQ );

        if( pOrTerm->leftCursor!=iCursor ){
          pOrTerm->wtFlags &= ~TERM_OR_OK;
        }else if( pOrTerm->u.x.leftColumn!=iColumn || (iColumn==XN_EXPR
               && sqlite3ExprCompare(pParse, pOrTerm->pExpr->pLeft, pLeft, -1)
        )){
          okToChngToIN = 0;
        }else{







>




















>







150059
150060
150061
150062
150063
150064
150065
150066
150067
150068
150069
150070
150071
150072
150073
150074
150075
150076
150077
150078
150079
150080
150081
150082
150083
150084
150085
150086
150087
150088
150089
150090
150091
150092
150093
150094
          ** or follwed by an inverted copy (t2.b==t1.a).  Skip this term
          ** and use its inversion. */
          testcase( pOrTerm->wtFlags & TERM_COPIED );
          testcase( pOrTerm->wtFlags & TERM_VIRTUAL );
          assert( pOrTerm->wtFlags & (TERM_COPIED|TERM_VIRTUAL) );
          continue;
        }
        assert( (pOrTerm->eOperator & (WO_OR|WO_AND))==0 );
        iColumn = pOrTerm->u.x.leftColumn;
        iCursor = pOrTerm->leftCursor;
        pLeft = pOrTerm->pExpr->pLeft;
        break;
      }
      if( i<0 ){
        /* No candidate table+column was found.  This can only occur
        ** on the second iteration */
        assert( j==1 );
        assert( IsPowerOfTwo(chngToIN) );
        assert( chngToIN==sqlite3WhereGetMask(&pWInfo->sMaskSet, iCursor) );
        break;
      }
      testcase( j==1 );

      /* We have found a candidate table and column.  Check to see if that
      ** table and column is common to every term in the OR clause */
      okToChngToIN = 1;
      for(; i>=0 && okToChngToIN; i--, pOrTerm++){
        assert( pOrTerm->eOperator & WO_EQ );
        assert( (pOrTerm->eOperator & (WO_OR|WO_AND))==0 );
        if( pOrTerm->leftCursor!=iCursor ){
          pOrTerm->wtFlags &= ~TERM_OR_OK;
        }else if( pOrTerm->u.x.leftColumn!=iColumn || (iColumn==XN_EXPR
               && sqlite3ExprCompare(pParse, pOrTerm->pExpr->pLeft, pLeft, -1)
        )){
          okToChngToIN = 0;
        }else{
149108
149109
149110
149111
149112
149113
149114

149115
149116
149117
149118
149119
149120
149121
149122
149123
149124
149125
149126
149127
149128
149129
149130
149131
149132
149133
149134
      ExprList *pList = 0;   /* The RHS of the IN operator */
      Expr *pLeft = 0;       /* The LHS of the IN operator */
      Expr *pNew;            /* The complete IN operator */

      for(i=pOrWc->nTerm-1, pOrTerm=pOrWc->a; i>=0; i--, pOrTerm++){
        if( (pOrTerm->wtFlags & TERM_OR_OK)==0 ) continue;
        assert( pOrTerm->eOperator & WO_EQ );

        assert( pOrTerm->leftCursor==iCursor );
        assert( pOrTerm->u.x.leftColumn==iColumn );
        pDup = sqlite3ExprDup(db, pOrTerm->pExpr->pRight, 0);
        pList = sqlite3ExprListAppend(pWInfo->pParse, pList, pDup);
        pLeft = pOrTerm->pExpr->pLeft;
      }
      assert( pLeft!=0 );
      pDup = sqlite3ExprDup(db, pLeft, 0);
      pNew = sqlite3PExpr(pParse, TK_IN, pDup, 0);
      if( pNew ){
        int idxNew;
        transferJoinMarkings(pNew, pExpr);
        assert( !ExprHasProperty(pNew, EP_xIsSelect) );
        pNew->x.pList = pList;
        idxNew = whereClauseInsert(pWC, pNew, TERM_VIRTUAL|TERM_DYNAMIC);
        testcase( idxNew==0 );
        exprAnalyze(pSrc, pWC, idxNew);
        /* pTerm = &pWC->a[idxTerm]; // would be needed if pTerm where reused */
        markTermAsChild(pWC, idxNew, idxTerm);
      }else{







>












|







150117
150118
150119
150120
150121
150122
150123
150124
150125
150126
150127
150128
150129
150130
150131
150132
150133
150134
150135
150136
150137
150138
150139
150140
150141
150142
150143
150144
      ExprList *pList = 0;   /* The RHS of the IN operator */
      Expr *pLeft = 0;       /* The LHS of the IN operator */
      Expr *pNew;            /* The complete IN operator */

      for(i=pOrWc->nTerm-1, pOrTerm=pOrWc->a; i>=0; i--, pOrTerm++){
        if( (pOrTerm->wtFlags & TERM_OR_OK)==0 ) continue;
        assert( pOrTerm->eOperator & WO_EQ );
        assert( (pOrTerm->eOperator & (WO_OR|WO_AND))==0 );
        assert( pOrTerm->leftCursor==iCursor );
        assert( pOrTerm->u.x.leftColumn==iColumn );
        pDup = sqlite3ExprDup(db, pOrTerm->pExpr->pRight, 0);
        pList = sqlite3ExprListAppend(pWInfo->pParse, pList, pDup);
        pLeft = pOrTerm->pExpr->pLeft;
      }
      assert( pLeft!=0 );
      pDup = sqlite3ExprDup(db, pLeft, 0);
      pNew = sqlite3PExpr(pParse, TK_IN, pDup, 0);
      if( pNew ){
        int idxNew;
        transferJoinMarkings(pNew, pExpr);
        assert( ExprUseXList(pNew) );
        pNew->x.pList = pList;
        idxNew = whereClauseInsert(pWC, pNew, TERM_VIRTUAL|TERM_DYNAMIC);
        testcase( idxNew==0 );
        exprAnalyze(pSrc, pWC, idxNew);
        /* pTerm = &pWC->a[idxTerm]; // would be needed if pTerm where reused */
        markTermAsChild(pWC, idxNew, idxTerm);
      }else{
149248
149249
149250
149251
149252
149253
149254

149255
149256
149257
149258
149259
149260
149261
  /* If this expression is a vector to the left or right of a
  ** inequality constraint (>, <, >= or <=), perform the processing
  ** on the first element of the vector.  */
  assert( TK_GT+1==TK_LE && TK_GT+2==TK_LT && TK_GT+3==TK_GE );
  assert( TK_IS<TK_GE && TK_ISNULL<TK_GE && TK_IN<TK_GE );
  assert( op<=TK_GE );
  if( pExpr->op==TK_VECTOR && (op>=TK_GT && ALWAYS(op<=TK_GE)) ){

    pExpr = pExpr->x.pList->a[0].pExpr;

  }

  if( pExpr->op==TK_COLUMN ){
    aiCurCol[0] = pExpr->iTable;
    aiCurCol[1] = pExpr->iColumn;







>







150258
150259
150260
150261
150262
150263
150264
150265
150266
150267
150268
150269
150270
150271
150272
  /* If this expression is a vector to the left or right of a
  ** inequality constraint (>, <, >= or <=), perform the processing
  ** on the first element of the vector.  */
  assert( TK_GT+1==TK_LE && TK_GT+2==TK_LT && TK_GT+3==TK_GE );
  assert( TK_IS<TK_GE && TK_ISNULL<TK_GE && TK_IN<TK_GE );
  assert( op<=TK_GE );
  if( pExpr->op==TK_VECTOR && (op>=TK_GT && ALWAYS(op<=TK_GE)) ){
    assert( ExprUseXList(pExpr) );
    pExpr = pExpr->x.pList->a[0].pExpr;

  }

  if( pExpr->op==TK_COLUMN ){
    aiCurCol[0] = pExpr->iTable;
    aiCurCol[1] = pExpr->iColumn;
149305
149306
149307
149308
149309
149310
149311

149312
149313
149314

149315

149316
149317
149318
149319
149320
149321
149322
149323
149324
149325
149326
149327
149328
149329







149330

149331


149332





149333
149334
149335
149336
149337
149338
149339
149340
  sqlite3 *db = pParse->db;        /* Database connection */
  unsigned char eOp2 = 0;          /* op2 value for LIKE/REGEXP/GLOB */
  int nLeft;                       /* Number of elements on left side vector */

  if( db->mallocFailed ){
    return;
  }

  pTerm = &pWC->a[idxTerm];
  pMaskSet = &pWInfo->sMaskSet;
  pExpr = pTerm->pExpr;

  assert( pExpr->op!=TK_AS && pExpr->op!=TK_COLLATE );

  prereqLeft = sqlite3WhereExprUsage(pMaskSet, pExpr->pLeft);
  op = pExpr->op;
  if( op==TK_IN ){
    assert( pExpr->pRight==0 );
    if( sqlite3ExprCheckIN(pParse, pExpr) ) return;
    if( ExprHasProperty(pExpr, EP_xIsSelect) ){
      pTerm->prereqRight = exprSelectUsage(pMaskSet, pExpr->x.pSelect);
    }else{
      pTerm->prereqRight = sqlite3WhereExprListUsage(pMaskSet, pExpr->x.pList);
    }
  }else if( op==TK_ISNULL ){
    pTerm->prereqRight = 0;
  }else{
    pTerm->prereqRight = sqlite3WhereExprUsage(pMaskSet, pExpr->pRight);







  }

  pMaskSet->bVarSelect = 0;


  prereqAll = sqlite3WhereExprUsageNN(pMaskSet, pExpr);





  if( pMaskSet->bVarSelect ) pTerm->wtFlags |= TERM_VARSELECT;
  if( ExprHasProperty(pExpr, EP_FromJoin) ){
    Bitmask x = sqlite3WhereGetMask(pMaskSet, pExpr->iRightJoinTable);
    prereqAll |= x;
    extraRight = x-1;  /* ON clause terms may not be used with an index
                       ** on left table of a LEFT JOIN.  Ticket #3015 */
    if( (prereqAll>>1)>=x ){
      sqlite3ErrorMsg(pParse, "ON clause references tables to its right");







>



>

>





|




<
|


>
>
>
>
>
>
>
|
>
|
>
>
|
>
>
>
>
>
|







150316
150317
150318
150319
150320
150321
150322
150323
150324
150325
150326
150327
150328
150329
150330
150331
150332
150333
150334
150335
150336
150337
150338
150339

150340
150341
150342
150343
150344
150345
150346
150347
150348
150349
150350
150351
150352
150353
150354
150355
150356
150357
150358
150359
150360
150361
150362
150363
150364
150365
150366
150367
150368
  sqlite3 *db = pParse->db;        /* Database connection */
  unsigned char eOp2 = 0;          /* op2 value for LIKE/REGEXP/GLOB */
  int nLeft;                       /* Number of elements on left side vector */

  if( db->mallocFailed ){
    return;
  }
  assert( pWC->nTerm > idxTerm );
  pTerm = &pWC->a[idxTerm];
  pMaskSet = &pWInfo->sMaskSet;
  pExpr = pTerm->pExpr;
  assert( pExpr!=0 ); /* Because malloc() has not failed */
  assert( pExpr->op!=TK_AS && pExpr->op!=TK_COLLATE );
  pMaskSet->bVarSelect = 0;
  prereqLeft = sqlite3WhereExprUsage(pMaskSet, pExpr->pLeft);
  op = pExpr->op;
  if( op==TK_IN ){
    assert( pExpr->pRight==0 );
    if( sqlite3ExprCheckIN(pParse, pExpr) ) return;
    if( ExprUseXSelect(pExpr) ){
      pTerm->prereqRight = exprSelectUsage(pMaskSet, pExpr->x.pSelect);
    }else{
      pTerm->prereqRight = sqlite3WhereExprListUsage(pMaskSet, pExpr->x.pList);
    }

    prereqAll = prereqLeft | pTerm->prereqRight;
  }else{
    pTerm->prereqRight = sqlite3WhereExprUsage(pMaskSet, pExpr->pRight);
    if( pExpr->pLeft==0
     || ExprHasProperty(pExpr, EP_xIsSelect|EP_IfNullRow)
     || pExpr->x.pList!=0
    ){
      prereqAll = sqlite3WhereExprUsageNN(pMaskSet, pExpr);
    }else{
      prereqAll = prereqLeft | pTerm->prereqRight;
    }
  }
  if( pMaskSet->bVarSelect ) pTerm->wtFlags |= TERM_VARSELECT;

#ifdef SQLITE_DEBUG
  if( prereqAll!=sqlite3WhereExprUsageNN(pMaskSet, pExpr) ){
    printf("\n*** Incorrect prereqAll computed for:\n");
    sqlite3TreeViewExpr(0,pExpr,0);
    abort();
  }
#endif

  if( ExprHasProperty(pExpr, EP_FromJoin) ){
    Bitmask x = sqlite3WhereGetMask(pMaskSet, pExpr->iRightJoinTable);
    prereqAll |= x;
    extraRight = x-1;  /* ON clause terms may not be used with an index
                       ** on left table of a LEFT JOIN.  Ticket #3015 */
    if( (prereqAll>>1)>=x ){
      sqlite3ErrorMsg(pParse, "ON clause references tables to its right");
149350
149351
149352
149353
149354
149355
149356

149357
149358
149359
149360
149361

149362
149363
149364
149365
149366
149367
149368
    Expr *pLeft = sqlite3ExprSkipCollate(pExpr->pLeft);
    Expr *pRight = sqlite3ExprSkipCollate(pExpr->pRight);
    u16 opMask = (pTerm->prereqRight & prereqLeft)==0 ? WO_ALL : WO_EQUIV;

    if( pTerm->u.x.iField>0 ){
      assert( op==TK_IN );
      assert( pLeft->op==TK_VECTOR );

      pLeft = pLeft->x.pList->a[pTerm->u.x.iField-1].pExpr;
    }

    if( exprMightBeIndexed(pSrc, prereqLeft, aiCurCol, pLeft, op) ){
      pTerm->leftCursor = aiCurCol[0];

      pTerm->u.x.leftColumn = aiCurCol[1];
      pTerm->eOperator = operatorMask(op) & opMask;
    }
    if( op==TK_IS ) pTerm->wtFlags |= TERM_IS;
    if( pRight
     && exprMightBeIndexed(pSrc, pTerm->prereqRight, aiCurCol, pRight, op)
     && !ExprHasProperty(pRight, EP_FixedCol)







>





>







150378
150379
150380
150381
150382
150383
150384
150385
150386
150387
150388
150389
150390
150391
150392
150393
150394
150395
150396
150397
150398
    Expr *pLeft = sqlite3ExprSkipCollate(pExpr->pLeft);
    Expr *pRight = sqlite3ExprSkipCollate(pExpr->pRight);
    u16 opMask = (pTerm->prereqRight & prereqLeft)==0 ? WO_ALL : WO_EQUIV;

    if( pTerm->u.x.iField>0 ){
      assert( op==TK_IN );
      assert( pLeft->op==TK_VECTOR );
      assert( ExprUseXList(pLeft) );
      pLeft = pLeft->x.pList->a[pTerm->u.x.iField-1].pExpr;
    }

    if( exprMightBeIndexed(pSrc, prereqLeft, aiCurCol, pLeft, op) ){
      pTerm->leftCursor = aiCurCol[0];
      assert( (pTerm->eOperator & (WO_OR|WO_AND))==0 );
      pTerm->u.x.leftColumn = aiCurCol[1];
      pTerm->eOperator = operatorMask(op) & opMask;
    }
    if( op==TK_IS ) pTerm->wtFlags |= TERM_IS;
    if( pRight
     && exprMightBeIndexed(pSrc, pTerm->prereqRight, aiCurCol, pRight, op)
     && !ExprHasProperty(pRight, EP_FixedCol)
149392
149393
149394
149395
149396
149397
149398

149399
149400
149401
149402
149403
149404
149405
149406
149407
149408

149409
149410
149411
149412
149413
149414
149415
        }
      }else{
        pDup = pExpr;
        pNew = pTerm;
      }
      pNew->wtFlags |= exprCommute(pParse, pDup);
      pNew->leftCursor = aiCurCol[0];

      pNew->u.x.leftColumn = aiCurCol[1];
      testcase( (prereqLeft | extraRight) != prereqLeft );
      pNew->prereqRight = prereqLeft | extraRight;
      pNew->prereqAll = prereqAll;
      pNew->eOperator = (operatorMask(pDup->op) + eExtraOp) & opMask;
    }else
    if( op==TK_ISNULL
     && !ExprHasProperty(pExpr,EP_FromJoin)
     && 0==sqlite3ExprCanBeNull(pLeft)
    ){

      pExpr->op = TK_TRUEFALSE;
      pExpr->u.zToken = "false";
      ExprSetProperty(pExpr, EP_IsFalse);
      pTerm->prereqAll = 0;
      pTerm->eOperator = 0;
    }
  }







>










>







150422
150423
150424
150425
150426
150427
150428
150429
150430
150431
150432
150433
150434
150435
150436
150437
150438
150439
150440
150441
150442
150443
150444
150445
150446
150447
        }
      }else{
        pDup = pExpr;
        pNew = pTerm;
      }
      pNew->wtFlags |= exprCommute(pParse, pDup);
      pNew->leftCursor = aiCurCol[0];
      assert( (pTerm->eOperator & (WO_OR|WO_AND))==0 );
      pNew->u.x.leftColumn = aiCurCol[1];
      testcase( (prereqLeft | extraRight) != prereqLeft );
      pNew->prereqRight = prereqLeft | extraRight;
      pNew->prereqAll = prereqAll;
      pNew->eOperator = (operatorMask(pDup->op) + eExtraOp) & opMask;
    }else
    if( op==TK_ISNULL
     && !ExprHasProperty(pExpr,EP_FromJoin)
     && 0==sqlite3ExprCanBeNull(pLeft)
    ){
      assert( !ExprHasProperty(pExpr, EP_IntValue) );
      pExpr->op = TK_TRUEFALSE;
      pExpr->u.zToken = "false";
      ExprSetProperty(pExpr, EP_IsFalse);
      pTerm->prereqAll = 0;
      pTerm->eOperator = 0;
    }
  }
149427
149428
149429
149430
149431
149432
149433
149434
149435
149436


149437
149438
149439
149440
149441
149442
149443
  ** The two new terms are added onto the end of the WhereClause object.
  ** The new terms are "dynamic" and are children of the original BETWEEN
  ** term.  That means that if the BETWEEN term is coded, the children are
  ** skipped.  Or, if the children are satisfied by an index, the original
  ** BETWEEN term is skipped.
  */
  else if( pExpr->op==TK_BETWEEN && pWC->op==TK_AND ){
    ExprList *pList = pExpr->x.pList;
    int i;
    static const u8 ops[] = {TK_GE, TK_LE};


    assert( pList!=0 );
    assert( pList->nExpr==2 );
    for(i=0; i<2; i++){
      Expr *pNewExpr;
      int idxNew;
      pNewExpr = sqlite3PExpr(pParse, ops[i],
                             sqlite3ExprDup(db, pExpr->pLeft, 0),







|


>
>







150459
150460
150461
150462
150463
150464
150465
150466
150467
150468
150469
150470
150471
150472
150473
150474
150475
150476
150477
  ** The two new terms are added onto the end of the WhereClause object.
  ** The new terms are "dynamic" and are children of the original BETWEEN
  ** term.  That means that if the BETWEEN term is coded, the children are
  ** skipped.  Or, if the children are satisfied by an index, the original
  ** BETWEEN term is skipped.
  */
  else if( pExpr->op==TK_BETWEEN && pWC->op==TK_AND ){
    ExprList *pList;
    int i;
    static const u8 ops[] = {TK_GE, TK_LE};
    assert( ExprUseXList(pExpr) );
    pList = pExpr->x.pList;
    assert( pList!=0 );
    assert( pList->nExpr==2 );
    for(i=0; i<2; i++){
      Expr *pNewExpr;
      int idxNew;
      pNewExpr = sqlite3PExpr(pParse, ops[i],
                             sqlite3ExprDup(db, pExpr->pLeft, 0),
149522
149523
149524
149525
149526
149527
149528

149529
149530



149531
149532
149533
149534
149535
149536
149537
    Expr *pNewExpr1;
    Expr *pNewExpr2;
    int idxNew1;
    int idxNew2;
    const char *zCollSeqName;     /* Name of collating sequence */
    const u16 wtFlags = TERM_LIKEOPT | TERM_VIRTUAL | TERM_DYNAMIC;


    pLeft = pExpr->x.pList->a[1].pExpr;
    pStr2 = sqlite3ExprDup(db, pStr1, 0);




    /* Convert the lower bound to upper-case and the upper bound to
    ** lower-case (upper-case is less than lower-case in ASCII) so that
    ** the range constraints also work for BLOBs
    */
    if( noCase && !pParse->db->mallocFailed ){
      int i;







>


>
>
>







150556
150557
150558
150559
150560
150561
150562
150563
150564
150565
150566
150567
150568
150569
150570
150571
150572
150573
150574
150575
    Expr *pNewExpr1;
    Expr *pNewExpr2;
    int idxNew1;
    int idxNew2;
    const char *zCollSeqName;     /* Name of collating sequence */
    const u16 wtFlags = TERM_LIKEOPT | TERM_VIRTUAL | TERM_DYNAMIC;

    assert( ExprUseXList(pExpr) );
    pLeft = pExpr->x.pList->a[1].pExpr;
    pStr2 = sqlite3ExprDup(db, pStr1, 0);
    assert( pStr1==0 || !ExprHasProperty(pStr1, EP_IntValue) );
    assert( pStr2==0 || !ExprHasProperty(pStr2, EP_IntValue) );


    /* Convert the lower bound to upper-case and the upper bound to
    ** lower-case (upper-case is less than lower-case in ASCII) so that
    ** the range constraints also work for BLOBs
    */
    if( noCase && !pParse->db->mallocFailed ){
      int i;
149623
149624
149625
149626
149627
149628
149629

149630
149631
149632
149633
149634
149635
149636
  **
  ** This only works if the RHS is a simple SELECT (not a compound) that does
  ** not use window functions.
  */
  else if( pExpr->op==TK_IN
   && pTerm->u.x.iField==0
   && pExpr->pLeft->op==TK_VECTOR

   && pExpr->x.pSelect->pPrior==0
#ifndef SQLITE_OMIT_WINDOWFUNC
   && pExpr->x.pSelect->pWin==0
#endif
   && pWC->op==TK_AND
  ){
    int i;







>







150661
150662
150663
150664
150665
150666
150667
150668
150669
150670
150671
150672
150673
150674
150675
  **
  ** This only works if the RHS is a simple SELECT (not a compound) that does
  ** not use window functions.
  */
  else if( pExpr->op==TK_IN
   && pTerm->u.x.iField==0
   && pExpr->pLeft->op==TK_VECTOR
   && ALWAYS( ExprUseXSelect(pExpr) )
   && pExpr->x.pSelect->pPrior==0
#ifndef SQLITE_OMIT_WINDOWFUNC
   && pExpr->x.pSelect->pWin==0
#endif
   && pWC->op==TK_AND
  ){
    int i;
149739
149740
149741
149742
149743
149744
149745

149746
149747
149748
149749
149750
149751
149752
149753
149754
149755
149756
149757
149758

149759










149760
149761
149762

149763

149764

149765
149766




149767
149768
149769
149770
149771
149772
149773
149774
149775
149776
149777
149778


























149779

149780


149781
149782
149783
149784
149785
149786
149787
149788
149789
149790
149791
149792
149793
149794
149795
149796
149797
149798
149799
149800

149801
149802
149803
149804
149805
149806









149807
149808
149809
149810
149811
149812
149813
  WhereClause *pWC,        /* The WhereClause to be initialized */
  WhereInfo *pWInfo        /* The WHERE processing context */
){
  pWC->pWInfo = pWInfo;
  pWC->hasOr = 0;
  pWC->pOuter = 0;
  pWC->nTerm = 0;

  pWC->nSlot = ArraySize(pWC->aStatic);
  pWC->a = pWC->aStatic;
}

/*
** Deallocate a WhereClause structure.  The WhereClause structure
** itself is not freed.  This routine is the inverse of
** sqlite3WhereClauseInit().
*/
SQLITE_PRIVATE void sqlite3WhereClauseClear(WhereClause *pWC){
  int i;
  WhereTerm *a;
  sqlite3 *db = pWC->pWInfo->pParse->db;

  for(i=pWC->nTerm-1, a=pWC->a; i>=0; i--, a++){










    if( a->wtFlags & TERM_DYNAMIC ){
      sqlite3ExprDelete(db, a->pExpr);
    }

    if( a->wtFlags & TERM_ORINFO ){

      whereOrInfoDelete(db, a->u.pOrInfo);

    }else if( a->wtFlags & TERM_ANDINFO ){
      whereAndInfoDelete(db, a->u.pAndInfo);




    }
  }
  if( pWC->a!=pWC->aStatic ){
    sqlite3DbFree(db, pWC->a);
  }
}


/*
** These routines walk (recursively) an expression tree and generate
** a bitmask indicating which tables are used in that expression
** tree.


























*/

SQLITE_PRIVATE Bitmask sqlite3WhereExprUsageNN(WhereMaskSet *pMaskSet, Expr *p){


  Bitmask mask;
  if( p->op==TK_COLUMN && !ExprHasProperty(p, EP_FixedCol) ){
    return sqlite3WhereGetMask(pMaskSet, p->iTable);
  }else if( ExprHasProperty(p, EP_TokenOnly|EP_Leaf) ){
    assert( p->op!=TK_IF_NULL_ROW );
    return 0;
  }
  mask = (p->op==TK_IF_NULL_ROW) ? sqlite3WhereGetMask(pMaskSet, p->iTable) : 0;
  if( p->pLeft ) mask |= sqlite3WhereExprUsageNN(pMaskSet, p->pLeft);
  if( p->pRight ){
    mask |= sqlite3WhereExprUsageNN(pMaskSet, p->pRight);
    assert( p->x.pList==0 );
  }else if( ExprHasProperty(p, EP_xIsSelect) ){
    if( ExprHasProperty(p, EP_VarSelect) ) pMaskSet->bVarSelect = 1;
    mask |= exprSelectUsage(pMaskSet, p->x.pSelect);
  }else if( p->x.pList ){
    mask |= sqlite3WhereExprListUsage(pMaskSet, p->x.pList);
  }
#ifndef SQLITE_OMIT_WINDOWFUNC
  if( (p->op==TK_FUNCTION || p->op==TK_AGG_FUNCTION) && p->y.pWin ){

    mask |= sqlite3WhereExprListUsage(pMaskSet, p->y.pWin->pPartition);
    mask |= sqlite3WhereExprListUsage(pMaskSet, p->y.pWin->pOrderBy);
    mask |= sqlite3WhereExprUsage(pMaskSet, p->y.pWin->pFilter);
  }
#endif
  return mask;









}
SQLITE_PRIVATE Bitmask sqlite3WhereExprUsage(WhereMaskSet *pMaskSet, Expr *p){
  return p ? sqlite3WhereExprUsageNN(pMaskSet,p) : 0;
}
SQLITE_PRIVATE Bitmask sqlite3WhereExprListUsage(WhereMaskSet *pMaskSet, ExprList *pList){
  int i;
  Bitmask mask = 0;







>










<
<

>
|
>
>
>
>
>
>
>
>
>
>
|
|
|
>
|
>
|
>
|
|
>
>
>
>












>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>

>
|
>
>

<
<
<
<
<
<





|






|
>






>
>
>
>
>
>
>
>
>







150778
150779
150780
150781
150782
150783
150784
150785
150786
150787
150788
150789
150790
150791
150792
150793
150794
150795


150796
150797
150798
150799
150800
150801
150802
150803
150804
150805
150806
150807
150808
150809
150810
150811
150812
150813
150814
150815
150816
150817
150818
150819
150820
150821
150822
150823
150824
150825
150826
150827
150828
150829
150830
150831
150832
150833
150834
150835
150836
150837
150838
150839
150840
150841
150842
150843
150844
150845
150846
150847
150848
150849
150850
150851
150852
150853
150854
150855
150856
150857
150858
150859
150860
150861
150862
150863
150864
150865
150866






150867
150868
150869
150870
150871
150872
150873
150874
150875
150876
150877
150878
150879
150880
150881
150882
150883
150884
150885
150886
150887
150888
150889
150890
150891
150892
150893
150894
150895
150896
150897
150898
150899
150900
150901
150902
  WhereClause *pWC,        /* The WhereClause to be initialized */
  WhereInfo *pWInfo        /* The WHERE processing context */
){
  pWC->pWInfo = pWInfo;
  pWC->hasOr = 0;
  pWC->pOuter = 0;
  pWC->nTerm = 0;
  pWC->nBase = 0;
  pWC->nSlot = ArraySize(pWC->aStatic);
  pWC->a = pWC->aStatic;
}

/*
** Deallocate a WhereClause structure.  The WhereClause structure
** itself is not freed.  This routine is the inverse of
** sqlite3WhereClauseInit().
*/
SQLITE_PRIVATE void sqlite3WhereClauseClear(WhereClause *pWC){


  sqlite3 *db = pWC->pWInfo->pParse->db;
  assert( pWC->nTerm>=pWC->nBase );
  if( pWC->nTerm>0 ){
    WhereTerm *a = pWC->a;
    WhereTerm *aLast = &pWC->a[pWC->nTerm-1];
#ifdef SQLITE_DEBUG
    int i;
    /* Verify that every term past pWC->nBase is virtual */
    for(i=pWC->nBase; i<pWC->nTerm; i++){
      assert( (pWC->a[i].wtFlags & TERM_VIRTUAL)!=0 );
    }
#endif
    while(1){
      if( a->wtFlags & TERM_DYNAMIC ){
        sqlite3ExprDelete(db, a->pExpr);
      }
      if( a->wtFlags & (TERM_ORINFO|TERM_ANDINFO) ){
        if( a->wtFlags & TERM_ORINFO ){
          assert( (a->wtFlags & TERM_ANDINFO)==0 );
          whereOrInfoDelete(db, a->u.pOrInfo);
        }else{
          assert( (a->wtFlags & TERM_ANDINFO)!=0 );
          whereAndInfoDelete(db, a->u.pAndInfo);
        }
      }
      if( a==aLast ) break;
      a++;
    }
  }
  if( pWC->a!=pWC->aStatic ){
    sqlite3DbFree(db, pWC->a);
  }
}


/*
** These routines walk (recursively) an expression tree and generate
** a bitmask indicating which tables are used in that expression
** tree.
**
** sqlite3WhereExprUsage(MaskSet, Expr) ->
**
**       Return a Bitmask of all tables referenced by Expr.  Expr can be
**       be NULL, in which case 0 is returned.
**
** sqlite3WhereExprUsageNN(MaskSet, Expr) ->
**
**       Same as sqlite3WhereExprUsage() except that Expr must not be
**       NULL.  The "NN" suffix on the name stands for "Not Null".
**
** sqlite3WhereExprListUsage(MaskSet, ExprList) ->
**
**       Return a Bitmask of all tables referenced by every expression
**       in the expression list ExprList.  ExprList can be NULL, in which
**       case 0 is returned.
**
** sqlite3WhereExprUsageFull(MaskSet, ExprList) ->
**
**       Internal use only.  Called only by sqlite3WhereExprUsageNN() for
**       complex expressions that require pushing register values onto
**       the stack.  Many calls to sqlite3WhereExprUsageNN() do not need
**       the more complex analysis done by this routine.  Hence, the
**       computations done by this routine are broken out into a separate
**       "no-inline" function to avoid the stack push overhead in the
**       common case where it is not needed.
*/
static SQLITE_NOINLINE Bitmask sqlite3WhereExprUsageFull(
  WhereMaskSet *pMaskSet,
  Expr *p
){
  Bitmask mask;






  mask = (p->op==TK_IF_NULL_ROW) ? sqlite3WhereGetMask(pMaskSet, p->iTable) : 0;
  if( p->pLeft ) mask |= sqlite3WhereExprUsageNN(pMaskSet, p->pLeft);
  if( p->pRight ){
    mask |= sqlite3WhereExprUsageNN(pMaskSet, p->pRight);
    assert( p->x.pList==0 );
  }else if( ExprUseXSelect(p) ){
    if( ExprHasProperty(p, EP_VarSelect) ) pMaskSet->bVarSelect = 1;
    mask |= exprSelectUsage(pMaskSet, p->x.pSelect);
  }else if( p->x.pList ){
    mask |= sqlite3WhereExprListUsage(pMaskSet, p->x.pList);
  }
#ifndef SQLITE_OMIT_WINDOWFUNC
  if( (p->op==TK_FUNCTION || p->op==TK_AGG_FUNCTION) && ExprUseYWin(p) ){
    assert( p->y.pWin!=0 );
    mask |= sqlite3WhereExprListUsage(pMaskSet, p->y.pWin->pPartition);
    mask |= sqlite3WhereExprListUsage(pMaskSet, p->y.pWin->pOrderBy);
    mask |= sqlite3WhereExprUsage(pMaskSet, p->y.pWin->pFilter);
  }
#endif
  return mask;
}
SQLITE_PRIVATE Bitmask sqlite3WhereExprUsageNN(WhereMaskSet *pMaskSet, Expr *p){
  if( p->op==TK_COLUMN && !ExprHasProperty(p, EP_FixedCol) ){
    return sqlite3WhereGetMask(pMaskSet, p->iTable);
  }else if( ExprHasProperty(p, EP_TokenOnly|EP_Leaf) ){
    assert( p->op!=TK_IF_NULL_ROW );
    return 0;
  }
  return sqlite3WhereExprUsageFull(pMaskSet, p);
}
SQLITE_PRIVATE Bitmask sqlite3WhereExprUsage(WhereMaskSet *pMaskSet, Expr *p){
  return p ? sqlite3WhereExprUsageNN(pMaskSet,p) : 0;
}
SQLITE_PRIVATE Bitmask sqlite3WhereExprListUsage(WhereMaskSet *pMaskSet, ExprList *pList){
  int i;
  Bitmask mask = 0;
149868
149869
149870
149871
149872
149873
149874

149875
149876
149877
149878
149879
149880
149881
                      pTab->zName, j);
      return;
    }
    pColRef = sqlite3ExprAlloc(pParse->db, TK_COLUMN, 0, 0);
    if( pColRef==0 ) return;
    pColRef->iTable = pItem->iCursor;
    pColRef->iColumn = k++;

    pColRef->y.pTab = pTab;
    pRhs = sqlite3PExpr(pParse, TK_UPLUS,
        sqlite3ExprDup(pParse->db, pArgs->a[j].pExpr, 0), 0);
    pTerm = sqlite3PExpr(pParse, TK_EQ, pColRef, pRhs);
    if( pItem->fg.jointype & JT_LEFT ){
      sqlite3SetJoinExpr(pTerm, pItem->iCursor);
    }







>







150957
150958
150959
150960
150961
150962
150963
150964
150965
150966
150967
150968
150969
150970
150971
                      pTab->zName, j);
      return;
    }
    pColRef = sqlite3ExprAlloc(pParse->db, TK_COLUMN, 0, 0);
    if( pColRef==0 ) return;
    pColRef->iTable = pItem->iCursor;
    pColRef->iColumn = k++;
    assert( ExprUseYTab(pColRef) );
    pColRef->y.pTab = pTab;
    pRhs = sqlite3PExpr(pParse, TK_UPLUS,
        sqlite3ExprDup(pParse->db, pArgs->a[j].pExpr, 0), 0);
    pTerm = sqlite3PExpr(pParse, TK_EQ, pColRef, pRhs);
    if( pItem->fg.jointype & JT_LEFT ){
      sqlite3SetJoinExpr(pTerm, pItem->iCursor);
    }
150117
150118
150119
150120
150121
150122
150123





150124
150125
150126
150127
150128
150129
150130
150131
/*
** Return the bitmask for the given cursor number.  Return 0 if
** iCursor is not in the set.
*/
SQLITE_PRIVATE Bitmask sqlite3WhereGetMask(WhereMaskSet *pMaskSet, int iCursor){
  int i;
  assert( pMaskSet->n<=(int)sizeof(Bitmask)*8 );





  for(i=0; i<pMaskSet->n; i++){
    if( pMaskSet->ix[i]==iCursor ){
      return MASKBIT(i);
    }
  }
  return 0;
}








>
>
>
>
>
|







151207
151208
151209
151210
151211
151212
151213
151214
151215
151216
151217
151218
151219
151220
151221
151222
151223
151224
151225
151226
/*
** Return the bitmask for the given cursor number.  Return 0 if
** iCursor is not in the set.
*/
SQLITE_PRIVATE Bitmask sqlite3WhereGetMask(WhereMaskSet *pMaskSet, int iCursor){
  int i;
  assert( pMaskSet->n<=(int)sizeof(Bitmask)*8 );
  assert( pMaskSet->n>0 || pMaskSet->ix[0]<0 );
  assert( iCursor>=-1 );
  if( pMaskSet->ix[0]==iCursor ){
    return 1;
  }
  for(i=1; i<pMaskSet->n; i++){
    if( pMaskSet->ix[i]==iCursor ){
      return MASKBIT(i);
    }
  }
  return 0;
}

150169
150170
150171
150172
150173
150174
150175

150176
150177

150178
150179
150180
150181
150182
150183
150184

  assert( pScan->iEquiv<=pScan->nEquiv );
  pWC = pScan->pWC;
  while(1){
    iColumn = pScan->aiColumn[pScan->iEquiv-1];
    iCur = pScan->aiCur[pScan->iEquiv-1];
    assert( pWC!=0 );

    do{
      for(pTerm=pWC->a+k; k<pWC->nTerm; k++, pTerm++){

        if( pTerm->leftCursor==iCur
         && pTerm->u.x.leftColumn==iColumn
         && (iColumn!=XN_EXPR
             || sqlite3ExprCompareSkip(pTerm->pExpr->pLeft,
                                       pScan->pIdxExpr,iCur)==0)
         && (pScan->iEquiv<=1 || !ExprHasProperty(pTerm->pExpr, EP_FromJoin))
        ){







>


>







151264
151265
151266
151267
151268
151269
151270
151271
151272
151273
151274
151275
151276
151277
151278
151279
151280
151281

  assert( pScan->iEquiv<=pScan->nEquiv );
  pWC = pScan->pWC;
  while(1){
    iColumn = pScan->aiColumn[pScan->iEquiv-1];
    iCur = pScan->aiCur[pScan->iEquiv-1];
    assert( pWC!=0 );
    assert( iCur>=0 );
    do{
      for(pTerm=pWC->a+k; k<pWC->nTerm; k++, pTerm++){
        assert( (pTerm->eOperator & (WO_OR|WO_AND))==0 || pTerm->leftCursor<0 );
        if( pTerm->leftCursor==iCur
         && pTerm->u.x.leftColumn==iColumn
         && (iColumn!=XN_EXPR
             || sqlite3ExprCompareSkip(pTerm->pExpr->pLeft,
                                       pScan->pIdxExpr,iCur)==0)
         && (pScan->iEquiv<=1 || !ExprHasProperty(pTerm->pExpr, EP_FromJoin))
        ){
150212
150213
150214
150215
150216
150217
150218
150219

150220
150221
150222
150223
150224
150225
150226
              pColl = sqlite3ExprCompareCollSeq(pParse, pX);
              if( pColl==0 ) pColl = pParse->db->pDfltColl;
              if( sqlite3StrICmp(pColl->zName, pScan->zCollName) ){
                continue;
              }
            }
            if( (pTerm->eOperator & (WO_EQ|WO_IS))!=0
             && (pX = pTerm->pExpr->pRight)->op==TK_COLUMN

             && pX->iTable==pScan->aiCur[0]
             && pX->iColumn==pScan->aiColumn[0]
            ){
              testcase( pTerm->eOperator & WO_IS );
              continue;
            }
            pScan->pWC = pWC;







|
>







151309
151310
151311
151312
151313
151314
151315
151316
151317
151318
151319
151320
151321
151322
151323
151324
              pColl = sqlite3ExprCompareCollSeq(pParse, pX);
              if( pColl==0 ) pColl = pParse->db->pDfltColl;
              if( sqlite3StrICmp(pColl->zName, pScan->zCollName) ){
                continue;
              }
            }
            if( (pTerm->eOperator & (WO_EQ|WO_IS))!=0
             && (pX = pTerm->pExpr->pRight, ALWAYS(pX!=0))
             && pX->op==TK_COLUMN
             && pX->iTable==pScan->aiCur[0]
             && pX->iColumn==pScan->aiColumn[0]
            ){
              testcase( pTerm->eOperator & WO_IS );
              continue;
            }
            pScan->pWC = pWC;
150299
150300
150301
150302
150303
150304
150305





150306
150307
150308
150309
150310
150311
150312
150313
150314
150315
150316
150317
150318
150319
150320
150321
150322
  pScan->k = 0;
  pScan->aiCur[0] = iCur;
  pScan->nEquiv = 1;
  pScan->iEquiv = 1;
  if( pIdx ){
    int j = iColumn;
    iColumn = pIdx->aiColumn[j];





    if( iColumn==XN_EXPR ){
      pScan->pIdxExpr = pIdx->aColExpr->a[j].pExpr;
      pScan->zCollName = pIdx->azColl[j];
      pScan->aiColumn[0] = XN_EXPR;
      return whereScanInitIndexExpr(pScan);
    }else if( iColumn==pIdx->pTable->iPKey ){
      iColumn = XN_ROWID;
    }else if( iColumn>=0 ){
      pScan->idxaff = pIdx->pTable->aCol[iColumn].affinity;
      pScan->zCollName = pIdx->azColl[j];
    }
  }else if( iColumn==XN_EXPR ){
    return 0;
  }
  pScan->aiColumn[0] = iColumn;
  return whereScanNext(pScan);
}







>
>
>
>
>
|




<
<
<
<
<







151397
151398
151399
151400
151401
151402
151403
151404
151405
151406
151407
151408
151409
151410
151411
151412
151413





151414
151415
151416
151417
151418
151419
151420
  pScan->k = 0;
  pScan->aiCur[0] = iCur;
  pScan->nEquiv = 1;
  pScan->iEquiv = 1;
  if( pIdx ){
    int j = iColumn;
    iColumn = pIdx->aiColumn[j];
    if( iColumn==pIdx->pTable->iPKey ){
      iColumn = XN_ROWID;
    }else if( iColumn>=0 ){
      pScan->idxaff = pIdx->pTable->aCol[iColumn].affinity;
      pScan->zCollName = pIdx->azColl[j];
    }else if( iColumn==XN_EXPR ){
      pScan->pIdxExpr = pIdx->aColExpr->a[j].pExpr;
      pScan->zCollName = pIdx->azColl[j];
      pScan->aiColumn[0] = XN_EXPR;
      return whereScanInitIndexExpr(pScan);





    }
  }else if( iColumn==XN_EXPR ){
    return 0;
  }
  pScan->aiColumn[0] = iColumn;
  return whereScanNext(pScan);
}
150592
150593
150594
150595
150596
150597
150598
150599
150600
150601
150602
150603
150604
150605
150606
150607
150608
150609
150610
150611
150612
150613
150614
150615

150616
150617
150618
150619
150620
150621
150622
150623
150624
150625
150626
150627
150628
150629
150630
150631
150632
150633
150634
150635
150636
150637
150638
150639
150640
150641
150642
#ifndef SQLITE_OMIT_AUTOMATIC_INDEX
/*
** Return TRUE if the WHERE clause term pTerm is of a form where it
** could be used with an index to access pSrc, assuming an appropriate
** index existed.
*/
static int termCanDriveIndex(
  WhereTerm *pTerm,              /* WHERE clause term to check */
  SrcItem *pSrc,                 /* Table we are trying to access */
  Bitmask notReady               /* Tables in outer loops of the join */
){
  char aff;
  if( pTerm->leftCursor!=pSrc->iCursor ) return 0;
  if( (pTerm->eOperator & (WO_EQ|WO_IS))==0 ) return 0;
  if( (pSrc->fg.jointype & JT_LEFT)
   && !ExprHasProperty(pTerm->pExpr, EP_FromJoin)
   && (pTerm->eOperator & WO_IS)
  ){
    /* Cannot use an IS term from the WHERE clause as an index driver for
    ** the RHS of a LEFT JOIN. Such a term can only be used if it is from
    ** the ON clause.  */
    return 0;
  }
  if( (pTerm->prereqRight & notReady)!=0 ) return 0;

  if( pTerm->u.x.leftColumn<0 ) return 0;
  aff = pSrc->pTab->aCol[pTerm->u.x.leftColumn].affinity;
  if( !sqlite3IndexAffinityOk(pTerm->pExpr, aff) ) return 0;
  testcase( pTerm->pExpr->op==TK_IS );
  return 1;
}
#endif


#ifndef SQLITE_OMIT_AUTOMATIC_INDEX
/*
** Generate code to construct the Index object for an automatic index
** and to set up the WhereLevel object pLevel so that the code generator
** makes use of the automatic index.
*/
static void constructAutomaticIndex(
  Parse *pParse,              /* The parsing context */
  WhereClause *pWC,           /* The WHERE clause */
  SrcItem *pSrc,              /* The FROM clause term to get the next index */
  Bitmask notReady,           /* Mask of cursors that are not available */
  WhereLevel *pLevel          /* Write new index here */
){
  int nKeyCol;                /* Number of columns in the constructed index */
  WhereTerm *pTerm;           /* A single term of the WHERE clause */
  WhereTerm *pWCEnd;          /* End of pWC->a[] */
  Index *pIdx;                /* Object describing the transient index */
  Vdbe *v;                    /* Prepared statement under construction */







|
|
|














>















|

|
|
|







151690
151691
151692
151693
151694
151695
151696
151697
151698
151699
151700
151701
151702
151703
151704
151705
151706
151707
151708
151709
151710
151711
151712
151713
151714
151715
151716
151717
151718
151719
151720
151721
151722
151723
151724
151725
151726
151727
151728
151729
151730
151731
151732
151733
151734
151735
151736
151737
151738
151739
151740
151741
#ifndef SQLITE_OMIT_AUTOMATIC_INDEX
/*
** Return TRUE if the WHERE clause term pTerm is of a form where it
** could be used with an index to access pSrc, assuming an appropriate
** index existed.
*/
static int termCanDriveIndex(
  const WhereTerm *pTerm,        /* WHERE clause term to check */
  const SrcItem *pSrc,           /* Table we are trying to access */
  const Bitmask notReady         /* Tables in outer loops of the join */
){
  char aff;
  if( pTerm->leftCursor!=pSrc->iCursor ) return 0;
  if( (pTerm->eOperator & (WO_EQ|WO_IS))==0 ) return 0;
  if( (pSrc->fg.jointype & JT_LEFT)
   && !ExprHasProperty(pTerm->pExpr, EP_FromJoin)
   && (pTerm->eOperator & WO_IS)
  ){
    /* Cannot use an IS term from the WHERE clause as an index driver for
    ** the RHS of a LEFT JOIN. Such a term can only be used if it is from
    ** the ON clause.  */
    return 0;
  }
  if( (pTerm->prereqRight & notReady)!=0 ) return 0;
  assert( (pTerm->eOperator & (WO_OR|WO_AND))==0 );
  if( pTerm->u.x.leftColumn<0 ) return 0;
  aff = pSrc->pTab->aCol[pTerm->u.x.leftColumn].affinity;
  if( !sqlite3IndexAffinityOk(pTerm->pExpr, aff) ) return 0;
  testcase( pTerm->pExpr->op==TK_IS );
  return 1;
}
#endif


#ifndef SQLITE_OMIT_AUTOMATIC_INDEX
/*
** Generate code to construct the Index object for an automatic index
** and to set up the WhereLevel object pLevel so that the code generator
** makes use of the automatic index.
*/
static SQLITE_NOINLINE void constructAutomaticIndex(
  Parse *pParse,              /* The parsing context */
  const WhereClause *pWC,     /* The WHERE clause */
  const SrcItem *pSrc,        /* The FROM clause term to get the next index */
  const Bitmask notReady,     /* Mask of cursors that are not available */
  WhereLevel *pLevel          /* Write new index here */
){
  int nKeyCol;                /* Number of columns in the constructed index */
  WhereTerm *pTerm;           /* A single term of the WHERE clause */
  WhereTerm *pWCEnd;          /* End of pWC->a[] */
  Index *pIdx;                /* Object describing the transient index */
  Vdbe *v;                    /* Prepared statement under construction */
150670
150671
150672
150673
150674
150675
150676
150677
150678
150679
150680

150681
150682
150683

150684
150685
150686
150687



150688
150689
150690
150691
150692
150693
150694
150695
150696
  nKeyCol = 0;
  pTable = pSrc->pTab;
  pWCEnd = &pWC->a[pWC->nTerm];
  pLoop = pLevel->pWLoop;
  idxCols = 0;
  for(pTerm=pWC->a; pTerm<pWCEnd; pTerm++){
    Expr *pExpr = pTerm->pExpr;
    assert( !ExprHasProperty(pExpr, EP_FromJoin)    /* prereq always non-zero */
         || pExpr->iRightJoinTable!=pSrc->iCursor   /*   for the right-hand   */
         || pLoop->prereq!=0 );                     /*   table of a LEFT JOIN */
    if( pLoop->prereq==0

     && (pTerm->wtFlags & TERM_VIRTUAL)==0
     && !ExprHasProperty(pExpr, EP_FromJoin)
     && sqlite3ExprIsTableConstant(pExpr, pSrc->iCursor) ){

      pPartial = sqlite3ExprAnd(pParse, pPartial,
                                sqlite3ExprDup(pParse->db, pExpr, 0));
    }
    if( termCanDriveIndex(pTerm, pSrc, notReady) ){



      int iCol = pTerm->u.x.leftColumn;
      Bitmask cMask = iCol>=BMS ? MASKBIT(BMS-1) : MASKBIT(iCol);
      testcase( iCol==BMS );
      testcase( iCol==BMS-1 );
      if( !sentWarning ){
        sqlite3_log(SQLITE_WARNING_AUTOINDEX,
            "automatic index on %s(%s)", pTable->zName,
            pTable->aCol[iCol].zCnName);
        sentWarning = 1;







|
<
|
<
>
|
|
|
>




>
>
>
|
|







151769
151770
151771
151772
151773
151774
151775
151776

151777

151778
151779
151780
151781
151782
151783
151784
151785
151786
151787
151788
151789
151790
151791
151792
151793
151794
151795
151796
151797
151798
  nKeyCol = 0;
  pTable = pSrc->pTab;
  pWCEnd = &pWC->a[pWC->nTerm];
  pLoop = pLevel->pWLoop;
  idxCols = 0;
  for(pTerm=pWC->a; pTerm<pWCEnd; pTerm++){
    Expr *pExpr = pTerm->pExpr;
    /* Make the automatic index a partial index if there are terms in the

    ** WHERE clause (or the ON clause of a LEFT join) that constrain which

    ** rows of the target table (pSrc) that can be used. */
    if( (pTerm->wtFlags & TERM_VIRTUAL)==0
     && ((pSrc->fg.jointype&JT_LEFT)==0 || ExprHasProperty(pExpr,EP_FromJoin))
     && sqlite3ExprIsTableConstant(pExpr, pSrc->iCursor)
    ){
      pPartial = sqlite3ExprAnd(pParse, pPartial,
                                sqlite3ExprDup(pParse->db, pExpr, 0));
    }
    if( termCanDriveIndex(pTerm, pSrc, notReady) ){
      int iCol;
      Bitmask cMask;
      assert( (pTerm->eOperator & (WO_OR|WO_AND))==0 );
      iCol = pTerm->u.x.leftColumn;
      cMask = iCol>=BMS ? MASKBIT(BMS-1) : MASKBIT(iCol);
      testcase( iCol==BMS );
      testcase( iCol==BMS-1 );
      if( !sentWarning ){
        sqlite3_log(SQLITE_WARNING_AUTOINDEX,
            "automatic index on %s(%s)", pTable->zName,
            pTable->aCol[iCol].zCnName);
        sentWarning = 1;
150734
150735
150736
150737
150738
150739
150740



150741
150742
150743
150744
150745
150746
150747
150748
150749
  pLoop->u.btree.pIndex = pIdx;
  pIdx->zName = "auto-index";
  pIdx->pTable = pTable;
  n = 0;
  idxCols = 0;
  for(pTerm=pWC->a; pTerm<pWCEnd; pTerm++){
    if( termCanDriveIndex(pTerm, pSrc, notReady) ){



      int iCol = pTerm->u.x.leftColumn;
      Bitmask cMask = iCol>=BMS ? MASKBIT(BMS-1) : MASKBIT(iCol);
      testcase( iCol==BMS-1 );
      testcase( iCol==BMS );
      if( (idxCols & cMask)==0 ){
        Expr *pX = pTerm->pExpr;
        idxCols |= cMask;
        pIdx->aiColumn[n] = pTerm->u.x.leftColumn;
        pColl = sqlite3ExprCompareCollSeq(pParse, pX);







>
>
>
|
|







151836
151837
151838
151839
151840
151841
151842
151843
151844
151845
151846
151847
151848
151849
151850
151851
151852
151853
151854
  pLoop->u.btree.pIndex = pIdx;
  pIdx->zName = "auto-index";
  pIdx->pTable = pTable;
  n = 0;
  idxCols = 0;
  for(pTerm=pWC->a; pTerm<pWCEnd; pTerm++){
    if( termCanDriveIndex(pTerm, pSrc, notReady) ){
      int iCol;
      Bitmask cMask;
      assert( (pTerm->eOperator & (WO_OR|WO_AND))==0 );
      iCol = pTerm->u.x.leftColumn;
      cMask = iCol>=BMS ? MASKBIT(BMS-1) : MASKBIT(iCol);
      testcase( iCol==BMS-1 );
      testcase( iCol==BMS );
      if( (idxCols & cMask)==0 ){
        Expr *pX = pTerm->pExpr;
        idxCols |= cMask;
        pIdx->aiColumn[n] = pTerm->u.x.leftColumn;
        pColl = sqlite3ExprCompareCollSeq(pParse, pX);
150777
150778
150779
150780
150781
150782
150783




150784
150785
150786
150787
150788
150789
150790

  /* Create the automatic index */
  assert( pLevel->iIdxCur>=0 );
  pLevel->iIdxCur = pParse->nTab++;
  sqlite3VdbeAddOp2(v, OP_OpenAutoindex, pLevel->iIdxCur, nKeyCol+1);
  sqlite3VdbeSetP4KeyInfo(pParse, pIdx);
  VdbeComment((v, "for %s", pTable->zName));





  /* Fill the automatic index with content */
  pTabItem = &pWC->pWInfo->pTabList->a[pLevel->iFrom];
  if( pTabItem->fg.viaCoroutine ){
    int regYield = pTabItem->regReturn;
    addrCounter = sqlite3VdbeAddOp2(v, OP_Integer, 0, 0);
    sqlite3VdbeAddOp3(v, OP_InitCoroutine, regYield, 0, pTabItem->addrFillSub);







>
>
>
>







151882
151883
151884
151885
151886
151887
151888
151889
151890
151891
151892
151893
151894
151895
151896
151897
151898
151899

  /* Create the automatic index */
  assert( pLevel->iIdxCur>=0 );
  pLevel->iIdxCur = pParse->nTab++;
  sqlite3VdbeAddOp2(v, OP_OpenAutoindex, pLevel->iIdxCur, nKeyCol+1);
  sqlite3VdbeSetP4KeyInfo(pParse, pIdx);
  VdbeComment((v, "for %s", pTable->zName));
  if( OptimizationEnabled(pParse->db, SQLITE_BloomFilter) ){
    pLevel->regFilter = ++pParse->nMem;
    sqlite3VdbeAddOp2(v, OP_Blob, 10000, pLevel->regFilter);
  }

  /* Fill the automatic index with content */
  pTabItem = &pWC->pWInfo->pTabList->a[pLevel->iFrom];
  if( pTabItem->fg.viaCoroutine ){
    int regYield = pTabItem->regReturn;
    addrCounter = sqlite3VdbeAddOp2(v, OP_Integer, 0, 0);
    sqlite3VdbeAddOp3(v, OP_InitCoroutine, regYield, 0, pTabItem->addrFillSub);
150799
150800
150801
150802
150803
150804
150805




150806
150807
150808
150809
150810
150811
150812
    sqlite3ExprIfFalse(pParse, pPartial, iContinue, SQLITE_JUMPIFNULL);
    pLoop->wsFlags |= WHERE_PARTIALIDX;
  }
  regRecord = sqlite3GetTempReg(pParse);
  regBase = sqlite3GenerateIndexKey(
      pParse, pIdx, pLevel->iTabCur, regRecord, 0, 0, 0, 0
  );




  sqlite3VdbeAddOp2(v, OP_IdxInsert, pLevel->iIdxCur, regRecord);
  sqlite3VdbeChangeP5(v, OPFLAG_USESEEKRESULT);
  if( pPartial ) sqlite3VdbeResolveLabel(v, iContinue);
  if( pTabItem->fg.viaCoroutine ){
    sqlite3VdbeChangeP2(v, addrCounter, regBase+n);
    testcase( pParse->db->mallocFailed );
    assert( pLevel->iIdxCur>0 );







>
>
>
>







151908
151909
151910
151911
151912
151913
151914
151915
151916
151917
151918
151919
151920
151921
151922
151923
151924
151925
    sqlite3ExprIfFalse(pParse, pPartial, iContinue, SQLITE_JUMPIFNULL);
    pLoop->wsFlags |= WHERE_PARTIALIDX;
  }
  regRecord = sqlite3GetTempReg(pParse);
  regBase = sqlite3GenerateIndexKey(
      pParse, pIdx, pLevel->iTabCur, regRecord, 0, 0, 0, 0
  );
  if( pLevel->regFilter ){
    sqlite3VdbeAddOp4Int(v, OP_FilterAdd, pLevel->regFilter, 0,
                         regBase, pLoop->u.btree.nEq);
  }
  sqlite3VdbeAddOp2(v, OP_IdxInsert, pLevel->iIdxCur, regRecord);
  sqlite3VdbeChangeP5(v, OPFLAG_USESEEKRESULT);
  if( pPartial ) sqlite3VdbeResolveLabel(v, iContinue);
  if( pTabItem->fg.viaCoroutine ){
    sqlite3VdbeChangeP2(v, addrCounter, regBase+n);
    testcase( pParse->db->mallocFailed );
    assert( pLevel->iIdxCur>0 );
150824
150825
150826
150827
150828
150829
150830





















































































































150831
150832
150833
150834
150835
150836
150837
  /* Jump here when skipping the initialization */
  sqlite3VdbeJumpHere(v, addrInit);

end_auto_index_create:
  sqlite3ExprDelete(pParse->db, pPartial);
}
#endif /* SQLITE_OMIT_AUTOMATIC_INDEX */






















































































































#ifndef SQLITE_OMIT_VIRTUALTABLE
/*
** Allocate and populate an sqlite3_index_info structure. It is the
** responsibility of the caller to eventually release the structure
** by passing the pointer returned by this function to sqlite3_free().
*/







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







151937
151938
151939
151940
151941
151942
151943
151944
151945
151946
151947
151948
151949
151950
151951
151952
151953
151954
151955
151956
151957
151958
151959
151960
151961
151962
151963
151964
151965
151966
151967
151968
151969
151970
151971
151972
151973
151974
151975
151976
151977
151978
151979
151980
151981
151982
151983
151984
151985
151986
151987
151988
151989
151990
151991
151992
151993
151994
151995
151996
151997
151998
151999
152000
152001
152002
152003
152004
152005
152006
152007
152008
152009
152010
152011
152012
152013
152014
152015
152016
152017
152018
152019
152020
152021
152022
152023
152024
152025
152026
152027
152028
152029
152030
152031
152032
152033
152034
152035
152036
152037
152038
152039
152040
152041
152042
152043
152044
152045
152046
152047
152048
152049
152050
152051
152052
152053
152054
152055
152056
152057
152058
152059
152060
152061
152062
152063
152064
152065
152066
152067
  /* Jump here when skipping the initialization */
  sqlite3VdbeJumpHere(v, addrInit);

end_auto_index_create:
  sqlite3ExprDelete(pParse->db, pPartial);
}
#endif /* SQLITE_OMIT_AUTOMATIC_INDEX */

/*
** Generate bytecode that will initialize a Bloom filter that is appropriate
** for pLevel.
**
** If there are inner loops within pLevel that have the WHERE_BLOOMFILTER
** flag set, initialize a Bloomfilter for them as well.  Except don't do
** this recursive initialization if the SQLITE_BloomPulldown optimization has
** been turned off.
**
** When the Bloom filter is initialized, the WHERE_BLOOMFILTER flag is cleared
** from the loop, but the regFilter value is set to a register that implements
** the Bloom filter.  When regFilter is positive, the
** sqlite3WhereCodeOneLoopStart() will generate code to test the Bloom filter
** and skip the subsequence B-Tree seek if the Bloom filter indicates that
** no matching rows exist.
**
** This routine may only be called if it has previously been determined that
** the loop would benefit from a Bloom filter, and the WHERE_BLOOMFILTER bit
** is set.
*/
static SQLITE_NOINLINE void constructBloomFilter(
  WhereInfo *pWInfo,    /* The WHERE clause */
  int iLevel,           /* Index in pWInfo->a[] that is pLevel */
  WhereLevel *pLevel,   /* Make a Bloom filter for this FROM term */
  Bitmask notReady      /* Loops that are not ready */
){
  int addrOnce;                        /* Address of opening OP_Once */
  int addrTop;                         /* Address of OP_Rewind */
  int addrCont;                        /* Jump here to skip a row */
  const WhereTerm *pTerm;              /* For looping over WHERE clause terms */
  const WhereTerm *pWCEnd;             /* Last WHERE clause term */
  Parse *pParse = pWInfo->pParse;      /* Parsing context */
  Vdbe *v = pParse->pVdbe;             /* VDBE under construction */
  WhereLoop *pLoop = pLevel->pWLoop;   /* The loop being coded */
  int iCur;                            /* Cursor for table getting the filter */

  assert( pLoop!=0 );
  assert( v!=0 );
  assert( pLoop->wsFlags & WHERE_BLOOMFILTER );

  addrOnce = sqlite3VdbeAddOp0(v, OP_Once); VdbeCoverage(v);
  do{
    const SrcItem *pItem;
    const Table *pTab;
    u64 sz;
    sqlite3WhereExplainBloomFilter(pParse, pWInfo, pLevel);
    addrCont = sqlite3VdbeMakeLabel(pParse);
    iCur = pLevel->iTabCur;
    pLevel->regFilter = ++pParse->nMem;

    /* The Bloom filter is a Blob held in a register.  Initialize it
    ** to zero-filled blob of at least 80K bits, but maybe more if the
    ** estimated size of the table is larger.  We could actually
    ** measure the size of the table at run-time using OP_Count with
    ** P3==1 and use that value to initialize the blob.  But that makes
    ** testing complicated.  By basing the blob size on the value in the
    ** sqlite_stat1 table, testing is much easier.
    */
    pItem = &pWInfo->pTabList->a[pLevel->iFrom];
    assert( pItem!=0 );
    pTab = pItem->pTab;
    assert( pTab!=0 );
    sz = sqlite3LogEstToInt(pTab->nRowLogEst);
    if( sz<10000 ){
      sz = 10000;
    }else if( sz>10000000 ){
      sz = 10000000;
    }
    sqlite3VdbeAddOp2(v, OP_Blob, (int)sz, pLevel->regFilter);

    addrTop = sqlite3VdbeAddOp1(v, OP_Rewind, iCur); VdbeCoverage(v);
    pWCEnd = &pWInfo->sWC.a[pWInfo->sWC.nTerm];
    for(pTerm=pWInfo->sWC.a; pTerm<pWCEnd; pTerm++){
      Expr *pExpr = pTerm->pExpr;
      if( (pTerm->wtFlags & TERM_VIRTUAL)==0
       && sqlite3ExprIsTableConstant(pExpr, iCur)
      ){
        sqlite3ExprIfFalse(pParse, pTerm->pExpr, addrCont, SQLITE_JUMPIFNULL);
      }
    }
    if( pLoop->wsFlags & WHERE_IPK ){
      int r1 = sqlite3GetTempReg(pParse);
      sqlite3VdbeAddOp2(v, OP_Rowid, iCur, r1);
      sqlite3VdbeAddOp4Int(v, OP_FilterAdd, pLevel->regFilter, 0, r1, 1);
      sqlite3ReleaseTempReg(pParse, r1);
    }else{
      Index *pIdx = pLoop->u.btree.pIndex;
      int n = pLoop->u.btree.nEq;
      int r1 = sqlite3GetTempRange(pParse, n);
      int jj;
      for(jj=0; jj<n; jj++){
        int iCol = pIdx->aiColumn[jj];
        assert( pIdx->pTable==pItem->pTab );
        sqlite3ExprCodeGetColumnOfTable(v, pIdx->pTable, iCur, iCol,r1+jj);
      }
      sqlite3VdbeAddOp4Int(v, OP_FilterAdd, pLevel->regFilter, 0, r1, n);
      sqlite3ReleaseTempRange(pParse, r1, n);
    }
    sqlite3VdbeResolveLabel(v, addrCont);
    sqlite3VdbeAddOp2(v, OP_Next, pLevel->iTabCur, addrTop+1);
    VdbeCoverage(v);
    sqlite3VdbeJumpHere(v, addrTop);
    pLoop->wsFlags &= ~WHERE_BLOOMFILTER;
    if( OptimizationDisabled(pParse->db, SQLITE_BloomPulldown) ) break;
    while( iLevel < pWInfo->nLevel ){
      iLevel++;
      pLevel = &pWInfo->a[iLevel];
      pLoop = pLevel->pWLoop;
      if( pLoop==0 ) continue;
      if( pLoop->prereq & notReady ) continue;
      if( pLoop->wsFlags & WHERE_BLOOMFILTER ) break;
    }
  }while( iLevel < pWInfo->nLevel );
  sqlite3VdbeJumpHere(v, addrOnce);
}


#ifndef SQLITE_OMIT_VIRTUALTABLE
/*
** Allocate and populate an sqlite3_index_info structure. It is the
** responsibility of the caller to eventually release the structure
** by passing the pointer returned by this function to sqlite3_free().
*/
150862
150863
150864
150865
150866
150867
150868

150869
150870
150871
150872
150873
150874
150875
    assert( IsPowerOfTwo(pTerm->eOperator & ~WO_EQUIV) );
    testcase( pTerm->eOperator & WO_IN );
    testcase( pTerm->eOperator & WO_ISNULL );
    testcase( pTerm->eOperator & WO_IS );
    testcase( pTerm->eOperator & WO_ALL );
    if( (pTerm->eOperator & ~(WO_EQUIV))==0 ) continue;
    if( pTerm->wtFlags & TERM_VNULL ) continue;

    assert( pTerm->u.x.leftColumn>=(-1) );
    nTerm++;
  }

  /* If the ORDER BY clause contains only columns in the current
  ** virtual table then allocate space for the aOrderBy part of
  ** the sqlite3_index_info structure.







>







152092
152093
152094
152095
152096
152097
152098
152099
152100
152101
152102
152103
152104
152105
152106
    assert( IsPowerOfTwo(pTerm->eOperator & ~WO_EQUIV) );
    testcase( pTerm->eOperator & WO_IN );
    testcase( pTerm->eOperator & WO_ISNULL );
    testcase( pTerm->eOperator & WO_IS );
    testcase( pTerm->eOperator & WO_ALL );
    if( (pTerm->eOperator & ~(WO_EQUIV))==0 ) continue;
    if( pTerm->wtFlags & TERM_VNULL ) continue;
    assert( (pTerm->eOperator & (WO_OR|WO_AND))==0 );
    assert( pTerm->u.x.leftColumn>=(-1) );
    nTerm++;
  }

  /* If the ORDER BY clause contains only columns in the current
  ** virtual table then allocate space for the aOrderBy part of
  ** the sqlite3_index_info structure.
150922
150923
150924
150925
150926
150927
150928

150929
150930
150931
150932
150933
150934
150935
    ** right-hand table of a LEFT JOIN.  See tag-20191211-001 for the
    ** equivalent restriction for ordinary tables. */
    if( (pSrc->fg.jointype & JT_LEFT)!=0
     && !ExprHasProperty(pTerm->pExpr, EP_FromJoin)
    ){
      continue;
    }

    assert( pTerm->u.x.leftColumn>=(-1) );
    pIdxCons[j].iColumn = pTerm->u.x.leftColumn;
    pIdxCons[j].iTermOffset = i;
    op = pTerm->eOperator & WO_ALL;
    if( op==WO_IN ) op = WO_EQ;
    if( op==WO_AUX ){
      pIdxCons[j].op = pTerm->eMatchOp;







>







152153
152154
152155
152156
152157
152158
152159
152160
152161
152162
152163
152164
152165
152166
152167
    ** right-hand table of a LEFT JOIN.  See tag-20191211-001 for the
    ** equivalent restriction for ordinary tables. */
    if( (pSrc->fg.jointype & JT_LEFT)!=0
     && !ExprHasProperty(pTerm->pExpr, EP_FromJoin)
    ){
      continue;
    }
    assert( (pTerm->eOperator & (WO_OR|WO_AND))==0 );
    assert( pTerm->u.x.leftColumn>=(-1) );
    pIdxCons[j].iColumn = pTerm->u.x.leftColumn;
    pIdxCons[j].iTermOffset = i;
    op = pTerm->eOperator & WO_ALL;
    if( op==WO_IN ) op = WO_EQ;
    if( op==WO_AUX ){
      pIdxCons[j].op = pTerm->eMatchOp;
151685
151686
151687
151688
151689
151690
151691

151692
151693
151694
151695
151696
151697
151698
151699
151700
151701
151702
151703
151704
151705
151706
151707
151708
151709
151710
151711
151712
151713
151714
151715
151716
    char zLeft[50];
    memcpy(zType, "....", 5);
    if( pTerm->wtFlags & TERM_VIRTUAL ) zType[0] = 'V';
    if( pTerm->eOperator & WO_EQUIV  ) zType[1] = 'E';
    if( ExprHasProperty(pTerm->pExpr, EP_FromJoin) ) zType[2] = 'L';
    if( pTerm->wtFlags & TERM_CODED  ) zType[3] = 'C';
    if( pTerm->eOperator & WO_SINGLE ){

      sqlite3_snprintf(sizeof(zLeft),zLeft,"left={%d:%d}",
                       pTerm->leftCursor, pTerm->u.x.leftColumn);
    }else if( (pTerm->eOperator & WO_OR)!=0 && pTerm->u.pOrInfo!=0 ){
      sqlite3_snprintf(sizeof(zLeft),zLeft,"indexable=0x%llx",
                       pTerm->u.pOrInfo->indexable);
    }else{
      sqlite3_snprintf(sizeof(zLeft),zLeft,"left=%d", pTerm->leftCursor);
    }
    sqlite3DebugPrintf(
       "TERM-%-3d %p %s %-12s op=%03x wtFlags=%04x",
       iTerm, pTerm, zType, zLeft, pTerm->eOperator, pTerm->wtFlags);
    /* The 0x10000 .wheretrace flag causes extra information to be
    ** shown about each Term */
    if( sqlite3WhereTrace & 0x10000 ){
      sqlite3DebugPrintf(" prob=%-3d prereq=%llx,%llx",
        pTerm->truthProb, (u64)pTerm->prereqAll, (u64)pTerm->prereqRight);
    }
    if( pTerm->u.x.iField ){
      sqlite3DebugPrintf(" iField=%d", pTerm->u.x.iField);
    }
    if( pTerm->iParent>=0 ){
      sqlite3DebugPrintf(" iParent=%d", pTerm->iParent);
    }
    sqlite3DebugPrintf("\n");
    sqlite3TreeViewExpr(0, pTerm->pExpr, 0);







>

















|







152917
152918
152919
152920
152921
152922
152923
152924
152925
152926
152927
152928
152929
152930
152931
152932
152933
152934
152935
152936
152937
152938
152939
152940
152941
152942
152943
152944
152945
152946
152947
152948
152949
    char zLeft[50];
    memcpy(zType, "....", 5);
    if( pTerm->wtFlags & TERM_VIRTUAL ) zType[0] = 'V';
    if( pTerm->eOperator & WO_EQUIV  ) zType[1] = 'E';
    if( ExprHasProperty(pTerm->pExpr, EP_FromJoin) ) zType[2] = 'L';
    if( pTerm->wtFlags & TERM_CODED  ) zType[3] = 'C';
    if( pTerm->eOperator & WO_SINGLE ){
      assert( (pTerm->eOperator & (WO_OR|WO_AND))==0 );
      sqlite3_snprintf(sizeof(zLeft),zLeft,"left={%d:%d}",
                       pTerm->leftCursor, pTerm->u.x.leftColumn);
    }else if( (pTerm->eOperator & WO_OR)!=0 && pTerm->u.pOrInfo!=0 ){
      sqlite3_snprintf(sizeof(zLeft),zLeft,"indexable=0x%llx",
                       pTerm->u.pOrInfo->indexable);
    }else{
      sqlite3_snprintf(sizeof(zLeft),zLeft,"left=%d", pTerm->leftCursor);
    }
    sqlite3DebugPrintf(
       "TERM-%-3d %p %s %-12s op=%03x wtFlags=%04x",
       iTerm, pTerm, zType, zLeft, pTerm->eOperator, pTerm->wtFlags);
    /* The 0x10000 .wheretrace flag causes extra information to be
    ** shown about each Term */
    if( sqlite3WhereTrace & 0x10000 ){
      sqlite3DebugPrintf(" prob=%-3d prereq=%llx,%llx",
        pTerm->truthProb, (u64)pTerm->prereqAll, (u64)pTerm->prereqRight);
    }
    if( (pTerm->eOperator & (WO_OR|WO_AND))==0 && pTerm->u.x.iField ){
      sqlite3DebugPrintf(" iField=%d", pTerm->u.x.iField);
    }
    if( pTerm->iParent>=0 ){
      sqlite3DebugPrintf(" iParent=%d", pTerm->iParent);
    }
    sqlite3DebugPrintf("\n");
    sqlite3TreeViewExpr(0, pTerm->pExpr, 0);
151764
151765
151766
151767
151768
151769
151770
151771
151772
151773
151774
151775
151776
151777
151778
151779
151780
    }else{
      z = sqlite3_mprintf("(%d,%x)", p->u.vtab.idxNum, p->u.vtab.omitMask);
    }
    sqlite3DebugPrintf(" %-19s", z);
    sqlite3_free(z);
  }
  if( p->wsFlags & WHERE_SKIPSCAN ){
    sqlite3DebugPrintf(" f %05x %d-%d", p->wsFlags, p->nLTerm,p->nSkip);
  }else{
    sqlite3DebugPrintf(" f %05x N %d", p->wsFlags, p->nLTerm);
  }
  sqlite3DebugPrintf(" cost %d,%d,%d\n", p->rSetup, p->rRun, p->nOut);
  if( p->nLTerm && (sqlite3WhereTrace & 0x100)!=0 ){
    int i;
    for(i=0; i<p->nLTerm; i++){
      sqlite3WhereTermPrint(p->aLTerm[i], i);
    }







|

|







152997
152998
152999
153000
153001
153002
153003
153004
153005
153006
153007
153008
153009
153010
153011
153012
153013
    }else{
      z = sqlite3_mprintf("(%d,%x)", p->u.vtab.idxNum, p->u.vtab.omitMask);
    }
    sqlite3DebugPrintf(" %-19s", z);
    sqlite3_free(z);
  }
  if( p->wsFlags & WHERE_SKIPSCAN ){
    sqlite3DebugPrintf(" f %06x %d-%d", p->wsFlags, p->nLTerm,p->nSkip);
  }else{
    sqlite3DebugPrintf(" f %06x N %d", p->wsFlags, p->nLTerm);
  }
  sqlite3DebugPrintf(" cost %d,%d,%d\n", p->rSetup, p->rRun, p->nOut);
  if( p->nLTerm && (sqlite3WhereTrace & 0x100)!=0 ){
    int i;
    for(i=0; i<p->nLTerm; i++){
      sqlite3WhereTermPrint(p->aLTerm[i], i);
    }
151866
151867
151868
151869
151870
151871
151872
151873

151874
151875
151876
151877
151878
151879
151880
** Free a WhereInfo structure
*/
static void whereInfoFree(sqlite3 *db, WhereInfo *pWInfo){
  int i;
  assert( pWInfo!=0 );
  for(i=0; i<pWInfo->nLevel; i++){
    WhereLevel *pLevel = &pWInfo->a[i];
    if( pLevel->pWLoop && (pLevel->pWLoop->wsFlags & WHERE_IN_ABLE) ){

      sqlite3DbFree(db, pLevel->u.in.aInLoop);
    }
  }
  sqlite3WhereClauseClear(&pWInfo->sWC);
  while( pWInfo->pLoops ){
    WhereLoop *p = pWInfo->pLoops;
    pWInfo->pLoops = p->pNextLoop;







|
>







153099
153100
153101
153102
153103
153104
153105
153106
153107
153108
153109
153110
153111
153112
153113
153114
** Free a WhereInfo structure
*/
static void whereInfoFree(sqlite3 *db, WhereInfo *pWInfo){
  int i;
  assert( pWInfo!=0 );
  for(i=0; i<pWInfo->nLevel; i++){
    WhereLevel *pLevel = &pWInfo->a[i];
    if( pLevel->pWLoop && (pLevel->pWLoop->wsFlags & WHERE_IN_ABLE)!=0 ){
      assert( (pLevel->pWLoop->wsFlags & WHERE_MULTI_OR)==0 );
      sqlite3DbFree(db, pLevel->u.in.aInLoop);
    }
  }
  sqlite3WhereClauseClear(&pWInfo->sWC);
  while( pWInfo->pLoops ){
    WhereLoop *p = pWInfo->pLoops;
    pWInfo->pLoops = p->pNextLoop;
152225
152226
152227
152228
152229
152230
152231
152232
152233
152234
152235
152236
152237
152238
152239
152240
152241
152242
152243







152244
152245
152246
152247
152248
152249
152250
){
  WhereTerm *pTerm, *pX;
  Bitmask notAllowed = ~(pLoop->prereq|pLoop->maskSelf);
  int i, j;
  LogEst iReduce = 0;    /* pLoop->nOut should not exceed nRow-iReduce */

  assert( (pLoop->wsFlags & WHERE_AUTO_INDEX)==0 );
  for(i=pWC->nTerm, pTerm=pWC->a; i>0; i--, pTerm++){
    assert( pTerm!=0 );
    if( (pTerm->wtFlags & TERM_VIRTUAL)!=0 ) break;
    if( (pTerm->prereqAll & pLoop->maskSelf)==0 ) continue;
    if( (pTerm->prereqAll & notAllowed)!=0 ) continue;
    for(j=pLoop->nLTerm-1; j>=0; j--){
      pX = pLoop->aLTerm[j];
      if( pX==0 ) continue;
      if( pX==pTerm ) break;
      if( pX->iParent>=0 && (&pWC->a[pX->iParent])==pTerm ) break;
    }
    if( j<0 ){







      if( pTerm->truthProb<=0 ){
        /* If a truth probability is specified using the likelihood() hints,
        ** then use the probability provided by the application. */
        pLoop->nOut += pTerm->truthProb;
      }else{
        /* In the absence of explicit truth probabilities, use heuristics to
        ** guess a reasonable truth probability. */







|

|

|







>
>
>
>
>
>
>







153459
153460
153461
153462
153463
153464
153465
153466
153467
153468
153469
153470
153471
153472
153473
153474
153475
153476
153477
153478
153479
153480
153481
153482
153483
153484
153485
153486
153487
153488
153489
153490
153491
){
  WhereTerm *pTerm, *pX;
  Bitmask notAllowed = ~(pLoop->prereq|pLoop->maskSelf);
  int i, j;
  LogEst iReduce = 0;    /* pLoop->nOut should not exceed nRow-iReduce */

  assert( (pLoop->wsFlags & WHERE_AUTO_INDEX)==0 );
  for(i=pWC->nBase, pTerm=pWC->a; i>0; i--, pTerm++){
    assert( pTerm!=0 );
    if( (pTerm->prereqAll & notAllowed)!=0 ) continue;
    if( (pTerm->prereqAll & pLoop->maskSelf)==0 ) continue;
    if( (pTerm->wtFlags & TERM_VIRTUAL)!=0 ) continue;
    for(j=pLoop->nLTerm-1; j>=0; j--){
      pX = pLoop->aLTerm[j];
      if( pX==0 ) continue;
      if( pX==pTerm ) break;
      if( pX->iParent>=0 && (&pWC->a[pX->iParent])==pTerm ) break;
    }
    if( j<0 ){
      if( pLoop->maskSelf==pTerm->prereqAll ){
        /* If there are extra terms in the WHERE clause not used by an index
        ** that depend only on the table being scanned, and that will tend to
        ** cause many rows to be omitted, then mark that table as
        ** "self-culling". */
        pLoop->wsFlags |= WHERE_SELFCULL;
      }
      if( pTerm->truthProb<=0 ){
        /* If a truth probability is specified using the likelihood() hints,
        ** then use the probability provided by the application. */
        pLoop->nOut += pTerm->truthProb;
      }else{
        /* In the absence of explicit truth probabilities, use heuristics to
        ** guess a reasonable truth probability. */
152264
152265
152266
152267
152268
152269
152270
152271


152272
152273
152274
152275
152276
152277
152278
            pTerm->wtFlags |= TERM_HEURTRUTH;
            iReduce = k;
          }
        }
      }
    }
  }
  if( pLoop->nOut > nRow-iReduce )  pLoop->nOut = nRow - iReduce;


}

/*
** Term pTerm is a vector range comparison operation. The first comparison
** in the vector can be optimized using column nEq of the index. This
** function returns the total number of vector elements that can be used
** as part of the range comparison.







|
>
>







153505
153506
153507
153508
153509
153510
153511
153512
153513
153514
153515
153516
153517
153518
153519
153520
153521
            pTerm->wtFlags |= TERM_HEURTRUTH;
            iReduce = k;
          }
        }
      }
    }
  }
  if( pLoop->nOut > nRow-iReduce ){
    pLoop->nOut = nRow - iReduce;
  }
}

/*
** Term pTerm is a vector range comparison operation. The first comparison
** in the vector can be optimized using column nEq of the index. This
** function returns the total number of vector elements that can be used
** as part of the range comparison.
152301
152302
152303
152304
152305
152306
152307



152308
152309
152310
152311
152312
152313
152314
152315
152316
152317
  nCmp = MIN(nCmp, (pIdx->nColumn - nEq));
  for(i=1; i<nCmp; i++){
    /* Test if comparison i of pTerm is compatible with column (i+nEq)
    ** of the index. If not, exit the loop.  */
    char aff;                     /* Comparison affinity */
    char idxaff = 0;              /* Indexed columns affinity */
    CollSeq *pColl;               /* Comparison collation sequence */



    Expr *pLhs = pTerm->pExpr->pLeft->x.pList->a[i].pExpr;
    Expr *pRhs = pTerm->pExpr->pRight;
    if( pRhs->flags & EP_xIsSelect ){
      pRhs = pRhs->x.pSelect->pEList->a[i].pExpr;
    }else{
      pRhs = pRhs->x.pList->a[i].pExpr;
    }

    /* Check that the LHS of the comparison is a column reference to
    ** the right column of the right source table. And that the sort







>
>
>
|
|
|







153544
153545
153546
153547
153548
153549
153550
153551
153552
153553
153554
153555
153556
153557
153558
153559
153560
153561
153562
153563
  nCmp = MIN(nCmp, (pIdx->nColumn - nEq));
  for(i=1; i<nCmp; i++){
    /* Test if comparison i of pTerm is compatible with column (i+nEq)
    ** of the index. If not, exit the loop.  */
    char aff;                     /* Comparison affinity */
    char idxaff = 0;              /* Indexed columns affinity */
    CollSeq *pColl;               /* Comparison collation sequence */
    Expr *pLhs, *pRhs;

    assert( ExprUseXList(pTerm->pExpr->pLeft) );
    pLhs = pTerm->pExpr->pLeft->x.pList->a[i].pExpr;
    pRhs = pTerm->pExpr->pRight;
    if( ExprUseXSelect(pRhs) ){
      pRhs = pRhs->x.pSelect->pEList->a[i].pExpr;
    }else{
      pRhs = pRhs->x.pList->a[i].pExpr;
    }

    /* Check that the LHS of the comparison is a column reference to
    ** the right column of the right source table. And that the sort
152464
152465
152466
152467
152468
152469
152470
152471
152472
152473
152474
152475
152476
152477
152478
        || (pNew->wsFlags & WHERE_COLUMN_NULL)!=0
        || (pNew->wsFlags & WHERE_COLUMN_IN)!=0
        || (pNew->wsFlags & WHERE_SKIPSCAN)!=0
    );

    if( eOp & WO_IN ){
      Expr *pExpr = pTerm->pExpr;
      if( ExprHasProperty(pExpr, EP_xIsSelect) ){
        /* "x IN (SELECT ...)":  TUNING: the SELECT returns 25 rows */
        int i;
        nIn = 46;  assert( 46==sqlite3LogEst(25) );

        /* The expression may actually be of the form (x, y) IN (SELECT...).
        ** In this case there is a separate term for each of (x) and (y).
        ** However, the nIn multiplier should only be applied once, not once







|







153710
153711
153712
153713
153714
153715
153716
153717
153718
153719
153720
153721
153722
153723
153724
        || (pNew->wsFlags & WHERE_COLUMN_NULL)!=0
        || (pNew->wsFlags & WHERE_COLUMN_IN)!=0
        || (pNew->wsFlags & WHERE_SKIPSCAN)!=0
    );

    if( eOp & WO_IN ){
      Expr *pExpr = pTerm->pExpr;
      if( ExprUseXSelect(pExpr) ){
        /* "x IN (SELECT ...)":  TUNING: the SELECT returns 25 rows */
        int i;
        nIn = 46;  assert( 46==sqlite3LogEst(25) );

        /* The expression may actually be of the form (x, y) IN (SELECT...).
        ** In this case there is a separate term for each of (x) and (y).
        ** However, the nIn multiplier should only be applied once, not once
152605
152606
152607
152608
152609
152610
152611
152612
152613
152614
152615
152616
152617
152618
152619
        pNew->nOut -= nIn;
      }else{
#ifdef SQLITE_ENABLE_STAT4
        tRowcnt nOut = 0;
        if( nInMul==0
         && pProbe->nSample
         && ALWAYS(pNew->u.btree.nEq<=pProbe->nSampleCol)
         && ((eOp & WO_IN)==0 || !ExprHasProperty(pTerm->pExpr, EP_xIsSelect))
         && OptimizationEnabled(db, SQLITE_Stat4)
        ){
          Expr *pExpr = pTerm->pExpr;
          if( (eOp & (WO_EQ|WO_ISNULL|WO_IS))!=0 ){
            testcase( eOp & WO_EQ );
            testcase( eOp & WO_IS );
            testcase( eOp & WO_ISNULL );







|







153851
153852
153853
153854
153855
153856
153857
153858
153859
153860
153861
153862
153863
153864
153865
        pNew->nOut -= nIn;
      }else{
#ifdef SQLITE_ENABLE_STAT4
        tRowcnt nOut = 0;
        if( nInMul==0
         && pProbe->nSample
         && ALWAYS(pNew->u.btree.nEq<=pProbe->nSampleCol)
         && ((eOp & WO_IN)==0 || ExprUseXList(pTerm->pExpr))
         && OptimizationEnabled(db, SQLITE_Stat4)
        ){
          Expr *pExpr = pTerm->pExpr;
          if( (eOp & (WO_EQ|WO_ISNULL|WO_IS))!=0 ){
            testcase( eOp & WO_EQ );
            testcase( eOp & WO_IS );
            testcase( eOp & WO_ISNULL );
152881
152882
152883
152884
152885
152886
152887

152888
152889
152890
152891
152892
152893
152894
  pTabList = pWInfo->pTabList;
  pSrc = pTabList->a + pNew->iTab;
  pTab = pSrc->pTab;
  pWC = pBuilder->pWC;
  assert( !IsVirtual(pSrc->pTab) );

  if( pSrc->fg.isIndexedBy ){

    /* An INDEXED BY clause specifies a particular index to use */
    pProbe = pSrc->u2.pIBIndex;
  }else if( !HasRowid(pTab) ){
    pProbe = pTab->pIndex;
  }else{
    /* There is no INDEXED BY clause.  Create a fake Index object in local
    ** variable sPk to represent the rowid primary key index.  Make this







>







154127
154128
154129
154130
154131
154132
154133
154134
154135
154136
154137
154138
154139
154140
154141
  pTabList = pWInfo->pTabList;
  pSrc = pTabList->a + pNew->iTab;
  pTab = pSrc->pTab;
  pWC = pBuilder->pWC;
  assert( !IsVirtual(pSrc->pTab) );

  if( pSrc->fg.isIndexedBy ){
    assert( pSrc->fg.isCte==0 );
    /* An INDEXED BY clause specifies a particular index to use */
    pProbe = pSrc->u2.pIBIndex;
  }else if( !HasRowid(pTab) ){
    pProbe = pTab->pIndex;
  }else{
    /* There is no INDEXED BY clause.  Create a fake Index object in local
    ** variable sPk to represent the rowid primary key index.  Make this
153496
153497
153498
153499
153500
153501
153502

153503
153504
153505
153506
153507
153508
153509
        if( (pOrTerm->eOperator & WO_AND)!=0 ){
          sSubBuild.pWC = &pOrTerm->u.pAndInfo->wc;
        }else if( pOrTerm->leftCursor==iCur ){
          tempWC.pWInfo = pWC->pWInfo;
          tempWC.pOuter = pWC;
          tempWC.op = TK_AND;
          tempWC.nTerm = 1;

          tempWC.a = pOrTerm;
          sSubBuild.pWC = &tempWC;
        }else{
          continue;
        }
        sCur.n = 0;
#ifdef WHERETRACE_ENABLED







>







154743
154744
154745
154746
154747
154748
154749
154750
154751
154752
154753
154754
154755
154756
154757
        if( (pOrTerm->eOperator & WO_AND)!=0 ){
          sSubBuild.pWC = &pOrTerm->u.pAndInfo->wc;
        }else if( pOrTerm->leftCursor==iCur ){
          tempWC.pWInfo = pWC->pWInfo;
          tempWC.pOuter = pWC;
          tempWC.op = TK_AND;
          tempWC.nTerm = 1;
          tempWC.nBase = 1;
          tempWC.a = pOrTerm;
          sSubBuild.pWC = &tempWC;
        }else{
          continue;
        }
        sCur.n = 0;
#ifdef WHERETRACE_ENABLED
153967
153968
153969
153970
153971
153972
153973
153974
153975
153976
153977
153978
153979
153980
153981
        }
      }
    }
  } /* End the loop over all WhereLoops from outer-most down to inner-most */
  if( obSat==obDone ) return (i8)nOrderBy;
  if( !isOrderDistinct ){
    for(i=nOrderBy-1; i>0; i--){
      Bitmask m = MASKBIT(i) - 1;
      if( (obSat&m)==m ) return i;
    }
    return 0;
  }
  return -1;
}








|







155215
155216
155217
155218
155219
155220
155221
155222
155223
155224
155225
155226
155227
155228
155229
        }
      }
    }
  } /* End the loop over all WhereLoops from outer-most down to inner-most */
  if( obSat==obDone ) return (i8)nOrderBy;
  if( !isOrderDistinct ){
    for(i=nOrderBy-1; i>0; i--){
      Bitmask m = ALWAYS(i<BMS) ? MASKBIT(i) - 1 : 0;
      if( (obSat&m)==m ) return i;
    }
    return 0;
  }
  return -1;
}

154492
154493
154494
154495
154496
154497
154498

154499
154500
154501
154502
154503
154504
154505
154506
154507
154508
  if( pItem->fg.isIndexedBy ) return 0;
  iCur = pItem->iCursor;
  pWC = &pWInfo->sWC;
  pLoop = pBuilder->pNew;
  pLoop->wsFlags = 0;
  pLoop->nSkip = 0;
  pTerm = whereScanInit(&scan, pWC, iCur, -1, WO_EQ|WO_IS, 0);

  if( pTerm ){
    testcase( pTerm->eOperator & WO_IS );
    assert( pTerm->prereqRight==0 );
    pLoop->wsFlags = WHERE_COLUMN_EQ|WHERE_IPK|WHERE_ONEROW;
    pLoop->aLTerm[0] = pTerm;
    pLoop->nLTerm = 1;
    pLoop->u.btree.nEq = 1;
    /* TUNING: Cost of a rowid lookup is 10 */
    pLoop->rRun = 33;  /* 33==sqlite3LogEst(10) */
  }else{







>


<







155740
155741
155742
155743
155744
155745
155746
155747
155748
155749

155750
155751
155752
155753
155754
155755
155756
  if( pItem->fg.isIndexedBy ) return 0;
  iCur = pItem->iCursor;
  pWC = &pWInfo->sWC;
  pLoop = pBuilder->pNew;
  pLoop->wsFlags = 0;
  pLoop->nSkip = 0;
  pTerm = whereScanInit(&scan, pWC, iCur, -1, WO_EQ|WO_IS, 0);
  while( pTerm && pTerm->prereqRight ) pTerm = whereScanNext(&scan);
  if( pTerm ){
    testcase( pTerm->eOperator & WO_IS );

    pLoop->wsFlags = WHERE_COLUMN_EQ|WHERE_IPK|WHERE_ONEROW;
    pLoop->aLTerm[0] = pTerm;
    pLoop->nLTerm = 1;
    pLoop->u.btree.nEq = 1;
    /* TUNING: Cost of a rowid lookup is 10 */
    pLoop->rRun = 33;  /* 33==sqlite3LogEst(10) */
  }else{
154602
154603
154604
154605
154606
154607
154608
















































































































































154609
154610
154611
154612
154613
154614
154615
    }
  }
}
# define WHERETRACE_ALL_LOOPS(W,C) showAllWhereLoops(W,C)
#else
# define WHERETRACE_ALL_LOOPS(W,C)
#endif

















































































































































/*
** Generate the beginning of the loop used for WHERE clause processing.
** The return value is a pointer to an opaque structure that contains
** information needed to terminate the loop.  Later, the calling routine
** should invoke sqlite3WhereEnd() with the return value of this function
** in order to complete the WHERE clause processing.







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







155850
155851
155852
155853
155854
155855
155856
155857
155858
155859
155860
155861
155862
155863
155864
155865
155866
155867
155868
155869
155870
155871
155872
155873
155874
155875
155876
155877
155878
155879
155880
155881
155882
155883
155884
155885
155886
155887
155888
155889
155890
155891
155892
155893
155894
155895
155896
155897
155898
155899
155900
155901
155902
155903
155904
155905
155906
155907
155908
155909
155910
155911
155912
155913
155914
155915
155916
155917
155918
155919
155920
155921
155922
155923
155924
155925
155926
155927
155928
155929
155930
155931
155932
155933
155934
155935
155936
155937
155938
155939
155940
155941
155942
155943
155944
155945
155946
155947
155948
155949
155950
155951
155952
155953
155954
155955
155956
155957
155958
155959
155960
155961
155962
155963
155964
155965
155966
155967
155968
155969
155970
155971
155972
155973
155974
155975
155976
155977
155978
155979
155980
155981
155982
155983
155984
155985
155986
155987
155988
155989
155990
155991
155992
155993
155994
155995
155996
155997
155998
155999
156000
156001
156002
156003
156004
156005
156006
156007
    }
  }
}
# define WHERETRACE_ALL_LOOPS(W,C) showAllWhereLoops(W,C)
#else
# define WHERETRACE_ALL_LOOPS(W,C)
#endif

/* Attempt to omit tables from a join that do not affect the result.
** For a table to not affect the result, the following must be true:
**
**   1) The query must not be an aggregate.
**   2) The table must be the RHS of a LEFT JOIN.
**   3) Either the query must be DISTINCT, or else the ON or USING clause
**      must contain a constraint that limits the scan of the table to
**      at most a single row.
**   4) The table must not be referenced by any part of the query apart
**      from its own USING or ON clause.
**
** For example, given:
**
**     CREATE TABLE t1(ipk INTEGER PRIMARY KEY, v1);
**     CREATE TABLE t2(ipk INTEGER PRIMARY KEY, v2);
**     CREATE TABLE t3(ipk INTEGER PRIMARY KEY, v3);
**
** then table t2 can be omitted from the following:
**
**     SELECT v1, v3 FROM t1
**       LEFT JOIN t2 ON (t1.ipk=t2.ipk)
**       LEFT JOIN t3 ON (t1.ipk=t3.ipk)
**
** or from:
**
**     SELECT DISTINCT v1, v3 FROM t1
**       LEFT JOIN t2
**       LEFT JOIN t3 ON (t1.ipk=t3.ipk)
*/
static SQLITE_NOINLINE Bitmask whereOmitNoopJoin(
  WhereInfo *pWInfo,
  Bitmask notReady
){
  int i;
  Bitmask tabUsed;

  /* Preconditions checked by the caller */
  assert( pWInfo->nLevel>=2 );
  assert( OptimizationEnabled(pWInfo->pParse->db, SQLITE_OmitNoopJoin) );

  /* These two preconditions checked by the caller combine to guarantee
  ** condition (1) of the header comment */
  assert( pWInfo->pResultSet!=0 );
  assert( 0==(pWInfo->wctrlFlags & WHERE_AGG_DISTINCT) );

  tabUsed = sqlite3WhereExprListUsage(&pWInfo->sMaskSet, pWInfo->pResultSet);
  if( pWInfo->pOrderBy ){
    tabUsed |= sqlite3WhereExprListUsage(&pWInfo->sMaskSet, pWInfo->pOrderBy);
  }
  for(i=pWInfo->nLevel-1; i>=1; i--){
    WhereTerm *pTerm, *pEnd;
    SrcItem *pItem;
    WhereLoop *pLoop;
    pLoop = pWInfo->a[i].pWLoop;
    pItem = &pWInfo->pTabList->a[pLoop->iTab];
    if( (pItem->fg.jointype & JT_LEFT)==0 ) continue;
    if( (pWInfo->wctrlFlags & WHERE_WANT_DISTINCT)==0
     && (pLoop->wsFlags & WHERE_ONEROW)==0
    ){
      continue;
    }
    if( (tabUsed & pLoop->maskSelf)!=0 ) continue;
    pEnd = pWInfo->sWC.a + pWInfo->sWC.nTerm;
    for(pTerm=pWInfo->sWC.a; pTerm<pEnd; pTerm++){
      if( (pTerm->prereqAll & pLoop->maskSelf)!=0 ){
        if( !ExprHasProperty(pTerm->pExpr, EP_FromJoin)
         || pTerm->pExpr->iRightJoinTable!=pItem->iCursor
        ){
          break;
        }
      }
    }
    if( pTerm<pEnd ) continue;
    WHERETRACE(0xffff, ("-> drop loop %c not used\n", pLoop->cId));
    notReady &= ~pLoop->maskSelf;
    for(pTerm=pWInfo->sWC.a; pTerm<pEnd; pTerm++){
      if( (pTerm->prereqAll & pLoop->maskSelf)!=0 ){
        pTerm->wtFlags |= TERM_CODED;
      }
    }
    if( i!=pWInfo->nLevel-1 ){
      int nByte = (pWInfo->nLevel-1-i) * sizeof(WhereLevel);
      memmove(&pWInfo->a[i], &pWInfo->a[i+1], nByte);
    }
    pWInfo->nLevel--;
    assert( pWInfo->nLevel>0 );
  }
  return notReady;
}

/*
** Check to see if there are any SEARCH loops that might benefit from
** using a Bloom filter.  Consider a Bloom filter if:
**
**   (1)  The SEARCH happens more than N times where N is the number
**        of rows in the table that is being considered for the Bloom
**        filter.
**   (2)  Some searches are expected to find zero rows.  (This is determined
**        by the WHERE_SELFCULL flag on the term.)
**   (3)  Bloom-filter processing is not disabled.  (Checked by the
**        caller.)
**   (4)  The size of the table being searched is known by ANALYZE.
**
** This block of code merely checks to see if a Bloom filter would be
** appropriate, and if so sets the WHERE_BLOOMFILTER flag on the
** WhereLoop.  The implementation of the Bloom filter comes further
** down where the code for each WhereLoop is generated.
*/
static SQLITE_NOINLINE void whereCheckIfBloomFilterIsUseful(
  const WhereInfo *pWInfo
){
  int i;
  LogEst nSearch;

  assert( pWInfo->nLevel>=2 );
  assert( OptimizationEnabled(pWInfo->pParse->db, SQLITE_BloomFilter) );
  nSearch = pWInfo->a[0].pWLoop->nOut;
  for(i=1; i<pWInfo->nLevel; i++){
    WhereLoop *pLoop = pWInfo->a[i].pWLoop;
    const int reqFlags = (WHERE_SELFCULL|WHERE_COLUMN_EQ);
    if( (pLoop->wsFlags & reqFlags)==reqFlags
     /* vvvvvv--- Always the case if WHERE_COLUMN_EQ is defined */
     && ALWAYS((pLoop->wsFlags & (WHERE_IPK|WHERE_INDEXED))!=0)
    ){
      SrcItem *pItem = &pWInfo->pTabList->a[pLoop->iTab];
      Table *pTab = pItem->pTab;
      pTab->tabFlags |= TF_StatsUsed;
      if( nSearch > pTab->nRowLogEst
       && (pTab->tabFlags & TF_HasStat1)!=0
      ){
        testcase( pItem->fg.jointype & JT_LEFT );
        pLoop->wsFlags |= WHERE_BLOOMFILTER;
        pLoop->wsFlags &= ~WHERE_IDX_ONLY;
        WHERETRACE(0xffff, (
           "-> use Bloom-filter on loop %c because there are ~%.1e "
           "lookups into %s which has only ~%.1e rows\n",
           pLoop->cId, (double)sqlite3LogEstToInt(nSearch), pTab->zName,
           (double)sqlite3LogEstToInt(pTab->nRowLogEst)));
      }
    }
    nSearch += pLoop->nOut;
  }
}

/*
** Generate the beginning of the loop used for WHERE clause processing.
** The return value is a pointer to an opaque structure that contains
** information needed to terminate the loop.  Later, the calling routine
** should invoke sqlite3WhereEnd() with the return value of this function
** in order to complete the WHERE clause processing.
154733
154734
154735
154736
154737
154738
154739
154740
154741
154742
154743
154744
154745
154746
154747
154748
154749
154750
154751
154752
  memset(&sWLB, 0, sizeof(sWLB));

  /* An ORDER/GROUP BY clause of more than 63 terms cannot be optimized */
  testcase( pOrderBy && pOrderBy->nExpr==BMS-1 );
  if( pOrderBy && pOrderBy->nExpr>=BMS ) pOrderBy = 0;
  sWLB.pOrderBy = pOrderBy;

  /* Disable the DISTINCT optimization if SQLITE_DistinctOpt is set via
  ** sqlite3_test_ctrl(SQLITE_TESTCTRL_OPTIMIZATIONS,...) */
  if( OptimizationDisabled(db, SQLITE_DistinctOpt) ){
    wctrlFlags &= ~WHERE_WANT_DISTINCT;
  }

  /* The number of tables in the FROM clause is limited by the number of
  ** bits in a Bitmask
  */
  testcase( pTabList->nSrc==BMS );
  if( pTabList->nSrc>BMS ){
    sqlite3ErrorMsg(pParse, "at most %d tables in a join", BMS);
    return 0;







<
<
<
<
<
<







156125
156126
156127
156128
156129
156130
156131






156132
156133
156134
156135
156136
156137
156138
  memset(&sWLB, 0, sizeof(sWLB));

  /* An ORDER/GROUP BY clause of more than 63 terms cannot be optimized */
  testcase( pOrderBy && pOrderBy->nExpr==BMS-1 );
  if( pOrderBy && pOrderBy->nExpr>=BMS ) pOrderBy = 0;
  sWLB.pOrderBy = pOrderBy;







  /* The number of tables in the FROM clause is limited by the number of
  ** bits in a Bitmask
  */
  testcase( pTabList->nSrc==BMS );
  if( pTabList->nSrc>BMS ){
    sqlite3ErrorMsg(pParse, "at most %d tables in a join", BMS);
    return 0;
154785
154786
154787
154788
154789
154790
154791




154792
154793
154794
154795
154796
154797
154798
154799
154800
154801
154802
154803
154804
154805
154806
154807
154808
154809
154810
154811
154812


154813
154814
154815
154816
154817
154818
154819
  pWInfo->iLimit = iAuxArg;
  pWInfo->savedNQueryLoop = pParse->nQueryLoop;
  memset(&pWInfo->nOBSat, 0,
         offsetof(WhereInfo,sWC) - offsetof(WhereInfo,nOBSat));
  memset(&pWInfo->a[0], 0, sizeof(WhereLoop)+nTabList*sizeof(WhereLevel));
  assert( pWInfo->eOnePass==ONEPASS_OFF );  /* ONEPASS defaults to OFF */
  pMaskSet = &pWInfo->sMaskSet;




  sWLB.pWInfo = pWInfo;
  sWLB.pWC = &pWInfo->sWC;
  sWLB.pNew = (WhereLoop*)(((char*)pWInfo)+nByteWInfo);
  assert( EIGHT_BYTE_ALIGNMENT(sWLB.pNew) );
  whereLoopInit(sWLB.pNew);
#ifdef SQLITE_DEBUG
  sWLB.pNew->cId = '*';
#endif

  /* Split the WHERE clause into separate subexpressions where each
  ** subexpression is separated by an AND operator.
  */
  initMaskSet(pMaskSet);
  sqlite3WhereClauseInit(&pWInfo->sWC, pWInfo);
  sqlite3WhereSplit(&pWInfo->sWC, pWhere, TK_AND);

  /* Special case: No FROM clause
  */
  if( nTabList==0 ){
    if( pOrderBy ) pWInfo->nOBSat = pOrderBy->nExpr;
    if( wctrlFlags & WHERE_WANT_DISTINCT ){


      pWInfo->eDistinct = WHERE_DISTINCT_UNIQUE;
    }
    ExplainQueryPlan((pParse, 0, "SCAN CONSTANT ROW"));
  }else{
    /* Assign a bit from the bitmask to every term in the FROM clause.
    **
    ** The N-th term of the FROM clause is assigned a bitmask of 1<<N.







>
>
>
>












<







|
>
>







156171
156172
156173
156174
156175
156176
156177
156178
156179
156180
156181
156182
156183
156184
156185
156186
156187
156188
156189
156190
156191
156192
156193

156194
156195
156196
156197
156198
156199
156200
156201
156202
156203
156204
156205
156206
156207
156208
156209
156210
  pWInfo->iLimit = iAuxArg;
  pWInfo->savedNQueryLoop = pParse->nQueryLoop;
  memset(&pWInfo->nOBSat, 0,
         offsetof(WhereInfo,sWC) - offsetof(WhereInfo,nOBSat));
  memset(&pWInfo->a[0], 0, sizeof(WhereLoop)+nTabList*sizeof(WhereLevel));
  assert( pWInfo->eOnePass==ONEPASS_OFF );  /* ONEPASS defaults to OFF */
  pMaskSet = &pWInfo->sMaskSet;
  pMaskSet->n = 0;
  pMaskSet->ix[0] = -99; /* Initialize ix[0] to a value that can never be
                         ** a valid cursor number, to avoid an initial
                         ** test for pMaskSet->n==0 in sqlite3WhereGetMask() */
  sWLB.pWInfo = pWInfo;
  sWLB.pWC = &pWInfo->sWC;
  sWLB.pNew = (WhereLoop*)(((char*)pWInfo)+nByteWInfo);
  assert( EIGHT_BYTE_ALIGNMENT(sWLB.pNew) );
  whereLoopInit(sWLB.pNew);
#ifdef SQLITE_DEBUG
  sWLB.pNew->cId = '*';
#endif

  /* Split the WHERE clause into separate subexpressions where each
  ** subexpression is separated by an AND operator.
  */

  sqlite3WhereClauseInit(&pWInfo->sWC, pWInfo);
  sqlite3WhereSplit(&pWInfo->sWC, pWhere, TK_AND);

  /* Special case: No FROM clause
  */
  if( nTabList==0 ){
    if( pOrderBy ) pWInfo->nOBSat = pOrderBy->nExpr;
    if( (wctrlFlags & WHERE_WANT_DISTINCT)!=0
     && OptimizationEnabled(db, SQLITE_DistinctOpt)
    ){
      pWInfo->eDistinct = WHERE_DISTINCT_UNIQUE;
    }
    ExplainQueryPlan((pParse, 0, "SCAN CONSTANT ROW"));
  }else{
    /* Assign a bit from the bitmask to every term in the FROM clause.
    **
    ** The N-th term of the FROM clause is assigned a bitmask of 1<<N.
154856
154857
154858
154859
154860
154861
154862
154863
154864
154865
154866
154867
154868
154869
154870
154871
154872





154873
154874
154875
154876
154877
154878
154879
154880
  ** Do not do this if the expression contains non-deterministic functions
  ** that are not within a sub-select. This is not strictly required, but
  ** preserves SQLite's legacy behaviour in the following two cases:
  **
  **   FROM ... WHERE random()>0;           -- eval random() once per row
  **   FROM ... WHERE (SELECT random())>0;  -- eval random() once overall
  */
  for(ii=0; ii<sWLB.pWC->nTerm; ii++){
    WhereTerm *pT = &sWLB.pWC->a[ii];
    if( pT->wtFlags & TERM_VIRTUAL ) continue;
    if( pT->prereqAll==0 && (nTabList==0 || exprIsDeterministic(pT->pExpr)) ){
      sqlite3ExprIfFalse(pParse, pT->pExpr, pWInfo->iBreak, SQLITE_JUMPIFNULL);
      pT->wtFlags |= TERM_CODED;
    }
  }

  if( wctrlFlags & WHERE_WANT_DISTINCT ){





    if( isDistinctRedundant(pParse, pTabList, &pWInfo->sWC, pResultSet) ){
      /* The DISTINCT marking is pointless.  Ignore it. */
      pWInfo->eDistinct = WHERE_DISTINCT_UNIQUE;
    }else if( pOrderBy==0 ){
      /* Try to ORDER BY the result set to make distinct processing easier */
      pWInfo->wctrlFlags |= WHERE_DISTINCTBY;
      pWInfo->pOrderBy = pResultSet;
    }







|









>
>
>
>
>
|







156247
156248
156249
156250
156251
156252
156253
156254
156255
156256
156257
156258
156259
156260
156261
156262
156263
156264
156265
156266
156267
156268
156269
156270
156271
156272
156273
156274
156275
156276
  ** Do not do this if the expression contains non-deterministic functions
  ** that are not within a sub-select. This is not strictly required, but
  ** preserves SQLite's legacy behaviour in the following two cases:
  **
  **   FROM ... WHERE random()>0;           -- eval random() once per row
  **   FROM ... WHERE (SELECT random())>0;  -- eval random() once overall
  */
  for(ii=0; ii<sWLB.pWC->nBase; ii++){
    WhereTerm *pT = &sWLB.pWC->a[ii];
    if( pT->wtFlags & TERM_VIRTUAL ) continue;
    if( pT->prereqAll==0 && (nTabList==0 || exprIsDeterministic(pT->pExpr)) ){
      sqlite3ExprIfFalse(pParse, pT->pExpr, pWInfo->iBreak, SQLITE_JUMPIFNULL);
      pT->wtFlags |= TERM_CODED;
    }
  }

  if( wctrlFlags & WHERE_WANT_DISTINCT ){
    if( OptimizationDisabled(db, SQLITE_DistinctOpt) ){
      /* Disable the DISTINCT optimization if SQLITE_DistinctOpt is set via
      ** sqlite3_test_ctrl(SQLITE_TESTCTRL_OPTIMIZATIONS,...) */
      wctrlFlags &= ~WHERE_WANT_DISTINCT;
      pWInfo->wctrlFlags &= ~WHERE_WANT_DISTINCT;
    }else if( isDistinctRedundant(pParse, pTabList, &pWInfo->sWC, pResultSet) ){
      /* The DISTINCT marking is pointless.  Ignore it. */
      pWInfo->eDistinct = WHERE_DISTINCT_UNIQUE;
    }else if( pOrderBy==0 ){
      /* Try to ORDER BY the result set to make distinct processing easier */
      pWInfo->wctrlFlags |= WHERE_DISTINCTBY;
      pWInfo->pOrderBy = pResultSet;
    }
154967
154968
154969
154970
154971
154972
154973
154974
154975
154976
154977
154978
154979
154980
154981
154982
154983
154984
154985
154986
154987
154988
154989
154990
154991
154992
154993
154994
154995
154996
154997
154998
154999
155000
155001
155002
155003
155004
155005
155006
155007
155008
155009
155010
155011
155012
155013
155014
155015
155016
155017
155018
155019
155020
155021
155022
155023
155024



155025
155026
155027
155028
155029
155030

155031
155032
155033
155034
155035
155036
155037
155038
155039
155040
155041
155042
155043
155044
155045
155046
155047
155048
155049
155050
155051
155052
155053
155054
155055
155056
155057
155058
    sqlite3DebugPrintf("\n");
    for(ii=0; ii<pWInfo->nLevel; ii++){
      sqlite3WhereLoopPrint(pWInfo->a[ii].pWLoop, sWLB.pWC);
    }
  }
#endif

  /* Attempt to omit tables from the join that do not affect the result.
  ** For a table to not affect the result, the following must be true:
  **
  **   1) The query must not be an aggregate.
  **   2) The table must be the RHS of a LEFT JOIN.
  **   3) Either the query must be DISTINCT, or else the ON or USING clause
  **      must contain a constraint that limits the scan of the table to
  **      at most a single row.
  **   4) The table must not be referenced by any part of the query apart
  **      from its own USING or ON clause.
  **
  ** For example, given:
  **
  **     CREATE TABLE t1(ipk INTEGER PRIMARY KEY, v1);
  **     CREATE TABLE t2(ipk INTEGER PRIMARY KEY, v2);
  **     CREATE TABLE t3(ipk INTEGER PRIMARY KEY, v3);
  **
  ** then table t2 can be omitted from the following:
  **
  **     SELECT v1, v3 FROM t1
  **       LEFT JOIN t2 ON (t1.ipk=t2.ipk)
  **       LEFT JOIN t3 ON (t1.ipk=t3.ipk)
  **
  ** or from:
  **
  **     SELECT DISTINCT v1, v3 FROM t1
  **       LEFT JOIN t2
  **       LEFT JOIN t3 ON (t1.ipk=t3.ipk)
  */
  notReady = ~(Bitmask)0;
  if( pWInfo->nLevel>=2
   && pResultSet!=0                         /* these two combine to guarantee */
   && 0==(wctrlFlags & WHERE_AGG_DISTINCT)  /* condition (1) above */
   && OptimizationEnabled(db, SQLITE_OmitNoopJoin)
  ){
    int i;
    Bitmask tabUsed = sqlite3WhereExprListUsage(pMaskSet, pResultSet);
    if( sWLB.pOrderBy ){
      tabUsed |= sqlite3WhereExprListUsage(pMaskSet, sWLB.pOrderBy);
    }
    for(i=pWInfo->nLevel-1; i>=1; i--){
      WhereTerm *pTerm, *pEnd;
      SrcItem *pItem;
      pLoop = pWInfo->a[i].pWLoop;
      pItem = &pWInfo->pTabList->a[pLoop->iTab];
      if( (pItem->fg.jointype & JT_LEFT)==0 ) continue;
      if( (wctrlFlags & WHERE_WANT_DISTINCT)==0
       && (pLoop->wsFlags & WHERE_ONEROW)==0
      ){
        continue;
      }



      if( (tabUsed & pLoop->maskSelf)!=0 ) continue;
      pEnd = sWLB.pWC->a + sWLB.pWC->nTerm;
      for(pTerm=sWLB.pWC->a; pTerm<pEnd; pTerm++){
        if( (pTerm->prereqAll & pLoop->maskSelf)!=0 ){
          if( !ExprHasProperty(pTerm->pExpr, EP_FromJoin)
           || pTerm->pExpr->iRightJoinTable!=pItem->iCursor

          ){
            break;
          }
        }
      }
      if( pTerm<pEnd ) continue;
      WHERETRACE(0xffff, ("-> drop loop %c not used\n", pLoop->cId));
      notReady &= ~pLoop->maskSelf;
      for(pTerm=sWLB.pWC->a; pTerm<pEnd; pTerm++){
        if( (pTerm->prereqAll & pLoop->maskSelf)!=0 ){
          pTerm->wtFlags |= TERM_CODED;
        }
      }
      if( i!=pWInfo->nLevel-1 ){
        int nByte = (pWInfo->nLevel-1-i) * sizeof(WhereLevel);
        memmove(&pWInfo->a[i], &pWInfo->a[i+1], nByte);
      }
      pWInfo->nLevel--;
      nTabList--;
    }
  }
#if defined(WHERETRACE_ENABLED)
  if( sqlite3WhereTrace & 0x100 ){ /* Display all terms of the WHERE clause */
    sqlite3DebugPrintf("---- WHERE clause at end of analysis:\n");
    sqlite3WhereClausePrint(sWLB.pWC);
  }
  WHERETRACE(0xffff,("*** Optimizer Finished ***\n"));
#endif







|
|

|
|
|
|
|
|
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<







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







156363
156364
156365
156366
156367
156368
156369
156370
156371
156372
156373
156374
156375
156376
156377
156378



















156379
156380
156381
156382
156383
156384
156385
156386
156387
156388

156389










156390
156391
156392
156393
156394





156395
156396
















156397

156398
156399
156400
156401
156402
156403
156404
156405
156406
    sqlite3DebugPrintf("\n");
    for(ii=0; ii<pWInfo->nLevel; ii++){
      sqlite3WhereLoopPrint(pWInfo->a[ii].pWLoop, sWLB.pWC);
    }
  }
#endif

  /* Attempt to omit tables from a join that do not affect the result.
  ** See the comment on whereOmitNoopJoin() for further information.
  **
  ** This query optimization is factored out into a separate "no-inline"
  ** procedure to keep the sqlite3WhereBegin() procedure from becoming
  ** too large.  If sqlite3WhereBegin() becomes too large, that prevents
  ** some C-compiler optimizers from in-lining the
  ** sqlite3WhereCodeOneLoopStart() procedure, and it is important to
  ** in-line sqlite3WhereCodeOneLoopStart() for performance reasons.



















  */
  notReady = ~(Bitmask)0;
  if( pWInfo->nLevel>=2
   && pResultSet!=0                         /* these two combine to guarantee */
   && 0==(wctrlFlags & WHERE_AGG_DISTINCT)  /* condition (1) above */
   && OptimizationEnabled(db, SQLITE_OmitNoopJoin)
  ){
    notReady = whereOmitNoopJoin(pWInfo, notReady);
    nTabList = pWInfo->nLevel;
    assert( nTabList>0 );

  }











  /* Check to see if there are any SEARCH loops that might benefit from
  ** using a Bloom filter.
  */
  if( pWInfo->nLevel>=2





   && OptimizationEnabled(db, SQLITE_BloomFilter)
  ){
















    whereCheckIfBloomFilterIsUseful(pWInfo);

  }

#if defined(WHERETRACE_ENABLED)
  if( sqlite3WhereTrace & 0x100 ){ /* Display all terms of the WHERE clause */
    sqlite3DebugPrintf("---- WHERE clause at end of analysis:\n");
    sqlite3WhereClausePrint(sWLB.pWC);
  }
  WHERETRACE(0xffff,("*** Optimizer Finished ***\n"));
#endif
155230
155231
155232
155233
155234
155235
155236

155237
155238


155239
155240
155241
155242




155243
155244
155245
155246
155247
155248
155249
155250
155251
155252
  /* Generate the code to do the search.  Each iteration of the for
  ** loop below generates code for a single nested loop of the VM
  ** program.
  */
  for(ii=0; ii<nTabList; ii++){
    int addrExplain;
    int wsFlags;

    pLevel = &pWInfo->a[ii];
    wsFlags = pLevel->pWLoop->wsFlags;


#ifndef SQLITE_OMIT_AUTOMATIC_INDEX
    if( (pLevel->pWLoop->wsFlags & WHERE_AUTO_INDEX)!=0 ){
      constructAutomaticIndex(pParse, &pWInfo->sWC,
                &pTabList->a[pLevel->iFrom], notReady, pLevel);




      if( db->mallocFailed ) goto whereBeginError;
    }
#endif
    addrExplain = sqlite3WhereExplainOneScan(
        pParse, pTabList, pLevel, wctrlFlags
    );
    pLevel->addrBody = sqlite3VdbeCurrentAddr(v);
    notReady = sqlite3WhereCodeOneLoopStart(pParse,v,pWInfo,ii,pLevel,notReady);
    pWInfo->iContinue = pLevel->addrCont;
    if( (wsFlags&WHERE_MULTI_OR)==0 && (wctrlFlags&WHERE_OR_SUBCLAUSE)==0 ){







>


>
>

<
|
|
>
>
>
>


<







156578
156579
156580
156581
156582
156583
156584
156585
156586
156587
156588
156589
156590

156591
156592
156593
156594
156595
156596
156597
156598

156599
156600
156601
156602
156603
156604
156605
  /* Generate the code to do the search.  Each iteration of the for
  ** loop below generates code for a single nested loop of the VM
  ** program.
  */
  for(ii=0; ii<nTabList; ii++){
    int addrExplain;
    int wsFlags;
    if( pParse->nErr ) goto whereBeginError;
    pLevel = &pWInfo->a[ii];
    wsFlags = pLevel->pWLoop->wsFlags;
    if( (wsFlags & (WHERE_AUTO_INDEX|WHERE_BLOOMFILTER))!=0 ){
      if( (wsFlags & WHERE_AUTO_INDEX)!=0 ){
#ifndef SQLITE_OMIT_AUTOMATIC_INDEX

        constructAutomaticIndex(pParse, &pWInfo->sWC,
                  &pTabList->a[pLevel->iFrom], notReady, pLevel);
#endif
      }else{
        constructBloomFilter(pWInfo, ii, pLevel, notReady);
      }
      if( db->mallocFailed ) goto whereBeginError;
    }

    addrExplain = sqlite3WhereExplainOneScan(
        pParse, pTabList, pLevel, wctrlFlags
    );
    pLevel->addrBody = sqlite3VdbeCurrentAddr(v);
    notReady = sqlite3WhereCodeOneLoopStart(pParse,v,pWInfo,ii,pLevel,notReady);
    pWInfo->iContinue = pLevel->addrCont;
    if( (wsFlags&WHERE_MULTI_OR)==0 && (wctrlFlags&WHERE_OR_SUBCLAUSE)==0 ){
155351
155352
155353
155354
155355
155356
155357
155358
155359
155360
155361
155362
155363
155364
155365
      }
#ifndef SQLITE_DISABLE_SKIPAHEAD_DISTINCT
      if( addrSeek ) sqlite3VdbeJumpHere(v, addrSeek);
#endif
    }else{
      sqlite3VdbeResolveLabel(v, pLevel->addrCont);
    }
    if( pLoop->wsFlags & WHERE_IN_ABLE && pLevel->u.in.nIn>0 ){
      struct InLoop *pIn;
      int j;
      sqlite3VdbeResolveLabel(v, pLevel->addrNxt);
      for(j=pLevel->u.in.nIn, pIn=&pLevel->u.in.aInLoop[j-1]; j>0; j--, pIn--){
        assert( sqlite3VdbeGetOp(v, pIn->addrInTop+1)->opcode==OP_IsNull
                 || pParse->db->mallocFailed );
        sqlite3VdbeJumpHere(v, pIn->addrInTop+1);







|







156704
156705
156706
156707
156708
156709
156710
156711
156712
156713
156714
156715
156716
156717
156718
      }
#ifndef SQLITE_DISABLE_SKIPAHEAD_DISTINCT
      if( addrSeek ) sqlite3VdbeJumpHere(v, addrSeek);
#endif
    }else{
      sqlite3VdbeResolveLabel(v, pLevel->addrCont);
    }
    if( (pLoop->wsFlags & WHERE_IN_ABLE)!=0 && pLevel->u.in.nIn>0 ){
      struct InLoop *pIn;
      int j;
      sqlite3VdbeResolveLabel(v, pLevel->addrNxt);
      for(j=pLevel->u.in.nIn, pIn=&pLevel->u.in.aInLoop[j-1]; j>0; j--, pIn--){
        assert( sqlite3VdbeGetOp(v, pIn->addrInTop+1)->opcode==OP_IsNull
                 || pParse->db->mallocFailed );
        sqlite3VdbeJumpHere(v, pIn->addrInTop+1);
155420
155421
155422
155423
155424
155425
155426
155427
155428
155429
155430
155431
155432
155433
155434
155435
155436
155437
      addr = sqlite3VdbeAddOp1(v, OP_IfPos, pLevel->iLeftJoin); VdbeCoverage(v);
      assert( (ws & WHERE_IDX_ONLY)==0 || (ws & WHERE_INDEXED)!=0 );
      if( (ws & WHERE_IDX_ONLY)==0 ){
        assert( pLevel->iTabCur==pTabList->a[pLevel->iFrom].iCursor );
        sqlite3VdbeAddOp1(v, OP_NullRow, pLevel->iTabCur);
      }
      if( (ws & WHERE_INDEXED)
       || ((ws & WHERE_MULTI_OR) && pLevel->u.pCovidx)
      ){
        if( ws & WHERE_MULTI_OR ){
          Index *pIx = pLevel->u.pCovidx;
          int iDb = sqlite3SchemaToIndex(db, pIx->pSchema);
          sqlite3VdbeAddOp3(v, OP_ReopenIdx, pLevel->iIdxCur, pIx->tnum, iDb);
          sqlite3VdbeSetP4KeyInfo(pParse, pIx);
        }
        sqlite3VdbeAddOp1(v, OP_NullRow, pLevel->iIdxCur);
      }
      if( pLevel->op==OP_Return ){







|


|







156773
156774
156775
156776
156777
156778
156779
156780
156781
156782
156783
156784
156785
156786
156787
156788
156789
156790
      addr = sqlite3VdbeAddOp1(v, OP_IfPos, pLevel->iLeftJoin); VdbeCoverage(v);
      assert( (ws & WHERE_IDX_ONLY)==0 || (ws & WHERE_INDEXED)!=0 );
      if( (ws & WHERE_IDX_ONLY)==0 ){
        assert( pLevel->iTabCur==pTabList->a[pLevel->iFrom].iCursor );
        sqlite3VdbeAddOp1(v, OP_NullRow, pLevel->iTabCur);
      }
      if( (ws & WHERE_INDEXED)
       || ((ws & WHERE_MULTI_OR) && pLevel->u.pCoveringIdx)
      ){
        if( ws & WHERE_MULTI_OR ){
          Index *pIx = pLevel->u.pCoveringIdx;
          int iDb = sqlite3SchemaToIndex(db, pIx->pSchema);
          sqlite3VdbeAddOp3(v, OP_ReopenIdx, pLevel->iIdxCur, pIx->tnum, iDb);
          sqlite3VdbeSetP4KeyInfo(pParse, pIx);
        }
        sqlite3VdbeAddOp1(v, OP_NullRow, pLevel->iIdxCur);
      }
      if( pLevel->op==OP_Return ){
155504
155505
155506
155507
155508
155509
155510
155511
155512
155513
155514
155515
155516
155517
155518
    ** directly.  This loop scans all that code looking for opcodes
    ** that reference the table and converts them into opcodes that
    ** reference the index.
    */
    if( pLoop->wsFlags & (WHERE_INDEXED|WHERE_IDX_ONLY) ){
      pIdx = pLoop->u.btree.pIndex;
    }else if( pLoop->wsFlags & WHERE_MULTI_OR ){
      pIdx = pLevel->u.pCovidx;
    }
    if( pIdx
     && !db->mallocFailed
    ){
      if( pWInfo->eOnePass==ONEPASS_OFF || !HasRowid(pIdx->pTable) ){
        last = iEnd;
      }else{







|







156857
156858
156859
156860
156861
156862
156863
156864
156865
156866
156867
156868
156869
156870
156871
    ** directly.  This loop scans all that code looking for opcodes
    ** that reference the table and converts them into opcodes that
    ** reference the index.
    */
    if( pLoop->wsFlags & (WHERE_INDEXED|WHERE_IDX_ONLY) ){
      pIdx = pLoop->u.btree.pIndex;
    }else if( pLoop->wsFlags & WHERE_MULTI_OR ){
      pIdx = pLevel->u.pCoveringIdx;
    }
    if( pIdx
     && !db->mallocFailed
    ){
      if( pWInfo->eOnePass==ONEPASS_OFF || !HasRowid(pIdx->pTable) ){
        last = iEnd;
      }else{
156165
156166
156167
156168
156169
156170
156171
156172
156173
156174
156175
156176
156177
156178
156179
156180
156181
156182
156183
156184
156185
156186
156187
156188
156189
156190
156191
156192
156193
156194
156195
156196
  assert(0);                 /*NO_TEST*/
}                            /*NO_TEST*/
static void noopValueFunc(sqlite3_context *p){ UNUSED_PARAMETER(p); /*no-op*/ }

/* Window functions that use all window interfaces: xStep, xFinal,
** xValue, and xInverse */
#define WINDOWFUNCALL(name,nArg,extra) {                                   \
  nArg, (SQLITE_UTF8|SQLITE_FUNC_WINDOW|extra), 0, 0,                      \
  name ## StepFunc, name ## FinalizeFunc, name ## ValueFunc,               \
  name ## InvFunc, name ## Name, {0}                                       \
}

/* Window functions that are implemented using bytecode and thus have
** no-op routines for their methods */
#define WINDOWFUNCNOOP(name,nArg,extra) {                                  \
  nArg, (SQLITE_UTF8|SQLITE_FUNC_WINDOW|extra), 0, 0,                      \
  noopStepFunc, noopValueFunc, noopValueFunc,                              \
  noopStepFunc, name ## Name, {0}                                          \
}

/* Window functions that use all window interfaces: xStep, the
** same routine for xFinalize and xValue and which never call
** xInverse. */
#define WINDOWFUNCX(name,nArg,extra) {                                     \
  nArg, (SQLITE_UTF8|SQLITE_FUNC_WINDOW|extra), 0, 0,                      \
  name ## StepFunc, name ## ValueFunc, name ## ValueFunc,                  \
  noopStepFunc, name ## Name, {0}                                          \
}


/*
** Register those built-in window functions that are not also aggregates.







|







|








|







157518
157519
157520
157521
157522
157523
157524
157525
157526
157527
157528
157529
157530
157531
157532
157533
157534
157535
157536
157537
157538
157539
157540
157541
157542
157543
157544
157545
157546
157547
157548
157549
  assert(0);                 /*NO_TEST*/
}                            /*NO_TEST*/
static void noopValueFunc(sqlite3_context *p){ UNUSED_PARAMETER(p); /*no-op*/ }

/* Window functions that use all window interfaces: xStep, xFinal,
** xValue, and xInverse */
#define WINDOWFUNCALL(name,nArg,extra) {                                   \
  nArg, (SQLITE_FUNC_BUILTIN|SQLITE_UTF8|SQLITE_FUNC_WINDOW|extra), 0, 0,  \
  name ## StepFunc, name ## FinalizeFunc, name ## ValueFunc,               \
  name ## InvFunc, name ## Name, {0}                                       \
}

/* Window functions that are implemented using bytecode and thus have
** no-op routines for their methods */
#define WINDOWFUNCNOOP(name,nArg,extra) {                                  \
  nArg, (SQLITE_FUNC_BUILTIN|SQLITE_UTF8|SQLITE_FUNC_WINDOW|extra), 0, 0,  \
  noopStepFunc, noopValueFunc, noopValueFunc,                              \
  noopStepFunc, name ## Name, {0}                                          \
}

/* Window functions that use all window interfaces: xStep, the
** same routine for xFinalize and xValue and which never call
** xInverse. */
#define WINDOWFUNCX(name,nArg,extra) {                                     \
  nArg, (SQLITE_FUNC_BUILTIN|SQLITE_UTF8|SQLITE_FUNC_WINDOW|extra), 0, 0,  \
  name ## StepFunc, name ## ValueFunc, name ## ValueFunc,                  \
  noopStepFunc, name ## Name, {0}                                          \
}


/*
** Register those built-in window functions that are not also aggregates.
156525
156526
156527
156528
156529
156530
156531

156532
156533
156534
156535
156536
156537
156538
156539
    pExpr->op2++;
  }
  return WRC_Continue;
}

static int disallowAggregatesInOrderByCb(Walker *pWalker, Expr *pExpr){
  if( pExpr->op==TK_AGG_FUNCTION && pExpr->pAggInfo==0 ){

    sqlite3ErrorMsg(pWalker->pParse,
         "misuse of aggregate: %s()", pExpr->u.zToken);
  }
  return WRC_Continue;
}

/*
** If the SELECT statement passed as the second argument does not invoke







>
|







157878
157879
157880
157881
157882
157883
157884
157885
157886
157887
157888
157889
157890
157891
157892
157893
    pExpr->op2++;
  }
  return WRC_Continue;
}

static int disallowAggregatesInOrderByCb(Walker *pWalker, Expr *pExpr){
  if( pExpr->op==TK_AGG_FUNCTION && pExpr->pAggInfo==0 ){
    assert( !ExprHasProperty(pExpr, EP_IntValue) );
     sqlite3ErrorMsg(pWalker->pParse,
         "misuse of aggregate: %s()", pExpr->u.zToken);
  }
  return WRC_Continue;
}

/*
** If the SELECT statement passed as the second argument does not invoke
156613
156614
156615
156616
156617
156618
156619


156620
156621
156622
156623
156624
156625
156626
156627
    pSublist = exprListAppendList(pParse, pSublist, pMWin->pOrderBy, 0);

    /* Append the arguments passed to each window function to the
    ** sub-select expression list. Also allocate two registers for each
    ** window function - one for the accumulator, another for interim
    ** results.  */
    for(pWin=pMWin; pWin; pWin=pWin->pNextWin){


      ExprList *pArgs = pWin->pOwner->x.pList;
      if( pWin->pFunc->funcFlags & SQLITE_FUNC_SUBTYPE ){
        selectWindowRewriteEList(pParse, pMWin, pSrc, pArgs, pTab, &pSublist);
        pWin->iArgCol = (pSublist ? pSublist->nExpr : 0);
        pWin->bExprArgs = 1;
      }else{
        pWin->iArgCol = (pSublist ? pSublist->nExpr : 0);
        pSublist = exprListAppendList(pParse, pSublist, pArgs, 0);







>
>
|







157967
157968
157969
157970
157971
157972
157973
157974
157975
157976
157977
157978
157979
157980
157981
157982
157983
    pSublist = exprListAppendList(pParse, pSublist, pMWin->pOrderBy, 0);

    /* Append the arguments passed to each window function to the
    ** sub-select expression list. Also allocate two registers for each
    ** window function - one for the accumulator, another for interim
    ** results.  */
    for(pWin=pMWin; pWin; pWin=pWin->pNextWin){
      ExprList *pArgs;
      assert( ExprUseXList(pWin->pOwner) );
      pArgs = pWin->pOwner->x.pList;
      if( pWin->pFunc->funcFlags & SQLITE_FUNC_SUBTYPE ){
        selectWindowRewriteEList(pParse, pMWin, pSrc, pArgs, pTab, &pSublist);
        pWin->iArgCol = (pSublist ? pSublist->nExpr : 0);
        pWin->bExprArgs = 1;
      }else{
        pWin->iArgCol = (pSublist ? pSublist->nExpr : 0);
        pSublist = exprListAppendList(pParse, pSublist, pArgs, 0);
156680
156681
156682
156683
156684
156685
156686
156687




156688
156689
156690
156691
156692
156693
156694
        w.xSelectCallback2 = sqlite3WalkerDepthDecrease;
        sqlite3WalkSelect(&w, pSub);
      }
    }else{
      sqlite3SelectDelete(db, pSub);
    }
    if( db->mallocFailed ) rc = SQLITE_NOMEM;
    sqlite3DbFree(db, pTab);




  }

  if( rc ){
    if( pParse->nErr==0 ){
      assert( pParse->db->mallocFailed );
      sqlite3ErrorToParser(pParse->db, SQLITE_NOMEM);
    }







|
>
>
>
>







158036
158037
158038
158039
158040
158041
158042
158043
158044
158045
158046
158047
158048
158049
158050
158051
158052
158053
158054
        w.xSelectCallback2 = sqlite3WalkerDepthDecrease;
        sqlite3WalkSelect(&w, pSub);
      }
    }else{
      sqlite3SelectDelete(db, pSub);
    }
    if( db->mallocFailed ) rc = SQLITE_NOMEM;

    /* Defer deleting the temporary table pTab because if an error occurred,
    ** there could still be references to that table embedded in the
    ** result-set or ORDER BY clause of the SELECT statement p.  */
    sqlite3ParserAddCleanup(pParse, sqlite3DbFree, pTab);
  }

  if( rc ){
    if( pParse->nErr==0 ){
      assert( pParse->db->mallocFailed );
      sqlite3ErrorToParser(pParse->db, SQLITE_NOMEM);
    }
157006
157007
157008
157009
157010
157011
157012



157013
157014
157015
157016
157017
157018
157019
157020
157021
      /* The inline versions of min() and max() require a single ephemeral
      ** table and 3 registers. The registers are used as follows:
      **
      **   regApp+0: slot to copy min()/max() argument to for MakeRecord
      **   regApp+1: integer value used to ensure keys are unique
      **   regApp+2: output of MakeRecord
      */



      ExprList *pList = pWin->pOwner->x.pList;
      KeyInfo *pKeyInfo = sqlite3KeyInfoFromExprList(pParse, pList, 0, 0);
      pWin->csrApp = pParse->nTab++;
      pWin->regApp = pParse->nMem+1;
      pParse->nMem += 3;
      if( pKeyInfo && pWin->pFunc->zName[1]=='i' ){
        assert( pKeyInfo->aSortFlags[0]==0 );
        pKeyInfo->aSortFlags[0] = KEYINFO_ORDER_DESC;
      }







>
>
>
|
|







158366
158367
158368
158369
158370
158371
158372
158373
158374
158375
158376
158377
158378
158379
158380
158381
158382
158383
158384
      /* The inline versions of min() and max() require a single ephemeral
      ** table and 3 registers. The registers are used as follows:
      **
      **   regApp+0: slot to copy min()/max() argument to for MakeRecord
      **   regApp+1: integer value used to ensure keys are unique
      **   regApp+2: output of MakeRecord
      */
      ExprList *pList;
      KeyInfo *pKeyInfo;
      assert( ExprUseXList(pWin->pOwner) );
      pList = pWin->pOwner->x.pList;
      pKeyInfo = sqlite3KeyInfoFromExprList(pParse, pList, 0, 0);
      pWin->csrApp = pParse->nTab++;
      pWin->regApp = pParse->nMem+1;
      pParse->nMem += 3;
      if( pKeyInfo && pWin->pFunc->zName[1]=='i' ){
        assert( pKeyInfo->aSortFlags[0]==0 );
        pKeyInfo->aSortFlags[0] = KEYINFO_ORDER_DESC;
      }
157095
157096
157097
157098
157099
157100
157101


157102
157103
157104
157105
157106
157107
157108
157109
}

/*
** Return the number of arguments passed to the window-function associated
** with the object passed as the only argument to this function.
*/
static int windowArgCount(Window *pWin){


  ExprList *pList = pWin->pOwner->x.pList;
  return (pList ? pList->nExpr : 0);
}

typedef struct WindowCodeArg WindowCodeArg;
typedef struct WindowCsrAndReg WindowCsrAndReg;

/*







>
>
|







158458
158459
158460
158461
158462
158463
158464
158465
158466
158467
158468
158469
158470
158471
158472
158473
158474
}

/*
** Return the number of arguments passed to the window-function associated
** with the object passed as the only argument to this function.
*/
static int windowArgCount(Window *pWin){
  const ExprList *pList;
  assert( ExprUseXList(pWin->pOwner) );
  pList = pWin->pOwner->x.pList;
  return (pList ? pList->nExpr : 0);
}

typedef struct WindowCodeArg WindowCodeArg;
typedef struct WindowCsrAndReg WindowCsrAndReg;

/*
157280
157281
157282
157283
157284
157285
157286

157287
157288
157289
157290
157291
157292
157293
157294
157295
157296
157297
157298
157299

157300
157301
157302
157303
157304
157305
157306
157307
157308
157309
157310
157311
157312
157313

157314
157315
157316
157317
157318
157319
157320
      );
      assert( bInverse==0 || bInverse==1 );
      sqlite3VdbeAddOp2(v, OP_AddImm, pWin->regApp+1-bInverse, 1);
    }else if( pFunc->xSFunc!=noopStepFunc ){
      int addrIf = 0;
      if( pWin->pFilter ){
        int regTmp;

        assert( pWin->bExprArgs || !nArg ||nArg==pWin->pOwner->x.pList->nExpr );
        assert( pWin->bExprArgs || nArg  ||pWin->pOwner->x.pList==0 );
        regTmp = sqlite3GetTempReg(pParse);
        sqlite3VdbeAddOp3(v, OP_Column, csr, pWin->iArgCol+nArg,regTmp);
        addrIf = sqlite3VdbeAddOp3(v, OP_IfNot, regTmp, 0, 1);
        VdbeCoverage(v);
        sqlite3ReleaseTempReg(pParse, regTmp);
      }

      if( pWin->bExprArgs ){
        int iOp = sqlite3VdbeCurrentAddr(v);
        int iEnd;


        nArg = pWin->pOwner->x.pList->nExpr;
        regArg = sqlite3GetTempRange(pParse, nArg);
        sqlite3ExprCodeExprList(pParse, pWin->pOwner->x.pList, regArg, 0, 0);

        for(iEnd=sqlite3VdbeCurrentAddr(v); iOp<iEnd; iOp++){
          VdbeOp *pOp = sqlite3VdbeGetOp(v, iOp);
          if( pOp->opcode==OP_Column && pOp->p1==pWin->iEphCsr ){
            pOp->p1 = csr;
          }
        }
      }
      if( pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL ){
        CollSeq *pColl;
        assert( nArg>0 );

        pColl = sqlite3ExprNNCollSeq(pParse, pWin->pOwner->x.pList->a[0].pExpr);
        sqlite3VdbeAddOp4(v, OP_CollSeq, 0,0,0, (const char*)pColl, P4_COLLSEQ);
      }
      sqlite3VdbeAddOp3(v, bInverse? OP_AggInverse : OP_AggStep,
                        bInverse, regArg, pWin->regAccum);
      sqlite3VdbeAppendP4(v, pFunc, P4_FUNCDEF);
      sqlite3VdbeChangeP5(v, (u8)nArg);







>













>














>







158645
158646
158647
158648
158649
158650
158651
158652
158653
158654
158655
158656
158657
158658
158659
158660
158661
158662
158663
158664
158665
158666
158667
158668
158669
158670
158671
158672
158673
158674
158675
158676
158677
158678
158679
158680
158681
158682
158683
158684
158685
158686
158687
158688
      );
      assert( bInverse==0 || bInverse==1 );
      sqlite3VdbeAddOp2(v, OP_AddImm, pWin->regApp+1-bInverse, 1);
    }else if( pFunc->xSFunc!=noopStepFunc ){
      int addrIf = 0;
      if( pWin->pFilter ){
        int regTmp;
        assert( ExprUseXList(pWin->pOwner) );
        assert( pWin->bExprArgs || !nArg ||nArg==pWin->pOwner->x.pList->nExpr );
        assert( pWin->bExprArgs || nArg  ||pWin->pOwner->x.pList==0 );
        regTmp = sqlite3GetTempReg(pParse);
        sqlite3VdbeAddOp3(v, OP_Column, csr, pWin->iArgCol+nArg,regTmp);
        addrIf = sqlite3VdbeAddOp3(v, OP_IfNot, regTmp, 0, 1);
        VdbeCoverage(v);
        sqlite3ReleaseTempReg(pParse, regTmp);
      }

      if( pWin->bExprArgs ){
        int iOp = sqlite3VdbeCurrentAddr(v);
        int iEnd;

        assert( ExprUseXList(pWin->pOwner) );
        nArg = pWin->pOwner->x.pList->nExpr;
        regArg = sqlite3GetTempRange(pParse, nArg);
        sqlite3ExprCodeExprList(pParse, pWin->pOwner->x.pList, regArg, 0, 0);

        for(iEnd=sqlite3VdbeCurrentAddr(v); iOp<iEnd; iOp++){
          VdbeOp *pOp = sqlite3VdbeGetOp(v, iOp);
          if( pOp->opcode==OP_Column && pOp->p1==pWin->iEphCsr ){
            pOp->p1 = csr;
          }
        }
      }
      if( pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL ){
        CollSeq *pColl;
        assert( nArg>0 );
        assert( ExprUseXList(pWin->pOwner) );
        pColl = sqlite3ExprNNCollSeq(pParse, pWin->pOwner->x.pList->a[0].pExpr);
        sqlite3VdbeAddOp4(v, OP_CollSeq, 0,0,0, (const char*)pColl, P4_COLLSEQ);
      }
      sqlite3VdbeAddOp3(v, bInverse? OP_AggInverse : OP_AggStep,
                        bInverse, regArg, pWin->regAccum);
      sqlite3VdbeAppendP4(v, pFunc, P4_FUNCDEF);
      sqlite3VdbeChangeP5(v, (u8)nArg);
157492
157493
157494
157495
157496
157497
157498

157499
157500
157501
157502
157503
157504
157505
    windowFullScan(p);
  }else{
    Parse *pParse = p->pParse;
    Window *pWin;

    for(pWin=pMWin; pWin; pWin=pWin->pNextWin){
      FuncDef *pFunc = pWin->pFunc;

      if( pFunc->zName==nth_valueName
       || pFunc->zName==first_valueName
      ){
        int csr = pWin->csrApp;
        int lbl = sqlite3VdbeMakeLabel(pParse);
        int tmpReg = sqlite3GetTempReg(pParse);
        sqlite3VdbeAddOp2(v, OP_Null, 0, pWin->regResult);







>







158860
158861
158862
158863
158864
158865
158866
158867
158868
158869
158870
158871
158872
158873
158874
    windowFullScan(p);
  }else{
    Parse *pParse = p->pParse;
    Window *pWin;

    for(pWin=pMWin; pWin; pWin=pWin->pNextWin){
      FuncDef *pFunc = pWin->pFunc;
      assert( ExprUseXList(pWin->pOwner) );
      if( pFunc->zName==nth_valueName
       || pFunc->zName==first_valueName
      ){
        int csr = pWin->csrApp;
        int lbl = sqlite3VdbeMakeLabel(pParse);
        int tmpReg = sqlite3GetTempReg(pParse);
        sqlite3VdbeAddOp2(v, OP_Null, 0, pWin->regResult);
158841
158842
158843
158844
158845
158846
158847
158848
158849

158850
158851
158852
158853
158854
158855
158856
158857
      /* memset(p, 0, sizeof(Expr)); */
      p->op = (u8)op;
      p->affExpr = 0;
      p->flags = EP_Leaf;
      ExprClearVVAProperties(p);
      p->iAgg = -1;
      p->pLeft = p->pRight = 0;
      p->x.pList = 0;
      p->pAggInfo = 0;

      p->y.pTab = 0;
      p->op2 = 0;
      p->iTable = 0;
      p->iColumn = 0;
      p->u.zToken = (char*)&p[1];
      memcpy(p->u.zToken, t.z, t.n);
      p->u.zToken[t.n] = 0;
      if( sqlite3Isquote(p->u.zToken[0]) ){







<

>
|







160210
160211
160212
160213
160214
160215
160216

160217
160218
160219
160220
160221
160222
160223
160224
160225
160226
      /* memset(p, 0, sizeof(Expr)); */
      p->op = (u8)op;
      p->affExpr = 0;
      p->flags = EP_Leaf;
      ExprClearVVAProperties(p);
      p->iAgg = -1;
      p->pLeft = p->pRight = 0;

      p->pAggInfo = 0;
      memset(&p->x, 0, sizeof(p->x));
      memset(&p->y, 0, sizeof(p->y));
      p->op2 = 0;
      p->iTable = 0;
      p->iColumn = 0;
      p->u.zToken = (char*)&p[1];
      memcpy(p->u.zToken, t.z, t.n);
      p->u.zToken[t.n] = 0;
      if( sqlite3Isquote(p->u.zToken[0]) ){
158949
158950
158951
158952
158953
158954
158955
158956
158957
158958
158959

158960
158961
158962
158963
158964
158965
158966
#define TK_DATABASE                       38
#define TK_DESC                           39
#define TK_DETACH                         40
#define TK_EACH                           41
#define TK_FAIL                           42
#define TK_OR                             43
#define TK_AND                            44
#define TK_IS                             45
#define TK_MATCH                          46
#define TK_LIKE_KW                        47
#define TK_BETWEEN                        48

#define TK_IN                             49
#define TK_ISNULL                         50
#define TK_NOTNULL                        51
#define TK_NE                             52
#define TK_EQ                             53
#define TK_GT                             54
#define TK_LE                             55







<
|
|
|
>







160318
160319
160320
160321
160322
160323
160324

160325
160326
160327
160328
160329
160330
160331
160332
160333
160334
160335
#define TK_DATABASE                       38
#define TK_DESC                           39
#define TK_DETACH                         40
#define TK_EACH                           41
#define TK_FAIL                           42
#define TK_OR                             43
#define TK_AND                            44

#define TK_MATCH                          45
#define TK_LIKE_KW                        46
#define TK_BETWEEN                        47
#define TK_IS                             48
#define TK_IN                             49
#define TK_ISNULL                         50
#define TK_NOTNULL                        51
#define TK_NE                             52
#define TK_EQ                             53
#define TK_GT                             54
#define TK_LE                             55
159264
159265
159266
159267
159268
159269
159270
159271
159272
159273
159274
159275
159276
159277
159278
159279
159280
159281
159282
159283
159284
159285
159286
159287
159288
159289
159290
159291
159292
159293
159294
159295
159296
159297
159298
159299
159300
159301
159302
159303
159304
159305
159306
159307
159308
159309
159310
159311
159312
159313
159314
159315
159316
159317
159318
159319
159320
159321
159322
159323
159324
159325
159326
159327
159328
159329
159330
159331
159332
159333
159334
159335
159336
159337
159338
159339
159340
159341
159342
159343
159344
159345
159346
159347
159348
159349
159350
159351
159352
159353
159354
159355
159356
159357
159358
159359
159360
159361
159362
159363
159364
159365
159366
159367
159368
159369
159370
159371
159372
159373
159374
159375
159376
159377
159378
159379
159380
159381
159382
159383
159384
159385
159386
159387
159388
159389
159390
159391
159392
159393
159394
159395
159396
159397
159398
159399
159400
159401
159402
159403
159404
159405
159406
159407
159408
159409
159410
159411
159412
159413
159414
159415
159416
159417
159418
159419
159420
159421
159422
159423
159424
159425
159426
159427
159428
159429
159430
159431
159432
159433
159434
159435
159436
159437
159438
159439
159440
159441
159442
159443
159444
159445
159446
159447
159448
159449
159450
159451
159452
159453
159454
159455
159456
159457
159458
159459
159460
159461
159462
159463
159464
159465
159466
159467
159468
159469
159470
159471
159472
159473
159474
159475
159476
159477
159478
159479
159480
159481
159482
159483
159484
159485
159486
159487
159488
159489
159490
159491
159492
159493
159494
159495
159496
159497
159498
159499
159500
159501
159502
159503
159504
159505
159506
159507
159508
159509
159510
159511
159512
159513
159514
159515
159516
159517
159518
159519
159520
159521
159522
159523
159524
159525
159526
159527
159528
159529
159530
159531
159532
159533
159534
159535
159536
159537
159538
159539
159540
159541
159542
159543
159544
159545
159546
159547
159548
159549
159550
159551
159552
159553
159554
159555
159556
159557
159558
159559
159560
159561
159562
159563
159564
159565
159566
159567
159568
159569
159570
159571
159572
159573
159574
159575
159576
159577
159578
159579
159580
159581
159582
159583
159584
159585
159586
159587
159588
159589
159590
159591
159592
159593
159594
159595
159596
159597
159598
159599
159600
159601
159602
159603
159604
159605
159606
159607
159608
159609
159610
159611
159612
159613
159614
159615
159616
159617
159618
159619
159620
159621
159622
159623
159624
159625
159626
159627
159628
159629
159630
159631
159632
159633
159634
159635
159636
159637
159638
159639
159640
159641
159642
159643
159644
159645
159646
159647

159648
159649
159650
159651
159652
159653
159654
159655
159656
159657
159658
159659
159660
159661
159662
159663
159664
159665
159666
159667
159668
159669
159670
159671
159672
159673
159674
159675
159676
159677
159678
159679
159680
159681
159682
159683
159684
159685
159686
159687
159688
159689
159690
159691
159692
159693
159694
159695
159696
159697
159698
159699
159700
159701
159702
159703
159704
159705
159706
159707
159708
159709
159710
159711
159712
159713
159714
159715
159716
159717
159718
159719
159720
159721
159722
159723
159724
159725
159726
159727
159728
159729
159730
159731
159732
159733
159734
159735
159736
159737
159738
159739
159740
159741
159742
159743
159744
159745
159746
159747
159748
159749
159750
159751
159752
159753
159754
159755
159756
159757
159758
159759
159760
159761
159762
159763
159764
159765
159766
159767
159768
159769
159770
159771
159772
159773
159774
159775
159776
159777
159778
159779
159780
159781
159782
159783
159784
159785
159786
159787
159788
159789
159790
159791
159792
159793
159794
159795
159796
159797
159798
159799
159800
159801
159802
159803
159804
159805
159806
159807
159808
159809
159810
159811
159812
159813
159814
159815
159816
159817
**  yy_shift_ofst[]    For each state, the offset into yy_action for
**                     shifting terminals.
**  yy_reduce_ofst[]   For each state, the offset into yy_action for
**                     shifting non-terminals after a reduce.
**  yy_default[]       Default action for each state.
**
*********** Begin parsing tables **********************************************/
#define YY_ACTTAB_COUNT (2037)
static const YYACTIONTYPE yy_action[] = {
 /*     0 */   564,  115,  112,  220,  169,  199,  115,  112,  220,  564,
 /*    10 */   375, 1266,  564,  376,  564,  270, 1309, 1309,  406,  407,
 /*    20 */  1084,  199, 1513,   41,   41,  515,  489,  521,  558,  558,
 /*    30 */   558,  965,   41,   41,  395,   41,   41,   51,   51,  966,
 /*    40 */   296, 1269,  296,  122,  123,  113, 1207, 1207, 1041, 1044,
 /*    50 */  1034, 1034,  120,  120,  121,  121,  121,  121,  564,  407,
 /*    60 */   275,  275,  275,  275, 1268,  115,  112,  220,  115,  112,
 /*    70 */   220, 1512,  846,  561,  516,  561,  115,  112,  220,  250,
 /*    80 */   217,   71,   71,  122,  123,  113, 1207, 1207, 1041, 1044,
 /*    90 */  1034, 1034,  120,  120,  121,  121,  121,  121,  440,  440,
 /*   100 */   440, 1149,  119,  119,  119,  119,  118,  118,  117,  117,
 /*   110 */   117,  116,  442, 1183, 1149,  116,  442, 1149,  546,  513,
 /*   120 */  1548, 1554,  374,  442,    6, 1183, 1154,  522, 1154,  407,
 /*   130 */  1556,  461,  373, 1554,  535,   99,  463,  332,  121,  121,
 /*   140 */   121,  121,  119,  119,  119,  119,  118,  118,  117,  117,
 /*   150 */   117,  116,  442,  122,  123,  113, 1207, 1207, 1041, 1044,
 /*   160 */  1034, 1034,  120,  120,  121,  121,  121,  121, 1257, 1183,
 /*   170 */  1184, 1185,  243, 1064,  564,  502,  499,  498,  567,  124,
 /*   180 */   567, 1183, 1184, 1185,  474,  497,  119,  119,  119,  119,
 /*   190 */   118,  118,  117,  117,  117,  116,  442,   70,   70,  407,
 /*   200 */   121,  121,  121,  121,  114,  117,  117,  117,  116,  442,
 /*   210 */  1409, 1469,  119,  119,  119,  119,  118,  118,  117,  117,
 /*   220 */   117,  116,  442,  122,  123,  113, 1207, 1207, 1041, 1044,
 /*   230 */  1034, 1034,  120,  120,  121,  121,  121,  121,  407, 1031,
 /*   240 */  1031, 1042, 1045,   81,  382,  541,  378,   80,  119,  119,
 /*   250 */   119,  119,  118,  118,  117,  117,  117,  116,  442,  381,
 /*   260 */   463,  332,  122,  123,  113, 1207, 1207, 1041, 1044, 1034,
 /*   270 */  1034,  120,  120,  121,  121,  121,  121,  262,  215,  512,
 /*   280 */  1424,  422,  119,  119,  119,  119,  118,  118,  117,  117,
 /*   290 */   117,  116,  442, 1231,    1,    1,  571,    2, 1235, 1573,
 /*   300 */   571,    2, 1235,  307, 1149,  141, 1600,  307,  407,  141,
 /*   310 */  1183,  361, 1317, 1035,  866,  531, 1317, 1149,  359, 1567,
 /*   320 */  1149,  119,  119,  119,  119,  118,  118,  117,  117,  117,
 /*   330 */   116,  442,  122,  123,  113, 1207, 1207, 1041, 1044, 1034,
 /*   340 */  1034,  120,  120,  121,  121,  121,  121,  275,  275, 1001,
 /*   350 */   426,  275,  275, 1128, 1627, 1021, 1627,  137,  542, 1541,
 /*   360 */   561,  272,  950,  950,  561, 1423, 1183, 1184, 1185, 1594,
 /*   370 */   866, 1012,  530,  315,  231, 1011,  468, 1276,  231,  119,
 /*   380 */   119,  119,  119,  118,  118,  117,  117,  117,  116,  442,
 /*   390 */  1570,  119,  119,  119,  119,  118,  118,  117,  117,  117,
 /*   400 */   116,  442,  330,  359, 1567,  564,  446, 1011, 1011, 1013,
 /*   410 */   446,  207,  564,  306,  555,  407,  363, 1021,  363,  346,
 /*   420 */   184,  118,  118,  117,  117,  117,  116,  442,   71,   71,
 /*   430 */   439,  438, 1126, 1012,  472,   71,   71, 1011,  205,  122,
 /*   440 */   123,  113, 1207, 1207, 1041, 1044, 1034, 1034,  120,  120,
 /*   450 */   121,  121,  121,  121,  219,  219,  472, 1183,  407,  570,
 /*   460 */  1183, 1235,  503, 1477,  149,  546,  307,  489,  141, 1011,
 /*   470 */  1011, 1013,  546,  140,  545, 1317, 1214,  191, 1214,  950,
 /*   480 */   950,  514,  122,  123,  113, 1207, 1207, 1041, 1044, 1034,
 /*   490 */  1034,  120,  120,  121,  121,  121,  121,  563,  119,  119,
 /*   500 */   119,  119,  118,  118,  117,  117,  117,  116,  442,  283,
 /*   510 */   275,  275,  415, 1183, 1184, 1185, 1183, 1184, 1185,  372,
 /*   520 */  1183,  243,  344,  561,  502,  499,  498, 1539,  407, 1540,
 /*   530 */  1183,  288,  870,  143,  497, 1549,  185,  231,    9,    6,
 /*   540 */   253,  119,  119,  119,  119,  118,  118,  117,  117,  117,
 /*   550 */   116,  442,  122,  123,  113, 1207, 1207, 1041, 1044, 1034,
 /*   560 */  1034,  120,  120,  121,  121,  121,  121,  407,  137,  446,
 /*   570 */   447,  863,  169, 1183,  397, 1204, 1183, 1184, 1185,  931,
 /*   580 */   526, 1001,   98,  339,  564,  342, 1183, 1184, 1185,  306,
 /*   590 */   555,  122,  123,  113, 1207, 1207, 1041, 1044, 1034, 1034,
 /*   600 */   120,  120,  121,  121,  121,  121,  452,   71,   71,  275,
 /*   610 */   275,  119,  119,  119,  119,  118,  118,  117,  117,  117,
 /*   620 */   116,  442,  561,  417,  306,  555, 1183, 1307, 1307, 1183,
 /*   630 */  1184, 1185, 1204, 1149,  330,  458,  318,  407,  363,  470,
 /*   640 */   431, 1167,   32,  541,  527,  350, 1149, 1629,  393, 1149,
 /*   650 */   119,  119,  119,  119,  118,  118,  117,  117,  117,  116,
 /*   660 */   442,  122,  123,  113, 1207, 1207, 1041, 1044, 1034, 1034,
 /*   670 */   120,  120,  121,  121,  121,  121,  407,  199,  472, 1183,
 /*   680 */  1022,  472, 1183, 1184, 1185,  386,  151,  539, 1548,  277,
 /*   690 */   400,  137,    6,  317,    5,  564,  562,    3,  920,  920,
 /*   700 */   122,  123,  113, 1207, 1207, 1041, 1044, 1034, 1034,  120,
 /*   710 */   120,  121,  121,  121,  121,  411,  505,   83,   71,   71,
 /*   720 */   119,  119,  119,  119,  118,  118,  117,  117,  117,  116,
 /*   730 */   442, 1183,  218,  428, 1183, 1183, 1184, 1185,  363,  261,
 /*   740 */   278,  358,  508,  353,  507,  248,  407,  306,  555, 1539,
 /*   750 */  1006,  349,  363,  291,  489,  302,  293, 1542,  281,  119,
 /*   760 */   119,  119,  119,  118,  118,  117,  117,  117,  116,  442,
 /*   770 */   122,  123,  113, 1207, 1207, 1041, 1044, 1034, 1034,  120,
 /*   780 */   120,  121,  121,  121,  121,  407,  148, 1183, 1184, 1185,
 /*   790 */  1183, 1184, 1185,  275,  275, 1304, 1257, 1283,  483, 1476,
 /*   800 */   150,  489,  480,  564, 1187, 1304,  561, 1587, 1255,  122,
 /*   810 */   123,  113, 1207, 1207, 1041, 1044, 1034, 1034,  120,  120,
 /*   820 */   121,  121,  121,  121,  564,  886,   13,   13,  520,  119,
 /*   830 */   119,  119,  119,  118,  118,  117,  117,  117,  116,  442,
 /*   840 */  1183,  420,  417,  564,  269,  269, 1316,   13,   13, 1539,
 /*   850 */  1546,   16,   16,  322,    6,  407,  506,  561, 1089, 1089,
 /*   860 */   486, 1187,  425, 1539,  887,  292,   71,   71,  119,  119,
 /*   870 */   119,  119,  118,  118,  117,  117,  117,  116,  442,  122,
 /*   880 */   123,  113, 1207, 1207, 1041, 1044, 1034, 1034,  120,  120,
 /*   890 */   121,  121,  121,  121,  564,   12, 1183, 1184, 1185,  407,
 /*   900 */   275,  275,  451,  303,  834,  835,  836,  417,  489,  276,
 /*   910 */   276, 1547,  284,  561,  319,    6,  321,   71,   71,  429,
 /*   920 */   451,  450,  561,  952,  101,  113, 1207, 1207, 1041, 1044,
 /*   930 */  1034, 1034,  120,  120,  121,  121,  121,  121,  119,  119,
 /*   940 */   119,  119,  118,  118,  117,  117,  117,  116,  442, 1105,
 /*   950 */  1183,  489,  564, 1312,  437,  455,  478,  564,  246,  245,
 /*   960 */   244, 1409, 1545,  547, 1106,  405,    6, 1544,  196, 1258,
 /*   970 */   413,    6,  105,  462,  103,   71,   71,  286,  564, 1107,
 /*   980 */    13,   13,  119,  119,  119,  119,  118,  118,  117,  117,
 /*   990 */   117,  116,  442,  451,  104,  427,  337,  320,  275,  275,
 /*  1000 */   906,   13,   13,  564, 1482, 1105, 1183, 1184, 1185,  126,
 /*  1010 */   907,  561,  546,  564,  407,  478,  295, 1321,  253,  200,
 /*  1020 */  1106,  548, 1482, 1484,  280, 1409,   55,   55, 1287,  561,
 /*  1030 */   478,  380,  423,  951,  407, 1107,   71,   71,  122,  123,
 /*  1040 */   113, 1207, 1207, 1041, 1044, 1034, 1034,  120,  120,  121,
 /*  1050 */   121,  121,  121, 1204,  407,  287,  552,  309,  122,  123,
 /*  1060 */   113, 1207, 1207, 1041, 1044, 1034, 1034,  120,  120,  121,
 /*  1070 */   121,  121,  121,  441, 1128, 1628,  146, 1628,  122,  111,
 /*  1080 */   113, 1207, 1207, 1041, 1044, 1034, 1034,  120,  120,  121,
 /*  1090 */   121,  121,  121,  404,  403, 1482,  424,  119,  119,  119,
 /*  1100 */   119,  118,  118,  117,  117,  117,  116,  442, 1183,  564,
 /*  1110 */  1204,  544, 1086,  858,  329,  361, 1086,  119,  119,  119,
 /*  1120 */   119,  118,  118,  117,  117,  117,  116,  442,  564,  294,
 /*  1130 */   144,  523,   56,   56,  224,  564,  510,  119,  119,  119,
 /*  1140 */   119,  118,  118,  117,  117,  117,  116,  442,  484, 1409,
 /*  1150 */   537,   15,   15, 1126,  434,  439,  438,  407,   13,   13,
 /*  1160 */  1523,   12,  926, 1211, 1183, 1184, 1185,  925, 1213,  536,
 /*  1170 */   858,  557,  413,  193, 1525,  494, 1212,  448, 1160, 1222,
 /*  1180 */  1183,  564,  123,  113, 1207, 1207, 1041, 1044, 1034, 1034,
 /*  1190 */   120,  120,  121,  121,  121,  121, 1521, 1149,  564,  965,
 /*  1200 */   564, 1214,  247, 1214,   13,   13, 1409,  966,  538,  564,
 /*  1210 */  1149,  108,  556, 1149,    4,  310,  392, 1227,   17,  194,
 /*  1220 */   485,   43,   43,   57,   57,  306,  555,  524,  559, 1160,
 /*  1230 */   464,  564,   44,   44,  392, 1127, 1183, 1184, 1185,  479,
 /*  1240 */   119,  119,  119,  119,  118,  118,  117,  117,  117,  116,
 /*  1250 */   442,  443,  564,  327,   13,   13,  564,  418, 1315,  414,
 /*  1260 */   171,  564,  311,  553,  213,  529, 1253,  564,  517,  543,
 /*  1270 */   412,  108,  556,  137,    4,   58,   58,  435,  314,   59,
 /*  1280 */    59,  274,  217,  549,   60,   60,  349,  476,  559, 1353,
 /*  1290 */    61,   61, 1021,  275,  275, 1228,  213,  564,  106,  106,
 /*  1300 */     8,  275,  275,  275,  275,  107,  561,  443,  566,  565,
 /*  1310 */   564,  443, 1011, 1228,  561,  564,  561,  564,  275,  275,
 /*  1320 */    62,   62, 1352,  553,  247,  456,  564,   98,  110,  306,
 /*  1330 */   555,  561,  564,   45,   45,  405, 1203,  533,   46,   46,
 /*  1340 */    47,   47,  532,  465, 1011, 1011, 1013, 1014,   27,   49,
 /*  1350 */    49,  564, 1021,  405,  469,   50,   50,  564,  106,  106,
 /*  1360 */   305,  564,   84,  204,  405,  107,  564,  443,  566,  565,
 /*  1370 */   405,  564, 1011,  564,   63,   63,  564, 1599,  564,  895,
 /*  1380 */    64,   64,  457,  477,   65,   65,  147,   96,   38,   14,
 /*  1390 */    14, 1528,  412,  564,   66,   66,  128,  128,  926,   67,
 /*  1400 */    67,   52,   52,  925, 1011, 1011, 1013, 1014,   27, 1572,
 /*  1410 */  1171,  445,  208, 1123,  279,  394,   68,   68,  228,  390,
 /*  1420 */   390,  389,  264,  387, 1171,  445,  843,  877,  279,  108,
 /*  1430 */   556,  453,    4,  390,  390,  389,  264,  387,  564,  225,
 /*  1440 */   843,  313,  328, 1003,   98,  252,  559,  544,  471,  312,
 /*  1450 */   252,  564,  208,  225,  564,  313,  473,   30,  252,  279,
 /*  1460 */   466,   69,   69,  312,  390,  390,  389,  264,  387,  443,
 /*  1470 */   333,  843,   98,  564,   53,   53,  323,  157,  157,  227,
 /*  1480 */   495,  553,  249,  289,  225,  564,  313,  162,   31, 1501,
 /*  1490 */   135,  564, 1500,  227,  312,  533,  158,  158,  885,  884,
 /*  1500 */   534,  162,  873,  301,  135,  564,  481,  226,   76,   76,
 /*  1510 */  1021,  347, 1071,   98,   54,   54,  106,  106, 1067,  564,
 /*  1520 */   249,  226,  519,  107,  227,  443,  566,  565,   72,   72,
 /*  1530 */  1011,  334,  162,  564,  230,  135,  108,  556,  959,    4,
 /*  1540 */   252,  408,  129,  129,  564, 1349,  306,  555,  564,  923,
 /*  1550 */   564,  110,  226,  559,  564,  408,   73,   73,  564,  873,
 /*  1560 */   306,  555, 1011, 1011, 1013, 1014,   27,  130,  130, 1071,
 /*  1570 */   449,  131,  131,  127,  127,  357,  443,  156,  156,  892,
 /*  1580 */   893,  155,  155,  338,  449,  356,  408,  564,  553,  968,
 /*  1590 */   969,  306,  555, 1015,  341,  564,  108,  556,  564,    4,
 /*  1600 */  1132, 1286,  533,  564,  856,  343,  145,  532,  345, 1300,
 /*  1610 */   136,  136, 1083,  559, 1083,  449,  564, 1021,  134,  134,
 /*  1620 */  1284,  132,  132,  106,  106, 1285,  133,  133,  564,  352,
 /*  1630 */   107,  564,  443,  566,  565, 1340,  443, 1011,  362,   75,
 /*  1640 */    75, 1082,  564, 1082,  564,  924, 1561,  110,  553,  551,
 /*  1650 */  1015,   77,   77, 1361,   74,   74, 1408, 1336, 1347,  550,
 /*  1660 */  1414, 1265, 1256, 1244, 1243,   42,   42,   48,   48, 1011,
 /*  1670 */  1011, 1013, 1014,   27, 1245, 1580,  490, 1021,  267,  202,
 /*  1680 */  1333,  365,   11,  106,  106,  930,  367,  210,  369,  391,
 /*  1690 */   107, 1395,  443,  566,  565,  223, 1390, 1011,  500,  454,
 /*  1700 */   282, 1400,  285,  108,  556,  214,    4,  325, 1383, 1283,
 /*  1710 */   475,  355, 1473, 1583, 1472, 1399,  371, 1222,  326,  398,
 /*  1720 */   559,  290,  331,  197,  100,  556,  209,    4,  198, 1011,
 /*  1730 */  1011, 1013, 1014,   27,  385,  256, 1520, 1518,  554, 1219,
 /*  1740 */   416,  559,   83,  443,  173,  206,  182,  221,  459,  167,
 /*  1750 */   177,  460,  175,  493,  233,  553,   79,  178, 1396,  179,
 /*  1760 */    35,  180,   96, 1402,  443,  396,   36,  467, 1478, 1401,
 /*  1770 */   482,  237, 1404,  399,   82,  186,  553, 1467,   89,  488,
 /*  1780 */   190,  268,  239,  491, 1021,  340,  240,  401, 1246, 1489,
 /*  1790 */   106,  106,  336,  509, 1294,  241, 1303,  107,  430,  443,
 /*  1800 */   566,  565, 1302,   91, 1011, 1021, 1598, 1301, 1273,  215,
 /*  1810 */  1597,  106,  106,  402,  877,  432,  354, 1272,  107, 1271,
 /*  1820 */   443,  566,  565, 1596, 1566, 1011, 1293,  433,  518,  299,
 /*  1830 */   300,  360,   95,  525, 1344,  364, 1011, 1011, 1013, 1014,
 /*  1840 */    27,  254,  255, 1552,  436, 1551,  125,  544,   10,  379,
 /*  1850 */  1326, 1453,  102,   97, 1345,  528,  304, 1011, 1011, 1013,
 /*  1860 */  1014,   27,  366,  377, 1343, 1342,  368,  370, 1325,  384,
 /*  1870 */   201,  383,   34, 1368, 1367,  568, 1177,  266,  263,  265,
 /*  1880 */  1505,  159,  569, 1241, 1236, 1506,  160,  142, 1504, 1503,
 /*  1890 */   297,  211,  830,  161,  212,   78,  444,  203,  308,  222,
 /*  1900 */  1081,  139, 1079,  316,  174,  163, 1203,  229,  176,  909,
 /*  1910 */   324,  232, 1095,  181,  409,  410,  172,  164,  165,  419,
 /*  1920 */   183,   85,   86,  421,  166,   87,   88, 1098, 1094,  234,
 /*  1930 */   235,  152,   18,  236,  335, 1087, 1216,  252,  187,  487,
 /*  1940 */   238,  188,   37,  845,  492,  356,  242,  496,  351,  501,
 /*  1950 */   189,   90,   19,  504,  348,   20,  875,   92,  298,  168,
 /*  1960 */   888,  153,   93,  511,   94, 1165,  154, 1047, 1134,   39,
 /*  1970 */   216, 1133,  271,  273,  958,  192,  953,  110, 1151, 1155,
 /*  1980 */   251,    7,   21, 1159, 1139,   22, 1153,   33,   23,   24,
 /*  1990 */    25,  540, 1158,  195,   98, 1062,   26, 1048, 1046, 1050,
 /*  2000 */  1104, 1051, 1103,  257,  258,   28,   40, 1173, 1016,  857,
 /*  2010 */   109,   29,  560,  388,  138, 1172,  259,  170,  260, 1232,
 /*  2020 */  1232,  919, 1232, 1232, 1232, 1232, 1232, 1232, 1232, 1232,
 /*  2030 */  1232, 1232, 1589, 1232, 1232, 1232, 1588,
};
static const YYCODETYPE yy_lookahead[] = {
 /*     0 */   192,  273,  274,  275,  192,  192,  273,  274,  275,  192,
 /*    10 */   218,  215,  192,  218,  192,  212,  234,  235,  205,   19,
 /*    20 */    11,  192,  294,  215,  216,  203,  192,  203,  209,  210,
 /*    30 */   211,   31,  215,  216,  205,  215,  216,  215,  216,   39,
 /*    40 */   227,  215,  229,   43,   44,   45,   46,   47,   48,   49,
 /*    50 */    50,   51,   52,   53,   54,   55,   56,   57,  192,   19,
 /*    60 */   238,  239,  238,  239,  215,  273,  274,  275,  273,  274,
 /*    70 */   275,  237,   21,  251,  252,  251,  273,  274,  275,  255,
 /*    80 */   256,  215,  216,   43,   44,   45,   46,   47,   48,   49,
 /*    90 */    50,   51,   52,   53,   54,   55,   56,   57,  209,  210,
 /*   100 */   211,   76,  102,  103,  104,  105,  106,  107,  108,  109,
 /*   110 */   110,  111,  112,   59,   89,  111,  112,   92,  252,  307,
 /*   120 */   308,  313,  314,  112,  312,   59,   86,  261,   88,   19,
 /*   130 */   313,   80,  315,  313,  314,   25,  127,  128,   54,   55,
 /*   140 */    56,   57,  102,  103,  104,  105,  106,  107,  108,  109,
 /*   150 */   110,  111,  112,   43,   44,   45,   46,   47,   48,   49,
 /*   160 */    50,   51,   52,   53,   54,   55,   56,   57,  192,  115,
 /*   170 */   116,  117,  118,  122,  192,  121,  122,  123,  202,   69,
 /*   180 */   204,  115,  116,  117,  192,  131,  102,  103,  104,  105,
 /*   190 */   106,  107,  108,  109,  110,  111,  112,  215,  216,   19,
 /*   200 */    54,   55,   56,   57,   58,  108,  109,  110,  111,  112,
 /*   210 */   192,  160,  102,  103,  104,  105,  106,  107,  108,  109,
 /*   220 */   110,  111,  112,   43,   44,   45,   46,   47,   48,   49,
 /*   230 */    50,   51,   52,   53,   54,   55,   56,   57,   19,   46,
 /*   240 */    47,   48,   49,   24,  248,  192,  250,   67,  102,  103,
 /*   250 */   104,  105,  106,  107,  108,  109,  110,  111,  112,  277,
 /*   260 */   127,  128,   43,   44,   45,   46,   47,   48,   49,   50,
 /*   270 */    51,   52,   53,   54,   55,   56,   57,   26,  164,  165,
 /*   280 */   272,  263,  102,  103,  104,  105,  106,  107,  108,  109,
 /*   290 */   110,  111,  112,  184,  185,  186,  187,  188,  189,  186,
 /*   300 */   187,  188,  189,  194,   76,  196,  229,  194,   19,  196,
 /*   310 */    59,  192,  203,  120,   59,   87,  203,   89,  310,  311,
 /*   320 */    92,  102,  103,  104,  105,  106,  107,  108,  109,  110,
 /*   330 */   111,  112,   43,   44,   45,   46,   47,   48,   49,   50,
 /*   340 */    51,   52,   53,   54,   55,   56,   57,  238,  239,   73,
 /*   350 */   231,  238,  239,   22,   23,  100,   25,   81,  305,  306,
 /*   360 */   251,   23,   25,   25,  251,  272,  115,  116,  117,  214,
 /*   370 */   115,  116,  144,  192,  265,  120,  114,  222,  265,  102,
 /*   380 */   103,  104,  105,  106,  107,  108,  109,  110,  111,  112,
 /*   390 */   192,  102,  103,  104,  105,  106,  107,  108,  109,  110,
 /*   400 */   111,  112,  126,  310,  311,  192,  297,  152,  153,  154,
 /*   410 */   297,  149,  192,  137,  138,   19,  192,  100,  192,   23,
 /*   420 */    22,  106,  107,  108,  109,  110,  111,  112,  215,  216,
 /*   430 */   106,  107,  101,  116,  192,  215,  216,  120,  149,   43,
 /*   440 */    44,   45,   46,   47,   48,   49,   50,   51,   52,   53,
 /*   450 */    54,   55,   56,   57,  117,  117,  192,   59,   19,  187,
 /*   460 */    59,  189,   23,  282,  240,  252,  194,  192,  196,  152,
 /*   470 */   153,  154,  252,   72,  261,  203,  152,   25,  154,  142,
 /*   480 */   142,  261,   43,   44,   45,   46,   47,   48,   49,   50,
 /*   490 */    51,   52,   53,   54,   55,   56,   57,  192,  102,  103,
 /*   500 */   104,  105,  106,  107,  108,  109,  110,  111,  112,  267,
 /*   510 */   238,  239,  237,  115,  116,  117,  115,  116,  117,  192,
 /*   520 */    59,  118,   16,  251,  121,  122,  123,  303,   19,  303,
 /*   530 */    59,  267,   23,   72,  131,  308,   22,  265,   22,  312,
 /*   540 */    24,  102,  103,  104,  105,  106,  107,  108,  109,  110,
 /*   550 */   111,  112,   43,   44,   45,   46,   47,   48,   49,   50,
 /*   560 */    51,   52,   53,   54,   55,   56,   57,   19,   81,  297,
 /*   570 */   295,   23,  192,   59,  203,   59,  115,  116,  117,  108,
 /*   580 */   192,   73,   25,   77,  192,   79,  115,  116,  117,  137,
 /*   590 */   138,   43,   44,   45,   46,   47,   48,   49,   50,   51,
 /*   600 */    52,   53,   54,   55,   56,   57,  119,  215,  216,  238,
 /*   610 */   239,  102,  103,  104,  105,  106,  107,  108,  109,  110,
 /*   620 */   111,  112,  251,  192,  137,  138,   59,  234,  235,  115,
 /*   630 */   116,  117,  116,   76,  126,  127,  128,   19,  192,  268,
 /*   640 */    19,   23,   22,  192,  252,   24,   89,  300,  301,   92,
 /*   650 */   102,  103,  104,  105,  106,  107,  108,  109,  110,  111,
 /*   660 */   112,   43,   44,   45,   46,   47,   48,   49,   50,   51,
 /*   670 */    52,   53,   54,   55,   56,   57,   19,  192,  192,   59,
 /*   680 */    23,  192,  115,  116,  117,  200,  240,  307,  308,   22,
 /*   690 */   205,   81,  312,  262,   22,  192,  133,   22,  135,  136,
 /*   700 */    43,   44,   45,   46,   47,   48,   49,   50,   51,   52,
 /*   710 */    53,   54,   55,   56,   57,  197,   95,  150,  215,  216,
 /*   720 */   102,  103,  104,  105,  106,  107,  108,  109,  110,  111,
 /*   730 */   112,   59,  192,  112,   59,  115,  116,  117,  192,  118,
 /*   740 */   119,  120,  121,  122,  123,  124,   19,  137,  138,  303,
 /*   750 */    23,  130,  192,  267,  192,  252,  267,  306,  203,  102,
 /*   760 */   103,  104,  105,  106,  107,  108,  109,  110,  111,  112,
 /*   770 */    43,   44,   45,   46,   47,   48,   49,   50,   51,   52,
 /*   780 */    53,   54,   55,   56,   57,   19,  240,  115,  116,  117,
 /*   790 */   115,  116,  117,  238,  239,  222,  192,  224,  280,  237,
 /*   800 */   240,  192,  284,  192,   59,  232,  251,  140,  204,   43,
 /*   810 */    44,   45,   46,   47,   48,   49,   50,   51,   52,   53,
 /*   820 */    54,   55,   56,   57,  192,   35,  215,  216,  192,  102,
 /*   830 */   103,  104,  105,  106,  107,  108,  109,  110,  111,  112,
 /*   840 */    59,  230,  192,  192,  238,  239,  237,  215,  216,  303,
 /*   850 */   308,  215,  216,   16,  312,   19,   66,  251,  126,  127,
 /*   860 */   128,  116,  230,  303,   74,  203,  215,  216,  102,  103,
 /*   870 */   104,  105,  106,  107,  108,  109,  110,  111,  112,   43,
 /*   880 */    44,   45,   46,   47,   48,   49,   50,   51,   52,   53,
 /*   890 */    54,   55,   56,   57,  192,  212,  115,  116,  117,   19,
 /*   900 */   238,  239,  192,  252,    7,    8,    9,  192,  192,  238,
 /*   910 */   239,  308,  262,  251,   77,  312,   79,  215,  216,  129,
 /*   920 */   210,  211,  251,  142,  158,   45,   46,   47,   48,   49,
 /*   930 */    50,   51,   52,   53,   54,   55,   56,   57,  102,  103,
 /*   940 */   104,  105,  106,  107,  108,  109,  110,  111,  112,   12,
 /*   950 */    59,  192,  192,  237,  252,  243,  192,  192,  126,  127,
 /*   960 */   128,  192,  308,  203,   27,  253,  312,  308,  285,  207,
 /*   970 */   208,  312,  157,  290,  159,  215,  216,  262,  192,   42,
 /*   980 */   215,  216,  102,  103,  104,  105,  106,  107,  108,  109,
 /*   990 */   110,  111,  112,  283,  158,  230,  237,  160,  238,  239,
 /*  1000 */    63,  215,  216,  192,  192,   12,  115,  116,  117,   22,
 /*  1010 */    73,  251,  252,  192,   19,  192,  230,  239,   24,   24,
 /*  1020 */    27,  261,  210,  211,   99,  192,  215,  216,  225,  251,
 /*  1030 */   192,  192,  263,  142,   19,   42,  215,  216,   43,   44,
 /*  1040 */    45,   46,   47,   48,   49,   50,   51,   52,   53,   54,
 /*  1050 */    55,   56,   57,   59,   19,  291,   63,  132,   43,   44,
 /*  1060 */    45,   46,   47,   48,   49,   50,   51,   52,   53,   54,
 /*  1070 */    55,   56,   57,  252,   22,   23,   22,   25,   43,   44,
 /*  1080 */    45,   46,   47,   48,   49,   50,   51,   52,   53,   54,
 /*  1090 */    55,   56,   57,  106,  107,  283,  263,  102,  103,  104,
 /*  1100 */   105,  106,  107,  108,  109,  110,  111,  112,   59,  192,
 /*  1110 */   116,  144,   29,   59,  291,  192,   33,  102,  103,  104,
 /*  1120 */   105,  106,  107,  108,  109,  110,  111,  112,  192,  291,
 /*  1130 */   163,   19,  215,  216,   15,  192,  108,  102,  103,  104,
 /*  1140 */   105,  106,  107,  108,  109,  110,  111,  112,   65,  192,
 /*  1150 */    66,  215,  216,  101,  231,  106,  107,   19,  215,  216,
 /*  1160 */   192,  212,  134,  114,  115,  116,  117,  139,  119,   85,
 /*  1170 */   116,  207,  208,  230,  192,   19,  127,  192,   94,   60,
 /*  1180 */    59,  192,   44,   45,   46,   47,   48,   49,   50,   51,
 /*  1190 */    52,   53,   54,   55,   56,   57,  192,   76,  192,   31,
 /*  1200 */   192,  152,   46,  154,  215,  216,  192,   39,   87,  192,
 /*  1210 */    89,   19,   20,   92,   22,  192,   22,   23,   22,  230,
 /*  1220 */   263,  215,  216,  215,  216,  137,  138,  115,   36,  145,
 /*  1230 */   128,  192,  215,  216,   22,   23,  115,  116,  117,  290,
 /*  1240 */   102,  103,  104,  105,  106,  107,  108,  109,  110,  111,
 /*  1250 */   112,   59,  192,  151,  215,  216,  192,   61,  203,  298,
 /*  1260 */   299,  192,  192,   71,   25,  144,  203,  192,  203,  230,
 /*  1270 */   114,   19,   20,   81,   22,  215,  216,  263,  192,  215,
 /*  1280 */   216,  255,  256,  203,  215,  216,  130,   19,   36,  192,
 /*  1290 */   215,  216,  100,  238,  239,  101,   25,  192,  106,  107,
 /*  1300 */    48,  238,  239,  238,  239,  113,  251,  115,  116,  117,
 /*  1310 */   192,   59,  120,  101,  251,  192,  251,  192,  238,  239,
 /*  1320 */   215,  216,  192,   71,   46,  243,  192,   25,   25,  137,
 /*  1330 */   138,  251,  192,  215,  216,  253,   25,   85,  215,  216,
 /*  1340 */   215,  216,   90,  243,  152,  153,  154,  155,  156,  215,
 /*  1350 */   216,  192,  100,  253,  243,  215,  216,  192,  106,  107,
 /*  1360 */   243,  192,  148,  149,  253,  113,  192,  115,  116,  117,
 /*  1370 */   253,  192,  120,  192,  215,  216,  192,   23,  192,   25,
 /*  1380 */   215,  216,  192,  115,  215,  216,   22,  148,   24,  215,
 /*  1390 */   216,  192,  114,  192,  215,  216,  215,  216,  134,  215,
 /*  1400 */   216,  215,  216,  139,  152,  153,  154,  155,  156,    0,
 /*  1410 */     1,    2,  141,   23,    5,   25,  215,  216,   24,   10,
 /*  1420 */    11,   12,   13,   14,    1,    2,   17,  125,    5,   19,
 /*  1430 */    20,  268,   22,   10,   11,   12,   13,   14,  192,   30,
 /*  1440 */    17,   32,   23,   23,   25,   25,   36,  144,   23,   40,
 /*  1450 */    25,  192,  141,   30,  192,   32,   23,   22,   25,    5,
 /*  1460 */   128,  215,  216,   40,   10,   11,   12,   13,   14,   59,
 /*  1470 */    23,   17,   25,  192,  215,  216,  192,  215,  216,   70,
 /*  1480 */    23,   71,   25,  151,   30,  192,   32,   78,   53,  192,
 /*  1490 */    81,  192,  192,   70,   40,   85,  215,  216,  119,  120,
 /*  1500 */    90,   78,   59,  254,   81,  192,  192,   98,  215,  216,
 /*  1510 */   100,   23,   59,   25,  215,  216,  106,  107,   23,  192,
 /*  1520 */    25,   98,   19,  113,   70,  115,  116,  117,  215,  216,
 /*  1530 */   120,  192,   78,  192,  140,   81,   19,   20,   23,   22,
 /*  1540 */    25,  132,  215,  216,  192,  192,  137,  138,  192,   23,
 /*  1550 */   192,   25,   98,   36,  192,  132,  215,  216,  192,  116,
 /*  1560 */   137,  138,  152,  153,  154,  155,  156,  215,  216,  116,
 /*  1570 */   161,  215,  216,  215,  216,  120,   59,  215,  216,    7,
 /*  1580 */     8,  215,  216,  192,  161,  130,  132,  192,   71,   83,
 /*  1590 */    84,  137,  138,   59,  192,  192,   19,   20,  192,   22,
 /*  1600 */    97,  225,   85,  192,   23,  192,   25,   90,  192,  192,
 /*  1610 */   215,  216,  152,   36,  154,  161,  192,  100,  215,  216,
 /*  1620 */   192,  215,  216,  106,  107,  225,  215,  216,  192,  192,
 /*  1630 */   113,  192,  115,  116,  117,  257,   59,  120,  192,  215,
 /*  1640 */   216,  152,  192,  154,  192,   23,  317,   25,   71,  235,
 /*  1650 */   116,  215,  216,  192,  215,  216,  192,  192,  192,  192,
 /*  1660 */   192,  192,  192,  192,  192,  215,  216,  215,  216,  152,
 /*  1670 */   153,  154,  155,  156,  192,  192,  287,  100,  286,  241,
 /*  1680 */   254,  254,  242,  106,  107,  108,  254,  213,  254,  190,

 /*  1690 */   113,  270,  115,  116,  117,  296,  266,  120,  219,  258,
 /*  1700 */   244,  270,  258,   19,   20,  228,   22,  292,  266,  224,
 /*  1710 */   292,  218,  218,  195,  218,  270,  258,   60,  245,  270,
 /*  1720 */    36,  245,  244,  248,   19,   20,  242,   22,  248,  152,
 /*  1730 */   153,  154,  155,  156,  244,  140,  199,  199,  279,   38,
 /*  1740 */   199,   36,  150,   59,  296,  149,   22,  296,   18,   43,
 /*  1750 */   236,  199,  233,   18,  198,   71,  293,  236,  271,  236,
 /*  1760 */   269,  236,  148,  271,   59,  245,  269,  245,  282,  271,
 /*  1770 */   199,  198,  233,  245,  293,  233,   71,  245,  157,   62,
 /*  1780 */    22,  199,  198,  220,  100,  199,  198,  220,  199,  289,
 /*  1790 */   106,  107,  288,  114,  226,  198,  217,  113,   64,  115,
 /*  1800 */   116,  117,  217,   22,  120,  100,  223,  217,  217,  164,
 /*  1810 */   223,  106,  107,  220,  125,   24,  217,  219,  113,  217,
 /*  1820 */   115,  116,  117,  217,  311,  120,  226,  112,  304,  281,
 /*  1830 */   281,  220,  114,  143,  260,  259,  152,  153,  154,  155,
 /*  1840 */   156,  199,   91,  316,   82,  316,  147,  144,   22,  199,
 /*  1850 */   249,  276,  157,  146,  260,  145,  278,  152,  153,  154,
 /*  1860 */   155,  156,  259,  248,  260,  260,  259,  259,  249,  245,
 /*  1870 */   247,  246,   25,  264,  264,  201,   13,    6,  193,  193,
 /*  1880 */   212,  206,  191,  191,  191,  212,  206,  221,  212,  212,
 /*  1890 */   221,  213,    4,  206,  213,  212,    3,   22,  162,   15,
 /*  1900 */    23,   16,   23,  138,  150,  129,   25,   24,  141,   20,
 /*  1910 */    16,  143,    1,  141,  302,  302,  299,  129,  129,   61,
 /*  1920 */   150,   53,   53,   37,  129,   53,   53,  115,    1,   34,
 /*  1930 */   140,    5,   22,  114,  160,   68,   75,   25,   68,   41,
 /*  1940 */   140,  114,   24,   20,   19,  130,  124,   67,   24,   67,
 /*  1950 */    22,   22,   22,   96,   23,   22,   59,   22,   67,   37,
 /*  1960 */    28,   23,  148,   22,   25,   23,   23,   23,   23,   22,
 /*  1970 */   140,   97,   23,   23,  115,   22,  142,   25,   88,   75,
 /*  1980 */    34,   44,   34,   75,   23,   34,   86,   22,   34,   34,
 /*  1990 */    34,   24,   93,   25,   25,   23,   34,   23,   23,   23,
 /*  2000 */    23,   11,   23,   25,   22,   22,   22,    1,   23,   23,
 /*  2010 */    22,   22,   25,   15,   23,    1,  140,   25,  140,  318,
 /*  2020 */   318,  134,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2030 */   318,  318,  140,  318,  318,  318,  140,  318,  318,  318,
 /*  2040 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2050 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2060 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2070 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2080 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2090 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2100 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2110 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2120 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2130 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2140 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2150 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2160 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2170 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2180 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2190 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2200 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2210 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2220 */   318,
};
#define YY_SHIFT_COUNT    (571)
#define YY_SHIFT_MIN      (0)
#define YY_SHIFT_MAX      (2014)
static const unsigned short int yy_shift_ofst[] = {
 /*     0 */  1423, 1409, 1454, 1192, 1192,  610, 1252, 1410, 1517, 1684,
 /*    10 */  1684, 1684,  276,    0,    0,  180, 1015, 1684, 1684, 1684,
 /*    20 */  1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684,
 /*    30 */  1049, 1049, 1121, 1121,   54,  487,  610,  610,  610,  610,
 /*    40 */   610,   40,  110,  219,  289,  396,  439,  509,  548,  618,
 /*    50 */   657,  727,  766,  836,  995, 1015, 1015, 1015, 1015, 1015,
 /*    60 */  1015, 1015, 1015, 1015, 1015, 1015, 1015, 1015, 1015, 1015,
 /*    70 */  1015, 1015, 1015, 1035, 1015, 1138,  880,  880, 1577, 1684,
 /*    80 */  1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684,
 /*    90 */  1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684,
 /*   100 */  1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684, 1684,
 /*   110 */  1684, 1684, 1684, 1705, 1684, 1684, 1684, 1684, 1684, 1684,
 /*   120 */  1684, 1684, 1684, 1684, 1684, 1684, 1684,  146,   84,   84,
 /*   130 */    84,   84,   84,  277,  315,  401,   97,  461,  251,   66,
 /*   140 */    66,   51, 1156,   66,   66,  324,  324,   66,  452,  452,
 /*   150 */   452,  452,  133,  114,  114,    4,   11, 2037, 2037,  621,
 /*   160 */   621,  621,  567,  398,  398,  398,  398,  937,  937,  228,
 /*   170 */   251,  331, 1052,   66,   66,   66,   66,   66,   66,   66,
 /*   180 */    66,   66,   66,   66,   66,   66,   66,   66,   66,   66,
 /*   190 */    66,   66,   66,  557,  557,   66,    9,   25,   25,  745,
 /*   200 */   745,  967, 1088, 2037, 2037, 2037, 2037, 2037, 2037, 2037,
 /*   210 */   255,  317,  317,  514,  403,  620,  471,  672,  781,  891,
 /*   220 */   675,   66,   66,   66,   66,   66,   66,   66,   66,   66,
 /*   230 */    66,  508,   66,   66,   66,   66,   66,   66,   66,   66,
 /*   240 */    66,   66,   66,   66,  790,  790,  790,   66,   66,   66,
 /*   250 */   338,   66,   66,   66,  516, 1084,   66,   66,  993,   66,
 /*   260 */    66,   66,   66,   66,   66,   66,   66,  732, 1083,  563,
 /*   270 */   994,  994,  994,  994,  337,  563,  563, 1028,  987,  897,
 /*   280 */  1119,  262, 1214, 1271, 1112, 1214, 1112, 1268, 1239,  262,
 /*   290 */   262, 1239,  262, 1271, 1268, 1302, 1354, 1278, 1168, 1168,
 /*   300 */  1168, 1112, 1303, 1303,  815, 1311, 1264, 1364, 1657, 1657,
 /*   310 */  1595, 1595, 1701, 1701, 1595, 1592, 1596, 1724, 1706, 1730,
 /*   320 */  1730, 1730, 1730, 1595, 1735, 1614, 1596, 1596, 1614, 1724,
 /*   330 */  1706, 1614, 1706, 1614, 1595, 1735, 1621, 1717, 1595, 1735,
 /*   340 */  1758, 1595, 1735, 1595, 1735, 1758, 1679, 1679, 1679, 1734,
 /*   350 */  1781, 1781, 1758, 1679, 1689, 1679, 1734, 1679, 1679, 1645,
 /*   360 */  1791, 1715, 1715, 1758, 1690, 1718, 1690, 1718, 1690, 1718,
 /*   370 */  1690, 1718, 1595, 1751, 1751, 1762, 1762, 1699, 1703, 1826,
 /*   380 */  1595, 1695, 1699, 1707, 1710, 1614, 1847, 1863, 1863, 1871,
 /*   390 */  1871, 1871, 2037, 2037, 2037, 2037, 2037, 2037, 2037, 2037,
 /*   400 */  2037, 2037, 2037, 2037, 2037, 2037, 2037,  193,  837, 1194,
 /*   410 */  1212,  506,  832, 1054, 1390,  925, 1435, 1394, 1102, 1332,
 /*   420 */  1419, 1196, 1420, 1425, 1433, 1447, 1457, 1488, 1443, 1379,
 /*   430 */  1572, 1455, 1503, 1453, 1495, 1515, 1506, 1526, 1460, 1489,
 /*   440 */  1581, 1622, 1534,  667, 1888, 1893, 1875, 1736, 1884, 1885,
 /*   450 */  1877, 1879, 1765, 1754, 1776, 1881, 1881, 1883, 1767, 1889,
 /*   460 */  1768, 1894, 1911, 1772, 1788, 1881, 1789, 1858, 1886, 1881,
 /*   470 */  1770, 1868, 1869, 1872, 1873, 1795, 1812, 1895, 1790, 1927,
 /*   480 */  1926, 1910, 1819, 1774, 1867, 1912, 1870, 1861, 1898, 1800,
 /*   490 */  1827, 1918, 1923, 1925, 1815, 1822, 1928, 1880, 1929, 1930,
 /*   500 */  1931, 1933, 1882, 1897, 1924, 1857, 1932, 1935, 1891, 1922,
 /*   510 */  1938, 1814, 1941, 1942, 1943, 1944, 1939, 1945, 1947, 1874,
 /*   520 */  1830, 1949, 1950, 1859, 1946, 1953, 1834, 1952, 1948, 1951,
 /*   530 */  1954, 1955, 1890, 1904, 1900, 1937, 1908, 1899, 1956, 1961,
 /*   540 */  1965, 1967, 1968, 1969, 1962, 1972, 1952, 1974, 1975, 1976,
 /*   550 */  1977, 1978, 1979, 1982, 1990, 1983, 1984, 1985, 1986, 1988,
 /*   560 */  1989, 1987, 1887, 1876, 1878, 1892, 1896, 1992, 1991, 1998,
 /*   570 */  2006, 2014,
};
#define YY_REDUCE_COUNT (406)
#define YY_REDUCE_MIN   (-272)
#define YY_REDUCE_MAX   (1693)
static const short yy_reduce_ofst[] = {
 /*     0 */   109,  113,  272,  760, -178, -176, -192, -183, -180, -134,
 /*    10 */   213,  220,  371, -208, -205, -272, -197,  611,  632,  765,
 /*    20 */   786,  392,  943,  989,  503,  651, 1039,  -18,  702,  821,
 /*    30 */   710,  812, -188,  380, -187,  555,  662, 1055, 1063, 1065,
 /*    40 */  1080, -267, -267, -267, -267, -267, -267, -267, -267, -267,
 /*    50 */  -267, -267, -267, -267, -267, -267, -267, -267, -267, -267,
 /*    60 */  -267, -267, -267, -267, -267, -267, -267, -267, -267, -267,
 /*    70 */  -267, -267, -267, -267, -267, -267, -267, -267,  636,  811,
 /*    80 */   917,  936, 1006, 1008, 1017, 1060, 1064, 1069, 1075, 1105,
 /*    90 */  1118, 1123, 1125, 1134, 1140, 1159, 1165, 1169, 1174, 1179,
 /*   100 */  1181, 1184, 1186, 1201, 1246, 1259, 1262, 1281, 1293, 1299,
 /*   110 */  1313, 1327, 1341, 1352, 1356, 1358, 1362, 1366, 1395, 1403,
 /*   120 */  1406, 1411, 1424, 1436, 1439, 1450, 1452, -267, -267, -267,
 /*   130 */  -267, -267, -267, -267, -267,  224, -267,  446,  -24,  275,
 /*   140 */   546,  518,  573,  560,   53, -181, -111,  485,  606,  671,
 /*   150 */   606,  671,  683,    8,   93, -267, -267, -267, -267,  155,
 /*   160 */   155,  155,  181,  242,  264,  486,  489, -218,  393,  227,
 /*   170 */   604,  347,  347, -171,  431,  650,  715, -166,  562,  609,
 /*   180 */   716,  764,   18,  823,  769,  833,  838,  957,  759,  119,
 /*   190 */   923,  226, 1014,  542,  603,  451,  949,  654,  659,  762,
 /*   200 */   964,   -4,  778,  961,  712, 1082, 1100, 1111, 1026, 1117,
 /*   210 */  -204, -174, -151,   -8,   77,  198,  305,  327,  388,  540,
 /*   220 */   839,  968,  982,  985, 1004, 1023, 1070, 1086, 1097, 1130,
 /*   230 */  1190, 1163, 1199, 1284, 1297, 1300, 1314, 1339, 1353, 1391,
 /*   240 */  1402, 1413, 1416, 1417,  803, 1376, 1400, 1428, 1437, 1446,
 /*   250 */  1378, 1461, 1464, 1465, 1249, 1329, 1466, 1467, 1414, 1468,
 /*   260 */   305, 1469, 1470, 1471, 1472, 1482, 1483, 1389, 1392, 1438,
 /*   270 */  1426, 1427, 1432, 1434, 1378, 1438, 1438, 1440, 1474, 1499,
 /*   280 */  1399, 1421, 1430, 1456, 1441, 1442, 1444, 1415, 1473, 1431,
 /*   290 */  1445, 1476, 1449, 1478, 1418, 1479, 1477, 1485, 1493, 1494,
 /*   300 */  1496, 1458, 1475, 1480, 1459, 1490, 1484, 1518, 1448, 1451,
 /*   310 */  1537, 1538, 1463, 1481, 1541, 1486, 1487, 1491, 1519, 1514,
 /*   320 */  1521, 1523, 1525, 1552, 1556, 1520, 1492, 1498, 1522, 1497,
 /*   330 */  1539, 1528, 1542, 1532, 1571, 1573, 1500, 1504, 1582, 1584,
 /*   340 */  1563, 1586, 1588, 1589, 1597, 1567, 1579, 1585, 1590, 1568,
 /*   350 */  1583, 1587, 1593, 1591, 1598, 1599, 1600, 1602, 1606, 1513,
 /*   360 */  1524, 1548, 1549, 1611, 1574, 1576, 1594, 1603, 1604, 1607,
 /*   370 */  1605, 1608, 1642, 1527, 1529, 1609, 1610, 1601, 1615, 1575,
 /*   380 */  1650, 1578, 1619, 1623, 1625, 1624, 1674, 1685, 1686, 1691,
 /*   390 */  1692, 1693, 1612, 1613, 1617, 1675, 1668, 1673, 1676, 1677,
 /*   400 */  1680, 1666, 1669, 1678, 1681, 1683, 1687,
};
static const YYACTIONTYPE yy_default[] = {
 /*     0 */  1633, 1633, 1633, 1462, 1230, 1341, 1230, 1230, 1230, 1462,
 /*    10 */  1462, 1462, 1230, 1371, 1371, 1515, 1263, 1230, 1230, 1230,
 /*    20 */  1230, 1230, 1230, 1230, 1230, 1230, 1230, 1461, 1230, 1230,
 /*    30 */  1230, 1230, 1550, 1550, 1230, 1230, 1230, 1230, 1230, 1230,
 /*    40 */  1230, 1230, 1380, 1230, 1387, 1230, 1230, 1230, 1230, 1230,







|





|



|



|


|


|


|
|
|
|

|
|
|

|
|

|

|
|
|



|


|
|
|
|
|
|

|
|
|

|
|
|
|
|
|

|
|
|

|
|
|
|
|


|
|
|

|
|
|
|
|
|

|
|
|

|
|
|
|
|


|
|
|

|
|
|
|
|
|
|
|
|
|
|

|
|
|
|
|
|
|
|
|
|
|
|
|

|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
<














|





|




|
|

|
|
|

|
|



|
|
|



|



|
|
|




|
|


|
|
|
|
|

|
|
|


|
|
|



|
|
|


|
|
|

|

|
|
|


|
|
|



|
|
|

|
|
|
|
|

|

|

|

|
|
|
|
|
|
|

|
|
|
|
|

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
















|
<
<



|

|
|
|
|
|


|
|
|
|
|
|
|
|
|

|
|
|
|

|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|



|




|
|


|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|







160633
160634
160635
160636
160637
160638
160639
160640
160641
160642
160643
160644
160645
160646
160647
160648
160649
160650
160651
160652
160653
160654
160655
160656
160657
160658
160659
160660
160661
160662
160663
160664
160665
160666
160667
160668
160669
160670
160671
160672
160673
160674
160675
160676
160677
160678
160679
160680
160681
160682
160683
160684
160685
160686
160687
160688
160689
160690
160691
160692
160693
160694
160695
160696
160697
160698
160699
160700
160701
160702
160703
160704
160705
160706
160707
160708
160709
160710
160711
160712
160713
160714
160715
160716
160717
160718
160719
160720
160721
160722
160723
160724
160725
160726
160727
160728
160729
160730
160731
160732
160733
160734
160735
160736
160737
160738
160739
160740
160741
160742
160743
160744
160745
160746
160747
160748
160749
160750
160751
160752
160753
160754
160755
160756
160757
160758
160759
160760
160761
160762
160763
160764
160765
160766
160767
160768
160769
160770
160771
160772
160773
160774
160775
160776
160777
160778
160779
160780
160781
160782
160783
160784
160785
160786
160787
160788
160789
160790
160791
160792
160793
160794
160795
160796
160797
160798
160799
160800
160801
160802
160803
160804
160805
160806
160807
160808
160809
160810
160811
160812
160813
160814
160815
160816
160817
160818
160819
160820
160821
160822
160823
160824
160825
160826
160827
160828
160829
160830
160831
160832
160833
160834
160835
160836
160837
160838
160839
160840
160841
160842
160843
160844

160845
160846
160847
160848
160849
160850
160851
160852
160853
160854
160855
160856
160857
160858
160859
160860
160861
160862
160863
160864
160865
160866
160867
160868
160869
160870
160871
160872
160873
160874
160875
160876
160877
160878
160879
160880
160881
160882
160883
160884
160885
160886
160887
160888
160889
160890
160891
160892
160893
160894
160895
160896
160897
160898
160899
160900
160901
160902
160903
160904
160905
160906
160907
160908
160909
160910
160911
160912
160913
160914
160915
160916
160917
160918
160919
160920
160921
160922
160923
160924
160925
160926
160927
160928
160929
160930
160931
160932
160933
160934
160935
160936
160937
160938
160939
160940
160941
160942
160943
160944
160945
160946
160947
160948
160949
160950
160951
160952
160953
160954
160955
160956
160957
160958
160959
160960
160961
160962
160963
160964
160965
160966
160967
160968
160969
160970
160971
160972
160973
160974
160975
160976
160977
160978
160979
160980
160981
160982
160983
160984
160985
160986
160987
160988
160989
160990
160991
160992
160993
160994
160995
160996
160997
160998
160999
161000
161001
161002
161003
161004
161005
161006
161007
161008
161009
161010
161011
161012
161013
161014
161015
161016
161017

161018
161019
161020
161021
161022
161023
161024
161025
161026
161027
161028
161029
161030
161031
161032
161033
161034
161035
161036
161037
161038
161039
161040
161041
161042
161043
161044
161045
161046
161047
161048
161049
161050
161051
161052
161053
161054
161055
161056
161057
161058
161059
161060
161061
161062
161063
161064
161065
161066
161067


161068
161069
161070
161071
161072
161073
161074
161075
161076
161077
161078
161079
161080
161081
161082
161083
161084
161085
161086
161087
161088
161089
161090
161091
161092
161093
161094
161095
161096
161097
161098
161099
161100
161101
161102
161103
161104
161105
161106
161107
161108
161109
161110
161111
161112
161113
161114
161115
161116
161117
161118
161119
161120
161121
161122
161123
161124
161125
161126
161127
161128
161129
161130
161131
161132
161133
161134
161135
161136
161137
161138
161139
161140
161141
161142
161143
161144
161145
161146
161147
161148
161149
161150
161151
161152
161153
161154
161155
161156
161157
161158
161159
161160
161161
161162
161163
161164
161165
161166
161167
161168
161169
161170
161171
161172
161173
161174
161175
161176
161177
161178
161179
161180
161181
161182
161183
**  yy_shift_ofst[]    For each state, the offset into yy_action for
**                     shifting terminals.
**  yy_reduce_ofst[]   For each state, the offset into yy_action for
**                     shifting non-terminals after a reduce.
**  yy_default[]       Default action for each state.
**
*********** Begin parsing tables **********************************************/
#define YY_ACTTAB_COUNT (2022)
static const YYACTIONTYPE yy_action[] = {
 /*     0 */   564,  115,  112,  220,  169,  199,  115,  112,  220,  564,
 /*    10 */   375, 1266,  564,  376,  564,  270, 1309, 1309,  406,  407,
 /*    20 */  1084,  199, 1513,   41,   41,  515,  489,  521,  558,  558,
 /*    30 */   558,  965,   41,   41,  395,   41,   41,   51,   51,  966,
 /*    40 */   296, 1269,  296,  122,  123, 1207, 1207, 1041,  113, 1044,
 /*    50 */  1034, 1034,  120,  120,  121,  121,  121,  121,  564,  407,
 /*    60 */   275,  275,  275,  275, 1268,  115,  112,  220,  115,  112,
 /*    70 */   220, 1512,  846,  561,  516,  561,  115,  112,  220,  250,
 /*    80 */   217,   71,   71,  122,  123, 1207, 1207, 1041,  113, 1044,
 /*    90 */  1034, 1034,  120,  120,  121,  121,  121,  121,  440,  440,
 /*   100 */   440, 1149,  119,  119,  119,  119,  118,  118,  117,  117,
 /*   110 */   117,  116,  442, 1183, 1149,  116,  442, 1149,  546,  513,
 /*   120 */  1548, 1554,  374,  213,    6,  169, 1154,  522, 1154,  407,
 /*   130 */  1556,  461,  373, 1554,  535,   99,  463,  332,  121,  121,
 /*   140 */   121,  121,  119,  119,  119,  119,  118,  118,  117,  117,
 /*   150 */   117,  116,  442,  122,  123, 1207, 1207, 1041,  113, 1044,
 /*   160 */  1034, 1034,  120,  120,  121,  121,  121,  121, 1257, 1183,
 /*   170 */  1184, 1185,  243, 1064,  564,  502,  499,  498,  567,  124,
 /*   180 */   567, 1128, 1627,  344, 1627,  497,  119,  119,  119,  119,
 /*   190 */   118,  118,  117,  117,  117,  116,  442,   70,   70,  407,
 /*   200 */   121,  121,  121,  121,  114,  117,  117,  117,  116,  442,
 /*   210 */   474, 1469,  119,  119,  119,  119,  118,  118,  117,  117,
 /*   220 */   117,  116,  442,  122,  123, 1207, 1207, 1041,  113, 1044,
 /*   230 */  1034, 1034,  120,  120,  121,  121,  121,  121,  407,  208,
 /*   240 */   539, 1548, 1424,   81,  339,    6,  342,   80,  119,  119,
 /*   250 */   119,  119,  118,  118,  117,  117,  117,  116,  442,  381,
 /*   260 */  1126,  442,  122,  123, 1207, 1207, 1041,  113, 1044, 1034,
 /*   270 */  1034,  120,  120,  121,  121,  121,  121,  262,  463,  332,
 /*   280 */   359, 1567,  119,  119,  119,  119,  118,  118,  117,  117,
 /*   290 */   117,  116,  442, 1231,    1,    1,  571,    2, 1235, 1573,
 /*   300 */   571,    2, 1235,  307, 1149,  141,  417,  307,  407,  141,
 /*   310 */  1183,   98, 1317,  489,  866,  531, 1317, 1149,  215,  512,
 /*   320 */  1149,  119,  119,  119,  119,  118,  118,  117,  117,  117,
 /*   330 */   116,  442,  122,  123, 1207, 1207, 1041,  113, 1044, 1034,
 /*   340 */  1034,  120,  120,  121,  121,  121,  121,  275,  275, 1001,
 /*   350 */  1257,  275,  275, 1128, 1628, 1021, 1628,  137,  415, 1600,
 /*   360 */   561,  272, 1255,  950,  561, 1423, 1183, 1184, 1185, 1594,
 /*   370 */   866, 1012,  530,  315,  231, 1011,  317, 1276,  231,  119,
 /*   380 */   119,  119,  119,  118,  118,  117,  117,  117,  116,  442,
 /*   390 */  1570,  119,  119,  119,  119,  118,  118,  117,  117,  117,
 /*   400 */   116,  442,  330,  359, 1567,  564,  446, 1011, 1011, 1013,
 /*   410 */   446,  877,  564,  306,  555,  407,  447, 1021,  563,  346,
 /*   420 */   184,  118,  118,  117,  117,  117,  116,  442,   71,   71,
 /*   430 */   439,  438, 1126, 1012,  472,   71,   71, 1011,  205,  122,
 /*   440 */   123, 1207, 1207, 1041,  113, 1044, 1034, 1034,  120,  120,
 /*   450 */   121,  121,  121,  121, 1304,  219, 1283, 1183,  407,  570,
 /*   460 */  1183, 1235,  503, 1477, 1304,  546,  307,  489,  141, 1011,
 /*   470 */  1011, 1013,  546,  140,  545, 1317, 1214,  382, 1214,  378,
 /*   480 */   950,  514,  122,  123, 1207, 1207, 1041,  113, 1044, 1034,
 /*   490 */  1034,  120,  120,  121,  121,  121,  121,  472,  119,  119,
 /*   500 */   119,  119,  118,  118,  117,  117,  117,  116,  442,  283,
 /*   510 */   275,  275, 1476, 1183, 1184, 1185, 1183, 1184, 1185,  417,
 /*   520 */  1183,  243,  541,  561,  502,  499,  498, 1001,  407,  478,
 /*   530 */  1183,  472,  870,  143,  497, 1549,  185,  231,    9,    6,
 /*   540 */   253,  119,  119,  119,  119,  118,  118,  117,  117,  117,
 /*   550 */   116,  442,  122,  123, 1207, 1207, 1041,  113, 1044, 1034,
 /*   560 */  1034,  120,  120,  121,  121,  121,  121,  407,  372,  446,
 /*   570 */   363,  863,  288, 1183,  397, 1204, 1183, 1184, 1185,  931,
 /*   580 */   330,  458,  318,  526,  564,  541, 1183, 1184, 1185,  284,
 /*   590 */  1183,  122,  123, 1207, 1207, 1041,  113, 1044, 1034, 1034,
 /*   600 */   120,  120,  121,  121,  121,  121,  291,   71,   71,  275,
 /*   610 */   275,  119,  119,  119,  119,  118,  118,  117,  117,  117,
 /*   620 */   116,  442,  561, 1031, 1031, 1042, 1183, 1045,  287, 1183,
 /*   630 */  1184, 1185, 1204,  137,  218,  542, 1541,  407,  363,  470,
 /*   640 */   431, 1167,   32,  363,  527,  350, 1183, 1184, 1185,  380,
 /*   650 */   119,  119,  119,  119,  118,  118,  117,  117,  117,  116,
 /*   660 */   442,  122,  123, 1207, 1207, 1041,  113, 1044, 1034, 1034,
 /*   670 */   120,  120,  121,  121,  121,  121,  407,  392, 1227, 1183,
 /*   680 */  1022, 1540, 1183, 1184, 1185, 1523,  149, 1307, 1307,  306,
 /*   690 */   555,  151, 1546,  361,    5,  564,    6,    3, 1035, 1542,
 /*   700 */   122,  123, 1207, 1207, 1041,  113, 1044, 1034, 1034,  120,
 /*   710 */   120,  121,  121,  121,  121,  411,  505,   83,   71,   71,
 /*   720 */   119,  119,  119,  119,  118,  118,  117,  117,  117,  116,
 /*   730 */   442, 1183,  426,  428, 1183, 1183, 1184, 1185,  191,  261,
 /*   740 */   278,  358,  508,  353,  507,  248,  407,  455,  137, 1539,
 /*   750 */  1006,  349,  363,  472, 1539,  302, 1228,  405,  281,  119,
 /*   760 */   119,  119,  119,  118,  118,  117,  117,  117,  116,  442,
 /*   770 */   122,  123, 1207, 1207, 1041,  113, 1044, 1034, 1034,  120,
 /*   780 */   120,  121,  121,  121,  121,  407,  452, 1183, 1184, 1185,
 /*   790 */  1183, 1184, 1185,  275,  275,  269,  269,  489,  483, 1525,
 /*   800 */   148,  363,  480,  564,  306,  555,  561,  489,  561,  122,
 /*   810 */   123, 1207, 1207, 1041,  113, 1044, 1034, 1034,  120,  120,
 /*   820 */   121,  121,  121,  121,  564,  886,   13,   13,  293,  119,
 /*   830 */   119,  119,  119,  118,  118,  117,  117,  117,  116,  442,
 /*   840 */  1183,  420, 1316,  564,   98,  417,  199,   13,   13,  150,
 /*   850 */   306,  555, 1312,  322,  386,  407,  506,  478,  562,  400,
 /*   860 */   920,  920,  425, 1539,  887,  292,   71,   71,  119,  119,
 /*   870 */   119,  119,  118,  118,  117,  117,  117,  116,  442,  122,
 /*   880 */   123, 1207, 1207, 1041,  113, 1044, 1034, 1034,  120,  120,
 /*   890 */   121,  121,  121,  121,  564, 1149, 1183, 1184, 1185,  407,
 /*   900 */   275,  275,  451,  303, 1089, 1089,  486,  448, 1149,  276,
 /*   910 */   276, 1149, 1539,  561,  319,  286,  321,   71,   71,  429,
 /*   920 */   451,  450,  561,  952,  101, 1207, 1207, 1041,  113, 1044,
 /*   930 */  1034, 1034,  120,  120,  121,  121,  121,  121,  119,  119,
 /*   940 */   119,  119,  118,  118,  117,  117,  117,  116,  442, 1105,
 /*   950 */  1183, 1547,  564,   12,  437,    6,  329,  564,  834,  835,
 /*   960 */   836, 1629,  393,  547, 1106,  246,  245,  244, 1545, 1258,
 /*   970 */   413, 1521,    6, 1086,  310,   71,   71, 1086,  564, 1107,
 /*   980 */    13,   13,  119,  119,  119,  119,  118,  118,  117,  117,
 /*   990 */   117,  116,  442,  451,  104,  427,  537,  320,  275,  275,
 /*  1000 */   906,   13,   13,  520, 1482, 1105, 1183, 1184, 1185,  484,
 /*  1010 */   907,  561,  546,  564,  407,  536,  295,  478,  253,  200,
 /*  1020 */  1106,  548, 1482, 1484, 1160, 1409,   16,   16,  126,  557,
 /*  1030 */   413,  479,  311,  951,  407, 1107,   71,   71,  122,  123,
 /*  1040 */  1207, 1207, 1041,  113, 1044, 1034, 1034,  120,  120,  121,
 /*  1050 */   121,  121,  121, 1204,  407,  544,  552,  314,  122,  123,
 /*  1060 */  1207, 1207, 1041,  113, 1044, 1034, 1034,  120,  120,  121,
 /*  1070 */   121,  121,  121,  441,  144, 1160,  468,  146,  122,  111,
 /*  1080 */  1207, 1207, 1041,  113, 1044, 1034, 1034,  120,  120,  121,
 /*  1090 */   121,  121,  121,  247,   12, 1482,  422,  119,  119,  119,
 /*  1100 */   119,  118,  118,  117,  117,  117,  116,  442, 1183,  564,
 /*  1110 */  1204,  207,  404,  403,  858,  950,  294,  119,  119,  119,
 /*  1120 */   119,  118,  118,  117,  117,  117,  116,  442,  564,   30,
 /*  1130 */   564, 1409,   55,   55, 1599,  564,  895,  119,  119,  119,
 /*  1140 */   119,  118,  118,  117,  117,  117,  116,  442,  510, 1409,
 /*  1150 */  1409,   56,   56,   15,   15,  439,  438,  407,   13,   13,
 /*  1160 */    31, 1187,  412, 1211, 1183, 1184, 1185,  196, 1213,  306,
 /*  1170 */   555,  858,  462,  193,  926,  564, 1212,  489,  361,  925,
 /*  1180 */  1183,  564,  123, 1207, 1207, 1041,  113, 1044, 1034, 1034,
 /*  1190 */   120,  120,  121,  121,  121,  121, 1544, 1149,   43,   43,
 /*  1200 */     6, 1214,  423, 1214,   13,   13,  564,  219,  538,  494,
 /*  1210 */  1149,  108,  556, 1149,    4,  392, 1127,  434, 1187,  194,
 /*  1220 */   424,  485,  337, 1315,  414,  171, 1253, 1321,  559,   57,
 /*  1230 */    57,  564,  950,  564,  224,  247, 1183, 1184, 1185,  561,
 /*  1240 */   119,  119,  119,  119,  118,  118,  117,  117,  117,  116,
 /*  1250 */   442,  443,  564,  517,   13,   13,   44,   44,  275,  275,
 /*  1260 */  1409,  275,  275,  553, 1353,  529,  213,  549,  456,  543,
 /*  1270 */   465,  561,  564,  137,  561,   58,   58,  469,  405, 1222,
 /*  1280 */   405,  274,  217,  108,  556,  110,    4,  405,  275,  275,
 /*  1290 */   564, 1352, 1021,  564, 1228,   59,   59,  523,  106,  106,
 /*  1300 */   559,  561,  275,  275,  412,  107,  457,  443,  566,  565,
 /*  1310 */   564,    8, 1011,   60,   60,  561,   61,   61,  564,  965,
 /*  1320 */   349,  926,  305,  443,   84,  204,  925,  966,  564,  306,
 /*  1330 */   555,  435,  405,   62,   62,  553,  476,  105,  564,  103,
 /*  1340 */   464,   45,   45, 1203, 1011, 1011, 1013, 1014,   27,  533,
 /*  1350 */   564,   46,   46,  453,  532, 1572, 1171,  445, 1528,  564,
 /*  1360 */   279,   47,   47,  327, 1021,  390,  390,  389,  264,  387,
 /*  1370 */   106,  106,  843,   49,   49,  108,  556,  107,    4,  443,
 /*  1380 */   566,  565,   50,   50, 1011,  225,  564,  313,  564,   96,
 /*  1390 */   564,  228,  559,  524,  147,  312,   38, 1123,  564,  394,
 /*  1400 */   466,  328,  280,   98,  544,  564,   17,  564,  323,   63,
 /*  1410 */    63,   64,   64,   65,   65,  443, 1011, 1011, 1013, 1014,
 /*  1420 */    27,   14,   14,  289,  564,  227,  564,  553,   66,   66,
 /*  1430 */   128,  128,  477,  162,  564,  309,  135,  564, 1003,  277,
 /*  1440 */   252,  533,  564, 1501,  564,  418,  534,   67,   67,   52,
 /*  1450 */    52,  564, 1287,  226,  564, 1500, 1021,   68,   68,  208,
 /*  1460 */    69,   69,  106,  106, 1286,   53,   53,  157,  157,  107,
 /*  1470 */   873,  443,  566,  565,  158,  158, 1011,   76,   76,  564,
 /*  1480 */   357,  564,  108,  556,  471,    4,  252,  408,  885,  884,
 /*  1490 */   356,  564,  306,  555,  564,  473,  564,  252,  481,  559,
 /*  1500 */   564,  334,   54,   54,   72,   72,  564,  230, 1011, 1011,
 /*  1510 */  1013, 1014,   27,  564,  129,  129,  449,   73,   73,  130,
 /*  1520 */   130,  564,  443,  131,  131,  519,  564,  873,  564,  127,
 /*  1530 */   127,  333, 1071,   98,  553, 1349,  156,  156,  564,  495,
 /*  1540 */   347,  249,   98,  338,  155,  155,  892,  893,  533,  136,
 /*  1550 */   136,  134,  134,  532,  341, 1171,  445, 1587,  564,  279,
 /*  1560 */   343,  132,  132, 1021,  390,  390,  389,  264,  387,  106,
 /*  1570 */   106,  843,  564, 1067,  564,  249,  107,  564,  443,  566,
 /*  1580 */   565,  133,  133, 1011,  225, 1015,  313,  108,  556, 1071,
 /*  1590 */     4,  345,  968,  969,  312,   75,   75,   77,   77, 1300,
 /*  1600 */    74,   74,  564, 1132,  559,  564,  108,  556,  959,    4,
 /*  1610 */   252,  923, 1083,  110, 1083, 1011, 1011, 1013, 1014,   27,
 /*  1620 */  1082, 1285, 1082,  559,  227,   42,   42,  443,   48,   48,
 /*  1630 */  1284,  856,  162,  145,  924,  135,  110,  352,  362,  553,
 /*  1640 */  1340, 1361, 1015, 1408, 1336,  301,  443, 1561, 1347,  550,
 /*  1650 */  1414,  551,  226,  202, 1265, 1333, 1256, 1244,  553, 1243,
 /*  1660 */   490, 1245, 1580,  267,   11,  391,  210,  223, 1021, 1390,
 /*  1670 */  1395,  282,  365,  367,  106,  106,  930,  369,  454,  285,
 /*  1680 */  1383,  107,  325,  443,  566,  565,  408, 1021, 1011,  326,
 /*  1690 */   475,  306,  555,  106,  106,  100,  556,  500,    4, 1400,
 /*  1700 */   107, 1399,  443,  566,  565,  398, 1283, 1011,  214,  355,
 /*  1710 */  1473,  290,  559, 1472, 1583,  449,  554,  371,  331,  197,
 /*  1720 */  1011, 1011, 1013, 1014,   27,  198,  209,  385, 1222,  173,
 /*  1730 */   221,  256, 1520, 1518, 1219,  443,   79,  416,  206, 1011,
 /*  1740 */  1011, 1013, 1014,   27,   83,  279,  182,  553,   82,  167,
 /*  1750 */   390,  390,  389,  264,  387,   35, 1396,  843, 1478,  459,
 /*  1760 */   175,  177,  460,  493,  178,  179,  180,  233,   96,  396,
 /*  1770 */   225, 1402,  313, 1401,   36, 1404, 1021,  467,  186,  482,
 /*  1780 */   312,  399,  106,  106,  237, 1467,   89, 1489,  488,  107,
 /*  1790 */   239,  443,  566,  565,  268,  336, 1011,  190,  491,  340,
 /*  1800 */   240,  401, 1246,  241,  509, 1294,  430, 1303,   91,  877,
 /*  1810 */   227,  215, 1566, 1302, 1301, 1273, 1598,  432,  162,  518,
 /*  1820 */  1272,  135, 1597,  354,  402,  433, 1271, 1596, 1011, 1011,
 /*  1830 */  1013, 1014,   27, 1293,  299,  360,  300,  525,  226,   95,
 /*  1840 */   254,  255, 1344,  364,  436,  125,  544, 1552,   10, 1453,
 /*  1850 */   379, 1551,  102,  304,   97,  528,   34,  568, 1177,  263,
 /*  1860 */   265,  266,  569, 1241, 1236,  172,  409,  410,  159,  383,
 /*  1870 */   377,  366,  408, 1345, 1343,  368,  370,  306,  555, 1342,
 /*  1880 */  1326, 1325, 1368,  201,  384, 1367, 1505, 1506,  160, 1504,
 /*  1890 */  1503,  142,  161,  211,  212,   78,  830,  444,  203,  308,
 /*  1900 */   297,  449,  222, 1081,  139, 1079,  316,  174,  163, 1203,
 /*  1910 */   229,  176,  232,  909,  324, 1095,  164,  181,  165,  419,
 /*  1920 */   421,  183,   85,   86,   87,   88,  166, 1098,  235,  234,
 /*  1930 */  1094,  152,   18,  236,  335, 1087,  252, 1216,  487,  238,
 /*  1940 */    37,  187,  188,  845,  492,  356,  242,  348,  496,  189,
 /*  1950 */    90,   93,   19,   20,  168,  875,  501,  351,   92,  504,
 /*  1960 */   888,  153,  511, 1133, 1165,  154,  298, 1047,   94, 1134,
 /*  1970 */    39,  958,  216,  271,  273,  192,  953,  110, 1151,  251,
 /*  1980 */  1155,   21, 1159,   22, 1158, 1139, 1153,   33,   23,   24,
 /*  1990 */   540,   25,  195,   98,   26, 1062, 1048, 1046, 1050, 1104,
 /*  2000 */     7, 1103,  257,  258, 1051,   28,   40,  560, 1016,  857,
 /*  2010 */   109,   29,  919,  138,  259,  260,  170, 1589,  388, 1588,
 /*  2020 */  1173, 1172,

};
static const YYCODETYPE yy_lookahead[] = {
 /*     0 */   192,  273,  274,  275,  192,  192,  273,  274,  275,  192,
 /*    10 */   218,  215,  192,  218,  192,  212,  234,  235,  205,   19,
 /*    20 */    11,  192,  294,  215,  216,  203,  192,  203,  209,  210,
 /*    30 */   211,   31,  215,  216,  205,  215,  216,  215,  216,   39,
 /*    40 */   227,  215,  229,   43,   44,   45,   46,   47,   48,   49,
 /*    50 */    50,   51,   52,   53,   54,   55,   56,   57,  192,   19,
 /*    60 */   238,  239,  238,  239,  215,  273,  274,  275,  273,  274,
 /*    70 */   275,  237,   21,  251,  252,  251,  273,  274,  275,  255,
 /*    80 */   256,  215,  216,   43,   44,   45,   46,   47,   48,   49,
 /*    90 */    50,   51,   52,   53,   54,   55,   56,   57,  209,  210,
 /*   100 */   211,   76,  102,  103,  104,  105,  106,  107,  108,  109,
 /*   110 */   110,  111,  112,   59,   89,  111,  112,   92,  252,  307,
 /*   120 */   308,  313,  314,   25,  312,  192,   86,  261,   88,   19,
 /*   130 */   313,   80,  315,  313,  314,   25,  127,  128,   54,   55,
 /*   140 */    56,   57,  102,  103,  104,  105,  106,  107,  108,  109,
 /*   150 */   110,  111,  112,   43,   44,   45,   46,   47,   48,   49,
 /*   160 */    50,   51,   52,   53,   54,   55,   56,   57,  192,  115,
 /*   170 */   116,  117,  118,  122,  192,  121,  122,  123,  202,   69,
 /*   180 */   204,   22,   23,   16,   25,  131,  102,  103,  104,  105,
 /*   190 */   106,  107,  108,  109,  110,  111,  112,  215,  216,   19,
 /*   200 */    54,   55,   56,   57,   58,  108,  109,  110,  111,  112,
 /*   210 */   192,  160,  102,  103,  104,  105,  106,  107,  108,  109,
 /*   220 */   110,  111,  112,   43,   44,   45,   46,   47,   48,   49,
 /*   230 */    50,   51,   52,   53,   54,   55,   56,   57,   19,  141,
 /*   240 */   307,  308,  272,   24,   77,  312,   79,   67,  102,  103,
 /*   250 */   104,  105,  106,  107,  108,  109,  110,  111,  112,  277,
 /*   260 */   101,  112,   43,   44,   45,   46,   47,   48,   49,   50,
 /*   270 */    51,   52,   53,   54,   55,   56,   57,   26,  127,  128,
 /*   280 */   310,  311,  102,  103,  104,  105,  106,  107,  108,  109,
 /*   290 */   110,  111,  112,  184,  185,  186,  187,  188,  189,  186,
 /*   300 */   187,  188,  189,  194,   76,  196,  192,  194,   19,  196,
 /*   310 */    59,   25,  203,  192,   59,   87,  203,   89,  164,  165,
 /*   320 */    92,  102,  103,  104,  105,  106,  107,  108,  109,  110,
 /*   330 */   111,  112,   43,   44,   45,   46,   47,   48,   49,   50,
 /*   340 */    51,   52,   53,   54,   55,   56,   57,  238,  239,   73,
 /*   350 */   192,  238,  239,   22,   23,  100,   25,   81,  237,  229,
 /*   360 */   251,   23,  204,   25,  251,  272,  115,  116,  117,  214,
 /*   370 */   115,  116,  144,  192,  265,  120,  262,  222,  265,  102,
 /*   380 */   103,  104,  105,  106,  107,  108,  109,  110,  111,  112,
 /*   390 */   192,  102,  103,  104,  105,  106,  107,  108,  109,  110,
 /*   400 */   111,  112,  126,  310,  311,  192,  297,  152,  153,  154,
 /*   410 */   297,  125,  192,  137,  138,   19,  295,  100,  192,   23,
 /*   420 */    22,  106,  107,  108,  109,  110,  111,  112,  215,  216,
 /*   430 */   106,  107,  101,  116,  192,  215,  216,  120,  149,   43,
 /*   440 */    44,   45,   46,   47,   48,   49,   50,   51,   52,   53,
 /*   450 */    54,   55,   56,   57,  222,  117,  224,   59,   19,  187,
 /*   460 */    59,  189,   23,  282,  232,  252,  194,  192,  196,  152,
 /*   470 */   153,  154,  252,   72,  261,  203,  152,  248,  154,  250,
 /*   480 */   142,  261,   43,   44,   45,   46,   47,   48,   49,   50,
 /*   490 */    51,   52,   53,   54,   55,   56,   57,  192,  102,  103,
 /*   500 */   104,  105,  106,  107,  108,  109,  110,  111,  112,  267,
 /*   510 */   238,  239,  237,  115,  116,  117,  115,  116,  117,  192,
 /*   520 */    59,  118,  192,  251,  121,  122,  123,   73,   19,  192,
 /*   530 */    59,  192,   23,   72,  131,  308,   22,  265,   22,  312,
 /*   540 */    24,  102,  103,  104,  105,  106,  107,  108,  109,  110,
 /*   550 */   111,  112,   43,   44,   45,   46,   47,   48,   49,   50,
 /*   560 */    51,   52,   53,   54,   55,   56,   57,   19,  192,  297,
 /*   570 */   192,   23,  267,   59,  203,   59,  115,  116,  117,  108,
 /*   580 */   126,  127,  128,  192,  192,  192,  115,  116,  117,  262,
 /*   590 */    59,   43,   44,   45,   46,   47,   48,   49,   50,   51,
 /*   600 */    52,   53,   54,   55,   56,   57,  267,  215,  216,  238,
 /*   610 */   239,  102,  103,  104,  105,  106,  107,  108,  109,  110,
 /*   620 */   111,  112,  251,   45,   46,   47,   59,   49,  291,  115,
 /*   630 */   116,  117,  116,   81,  192,  305,  306,   19,  192,  268,
 /*   640 */    19,   23,   22,  192,  252,   24,  115,  116,  117,  192,
 /*   650 */   102,  103,  104,  105,  106,  107,  108,  109,  110,  111,
 /*   660 */   112,   43,   44,   45,   46,   47,   48,   49,   50,   51,
 /*   670 */    52,   53,   54,   55,   56,   57,   19,   22,   23,   59,
 /*   680 */    23,  303,  115,  116,  117,  192,  240,  234,  235,  137,
 /*   690 */   138,  240,  308,  192,   22,  192,  312,   22,  120,  306,
 /*   700 */    43,   44,   45,   46,   47,   48,   49,   50,   51,   52,
 /*   710 */    53,   54,   55,   56,   57,  197,   95,  150,  215,  216,
 /*   720 */   102,  103,  104,  105,  106,  107,  108,  109,  110,  111,
 /*   730 */   112,   59,  231,  112,   59,  115,  116,  117,   25,  118,
 /*   740 */   119,  120,  121,  122,  123,  124,   19,  243,   81,  303,
 /*   750 */    23,  130,  192,  192,  303,  252,  101,  253,  203,  102,
 /*   760 */   103,  104,  105,  106,  107,  108,  109,  110,  111,  112,
 /*   770 */    43,   44,   45,   46,   47,   48,   49,   50,   51,   52,
 /*   780 */    53,   54,   55,   56,   57,   19,  119,  115,  116,  117,
 /*   790 */   115,  116,  117,  238,  239,  238,  239,  192,  280,  192,
 /*   800 */   240,  192,  284,  192,  137,  138,  251,  192,  251,   43,
 /*   810 */    44,   45,   46,   47,   48,   49,   50,   51,   52,   53,
 /*   820 */    54,   55,   56,   57,  192,   35,  215,  216,  267,  102,
 /*   830 */   103,  104,  105,  106,  107,  108,  109,  110,  111,  112,
 /*   840 */    59,  230,  237,  192,   25,  192,  192,  215,  216,  240,
 /*   850 */   137,  138,  237,   16,  200,   19,   66,  192,  133,  205,
 /*   860 */   135,  136,  230,  303,   74,  203,  215,  216,  102,  103,
 /*   870 */   104,  105,  106,  107,  108,  109,  110,  111,  112,   43,
 /*   880 */    44,   45,   46,   47,   48,   49,   50,   51,   52,   53,
 /*   890 */    54,   55,   56,   57,  192,   76,  115,  116,  117,   19,
 /*   900 */   238,  239,  192,  252,  126,  127,  128,  192,   89,  238,
 /*   910 */   239,   92,  303,  251,   77,  262,   79,  215,  216,  129,
 /*   920 */   210,  211,  251,  142,  158,   45,   46,   47,   48,   49,
 /*   930 */    50,   51,   52,   53,   54,   55,   56,   57,  102,  103,
 /*   940 */   104,  105,  106,  107,  108,  109,  110,  111,  112,   12,
 /*   950 */    59,  308,  192,  212,  252,  312,  291,  192,    7,    8,
 /*   960 */     9,  300,  301,  203,   27,  126,  127,  128,  308,  207,
 /*   970 */   208,  192,  312,   29,  192,  215,  216,   33,  192,   42,
 /*   980 */   215,  216,  102,  103,  104,  105,  106,  107,  108,  109,
 /*   990 */   110,  111,  112,  283,  158,  230,   66,  160,  238,  239,
 /*  1000 */    63,  215,  216,  192,  192,   12,  115,  116,  117,   65,
 /*  1010 */    73,  251,  252,  192,   19,   85,  230,  192,   24,   24,
 /*  1020 */    27,  261,  210,  211,   94,  192,  215,  216,   22,  207,
 /*  1030 */   208,  290,  192,  142,   19,   42,  215,  216,   43,   44,
 /*  1040 */    45,   46,   47,   48,   49,   50,   51,   52,   53,   54,
 /*  1050 */    55,   56,   57,   59,   19,  144,   63,  192,   43,   44,
 /*  1060 */    45,   46,   47,   48,   49,   50,   51,   52,   53,   54,
 /*  1070 */    55,   56,   57,  252,  163,  145,  114,   22,   43,   44,
 /*  1080 */    45,   46,   47,   48,   49,   50,   51,   52,   53,   54,
 /*  1090 */    55,   56,   57,   45,  212,  283,  263,  102,  103,  104,
 /*  1100 */   105,  106,  107,  108,  109,  110,  111,  112,   59,  192,
 /*  1110 */   116,  149,  106,  107,   59,   25,  291,  102,  103,  104,
 /*  1120 */   105,  106,  107,  108,  109,  110,  111,  112,  192,   22,
 /*  1130 */   192,  192,  215,  216,   23,  192,   25,  102,  103,  104,
 /*  1140 */   105,  106,  107,  108,  109,  110,  111,  112,  108,  192,
 /*  1150 */   192,  215,  216,  215,  216,  106,  107,   19,  215,  216,
 /*  1160 */    53,   59,  114,  114,  115,  116,  117,  285,  119,  137,
 /*  1170 */   138,  116,  290,  230,  134,  192,  127,  192,  192,  139,
 /*  1180 */    59,  192,   44,   45,   46,   47,   48,   49,   50,   51,
 /*  1190 */    52,   53,   54,   55,   56,   57,  308,   76,  215,  216,
 /*  1200 */   312,  152,  263,  154,  215,  216,  192,  117,   87,   19,
 /*  1210 */    89,   19,   20,   92,   22,   22,   23,  231,  116,  230,
 /*  1220 */   263,  263,  237,  203,  298,  299,  203,  239,   36,  215,
 /*  1230 */   216,  192,  142,  192,   15,   45,  115,  116,  117,  251,
 /*  1240 */   102,  103,  104,  105,  106,  107,  108,  109,  110,  111,
 /*  1250 */   112,   59,  192,  203,  215,  216,  215,  216,  238,  239,
 /*  1260 */   192,  238,  239,   71,  192,  144,   25,  203,  243,  230,
 /*  1270 */   243,  251,  192,   81,  251,  215,  216,  243,  253,   60,
 /*  1280 */   253,  255,  256,   19,   20,   25,   22,  253,  238,  239,
 /*  1290 */   192,  192,  100,  192,  101,  215,  216,   19,  106,  107,
 /*  1300 */    36,  251,  238,  239,  114,  113,  192,  115,  116,  117,
 /*  1310 */   192,   47,  120,  215,  216,  251,  215,  216,  192,   31,
 /*  1320 */   130,  134,  243,   59,  148,  149,  139,   39,  192,  137,
 /*  1330 */   138,  263,  253,  215,  216,   71,   19,  157,  192,  159,
 /*  1340 */   128,  215,  216,   25,  152,  153,  154,  155,  156,   85,
 /*  1350 */   192,  215,  216,  268,   90,    0,    1,    2,  192,  192,
 /*  1360 */     5,  215,  216,  151,  100,   10,   11,   12,   13,   14,
 /*  1370 */   106,  107,   17,  215,  216,   19,   20,  113,   22,  115,
 /*  1380 */   116,  117,  215,  216,  120,   30,  192,   32,  192,  148,
 /*  1390 */   192,   24,   36,  115,   22,   40,   24,   23,  192,   25,
 /*  1400 */   128,   23,   99,   25,  144,  192,   22,  192,  192,  215,
 /*  1410 */   216,  215,  216,  215,  216,   59,  152,  153,  154,  155,
 /*  1420 */   156,  215,  216,  151,  192,   70,  192,   71,  215,  216,
 /*  1430 */   215,  216,  115,   78,  192,  132,   81,  192,   23,   22,
 /*  1440 */    25,   85,  192,  192,  192,   61,   90,  215,  216,  215,
 /*  1450 */   216,  192,  225,   98,  192,  192,  100,  215,  216,  141,
 /*  1460 */   215,  216,  106,  107,  225,  215,  216,  215,  216,  113,
 /*  1470 */    59,  115,  116,  117,  215,  216,  120,  215,  216,  192,
 /*  1480 */   120,  192,   19,   20,   23,   22,   25,  132,  119,  120,
 /*  1490 */   130,  192,  137,  138,  192,   23,  192,   25,  192,   36,
 /*  1500 */   192,  192,  215,  216,  215,  216,  192,  140,  152,  153,
 /*  1510 */   154,  155,  156,  192,  215,  216,  161,  215,  216,  215,
 /*  1520 */   216,  192,   59,  215,  216,   19,  192,  116,  192,  215,
 /*  1530 */   216,   23,   59,   25,   71,  192,  215,  216,  192,   23,
 /*  1540 */    23,   25,   25,  192,  215,  216,    7,    8,   85,  215,
 /*  1550 */   216,  215,  216,   90,  192,    1,    2,  140,  192,    5,
 /*  1560 */   192,  215,  216,  100,   10,   11,   12,   13,   14,  106,
 /*  1570 */   107,   17,  192,   23,  192,   25,  113,  192,  115,  116,
 /*  1580 */   117,  215,  216,  120,   30,   59,   32,   19,   20,  116,
 /*  1590 */    22,  192,   83,   84,   40,  215,  216,  215,  216,  192,
 /*  1600 */   215,  216,  192,   97,   36,  192,   19,   20,   23,   22,
 /*  1610 */    25,   23,  152,   25,  154,  152,  153,  154,  155,  156,
 /*  1620 */   152,  225,  154,   36,   70,  215,  216,   59,  215,  216,
 /*  1630 */   192,   23,   78,   25,   23,   81,   25,  192,  192,   71,
 /*  1640 */   257,  192,  116,  192,  192,  254,   59,  317,  192,  192,
 /*  1650 */   192,  235,   98,  241,  192,  254,  192,  192,   71,  192,
 /*  1660 */   287,  192,  192,  286,  242,  190,  213,  296,  100,  266,
 /*  1670 */   270,  244,  254,  254,  106,  107,  108,  254,  258,  258,
 /*  1680 */   266,  113,  292,  115,  116,  117,  132,  100,  120,  245,
 /*  1690 */   292,  137,  138,  106,  107,   19,   20,  219,   22,  270,
 /*  1700 */   113,  270,  115,  116,  117,  270,  224,  120,  228,  218,

 /*  1710 */   218,  245,   36,  218,  195,  161,  279,  258,  244,  248,
 /*  1720 */   152,  153,  154,  155,  156,  248,  242,  244,   60,  296,
 /*  1730 */   296,  140,  199,  199,   38,   59,  293,  199,  149,  152,
 /*  1740 */   153,  154,  155,  156,  150,    5,   22,   71,  293,   43,
 /*  1750 */    10,   11,   12,   13,   14,  269,  271,   17,  282,   18,
 /*  1760 */   233,  236,  199,   18,  236,  236,  236,  198,  148,  245,
 /*  1770 */    30,  271,   32,  271,  269,  233,  100,  245,  233,  199,
 /*  1780 */    40,  245,  106,  107,  198,  245,  157,  289,   62,  113,
 /*  1790 */   198,  115,  116,  117,  199,  288,  120,   22,  220,  199,
 /*  1800 */   198,  220,  199,  198,  114,  226,   64,  217,   22,  125,
 /*  1810 */    70,  164,  311,  217,  217,  217,  223,   24,   78,  304,
 /*  1820 */   219,   81,  223,  217,  220,  112,  217,  217,  152,  153,
 /*  1830 */   154,  155,  156,  226,  281,  220,  281,  143,   98,  114,
 /*  1840 */   199,   91,  260,  259,   82,  147,  144,  316,   22,  276,
 /*  1850 */   199,  316,  157,  278,  146,  145,   25,  201,   13,  193,
 /*  1860 */   193,    6,  191,  191,  191,  299,  302,  302,  206,  246,
 /*  1870 */   248,  259,  132,  260,  260,  259,  259,  137,  138,  260,
 /*  1880 */   249,  249,  264,  247,  245,  264,  212,  212,  206,  212,
 /*  1890 */   212,  221,  206,  213,  213,  212,    4,    3,   22,  162,
 /*  1900 */   221,  161,   15,   23,   16,   23,  138,  150,  129,   25,
 /*  1910 */    24,  141,  143,   20,   16,    1,  129,  141,  129,   61,
 /*  1920 */    37,  150,   53,   53,   53,   53,  129,  115,  140,   34,
 /*  1930 */     1,    5,   22,  114,  160,   68,   25,   75,   41,  140,
 /*  1940 */    24,   68,  114,   20,   19,  130,  124,   23,   67,   22,
 /*  1950 */    22,  148,   22,   22,   37,   59,   67,   24,   22,   96,
 /*  1960 */    28,   23,   22,   97,   23,   23,   67,   23,   25,   23,
 /*  1970 */    22,  115,  140,   23,   23,   22,  142,   25,   88,   34,
 /*  1980 */    75,   34,   75,   34,   93,   23,   86,   22,   34,   34,
 /*  1990 */    24,   34,   25,   25,   34,   23,   23,   23,   23,   23,
 /*  2000 */    44,   23,   25,   22,   11,   22,   22,   25,   23,   23,
 /*  2010 */    22,   22,  134,   23,  140,  140,   25,  140,   15,  140,
 /*  2020 */     1,    1,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2030 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2040 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2050 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2060 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2070 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2080 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2090 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2100 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2110 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2120 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2130 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2140 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2150 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2160 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2170 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2180 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2190 */   318,  318,  318,  318,  318,  318,  318,  318,  318,  318,
 /*  2200 */   318,  318,  318,  318,  318,  318,


};
#define YY_SHIFT_COUNT    (571)
#define YY_SHIFT_MIN      (0)
#define YY_SHIFT_MAX      (2020)
static const unsigned short int yy_shift_ofst[] = {
 /*     0 */  1554, 1355, 1740, 1192, 1192,  552, 1264, 1356, 1463, 1587,
 /*    10 */  1587, 1587,  276,    0,    0,  180, 1015, 1587, 1587, 1587,
 /*    20 */  1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587,
 /*    30 */  1049, 1049, 1121, 1121,   54,  667,  552,  552,  552,  552,
 /*    40 */   552,   40,  110,  219,  289,  396,  439,  509,  548,  618,
 /*    50 */   657,  727,  766,  836,  995, 1015, 1015, 1015, 1015, 1015,
 /*    60 */  1015, 1015, 1015, 1015, 1015, 1015, 1015, 1015, 1015, 1015,
 /*    70 */  1015, 1015, 1015, 1035, 1015, 1138,  880,  880, 1568, 1587,
 /*    80 */  1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587,
 /*    90 */  1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587,
 /*   100 */  1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587, 1587,
 /*   110 */  1587, 1587, 1587, 1676, 1587, 1587, 1587, 1587, 1587, 1587,
 /*   120 */  1587, 1587, 1587, 1587, 1587, 1587, 1587,  146,   84,   84,
 /*   130 */    84,   84,   84,  277,  315,  401,   97,  461,  251,  531,
 /*   140 */   531,   51, 1190,  531,  531,  324,  324,  531,  713,  713,
 /*   150 */   713,  713,  151,  154,  154,    4,  149, 2022, 2022,  621,
 /*   160 */   621,  621,  567,  398,  398,  398,  398,  937,  937,  228,
 /*   170 */   251,  159,  331,  531,  531,  531,  531,  531,  531,  531,
 /*   180 */   531,  531,  531,  531,  531,  531,  531,  531,  531,  531,
 /*   190 */   531,  531,  531,  819,  819,  531,    9,   25,   25, 1102,
 /*   200 */  1102,  911, 1032, 2022, 2022, 2022, 2022, 2022, 2022, 2022,
 /*   210 */   255,  317,  317,  514,  403,  620,  471,  672,  781,  891,
 /*   220 */   675,  531,  531,  531,  531,  531,  531,  531,  531,  531,
 /*   230 */   531,  454,  531,  531,  531,  531,  531,  531,  531,  531,
 /*   240 */   531,  531,  531,  531,  790,  790,  790,  531,  531,  531,
 /*   250 */   338,  531,  531,  531,  516,  930,  531,  531,  993,  531,
 /*   260 */   531,  531,  531,  531,  531,  531,  531,  778,  944,  725,
 /*   270 */   994,  994,  994,  994, 1090,  725,  725, 1040, 1006,  951,
 /*   280 */  1219,  962, 1176,   98, 1278, 1176, 1278, 1317, 1241,  962,
 /*   290 */   962, 1241,  962,   98, 1317,  286, 1111, 1048, 1288, 1288,
 /*   300 */  1288, 1278, 1260, 1260, 1180, 1318, 1187, 1372, 1668, 1668,
 /*   310 */  1591, 1591, 1696, 1696, 1591, 1594, 1589, 1724, 1706, 1741,
 /*   320 */  1741, 1741, 1741, 1591, 1745, 1620, 1589, 1589, 1620, 1724,
 /*   330 */  1706, 1620, 1706, 1620, 1591, 1745, 1629, 1726, 1591, 1745,
 /*   340 */  1775, 1591, 1745, 1591, 1745, 1775, 1690, 1690, 1690, 1742,
 /*   350 */  1786, 1786, 1775, 1690, 1684, 1690, 1742, 1690, 1690, 1647,
 /*   360 */  1793, 1713, 1713, 1775, 1694, 1725, 1694, 1725, 1694, 1725,
 /*   370 */  1694, 1725, 1591, 1750, 1750, 1762, 1762, 1698, 1702, 1826,
 /*   380 */  1591, 1695, 1698, 1708, 1710, 1620, 1831, 1845, 1845, 1855,
 /*   390 */  1855, 1855, 2022, 2022, 2022, 2022, 2022, 2022, 2022, 2022,
 /*   400 */  2022, 2022, 2022, 2022, 2022, 2022, 2022,  578,  837,  655,
 /*   410 */  1193,  167,  839, 1055, 1374, 1303, 1107, 1367, 1212, 1272,
 /*   420 */  1378, 1384, 1415, 1461, 1472, 1508, 1516, 1517, 1411, 1369,
 /*   430 */  1539, 1360, 1506, 1473, 1550, 1585, 1509, 1588, 1460, 1468,
 /*   440 */  1608, 1611, 1526, 1417, 1892, 1894, 1876, 1737, 1887, 1888,
 /*   450 */  1880, 1882, 1768, 1757, 1779, 1884, 1884, 1886, 1770, 1893,
 /*   460 */  1769, 1898, 1914, 1776, 1787, 1884, 1789, 1858, 1883, 1884,
 /*   470 */  1771, 1869, 1870, 1871, 1872, 1797, 1812, 1895, 1788, 1929,
 /*   480 */  1926, 1910, 1819, 1774, 1867, 1911, 1873, 1862, 1897, 1799,
 /*   490 */  1828, 1916, 1923, 1925, 1815, 1822, 1927, 1881, 1928, 1930,
 /*   500 */  1924, 1931, 1889, 1896, 1933, 1863, 1932, 1936, 1899, 1917,
 /*   510 */  1938, 1803, 1940, 1941, 1942, 1944, 1943, 1946, 1948, 1866,
 /*   520 */  1832, 1950, 1951, 1856, 1945, 1953, 1834, 1952, 1947, 1949,
 /*   530 */  1954, 1955, 1890, 1905, 1900, 1956, 1907, 1891, 1957, 1962,
 /*   540 */  1965, 1966, 1967, 1968, 1960, 1972, 1952, 1973, 1974, 1975,
 /*   550 */  1976, 1977, 1978, 1981, 1993, 1983, 1984, 1985, 1986, 1988,
 /*   560 */  1989, 1982, 1878, 1874, 1875, 1877, 1879, 1991, 1990, 2003,
 /*   570 */  2019, 2020,
};
#define YY_REDUCE_COUNT (406)
#define YY_REDUCE_MIN   (-272)
#define YY_REDUCE_MAX   (1686)
static const short yy_reduce_ofst[] = {
 /*     0 */   109,  113,  272,  760, -178, -176, -192, -183, -180, -134,
 /*    10 */   213,  220,  371, -208, -205, -272, -197,  611,  632,  765,
 /*    20 */   786,  392,  943,  989,  503,  651, 1039,  -18,  702,  821,
 /*    30 */   710,  812, -188,  -67, -187,  555,  662, 1020, 1023, 1050,
 /*    40 */  1064, -267, -267, -267, -267, -267, -267, -267, -267, -267,
 /*    50 */  -267, -267, -267, -267, -267, -267, -267, -267, -267, -267,
 /*    60 */  -267, -267, -267, -267, -267, -267, -267, -267, -267, -267,
 /*    70 */  -267, -267, -267, -267, -267, -267, -267, -267,  811,  917,
 /*    80 */   936,  938,  983, 1014, 1041, 1060, 1080, 1098, 1101, 1118,
 /*    90 */  1126, 1136, 1146, 1158, 1167, 1194, 1196, 1198, 1206, 1213,
 /*   100 */  1215, 1232, 1234, 1242, 1245, 1250, 1252, 1259, 1262, 1287,
 /*   110 */  1289, 1299, 1302, 1304, 1308, 1314, 1321, 1329, 1334, 1336,
 /*   120 */  1346, 1366, 1380, 1382, 1385, 1410, 1413, -267, -267, -267,
 /*   130 */  -267, -267, -267, -267, -267,  446, -267,  451,  -24,  121,
 /*   140 */   560,  518,  232,  609,  330, -181, -111,  654,  557,  671,
 /*   150 */   557,  671,  882,  -30,   93, -267, -267, -267, -267,  155,
 /*   160 */   155,  155,  181,  242,  305,  339,  561, -218,  453,  227,
 /*   170 */   158,  661,  661, -171,  114,  327,  653, -166,  275,  605,
 /*   180 */   615,  337,  833,  665,  939,  957,  825,  958,  985,  501,
 /*   190 */   986,  378, 1068,  384,  643,  393,  741,  660,  888,  762,
 /*   200 */   822,  229,  988,  926,  504, 1025, 1027, 1034, 1026, 1079,
 /*   210 */  -204, -174, -151,   18,  130,  198,  226,  376,  391,  442,
 /*   220 */   457,  493,  607,  715,  779,  782,  840,  865, 1072, 1099,
 /*   230 */  1114, 1085, 1166, 1216, 1251, 1263, 1306, 1309, 1343, 1351,
 /*   240 */  1362, 1368, 1399, 1407, 1227, 1239, 1396, 1438, 1445, 1446,
 /*   250 */  1383, 1449, 1451, 1452, 1391, 1330, 1456, 1457, 1416, 1458,
 /*   260 */   226, 1462, 1464, 1465, 1467, 1469, 1470, 1373, 1377, 1412,
 /*   270 */  1401, 1418, 1419, 1423, 1383, 1412, 1412, 1422, 1453, 1475,
 /*   280 */  1371, 1400, 1403, 1427, 1420, 1414, 1421, 1390, 1444, 1429,
 /*   290 */  1431, 1466, 1435, 1474, 1398, 1478, 1480, 1482, 1491, 1492,
 /*   300 */  1495, 1459, 1471, 1477, 1437, 1483, 1484, 1519, 1433, 1434,
 /*   310 */  1533, 1534, 1443, 1455, 1538, 1476, 1485, 1486, 1527, 1525,
 /*   320 */  1528, 1529, 1530, 1563, 1569, 1524, 1500, 1502, 1532, 1505,
 /*   330 */  1542, 1536, 1545, 1540, 1580, 1586, 1498, 1507, 1595, 1592,
 /*   340 */  1578, 1600, 1602, 1603, 1605, 1581, 1590, 1596, 1597, 1579,
 /*   350 */  1593, 1599, 1604, 1598, 1601, 1606, 1607, 1609, 1610, 1501,
 /*   360 */  1515, 1553, 1555, 1615, 1582, 1584, 1613, 1612, 1614, 1616,
 /*   370 */  1619, 1617, 1641, 1531, 1535, 1618, 1621, 1631, 1622, 1573,
 /*   380 */  1651, 1575, 1632, 1636, 1623, 1639, 1656, 1666, 1667, 1671,
 /*   390 */  1672, 1673, 1564, 1565, 1566, 1662, 1674, 1675, 1677, 1678,
 /*   400 */  1682, 1670, 1679, 1680, 1681, 1683, 1686,
};
static const YYACTIONTYPE yy_default[] = {
 /*     0 */  1633, 1633, 1633, 1462, 1230, 1341, 1230, 1230, 1230, 1462,
 /*    10 */  1462, 1462, 1230, 1371, 1371, 1515, 1263, 1230, 1230, 1230,
 /*    20 */  1230, 1230, 1230, 1230, 1230, 1230, 1230, 1461, 1230, 1230,
 /*    30 */  1230, 1230, 1550, 1550, 1230, 1230, 1230, 1230, 1230, 1230,
 /*    40 */  1230, 1230, 1380, 1230, 1387, 1230, 1230, 1230, 1230, 1230,
159928
159929
159930
159931
159932
159933
159934
159935
159936
159937
159938

159939
159940
159941
159942
159943
159944
159945
   59,  /*   DATABASE => ID */
   59,  /*       DESC => ID */
   59,  /*     DETACH => ID */
   59,  /*       EACH => ID */
   59,  /*       FAIL => ID */
    0,  /*         OR => nothing */
    0,  /*        AND => nothing */
    0,  /*         IS => nothing */
   59,  /*      MATCH => ID */
   59,  /*    LIKE_KW => ID */
    0,  /*    BETWEEN => nothing */

    0,  /*         IN => nothing */
    0,  /*     ISNULL => nothing */
    0,  /*    NOTNULL => nothing */
    0,  /*         NE => nothing */
    0,  /*         EQ => nothing */
    0,  /*         GT => nothing */
    0,  /*         LE => nothing */







<



>







161294
161295
161296
161297
161298
161299
161300

161301
161302
161303
161304
161305
161306
161307
161308
161309
161310
161311
   59,  /*   DATABASE => ID */
   59,  /*       DESC => ID */
   59,  /*     DETACH => ID */
   59,  /*       EACH => ID */
   59,  /*       FAIL => ID */
    0,  /*         OR => nothing */
    0,  /*        AND => nothing */

   59,  /*      MATCH => ID */
   59,  /*    LIKE_KW => ID */
    0,  /*    BETWEEN => nothing */
    0,  /*         IS => nothing */
    0,  /*         IN => nothing */
    0,  /*     ISNULL => nothing */
    0,  /*    NOTNULL => nothing */
    0,  /*         NE => nothing */
    0,  /*         EQ => nothing */
    0,  /*         GT => nothing */
    0,  /*         LE => nothing */
160118
160119
160120
160121
160122
160123
160124

160125
160126
160127
160128
160129
160130
160131
160132
160133
160134
#else
  yyStackEntry yystack[YYSTACKDEPTH];  /* The parser's stack */
  yyStackEntry *yystackEnd;            /* Last entry in the stack */
#endif
};
typedef struct yyParser yyParser;


#ifndef NDEBUG
/* #include <stdio.h> */
/* #include <assert.h> */
static FILE *yyTraceFILE = 0;
static char *yyTracePrompt = 0;
#endif /* NDEBUG */

#ifndef NDEBUG
/*
** Turn parser tracing on by giving a stream to which to write the trace







>


<







161484
161485
161486
161487
161488
161489
161490
161491
161492
161493

161494
161495
161496
161497
161498
161499
161500
#else
  yyStackEntry yystack[YYSTACKDEPTH];  /* The parser's stack */
  yyStackEntry *yystackEnd;            /* Last entry in the stack */
#endif
};
typedef struct yyParser yyParser;

/* #include <assert.h> */
#ifndef NDEBUG
/* #include <stdio.h> */

static FILE *yyTraceFILE = 0;
static char *yyTracePrompt = 0;
#endif /* NDEBUG */

#ifndef NDEBUG
/*
** Turn parser tracing on by giving a stream to which to write the trace
160200
160201
160202
160203
160204
160205
160206
160207
160208
160209
160210
160211
160212
160213
160214
160215
160216
160217
  /*   38 */ "DATABASE",
  /*   39 */ "DESC",
  /*   40 */ "DETACH",
  /*   41 */ "EACH",
  /*   42 */ "FAIL",
  /*   43 */ "OR",
  /*   44 */ "AND",
  /*   45 */ "IS",
  /*   46 */ "MATCH",
  /*   47 */ "LIKE_KW",
  /*   48 */ "BETWEEN",
  /*   49 */ "IN",
  /*   50 */ "ISNULL",
  /*   51 */ "NOTNULL",
  /*   52 */ "NE",
  /*   53 */ "EQ",
  /*   54 */ "GT",
  /*   55 */ "LE",







|
|
|
|







161566
161567
161568
161569
161570
161571
161572
161573
161574
161575
161576
161577
161578
161579
161580
161581
161582
161583
  /*   38 */ "DATABASE",
  /*   39 */ "DESC",
  /*   40 */ "DETACH",
  /*   41 */ "EACH",
  /*   42 */ "FAIL",
  /*   43 */ "OR",
  /*   44 */ "AND",
  /*   45 */ "MATCH",
  /*   46 */ "LIKE_KW",
  /*   47 */ "BETWEEN",
  /*   48 */ "IS",
  /*   49 */ "IN",
  /*   50 */ "ISNULL",
  /*   51 */ "NOTNULL",
  /*   52 */ "NE",
  /*   53 */ "EQ",
  /*   54 */ "GT",
  /*   55 */ "LE",
163869
163870
163871
163872
163873
163874
163875
163876
163877

163878
163879
163880
163881
163882
163883
163884

  while(1){ /* Exit by "break" */
    assert( yypParser->yytos>=yypParser->yystack );
    assert( yyact==yypParser->yytos->stateno );
    yyact = yy_find_shift_action((YYCODETYPE)yymajor,yyact);
    if( yyact >= YY_MIN_REDUCE ){
      unsigned int yyruleno = yyact - YY_MIN_REDUCE; /* Reduce by this rule */
      assert( yyruleno<(int)(sizeof(yyRuleName)/sizeof(yyRuleName[0])) );
#ifndef NDEBUG

      if( yyTraceFILE ){
        int yysize = yyRuleInfoNRhs[yyruleno];
        if( yysize ){
          fprintf(yyTraceFILE, "%sReduce %d [%s]%s, pop back to state %d.\n",
            yyTracePrompt,
            yyruleno, yyRuleName[yyruleno],
            yyruleno<YYNRULE_WITH_ACTION ? "" : " without external action",







<

>







165235
165236
165237
165238
165239
165240
165241

165242
165243
165244
165245
165246
165247
165248
165249
165250

  while(1){ /* Exit by "break" */
    assert( yypParser->yytos>=yypParser->yystack );
    assert( yyact==yypParser->yytos->stateno );
    yyact = yy_find_shift_action((YYCODETYPE)yymajor,yyact);
    if( yyact >= YY_MIN_REDUCE ){
      unsigned int yyruleno = yyact - YY_MIN_REDUCE; /* Reduce by this rule */

#ifndef NDEBUG
      assert( yyruleno<(int)(sizeof(yyRuleName)/sizeof(yyRuleName[0])) );
      if( yyTraceFILE ){
        int yysize = yyRuleInfoNRhs[yyruleno];
        if( yysize ){
          fprintf(yyTraceFILE, "%sReduce %d [%s]%s, pop back to state %d.\n",
            yyTracePrompt,
            yyruleno, yyRuleName[yyruleno],
            yyruleno<YYNRULE_WITH_ACTION ? "" : " without external action",
165117
165118
165119
165120
165121
165122
165123

165124
165125
165126
165127
165128
165129
165130
  int nErr = 0;                   /* Number of errors encountered */
  void *pEngine;                  /* The LEMON-generated LALR(1) parser */
  int n = 0;                      /* Length of the next token token */
  int tokenType;                  /* type of the next token */
  int lastTokenParsed = -1;       /* type of the previous token */
  sqlite3 *db = pParse->db;       /* The database connection */
  int mxSqlLen;                   /* Max length of an SQL string */

#ifdef sqlite3Parser_ENGINEALWAYSONSTACK
  yyParser sEngine;    /* Space to hold the Lemon-generated Parser object */
#endif
  VVA_ONLY( u8 startedWithOom = db->mallocFailed );

  assert( zSql!=0 );
  mxSqlLen = db->aLimit[SQLITE_LIMIT_SQL_LENGTH];







>







166483
166484
166485
166486
166487
166488
166489
166490
166491
166492
166493
166494
166495
166496
166497
  int nErr = 0;                   /* Number of errors encountered */
  void *pEngine;                  /* The LEMON-generated LALR(1) parser */
  int n = 0;                      /* Length of the next token token */
  int tokenType;                  /* type of the next token */
  int lastTokenParsed = -1;       /* type of the previous token */
  sqlite3 *db = pParse->db;       /* The database connection */
  int mxSqlLen;                   /* Max length of an SQL string */
  Parse *pParentParse = 0;        /* Outer parse context, if any */
#ifdef sqlite3Parser_ENGINEALWAYSONSTACK
  yyParser sEngine;    /* Space to hold the Lemon-generated Parser object */
#endif
  VVA_ONLY( u8 startedWithOom = db->mallocFailed );

  assert( zSql!=0 );
  mxSqlLen = db->aLimit[SQLITE_LIMIT_SQL_LENGTH];
165152
165153
165154
165155
165156
165157
165158
165159
165160
165161
165162
165163
165164
165165
165166
    return SQLITE_NOMEM_BKPT;
  }
#endif
  assert( pParse->pNewTable==0 );
  assert( pParse->pNewTrigger==0 );
  assert( pParse->nVar==0 );
  assert( pParse->pVList==0 );
  pParse->pParentParse = db->pParse;
  db->pParse = pParse;
  while( 1 ){
    n = sqlite3GetToken((u8*)zSql, &tokenType);
    mxSqlLen -= n;
    if( mxSqlLen<0 ){
      pParse->rc = SQLITE_TOOBIG;
      break;







|







166519
166520
166521
166522
166523
166524
166525
166526
166527
166528
166529
166530
166531
166532
166533
    return SQLITE_NOMEM_BKPT;
  }
#endif
  assert( pParse->pNewTable==0 );
  assert( pParse->pNewTrigger==0 );
  assert( pParse->nVar==0 );
  assert( pParse->pVList==0 );
  pParentParse = db->pParse;
  db->pParse = pParse;
  while( 1 ){
    n = sqlite3GetToken((u8*)zSql, &tokenType);
    mxSqlLen -= n;
    if( mxSqlLen<0 ){
      pParse->rc = SQLITE_TOOBIG;
      break;
165267
165268
165269
165270
165271
165272
165273
165274
165275
165276
165277
165278
165279
165280
165281
165282
    */
    sqlite3DeleteTable(db, pParse->pNewTable);
  }
  if( !IN_RENAME_OBJECT ){
    sqlite3DeleteTrigger(db, pParse->pNewTrigger);
  }
  sqlite3DbFree(db, pParse->pVList);
  db->pParse = pParse->pParentParse;
  pParse->pParentParse = 0;
  assert( nErr==0 || pParse->rc!=SQLITE_OK );
  return nErr;
}


#ifdef SQLITE_ENABLE_NORMALIZE
/*







|
<







166634
166635
166636
166637
166638
166639
166640
166641

166642
166643
166644
166645
166646
166647
166648
    */
    sqlite3DeleteTable(db, pParse->pNewTable);
  }
  if( !IN_RENAME_OBJECT ){
    sqlite3DeleteTrigger(db, pParse->pNewTrigger);
  }
  sqlite3DbFree(db, pParse->pVList);
  db->pParse = pParentParse;

  assert( nErr==0 || pParse->rc!=SQLITE_OK );
  return nErr;
}


#ifdef SQLITE_ENABLE_NORMALIZE
/*
166937
166938
166939
166940
166941
166942
166943
166944


166945
166946
166947
166948
166949
166950
166951
/*
** Invoke the destructor function associated with FuncDef p, if any. Except,
** if this is not the last copy of the function, do not invoke it. Multiple
** copies of a single function are created when create_function() is called
** with SQLITE_ANY as the encoding.
*/
static void functionDestroy(sqlite3 *db, FuncDef *p){
  FuncDestructor *pDestructor = p->u.pDestructor;


  if( pDestructor ){
    pDestructor->nRef--;
    if( pDestructor->nRef==0 ){
      pDestructor->xDestroy(pDestructor->pUserData);
      sqlite3DbFree(db, pDestructor);
    }
  }







|
>
>







168303
168304
168305
168306
168307
168308
168309
168310
168311
168312
168313
168314
168315
168316
168317
168318
168319
/*
** Invoke the destructor function associated with FuncDef p, if any. Except,
** if this is not the last copy of the function, do not invoke it. Multiple
** copies of a single function are created when create_function() is called
** with SQLITE_ANY as the encoding.
*/
static void functionDestroy(sqlite3 *db, FuncDef *p){
  FuncDestructor *pDestructor;
  assert( (p->funcFlags & SQLITE_FUNC_BUILTIN)==0 );
  pDestructor = p->u.pDestructor;
  if( pDestructor ){
    pDestructor->nRef--;
    if( pDestructor->nRef==0 ){
      pDestructor->xDestroy(pDestructor->pUserData);
      sqlite3DbFree(db, pDestructor);
    }
  }
167200
167201
167202
167203
167204
167205
167206



167207
167208
167209
167210
167211
167212
167213
  /* The temp-database schema is allocated differently from the other schema
  ** objects (using sqliteMalloc() directly, instead of sqlite3BtreeSchema()).
  ** So it needs to be freed here. Todo: Why not roll the temp schema into
  ** the same sqliteMalloc() as the one that allocates the database
  ** structure?
  */
  sqlite3DbFree(db, db->aDb[1].pSchema);



  sqlite3_mutex_leave(db->mutex);
  db->eOpenState = SQLITE_STATE_CLOSED;
  sqlite3_mutex_free(db->mutex);
  assert( sqlite3LookasideUsed(db,0)==0 );
  if( db->lookaside.bMalloced ){
    sqlite3_free(db->lookaside.pStart);
  }







>
>
>







168568
168569
168570
168571
168572
168573
168574
168575
168576
168577
168578
168579
168580
168581
168582
168583
168584
  /* The temp-database schema is allocated differently from the other schema
  ** objects (using sqliteMalloc() directly, instead of sqlite3BtreeSchema()).
  ** So it needs to be freed here. Todo: Why not roll the temp schema into
  ** the same sqliteMalloc() as the one that allocates the database
  ** structure?
  */
  sqlite3DbFree(db, db->aDb[1].pSchema);
  if( db->xAutovacDestr ){
    db->xAutovacDestr(db->pAutovacPagesArg);
  }
  sqlite3_mutex_leave(db->mutex);
  db->eOpenState = SQLITE_STATE_CLOSED;
  sqlite3_mutex_free(db->mutex);
  assert( sqlite3LookasideUsed(db,0)==0 );
  if( db->lookaside.bMalloced ){
    sqlite3_free(db->lookaside.pStart);
  }
167254
167255
167256
167257
167258
167259
167260
167261
167262
167263
167264
167265
167266
167267
167268
    sqlite3ResetAllSchemasOfConnection(db);
  }
  sqlite3BtreeLeaveAll(db);

  /* Any deferred constraint violations have now been resolved. */
  db->nDeferredCons = 0;
  db->nDeferredImmCons = 0;
  db->flags &= ~(u64)SQLITE_DeferFKs;

  /* If one has been configured, invoke the rollback-hook callback */
  if( db->xRollbackCallback && (inTrans || !db->autoCommit) ){
    db->xRollbackCallback(db->pRollbackArg);
  }
}








|







168625
168626
168627
168628
168629
168630
168631
168632
168633
168634
168635
168636
168637
168638
168639
    sqlite3ResetAllSchemasOfConnection(db);
  }
  sqlite3BtreeLeaveAll(db);

  /* Any deferred constraint violations have now been resolved. */
  db->nDeferredCons = 0;
  db->nDeferredImmCons = 0;
  db->flags &= ~(u64)(SQLITE_DeferFKs|SQLITE_CorruptRdOnly);

  /* If one has been configured, invoke the rollback-hook callback */
  if( db->xRollbackCallback && (inTrans || !db->autoCommit) ){
    db->xRollbackCallback(db->pRollbackArg);
  }
}

167618
167619
167620
167621
167622
167623
167624
167625
167626
167627
167628
167629
167630
167631
167632
167633
167634
167635
167636
167637
167638
167639
167640
167641
167642
  void (*xStep)(sqlite3_context*,int,sqlite3_value **),
  void (*xFinal)(sqlite3_context*),
  void (*xValue)(sqlite3_context*),
  void (*xInverse)(sqlite3_context*,int,sqlite3_value **),
  FuncDestructor *pDestructor
){
  FuncDef *p;
  int nName;
  int extraFlags;

  assert( sqlite3_mutex_held(db->mutex) );
  assert( xValue==0 || xSFunc==0 );
  if( zFunctionName==0                /* Must have a valid name */
   || (xSFunc!=0 && xFinal!=0)        /* Not both xSFunc and xFinal */
   || ((xFinal==0)!=(xStep==0))       /* Both or neither of xFinal and xStep */
   || ((xValue==0)!=(xInverse==0))    /* Both or neither of xValue, xInverse */
   || (nArg<-1 || nArg>SQLITE_MAX_FUNCTION_ARG)
   || (255<(nName = sqlite3Strlen30( zFunctionName)))
  ){
    return SQLITE_MISUSE_BKPT;
  }

  assert( SQLITE_FUNC_CONSTANT==SQLITE_DETERMINISTIC );
  assert( SQLITE_FUNC_DIRECT==SQLITE_DIRECTONLY );
  extraFlags = enc &  (SQLITE_DETERMINISTIC|SQLITE_DIRECTONLY|







<









|







168989
168990
168991
168992
168993
168994
168995

168996
168997
168998
168999
169000
169001
169002
169003
169004
169005
169006
169007
169008
169009
169010
169011
169012
  void (*xStep)(sqlite3_context*,int,sqlite3_value **),
  void (*xFinal)(sqlite3_context*),
  void (*xValue)(sqlite3_context*),
  void (*xInverse)(sqlite3_context*,int,sqlite3_value **),
  FuncDestructor *pDestructor
){
  FuncDef *p;

  int extraFlags;

  assert( sqlite3_mutex_held(db->mutex) );
  assert( xValue==0 || xSFunc==0 );
  if( zFunctionName==0                /* Must have a valid name */
   || (xSFunc!=0 && xFinal!=0)        /* Not both xSFunc and xFinal */
   || ((xFinal==0)!=(xStep==0))       /* Both or neither of xFinal and xStep */
   || ((xValue==0)!=(xInverse==0))    /* Both or neither of xValue, xInverse */
   || (nArg<-1 || nArg>SQLITE_MAX_FUNCTION_ARG)
   || (255<sqlite3Strlen30(zFunctionName))
  ){
    return SQLITE_MISUSE_BKPT;
  }

  assert( SQLITE_FUNC_CONSTANT==SQLITE_DETERMINISTIC );
  assert( SQLITE_FUNC_DIRECT==SQLITE_DIRECTONLY );
  extraFlags = enc &  (SQLITE_DETERMINISTIC|SQLITE_DIRECTONLY|
168101
168102
168103
168104
168105
168106
168107




























168108
168109
168110
168111
168112
168113
168114
  pRet = db->pPreUpdateArg;
  db->xPreUpdateCallback = xCallback;
  db->pPreUpdateArg = pArg;
  sqlite3_mutex_leave(db->mutex);
  return pRet;
}
#endif /* SQLITE_ENABLE_PREUPDATE_HOOK */





























#ifndef SQLITE_OMIT_WAL
/*
** The sqlite3_wal_hook() callback registered by sqlite3_wal_autocheckpoint().
** Invoke sqlite3_wal_checkpoint if the number of frames in the log file
** is greater than sqlite3.pWalArg cast to an integer (the value configured by
** wal_autocheckpoint()).







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







169471
169472
169473
169474
169475
169476
169477
169478
169479
169480
169481
169482
169483
169484
169485
169486
169487
169488
169489
169490
169491
169492
169493
169494
169495
169496
169497
169498
169499
169500
169501
169502
169503
169504
169505
169506
169507
169508
169509
169510
169511
169512
  pRet = db->pPreUpdateArg;
  db->xPreUpdateCallback = xCallback;
  db->pPreUpdateArg = pArg;
  sqlite3_mutex_leave(db->mutex);
  return pRet;
}
#endif /* SQLITE_ENABLE_PREUPDATE_HOOK */

/*
** Register a function to be invoked prior to each autovacuum that
** determines the number of pages to vacuum.
*/
SQLITE_API int sqlite3_autovacuum_pages(
  sqlite3 *db,                 /* Attach the hook to this database */
  unsigned int (*xCallback)(void*,const char*,u32,u32,u32),
  void *pArg,                  /* Argument to the function */
  void (*xDestructor)(void*)   /* Destructor for pArg */
){
#ifdef SQLITE_ENABLE_API_ARMOR
  if( !sqlite3SafetyCheckOk(db) ){
    if( xDestructor ) xDestructor(pArg);
    return SQLITE_MISUSE_BKPT;
  }
#endif
  sqlite3_mutex_enter(db->mutex);
  if( db->xAutovacDestr ){
    db->xAutovacDestr(db->pAutovacPagesArg);
  }
  db->xAutovacPages = xCallback;
  db->pAutovacPagesArg = pArg;
  db->xAutovacDestr = xDestructor;
  sqlite3_mutex_leave(db->mutex);
  return SQLITE_OK;
}


#ifndef SQLITE_OMIT_WAL
/*
** The sqlite3_wal_hook() callback registered by sqlite3_wal_autocheckpoint().
** Invoke sqlite3_wal_checkpoint if the number of frames in the log file
** is greater than sqlite3.pWalArg cast to an integer (the value configured by
** wal_autocheckpoint()).
168624
168625
168626
168627
168628
168629
168630


168631
168632
168633
168634
168635
168636
168637
  if( limitId<0 || limitId>=SQLITE_N_LIMIT ){
    return -1;
  }
  oldLimit = db->aLimit[limitId];
  if( newLimit>=0 ){                   /* IMP: R-52476-28732 */
    if( newLimit>aHardLimit[limitId] ){
      newLimit = aHardLimit[limitId];  /* IMP: R-51463-25634 */


    }
    db->aLimit[limitId] = newLimit;
  }
  return oldLimit;                     /* IMP: R-53341-35419 */
}

/*







>
>







170022
170023
170024
170025
170026
170027
170028
170029
170030
170031
170032
170033
170034
170035
170036
170037
  if( limitId<0 || limitId>=SQLITE_N_LIMIT ){
    return -1;
  }
  oldLimit = db->aLimit[limitId];
  if( newLimit>=0 ){                   /* IMP: R-52476-28732 */
    if( newLimit>aHardLimit[limitId] ){
      newLimit = aHardLimit[limitId];  /* IMP: R-51463-25634 */
    }else if( newLimit<1 && limitId==SQLITE_LIMIT_LENGTH ){
      newLimit = 1;
    }
    db->aLimit[limitId] = newLimit;
  }
  return oldLimit;                     /* IMP: R-53341-35419 */
}

/*
168895
168896
168897
168898
168899
168900
168901
168902
168903
168904
168905
168906
168907
168908
168909

/*
** This routine does the core work of extracting URI parameters from a
** database filename for the sqlite3_uri_parameter() interface.
*/
static const char *uriParameter(const char *zFilename, const char *zParam){
  zFilename += sqlite3Strlen30(zFilename) + 1;
  while( zFilename[0] ){
    int x = strcmp(zFilename, zParam);
    zFilename += sqlite3Strlen30(zFilename) + 1;
    if( x==0 ) return zFilename;
    zFilename += sqlite3Strlen30(zFilename) + 1;
  }
  return 0;
}







|







170295
170296
170297
170298
170299
170300
170301
170302
170303
170304
170305
170306
170307
170308
170309

/*
** This routine does the core work of extracting URI parameters from a
** database filename for the sqlite3_uri_parameter() interface.
*/
static const char *uriParameter(const char *zFilename, const char *zParam){
  zFilename += sqlite3Strlen30(zFilename) + 1;
  while( ALWAYS(zFilename!=0) && zFilename[0] ){
    int x = strcmp(zFilename, zParam);
    zFilename += sqlite3Strlen30(zFilename) + 1;
    if( x==0 ) return zFilename;
    zFilename += sqlite3Strlen30(zFilename) + 1;
  }
  return 0;
}
168955
168956
168957
168958
168959
168960
168961
168962
168963
168964
168965

168966
168967
168968
168969
168970
168971
168972

  /* Remove harmful bits from the flags parameter
  **
  ** The SQLITE_OPEN_NOMUTEX and SQLITE_OPEN_FULLMUTEX flags were
  ** dealt with in the previous code block.  Besides these, the only
  ** valid input flags for sqlite3_open_v2() are SQLITE_OPEN_READONLY,
  ** SQLITE_OPEN_READWRITE, SQLITE_OPEN_CREATE, SQLITE_OPEN_SHAREDCACHE,
  ** SQLITE_OPEN_PRIVATECACHE, and some reserved bits.  Silently mask
  ** off all other flags.
  */
  flags &=  ~( SQLITE_OPEN_DELETEONCLOSE |

               SQLITE_OPEN_MAIN_DB |
               SQLITE_OPEN_TEMP_DB |
               SQLITE_OPEN_TRANSIENT_DB |
               SQLITE_OPEN_MAIN_JOURNAL |
               SQLITE_OPEN_TEMP_JOURNAL |
               SQLITE_OPEN_SUBJOURNAL |
               SQLITE_OPEN_SUPER_JOURNAL |







|
|


>







170355
170356
170357
170358
170359
170360
170361
170362
170363
170364
170365
170366
170367
170368
170369
170370
170371
170372
170373

  /* Remove harmful bits from the flags parameter
  **
  ** The SQLITE_OPEN_NOMUTEX and SQLITE_OPEN_FULLMUTEX flags were
  ** dealt with in the previous code block.  Besides these, the only
  ** valid input flags for sqlite3_open_v2() are SQLITE_OPEN_READONLY,
  ** SQLITE_OPEN_READWRITE, SQLITE_OPEN_CREATE, SQLITE_OPEN_SHAREDCACHE,
  ** SQLITE_OPEN_PRIVATECACHE, SQLITE_OPEN_EXRESCODE, and some reserved
  ** bits.  Silently mask off all other flags.
  */
  flags &=  ~( SQLITE_OPEN_DELETEONCLOSE |
               SQLITE_OPEN_EXCLUSIVE |
               SQLITE_OPEN_MAIN_DB |
               SQLITE_OPEN_TEMP_DB |
               SQLITE_OPEN_TRANSIENT_DB |
               SQLITE_OPEN_MAIN_JOURNAL |
               SQLITE_OPEN_TEMP_JOURNAL |
               SQLITE_OPEN_SUBJOURNAL |
               SQLITE_OPEN_SUPER_JOURNAL |
168990
168991
168992
168993
168994
168995
168996
168997
168998
168999
169000
169001
169002
169003
169004
      goto opendb_out;
    }
    if( isThreadsafe==0 ){
      sqlite3MutexWarnOnContention(db->mutex);
    }
  }
  sqlite3_mutex_enter(db->mutex);
  db->errMask = 0xff;
  db->nDb = 2;
  db->eOpenState = SQLITE_STATE_BUSY;
  db->aDb = db->aDbStatic;
  db->lookaside.bDisable = 1;
  db->lookaside.sz = 0;

  assert( sizeof(db->aLimit)==sizeof(aHardLimit) );







|







170391
170392
170393
170394
170395
170396
170397
170398
170399
170400
170401
170402
170403
170404
170405
      goto opendb_out;
    }
    if( isThreadsafe==0 ){
      sqlite3MutexWarnOnContention(db->mutex);
    }
  }
  sqlite3_mutex_enter(db->mutex);
  db->errMask = (flags & SQLITE_OPEN_EXRESCODE)!=0 ? 0xffffffff : 0xff;
  db->nDb = 2;
  db->eOpenState = SQLITE_STATE_BUSY;
  db->aDb = db->aDbStatic;
  db->lookaside.bDisable = 1;
  db->lookaside.sz = 0;

  assert( sizeof(db->aLimit)==sizeof(aHardLimit) );
169222
169223
169224
169225
169226
169227
169228
169229
169230
169231
169232
169233
169234
169235
169236
169237
169238
169239
169240
169241
169242
169243
169244
169245
169246
169247
169248
169249
169250
169251
169252
opendb_out:
  if( db ){
    assert( db->mutex!=0 || isThreadsafe==0
           || sqlite3GlobalConfig.bFullMutex==0 );
    sqlite3_mutex_leave(db->mutex);
  }
  rc = sqlite3_errcode(db);
  assert( db!=0 || rc==SQLITE_NOMEM );
  if( rc==SQLITE_NOMEM ){
    sqlite3_close(db);
    db = 0;
  }else if( rc!=SQLITE_OK ){
    db->eOpenState = SQLITE_STATE_SICK;
  }
  *ppDb = db;
#ifdef SQLITE_ENABLE_SQLLOG
  if( sqlite3GlobalConfig.xSqllog ){
    /* Opening a db handle. Fourth parameter is passed 0. */
    void *pArg = sqlite3GlobalConfig.pSqllogArg;
    sqlite3GlobalConfig.xSqllog(pArg, db, zFilename, 0);
  }
#endif
  sqlite3_free_filename(zOpen);
  return rc & 0xff;
}


/*
** Open a new database handle.
*/
SQLITE_API int sqlite3_open(







|
|














|







170623
170624
170625
170626
170627
170628
170629
170630
170631
170632
170633
170634
170635
170636
170637
170638
170639
170640
170641
170642
170643
170644
170645
170646
170647
170648
170649
170650
170651
170652
170653
opendb_out:
  if( db ){
    assert( db->mutex!=0 || isThreadsafe==0
           || sqlite3GlobalConfig.bFullMutex==0 );
    sqlite3_mutex_leave(db->mutex);
  }
  rc = sqlite3_errcode(db);
  assert( db!=0 || (rc&0xff)==SQLITE_NOMEM );
  if( (rc&0xff)==SQLITE_NOMEM ){
    sqlite3_close(db);
    db = 0;
  }else if( rc!=SQLITE_OK ){
    db->eOpenState = SQLITE_STATE_SICK;
  }
  *ppDb = db;
#ifdef SQLITE_ENABLE_SQLLOG
  if( sqlite3GlobalConfig.xSqllog ){
    /* Opening a db handle. Fourth parameter is passed 0. */
    void *pArg = sqlite3GlobalConfig.pSqllogArg;
    sqlite3GlobalConfig.xSqllog(pArg, db, zFilename, 0);
  }
#endif
  sqlite3_free_filename(zOpen);
  return rc;
}


/*
** Open a new database handle.
*/
SQLITE_API int sqlite3_open(
170026
170027
170028
170029
170030
170031
170032

170033
170034


170035
170036
170037
170038

170039
170040
170041
170042
170043
170044
170045
    **
    ** If onOff==0 and tnum>0 then reset the schema for all databases, causing
    ** the schema to be reparsed the next time it is needed.  This has the
    ** effect of erasing all imposter tables.
    */
    case SQLITE_TESTCTRL_IMPOSTER: {
      sqlite3 *db = va_arg(ap, sqlite3*);

      sqlite3_mutex_enter(db->mutex);
      db->init.iDb = sqlite3FindDbName(db, va_arg(ap,const char*));


      db->init.busy = db->init.imposterTable = va_arg(ap,int);
      db->init.newTnum = va_arg(ap,int);
      if( db->init.busy==0 && db->init.newTnum>0 ){
        sqlite3ResetAllSchemasOfConnection(db);

      }
      sqlite3_mutex_leave(db->mutex);
      break;
    }

#if defined(YYCOVERAGE)
    /*  sqlite3_test_control(SQLITE_TESTCTRL_PARSER_COVERAGE, FILE *out)







>

|
>
>
|
|
|
|
>







171427
171428
171429
171430
171431
171432
171433
171434
171435
171436
171437
171438
171439
171440
171441
171442
171443
171444
171445
171446
171447
171448
171449
171450
    **
    ** If onOff==0 and tnum>0 then reset the schema for all databases, causing
    ** the schema to be reparsed the next time it is needed.  This has the
    ** effect of erasing all imposter tables.
    */
    case SQLITE_TESTCTRL_IMPOSTER: {
      sqlite3 *db = va_arg(ap, sqlite3*);
      int iDb;
      sqlite3_mutex_enter(db->mutex);
      iDb = sqlite3FindDbName(db, va_arg(ap,const char*));
      if( iDb>=0 ){
        db->init.iDb = iDb;
        db->init.busy = db->init.imposterTable = va_arg(ap,int);
        db->init.newTnum = va_arg(ap,int);
        if( db->init.busy==0 && db->init.newTnum>0 ){
          sqlite3ResetAllSchemasOfConnection(db);
        }
      }
      sqlite3_mutex_leave(db->mutex);
      break;
    }

#if defined(YYCOVERAGE)
    /*  sqlite3_test_control(SQLITE_TESTCTRL_PARSER_COVERAGE, FILE *out)
170106
170107
170108
170109
170110
170111
170112




















170113
170114
170115
170116
170117
170118
170119
         case 0:   *ptr = sqlite3SelectTrace;      break;
         case 1:   sqlite3SelectTrace = *ptr;      break;
         case 2:   *ptr = sqlite3WhereTrace;       break;
         case 3:   sqlite3WhereTrace = *ptr;       break;
       }
       break;
    }





















#if defined(SQLITE_DEBUG) && !defined(SQLITE_OMIT_WSD)
    /* sqlite3_test_control(SQLITE_TESTCTRL_TUNE, id, *piValue)
    **
    ** If "id" is an integer between 1 and SQLITE_NTUNE then set the value
    ** of the id-th tuning parameter to *piValue.  If "id" is between -1
    ** and -SQLITE_NTUNE, then write the current value of the (-id)-th







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







171511
171512
171513
171514
171515
171516
171517
171518
171519
171520
171521
171522
171523
171524
171525
171526
171527
171528
171529
171530
171531
171532
171533
171534
171535
171536
171537
171538
171539
171540
171541
171542
171543
171544
         case 0:   *ptr = sqlite3SelectTrace;      break;
         case 1:   sqlite3SelectTrace = *ptr;      break;
         case 2:   *ptr = sqlite3WhereTrace;       break;
         case 3:   sqlite3WhereTrace = *ptr;       break;
       }
       break;
    }

    /* sqlite3_test_control(SQLITE_TESTCTRL_LOGEST,
    **      double fIn,     // Input value
    **      int *pLogEst,   // sqlite3LogEstFromDouble(fIn)
    **      u64 *pInt,      // sqlite3LogEstToInt(*pLogEst)
    **      int *pLogEst2   // sqlite3LogEst(*pInt)
    ** );
    **
    ** Test access for the LogEst conversion routines.
    */
    case SQLITE_TESTCTRL_LOGEST: {
      double rIn = va_arg(ap, double);
      LogEst rLogEst = sqlite3LogEstFromDouble(rIn);
      u64 iInt = sqlite3LogEstToInt(rLogEst);
      va_arg(ap, int*)[0] = rLogEst;
      va_arg(ap, u64*)[0] = iInt;
      va_arg(ap, int*)[0] = sqlite3LogEst(iInt);
      break;
    }


#if defined(SQLITE_DEBUG) && !defined(SQLITE_OMIT_WSD)
    /* sqlite3_test_control(SQLITE_TESTCTRL_TUNE, id, *piValue)
    **
    ** If "id" is an integer between 1 and SQLITE_NTUNE then set the value
    ** of the id-th tuning parameter to *piValue.  If "id" is between -1
    ** and -SQLITE_NTUNE, then write the current value of the (-id)-th
170243
170244
170245
170246
170247
170248
170249
170250
170251
170252
170253
170254
170255
170256
170257
/*
** Return a pointer to the name of Nth query parameter of the filename.
*/
SQLITE_API const char *sqlite3_uri_key(const char *zFilename, int N){
  if( zFilename==0 || N<0 ) return 0;
  zFilename = databaseName(zFilename);
  zFilename += sqlite3Strlen30(zFilename) + 1;
  while( zFilename[0] && (N--)>0 ){
    zFilename += sqlite3Strlen30(zFilename) + 1;
    zFilename += sqlite3Strlen30(zFilename) + 1;
  }
  return zFilename[0] ? zFilename : 0;
}

/*







|







171668
171669
171670
171671
171672
171673
171674
171675
171676
171677
171678
171679
171680
171681
171682
/*
** Return a pointer to the name of Nth query parameter of the filename.
*/
SQLITE_API const char *sqlite3_uri_key(const char *zFilename, int N){
  if( zFilename==0 || N<0 ) return 0;
  zFilename = databaseName(zFilename);
  zFilename += sqlite3Strlen30(zFilename) + 1;
  while( ALWAYS(zFilename) && zFilename[0] && (N--)>0 ){
    zFilename += sqlite3Strlen30(zFilename) + 1;
    zFilename += sqlite3Strlen30(zFilename) + 1;
  }
  return zFilename[0] ? zFilename : 0;
}

/*
170293
170294
170295
170296
170297
170298
170299
170300
170301
170302
170303
170304
170305
170306
170307
  if( zFilename==0 ) return 0;
  return databaseName(zFilename);
}
SQLITE_API const char *sqlite3_filename_journal(const char *zFilename){
  if( zFilename==0 ) return 0;
  zFilename = databaseName(zFilename);
  zFilename += sqlite3Strlen30(zFilename) + 1;
  while( zFilename[0] ){
    zFilename += sqlite3Strlen30(zFilename) + 1;
    zFilename += sqlite3Strlen30(zFilename) + 1;
  }
  return zFilename + 1;
}
SQLITE_API const char *sqlite3_filename_wal(const char *zFilename){
#ifdef SQLITE_OMIT_WAL







|







171718
171719
171720
171721
171722
171723
171724
171725
171726
171727
171728
171729
171730
171731
171732
  if( zFilename==0 ) return 0;
  return databaseName(zFilename);
}
SQLITE_API const char *sqlite3_filename_journal(const char *zFilename){
  if( zFilename==0 ) return 0;
  zFilename = databaseName(zFilename);
  zFilename += sqlite3Strlen30(zFilename) + 1;
  while( ALWAYS(zFilename) && zFilename[0] ){
    zFilename += sqlite3Strlen30(zFilename) + 1;
    zFilename += sqlite3Strlen30(zFilename) + 1;
  }
  return zFilename + 1;
}
SQLITE_API const char *sqlite3_filename_wal(const char *zFilename){
#ifdef SQLITE_OMIT_WAL
171597
171598
171599
171600
171601
171602
171603
171604



171605
171606
171607
171608
171609
171610
171611
171612
171613
171614
171615
171616
171617
171618
171619
171620
171621
** amalgamation.
*/
#ifndef SQLITE_AMALGAMATION
/*
** Macros indicating that conditional expressions are always true or
** false.
*/
#ifdef SQLITE_COVERAGE_TEST



# define ALWAYS(x) (1)
# define NEVER(X)  (0)
#elif defined(SQLITE_DEBUG)
# define ALWAYS(x) sqlite3Fts3Always((x)!=0)
# define NEVER(x) sqlite3Fts3Never((x)!=0)
SQLITE_PRIVATE int sqlite3Fts3Always(int b);
SQLITE_PRIVATE int sqlite3Fts3Never(int b);
#else
# define ALWAYS(x) (x)
# define NEVER(x)  (x)
#endif

/*
** Internal types used by SQLite.
*/
typedef unsigned char u8;         /* 1-byte (or larger) unsigned integer */
typedef short int i16;            /* 2-byte (or larger) signed integer */







|
>
>
>
|
|
|
|
|
<
<

|
|







173022
173023
173024
173025
173026
173027
173028
173029
173030
173031
173032
173033
173034
173035
173036
173037


173038
173039
173040
173041
173042
173043
173044
173045
173046
173047
** amalgamation.
*/
#ifndef SQLITE_AMALGAMATION
/*
** Macros indicating that conditional expressions are always true or
** false.
*/
#if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_MUTATION_TEST)
# define SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS 1
#endif
#if defined(SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS)
# define ALWAYS(X)      (1)
# define NEVER(X)       (0)
#elif !defined(NDEBUG)
# define ALWAYS(X)      ((X)?1:(assert(0),0))
# define NEVER(X)       ((X)?(assert(0),1):0)


#else
# define ALWAYS(X)      (X)
# define NEVER(X)       (X)
#endif

/*
** Internal types used by SQLite.
*/
typedef unsigned char u8;         /* 1-byte (or larger) unsigned integer */
typedef short int i16;            /* 2-byte (or larger) signed integer */
172066
172067
172068
172069
172070
172071
172072

172073
172074
172075
172076
172077
172078
172079
  char **, int, int, int, const char *, int, Fts3Expr **, char **
);
SQLITE_PRIVATE void sqlite3Fts3ExprFree(Fts3Expr *);
#ifdef SQLITE_TEST
SQLITE_PRIVATE int sqlite3Fts3ExprInitTestInterface(sqlite3 *db, Fts3Hash*);
SQLITE_PRIVATE int sqlite3Fts3InitTerm(sqlite3 *db);
#endif


SQLITE_PRIVATE int sqlite3Fts3OpenTokenizer(sqlite3_tokenizer *, int, const char *, int,
  sqlite3_tokenizer_cursor **
);

/* fts3_aux.c */
SQLITE_PRIVATE int sqlite3Fts3InitAux(sqlite3 *db);







>







173492
173493
173494
173495
173496
173497
173498
173499
173500
173501
173502
173503
173504
173505
173506
  char **, int, int, int, const char *, int, Fts3Expr **, char **
);
SQLITE_PRIVATE void sqlite3Fts3ExprFree(Fts3Expr *);
#ifdef SQLITE_TEST
SQLITE_PRIVATE int sqlite3Fts3ExprInitTestInterface(sqlite3 *db, Fts3Hash*);
SQLITE_PRIVATE int sqlite3Fts3InitTerm(sqlite3 *db);
#endif
SQLITE_PRIVATE void *sqlite3Fts3MallocZero(i64 nByte);

SQLITE_PRIVATE int sqlite3Fts3OpenTokenizer(sqlite3_tokenizer *, int, const char *, int,
  sqlite3_tokenizer_cursor **
);

/* fts3_aux.c */
SQLITE_PRIVATE int sqlite3Fts3InitAux(sqlite3 *db);
172123
172124
172125
172126
172127
172128
172129
172130
172131
172132
172133
172134
172135
172136
172137
172138
172139
172140
172141
172142
172143
#endif

static int fts3EvalNext(Fts3Cursor *pCsr);
static int fts3EvalStart(Fts3Cursor *pCsr);
static int fts3TermSegReaderCursor(
    Fts3Cursor *, const char *, int, int, Fts3MultiSegReader **);

#ifndef SQLITE_AMALGAMATION
# if defined(SQLITE_DEBUG)
SQLITE_PRIVATE int sqlite3Fts3Always(int b) { assert( b ); return b; }
SQLITE_PRIVATE int sqlite3Fts3Never(int b)  { assert( !b ); return b; }
# endif
#endif

/*
** This variable is set to false when running tests for which the on disk
** structures should not be corrupt. Otherwise, true. If it is false, extra
** assert() conditions in the fts3 code are activated - conditions that are
** only true if it is guaranteed that the fts3 database is not corrupt.
*/
#ifdef SQLITE_DEBUG







<
<
<
<
<
<
<







173550
173551
173552
173553
173554
173555
173556







173557
173558
173559
173560
173561
173562
173563
#endif

static int fts3EvalNext(Fts3Cursor *pCsr);
static int fts3EvalStart(Fts3Cursor *pCsr);
static int fts3TermSegReaderCursor(
    Fts3Cursor *, const char *, int, int, Fts3MultiSegReader **);








/*
** This variable is set to false when running tests for which the on disk
** structures should not be corrupt. Otherwise, true. If it is false, extra
** assert() conditions in the fts3 code are activated - conditions that are
** only true if it is guaranteed that the fts3 database is not corrupt.
*/
#ifdef SQLITE_DEBUG
177154
177155
177156
177157
177158
177159
177160
177161
177162
177163
177164
177165
177166
177167
177168
177169
      }

      case FTSQUERY_OR: {
        Fts3Expr *pLeft = pExpr->pLeft;
        Fts3Expr *pRight = pExpr->pRight;
        sqlite3_int64 iCmp = DOCID_CMP(pLeft->iDocid, pRight->iDocid);

        assert( pLeft->bStart || pLeft->iDocid==pRight->iDocid );
        assert( pRight->bStart || pLeft->iDocid==pRight->iDocid );

        if( pRight->bEof || (pLeft->bEof==0 && iCmp<0) ){
          fts3EvalNextRow(pCsr, pLeft, pRc);
        }else if( pLeft->bEof || iCmp>0 ){
          fts3EvalNextRow(pCsr, pRight, pRc);
        }else{
          fts3EvalNextRow(pCsr, pLeft, pRc);







|
|







178574
178575
178576
178577
178578
178579
178580
178581
178582
178583
178584
178585
178586
178587
178588
178589
      }

      case FTSQUERY_OR: {
        Fts3Expr *pLeft = pExpr->pLeft;
        Fts3Expr *pRight = pExpr->pRight;
        sqlite3_int64 iCmp = DOCID_CMP(pLeft->iDocid, pRight->iDocid);

        assert_fts3_nc( pLeft->bStart || pLeft->iDocid==pRight->iDocid );
        assert_fts3_nc( pRight->bStart || pLeft->iDocid==pRight->iDocid );

        if( pRight->bEof || (pLeft->bEof==0 && iCmp<0) ){
          fts3EvalNextRow(pCsr, pLeft, pRc);
        }else if( pLeft->bEof || iCmp>0 ){
          fts3EvalNextRow(pCsr, pRight, pRc);
        }else{
          fts3EvalNextRow(pCsr, pLeft, pRc);
177793
177794
177795
177796
177797
177798
177799



177800
177801
177802
177803
177804
177805
177806
      int bEofSave = pNear->bEof;
      fts3EvalRestart(pCsr, pNear, &rc);
      while( rc==SQLITE_OK && !pNear->bEof ){
        fts3EvalNextRow(pCsr, pNear, &rc);
        if( bEofSave==0 && pNear->iDocid==iDocid ) break;
      }
      assert( rc!=SQLITE_OK || pPhrase->bIncr==0 );



    }
    if( bTreeEof ){
      while( rc==SQLITE_OK && !pNear->bEof ){
        fts3EvalNextRow(pCsr, pNear, &rc);
      }
    }
    if( rc!=SQLITE_OK ) return rc;







>
>
>







179213
179214
179215
179216
179217
179218
179219
179220
179221
179222
179223
179224
179225
179226
179227
179228
179229
      int bEofSave = pNear->bEof;
      fts3EvalRestart(pCsr, pNear, &rc);
      while( rc==SQLITE_OK && !pNear->bEof ){
        fts3EvalNextRow(pCsr, pNear, &rc);
        if( bEofSave==0 && pNear->iDocid==iDocid ) break;
      }
      assert( rc!=SQLITE_OK || pPhrase->bIncr==0 );
      if( rc==SQLITE_OK && pNear->bEof!=bEofSave ){
        rc = FTS_CORRUPT_VTAB;
      }
    }
    if( bTreeEof ){
      while( rc==SQLITE_OK && !pNear->bEof ){
        fts3EvalNextRow(pCsr, pNear, &rc);
      }
    }
    if( rc!=SQLITE_OK ) return rc;
178215
178216
178217
178218
178219
178220
178221

178222
178223
178224
178225
178226
178227
178228
        return SQLITE_OK;
      }
    }

    if( fts3auxGrowStatArray(pCsr, 2) ) return SQLITE_NOMEM;
    memset(pCsr->aStat, 0, sizeof(struct Fts3auxColstats) * pCsr->nStat);
    iCol = 0;


    while( i<nDoclist ){
      sqlite3_int64 v = 0;

      i += sqlite3Fts3GetVarint(&aDoclist[i], &v);
      switch( eState ){
        /* State 0. In this state the integer just read was a docid. */







>







179638
179639
179640
179641
179642
179643
179644
179645
179646
179647
179648
179649
179650
179651
179652
        return SQLITE_OK;
      }
    }

    if( fts3auxGrowStatArray(pCsr, 2) ) return SQLITE_NOMEM;
    memset(pCsr->aStat, 0, sizeof(struct Fts3auxColstats) * pCsr->nStat);
    iCol = 0;
    rc = SQLITE_OK;

    while( i<nDoclist ){
      sqlite3_int64 v = 0;

      i += sqlite3Fts3GetVarint(&aDoclist[i], &v);
      switch( eState ){
        /* State 0. In this state the integer just read was a docid. */
178258
178259
178260
178261
178262
178263
178264




178265
178266
178267
178268
178269
178270
178271
178272
178273
178274
178275
178276
178277
178278
178279
178280
            pCsr->aStat[0].nOcc++;
          }
          break;

        /* State 3. The integer just read is a column number. */
        default: assert( eState==3 );
          iCol = (int)v;




          if( fts3auxGrowStatArray(pCsr, iCol+2) ) return SQLITE_NOMEM;
          pCsr->aStat[iCol+1].nDoc++;
          eState = 2;
          break;
      }
    }

    pCsr->iCol = 0;
    rc = SQLITE_OK;
  }else{
    pCsr->isEof = 1;
  }
  return rc;
}

/*







>
>
>
>








<







179682
179683
179684
179685
179686
179687
179688
179689
179690
179691
179692
179693
179694
179695
179696
179697
179698
179699
179700

179701
179702
179703
179704
179705
179706
179707
            pCsr->aStat[0].nOcc++;
          }
          break;

        /* State 3. The integer just read is a column number. */
        default: assert( eState==3 );
          iCol = (int)v;
          if( iCol<1 ){
            rc = SQLITE_CORRUPT_VTAB;
            break;
          }
          if( fts3auxGrowStatArray(pCsr, iCol+2) ) return SQLITE_NOMEM;
          pCsr->aStat[iCol+1].nDoc++;
          eState = 2;
          break;
      }
    }

    pCsr->iCol = 0;

  }else{
    pCsr->isEof = 1;
  }
  return rc;
}

/*
178595
178596
178597
178598
178599
178600
178601
178602
178603
178604
178605
178606
178607
178608
178609
}

/*
** Allocate nByte bytes of memory using sqlite3_malloc(). If successful,
** zero the memory before returning a pointer to it. If unsuccessful,
** return NULL.
*/
static void *fts3MallocZero(sqlite3_int64 nByte){
  void *pRet = sqlite3_malloc64(nByte);
  if( pRet ) memset(pRet, 0, nByte);
  return pRet;
}

SQLITE_PRIVATE int sqlite3Fts3OpenTokenizer(
  sqlite3_tokenizer *pTokenizer,







|







180022
180023
180024
180025
180026
180027
180028
180029
180030
180031
180032
180033
180034
180035
180036
}

/*
** Allocate nByte bytes of memory using sqlite3_malloc(). If successful,
** zero the memory before returning a pointer to it. If unsuccessful,
** return NULL.
*/
SQLITE_PRIVATE void *sqlite3Fts3MallocZero(sqlite3_int64 nByte){
  void *pRet = sqlite3_malloc64(nByte);
  if( pRet ) memset(pRet, 0, nByte);
  return pRet;
}

SQLITE_PRIVATE int sqlite3Fts3OpenTokenizer(
  sqlite3_tokenizer *pTokenizer,
178676
178677
178678
178679
178680
178681
178682
178683
178684
178685
178686
178687
178688
178689
178690
    const char *zToken;
    int nToken = 0, iStart = 0, iEnd = 0, iPosition = 0;
    sqlite3_int64 nByte;                    /* total space to allocate */

    rc = pModule->xNext(pCursor, &zToken, &nToken, &iStart, &iEnd, &iPosition);
    if( rc==SQLITE_OK ){
      nByte = sizeof(Fts3Expr) + sizeof(Fts3Phrase) + nToken;
      pRet = (Fts3Expr *)fts3MallocZero(nByte);
      if( !pRet ){
        rc = SQLITE_NOMEM;
      }else{
        pRet->eType = FTSQUERY_PHRASE;
        pRet->pPhrase = (Fts3Phrase *)&pRet[1];
        pRet->pPhrase->nToken = 1;
        pRet->pPhrase->iColumn = iCol;







|







180103
180104
180105
180106
180107
180108
180109
180110
180111
180112
180113
180114
180115
180116
180117
    const char *zToken;
    int nToken = 0, iStart = 0, iEnd = 0, iPosition = 0;
    sqlite3_int64 nByte;                    /* total space to allocate */

    rc = pModule->xNext(pCursor, &zToken, &nToken, &iStart, &iEnd, &iPosition);
    if( rc==SQLITE_OK ){
      nByte = sizeof(Fts3Expr) + sizeof(Fts3Phrase) + nToken;
      pRet = (Fts3Expr *)sqlite3Fts3MallocZero(nByte);
      if( !pRet ){
        rc = SQLITE_NOMEM;
      }else{
        pRet->eType = FTSQUERY_PHRASE;
        pRet->pPhrase = (Fts3Phrase *)&pRet[1];
        pRet->pPhrase->nToken = 1;
        pRet->pPhrase->iColumn = iCol;
178931
178932
178933
178934
178935
178936
178937
178938
178939
178940
178941
178942
178943
178944
178945
      ** the next byte must contain either whitespace, an open or close
      ** parenthesis, a quote character, or EOF.
      */
      cNext = zInput[nKey];
      if( fts3isspace(cNext)
       || cNext=='"' || cNext=='(' || cNext==')' || cNext==0
      ){
        pRet = (Fts3Expr *)fts3MallocZero(sizeof(Fts3Expr));
        if( !pRet ){
          return SQLITE_NOMEM;
        }
        pRet->eType = pKey->eType;
        pRet->nNear = nNear;
        *ppExpr = pRet;
        *pnConsumed = (int)((zInput - z) + nKey);







|







180358
180359
180360
180361
180362
180363
180364
180365
180366
180367
180368
180369
180370
180371
180372
      ** the next byte must contain either whitespace, an open or close
      ** parenthesis, a quote character, or EOF.
      */
      cNext = zInput[nKey];
      if( fts3isspace(cNext)
       || cNext=='"' || cNext=='(' || cNext==')' || cNext==0
      ){
        pRet = (Fts3Expr *)sqlite3Fts3MallocZero(sizeof(Fts3Expr));
        if( !pRet ){
          return SQLITE_NOMEM;
        }
        pRet->eType = pKey->eType;
        pRet->nNear = nNear;
        *ppExpr = pRet;
        *pnConsumed = (int)((zInput - z) + nKey);
179110
179111
179112
179113
179114
179115
179116
179117
179118
179119
179120
179121
179122
179123
179124
      if( p ){
        int isPhrase;

        if( !sqlite3_fts3_enable_parentheses
            && p->eType==FTSQUERY_PHRASE && pParse->isNot
        ){
          /* Create an implicit NOT operator. */
          Fts3Expr *pNot = fts3MallocZero(sizeof(Fts3Expr));
          if( !pNot ){
            sqlite3Fts3ExprFree(p);
            rc = SQLITE_NOMEM;
            goto exprparse_out;
          }
          pNot->eType = FTSQUERY_NOT;
          pNot->pRight = p;







|







180537
180538
180539
180540
180541
180542
180543
180544
180545
180546
180547
180548
180549
180550
180551
      if( p ){
        int isPhrase;

        if( !sqlite3_fts3_enable_parentheses
            && p->eType==FTSQUERY_PHRASE && pParse->isNot
        ){
          /* Create an implicit NOT operator. */
          Fts3Expr *pNot = sqlite3Fts3MallocZero(sizeof(Fts3Expr));
          if( !pNot ){
            sqlite3Fts3ExprFree(p);
            rc = SQLITE_NOMEM;
            goto exprparse_out;
          }
          pNot->eType = FTSQUERY_NOT;
          pNot->pRight = p;
179144
179145
179146
179147
179148
179149
179150
179151
179152
179153
179154
179155
179156
179157
179158
            goto exprparse_out;
          }

          if( isPhrase && !isRequirePhrase ){
            /* Insert an implicit AND operator. */
            Fts3Expr *pAnd;
            assert( pRet && pPrev );
            pAnd = fts3MallocZero(sizeof(Fts3Expr));
            if( !pAnd ){
              sqlite3Fts3ExprFree(p);
              rc = SQLITE_NOMEM;
              goto exprparse_out;
            }
            pAnd->eType = FTSQUERY_AND;
            insertBinaryOperator(&pRet, pPrev, pAnd);







|







180571
180572
180573
180574
180575
180576
180577
180578
180579
180580
180581
180582
180583
180584
180585
            goto exprparse_out;
          }

          if( isPhrase && !isRequirePhrase ){
            /* Insert an implicit AND operator. */
            Fts3Expr *pAnd;
            assert( pRet && pPrev );
            pAnd = sqlite3Fts3MallocZero(sizeof(Fts3Expr));
            if( !pAnd ){
              sqlite3Fts3ExprFree(p);
              rc = SQLITE_NOMEM;
              goto exprparse_out;
            }
            pAnd->eType = FTSQUERY_AND;
            insertBinaryOperator(&pRet, pPrev, pAnd);
183374
183375
183376
183377
183378
183379
183380




183381





183382

183383
183384
183385
183386
183387
183388
183389
      Fts3HashElem *pElem = *(pReader->ppNextElem);
      sqlite3_free(pReader->aNode);
      pReader->aNode = 0;
      if( pElem ){
        char *aCopy;
        PendingList *pList = (PendingList *)fts3HashData(pElem);
        int nCopy = pList->nData+1;




        pReader->zTerm = (char *)fts3HashKey(pElem);





        pReader->nTerm = fts3HashKeysize(pElem);

        aCopy = (char*)sqlite3_malloc(nCopy);
        if( !aCopy ) return SQLITE_NOMEM;
        memcpy(aCopy, pList->aData, nCopy);
        pReader->nNode = pReader->nDoclist = nCopy;
        pReader->aNode = pReader->aDoclist = aCopy;
        pReader->ppNextElem++;
        assert( pReader->aNode );







>
>
>
>
|
>
>
>
>
>
|
>







184801
184802
184803
184804
184805
184806
184807
184808
184809
184810
184811
184812
184813
184814
184815
184816
184817
184818
184819
184820
184821
184822
184823
184824
184825
184826
      Fts3HashElem *pElem = *(pReader->ppNextElem);
      sqlite3_free(pReader->aNode);
      pReader->aNode = 0;
      if( pElem ){
        char *aCopy;
        PendingList *pList = (PendingList *)fts3HashData(pElem);
        int nCopy = pList->nData+1;

        int nTerm = fts3HashKeysize(pElem);
        if( (nTerm+1)>pReader->nTermAlloc ){
          sqlite3_free(pReader->zTerm);
          pReader->zTerm = (char*)sqlite3_malloc((nTerm+1)*2);
          if( !pReader->zTerm ) return SQLITE_NOMEM;
          pReader->nTermAlloc = (nTerm+1)*2;
        }
        memcpy(pReader->zTerm, fts3HashKey(pElem), nTerm);
        pReader->zTerm[nTerm] = '\0';
        pReader->nTerm = nTerm;

        aCopy = (char*)sqlite3_malloc(nCopy);
        if( !aCopy ) return SQLITE_NOMEM;
        memcpy(aCopy, pList->aData, nCopy);
        pReader->nNode = pReader->nDoclist = nCopy;
        pReader->aNode = pReader->aDoclist = aCopy;
        pReader->ppNextElem++;
        assert( pReader->aNode );
183628
183629
183630
183631
183632
183633
183634
183635
183636
183637
183638
183639
183640
183641
183642
183643
183644

/*
** Free all allocations associated with the iterator passed as the
** second argument.
*/
SQLITE_PRIVATE void sqlite3Fts3SegReaderFree(Fts3SegReader *pReader){
  if( pReader ){
    if( !fts3SegReaderIsPending(pReader) ){
      sqlite3_free(pReader->zTerm);
    }
    if( !fts3SegReaderIsRootOnly(pReader) ){
      sqlite3_free(pReader->aNode);
    }
    sqlite3_blob_close(pReader->pBlob);
  }
  sqlite3_free(pReader);
}







<
|
<







185065
185066
185067
185068
185069
185070
185071

185072

185073
185074
185075
185076
185077
185078
185079

/*
** Free all allocations associated with the iterator passed as the
** second argument.
*/
SQLITE_PRIVATE void sqlite3Fts3SegReaderFree(Fts3SegReader *pReader){
  if( pReader ){

    sqlite3_free(pReader->zTerm);

    if( !fts3SegReaderIsRootOnly(pReader) ){
      sqlite3_free(pReader->aNode);
    }
    sqlite3_blob_close(pReader->pBlob);
  }
  sqlite3_free(pReader);
}
185822
185823
185824
185825
185826
185827
185828
185829
185830
185831
185832
185833
185834
185835
185836
    }
    p->iOff += fts3GetVarint32(&p->aNode[p->iOff], &nSuffix);

    if( nPrefix>p->term.n || nSuffix>p->nNode-p->iOff || nSuffix==0 ){
      return FTS_CORRUPT_VTAB;
    }
    blobGrowBuffer(&p->term, nPrefix+nSuffix, &rc);
    if( rc==SQLITE_OK ){
      memcpy(&p->term.a[nPrefix], &p->aNode[p->iOff], nSuffix);
      p->term.n = nPrefix+nSuffix;
      p->iOff += nSuffix;
      if( p->iChild==0 ){
        p->iOff += fts3GetVarint32(&p->aNode[p->iOff], &p->nDoclist);
        if( (p->nNode-p->iOff)<p->nDoclist ){
          return FTS_CORRUPT_VTAB;







|







187257
187258
187259
187260
187261
187262
187263
187264
187265
187266
187267
187268
187269
187270
187271
    }
    p->iOff += fts3GetVarint32(&p->aNode[p->iOff], &nSuffix);

    if( nPrefix>p->term.n || nSuffix>p->nNode-p->iOff || nSuffix==0 ){
      return FTS_CORRUPT_VTAB;
    }
    blobGrowBuffer(&p->term, nPrefix+nSuffix, &rc);
    if( rc==SQLITE_OK && ALWAYS(p->term.a!=0) ){
      memcpy(&p->term.a[nPrefix], &p->aNode[p->iOff], nSuffix);
      p->term.n = nPrefix+nSuffix;
      p->iOff += nSuffix;
      if( p->iChild==0 ){
        p->iOff += fts3GetVarint32(&p->aNode[p->iOff], &p->nDoclist);
        if( (p->nNode-p->iOff)<p->nDoclist ){
          return FTS_CORRUPT_VTAB;
186216
186217
186218
186219
186220
186221
186222

186223



186224
186225
186226
186227
186228
186229
186230
static int fts3TermCmp(
  const char *zLhs, int nLhs,     /* LHS of comparison */
  const char *zRhs, int nRhs      /* RHS of comparison */
){
  int nCmp = MIN(nLhs, nRhs);
  int res;


  res = (nCmp ? memcmp(zLhs, zRhs, nCmp) : 0);



  if( res==0 ) res = nLhs - nRhs;

  return res;
}


/*







>
|
>
>
>







187651
187652
187653
187654
187655
187656
187657
187658
187659
187660
187661
187662
187663
187664
187665
187666
187667
187668
187669
static int fts3TermCmp(
  const char *zLhs, int nLhs,     /* LHS of comparison */
  const char *zRhs, int nRhs      /* RHS of comparison */
){
  int nCmp = MIN(nLhs, nRhs);
  int res;

  if( nCmp && ALWAYS(zLhs) && ALWAYS(zRhs) ){
    res = memcmp(zLhs, zRhs, nCmp);
  }else{
    res = 0;
  }
  if( res==0 ) res = nLhs - nRhs;

  return res;
}


/*
186860
186861
186862
186863
186864
186865
186866
186867
186868
186869
186870
186871
186872
186873
186874
    sqlite3_bind_int(pSelect, 1, FTS_STAT_INCRMERGEHINT);
    if( SQLITE_ROW==sqlite3_step(pSelect) ){
      const char *aHint = sqlite3_column_blob(pSelect, 0);
      int nHint = sqlite3_column_bytes(pSelect, 0);
      if( aHint ){
        blobGrowBuffer(pHint, nHint, &rc);
        if( rc==SQLITE_OK ){
          memcpy(pHint->a, aHint, nHint);
          pHint->n = nHint;
        }
      }
    }
    rc2 = sqlite3_reset(pSelect);
    if( rc==SQLITE_OK ) rc = rc2;
  }







|







188299
188300
188301
188302
188303
188304
188305
188306
188307
188308
188309
188310
188311
188312
188313
    sqlite3_bind_int(pSelect, 1, FTS_STAT_INCRMERGEHINT);
    if( SQLITE_ROW==sqlite3_step(pSelect) ){
      const char *aHint = sqlite3_column_blob(pSelect, 0);
      int nHint = sqlite3_column_bytes(pSelect, 0);
      if( aHint ){
        blobGrowBuffer(pHint, nHint, &rc);
        if( rc==SQLITE_OK ){
          if( ALWAYS(pHint->a!=0) ) memcpy(pHint->a, aHint, nHint);
          pHint->n = nHint;
        }
      }
    }
    rc2 = sqlite3_reset(pSelect);
    if( rc==SQLITE_OK ) rc = rc2;
  }
187977
187978
187979
187980
187981
187982
187983
187984
187985
187986
187987
187988
187989
187990
187991
187992
187993
*/
static MatchinfoBuffer *fts3MIBufferNew(size_t nElem, const char *zMatchinfo){
  MatchinfoBuffer *pRet;
  sqlite3_int64 nByte = sizeof(u32) * (2*(sqlite3_int64)nElem + 1)
                           + sizeof(MatchinfoBuffer);
  sqlite3_int64 nStr = strlen(zMatchinfo);

  pRet = sqlite3_malloc64(nByte + nStr+1);
  if( pRet ){
    memset(pRet, 0, nByte);
    pRet->aMatchinfo[0] = (u8*)(&pRet->aMatchinfo[1]) - (u8*)pRet;
    pRet->aMatchinfo[1+nElem] = pRet->aMatchinfo[0]
                                      + sizeof(u32)*((int)nElem+1);
    pRet->nElem = (int)nElem;
    pRet->zMatchinfo = ((char*)pRet) + nByte;
    memcpy(pRet->zMatchinfo, zMatchinfo, nStr+1);
    pRet->aRef[0] = 1;







|

<







189416
189417
189418
189419
189420
189421
189422
189423
189424

189425
189426
189427
189428
189429
189430
189431
*/
static MatchinfoBuffer *fts3MIBufferNew(size_t nElem, const char *zMatchinfo){
  MatchinfoBuffer *pRet;
  sqlite3_int64 nByte = sizeof(u32) * (2*(sqlite3_int64)nElem + 1)
                           + sizeof(MatchinfoBuffer);
  sqlite3_int64 nStr = strlen(zMatchinfo);

  pRet = sqlite3Fts3MallocZero(nByte + nStr+1);
  if( pRet ){

    pRet->aMatchinfo[0] = (u8*)(&pRet->aMatchinfo[1]) - (u8*)pRet;
    pRet->aMatchinfo[1+nElem] = pRet->aMatchinfo[0]
                                      + sizeof(u32)*((int)nElem+1);
    pRet->nElem = (int)nElem;
    pRet->zMatchinfo = ((char*)pRet) + nByte;
    memcpy(pRet->zMatchinfo, zMatchinfo, nStr+1);
    pRet->aRef[0] = 1;
188383
188384
188385
188386
188387
188388
188389
188390
188391
188392
188393
188394
188395
188396
188397
188398
188399
188400
188401
    return rc;
  }

  /* Now that it is known how many phrases there are, allocate and zero
  ** the required space using malloc().
  */
  nByte = sizeof(SnippetPhrase) * nList;
  sIter.aPhrase = (SnippetPhrase *)sqlite3_malloc64(nByte);
  if( !sIter.aPhrase ){
    return SQLITE_NOMEM;
  }
  memset(sIter.aPhrase, 0, nByte);

  /* Initialize the contents of the SnippetIter object. Then iterate through
  ** the set of phrases in the expression to populate the aPhrase[] array.
  */
  sIter.pCsr = pCsr;
  sIter.iCol = iCol;
  sIter.nSnippet = nSnippet;







|



<







189821
189822
189823
189824
189825
189826
189827
189828
189829
189830
189831

189832
189833
189834
189835
189836
189837
189838
    return rc;
  }

  /* Now that it is known how many phrases there are, allocate and zero
  ** the required space using malloc().
  */
  nByte = sizeof(SnippetPhrase) * nList;
  sIter.aPhrase = (SnippetPhrase *)sqlite3Fts3MallocZero(nByte);
  if( !sIter.aPhrase ){
    return SQLITE_NOMEM;
  }


  /* Initialize the contents of the SnippetIter object. Then iterate through
  ** the set of phrases in the expression to populate the aPhrase[] array.
  */
  sIter.pCsr = pCsr;
  sIter.iCol = iCol;
  sIter.nSnippet = nSnippet;
188951
188952
188953
188954
188955
188956
188957
188958
188959
188960
188961


188962
188963
188964
188965
188966
188967
188968

/*
** Advance the iterator passed as an argument to the next position. Return
** 1 if the iterator is at EOF or if it now points to the start of the
** position list for the next column.
*/
static int fts3LcsIteratorAdvance(LcsIterator *pIter){
  char *pRead = pIter->pRead;
  sqlite3_int64 iRead;
  int rc = 0;



  pRead += sqlite3Fts3GetVarint(pRead, &iRead);
  if( iRead==0 || iRead==1 ){
    pRead = 0;
    rc = 1;
  }else{
    pIter->iPos += (int)(iRead-2);
  }







|



>
>







190388
190389
190390
190391
190392
190393
190394
190395
190396
190397
190398
190399
190400
190401
190402
190403
190404
190405
190406
190407

/*
** Advance the iterator passed as an argument to the next position. Return
** 1 if the iterator is at EOF or if it now points to the start of the
** position list for the next column.
*/
static int fts3LcsIteratorAdvance(LcsIterator *pIter){
  char *pRead;
  sqlite3_int64 iRead;
  int rc = 0;

  if( NEVER(pIter==0) ) return 1;
  pRead = pIter->pRead;
  pRead += sqlite3Fts3GetVarint(pRead, &iRead);
  if( iRead==0 || iRead==1 ){
    pRead = 0;
    rc = 1;
  }else{
    pIter->iPos += (int)(iRead-2);
  }
188988
188989
188990
188991
188992
188993
188994
188995
188996
188997
188998
188999
189000
189001
189002
189003
189004
  int iCol;
  int nToken = 0;
  int rc = SQLITE_OK;

  /* Allocate and populate the array of LcsIterator objects. The array
  ** contains one element for each matchable phrase in the query.
  **/
  aIter = sqlite3_malloc64(sizeof(LcsIterator) * pCsr->nPhrase);
  if( !aIter ) return SQLITE_NOMEM;
  memset(aIter, 0, sizeof(LcsIterator) * pCsr->nPhrase);
  (void)fts3ExprIterate(pCsr->pExpr, fts3MatchinfoLcsCb, (void*)aIter);

  for(i=0; i<pInfo->nPhrase; i++){
    LcsIterator *pIter = &aIter[i];
    nToken -= pIter->pExpr->pPhrase->nToken;
    pIter->iPosOffset = nToken;
  }







|

<







190427
190428
190429
190430
190431
190432
190433
190434
190435

190436
190437
190438
190439
190440
190441
190442
  int iCol;
  int nToken = 0;
  int rc = SQLITE_OK;

  /* Allocate and populate the array of LcsIterator objects. The array
  ** contains one element for each matchable phrase in the query.
  **/
  aIter = sqlite3Fts3MallocZero(sizeof(LcsIterator) * pCsr->nPhrase);
  if( !aIter ) return SQLITE_NOMEM;

  (void)fts3ExprIterate(pCsr->pExpr, fts3MatchinfoLcsCb, (void*)aIter);

  for(i=0; i<pInfo->nPhrase; i++){
    LcsIterator *pIter = &aIter[i];
    nToken -= pIter->pExpr->pPhrase->nToken;
    pIter->iPosOffset = nToken;
  }
189451
189452
189453
189454
189455
189456
189457
189458
189459
189460
189461
189462
189463
189464
189465
189466
189467
189468
189469
189470
189471
189472
189473
189474
189475
189476
189477
189478
189479
189480
189481
189482
189483
189484
189485

189486
189487
189488
189489
189490
189491
189492
  assert( pCsr->isRequireSeek==0 );

  /* Count the number of terms in the query */
  rc = fts3ExprLoadDoclists(pCsr, 0, &nToken);
  if( rc!=SQLITE_OK ) goto offsets_out;

  /* Allocate the array of TermOffset iterators. */
  sCtx.aTerm = (TermOffset *)sqlite3_malloc64(sizeof(TermOffset)*nToken);
  if( 0==sCtx.aTerm ){
    rc = SQLITE_NOMEM;
    goto offsets_out;
  }
  sCtx.iDocid = pCsr->iPrevId;
  sCtx.pCsr = pCsr;

  /* Loop through the table columns, appending offset information to
  ** string-buffer res for each column.
  */
  for(iCol=0; iCol<pTab->nColumn; iCol++){
    sqlite3_tokenizer_cursor *pC; /* Tokenizer cursor */
    const char *ZDUMMY;           /* Dummy argument used with xNext() */
    int NDUMMY = 0;               /* Dummy argument used with xNext() */
    int iStart = 0;
    int iEnd = 0;
    int iCurrent = 0;
    const char *zDoc;
    int nDoc;

    /* Initialize the contents of sCtx.aTerm[] for column iCol. There is
    ** no way that this operation can fail, so the return code from
    ** fts3ExprIterate() can be discarded.
    */
    sCtx.iCol = iCol;
    sCtx.iTerm = 0;
    (void)fts3ExprIterate(pCsr->pExpr, fts3ExprTermOffsetInit, (void*)&sCtx);


    /* Retreive the text stored in column iCol. If an SQL NULL is stored
    ** in column iCol, jump immediately to the next iteration of the loop.
    ** If an OOM occurs while retrieving the data (this can happen if SQLite
    ** needs to transform the data from utf-16 to utf-8), return SQLITE_NOMEM
    ** to the caller.
    */







|




















|
|
<



|
>







190889
190890
190891
190892
190893
190894
190895
190896
190897
190898
190899
190900
190901
190902
190903
190904
190905
190906
190907
190908
190909
190910
190911
190912
190913
190914
190915
190916
190917
190918

190919
190920
190921
190922
190923
190924
190925
190926
190927
190928
190929
190930
  assert( pCsr->isRequireSeek==0 );

  /* Count the number of terms in the query */
  rc = fts3ExprLoadDoclists(pCsr, 0, &nToken);
  if( rc!=SQLITE_OK ) goto offsets_out;

  /* Allocate the array of TermOffset iterators. */
  sCtx.aTerm = (TermOffset *)sqlite3Fts3MallocZero(sizeof(TermOffset)*nToken);
  if( 0==sCtx.aTerm ){
    rc = SQLITE_NOMEM;
    goto offsets_out;
  }
  sCtx.iDocid = pCsr->iPrevId;
  sCtx.pCsr = pCsr;

  /* Loop through the table columns, appending offset information to
  ** string-buffer res for each column.
  */
  for(iCol=0; iCol<pTab->nColumn; iCol++){
    sqlite3_tokenizer_cursor *pC; /* Tokenizer cursor */
    const char *ZDUMMY;           /* Dummy argument used with xNext() */
    int NDUMMY = 0;               /* Dummy argument used with xNext() */
    int iStart = 0;
    int iEnd = 0;
    int iCurrent = 0;
    const char *zDoc;
    int nDoc;

    /* Initialize the contents of sCtx.aTerm[] for column iCol. This
    ** operation may fail if the database contains corrupt records.

    */
    sCtx.iCol = iCol;
    sCtx.iTerm = 0;
    rc = fts3ExprIterate(pCsr->pExpr, fts3ExprTermOffsetInit, (void*)&sCtx);
    if( rc!=SQLITE_OK ) goto offsets_out;

    /* Retreive the text stored in column iCol. If an SQL NULL is stored
    ** in column iCol, jump immediately to the next iteration of the loop.
    ** If an OOM occurs while retrieving the data (this can happen if SQLite
    ** needs to transform the data from utf-16 to utf-8), return SQLITE_NOMEM
    ** to the caller.
    */
190476
190477
190478
190479
190480
190481
190482














190483













190484
190485
190486
190487
190488
190489
190490
#ifndef SQLITE_AMALGAMATION
  /* Unsigned integer types.  These are already defined in the sqliteInt.h,
  ** but the definitions need to be repeated for separate compilation. */
  typedef sqlite3_uint64 u64;
  typedef unsigned int u32;
  typedef unsigned short int u16;
  typedef unsigned char u8;














#endif














/* Objects */
typedef struct JsonString JsonString;
typedef struct JsonNode JsonNode;
typedef struct JsonParse JsonParse;

/* An instance of this object represents a JSON string







>
>
>
>
>
>
>
>
>
>
>
>
>
>

>
>
>
>
>
>
>
>
>
>
>
>
>







191914
191915
191916
191917
191918
191919
191920
191921
191922
191923
191924
191925
191926
191927
191928
191929
191930
191931
191932
191933
191934
191935
191936
191937
191938
191939
191940
191941
191942
191943
191944
191945
191946
191947
191948
191949
191950
191951
191952
191953
191954
191955
#ifndef SQLITE_AMALGAMATION
  /* Unsigned integer types.  These are already defined in the sqliteInt.h,
  ** but the definitions need to be repeated for separate compilation. */
  typedef sqlite3_uint64 u64;
  typedef unsigned int u32;
  typedef unsigned short int u16;
  typedef unsigned char u8;
# if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_MUTATION_TEST)
#   define SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS 1
# endif
# if defined(SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS)
#   define ALWAYS(X)      (1)
#   define NEVER(X)       (0)
# elif !defined(NDEBUG)
#   define ALWAYS(X)      ((X)?1:(assert(0),0))
#   define NEVER(X)       ((X)?(assert(0),1):0)
# else
#   define ALWAYS(X)      (X)
#   define NEVER(X)       (X)
# endif
# define testcase(X)
#endif
#if !defined(SQLITE_DEBUG) && !defined(SQLITE_COVERAGE_TEST)
#  define VVA(X)
#else
#  define VVA(X) X
#endif

/*
** Some of the testcase() macros in this file are problematic for gcov
** in that they generate false-miss errors randomly.  This is a gcov problem,
** not a problem in this case.  But to work around it, we disable the
** problematic test cases for production builds.
*/
#define json_testcase(X)

/* Objects */
typedef struct JsonString JsonString;
typedef struct JsonNode JsonNode;
typedef struct JsonParse JsonParse;

/* An instance of this object represents a JSON string
190534
190535
190536
190537
190538
190539
190540

190541
190542
190543
190544
190545
190546
190547
190548
190549
190550
190551
190552
190553
190554


/* A single node of parsed JSON
*/
struct JsonNode {
  u8 eType;              /* One of the JSON_ type values */
  u8 jnFlags;            /* JNODE flags */

  u32 n;                 /* Bytes of content, or number of sub-nodes */
  union {
    const char *zJContent; /* Content for INT, REAL, and STRING */
    u32 iAppend;           /* More terms for ARRAY and OBJECT */
    u32 iKey;              /* Key for ARRAY objects in json_tree() */
    u32 iReplace;          /* Replacement content for JNODE_REPLACE */
    JsonNode *pPatch;      /* Node chain of patch for JNODE_PATCH */
  } u;
};

/* A completely parsed JSON string
*/
struct JsonParse {
  u32 nNode;         /* Number of slots of aNode[] used */







>


|
|
|
|
|







191999
192000
192001
192002
192003
192004
192005
192006
192007
192008
192009
192010
192011
192012
192013
192014
192015
192016
192017
192018
192019
192020


/* A single node of parsed JSON
*/
struct JsonNode {
  u8 eType;              /* One of the JSON_ type values */
  u8 jnFlags;            /* JNODE flags */
  u8 eU;                 /* Which union element to use */
  u32 n;                 /* Bytes of content, or number of sub-nodes */
  union {
    const char *zJContent; /* 1: Content for INT, REAL, and STRING */
    u32 iAppend;           /* 2: More terms for ARRAY and OBJECT */
    u32 iKey;              /* 3: Key for ARRAY objects in json_tree() */
    u32 iReplace;          /* 4: Replacement content for JNODE_REPLACE */
    JsonNode *pPatch;      /* 5: Node chain of patch for JNODE_PATCH */
  } u;
};

/* A completely parsed JSON string
*/
struct JsonParse {
  u32 nNode;         /* Number of slots of aNode[] used */
190818
190819
190820
190821
190822
190823
190824

190825
190826

190827
190828
190829

190830
190831
190832
190833
190834
190835
190836
190837
190838
190839
190840
190841
190842
190843
190844
190845
190846
190847

190848
190849
190850
190851
190852
190853
190854

190855
190856
190857
190858
190859
190860
190861
190862
190863
190864
190865
190866
190867
190868
190869

190870
190871
190872
190873
190874
190875
190876
190877
190878
190879
190880
190881
190882
190883
190884
190885
190886
190887
190888
190889

190890
190891
190892
190893
190894
190895
190896
** the number of JsonNode objects that are encoded.
*/
static void jsonRenderNode(
  JsonNode *pNode,               /* The node to render */
  JsonString *pOut,              /* Write JSON here */
  sqlite3_value **aReplace       /* Replacement values */
){

  if( pNode->jnFlags & (JNODE_REPLACE|JNODE_PATCH) ){
    if( pNode->jnFlags & JNODE_REPLACE ){

      jsonAppendValue(pOut, aReplace[pNode->u.iReplace]);
      return;
    }

    pNode = pNode->u.pPatch;
  }
  switch( pNode->eType ){
    default: {
      assert( pNode->eType==JSON_NULL );
      jsonAppendRaw(pOut, "null", 4);
      break;
    }
    case JSON_TRUE: {
      jsonAppendRaw(pOut, "true", 4);
      break;
    }
    case JSON_FALSE: {
      jsonAppendRaw(pOut, "false", 5);
      break;
    }
    case JSON_STRING: {
      if( pNode->jnFlags & JNODE_RAW ){

        jsonAppendString(pOut, pNode->u.zJContent, pNode->n);
        break;
      }
      /* no break */ deliberate_fall_through
    }
    case JSON_REAL:
    case JSON_INT: {

      jsonAppendRaw(pOut, pNode->u.zJContent, pNode->n);
      break;
    }
    case JSON_ARRAY: {
      u32 j = 1;
      jsonAppendChar(pOut, '[');
      for(;;){
        while( j<=pNode->n ){
          if( (pNode[j].jnFlags & JNODE_REMOVE)==0 ){
            jsonAppendSeparator(pOut);
            jsonRenderNode(&pNode[j], pOut, aReplace);
          }
          j += jsonNodeSize(&pNode[j]);
        }
        if( (pNode->jnFlags & JNODE_APPEND)==0 ) break;

        pNode = &pNode[pNode->u.iAppend];
        j = 1;
      }
      jsonAppendChar(pOut, ']');
      break;
    }
    case JSON_OBJECT: {
      u32 j = 1;
      jsonAppendChar(pOut, '{');
      for(;;){
        while( j<=pNode->n ){
          if( (pNode[j+1].jnFlags & JNODE_REMOVE)==0 ){
            jsonAppendSeparator(pOut);
            jsonRenderNode(&pNode[j], pOut, aReplace);
            jsonAppendChar(pOut, ':');
            jsonRenderNode(&pNode[j+1], pOut, aReplace);
          }
          j += 1 + jsonNodeSize(&pNode[j+1]);
        }
        if( (pNode->jnFlags & JNODE_APPEND)==0 ) break;

        pNode = &pNode[pNode->u.iAppend];
        j = 1;
      }
      jsonAppendChar(pOut, '}');
      break;
    }
  }







>

|
>



>


















>







>















>




















>







192284
192285
192286
192287
192288
192289
192290
192291
192292
192293
192294
192295
192296
192297
192298
192299
192300
192301
192302
192303
192304
192305
192306
192307
192308
192309
192310
192311
192312
192313
192314
192315
192316
192317
192318
192319
192320
192321
192322
192323
192324
192325
192326
192327
192328
192329
192330
192331
192332
192333
192334
192335
192336
192337
192338
192339
192340
192341
192342
192343
192344
192345
192346
192347
192348
192349
192350
192351
192352
192353
192354
192355
192356
192357
192358
192359
192360
192361
192362
192363
192364
192365
192366
192367
192368
192369
** the number of JsonNode objects that are encoded.
*/
static void jsonRenderNode(
  JsonNode *pNode,               /* The node to render */
  JsonString *pOut,              /* Write JSON here */
  sqlite3_value **aReplace       /* Replacement values */
){
  assert( pNode!=0 );
  if( pNode->jnFlags & (JNODE_REPLACE|JNODE_PATCH) ){
    if( (pNode->jnFlags & JNODE_REPLACE)!=0 && ALWAYS(aReplace!=0) ){
      assert( pNode->eU==4 );
      jsonAppendValue(pOut, aReplace[pNode->u.iReplace]);
      return;
    }
    assert( pNode->eU==5 );
    pNode = pNode->u.pPatch;
  }
  switch( pNode->eType ){
    default: {
      assert( pNode->eType==JSON_NULL );
      jsonAppendRaw(pOut, "null", 4);
      break;
    }
    case JSON_TRUE: {
      jsonAppendRaw(pOut, "true", 4);
      break;
    }
    case JSON_FALSE: {
      jsonAppendRaw(pOut, "false", 5);
      break;
    }
    case JSON_STRING: {
      if( pNode->jnFlags & JNODE_RAW ){
        assert( pNode->eU==1 );
        jsonAppendString(pOut, pNode->u.zJContent, pNode->n);
        break;
      }
      /* no break */ deliberate_fall_through
    }
    case JSON_REAL:
    case JSON_INT: {
      assert( pNode->eU==1 );
      jsonAppendRaw(pOut, pNode->u.zJContent, pNode->n);
      break;
    }
    case JSON_ARRAY: {
      u32 j = 1;
      jsonAppendChar(pOut, '[');
      for(;;){
        while( j<=pNode->n ){
          if( (pNode[j].jnFlags & JNODE_REMOVE)==0 ){
            jsonAppendSeparator(pOut);
            jsonRenderNode(&pNode[j], pOut, aReplace);
          }
          j += jsonNodeSize(&pNode[j]);
        }
        if( (pNode->jnFlags & JNODE_APPEND)==0 ) break;
        assert( pNode->eU==2 );
        pNode = &pNode[pNode->u.iAppend];
        j = 1;
      }
      jsonAppendChar(pOut, ']');
      break;
    }
    case JSON_OBJECT: {
      u32 j = 1;
      jsonAppendChar(pOut, '{');
      for(;;){
        while( j<=pNode->n ){
          if( (pNode[j+1].jnFlags & JNODE_REMOVE)==0 ){
            jsonAppendSeparator(pOut);
            jsonRenderNode(&pNode[j], pOut, aReplace);
            jsonAppendChar(pOut, ':');
            jsonRenderNode(&pNode[j+1], pOut, aReplace);
          }
          j += 1 + jsonNodeSize(&pNode[j+1]);
        }
        if( (pNode->jnFlags & JNODE_APPEND)==0 ) break;
        assert( pNode->eU==2 );
        pNode = &pNode[pNode->u.iAppend];
        j = 1;
      }
      jsonAppendChar(pOut, '}');
      break;
    }
  }
190962
190963
190964
190965
190966
190967
190968
190969


190970
190971
190972
190973
190974
190975
190976
    }
    case JSON_FALSE: {
      sqlite3_result_int(pCtx, 0);
      break;
    }
    case JSON_INT: {
      sqlite3_int64 i = 0;
      const char *z = pNode->u.zJContent;


      if( z[0]=='-' ){ z++; }
      while( z[0]>='0' && z[0]<='9' ){
        unsigned v = *(z++) - '0';
        if( i>=LARGEST_INT64/10 ){
          if( i>LARGEST_INT64/10 ) goto int_as_real;
          if( z[0]>='0' && z[0]<='9' ) goto int_as_real;
          if( v==9 ) goto int_as_real;







|
>
>







192435
192436
192437
192438
192439
192440
192441
192442
192443
192444
192445
192446
192447
192448
192449
192450
192451
    }
    case JSON_FALSE: {
      sqlite3_result_int(pCtx, 0);
      break;
    }
    case JSON_INT: {
      sqlite3_int64 i = 0;
      const char *z;
      assert( pNode->eU==1 );
      z = pNode->u.zJContent;
      if( z[0]=='-' ){ z++; }
      while( z[0]>='0' && z[0]<='9' ){
        unsigned v = *(z++) - '0';
        if( i>=LARGEST_INT64/10 ){
          if( i>LARGEST_INT64/10 ) goto int_as_real;
          if( z[0]>='0' && z[0]<='9' ) goto int_as_real;
          if( v==9 ) goto int_as_real;
190990
190991
190992
190993
190994
190995
190996
190997


190998
190999

191000
191001
191002
191003
191004
191005
191006
191007
191008
191009

191010
191011
191012
191013
191014
191015
191016

191017
191018
191019
191020
191021
191022
191023
191024
191025


191026
191027
191028
191029
191030
191031
191032
      int_done:
      break;
      int_as_real: ; /* no break */ deliberate_fall_through
    }
    case JSON_REAL: {
      double r;
#ifdef SQLITE_AMALGAMATION
      const char *z = pNode->u.zJContent;


      sqlite3AtoF(z, &r, sqlite3Strlen30(z), SQLITE_UTF8);
#else

      r = strtod(pNode->u.zJContent, 0);
#endif
      sqlite3_result_double(pCtx, r);
      break;
    }
    case JSON_STRING: {
#if 0 /* Never happens because JNODE_RAW is only set by json_set(),
      ** json_insert() and json_replace() and those routines do not
      ** call jsonReturn() */
      if( pNode->jnFlags & JNODE_RAW ){

        sqlite3_result_text(pCtx, pNode->u.zJContent, pNode->n,
                            SQLITE_TRANSIENT);
      }else
#endif
      assert( (pNode->jnFlags & JNODE_RAW)==0 );
      if( (pNode->jnFlags & JNODE_ESCAPE)==0 ){
        /* JSON formatted without any backslash-escapes */

        sqlite3_result_text(pCtx, pNode->u.zJContent+1, pNode->n-2,
                            SQLITE_TRANSIENT);
      }else{
        /* Translate JSON formatted string into raw text */
        u32 i;
        u32 n = pNode->n;
        const char *z = pNode->u.zJContent;
        char *zOut;
        u32 j;


        zOut = sqlite3_malloc( n+1 );
        if( zOut==0 ){
          sqlite3_result_error_nomem(pCtx);
          break;
        }
        for(i=1, j=0; i<n-1; i++){
          char c = z[i];







|
>
>


>










>







>






|


>
>







192465
192466
192467
192468
192469
192470
192471
192472
192473
192474
192475
192476
192477
192478
192479
192480
192481
192482
192483
192484
192485
192486
192487
192488
192489
192490
192491
192492
192493
192494
192495
192496
192497
192498
192499
192500
192501
192502
192503
192504
192505
192506
192507
192508
192509
192510
192511
192512
192513
192514
      int_done:
      break;
      int_as_real: ; /* no break */ deliberate_fall_through
    }
    case JSON_REAL: {
      double r;
#ifdef SQLITE_AMALGAMATION
      const char *z;
      assert( pNode->eU==1 );
      z = pNode->u.zJContent;
      sqlite3AtoF(z, &r, sqlite3Strlen30(z), SQLITE_UTF8);
#else
      assert( pNode->eU==1 );
      r = strtod(pNode->u.zJContent, 0);
#endif
      sqlite3_result_double(pCtx, r);
      break;
    }
    case JSON_STRING: {
#if 0 /* Never happens because JNODE_RAW is only set by json_set(),
      ** json_insert() and json_replace() and those routines do not
      ** call jsonReturn() */
      if( pNode->jnFlags & JNODE_RAW ){
        assert( pNode->eU==1 );
        sqlite3_result_text(pCtx, pNode->u.zJContent, pNode->n,
                            SQLITE_TRANSIENT);
      }else
#endif
      assert( (pNode->jnFlags & JNODE_RAW)==0 );
      if( (pNode->jnFlags & JNODE_ESCAPE)==0 ){
        /* JSON formatted without any backslash-escapes */
        assert( pNode->eU==1 );
        sqlite3_result_text(pCtx, pNode->u.zJContent+1, pNode->n-2,
                            SQLITE_TRANSIENT);
      }else{
        /* Translate JSON formatted string into raw text */
        u32 i;
        u32 n = pNode->n;
        const char *z;
        char *zOut;
        u32 j;
        assert( pNode->eU==1 );
        z = pNode->u.zJContent;
        zOut = sqlite3_malloc( n+1 );
        if( zOut==0 ){
          sqlite3_result_error_nomem(pCtx);
          break;
        }
        for(i=1, j=0; i<n-1; i++){
          char c = z[i];
191139
191140
191141
191142
191143
191144
191145
191146
191147
191148
191149
191150
191151

191152
191153
191154
191155
191156
191157
191158
static int jsonParseAddNode(
  JsonParse *pParse,        /* Append the node to this object */
  u32 eType,                /* Node type */
  u32 n,                    /* Content size or sub-node count */
  const char *zContent      /* Content */
){
  JsonNode *p;
  if( pParse->nNode>=pParse->nAlloc ){
    return jsonParseAddNodeExpand(pParse, eType, n, zContent);
  }
  p = &pParse->aNode[pParse->nNode];
  p->eType = (u8)eType;
  p->jnFlags = 0;

  p->n = n;
  p->u.zJContent = zContent;
  return pParse->nNode++;
}

/*
** Return true if z[] begins with 4 (or more) hexadecimal digits







|





>







192621
192622
192623
192624
192625
192626
192627
192628
192629
192630
192631
192632
192633
192634
192635
192636
192637
192638
192639
192640
192641
static int jsonParseAddNode(
  JsonParse *pParse,        /* Append the node to this object */
  u32 eType,                /* Node type */
  u32 n,                    /* Content size or sub-node count */
  const char *zContent      /* Content */
){
  JsonNode *p;
  if( pParse->aNode==0 || pParse->nNode>=pParse->nAlloc ){
    return jsonParseAddNodeExpand(pParse, eType, n, zContent);
  }
  p = &pParse->aNode[pParse->nNode];
  p->eType = (u8)eType;
  p->jnFlags = 0;
  VVA( p->eU = zContent ? 1 : 0 );
  p->n = n;
  p->u.zJContent = zContent;
  return pParse->nNode++;
}

/*
** Return true if z[] begins with 4 (or more) hexadecimal digits
191212
191213
191214
191215
191216
191217
191218

191219
191220
191221
191222
191223
191224
191225
    }
    pParse->aNode[iThis].n = pParse->nNode - (u32)iThis - 1;
    return j+1;
  }else if( c=='[' ){
    /* Parse array */
    iThis = jsonParseAddNode(pParse, JSON_ARRAY, 0, 0);
    if( iThis<0 ) return -1;

    for(j=i+1;;j++){
      while( safe_isspace(z[j]) ){ j++; }
      if( ++pParse->iDepth > JSON_MAX_DEPTH ) return -1;
      x = jsonParseValue(pParse, j);
      pParse->iDepth--;
      if( x<0 ){
        if( x==(-3) && pParse->nNode==(u32)iThis+1 ) return j+1;







>







192695
192696
192697
192698
192699
192700
192701
192702
192703
192704
192705
192706
192707
192708
192709
    }
    pParse->aNode[iThis].n = pParse->nNode - (u32)iThis - 1;
    return j+1;
  }else if( c=='[' ){
    /* Parse array */
    iThis = jsonParseAddNode(pParse, JSON_ARRAY, 0, 0);
    if( iThis<0 ) return -1;
    memset(&pParse->aNode[iThis].u, 0, sizeof(pParse->aNode[iThis].u));
    for(j=i+1;;j++){
      while( safe_isspace(z[j]) ){ j++; }
      if( ++pParse->iDepth > JSON_MAX_DEPTH ) return -1;
      x = jsonParseValue(pParse, j);
      pParse->iDepth--;
      if( x<0 ){
        if( x==(-3) && pParse->nNode==(u32)iThis+1 ) return j+1;
191476
191477
191478
191479
191480
191481
191482

191483
191484
191485
191486
191487
191488
191489
}

/*
** Compare the OBJECT label at pNode against zKey,nKey.  Return true on
** a match.
*/
static int jsonLabelCompare(JsonNode *pNode, const char *zKey, u32 nKey){

  if( pNode->jnFlags & JNODE_RAW ){
    if( pNode->n!=nKey ) return 0;
    return strncmp(pNode->u.zJContent, zKey, nKey)==0;
  }else{
    if( pNode->n!=nKey+2 ) return 0;
    return strncmp(pNode->u.zJContent+1, zKey, nKey)==0;
  }







>







192960
192961
192962
192963
192964
192965
192966
192967
192968
192969
192970
192971
192972
192973
192974
}

/*
** Compare the OBJECT label at pNode against zKey,nKey.  Return true on
** a match.
*/
static int jsonLabelCompare(JsonNode *pNode, const char *zKey, u32 nKey){
  assert( pNode->eU==1 );
  if( pNode->jnFlags & JNODE_RAW ){
    if( pNode->n!=nKey ) return 0;
    return strncmp(pNode->u.zJContent, zKey, nKey)==0;
  }else{
    if( pNode->n!=nKey+2 ) return 0;
    return strncmp(pNode->u.zJContent+1, zKey, nKey)==0;
  }
191541
191542
191543
191544
191545
191546
191547

191548
191549
191550
191551
191552
191553
191554
191555
191556
191557
191558
191559
191560
191561

191562
191563

191564
191565
191566
191567
191568
191569
191570
        if( jsonLabelCompare(pRoot+j, zKey, nKey) ){
          return jsonLookupStep(pParse, iRoot+j+1, &zPath[i], pApnd, pzErr);
        }
        j++;
        j += jsonNodeSize(&pRoot[j]);
      }
      if( (pRoot->jnFlags & JNODE_APPEND)==0 ) break;

      iRoot += pRoot->u.iAppend;
      pRoot = &pParse->aNode[iRoot];
      j = 1;
    }
    if( pApnd ){
      u32 iStart, iLabel;
      JsonNode *pNode;
      iStart = jsonParseAddNode(pParse, JSON_OBJECT, 2, 0);
      iLabel = jsonParseAddNode(pParse, JSON_STRING, nKey, zKey);
      zPath += i;
      pNode = jsonLookupAppend(pParse, zPath, pApnd, pzErr);
      if( pParse->oom ) return 0;
      if( pNode ){
        pRoot = &pParse->aNode[iRoot];

        pRoot->u.iAppend = iStart - iRoot;
        pRoot->jnFlags |= JNODE_APPEND;

        pParse->aNode[iLabel].jnFlags |= JNODE_RAW;
      }
      return pNode;
    }
  }else if( zPath[0]=='[' ){
    i = 0;
    j = 1;







>














>


>







193026
193027
193028
193029
193030
193031
193032
193033
193034
193035
193036
193037
193038
193039
193040
193041
193042
193043
193044
193045
193046
193047
193048
193049
193050
193051
193052
193053
193054
193055
193056
193057
193058
        if( jsonLabelCompare(pRoot+j, zKey, nKey) ){
          return jsonLookupStep(pParse, iRoot+j+1, &zPath[i], pApnd, pzErr);
        }
        j++;
        j += jsonNodeSize(&pRoot[j]);
      }
      if( (pRoot->jnFlags & JNODE_APPEND)==0 ) break;
      assert( pRoot->eU==2 );
      iRoot += pRoot->u.iAppend;
      pRoot = &pParse->aNode[iRoot];
      j = 1;
    }
    if( pApnd ){
      u32 iStart, iLabel;
      JsonNode *pNode;
      iStart = jsonParseAddNode(pParse, JSON_OBJECT, 2, 0);
      iLabel = jsonParseAddNode(pParse, JSON_STRING, nKey, zKey);
      zPath += i;
      pNode = jsonLookupAppend(pParse, zPath, pApnd, pzErr);
      if( pParse->oom ) return 0;
      if( pNode ){
        pRoot = &pParse->aNode[iRoot];
        assert( pRoot->eU==0 );
        pRoot->u.iAppend = iStart - iRoot;
        pRoot->jnFlags |= JNODE_APPEND;
        VVA( pRoot->eU = 2 );
        pParse->aNode[iLabel].jnFlags |= JNODE_RAW;
      }
      return pNode;
    }
  }else if( zPath[0]=='[' ){
    i = 0;
    j = 1;
191579
191580
191581
191582
191583
191584
191585

191586
191587
191588
191589
191590
191591
191592
        if( pRoot->eType!=JSON_ARRAY ) return 0;
        for(;;){
          while( j<=pBase->n ){
            if( (pBase[j].jnFlags & JNODE_REMOVE)==0 ) i++;
            j += jsonNodeSize(&pBase[j]);
          }
          if( (pBase->jnFlags & JNODE_APPEND)==0 ) break;

          iBase += pBase->u.iAppend;
          pBase = &pParse->aNode[iBase];
          j = 1;
        }
        j = 2;
        if( zPath[2]=='-' && safe_isdigit(zPath[3]) ){
          unsigned int x = 0;







>







193067
193068
193069
193070
193071
193072
193073
193074
193075
193076
193077
193078
193079
193080
193081
        if( pRoot->eType!=JSON_ARRAY ) return 0;
        for(;;){
          while( j<=pBase->n ){
            if( (pBase[j].jnFlags & JNODE_REMOVE)==0 ) i++;
            j += jsonNodeSize(&pBase[j]);
          }
          if( (pBase->jnFlags & JNODE_APPEND)==0 ) break;
          assert( pBase->eU==2 );
          iBase += pBase->u.iAppend;
          pBase = &pParse->aNode[iBase];
          j = 1;
        }
        j = 2;
        if( zPath[2]=='-' && safe_isdigit(zPath[3]) ){
          unsigned int x = 0;
191612
191613
191614
191615
191616
191617
191618

191619
191620
191621
191622
191623
191624
191625
191626
191627
191628
191629
191630
191631
191632
191633

191634
191635

191636
191637
191638
191639
191640
191641
191642
    j = 1;
    for(;;){
      while( j<=pRoot->n && (i>0 || (pRoot[j].jnFlags & JNODE_REMOVE)!=0) ){
        if( (pRoot[j].jnFlags & JNODE_REMOVE)==0 ) i--;
        j += jsonNodeSize(&pRoot[j]);
      }
      if( (pRoot->jnFlags & JNODE_APPEND)==0 ) break;

      iRoot += pRoot->u.iAppend;
      pRoot = &pParse->aNode[iRoot];
      j = 1;
    }
    if( j<=pRoot->n ){
      return jsonLookupStep(pParse, iRoot+j, zPath, pApnd, pzErr);
    }
    if( i==0 && pApnd ){
      u32 iStart;
      JsonNode *pNode;
      iStart = jsonParseAddNode(pParse, JSON_ARRAY, 1, 0);
      pNode = jsonLookupAppend(pParse, zPath, pApnd, pzErr);
      if( pParse->oom ) return 0;
      if( pNode ){
        pRoot = &pParse->aNode[iRoot];

        pRoot->u.iAppend = iStart - iRoot;
        pRoot->jnFlags |= JNODE_APPEND;

      }
      return pNode;
    }
  }else{
    *pzErr = zPath;
  }
  return 0;







>















>


>







193101
193102
193103
193104
193105
193106
193107
193108
193109
193110
193111
193112
193113
193114
193115
193116
193117
193118
193119
193120
193121
193122
193123
193124
193125
193126
193127
193128
193129
193130
193131
193132
193133
193134
    j = 1;
    for(;;){
      while( j<=pRoot->n && (i>0 || (pRoot[j].jnFlags & JNODE_REMOVE)!=0) ){
        if( (pRoot[j].jnFlags & JNODE_REMOVE)==0 ) i--;
        j += jsonNodeSize(&pRoot[j]);
      }
      if( (pRoot->jnFlags & JNODE_APPEND)==0 ) break;
      assert( pRoot->eU==2 );
      iRoot += pRoot->u.iAppend;
      pRoot = &pParse->aNode[iRoot];
      j = 1;
    }
    if( j<=pRoot->n ){
      return jsonLookupStep(pParse, iRoot+j, zPath, pApnd, pzErr);
    }
    if( i==0 && pApnd ){
      u32 iStart;
      JsonNode *pNode;
      iStart = jsonParseAddNode(pParse, JSON_ARRAY, 1, 0);
      pNode = jsonLookupAppend(pParse, zPath, pApnd, pzErr);
      if( pParse->oom ) return 0;
      if( pNode ){
        pRoot = &pParse->aNode[iRoot];
        assert( pRoot->eU==0 );
        pRoot->u.iAppend = iStart - iRoot;
        pRoot->jnFlags |= JNODE_APPEND;
        VVA( pRoot->eU = 2 );
      }
      return pNode;
    }
  }else{
    *pzErr = zPath;
  }
  return 0;
191782
191783
191784
191785
191786
191787
191788

191789

191790
191791


191792
191793
191794
191795
191796
191797
191798
      assert( x.aNode[i].eType==JSON_STRING );
      zType = "label";
    }else{
      zType = jsonType[x.aNode[i].eType];
    }
    jsonPrintf(100, &s,"node %3u: %7s n=%-4d up=%-4d",
               i, zType, x.aNode[i].n, x.aUp[i]);

    if( x.aNode[i].u.zJContent!=0 ){

      jsonAppendRaw(&s, " ", 1);
      jsonAppendRaw(&s, x.aNode[i].u.zJContent, x.aNode[i].n);


    }
    jsonAppendRaw(&s, "\n", 1);
  }
  jsonParseReset(&x);
  jsonResult(&s);
}








>

>


>
>







193274
193275
193276
193277
193278
193279
193280
193281
193282
193283
193284
193285
193286
193287
193288
193289
193290
193291
193292
193293
193294
      assert( x.aNode[i].eType==JSON_STRING );
      zType = "label";
    }else{
      zType = jsonType[x.aNode[i].eType];
    }
    jsonPrintf(100, &s,"node %3u: %7s n=%-4d up=%-4d",
               i, zType, x.aNode[i].n, x.aUp[i]);
    assert( x.aNode[i].eU==0 || x.aNode[i].eU==1 );
    if( x.aNode[i].u.zJContent!=0 ){
      assert( x.aNode[i].eU==1 );
      jsonAppendRaw(&s, " ", 1);
      jsonAppendRaw(&s, x.aNode[i].u.zJContent, x.aNode[i].n);
    }else{
      assert( x.aNode[i].eU==0 );
    }
    jsonAppendRaw(&s, "\n", 1);
  }
  jsonParseReset(&x);
  jsonResult(&s);
}

191967
191968
191969
191970
191971
191972
191973

191974
191975
191976
191977
191978
191979
191980
191981
191982
191983
191984
191985
191986
191987
191988
191989






191990
191991
191992
191993
191994
191995
191996
191997
191998
191999
192000
192001
192002
192003
192004


192005

192006
192007


192008
192009
192010
192011
192012
192013
192014
  }
  iRoot = iTarget;
  for(i=1; i<pPatch->n; i += jsonNodeSize(&pPatch[i+1])+1){
    u32 nKey;
    const char *zKey;
    assert( pPatch[i].eType==JSON_STRING );
    assert( pPatch[i].jnFlags & JNODE_LABEL );

    nKey = pPatch[i].n;
    zKey = pPatch[i].u.zJContent;
    assert( (pPatch[i].jnFlags & JNODE_RAW)==0 );
    for(j=1; j<pTarget->n; j += jsonNodeSize(&pTarget[j+1])+1 ){
      assert( pTarget[j].eType==JSON_STRING );
      assert( pTarget[j].jnFlags & JNODE_LABEL );
      assert( (pPatch[i].jnFlags & JNODE_RAW)==0 );
      if( pTarget[j].n==nKey && strncmp(pTarget[j].u.zJContent,zKey,nKey)==0 ){
        if( pTarget[j+1].jnFlags & (JNODE_REMOVE|JNODE_PATCH) ) break;
        if( pPatch[i+1].eType==JSON_NULL ){
          pTarget[j+1].jnFlags |= JNODE_REMOVE;
        }else{
          JsonNode *pNew = jsonMergePatch(pParse, iTarget+j+1, &pPatch[i+1]);
          if( pNew==0 ) return 0;
          pTarget = &pParse->aNode[iTarget];
          if( pNew!=&pTarget[j+1] ){






            pTarget[j+1].u.pPatch = pNew;
            pTarget[j+1].jnFlags |= JNODE_PATCH;
          }
        }
        break;
      }
    }
    if( j>=pTarget->n && pPatch[i+1].eType!=JSON_NULL ){
      int iStart, iPatch;
      iStart = jsonParseAddNode(pParse, JSON_OBJECT, 2, 0);
      jsonParseAddNode(pParse, JSON_STRING, nKey, zKey);
      iPatch = jsonParseAddNode(pParse, JSON_TRUE, 0, 0);
      if( pParse->oom ) return 0;
      jsonRemoveAllNulls(pPatch);
      pTarget = &pParse->aNode[iTarget];


      pParse->aNode[iRoot].jnFlags |= JNODE_APPEND;

      pParse->aNode[iRoot].u.iAppend = iStart - iRoot;
      iRoot = iStart;


      pParse->aNode[iPatch].jnFlags |= JNODE_PATCH;
      pParse->aNode[iPatch].u.pPatch = &pPatch[i+1];
    }
  }
  return pTarget;
}








>
















>
>
>
>
>
>















>
>

>


>
>







193463
193464
193465
193466
193467
193468
193469
193470
193471
193472
193473
193474
193475
193476
193477
193478
193479
193480
193481
193482
193483
193484
193485
193486
193487
193488
193489
193490
193491
193492
193493
193494
193495
193496
193497
193498
193499
193500
193501
193502
193503
193504
193505
193506
193507
193508
193509
193510
193511
193512
193513
193514
193515
193516
193517
193518
193519
193520
193521
193522
  }
  iRoot = iTarget;
  for(i=1; i<pPatch->n; i += jsonNodeSize(&pPatch[i+1])+1){
    u32 nKey;
    const char *zKey;
    assert( pPatch[i].eType==JSON_STRING );
    assert( pPatch[i].jnFlags & JNODE_LABEL );
    assert( pPatch[i].eU==1 );
    nKey = pPatch[i].n;
    zKey = pPatch[i].u.zJContent;
    assert( (pPatch[i].jnFlags & JNODE_RAW)==0 );
    for(j=1; j<pTarget->n; j += jsonNodeSize(&pTarget[j+1])+1 ){
      assert( pTarget[j].eType==JSON_STRING );
      assert( pTarget[j].jnFlags & JNODE_LABEL );
      assert( (pPatch[i].jnFlags & JNODE_RAW)==0 );
      if( pTarget[j].n==nKey && strncmp(pTarget[j].u.zJContent,zKey,nKey)==0 ){
        if( pTarget[j+1].jnFlags & (JNODE_REMOVE|JNODE_PATCH) ) break;
        if( pPatch[i+1].eType==JSON_NULL ){
          pTarget[j+1].jnFlags |= JNODE_REMOVE;
        }else{
          JsonNode *pNew = jsonMergePatch(pParse, iTarget+j+1, &pPatch[i+1]);
          if( pNew==0 ) return 0;
          pTarget = &pParse->aNode[iTarget];
          if( pNew!=&pTarget[j+1] ){
            assert( pTarget[j+1].eU==0
                 || pTarget[j+1].eU==1
                 || pTarget[j+1].eU==2 );
            testcase( pTarget[j+1].eU==1 );
            testcase( pTarget[j+1].eU==2 );
            VVA( pTarget[j+1].eU = 5 );
            pTarget[j+1].u.pPatch = pNew;
            pTarget[j+1].jnFlags |= JNODE_PATCH;
          }
        }
        break;
      }
    }
    if( j>=pTarget->n && pPatch[i+1].eType!=JSON_NULL ){
      int iStart, iPatch;
      iStart = jsonParseAddNode(pParse, JSON_OBJECT, 2, 0);
      jsonParseAddNode(pParse, JSON_STRING, nKey, zKey);
      iPatch = jsonParseAddNode(pParse, JSON_TRUE, 0, 0);
      if( pParse->oom ) return 0;
      jsonRemoveAllNulls(pPatch);
      pTarget = &pParse->aNode[iTarget];
      assert( pParse->aNode[iRoot].eU==0 || pParse->aNode[iRoot].eU==2 );
      testcase( pParse->aNode[iRoot].eU==2 );
      pParse->aNode[iRoot].jnFlags |= JNODE_APPEND;
      VVA( pParse->aNode[iRoot].eU = 2 );
      pParse->aNode[iRoot].u.iAppend = iStart - iRoot;
      iRoot = iStart;
      assert( pParse->aNode[iPatch].eU==0 );
      VVA( pParse->aNode[iPatch].eU = 5 );
      pParse->aNode[iPatch].jnFlags |= JNODE_PATCH;
      pParse->aNode[iPatch].u.pPatch = &pPatch[i+1];
    }
  }
  return pTarget;
}

192142
192143
192144
192145
192146
192147
192148


192149

192150
192151
192152
192153

192154
192155
192156
192157
192158
192159
192160
  if( jsonParse(&x, ctx, (const char*)sqlite3_value_text(argv[0])) ) return;
  assert( x.nNode );
  for(i=1; i<(u32)argc; i+=2){
    zPath = (const char*)sqlite3_value_text(argv[i]);
    pNode = jsonLookup(&x, zPath, 0, ctx);
    if( x.nErr ) goto replace_err;
    if( pNode ){


      pNode->jnFlags |= (u8)JNODE_REPLACE;

      pNode->u.iReplace = i + 1;
    }
  }
  if( x.aNode[0].jnFlags & JNODE_REPLACE ){

    sqlite3_result_value(ctx, argv[x.aNode[0].u.iReplace]);
  }else{
    jsonReturnJson(x.aNode, ctx, argv);
  }
replace_err:
  jsonParseReset(&x);
}







>
>

>




>







193650
193651
193652
193653
193654
193655
193656
193657
193658
193659
193660
193661
193662
193663
193664
193665
193666
193667
193668
193669
193670
193671
193672
  if( jsonParse(&x, ctx, (const char*)sqlite3_value_text(argv[0])) ) return;
  assert( x.nNode );
  for(i=1; i<(u32)argc; i+=2){
    zPath = (const char*)sqlite3_value_text(argv[i]);
    pNode = jsonLookup(&x, zPath, 0, ctx);
    if( x.nErr ) goto replace_err;
    if( pNode ){
      assert( pNode->eU==0 || pNode->eU==1 || pNode->eU==4 );
      json_testcase( pNode->eU!=0 && pNode->eU!=1 );
      pNode->jnFlags |= (u8)JNODE_REPLACE;
      VVA( pNode->eU =  4 );
      pNode->u.iReplace = i + 1;
    }
  }
  if( x.aNode[0].jnFlags & JNODE_REPLACE ){
    assert( x.aNode[0].eU==4 );
    sqlite3_result_value(ctx, argv[x.aNode[0].u.iReplace]);
  }else{
    jsonReturnJson(x.aNode, ctx, argv);
  }
replace_err:
  jsonParseReset(&x);
}
192196
192197
192198
192199
192200
192201
192202



192203
192204
192205
192206
192207

192208
192209
192210
192211
192212
192213
192214
    pNode = jsonLookup(&x, zPath, &bApnd, ctx);
    if( x.oom ){
      sqlite3_result_error_nomem(ctx);
      goto jsonSetDone;
    }else if( x.nErr ){
      goto jsonSetDone;
    }else if( pNode && (bApnd || bIsSet) ){



      pNode->jnFlags |= (u8)JNODE_REPLACE;
      pNode->u.iReplace = i + 1;
    }
  }
  if( x.aNode[0].jnFlags & JNODE_REPLACE ){

    sqlite3_result_value(ctx, argv[x.aNode[0].u.iReplace]);
  }else{
    jsonReturnJson(x.aNode, ctx, argv);
  }
jsonSetDone:
  jsonParseReset(&x);
}







>
>
>





>







193708
193709
193710
193711
193712
193713
193714
193715
193716
193717
193718
193719
193720
193721
193722
193723
193724
193725
193726
193727
193728
193729
193730
    pNode = jsonLookup(&x, zPath, &bApnd, ctx);
    if( x.oom ){
      sqlite3_result_error_nomem(ctx);
      goto jsonSetDone;
    }else if( x.nErr ){
      goto jsonSetDone;
    }else if( pNode && (bApnd || bIsSet) ){
      json_testcase( pNode->eU!=0 && pNode->eU!=1 && pNode->eU!=4 );
      assert( pNode->eU!=3 || pNode->eU!=5 );
      VVA( pNode->eU = 4 );
      pNode->jnFlags |= (u8)JNODE_REPLACE;
      pNode->u.iReplace = i + 1;
    }
  }
  if( x.aNode[0].jnFlags & JNODE_REPLACE ){
    assert( x.aNode[0].eU==4 );
    sqlite3_result_value(ctx, argv[x.aNode[0].u.iReplace]);
  }else{
    jsonReturnJson(x.aNode, ctx, argv);
  }
jsonSetDone:
  jsonParseReset(&x);
}
192551
192552
192553
192554
192555
192556
192557



192558
192559
192560
192561
192562
192563
192564
    p->i++;
    p->iRowid++;
    if( p->i<p->iEnd ){
      u32 iUp = p->sParse.aUp[p->i];
      JsonNode *pUp = &p->sParse.aNode[iUp];
      p->eType = pUp->eType;
      if( pUp->eType==JSON_ARRAY ){



        if( iUp==p->i-1 ){
          pUp->u.iKey = 0;
        }else{
          pUp->u.iKey++;
        }
      }
    }







>
>
>







194067
194068
194069
194070
194071
194072
194073
194074
194075
194076
194077
194078
194079
194080
194081
194082
194083
    p->i++;
    p->iRowid++;
    if( p->i<p->iEnd ){
      u32 iUp = p->sParse.aUp[p->i];
      JsonNode *pUp = &p->sParse.aNode[iUp];
      p->eType = pUp->eType;
      if( pUp->eType==JSON_ARRAY ){
        assert( pUp->eU==0 || pUp->eU==3 );
        json_testcase( pUp->eU==3 );
        VVA( pUp->eU = 3 );
        if( iUp==p->i-1 ){
          pUp->u.iKey = 0;
        }else{
          pUp->u.iKey++;
        }
      }
    }
192597
192598
192599
192600
192601
192602
192603


192604
192605
192606
192607
192608
192609

192610
192611
192612
192613
192614
192615
192616
    return;
  }
  iUp = p->sParse.aUp[i];
  jsonEachComputePath(p, pStr, iUp);
  pNode = &p->sParse.aNode[i];
  pUp = &p->sParse.aNode[iUp];
  if( pUp->eType==JSON_ARRAY ){


    jsonPrintf(30, pStr, "[%d]", pUp->u.iKey);
  }else{
    assert( pUp->eType==JSON_OBJECT );
    if( (pNode->jnFlags & JNODE_LABEL)==0 ) pNode--;
    assert( pNode->eType==JSON_STRING );
    assert( pNode->jnFlags & JNODE_LABEL );

    jsonPrintf(pNode->n+1, pStr, ".%.*s", pNode->n-2, pNode->u.zJContent+1);
  }
}

/* Return the value of a column */
static int jsonEachColumn(
  sqlite3_vtab_cursor *cur,   /* The cursor */







>
>






>







194116
194117
194118
194119
194120
194121
194122
194123
194124
194125
194126
194127
194128
194129
194130
194131
194132
194133
194134
194135
194136
194137
194138
    return;
  }
  iUp = p->sParse.aUp[i];
  jsonEachComputePath(p, pStr, iUp);
  pNode = &p->sParse.aNode[i];
  pUp = &p->sParse.aNode[iUp];
  if( pUp->eType==JSON_ARRAY ){
    assert( pUp->eU==3 || (pUp->eU==0 && pUp->u.iKey==0) );
    testcase( pUp->eU==0 );
    jsonPrintf(30, pStr, "[%d]", pUp->u.iKey);
  }else{
    assert( pUp->eType==JSON_OBJECT );
    if( (pNode->jnFlags & JNODE_LABEL)==0 ) pNode--;
    assert( pNode->eType==JSON_STRING );
    assert( pNode->jnFlags & JNODE_LABEL );
    assert( pNode->eU==1 );
    jsonPrintf(pNode->n+1, pStr, ".%.*s", pNode->n-2, pNode->u.zJContent+1);
  }
}

/* Return the value of a column */
static int jsonEachColumn(
  sqlite3_vtab_cursor *cur,   /* The cursor */
192624
192625
192626
192627
192628
192629
192630

192631
192632
192633
192634
192635
192636
192637
      if( p->i==0 ) break;
      if( p->eType==JSON_OBJECT ){
        jsonReturn(pThis, ctx, 0);
      }else if( p->eType==JSON_ARRAY ){
        u32 iKey;
        if( p->bRecursive ){
          if( p->iRowid==0 ) break;

          iKey = p->sParse.aNode[p->sParse.aUp[p->i]].u.iKey;
        }else{
          iKey = p->iRowid;
        }
        sqlite3_result_int64(ctx, (sqlite3_int64)iKey);
      }
      break;







>







194146
194147
194148
194149
194150
194151
194152
194153
194154
194155
194156
194157
194158
194159
194160
      if( p->i==0 ) break;
      if( p->eType==JSON_OBJECT ){
        jsonReturn(pThis, ctx, 0);
      }else if( p->eType==JSON_ARRAY ){
        u32 iKey;
        if( p->bRecursive ){
          if( p->iRowid==0 ) break;
          assert( p->sParse.aNode[p->sParse.aUp[p->i]].eU==3 );
          iKey = p->sParse.aNode[p->sParse.aUp[p->i]].u.iKey;
        }else{
          iKey = p->iRowid;
        }
        sqlite3_result_int64(ctx, (sqlite3_int64)iKey);
      }
      break;
192673
192674
192675
192676
192677
192678
192679

192680
192681
192682
192683
192684
192685
192686
          jsonAppendRaw(&x, p->zRoot, (int)strlen(p->zRoot));
        }else{
          jsonAppendChar(&x, '$');
        }
        if( p->eType==JSON_ARRAY ){
          jsonPrintf(30, &x, "[%d]", p->iRowid);
        }else if( p->eType==JSON_OBJECT ){

          jsonPrintf(pThis->n, &x, ".%.*s", pThis->n-2, pThis->u.zJContent+1);
        }
      }
      jsonResult(&x);
      break;
    }
    case JEACH_PATH: {







>







194196
194197
194198
194199
194200
194201
194202
194203
194204
194205
194206
194207
194208
194209
194210
          jsonAppendRaw(&x, p->zRoot, (int)strlen(p->zRoot));
        }else{
          jsonAppendChar(&x, '$');
        }
        if( p->eType==JSON_ARRAY ){
          jsonPrintf(30, &x, "[%d]", p->iRowid);
        }else if( p->eType==JSON_OBJECT ){
          assert( pThis->eU==1 );
          jsonPrintf(pThis->n, &x, ".%.*s", pThis->n-2, pThis->u.zJContent+1);
        }
      }
      jsonResult(&x);
      break;
    }
    case JEACH_PATH: {
192740
192741
192742
192743
192744
192745
192746

192747
192748
192749
192750
192751
192752
192753
  pConstraint = pIdxInfo->aConstraint;
  for(i=0; i<pIdxInfo->nConstraint; i++, pConstraint++){
    int iCol;
    int iMask;
    if( pConstraint->iColumn < JEACH_JSON ) continue;
    iCol = pConstraint->iColumn - JEACH_JSON;
    assert( iCol==0 || iCol==1 );

    iMask = 1 << iCol;
    if( pConstraint->usable==0 ){
      unusableMask |= iMask;
    }else if( pConstraint->op==SQLITE_INDEX_CONSTRAINT_EQ ){
      aIdx[iCol] = i;
      idxMask |= iMask;
    }







>







194264
194265
194266
194267
194268
194269
194270
194271
194272
194273
194274
194275
194276
194277
194278
  pConstraint = pIdxInfo->aConstraint;
  for(i=0; i<pIdxInfo->nConstraint; i++, pConstraint++){
    int iCol;
    int iMask;
    if( pConstraint->iColumn < JEACH_JSON ) continue;
    iCol = pConstraint->iColumn - JEACH_JSON;
    assert( iCol==0 || iCol==1 );
    testcase( iCol==0 );
    iMask = 1 << iCol;
    if( pConstraint->usable==0 ){
      unusableMask |= iMask;
    }else if( pConstraint->op==SQLITE_INDEX_CONSTRAINT_EQ ){
      aIdx[iCol] = i;
      idxMask |= iMask;
    }
192837
192838
192839
192840
192841
192842
192843


192844
192845
192846
192847
192848
192849
192850
      }
    }else{
      pNode = p->sParse.aNode;
    }
    p->iBegin = p->i = (int)(pNode - p->sParse.aNode);
    p->eType = pNode->eType;
    if( p->eType>=JSON_ARRAY ){


      pNode->u.iKey = 0;
      p->iEnd = p->i + pNode->n + 1;
      if( p->bRecursive ){
        p->eType = p->sParse.aNode[p->sParse.aUp[p->i]].eType;
        if( p->i>0 && (p->sParse.aNode[p->i-1].jnFlags & JNODE_LABEL)!=0 ){
          p->i--;
        }







>
>







194362
194363
194364
194365
194366
194367
194368
194369
194370
194371
194372
194373
194374
194375
194376
194377
      }
    }else{
      pNode = p->sParse.aNode;
    }
    p->iBegin = p->i = (int)(pNode - p->sParse.aNode);
    p->eType = pNode->eType;
    if( p->eType>=JSON_ARRAY ){
      assert( pNode->eU==0 );
      VVA( pNode->eU = 3 );
      pNode->u.iKey = 0;
      p->iEnd = p->i + pNode->n + 1;
      if( p->bRecursive ){
        p->eType = p->sParse.aNode[p->sParse.aUp[p->i]].eType;
        if( p->i>0 && (p->sParse.aNode[p->i-1].jnFlags & JNODE_LABEL)!=0 ){
          p->i--;
        }
193097
193098
193099
193100
193101
193102
193103



193104
193105
193106
193107
193108
193109
193110
#if !defined(NDEBUG) && !defined(SQLITE_DEBUG)
# define NDEBUG 1
#endif
#if defined(NDEBUG) && defined(SQLITE_DEBUG)
# undef NDEBUG
#endif
#if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_MUTATION_TEST)



# define ALWAYS(X)      (1)
# define NEVER(X)       (0)
#elif !defined(NDEBUG)
# define ALWAYS(X)      ((X)?1:(assert(0),0))
# define NEVER(X)       ((X)?(assert(0),1):0)
#else
# define ALWAYS(X)      (X)







>
>
>







194624
194625
194626
194627
194628
194629
194630
194631
194632
194633
194634
194635
194636
194637
194638
194639
194640
#if !defined(NDEBUG) && !defined(SQLITE_DEBUG)
# define NDEBUG 1
#endif
#if defined(NDEBUG) && defined(SQLITE_DEBUG)
# undef NDEBUG
#endif
#if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_MUTATION_TEST)
# define SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS 1
#endif
#if defined(SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS)
# define ALWAYS(X)      (1)
# define NEVER(X)       (0)
#elif !defined(NDEBUG)
# define ALWAYS(X)      ((X)?1:(assert(0),0))
# define NEVER(X)       ((X)?(assert(0),1):0)
#else
# define ALWAYS(X)      (X)
193448
193449
193450
193451
193452
193453
193454




193455

193456
193457
193458
193459
193460
193461
193462
#endif
#endif

/* The testcase() macro should already be defined in the amalgamation.  If
** it is not, make it a no-op.
*/
#ifndef SQLITE_AMALGAMATION




# define testcase(X)

#endif

/*
** Make sure that the compiler intrinsics we desire are enabled when
** compiling with an appropriate version of MSVC unless prevented by
** the SQLITE_DISABLE_INTRINSIC define.
*/







>
>
>
>
|
>







194978
194979
194980
194981
194982
194983
194984
194985
194986
194987
194988
194989
194990
194991
194992
194993
194994
194995
194996
194997
#endif
#endif

/* The testcase() macro should already be defined in the amalgamation.  If
** it is not, make it a no-op.
*/
#ifndef SQLITE_AMALGAMATION
# if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_DEBUG)
    unsigned int sqlite3RtreeTestcase = 0;
#   define testcase(X)  if( X ){ sqlite3RtreeTestcase += __LINE__; }
# else
#   define testcase(X)
# endif
#endif

/*
** Make sure that the compiler intrinsics we desire are enabled when
** compiling with an appropriate version of MSVC unless prevented by
** the SQLITE_DISABLE_INTRINSIC define.
*/
194294
194295
194296
194297
194298
194299
194300
194301
194302
194303
194304
194305
194306






194307
194308




194309
194310
194311
194312
194313
194314

194315
194316
194317
194318
194319
194320
194321
  assert(p->op==RTREE_LE || p->op==RTREE_LT || p->op==RTREE_GE
      || p->op==RTREE_GT || p->op==RTREE_EQ || p->op==RTREE_TRUE
      || p->op==RTREE_FALSE );
  assert( ((((char*)pCellData) - (char*)0)&3)==0 );  /* 4-byte aligned */
  switch( p->op ){
    case RTREE_TRUE:  return;   /* Always satisfied */
    case RTREE_FALSE: break;    /* Never satisfied */
    case RTREE_LE:
    case RTREE_LT:
    case RTREE_EQ:
      RTREE_DECODE_COORD(eInt, pCellData, val);
      /* val now holds the lower bound of the coordinate pair */
      if( p->u.rValue>=val ) return;






      if( p->op!=RTREE_EQ ) break;  /* RTREE_LE and RTREE_LT end here */
      /* Fall through for the RTREE_EQ case */





    default: /* RTREE_GT or RTREE_GE,  or fallthrough of RTREE_EQ */
      pCellData += 4;
      RTREE_DECODE_COORD(eInt, pCellData, val);
      /* val now holds the upper bound of the coordinate pair */
      if( p->u.rValue<=val ) return;

  }
  *peWithin = NOT_WITHIN;
}

/*
** Check the leaf RTree cell given by pCellData against constraint p.
** If this constraint is not satisfied, set *peWithin to NOT_WITHIN.







<
<



|
>
>
>
>
>
>
|
|
>
>
>
>

|




>







195829
195830
195831
195832
195833
195834
195835


195836
195837
195838
195839
195840
195841
195842
195843
195844
195845
195846
195847
195848
195849
195850
195851
195852
195853
195854
195855
195856
195857
195858
195859
195860
195861
195862
195863
195864
195865
  assert(p->op==RTREE_LE || p->op==RTREE_LT || p->op==RTREE_GE
      || p->op==RTREE_GT || p->op==RTREE_EQ || p->op==RTREE_TRUE
      || p->op==RTREE_FALSE );
  assert( ((((char*)pCellData) - (char*)0)&3)==0 );  /* 4-byte aligned */
  switch( p->op ){
    case RTREE_TRUE:  return;   /* Always satisfied */
    case RTREE_FALSE: break;    /* Never satisfied */


    case RTREE_EQ:
      RTREE_DECODE_COORD(eInt, pCellData, val);
      /* val now holds the lower bound of the coordinate pair */
      if( p->u.rValue>=val ){
        pCellData += 4;
        RTREE_DECODE_COORD(eInt, pCellData, val);
        /* val now holds the upper bound of the coordinate pair */
        if( p->u.rValue<=val ) return;
      }
      break;
    case RTREE_LE:
    case RTREE_LT:
      RTREE_DECODE_COORD(eInt, pCellData, val);
      /* val now holds the lower bound of the coordinate pair */
      if( p->u.rValue>=val ) return;
      break;

    default:
      pCellData += 4;
      RTREE_DECODE_COORD(eInt, pCellData, val);
      /* val now holds the upper bound of the coordinate pair */
      if( p->u.rValue<=val ) return;
      break;
  }
  *peWithin = NOT_WITHIN;
}

/*
** Check the leaf RTree cell given by pCellData against constraint p.
** If this constraint is not satisfied, set *peWithin to NOT_WITHIN.
195212
195213
195214
195215
195216
195217
195218
195219
195220
195221
195222
195223
195224
195225
195226
    sqlite3_int64 iBest = 0;

    RtreeDValue fMinGrowth = RTREE_ZERO;
    RtreeDValue fMinArea = RTREE_ZERO;

    int nCell = NCELL(pNode);
    RtreeCell cell;
    RtreeNode *pChild;

    RtreeCell *aCell = 0;

    /* Select the child node which will be enlarged the least if pCell
    ** is inserted into it. Resolve ties by choosing the entry with
    ** the smallest area.
    */







|







196756
196757
196758
196759
196760
196761
196762
196763
196764
196765
196766
196767
196768
196769
196770
    sqlite3_int64 iBest = 0;

    RtreeDValue fMinGrowth = RTREE_ZERO;
    RtreeDValue fMinArea = RTREE_ZERO;

    int nCell = NCELL(pNode);
    RtreeCell cell;
    RtreeNode *pChild = 0;

    RtreeCell *aCell = 0;

    /* Select the child node which will be enlarged the least if pCell
    ** is inserted into it. Resolve ties by choosing the entry with
    ** the smallest area.
    */
195570
195571
195572
195573
195574
195575
195576

195577
195578
195579
195580
195581
195582
195583
    }
    if( pChild ){
      nodeRelease(pRtree, pChild->pParent);
      nodeReference(pNode);
      pChild->pParent = pNode;
    }
  }

  return xSetMapping(pRtree, iRowid, pNode->iNode);
}

static int SplitNode(
  Rtree *pRtree,
  RtreeNode *pNode,
  RtreeCell *pCell,







>







197114
197115
197116
197117
197118
197119
197120
197121
197122
197123
197124
197125
197126
197127
197128
    }
    if( pChild ){
      nodeRelease(pRtree, pChild->pParent);
      nodeReference(pNode);
      pChild->pParent = pNode;
    }
  }
  if( NEVER(pNode==0) ) return SQLITE_ERROR;
  return xSetMapping(pRtree, iRowid, pNode->iNode);
}

static int SplitNode(
  Rtree *pRtree,
  RtreeNode *pNode,
  RtreeCell *pCell,
196874
196875
196876
196877
196878
196879
196880

196881
196882
196883
196884
196885
196886
196887
  memset(&node, 0, sizeof(RtreeNode));
  memset(&tree, 0, sizeof(Rtree));
  tree.nDim = (u8)sqlite3_value_int(apArg[0]);
  if( tree.nDim<1 || tree.nDim>5 ) return;
  tree.nDim2 = tree.nDim*2;
  tree.nBytesPerCell = 8 + 8 * tree.nDim;
  node.zData = (u8 *)sqlite3_value_blob(apArg[1]);

  nData = sqlite3_value_bytes(apArg[1]);
  if( nData<4 ) return;
  if( nData<NCELL(&node)*tree.nBytesPerCell ) return;

  pOut = sqlite3_str_new(0);
  for(ii=0; ii<NCELL(&node); ii++){
    RtreeCell cell;







>







198419
198420
198421
198422
198423
198424
198425
198426
198427
198428
198429
198430
198431
198432
198433
  memset(&node, 0, sizeof(RtreeNode));
  memset(&tree, 0, sizeof(Rtree));
  tree.nDim = (u8)sqlite3_value_int(apArg[0]);
  if( tree.nDim<1 || tree.nDim>5 ) return;
  tree.nDim2 = tree.nDim*2;
  tree.nBytesPerCell = 8 + 8 * tree.nDim;
  node.zData = (u8 *)sqlite3_value_blob(apArg[1]);
  if( node.zData==0 ) return;
  nData = sqlite3_value_bytes(apArg[1]);
  if( nData<4 ) return;
  if( nData<NCELL(&node)*tree.nBytesPerCell ) return;

  pOut = sqlite3_str_new(0);
  for(ii=0; ii<NCELL(&node); ii++){
    RtreeCell cell;
197705
197706
197707
197708
197709
197710
197711

197712
197713
197714
197715
197716
197717
197718
197719
197720
197721
197722
197723
197724
197725
static GeoPoly *geopolyFuncParam(
  sqlite3_context *pCtx,      /* Context for error messages */
  sqlite3_value *pVal,        /* The value to decode */
  int *pRc                    /* Write error here */
){
  GeoPoly *p = 0;
  int nByte;

  if( sqlite3_value_type(pVal)==SQLITE_BLOB
   && (nByte = sqlite3_value_bytes(pVal))>=(4+6*sizeof(GeoCoord))
  ){
    const unsigned char *a = sqlite3_value_blob(pVal);
    int nVertex;
    if( a==0 ){
      sqlite3_result_error_nomem(pCtx);
      return 0;
    }
    nVertex = (a[1]<<16) + (a[2]<<8) + a[3];
    if( (a[0]==0 || a[0]==1)
     && (nVertex*2*sizeof(GeoCoord) + 4)==(unsigned int)nByte
    ){
      p = sqlite3_malloc64( sizeof(*p) + (nVertex-1)*2*sizeof(GeoCoord) );







>






|







199251
199252
199253
199254
199255
199256
199257
199258
199259
199260
199261
199262
199263
199264
199265
199266
199267
199268
199269
199270
199271
199272
static GeoPoly *geopolyFuncParam(
  sqlite3_context *pCtx,      /* Context for error messages */
  sqlite3_value *pVal,        /* The value to decode */
  int *pRc                    /* Write error here */
){
  GeoPoly *p = 0;
  int nByte;
  testcase( pCtx==0 );
  if( sqlite3_value_type(pVal)==SQLITE_BLOB
   && (nByte = sqlite3_value_bytes(pVal))>=(4+6*sizeof(GeoCoord))
  ){
    const unsigned char *a = sqlite3_value_blob(pVal);
    int nVertex;
    if( a==0 ){
      if( pCtx ) sqlite3_result_error_nomem(pCtx);
      return 0;
    }
    nVertex = (a[1]<<16) + (a[2]<<8) + a[3];
    if( (a[0]==0 || a[0]==1)
     && (nVertex*2*sizeof(GeoCoord) + 4)==(unsigned int)nByte
    ){
      p = sqlite3_malloc64( sizeof(*p) + (nVertex-1)*2*sizeof(GeoCoord) );
198538
198539
198540
198541
198542
198543
198544
198545
198546
198547
198548
198549
198550
198551
198552
198553
198554
198555
198556
      pSeg->y = pSeg->y0;
      pSeg->pNext = pActive;
      pActive = pSeg;
      needSort = 1;
    }else{
      /* Remove a segment */
      if( pActive==pThisEvent->pSeg ){
        pActive = pActive->pNext;
      }else{
        for(pSeg=pActive; pSeg; pSeg=pSeg->pNext){
          if( pSeg->pNext==pThisEvent->pSeg ){
            pSeg->pNext = pSeg->pNext->pNext;
            break;
          }
        }
      }
    }
    pThisEvent = pThisEvent->pNext;
  }







|



|







200085
200086
200087
200088
200089
200090
200091
200092
200093
200094
200095
200096
200097
200098
200099
200100
200101
200102
200103
      pSeg->y = pSeg->y0;
      pSeg->pNext = pActive;
      pActive = pSeg;
      needSort = 1;
    }else{
      /* Remove a segment */
      if( pActive==pThisEvent->pSeg ){
        pActive = ALWAYS(pActive) ? pActive->pNext : 0;
      }else{
        for(pSeg=pActive; pSeg; pSeg=pSeg->pNext){
          if( pSeg->pNext==pThisEvent->pSeg ){
            pSeg->pNext = ALWAYS(pSeg->pNext) ? pSeg->pNext->pNext : 0;
            break;
          }
        }
      }
    }
    pThisEvent = pThisEvent->pNext;
  }
198786
198787
198788
198789
198790
198791
198792

198793
198794
198795
198796
198797
198798
198799
    ** with the configured constraints.
    */
    rc = nodeAcquire(pRtree, 1, 0, &pRoot);
    if( rc==SQLITE_OK && idxNum<=3 ){
      RtreeCoord bbox[4];
      RtreeConstraint *p;
      assert( argc==1 );

      geopolyBBox(0, argv[0], bbox, &rc);
      if( rc ){
        goto geopoly_filter_end;
      }
      pCsr->aConstraint = p = sqlite3_malloc(sizeof(RtreeConstraint)*4);
      pCsr->nConstraint = 4;
      if( p==0 ){







>







200333
200334
200335
200336
200337
200338
200339
200340
200341
200342
200343
200344
200345
200346
200347
    ** with the configured constraints.
    */
    rc = nodeAcquire(pRtree, 1, 0, &pRoot);
    if( rc==SQLITE_OK && idxNum<=3 ){
      RtreeCoord bbox[4];
      RtreeConstraint *p;
      assert( argc==1 );
      assert( argv[0]!=0 );
      geopolyBBox(0, argv[0], bbox, &rc);
      if( rc ){
        goto geopoly_filter_end;
      }
      pCsr->aConstraint = p = sqlite3_malloc(sizeof(RtreeConstraint)*4);
      pCsr->nConstraint = 4;
      if( p==0 ){
199013
199014
199015
199016
199017
199018
199019

199020
199021
199022
199023
199024
199025
199026
  cell.iRowid = newRowid;

  if( nData>1                                 /* not a DELETE */
   && (!oldRowidValid                         /* INSERT */
        || !sqlite3_value_nochange(aData[2])  /* UPDATE _shape */
        || oldRowid!=newRowid)                /* Rowid change */
  ){

    geopolyBBox(0, aData[2], cell.aCoord, &rc);
    if( rc ){
      if( rc==SQLITE_ERROR ){
        pVtab->zErrMsg =
          sqlite3_mprintf("_shape does not contain a valid polygon");
      }
      goto geopoly_update_end;







>







200561
200562
200563
200564
200565
200566
200567
200568
200569
200570
200571
200572
200573
200574
200575
  cell.iRowid = newRowid;

  if( nData>1                                 /* not a DELETE */
   && (!oldRowidValid                         /* INSERT */
        || !sqlite3_value_nochange(aData[2])  /* UPDATE _shape */
        || oldRowid!=newRowid)                /* Rowid change */
  ){
    assert( aData[2]!=0 );
    geopolyBBox(0, aData[2], cell.aCoord, &rc);
    if( rc ){
      if( rc==SQLITE_ERROR ){
        pVtab->zErrMsg =
          sqlite3_mprintf("_shape does not contain a valid polygon");
      }
      goto geopoly_update_end;
200939
200940
200941
200942
200943
200944
200945







200946
200947
200948
200949
200950
200951
200952

/*
** Swap two objects of type TYPE.
*/
#if !defined(SQLITE_AMALGAMATION)
# define SWAP(TYPE,A,B) {TYPE t=A; A=B; B=t;}
#endif








/*
** The rbu_state table is used to save the state of a partially applied
** update so that it can be resumed later. The table consists of integer
** keys mapped to values as follows:
**
** RBU_STATE_STAGE:







>
>
>
>
>
>
>







202488
202489
202490
202491
202492
202493
202494
202495
202496
202497
202498
202499
202500
202501
202502
202503
202504
202505
202506
202507
202508

/*
** Swap two objects of type TYPE.
*/
#if !defined(SQLITE_AMALGAMATION)
# define SWAP(TYPE,A,B) {TYPE t=A; A=B; B=t;}
#endif

/*
** Name of the URI option that causes RBU to take an exclusive lock as
** part of the incremental checkpoint operation.
*/
#define RBU_EXCLUSIVE_CHECKPOINT "rbu_exclusive_checkpoint"


/*
** The rbu_state table is used to save the state of a partially applied
** update so that it can be resumed later. The table consists of integer
** keys mapped to values as follows:
**
** RBU_STATE_STAGE:
202386
202387
202388
202389
202390
202391
202392
202393
202394
202395
202396
202397
202398
202399
202400
**
** except that the "?" placeholders are replaced with literal values.
**
** If the expression cannot be created, NULL is returned. In this case,
** the caller has to use an OFFSET clause to extract only the required
** rows from the sourct table, just as it does for an RBU update operation.
*/
char *rbuVacuumIndexStart(
  sqlite3rbu *p,                  /* RBU handle */
  RbuObjIter *pIter               /* RBU iterator object */
){
  char *zOrder = 0;
  char *zLhs = 0;
  char *zSelect = 0;
  char *zVector = 0;







|







203942
203943
203944
203945
203946
203947
203948
203949
203950
203951
203952
203953
203954
203955
203956
**
** except that the "?" placeholders are replaced with literal values.
**
** If the expression cannot be created, NULL is returned. In this case,
** the caller has to use an OFFSET clause to extract only the required
** rows from the sourct table, just as it does for an RBU update operation.
*/
static char *rbuVacuumIndexStart(
  sqlite3rbu *p,                  /* RBU handle */
  RbuObjIter *pIter               /* RBU iterator object */
){
  char *zOrder = 0;
  char *zLhs = 0;
  char *zSelect = 0;
  char *zVector = 0;
203586
203587
203588
203589
203590
203591
203592




203593
203594
203595
203596

203597
203598
203599

203600
203601
203602
203603
203604
203605
203606
  return pRet;
}


/*
** Open the database handle and attach the RBU database as "rbu". If an
** error occurs, leave an error code and message in the RBU handle.




*/
static void rbuOpenDatabase(sqlite3rbu *p, int *pbRetry){
  assert( p->rc || (p->dbMain==0 && p->dbRbu==0) );
  assert( p->rc || rbuIsVacuum(p) || p->zTarget!=0 );


  /* Open the RBU database */
  p->dbRbu = rbuOpenDbhandle(p, p->zRbu, 1);


  if( p->rc==SQLITE_OK && rbuIsVacuum(p) ){
    sqlite3_file_control(p->dbRbu, "main", SQLITE_FCNTL_RBUCNT, (void*)p);
    if( p->zState==0 ){
      const char *zFile = sqlite3_db_filename(p->dbRbu, "main");
      p->zState = rbuMPrintf(p, "file://%s-vacuum?modeof=%s", zFile, zFile);
    }







>
>
>
>

|


>



>







205142
205143
205144
205145
205146
205147
205148
205149
205150
205151
205152
205153
205154
205155
205156
205157
205158
205159
205160
205161
205162
205163
205164
205165
205166
205167
205168
  return pRet;
}


/*
** Open the database handle and attach the RBU database as "rbu". If an
** error occurs, leave an error code and message in the RBU handle.
**
** If argument dbMain is not NULL, then it is a database handle already
** open on the target database. Use this handle instead of opening a new
** one.
*/
static void rbuOpenDatabase(sqlite3rbu *p, sqlite3 *dbMain, int *pbRetry){
  assert( p->rc || (p->dbMain==0 && p->dbRbu==0) );
  assert( p->rc || rbuIsVacuum(p) || p->zTarget!=0 );
  assert( dbMain==0 || rbuIsVacuum(p)==0 );

  /* Open the RBU database */
  p->dbRbu = rbuOpenDbhandle(p, p->zRbu, 1);
  p->dbMain = dbMain;

  if( p->rc==SQLITE_OK && rbuIsVacuum(p) ){
    sqlite3_file_control(p->dbRbu, "main", SQLITE_FCNTL_RBUCNT, (void*)p);
    if( p->zState==0 ){
      const char *zFile = sqlite3_db_filename(p->dbRbu, "main");
      p->zState = rbuMPrintf(p, "file://%s-vacuum?modeof=%s", zFile, zFile);
    }
203958
203959
203960
203961
203962
203963
203964
203965

203966
203967

203968

203969

203970
203971
203972
203973












203974
203975
203976
203977
203978
203979
203980

  iOff = (i64)(pFrame->iDbPage-1) * p->pgsz;
  p->rc = pDb->pMethods->xWrite(pDb, p->aBuf, p->pgsz, iOff);
}


/*
** Take an EXCLUSIVE lock on the database file.

*/
static void rbuLockDatabase(sqlite3rbu *p){

  sqlite3_file *pReal = p->pTargetFd->pReal;

  assert( p->rc==SQLITE_OK );

  p->rc = pReal->pMethods->xLock(pReal, SQLITE_LOCK_SHARED);
  if( p->rc==SQLITE_OK ){
    p->rc = pReal->pMethods->xLock(pReal, SQLITE_LOCK_EXCLUSIVE);
  }












}

#if defined(_WIN32_WCE)
static LPWSTR rbuWinUtf8ToUnicode(const char *zFilename){
  int nChar;
  LPWSTR zWideFilename;








|
>

|
>
|
>
|
>
|
|
|
|
>
>
>
>
>
>
>
>
>
>
>
>







205520
205521
205522
205523
205524
205525
205526
205527
205528
205529
205530
205531
205532
205533
205534
205535
205536
205537
205538
205539
205540
205541
205542
205543
205544
205545
205546
205547
205548
205549
205550
205551
205552
205553
205554
205555
205556
205557
205558

  iOff = (i64)(pFrame->iDbPage-1) * p->pgsz;
  p->rc = pDb->pMethods->xWrite(pDb, p->aBuf, p->pgsz, iOff);
}


/*
** Take an EXCLUSIVE lock on the database file. Return SQLITE_OK if
** successful, or an SQLite error code otherwise.
*/
static int rbuLockDatabase(sqlite3 *db){
  int rc = SQLITE_OK;
  sqlite3_file *fd = 0;
  sqlite3_file_control(db, "main", SQLITE_FCNTL_FILE_POINTER, &fd);

  if( fd->pMethods ){
    rc = fd->pMethods->xLock(fd, SQLITE_LOCK_SHARED);
    if( rc==SQLITE_OK ){
      rc = fd->pMethods->xLock(fd, SQLITE_LOCK_EXCLUSIVE);
    }
  }
  return rc;
}

/*
** Return true if the database handle passed as the only argument
** was opened with the rbu_exclusive_checkpoint=1 URI parameter
** specified. Or false otherwise.
*/
static int rbuExclusiveCheckpoint(sqlite3 *db){
  const char *zUri = sqlite3_db_filename(db, 0);
  return sqlite3_uri_boolean(zUri, RBU_EXCLUSIVE_CHECKPOINT, 0);
}

#if defined(_WIN32_WCE)
static LPWSTR rbuWinUtf8ToUnicode(const char *zFilename){
  int nChar;
  LPWSTR zWideFilename;

204024
204025
204026
204027
204028
204029
204030
204031
204032
204033
204034
204035
204036
204037
204038
204039
204040
204041
204042







204043
204044
204045
204046
204047
204048
204049
    /* Move the *-oal file to *-wal. At this point connection p->db is
    ** holding a SHARED lock on the target database file (because it is
    ** in WAL mode). So no other connection may be writing the db.
    **
    ** In order to ensure that there are no database readers, an EXCLUSIVE
    ** lock is obtained here before the *-oal is moved to *-wal.
    */
    rbuLockDatabase(p);
    if( p->rc==SQLITE_OK ){
      rbuFileSuffix3(zBase, zWal);
      rbuFileSuffix3(zBase, zOal);

      /* Re-open the databases. */
      rbuObjIterFinalize(&p->objiter);
      sqlite3_close(p->dbRbu);
      sqlite3_close(p->dbMain);
      p->dbMain = 0;
      p->dbRbu = 0;








#if defined(_WIN32_WCE)
      {
        LPWSTR zWideOal;
        LPWSTR zWideWal;

        zWideOal = rbuWinUtf8ToUnicode(zOal);
        if( zWideOal ){







|
<
|
|

|
|
|
|
|
|

>
>
>
>
>
>
>







205602
205603
205604
205605
205606
205607
205608
205609

205610
205611
205612
205613
205614
205615
205616
205617
205618
205619
205620
205621
205622
205623
205624
205625
205626
205627
205628
205629
205630
205631
205632
205633
    /* Move the *-oal file to *-wal. At this point connection p->db is
    ** holding a SHARED lock on the target database file (because it is
    ** in WAL mode). So no other connection may be writing the db.
    **
    ** In order to ensure that there are no database readers, an EXCLUSIVE
    ** lock is obtained here before the *-oal is moved to *-wal.
    */
    sqlite3 *dbMain = 0;

    rbuFileSuffix3(zBase, zWal);
    rbuFileSuffix3(zBase, zOal);

    /* Re-open the databases. */
    rbuObjIterFinalize(&p->objiter);
    sqlite3_close(p->dbRbu);
    sqlite3_close(p->dbMain);
    p->dbMain = 0;
    p->dbRbu = 0;

    dbMain = rbuOpenDbhandle(p, p->zTarget, 1);
    if( dbMain ){
      assert( p->rc==SQLITE_OK );
      p->rc = rbuLockDatabase(dbMain);
    }

    if( p->rc==SQLITE_OK ){
#if defined(_WIN32_WCE)
      {
        LPWSTR zWideOal;
        LPWSTR zWideWal;

        zWideOal = rbuWinUtf8ToUnicode(zOal);
        if( zWideOal ){
204062
204063
204064
204065
204066
204067
204068
204069









204070
204071
204072
204073
204074
204075
204076
204077
204078
204079
204080
        }else{
          p->rc = SQLITE_IOERR_NOMEM;
        }
      }
#else
      p->rc = rename(zOal, zWal) ? SQLITE_IOERR : SQLITE_OK;
#endif










      if( p->rc==SQLITE_OK ){
        rbuOpenDatabase(p, 0);
        rbuSetupCheckpoint(p, 0);
      }
    }
  }

  sqlite3_free(zWal);
  sqlite3_free(zOal);
}








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







205646
205647
205648
205649
205650
205651
205652
205653
205654
205655
205656
205657
205658
205659
205660
205661
205662
205663
205664
205665

205666
205667
205668
205669
205670
205671
205672
        }else{
          p->rc = SQLITE_IOERR_NOMEM;
        }
      }
#else
      p->rc = rename(zOal, zWal) ? SQLITE_IOERR : SQLITE_OK;
#endif
    }

    if( p->rc!=SQLITE_OK
     || rbuIsVacuum(p)
     || rbuExclusiveCheckpoint(dbMain)==0
    ){
      sqlite3_close(dbMain);
      dbMain = 0;
    }

    if( p->rc==SQLITE_OK ){
      rbuOpenDatabase(p, dbMain, 0);
      rbuSetupCheckpoint(p, 0);

    }
  }

  sqlite3_free(zWal);
  sqlite3_free(zOal);
}

204817
204818
204819
204820
204821
204822
204823
204824
204825
204826
204827
204828
204829
204830
204831
204832
204833
      /* If the first attempt to open the database file fails and the bRetry
      ** flag it set, this means that the db was not opened because it seemed
      ** to be a wal-mode db. But, this may have happened due to an earlier
      ** RBU vacuum operation leaving an old wal file in the directory.
      ** If this is the case, it will have been checkpointed and deleted
      ** when the handle was closed and a second attempt to open the
      ** database may succeed.  */
      rbuOpenDatabase(p, &bRetry);
      if( bRetry ){
        rbuOpenDatabase(p, 0);
      }
    }

    if( p->rc==SQLITE_OK ){
      pState = rbuLoadState(p);
      assert( pState || p->rc!=SQLITE_OK );
      if( p->rc==SQLITE_OK ){







|

|







206409
206410
206411
206412
206413
206414
206415
206416
206417
206418
206419
206420
206421
206422
206423
206424
206425
      /* If the first attempt to open the database file fails and the bRetry
      ** flag it set, this means that the db was not opened because it seemed
      ** to be a wal-mode db. But, this may have happened due to an earlier
      ** RBU vacuum operation leaving an old wal file in the directory.
      ** If this is the case, it will have been checkpointed and deleted
      ** when the handle was closed and a second attempt to open the
      ** database may succeed.  */
      rbuOpenDatabase(p, 0, &bRetry);
      if( bRetry ){
        rbuOpenDatabase(p, 0, 0);
      }
    }

    if( p->rc==SQLITE_OK ){
      pState = rbuLoadState(p);
      assert( pState || p->rc!=SQLITE_OK );
      if( p->rc==SQLITE_OK ){
204914
204915
204916
204917
204918
204919
204920








204921
204922
204923
204924
204925
204926
204927
          if( p->rc==SQLITE_OK ){
            rbuSetupOal(p, pState);
          }
        }
      }else if( p->eStage==RBU_STAGE_MOVE ){
        /* no-op */
      }else if( p->eStage==RBU_STAGE_CKPT ){








        rbuSetupCheckpoint(p, pState);
      }else if( p->eStage==RBU_STAGE_DONE ){
        p->rc = SQLITE_DONE;
      }else{
        p->rc = SQLITE_CORRUPT;
      }
    }







>
>
>
>
>
>
>
>







206506
206507
206508
206509
206510
206511
206512
206513
206514
206515
206516
206517
206518
206519
206520
206521
206522
206523
206524
206525
206526
206527
          if( p->rc==SQLITE_OK ){
            rbuSetupOal(p, pState);
          }
        }
      }else if( p->eStage==RBU_STAGE_MOVE ){
        /* no-op */
      }else if( p->eStage==RBU_STAGE_CKPT ){
        if( !rbuIsVacuum(p) && rbuExclusiveCheckpoint(p->dbMain) ){
          /* If the rbu_exclusive_checkpoint=1 URI parameter was specified
          ** and an incremental checkpoint is being resumed, attempt an
          ** exclusive lock on the db file. If this fails, so be it.  */
          p->eStage = RBU_STAGE_DONE;
          rbuLockDatabase(p->dbMain);
          p->eStage = RBU_STAGE_CKPT;
        }
        rbuSetupCheckpoint(p, pState);
      }else if( p->eStage==RBU_STAGE_DONE ){
        p->rc = SQLITE_DONE;
      }else{
        p->rc = SQLITE_CORRUPT;
      }
    }
204951
204952
204953
204954
204955
204956
204957
204958
204959
204960
204961
204962
204963
204964
204965
*/
SQLITE_API sqlite3rbu *sqlite3rbu_open(
  const char *zTarget,
  const char *zRbu,
  const char *zState
){
  if( zTarget==0 || zRbu==0 ){ return rbuMisuseError(); }
  /* TODO: Check that zTarget and zRbu are non-NULL */
  return openRbuHandle(zTarget, zRbu, zState);
}

/*
** Open a handle to begin or resume an RBU VACUUM operation.
*/
SQLITE_API sqlite3rbu *sqlite3rbu_vacuum(







<







206551
206552
206553
206554
206555
206556
206557

206558
206559
206560
206561
206562
206563
206564
*/
SQLITE_API sqlite3rbu *sqlite3rbu_open(
  const char *zTarget,
  const char *zRbu,
  const char *zState
){
  if( zTarget==0 || zRbu==0 ){ return rbuMisuseError(); }

  return openRbuHandle(zTarget, zRbu, zState);
}

/*
** Open a handle to begin or resume an RBU VACUUM operation.
*/
SQLITE_API sqlite3rbu *sqlite3rbu_vacuum(
207871
207872
207873
207874
207875
207876
207877
207878
207879
207880
207881
207882
207883
207884
207885
        }
        n = sqlite3_value_bytes(pValue);
        if( z==0 && (eType!=SQLITE_BLOB || n>0) ) return SQLITE_NOMEM;
        nVarint = sessionVarintLen(n);

        if( aBuf ){
          sessionVarintPut(&aBuf[1], n);
          if( n ) memcpy(&aBuf[nVarint + 1], z, n);
        }

        nByte = 1 + nVarint + n;
        break;
      }
    }
  }else{







|







209470
209471
209472
209473
209474
209475
209476
209477
209478
209479
209480
209481
209482
209483
209484
        }
        n = sqlite3_value_bytes(pValue);
        if( z==0 && (eType!=SQLITE_BLOB || n>0) ) return SQLITE_NOMEM;
        nVarint = sessionVarintLen(n);

        if( aBuf ){
          sessionVarintPut(&aBuf[1], n);
          if( n>0 ) memcpy(&aBuf[nVarint + 1], z, n);
        }

        nByte = 1 + nVarint + n;
        break;
      }
    }
  }else{
208476
208477
208478
208479
208480
208481
208482




208483
208484
208485
208486
208487
208488






208489
208490
208491
208492






208493
208494
208495
208496
208497
208498
208499
          "SELECT 0, 'tbl',  '', 0, '', 1     UNION ALL "
          "SELECT 1, 'idx',  '', 0, '', 2     UNION ALL "
          "SELECT 2, 'stat', '', 0, '', 0"
      );
    }else if( rc==SQLITE_ERROR ){
      zPragma = sqlite3_mprintf("");
    }else{




      return rc;
    }
  }else{
    zPragma = sqlite3_mprintf("PRAGMA '%q'.table_info('%q')", zDb, zThis);
  }
  if( !zPragma ) return SQLITE_NOMEM;







  rc = sqlite3_prepare_v2(db, zPragma, -1, &pStmt, 0);
  sqlite3_free(zPragma);
  if( rc!=SQLITE_OK ) return rc;







  nByte = nThis + 1;
  while( SQLITE_ROW==sqlite3_step(pStmt) ){
    nByte += sqlite3_column_bytes(pStmt, 1);
    nDbCol++;
  }
  rc = sqlite3_reset(pStmt);







>
>
>
>





|
>
>
>
>
>
>



|
>
>
>
>
>
>







210075
210076
210077
210078
210079
210080
210081
210082
210083
210084
210085
210086
210087
210088
210089
210090
210091
210092
210093
210094
210095
210096
210097
210098
210099
210100
210101
210102
210103
210104
210105
210106
210107
210108
210109
210110
210111
210112
210113
210114
          "SELECT 0, 'tbl',  '', 0, '', 1     UNION ALL "
          "SELECT 1, 'idx',  '', 0, '', 2     UNION ALL "
          "SELECT 2, 'stat', '', 0, '', 0"
      );
    }else if( rc==SQLITE_ERROR ){
      zPragma = sqlite3_mprintf("");
    }else{
      *pazCol = 0;
      *pabPK = 0;
      *pnCol = 0;
      if( pzTab ) *pzTab = 0;
      return rc;
    }
  }else{
    zPragma = sqlite3_mprintf("PRAGMA '%q'.table_info('%q')", zDb, zThis);
  }
  if( !zPragma ){
    *pazCol = 0;
    *pabPK = 0;
    *pnCol = 0;
    if( pzTab ) *pzTab = 0;
    return SQLITE_NOMEM;
  }

  rc = sqlite3_prepare_v2(db, zPragma, -1, &pStmt, 0);
  sqlite3_free(zPragma);
  if( rc!=SQLITE_OK ){
    *pazCol = 0;
    *pabPK = 0;
    *pnCol = 0;
    if( pzTab ) *pzTab = 0;
    return rc;
  }

  nByte = nThis + 1;
  while( SQLITE_ROW==sqlite3_step(pStmt) ){
    nByte += sqlite3_column_bytes(pStmt, 1);
    nDbCol++;
  }
  rc = sqlite3_reset(pStmt);
208903
208904
208905
208906
208907
208908
208909
208910




208911
208912
208913
208914
208915
208916
208917
    /* If there is a table-filter configured, invoke it. If it returns 0,
    ** do not automatically add the new table. */
    if( pSession->xTableFilter==0
     || pSession->xTableFilter(pSession->pFilterCtx, zName)
    ){
      rc = sqlite3session_attach(pSession, zName);
      if( rc==SQLITE_OK ){
        for(pRet=pSession->pTable; pRet->pNext; pRet=pRet->pNext);




        assert( 0==sqlite3_strnicmp(pRet->zName, zName, nName+1) );
      }
    }
  }

  assert( rc==SQLITE_OK || pRet==0 );
  *ppTab = pRet;







|
>
>
>
>







210518
210519
210520
210521
210522
210523
210524
210525
210526
210527
210528
210529
210530
210531
210532
210533
210534
210535
210536
    /* If there is a table-filter configured, invoke it. If it returns 0,
    ** do not automatically add the new table. */
    if( pSession->xTableFilter==0
     || pSession->xTableFilter(pSession->pFilterCtx, zName)
    ){
      rc = sqlite3session_attach(pSession, zName);
      if( rc==SQLITE_OK ){
        pRet = pSession->pTable;
        while( ALWAYS(pRet) && pRet->pNext ){
          pRet = pRet->pNext;
        }
        assert( pRet!=0 );
        assert( 0==sqlite3_strnicmp(pRet->zName, zName, nName+1) );
      }
    }
  }

  assert( rc==SQLITE_OK || pRet==0 );
  *ppTab = pRet;
209676
209677
209678
209679
209680
209681
209682

209683
209684
209685
209686
209687
209688
209689
  int rc = SQLITE_OK;
  SessionBuffer buf2 = {0,0,0}; /* Buffer to accumulate new.* record in */
  int bNoop = 1;                /* Set to zero if any values are modified */
  int nRewind = pBuf->nBuf;     /* Set to zero if any values are modified */
  int i;                        /* Used to iterate through columns */
  u8 *pCsr = p->aRecord;        /* Used to iterate through old.* values */


  sessionAppendByte(pBuf, SQLITE_UPDATE, &rc);
  sessionAppendByte(pBuf, p->bIndirect, &rc);
  for(i=0; i<sqlite3_column_count(pStmt); i++){
    int bChanged = 0;
    int nAdvance;
    int eType = *pCsr;
    switch( eType ){







>







211295
211296
211297
211298
211299
211300
211301
211302
211303
211304
211305
211306
211307
211308
211309
  int rc = SQLITE_OK;
  SessionBuffer buf2 = {0,0,0}; /* Buffer to accumulate new.* record in */
  int bNoop = 1;                /* Set to zero if any values are modified */
  int nRewind = pBuf->nBuf;     /* Set to zero if any values are modified */
  int i;                        /* Used to iterate through columns */
  u8 *pCsr = p->aRecord;        /* Used to iterate through old.* values */

  assert( abPK!=0 );
  sessionAppendByte(pBuf, SQLITE_UPDATE, &rc);
  sessionAppendByte(pBuf, p->bIndirect, &rc);
  for(i=0; i<sqlite3_column_count(pStmt); i++){
    int bChanged = 0;
    int nAdvance;
    int eType = *pCsr;
    switch( eType ){
209980
209981
209982
209983
209984
209985
209986
209987

209988
209989
209990
209991
209992

209993
209994
209995
209996
209997
209998
209999
210000
210001
210002
210003
210004
210005
210006
210007
210008
210009
210010
210011
210012
210013
210014
  void **ppChangeset              /* OUT: Buffer containing changeset */
){
  sqlite3 *db = pSession->db;     /* Source database handle */
  SessionTable *pTab;             /* Used to iterate through attached tables */
  SessionBuffer buf = {0,0,0};    /* Buffer in which to accumlate changeset */
  int rc;                         /* Return code */

  assert( xOutput==0 || (pnChangeset==0 && ppChangeset==0 ) );


  /* Zero the output variables in case an error occurs. If this session
  ** object is already in the error state (sqlite3_session.rc != SQLITE_OK),
  ** this call will be a no-op.  */
  if( xOutput==0 ){

    *pnChangeset = 0;
    *ppChangeset = 0;
  }

  if( pSession->rc ) return pSession->rc;
  rc = sqlite3_exec(pSession->db, "SAVEPOINT changeset", 0, 0, 0);
  if( rc!=SQLITE_OK ) return rc;

  sqlite3_mutex_enter(sqlite3_db_mutex(db));

  for(pTab=pSession->pTable; rc==SQLITE_OK && pTab; pTab=pTab->pNext){
    if( pTab->nEntry ){
      const char *zName = pTab->zName;
      int nCol;                   /* Number of columns in table */
      u8 *abPK;                   /* Primary key array */
      const char **azCol = 0;     /* Table columns */
      int i;                      /* Used to iterate through hash buckets */
      sqlite3_stmt *pSel = 0;     /* SELECT statement to query table pTab */
      int nRewind = buf.nBuf;     /* Initial size of write buffer */
      int nNoop;                  /* Size of buffer after writing tbl header */

      /* Check the table schema is still Ok. */







|
>





>













|
|







211600
211601
211602
211603
211604
211605
211606
211607
211608
211609
211610
211611
211612
211613
211614
211615
211616
211617
211618
211619
211620
211621
211622
211623
211624
211625
211626
211627
211628
211629
211630
211631
211632
211633
211634
211635
211636
  void **ppChangeset              /* OUT: Buffer containing changeset */
){
  sqlite3 *db = pSession->db;     /* Source database handle */
  SessionTable *pTab;             /* Used to iterate through attached tables */
  SessionBuffer buf = {0,0,0};    /* Buffer in which to accumlate changeset */
  int rc;                         /* Return code */

  assert( xOutput==0 || (pnChangeset==0 && ppChangeset==0) );
  assert( xOutput!=0 || (pnChangeset!=0 && ppChangeset!=0) );

  /* Zero the output variables in case an error occurs. If this session
  ** object is already in the error state (sqlite3_session.rc != SQLITE_OK),
  ** this call will be a no-op.  */
  if( xOutput==0 ){
    assert( pnChangeset!=0  && ppChangeset!=0 );
    *pnChangeset = 0;
    *ppChangeset = 0;
  }

  if( pSession->rc ) return pSession->rc;
  rc = sqlite3_exec(pSession->db, "SAVEPOINT changeset", 0, 0, 0);
  if( rc!=SQLITE_OK ) return rc;

  sqlite3_mutex_enter(sqlite3_db_mutex(db));

  for(pTab=pSession->pTable; rc==SQLITE_OK && pTab; pTab=pTab->pNext){
    if( pTab->nEntry ){
      const char *zName = pTab->zName;
      int nCol = 0;               /* Number of columns in table */
      u8 *abPK = 0;               /* Primary key array */
      const char **azCol = 0;     /* Table columns */
      int i;                      /* Used to iterate through hash buckets */
      sqlite3_stmt *pSel = 0;     /* SELECT statement to query table pTab */
      int nRewind = buf.nBuf;     /* Initial size of write buffer */
      int nNoop;                  /* Size of buffer after writing tbl header */

      /* Check the table schema is still Ok. */
210038
210039
210040
210041
210042
210043
210044

210045
210046
210047
210048
210049
210050
210051
              int iCol;
              sessionAppendByte(&buf, SQLITE_INSERT, &rc);
              sessionAppendByte(&buf, p->bIndirect, &rc);
              for(iCol=0; iCol<nCol; iCol++){
                sessionAppendCol(&buf, pSel, iCol, &rc);
              }
            }else{

              rc = sessionAppendUpdate(&buf, bPatchset, pSel, p, abPK);
            }
          }else if( p->op!=SQLITE_INSERT ){
            rc = sessionAppendDelete(&buf, bPatchset, p, nCol, abPK);
          }
          if( rc==SQLITE_OK ){
            rc = sqlite3_reset(pSel);







>







211660
211661
211662
211663
211664
211665
211666
211667
211668
211669
211670
211671
211672
211673
211674
              int iCol;
              sessionAppendByte(&buf, SQLITE_INSERT, &rc);
              sessionAppendByte(&buf, p->bIndirect, &rc);
              for(iCol=0; iCol<nCol; iCol++){
                sessionAppendCol(&buf, pSel, iCol, &rc);
              }
            }else{
              assert( abPK!=0 );  /* Because sessionSelectStmt() returned ok */
              rc = sessionAppendUpdate(&buf, bPatchset, pSel, p, abPK);
            }
          }else if( p->op!=SQLITE_INSERT ){
            rc = sessionAppendDelete(&buf, bPatchset, p, nCol, abPK);
          }
          if( rc==SQLITE_OK ){
            rc = sqlite3_reset(pSel);
210098
210099
210100
210101
210102
210103
210104



210105
210106
210107
210108
210109
210110
210111
210112
210113
210114
210115
210116
210117
210118
210119

210120
210121
210122
210123
210124
210125
210126
210127
210128
210129
210130

210131
210132
210133
210134
210135
210136
210137
210138
210139
210140
210141
210142
210143
210144
210145

210146
210147
210148
210149
210150
210151
210152
** using sqlite3_free().
*/
SQLITE_API int sqlite3session_changeset(
  sqlite3_session *pSession,      /* Session object */
  int *pnChangeset,               /* OUT: Size of buffer at *ppChangeset */
  void **ppChangeset              /* OUT: Buffer containing changeset */
){



  int rc = sessionGenerateChangeset(pSession, 0, 0, 0, pnChangeset,ppChangeset);
  assert( rc || pnChangeset==0
       || pSession->bEnableSize==0 || *pnChangeset<=pSession->nMaxChangesetSize
  );
  return rc;
}

/*
** Streaming version of sqlite3session_changeset().
*/
SQLITE_API int sqlite3session_changeset_strm(
  sqlite3_session *pSession,
  int (*xOutput)(void *pOut, const void *pData, int nData),
  void *pOut
){

  return sessionGenerateChangeset(pSession, 0, xOutput, pOut, 0, 0);
}

/*
** Streaming version of sqlite3session_patchset().
*/
SQLITE_API int sqlite3session_patchset_strm(
  sqlite3_session *pSession,
  int (*xOutput)(void *pOut, const void *pData, int nData),
  void *pOut
){

  return sessionGenerateChangeset(pSession, 1, xOutput, pOut, 0, 0);
}

/*
** Obtain a patchset object containing all changes recorded by the
** session object passed as the first argument.
**
** It is the responsibility of the caller to eventually free the buffer
** using sqlite3_free().
*/
SQLITE_API int sqlite3session_patchset(
  sqlite3_session *pSession,      /* Session object */
  int *pnPatchset,                /* OUT: Size of buffer at *ppChangeset */
  void **ppPatchset               /* OUT: Buffer containing changeset */
){

  return sessionGenerateChangeset(pSession, 1, 0, 0, pnPatchset, ppPatchset);
}

/*
** Enable or disable the session object passed as the first argument.
*/
SQLITE_API int sqlite3session_enable(sqlite3_session *pSession, int bEnable){







>
>
>
|














>











>















>







211721
211722
211723
211724
211725
211726
211727
211728
211729
211730
211731
211732
211733
211734
211735
211736
211737
211738
211739
211740
211741
211742
211743
211744
211745
211746
211747
211748
211749
211750
211751
211752
211753
211754
211755
211756
211757
211758
211759
211760
211761
211762
211763
211764
211765
211766
211767
211768
211769
211770
211771
211772
211773
211774
211775
211776
211777
211778
211779
211780
211781
** using sqlite3_free().
*/
SQLITE_API int sqlite3session_changeset(
  sqlite3_session *pSession,      /* Session object */
  int *pnChangeset,               /* OUT: Size of buffer at *ppChangeset */
  void **ppChangeset              /* OUT: Buffer containing changeset */
){
  int rc;

  if( pnChangeset==0 || ppChangeset==0 ) return SQLITE_MISUSE;
  rc = sessionGenerateChangeset(pSession, 0, 0, 0, pnChangeset,ppChangeset);
  assert( rc || pnChangeset==0
       || pSession->bEnableSize==0 || *pnChangeset<=pSession->nMaxChangesetSize
  );
  return rc;
}

/*
** Streaming version of sqlite3session_changeset().
*/
SQLITE_API int sqlite3session_changeset_strm(
  sqlite3_session *pSession,
  int (*xOutput)(void *pOut, const void *pData, int nData),
  void *pOut
){
  if( xOutput==0 ) return SQLITE_MISUSE;
  return sessionGenerateChangeset(pSession, 0, xOutput, pOut, 0, 0);
}

/*
** Streaming version of sqlite3session_patchset().
*/
SQLITE_API int sqlite3session_patchset_strm(
  sqlite3_session *pSession,
  int (*xOutput)(void *pOut, const void *pData, int nData),
  void *pOut
){
  if( xOutput==0 ) return SQLITE_MISUSE;
  return sessionGenerateChangeset(pSession, 1, xOutput, pOut, 0, 0);
}

/*
** Obtain a patchset object containing all changes recorded by the
** session object passed as the first argument.
**
** It is the responsibility of the caller to eventually free the buffer
** using sqlite3_free().
*/
SQLITE_API int sqlite3session_patchset(
  sqlite3_session *pSession,      /* Session object */
  int *pnPatchset,                /* OUT: Size of buffer at *ppChangeset */
  void **ppPatchset               /* OUT: Buffer containing changeset */
){
  if( pnPatchset==0 || ppPatchset==0 ) return SQLITE_MISUSE;
  return sessionGenerateChangeset(pSession, 1, 0, 0, pnPatchset, ppPatchset);
}

/*
** Enable or disable the session object passed as the first argument.
*/
SQLITE_API int sqlite3session_enable(sqlite3_session *pSession, int bEnable){
211102
211103
211104
211105
211106
211107
211108
211109
211110
211111
211112
211113
211114
211115
211116
211117
211118
211119
211120
      rc = xOutput(pOut, sOut.aBuf, sOut.nBuf);
      sOut.nBuf = 0;
      if( rc!=SQLITE_OK ) goto finished_invert;
    }
  }

  assert( rc==SQLITE_OK );
  if( pnInverted ){
    *pnInverted = sOut.nBuf;
    *ppInverted = sOut.aBuf;
    sOut.aBuf = 0;
  }else if( sOut.nBuf>0 ){
    rc = xOutput(pOut, sOut.aBuf, sOut.nBuf);
  }

 finished_invert:
  sqlite3_free(sOut.aBuf);
  sqlite3_free(apVal);
  sqlite3_free(sPK.aBuf);







|



|







212731
212732
212733
212734
212735
212736
212737
212738
212739
212740
212741
212742
212743
212744
212745
212746
212747
212748
212749
      rc = xOutput(pOut, sOut.aBuf, sOut.nBuf);
      sOut.nBuf = 0;
      if( rc!=SQLITE_OK ) goto finished_invert;
    }
  }

  assert( rc==SQLITE_OK );
  if( pnInverted && ALWAYS(ppInverted) ){
    *pnInverted = sOut.nBuf;
    *ppInverted = sOut.aBuf;
    sOut.aBuf = 0;
  }else if( sOut.nBuf>0 && ALWAYS(xOutput!=0) ){
    rc = xOutput(pOut, sOut.aBuf, sOut.nBuf);
  }

 finished_invert:
  sqlite3_free(sOut.aBuf);
  sqlite3_free(apVal);
  sqlite3_free(sPK.aBuf);
211562
211563
211564
211565
211566
211567
211568
211569
211570
211571
211572
211573
211574
211575
211576
  ** argument iterator points to a suitable entry. Make sure that xValue
  ** is one of these to guarantee that it is safe to ignore the return
  ** in the code below. */
  assert( xValue==sqlite3changeset_old || xValue==sqlite3changeset_new );

  for(i=0; rc==SQLITE_OK && i<nCol; i++){
    if( !abPK || abPK[i] ){
      sqlite3_value *pVal;
      (void)xValue(pIter, i, &pVal);
      if( pVal==0 ){
        /* The value in the changeset was "undefined". This indicates a
        ** corrupt changeset blob.  */
        rc = SQLITE_CORRUPT_BKPT;
      }else{
        rc = sessionBindValue(pStmt, i+1, pVal);







|







213191
213192
213193
213194
213195
213196
213197
213198
213199
213200
213201
213202
213203
213204
213205
  ** argument iterator points to a suitable entry. Make sure that xValue
  ** is one of these to guarantee that it is safe to ignore the return
  ** in the code below. */
  assert( xValue==sqlite3changeset_old || xValue==sqlite3changeset_new );

  for(i=0; rc==SQLITE_OK && i<nCol; i++){
    if( !abPK || abPK[i] ){
      sqlite3_value *pVal = 0;
      (void)xValue(pIter, i, &pVal);
      if( pVal==0 ){
        /* The value in the changeset was "undefined". This indicates a
        ** corrupt changeset blob.  */
        rc = SQLITE_CORRUPT_BKPT;
      }else{
        rc = sessionBindValue(pStmt, i+1, pVal);
212705
212706
212707
212708
212709
212710
212711
212712
212713
212714
212715
212716
212717
212718
212719
212720
212721
      }
    }
  }

  if( rc==SQLITE_OK ){
    if( xOutput ){
      if( buf.nBuf>0 ) rc = xOutput(pOut, buf.aBuf, buf.nBuf);
    }else{
      *ppOut = buf.aBuf;
      *pnOut = buf.nBuf;
      buf.aBuf = 0;
    }
  }
  sqlite3_free(buf.aBuf);

  return rc;
}







|

|







214334
214335
214336
214337
214338
214339
214340
214341
214342
214343
214344
214345
214346
214347
214348
214349
214350
      }
    }
  }

  if( rc==SQLITE_OK ){
    if( xOutput ){
      if( buf.nBuf>0 ) rc = xOutput(pOut, buf.aBuf, buf.nBuf);
    }else if( ppOut ){
      *ppOut = buf.aBuf;
      if( pnOut ) *pnOut = buf.nBuf;
      buf.aBuf = 0;
    }
  }
  sqlite3_free(buf.aBuf);

  return rc;
}
213107
213108
213109
213110
213111
213112
213113
213114
213115
213116
213117
213118
213119
213120
213121
  }

  if( rc==SQLITE_OK ){
    if( xOutput ){
      if( sOut.nBuf>0 ){
        rc = xOutput(pOut, sOut.aBuf, sOut.nBuf);
      }
    }else{
      *ppOut = (void*)sOut.aBuf;
      *pnOut = sOut.nBuf;
      sOut.aBuf = 0;
    }
  }
  sqlite3_free(sOut.aBuf);
  return rc;







|







214736
214737
214738
214739
214740
214741
214742
214743
214744
214745
214746
214747
214748
214749
214750
  }

  if( rc==SQLITE_OK ){
    if( xOutput ){
      if( sOut.nBuf>0 ){
        rc = xOutput(pOut, sOut.aBuf, sOut.nBuf);
      }
    }else if( ppOut ){
      *ppOut = (void*)sOut.aBuf;
      *pnOut = sOut.nBuf;
      sOut.aBuf = 0;
    }
  }
  sqlite3_free(sOut.aBuf);
  return rc;
213850
213851
213852
213853
213854
213855
213856





213857
213858







213859
213860
213861
213862
213863
213864
213865
typedef sqlite3_uint64 u64;

#ifndef ArraySize
# define ArraySize(x) ((int)(sizeof(x) / sizeof(x[0])))
#endif

#define testcase(x)





#define ALWAYS(x) 1
#define NEVER(x) 0








#define MIN(x,y) (((x) < (y)) ? (x) : (y))
#define MAX(x,y) (((x) > (y)) ? (x) : (y))

/*
** Constants for the largest and smallest possible 64-bit signed integers.
*/







>
>
>
>
>
|
|
>
>
>
>
>
>
>







215479
215480
215481
215482
215483
215484
215485
215486
215487
215488
215489
215490
215491
215492
215493
215494
215495
215496
215497
215498
215499
215500
215501
215502
215503
215504
215505
215506
typedef sqlite3_uint64 u64;

#ifndef ArraySize
# define ArraySize(x) ((int)(sizeof(x) / sizeof(x[0])))
#endif

#define testcase(x)

#if defined(SQLITE_COVERAGE_TEST) || defined(SQLITE_MUTATION_TEST)
# define SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS 1
#endif
#if defined(SQLITE_OMIT_AUXILIARY_SAFETY_CHECKS)
# define ALWAYS(X)      (1)
# define NEVER(X)       (0)
#elif !defined(NDEBUG)
# define ALWAYS(X)      ((X)?1:(assert(0),0))
# define NEVER(X)       ((X)?(assert(0),1):0)
#else
# define ALWAYS(X)      (X)
# define NEVER(X)       (X)
#endif

#define MIN(x,y) (((x) < (y)) ? (x) : (y))
#define MAX(x,y) (((x) > (y)) ? (x) : (y))

/*
** Constants for the largest and smallest possible 64-bit signed integers.
*/
213911
213912
213913
213914
213915
213916
213917
213918
213919
213920
213921
213922
213923
213924
213925
# define assert_nc(x) assert(x)
#endif

/*
** A version of memcmp() that does not cause asan errors if one of the pointer
** parameters is NULL and the number of bytes to compare is zero.
*/
#define fts5Memcmp(s1, s2, n) ((n)==0 ? 0 : memcmp((s1), (s2), (n)))

/* Mark a function parameter as unused, to suppress nuisance compiler
** warnings. */
#ifndef UNUSED_PARAM
# define UNUSED_PARAM(X)  (void)(X)
#endif








|







215552
215553
215554
215555
215556
215557
215558
215559
215560
215561
215562
215563
215564
215565
215566
# define assert_nc(x) assert(x)
#endif

/*
** A version of memcmp() that does not cause asan errors if one of the pointer
** parameters is NULL and the number of bytes to compare is zero.
*/
#define fts5Memcmp(s1, s2, n) ((n)<=0 ? 0 : memcmp((s1), (s2), (n)))

/* Mark a function parameter as unused, to suppress nuisance compiler
** warnings. */
#ifndef UNUSED_PARAM
# define UNUSED_PARAM(X)  (void)(X)
#endif

215030
215031
215032
215033
215034
215035
215036

215037
215038
215039
215040
215041
215042
215043
215044
215045
215046
#else
  fts5yyStackEntry fts5yystack[fts5YYSTACKDEPTH];  /* The parser's stack */
  fts5yyStackEntry *fts5yystackEnd;            /* Last entry in the stack */
#endif
};
typedef struct fts5yyParser fts5yyParser;


#ifndef NDEBUG
/* #include <stdio.h> */
/* #include <assert.h> */
static FILE *fts5yyTraceFILE = 0;
static char *fts5yyTracePrompt = 0;
#endif /* NDEBUG */

#ifndef NDEBUG
/*
** Turn parser tracing on by giving a stream to which to write the trace







>


<







216671
216672
216673
216674
216675
216676
216677
216678
216679
216680

216681
216682
216683
216684
216685
216686
216687
#else
  fts5yyStackEntry fts5yystack[fts5YYSTACKDEPTH];  /* The parser's stack */
  fts5yyStackEntry *fts5yystackEnd;            /* Last entry in the stack */
#endif
};
typedef struct fts5yyParser fts5yyParser;

/* #include <assert.h> */
#ifndef NDEBUG
/* #include <stdio.h> */

static FILE *fts5yyTraceFILE = 0;
static char *fts5yyTracePrompt = 0;
#endif /* NDEBUG */

#ifndef NDEBUG
/*
** Turn parser tracing on by giving a stream to which to write the trace
215969
215970
215971
215972
215973
215974
215975
215976
215977

215978
215979
215980
215981
215982
215983
215984

  while(1){ /* Exit by "break" */
    assert( fts5yypParser->fts5yytos>=fts5yypParser->fts5yystack );
    assert( fts5yyact==fts5yypParser->fts5yytos->stateno );
    fts5yyact = fts5yy_find_shift_action((fts5YYCODETYPE)fts5yymajor,fts5yyact);
    if( fts5yyact >= fts5YY_MIN_REDUCE ){
      unsigned int fts5yyruleno = fts5yyact - fts5YY_MIN_REDUCE; /* Reduce by this rule */
      assert( fts5yyruleno<(int)(sizeof(fts5yyRuleName)/sizeof(fts5yyRuleName[0])) );
#ifndef NDEBUG

      if( fts5yyTraceFILE ){
        int fts5yysize = fts5yyRuleInfoNRhs[fts5yyruleno];
        if( fts5yysize ){
          fprintf(fts5yyTraceFILE, "%sReduce %d [%s]%s, pop back to state %d.\n",
            fts5yyTracePrompt,
            fts5yyruleno, fts5yyRuleName[fts5yyruleno],
            fts5yyruleno<fts5YYNRULE_WITH_ACTION ? "" : " without external action",







<

>







217610
217611
217612
217613
217614
217615
217616

217617
217618
217619
217620
217621
217622
217623
217624
217625

  while(1){ /* Exit by "break" */
    assert( fts5yypParser->fts5yytos>=fts5yypParser->fts5yystack );
    assert( fts5yyact==fts5yypParser->fts5yytos->stateno );
    fts5yyact = fts5yy_find_shift_action((fts5YYCODETYPE)fts5yymajor,fts5yyact);
    if( fts5yyact >= fts5YY_MIN_REDUCE ){
      unsigned int fts5yyruleno = fts5yyact - fts5YY_MIN_REDUCE; /* Reduce by this rule */

#ifndef NDEBUG
      assert( fts5yyruleno<(int)(sizeof(fts5yyRuleName)/sizeof(fts5yyRuleName[0])) );
      if( fts5yyTraceFILE ){
        int fts5yysize = fts5yyRuleInfoNRhs[fts5yyruleno];
        if( fts5yysize ){
          fprintf(fts5yyTraceFILE, "%sReduce %d [%s]%s, pop back to state %d.\n",
            fts5yyTracePrompt,
            fts5yyruleno, fts5yyRuleName[fts5yyruleno],
            fts5yyruleno<fts5YYNRULE_WITH_ACTION ? "" : " without external action",
216937
216938
216939
216940
216941
216942
216943
216944
216945
216946
216947
216948
216949
216950
216951
*/
static void sqlite3Fts5BufferAppendBlob(
  int *pRc,
  Fts5Buffer *pBuf,
  u32 nData,
  const u8 *pData
){
  assert_nc( *pRc || nData>=0 );
  if( nData ){
    if( fts5BufferGrow(pRc, pBuf, nData) ) return;
    memcpy(&pBuf->p[pBuf->n], pData, nData);
    pBuf->n += nData;
  }
}








<







218578
218579
218580
218581
218582
218583
218584

218585
218586
218587
218588
218589
218590
218591
*/
static void sqlite3Fts5BufferAppendBlob(
  int *pRc,
  Fts5Buffer *pBuf,
  u32 nData,
  const u8 *pData
){

  if( nData ){
    if( fts5BufferGrow(pRc, pBuf, nData) ) return;
    memcpy(&pBuf->p[pBuf->n], pData, nData);
    pBuf->n += nData;
  }
}

217049
217050
217051
217052
217053
217054
217055
217056
217057
217058
217059
217060
217061
217062
217063
    /* EOF */
    *piOff = -1;
    return 1;
  }else{
    i64 iOff = *piOff;
    u32 iVal;
    fts5FastGetVarint32(a, i, iVal);
    assert( iVal>=0 );
    if( iVal<=1 ){
      if( iVal==0 ){
        *pi = i;
        return 0;
      }
      fts5FastGetVarint32(a, i, iVal);
      iOff = ((i64)iVal) << 32;







<







218689
218690
218691
218692
218693
218694
218695

218696
218697
218698
218699
218700
218701
218702
    /* EOF */
    *piOff = -1;
    return 1;
  }else{
    i64 iOff = *piOff;
    u32 iVal;
    fts5FastGetVarint32(a, i, iVal);

    if( iVal<=1 ){
      if( iVal==0 ){
        *pi = i;
        return 0;
      }
      fts5FastGetVarint32(a, i, iVal);
      iOff = ((i64)iVal) << 32;
217844
217845
217846
217847
217848
217849
217850

217851
217852
217853
217854
217855
217856
217857
217858
217859
217860
217861
217862
217863
217864
217865
217866
217867




217868
217869
217870
217871
217872
217873
217874
    int bOption = 0;
    int bMustBeCol = 0;

    z = fts5ConfigGobbleWord(&rc, zOrig, &zOne, &bMustBeCol);
    z = fts5ConfigSkipWhitespace(z);
    if( z && *z=='=' ){
      bOption = 1;

      z++;
      if( bMustBeCol ) z = 0;
    }
    z = fts5ConfigSkipWhitespace(z);
    if( z && z[0] ){
      int bDummy;
      z = fts5ConfigGobbleWord(&rc, z, &zTwo, &bDummy);
      if( z && z[0] ) z = 0;
    }

    if( rc==SQLITE_OK ){
      if( z==0 ){
        *pzErr = sqlite3_mprintf("parse error in \"%s\"", zOrig);
        rc = SQLITE_ERROR;
      }else{
        if( bOption ){
          rc = fts5ConfigParseSpecial(pGlobal, pRet, zOne, zTwo?zTwo:"", pzErr);




        }else{
          rc = fts5ConfigParseColumn(pRet, zOne, zTwo, pzErr);
          zOne = 0;
        }
      }
    }








>
















|
>
>
>
>







219483
219484
219485
219486
219487
219488
219489
219490
219491
219492
219493
219494
219495
219496
219497
219498
219499
219500
219501
219502
219503
219504
219505
219506
219507
219508
219509
219510
219511
219512
219513
219514
219515
219516
219517
219518
    int bOption = 0;
    int bMustBeCol = 0;

    z = fts5ConfigGobbleWord(&rc, zOrig, &zOne, &bMustBeCol);
    z = fts5ConfigSkipWhitespace(z);
    if( z && *z=='=' ){
      bOption = 1;
      assert( zOne!=0 );
      z++;
      if( bMustBeCol ) z = 0;
    }
    z = fts5ConfigSkipWhitespace(z);
    if( z && z[0] ){
      int bDummy;
      z = fts5ConfigGobbleWord(&rc, z, &zTwo, &bDummy);
      if( z && z[0] ) z = 0;
    }

    if( rc==SQLITE_OK ){
      if( z==0 ){
        *pzErr = sqlite3_mprintf("parse error in \"%s\"", zOrig);
        rc = SQLITE_ERROR;
      }else{
        if( bOption ){
          rc = fts5ConfigParseSpecial(pGlobal, pRet,
            ALWAYS(zOne)?zOne:"",
            zTwo?zTwo:"",
            pzErr
          );
        }else{
          rc = fts5ConfigParseColumn(pRet, zOne, zTwo, pzErr);
          zOne = 0;
        }
      }
    }

218677
218678
218679
218680
218681
218682
218683

218684
218685
218686
218687
218688
218689
218690
** that it points to.
*/
static i64 fts5ExprSynonymRowid(Fts5ExprTerm *pTerm, int bDesc, int *pbEof){
  i64 iRet = 0;
  int bRetValid = 0;
  Fts5ExprTerm *p;


  assert( pTerm->pSynonym );
  assert( bDesc==0 || bDesc==1 );
  for(p=pTerm; p; p=p->pSynonym){
    if( 0==sqlite3Fts5IterEof(p->pIter) ){
      i64 iRowid = p->pIter->iRowid;
      if( bRetValid==0 || (bDesc!=(iRowid<iRet)) ){
        iRet = iRowid;







>







220321
220322
220323
220324
220325
220326
220327
220328
220329
220330
220331
220332
220333
220334
220335
** that it points to.
*/
static i64 fts5ExprSynonymRowid(Fts5ExprTerm *pTerm, int bDesc, int *pbEof){
  i64 iRet = 0;
  int bRetValid = 0;
  Fts5ExprTerm *p;

  assert( pTerm );
  assert( pTerm->pSynonym );
  assert( bDesc==0 || bDesc==1 );
  for(p=pTerm; p; p=p->pSynonym){
    if( 0==sqlite3Fts5IterEof(p->pIter) ){
      i64 iRowid = p->pIter->iRowid;
      if( bRetValid==0 || (bDesc!=(iRowid<iRet)) ){
        iRet = iRowid;
220117
220118
220119
220120
220121
220122
220123
220124
220125
220126
220127
220128
220129
220130
220131
    }
  }else{
    /* This happens when parsing a token or quoted phrase that contains
    ** no token characters at all. (e.g ... MATCH '""'). */
    sCtx.pPhrase = sqlite3Fts5MallocZero(&rc, sizeof(Fts5ExprPhrase));
  }

  if( rc==SQLITE_OK ){
    /* All the allocations succeeded. Put the expression object together. */
    pNew->pIndex = pExpr->pIndex;
    pNew->pConfig = pExpr->pConfig;
    pNew->nPhrase = 1;
    pNew->apExprPhrase[0] = sCtx.pPhrase;
    pNew->pRoot->pNear->apPhrase[0] = sCtx.pPhrase;
    pNew->pRoot->pNear->nPhrase = 1;







|







221762
221763
221764
221765
221766
221767
221768
221769
221770
221771
221772
221773
221774
221775
221776
    }
  }else{
    /* This happens when parsing a token or quoted phrase that contains
    ** no token characters at all. (e.g ... MATCH '""'). */
    sCtx.pPhrase = sqlite3Fts5MallocZero(&rc, sizeof(Fts5ExprPhrase));
  }

  if( rc==SQLITE_OK && ALWAYS(sCtx.pPhrase) ){
    /* All the allocations succeeded. Put the expression object together. */
    pNew->pIndex = pExpr->pIndex;
    pNew->pConfig = pExpr->pConfig;
    pNew->nPhrase = 1;
    pNew->apExprPhrase[0] = sCtx.pPhrase;
    pNew->pRoot->pNear->apPhrase[0] = sCtx.pPhrase;
    pNew->pRoot->pNear->nPhrase = 1;
221098
221099
221100
221101
221102
221103
221104









221105
221106
221107
221108
221109
221110
221111
221112
221113
221114
221115
221116
221117
221118
221119
221120
221121

struct Fts5PoslistPopulator {
  Fts5PoslistWriter writer;
  int bOk;                        /* True if ok to populate */
  int bMiss;
};










static Fts5PoslistPopulator *sqlite3Fts5ExprClearPoslists(Fts5Expr *pExpr, int bLive){
  Fts5PoslistPopulator *pRet;
  pRet = sqlite3_malloc64(sizeof(Fts5PoslistPopulator)*pExpr->nPhrase);
  if( pRet ){
    int i;
    memset(pRet, 0, sizeof(Fts5PoslistPopulator)*pExpr->nPhrase);
    for(i=0; i<pExpr->nPhrase; i++){
      Fts5Buffer *pBuf = &pExpr->apExprPhrase[i]->poslist;
      Fts5ExprNode *pNode = pExpr->apExprPhrase[i]->pNode;
      assert( pExpr->apExprPhrase[i]->nTerm==1 );
      if( bLive &&
          (pBuf->n==0 || pNode->iRowid!=pExpr->pRoot->iRowid || pNode->bEof)
      ){
        pRet[i].bMiss = 1;
      }else{
        pBuf->n = 0;
      }







>
>
>
>
>
>
>
>
>









|







222743
222744
222745
222746
222747
222748
222749
222750
222751
222752
222753
222754
222755
222756
222757
222758
222759
222760
222761
222762
222763
222764
222765
222766
222767
222768
222769
222770
222771
222772
222773
222774
222775

struct Fts5PoslistPopulator {
  Fts5PoslistWriter writer;
  int bOk;                        /* True if ok to populate */
  int bMiss;
};

/*
** Clear the position lists associated with all phrases in the expression
** passed as the first argument. Argument bLive is true if the expression
** might be pointing to a real entry, otherwise it has just been reset.
**
** At present this function is only used for detail=col and detail=none
** fts5 tables. This implies that all phrases must be at most 1 token
** in size, as phrase matches are not supported without detail=full.
*/
static Fts5PoslistPopulator *sqlite3Fts5ExprClearPoslists(Fts5Expr *pExpr, int bLive){
  Fts5PoslistPopulator *pRet;
  pRet = sqlite3_malloc64(sizeof(Fts5PoslistPopulator)*pExpr->nPhrase);
  if( pRet ){
    int i;
    memset(pRet, 0, sizeof(Fts5PoslistPopulator)*pExpr->nPhrase);
    for(i=0; i<pExpr->nPhrase; i++){
      Fts5Buffer *pBuf = &pExpr->apExprPhrase[i]->poslist;
      Fts5ExprNode *pNode = pExpr->apExprPhrase[i]->pNode;
      assert( pExpr->apExprPhrase[i]->nTerm<=1 );
      if( bLive &&
          (pBuf->n==0 || pNode->iRowid!=pExpr->pRoot->iRowid || pNode->bEof)
      ){
        pRet[i].bMiss = 1;
      }else{
        pBuf->n = 0;
      }
221658
221659
221660
221661
221662
221663
221664
221665
221666
221667
221668
221669
221670
221671
221672
  }

  if( iCol>=0 ){
    if( pHash->eDetail==FTS5_DETAIL_NONE ){
      p->bContent = 1;
    }else{
      /* Append a new column value, if necessary */
      assert( iCol>=p->iCol );
      if( iCol!=p->iCol ){
        if( pHash->eDetail==FTS5_DETAIL_FULL ){
          pPtr[p->nData++] = 0x01;
          p->nData += sqlite3Fts5PutVarint(&pPtr[p->nData], iCol);
          p->iCol = (i16)iCol;
          p->iPos = 0;
        }else{







|







223312
223313
223314
223315
223316
223317
223318
223319
223320
223321
223322
223323
223324
223325
223326
  }

  if( iCol>=0 ){
    if( pHash->eDetail==FTS5_DETAIL_NONE ){
      p->bContent = 1;
    }else{
      /* Append a new column value, if necessary */
      assert_nc( iCol>=p->iCol );
      if( iCol!=p->iCol ){
        if( pHash->eDetail==FTS5_DETAIL_FULL ){
          pPtr[p->nData++] = 0x01;
          p->nData += sqlite3Fts5PutVarint(&pPtr[p->nData], iCol);
          p->iCol = (i16)iCol;
          p->iPos = 0;
        }else{
222463
222464
222465
222466
222467
222468
222469

222470


222471
222472
222473
222474
222475
222476
222477
222478
**
** Return -ve if pLeft is smaller than pRight, 0 if they are equal or
** +ve if pRight is smaller than pLeft. In other words:
**
**     res = *pLeft - *pRight
*/
static int fts5BufferCompare(Fts5Buffer *pLeft, Fts5Buffer *pRight){

  int nCmp = MIN(pLeft->n, pRight->n);


  int res = fts5Memcmp(pLeft->p, pRight->p, nCmp);
  return (res==0 ? (pLeft->n - pRight->n) : res);
}

static int fts5LeafFirstTermOff(Fts5Data *pLeaf){
  int ret;
  fts5GetVarint32(&pLeaf->p[pLeaf->szLeaf], ret);
  return ret;







>
|
>
>
|







224117
224118
224119
224120
224121
224122
224123
224124
224125
224126
224127
224128
224129
224130
224131
224132
224133
224134
224135
**
** Return -ve if pLeft is smaller than pRight, 0 if they are equal or
** +ve if pRight is smaller than pLeft. In other words:
**
**     res = *pLeft - *pRight
*/
static int fts5BufferCompare(Fts5Buffer *pLeft, Fts5Buffer *pRight){
  int nCmp, res;
  nCmp = MIN(pLeft->n, pRight->n);
  assert( nCmp<=0 || pLeft->p!=0 );
  assert( nCmp<=0 || pRight->p!=0 );
  res = fts5Memcmp(pLeft->p, pRight->p, nCmp);
  return (res==0 ? (pLeft->n - pRight->n) : res);
}

static int fts5LeafFirstTermOff(Fts5Data *pLeaf){
  int ret;
  fts5GetVarint32(&pLeaf->p[pLeaf->szLeaf], ret);
  return ret;
222710
222711
222712
222713
222714
222715
222716
222717
222718
222719
222720
222721
222722
222723
222724
**
** This function is a no-op if (*pRc) is not SQLITE_OK when it is called. If
** an error occurs, (*pRc) is set to an SQLite error code before returning.
*/
static void fts5StructureMakeWritable(int *pRc, Fts5Structure **pp){
  Fts5Structure *p = *pp;
  if( *pRc==SQLITE_OK && p->nRef>1 ){
    int nByte = sizeof(Fts5Structure)+(p->nLevel-1)*sizeof(Fts5StructureLevel);
    Fts5Structure *pNew;
    pNew = (Fts5Structure*)sqlite3Fts5MallocZero(pRc, nByte);
    if( pNew ){
      int i;
      memcpy(pNew, p, nByte);
      for(i=0; i<p->nLevel; i++) pNew->aLevel[i].aSeg = 0;
      for(i=0; i<p->nLevel; i++){







|







224367
224368
224369
224370
224371
224372
224373
224374
224375
224376
224377
224378
224379
224380
224381
**
** This function is a no-op if (*pRc) is not SQLITE_OK when it is called. If
** an error occurs, (*pRc) is set to an SQLite error code before returning.
*/
static void fts5StructureMakeWritable(int *pRc, Fts5Structure **pp){
  Fts5Structure *p = *pp;
  if( *pRc==SQLITE_OK && p->nRef>1 ){
    i64 nByte = sizeof(Fts5Structure)+(p->nLevel-1)*sizeof(Fts5StructureLevel);
    Fts5Structure *pNew;
    pNew = (Fts5Structure*)sqlite3Fts5MallocZero(pRc, nByte);
    if( pNew ){
      int i;
      memcpy(pNew, p, nByte);
      for(i=0; i<p->nLevel; i++) pNew->aLevel[i].aSeg = 0;
      for(i=0; i<p->nLevel; i++){
223636
223637
223638
223639
223640
223641
223642

223643
223644
223645
223646
223647
223648
223649
    pIter->pSeg = pSeg;
    pIter->iLeafPgno = pSeg->pgnoFirst-1;
    fts5SegIterNextPage(p, pIter);
  }

  if( p->rc==SQLITE_OK ){
    pIter->iLeafOffset = 4;

    assert_nc( pIter->pLeaf->nn>4 );
    assert_nc( fts5LeafFirstTermOff(pIter->pLeaf)==4 );
    pIter->iPgidxOff = pIter->pLeaf->szLeaf+1;
    fts5SegIterLoadTerm(p, pIter, 0);
    fts5SegIterLoadNPos(p, pIter);
  }
}







>







225293
225294
225295
225296
225297
225298
225299
225300
225301
225302
225303
225304
225305
225306
225307
    pIter->pSeg = pSeg;
    pIter->iLeafPgno = pSeg->pgnoFirst-1;
    fts5SegIterNextPage(p, pIter);
  }

  if( p->rc==SQLITE_OK ){
    pIter->iLeafOffset = 4;
    assert( pIter->pLeaf!=0 );
    assert_nc( pIter->pLeaf->nn>4 );
    assert_nc( fts5LeafFirstTermOff(pIter->pLeaf)==4 );
    pIter->iPgidxOff = pIter->pLeaf->szLeaf+1;
    fts5SegIterLoadTerm(p, pIter, 0);
    fts5SegIterLoadNPos(p, pIter);
  }
}
223738
223739
223740
223741
223742
223743
223744



223745
223746

223747
223748
223749
223750
223751
223752
223753
          pIter->pLeaf = pNew;
          pIter->iLeafOffset = pIter->iTermLeafOffset;
        }
      }else{
        int iRowidOff;
        iRowidOff = fts5LeafFirstRowidOff(pNew);
        if( iRowidOff ){



          pIter->pLeaf = pNew;
          pIter->iLeafOffset = iRowidOff;

        }
      }

      if( pIter->pLeaf ){
        u8 *a = &pIter->pLeaf->p[pIter->iLeafOffset];
        pIter->iLeafOffset += fts5GetVarint(a, (u64*)&pIter->iRowid);
        break;







>
>
>
|
|
>







225396
225397
225398
225399
225400
225401
225402
225403
225404
225405
225406
225407
225408
225409
225410
225411
225412
225413
225414
225415
          pIter->pLeaf = pNew;
          pIter->iLeafOffset = pIter->iTermLeafOffset;
        }
      }else{
        int iRowidOff;
        iRowidOff = fts5LeafFirstRowidOff(pNew);
        if( iRowidOff ){
          if( iRowidOff>=pNew->szLeaf ){
            p->rc = FTS5_CORRUPT;
          }else{
            pIter->pLeaf = pNew;
            pIter->iLeafOffset = iRowidOff;
          }
        }
      }

      if( pIter->pLeaf ){
        u8 *a = &pIter->pLeaf->p[pIter->iLeafOffset];
        pIter->iLeafOffset += fts5GetVarint(a, (u64*)&pIter->iRowid);
        break;
224140
224141
224142
224143
224144
224145
224146
224147
224148
224149
224150
224151
224152
224153
224154
224155
224156
224157
224158
224159
224160
224161
224162
224163
224164
224165
224166
224167
224168
*/
static void fts5LeafSeek(
  Fts5Index *p,                   /* Leave any error code here */
  int bGe,                        /* True for a >= search */
  Fts5SegIter *pIter,             /* Iterator to seek */
  const u8 *pTerm, int nTerm      /* Term to search for */
){
  int iOff;
  const u8 *a = pIter->pLeaf->p;
  int szLeaf = pIter->pLeaf->szLeaf;
  int n = pIter->pLeaf->nn;

  u32 nMatch = 0;
  u32 nKeep = 0;
  u32 nNew = 0;
  u32 iTermOff;
  int iPgidx;                     /* Current offset in pgidx */
  int bEndOfPage = 0;

  assert( p->rc==SQLITE_OK );

  iPgidx = szLeaf;
  iPgidx += fts5GetVarint32(&a[iPgidx], iTermOff);
  iOff = iTermOff;
  if( iOff>n ){
    p->rc = FTS5_CORRUPT;
    return;
  }








|

<
|





|




|







225802
225803
225804
225805
225806
225807
225808
225809
225810

225811
225812
225813
225814
225815
225816
225817
225818
225819
225820
225821
225822
225823
225824
225825
225826
225827
225828
225829
*/
static void fts5LeafSeek(
  Fts5Index *p,                   /* Leave any error code here */
  int bGe,                        /* True for a >= search */
  Fts5SegIter *pIter,             /* Iterator to seek */
  const u8 *pTerm, int nTerm      /* Term to search for */
){
  u32 iOff;
  const u8 *a = pIter->pLeaf->p;

  u32 n = (u32)pIter->pLeaf->nn;

  u32 nMatch = 0;
  u32 nKeep = 0;
  u32 nNew = 0;
  u32 iTermOff;
  u32 iPgidx;                     /* Current offset in pgidx */
  int bEndOfPage = 0;

  assert( p->rc==SQLITE_OK );

  iPgidx = (u32)pIter->pLeaf->szLeaf;
  iPgidx += fts5GetVarint32(&a[iPgidx], iTermOff);
  iOff = iTermOff;
  if( iOff>n ){
    p->rc = FTS5_CORRUPT;
    return;
  }

224220
224221
224222
224223
224224
224225
224226
224227
224228
224229
224230
224231
224232
224233
224234
224235
224236
224237
224238
224239
224240
224241
224242
    return;
  }else if( bEndOfPage ){
    do {
      fts5SegIterNextPage(p, pIter);
      if( pIter->pLeaf==0 ) return;
      a = pIter->pLeaf->p;
      if( fts5LeafIsTermless(pIter->pLeaf)==0 ){
        iPgidx = pIter->pLeaf->szLeaf;
        iPgidx += fts5GetVarint32(&pIter->pLeaf->p[iPgidx], iOff);
        if( iOff<4 || iOff>=pIter->pLeaf->szLeaf ){
          p->rc = FTS5_CORRUPT;
          return;
        }else{
          nKeep = 0;
          iTermOff = iOff;
          n = pIter->pLeaf->nn;
          iOff += fts5GetVarint32(&a[iOff], nNew);
          break;
        }
      }
    }while( 1 );
  }








|

|





|







225881
225882
225883
225884
225885
225886
225887
225888
225889
225890
225891
225892
225893
225894
225895
225896
225897
225898
225899
225900
225901
225902
225903
    return;
  }else if( bEndOfPage ){
    do {
      fts5SegIterNextPage(p, pIter);
      if( pIter->pLeaf==0 ) return;
      a = pIter->pLeaf->p;
      if( fts5LeafIsTermless(pIter->pLeaf)==0 ){
        iPgidx = (u32)pIter->pLeaf->szLeaf;
        iPgidx += fts5GetVarint32(&pIter->pLeaf->p[iPgidx], iOff);
        if( iOff<4 || (i64)iOff>=pIter->pLeaf->szLeaf ){
          p->rc = FTS5_CORRUPT;
          return;
        }else{
          nKeep = 0;
          iTermOff = iOff;
          n = (u32)pIter->pLeaf->nn;
          iOff += fts5GetVarint32(&a[iOff], nNew);
          break;
        }
      }
    }while( 1 );
  }

224596
224597
224598
224599
224600
224601
224602
224603
224604
224605
224606
224607
224608
224609
224610
  }else{
    fts5DataRelease(pIter->pNextLeaf);
    pIter->pNextLeaf = 0;
    pIter->iLeafPgno = iLeafPgno-1;
    fts5SegIterNextPage(p, pIter);
    assert( p->rc!=SQLITE_OK || pIter->iLeafPgno==iLeafPgno );

    if( p->rc==SQLITE_OK ){
      int iOff;
      u8 *a = pIter->pLeaf->p;
      int n = pIter->pLeaf->szLeaf;

      iOff = fts5LeafFirstRowidOff(pIter->pLeaf);
      if( iOff<4 || iOff>=n ){
        p->rc = FTS5_CORRUPT;







|







226257
226258
226259
226260
226261
226262
226263
226264
226265
226266
226267
226268
226269
226270
226271
  }else{
    fts5DataRelease(pIter->pNextLeaf);
    pIter->pNextLeaf = 0;
    pIter->iLeafPgno = iLeafPgno-1;
    fts5SegIterNextPage(p, pIter);
    assert( p->rc!=SQLITE_OK || pIter->iLeafPgno==iLeafPgno );

    if( p->rc==SQLITE_OK && ALWAYS(pIter->pLeaf!=0) ){
      int iOff;
      u8 *a = pIter->pLeaf->p;
      int n = pIter->pLeaf->szLeaf;

      iOff = fts5LeafFirstRowidOff(pIter->pLeaf);
      if( iOff<4 || iOff>=n ){
        p->rc = FTS5_CORRUPT;
225028
225029
225030
225031
225032
225033
225034


225035


225036
225037
225038
225039
225040
225041
225042
*/
static void fts5SegiterPoslist(
  Fts5Index *p,
  Fts5SegIter *pSeg,
  Fts5Colset *pColset,
  Fts5Buffer *pBuf
){


  if( 0==fts5BufferGrow(&p->rc, pBuf, pSeg->nPos+FTS5_DATA_ZERO_PADDING) ){


    memset(&pBuf->p[pBuf->n+pSeg->nPos], 0, FTS5_DATA_ZERO_PADDING);
    if( pColset==0 ){
      fts5ChunkIterate(p, pSeg, (void*)pBuf, fts5PoslistCallback);
    }else{
      if( p->pConfig->eDetail==FTS5_DETAIL_FULL ){
        PoslistCallbackCtx sCtx;
        sCtx.pBuf = pBuf;







>
>

>
>







226689
226690
226691
226692
226693
226694
226695
226696
226697
226698
226699
226700
226701
226702
226703
226704
226705
226706
226707
*/
static void fts5SegiterPoslist(
  Fts5Index *p,
  Fts5SegIter *pSeg,
  Fts5Colset *pColset,
  Fts5Buffer *pBuf
){
  assert( pBuf!=0 );
  assert( pSeg!=0 );
  if( 0==fts5BufferGrow(&p->rc, pBuf, pSeg->nPos+FTS5_DATA_ZERO_PADDING) ){
    assert( pBuf->p!=0 );
    assert( pBuf->nSpace >= pBuf->n+pSeg->nPos+FTS5_DATA_ZERO_PADDING );
    memset(&pBuf->p[pBuf->n+pSeg->nPos], 0, FTS5_DATA_ZERO_PADDING);
    if( pColset==0 ){
      fts5ChunkIterate(p, pSeg, (void*)pBuf, fts5PoslistCallback);
    }else{
      if( p->pConfig->eDetail==FTS5_DETAIL_FULL ){
        PoslistCallbackCtx sCtx;
        sCtx.pBuf = pBuf;
225252
225253
225254
225255
225256
225257
225258

225259
225260
225261
225262
225263
225264
225265
    fts5SegiterPoslist(pIter->pIndex, pSeg, pColset, &pIter->poslist);
    pIter->base.pData = pIter->poslist.p;
    pIter->base.nData = pIter->poslist.n;
  }
}

static void fts5IterSetOutputCb(int *pRc, Fts5Iter *pIter){

  if( *pRc==SQLITE_OK ){
    Fts5Config *pConfig = pIter->pIndex->pConfig;
    if( pConfig->eDetail==FTS5_DETAIL_NONE ){
      pIter->xSetOutputs = fts5IterSetOutputs_None;
    }

    else if( pIter->pColset==0 ){







>







226917
226918
226919
226920
226921
226922
226923
226924
226925
226926
226927
226928
226929
226930
226931
    fts5SegiterPoslist(pIter->pIndex, pSeg, pColset, &pIter->poslist);
    pIter->base.pData = pIter->poslist.p;
    pIter->base.nData = pIter->poslist.n;
  }
}

static void fts5IterSetOutputCb(int *pRc, Fts5Iter *pIter){
  assert( pIter!=0 || (*pRc)!=SQLITE_OK );
  if( *pRc==SQLITE_OK ){
    Fts5Config *pConfig = pIter->pIndex->pConfig;
    if( pConfig->eDetail==FTS5_DETAIL_NONE ){
      pIter->xSetOutputs = fts5IterSetOutputs_None;
    }

    else if( pIter->pColset==0 ){
225323
225324
225325
225326
225327
225328
225329
225330



225331
225332
225333
225334
225335
225336
225337
      nSeg = pStruct->nSegment;
      nSeg += (p->pHash ? 1 : 0);
    }else{
      nSeg = MIN(pStruct->aLevel[iLevel].nSeg, nSegment);
    }
  }
  *ppOut = pNew = fts5MultiIterAlloc(p, nSeg);
  if( pNew==0 ) return;



  pNew->bRev = (0!=(flags & FTS5INDEX_QUERY_DESC));
  pNew->bSkipEmpty = (0!=(flags & FTS5INDEX_QUERY_SKIPEMPTY));
  pNew->pColset = pColset;
  if( (flags & FTS5INDEX_QUERY_NOOUTPUT)==0 ){
    fts5IterSetOutputCb(&p->rc, pNew);
  }








|
>
>
>







226989
226990
226991
226992
226993
226994
226995
226996
226997
226998
226999
227000
227001
227002
227003
227004
227005
227006
      nSeg = pStruct->nSegment;
      nSeg += (p->pHash ? 1 : 0);
    }else{
      nSeg = MIN(pStruct->aLevel[iLevel].nSeg, nSegment);
    }
  }
  *ppOut = pNew = fts5MultiIterAlloc(p, nSeg);
  if( pNew==0 ){
    assert( p->rc!=SQLITE_OK );
    goto fts5MultiIterNew_post_check;
  }
  pNew->bRev = (0!=(flags & FTS5INDEX_QUERY_DESC));
  pNew->bSkipEmpty = (0!=(flags & FTS5INDEX_QUERY_SKIPEMPTY));
  pNew->pColset = pColset;
  if( (flags & FTS5INDEX_QUERY_NOOUTPUT)==0 ){
    fts5IterSetOutputCb(&p->rc, pNew);
  }

225387
225388
225389
225390
225391
225392
225393




225394
225395
225396
225397
225398
225399
225400
      pNew->xSetOutputs(pNew, pSeg);
    }

  }else{
    fts5MultiIterFree(pNew);
    *ppOut = 0;
  }




}

/*
** Create an Fts5Iter that iterates through the doclist provided
** as the second argument.
*/
static void fts5MultiIterNew2(







>
>
>
>







227056
227057
227058
227059
227060
227061
227062
227063
227064
227065
227066
227067
227068
227069
227070
227071
227072
227073
      pNew->xSetOutputs(pNew, pSeg);
    }

  }else{
    fts5MultiIterFree(pNew);
    *ppOut = 0;
  }

fts5MultiIterNew_post_check:
  assert( (*ppOut)!=0 || p->rc!=SQLITE_OK );
  return;
}

/*
** Create an Fts5Iter that iterates through the doclist provided
** as the second argument.
*/
static void fts5MultiIterNew2(
225434
225435
225436
225437
225438
225439
225440

225441
225442
225443
225444
225445
225446
225447
225448
}

/*
** Return true if the iterator is at EOF or if an error has occurred.
** False otherwise.
*/
static int fts5MultiIterEof(Fts5Index *p, Fts5Iter *pIter){

  assert( p->rc
      || (pIter->aSeg[ pIter->aFirst[1].iFirst ].pLeaf==0)==pIter->base.bEof
  );
  return (p->rc || pIter->base.bEof);
}

/*
** Return the rowid of the entry that the iterator currently points







>
|







227107
227108
227109
227110
227111
227112
227113
227114
227115
227116
227117
227118
227119
227120
227121
227122
}

/*
** Return true if the iterator is at EOF or if an error has occurred.
** False otherwise.
*/
static int fts5MultiIterEof(Fts5Index *p, Fts5Iter *pIter){
  assert( pIter!=0 || p->rc!=SQLITE_OK );
  assert( p->rc!=SQLITE_OK
      || (pIter->aSeg[ pIter->aFirst[1].iFirst ].pLeaf==0)==pIter->base.bEof
  );
  return (p->rc || pIter->base.bEof);
}

/*
** Return the rowid of the entry that the iterator currently points
226238
226239
226240
226241
226242
226243
226244

226245
226246
226247
226248
226249
226250
226251
    }
  }

  /* Flush the last leaf page to disk. Set the output segment b-tree height
  ** and last leaf page number at the same time.  */
  fts5WriteFinish(p, &writer, &pSeg->pgnoLast);


  if( fts5MultiIterEof(p, pIter) ){
    int i;

    /* Remove the redundant segments from the %_data table */
    for(i=0; i<nInput; i++){
      fts5DataRemoveSegment(p, pLvl->aSeg[i].iSegid);
    }







>







227912
227913
227914
227915
227916
227917
227918
227919
227920
227921
227922
227923
227924
227925
227926
    }
  }

  /* Flush the last leaf page to disk. Set the output segment b-tree height
  ** and last leaf page number at the same time.  */
  fts5WriteFinish(p, &writer, &pSeg->pgnoLast);

  assert( pIter!=0 || p->rc!=SQLITE_OK );
  if( fts5MultiIterEof(p, pIter) ){
    int i;

    /* Remove the redundant segments from the %_data table */
    for(i=0; i<nInput; i++){
      fts5DataRemoveSegment(p, pLvl->aSeg[i].iSegid);
    }
226338
226339
226340
226341
226342
226343
226344
226345
226346
226347
226348
226349
226350
226351
226352
** already occurred, this function is a no-op.
*/
static void fts5IndexAutomerge(
  Fts5Index *p,                   /* FTS5 backend object */
  Fts5Structure **ppStruct,       /* IN/OUT: Current structure of index */
  int nLeaf                       /* Number of output leaves just written */
){
  if( p->rc==SQLITE_OK && p->pConfig->nAutomerge>0 ){
    Fts5Structure *pStruct = *ppStruct;
    u64 nWrite;                   /* Initial value of write-counter */
    int nWork;                    /* Number of work-quanta to perform */
    int nRem;                     /* Number of leaf pages left to write */

    /* Update the write-counter. While doing so, set nWork. */
    nWrite = pStruct->nWriteCounter;







|







228013
228014
228015
228016
228017
228018
228019
228020
228021
228022
228023
228024
228025
228026
228027
** already occurred, this function is a no-op.
*/
static void fts5IndexAutomerge(
  Fts5Index *p,                   /* FTS5 backend object */
  Fts5Structure **ppStruct,       /* IN/OUT: Current structure of index */
  int nLeaf                       /* Number of output leaves just written */
){
  if( p->rc==SQLITE_OK && p->pConfig->nAutomerge>0 && ALWAYS((*ppStruct)!=0) ){
    Fts5Structure *pStruct = *ppStruct;
    u64 nWrite;                   /* Initial value of write-counter */
    int nWork;                    /* Number of work-quanta to perform */
    int nRem;                     /* Number of leaf pages left to write */

    /* Update the write-counter. While doing so, set nWork. */
    nWrite = pStruct->nWriteCounter;
227448
227449
227450
227451
227452
227453
227454

227455


227456
227457
227458
227459

227460
227461
227462
227463
227464
227465
227466
        );
        fts5StructureRelease(pStruct);
      }
    }else{
      /* Scan multiple terms in the main index */
      int bDesc = (flags & FTS5INDEX_QUERY_DESC)!=0;
      fts5SetupPrefixIter(p, bDesc, iPrefixIdx, buf.p, nToken+1, pColset,&pRet);

      assert( p->rc!=SQLITE_OK || pRet->pColset==0 );


      fts5IterSetOutputCb(&p->rc, pRet);
      if( p->rc==SQLITE_OK ){
        Fts5SegIter *pSeg = &pRet->aSeg[pRet->aFirst[1].iFirst];
        if( pSeg->pLeaf ) pRet->xSetOutputs(pRet, pSeg);

      }
    }

    if( p->rc ){
      sqlite3Fts5IterClose((Fts5IndexIter*)pRet);
      pRet = 0;
      sqlite3Fts5IndexCloseReader(p);







>
|
>
>
|
|
|
|
>







229123
229124
229125
229126
229127
229128
229129
229130
229131
229132
229133
229134
229135
229136
229137
229138
229139
229140
229141
229142
229143
229144
229145
        );
        fts5StructureRelease(pStruct);
      }
    }else{
      /* Scan multiple terms in the main index */
      int bDesc = (flags & FTS5INDEX_QUERY_DESC)!=0;
      fts5SetupPrefixIter(p, bDesc, iPrefixIdx, buf.p, nToken+1, pColset,&pRet);
      if( pRet==0 ){
        assert( p->rc!=SQLITE_OK );
      }else{
        assert( pRet->pColset==0 );
        fts5IterSetOutputCb(&p->rc, pRet);
        if( p->rc==SQLITE_OK ){
          Fts5SegIter *pSeg = &pRet->aSeg[pRet->aFirst[1].iFirst];
          if( pSeg->pLeaf ) pRet->xSetOutputs(pRet, pSeg);
        }
      }
    }

    if( p->rc ){
      sqlite3Fts5IterClose((Fts5IndexIter*)pRet);
      pRet = 0;
      sqlite3Fts5IndexCloseReader(p);
227700
227701
227702
227703
227704
227705
227706
227707
227708
227709
227710
227711
227712
227713
227714
  u64 *pCksum                     /* IN/OUT: Checksum value */
){
  int eDetail = p->pConfig->eDetail;
  u64 cksum = *pCksum;
  Fts5IndexIter *pIter = 0;
  int rc = sqlite3Fts5IndexQuery(p, z, n, flags, 0, &pIter);

  while( rc==SQLITE_OK && 0==sqlite3Fts5IterEof(pIter) ){
    i64 rowid = pIter->iRowid;

    if( eDetail==FTS5_DETAIL_NONE ){
      cksum ^= sqlite3Fts5IndexEntryCksum(rowid, 0, 0, iIdx, z, n);
    }else{
      Fts5PoslistReader sReader;
      for(sqlite3Fts5PoslistReaderInit(pIter->pData, pIter->nData, &sReader);







|







229379
229380
229381
229382
229383
229384
229385
229386
229387
229388
229389
229390
229391
229392
229393
  u64 *pCksum                     /* IN/OUT: Checksum value */
){
  int eDetail = p->pConfig->eDetail;
  u64 cksum = *pCksum;
  Fts5IndexIter *pIter = 0;
  int rc = sqlite3Fts5IndexQuery(p, z, n, flags, 0, &pIter);

  while( rc==SQLITE_OK && ALWAYS(pIter!=0) && 0==sqlite3Fts5IterEof(pIter) ){
    i64 rowid = pIter->iRowid;

    if( eDetail==FTS5_DETAIL_NONE ){
      cksum ^= sqlite3Fts5IndexEntryCksum(rowid, 0, 0, iIdx, z, n);
    }else{
      Fts5PoslistReader sReader;
      for(sqlite3Fts5PoslistReaderInit(pIter->pData, pIter->nData, &sReader);
228065
228066
228067
228068
228069
228070
228071

228072
228073
228074
228075
228076
228077
228078
228079
228080
228081



228082

228083
228084
228085
228086
228087
228088
228089
228090
228091
228092
228093
228094
228095
228096
228097
*/
static int sqlite3Fts5IndexIntegrityCheck(Fts5Index *p, u64 cksum, int bUseCksum){
  int eDetail = p->pConfig->eDetail;
  u64 cksum2 = 0;                 /* Checksum based on contents of indexes */
  Fts5Buffer poslist = {0,0,0};   /* Buffer used to hold a poslist */
  Fts5Iter *pIter;                /* Used to iterate through entire index */
  Fts5Structure *pStruct;         /* Index structure */


#ifdef SQLITE_DEBUG
  /* Used by extra internal tests only run if NDEBUG is not defined */
  u64 cksum3 = 0;                 /* Checksum based on contents of indexes */
  Fts5Buffer term = {0,0,0};      /* Buffer used to hold most recent term */
#endif
  const int flags = FTS5INDEX_QUERY_NOOUTPUT;

  /* Load the FTS index structure */
  pStruct = fts5StructureRead(p);





  /* Check that the internal nodes of each segment match the leaves */
  if( pStruct ){
    int iLvl, iSeg;
    for(iLvl=0; iLvl<pStruct->nLevel; iLvl++){
      for(iSeg=0; iSeg<pStruct->aLevel[iLvl].nSeg; iSeg++){
        Fts5StructureSegment *pSeg = &pStruct->aLevel[iLvl].aSeg[iSeg];
        fts5IndexIntegrityCheckSegment(p, pSeg);
      }
    }
  }

  /* The cksum argument passed to this function is a checksum calculated
  ** based on all expected entries in the FTS index (including prefix index
  ** entries). This block checks that a checksum calculated based on the
  ** actual contents of FTS index is identical.







>










>
>
>
|
>

<
<
|
|
|
|
<







229744
229745
229746
229747
229748
229749
229750
229751
229752
229753
229754
229755
229756
229757
229758
229759
229760
229761
229762
229763
229764
229765
229766
229767


229768
229769
229770
229771

229772
229773
229774
229775
229776
229777
229778
*/
static int sqlite3Fts5IndexIntegrityCheck(Fts5Index *p, u64 cksum, int bUseCksum){
  int eDetail = p->pConfig->eDetail;
  u64 cksum2 = 0;                 /* Checksum based on contents of indexes */
  Fts5Buffer poslist = {0,0,0};   /* Buffer used to hold a poslist */
  Fts5Iter *pIter;                /* Used to iterate through entire index */
  Fts5Structure *pStruct;         /* Index structure */
  int iLvl, iSeg;

#ifdef SQLITE_DEBUG
  /* Used by extra internal tests only run if NDEBUG is not defined */
  u64 cksum3 = 0;                 /* Checksum based on contents of indexes */
  Fts5Buffer term = {0,0,0};      /* Buffer used to hold most recent term */
#endif
  const int flags = FTS5INDEX_QUERY_NOOUTPUT;

  /* Load the FTS index structure */
  pStruct = fts5StructureRead(p);
  if( pStruct==0 ){
    assert( p->rc!=SQLITE_OK );
    return fts5IndexReturn(p);
  }

  /* Check that the internal nodes of each segment match the leaves */


  for(iLvl=0; iLvl<pStruct->nLevel; iLvl++){
    for(iSeg=0; iSeg<pStruct->aLevel[iLvl].nSeg; iSeg++){
      Fts5StructureSegment *pSeg = &pStruct->aLevel[iLvl].aSeg[iSeg];
      fts5IndexIntegrityCheckSegment(p, pSeg);

    }
  }

  /* The cksum argument passed to this function is a checksum calculated
  ** based on all expected entries in the FTS index (including prefix index
  ** entries). This block checks that a checksum calculated based on the
  ** actual contents of FTS index is identical.
230030
230031
230032
230033
230034
230035
230036

230037
230038
230039
230040
230041
230042
230043
230044
    /* This is either a full-table scan (ePlan==FTS5_PLAN_SCAN) or a lookup
    ** by rowid (ePlan==FTS5_PLAN_ROWID).  */
    pCsr->ePlan = (pRowidEq ? FTS5_PLAN_ROWID : FTS5_PLAN_SCAN);
    rc = sqlite3Fts5StorageStmt(
        pTab->pStorage, fts5StmtType(pCsr), &pCsr->pStmt, &pTab->p.base.zErrMsg
    );
    if( rc==SQLITE_OK ){

      if( pCsr->ePlan==FTS5_PLAN_ROWID ){
        sqlite3_bind_value(pCsr->pStmt, 1, pRowidEq);
      }else{
        sqlite3_bind_int64(pCsr->pStmt, 1, pCsr->iFirstRowid);
        sqlite3_bind_int64(pCsr->pStmt, 2, pCsr->iLastRowid);
      }
      rc = fts5NextMethod(pCursor);
    }







>
|







231711
231712
231713
231714
231715
231716
231717
231718
231719
231720
231721
231722
231723
231724
231725
231726
    /* This is either a full-table scan (ePlan==FTS5_PLAN_SCAN) or a lookup
    ** by rowid (ePlan==FTS5_PLAN_ROWID).  */
    pCsr->ePlan = (pRowidEq ? FTS5_PLAN_ROWID : FTS5_PLAN_SCAN);
    rc = sqlite3Fts5StorageStmt(
        pTab->pStorage, fts5StmtType(pCsr), &pCsr->pStmt, &pTab->p.base.zErrMsg
    );
    if( rc==SQLITE_OK ){
      if( pRowidEq!=0 ){
        assert( pCsr->ePlan==FTS5_PLAN_ROWID );
        sqlite3_bind_value(pCsr->pStmt, 1, pRowidEq);
      }else{
        sqlite3_bind_int64(pCsr->pStmt, 1, pCsr->iFirstRowid);
        sqlite3_bind_int64(pCsr->pStmt, 2, pCsr->iLastRowid);
      }
      rc = fts5NextMethod(pCursor);
    }
231448
231449
231450
231451
231452
231453
231454
231455
231456
231457
231458
231459
231460
231461
231462
static void fts5SourceIdFunc(
  sqlite3_context *pCtx,          /* Function call context */
  int nArg,                       /* Number of args */
  sqlite3_value **apUnused        /* Function arguments */
){
  assert( nArg==0 );
  UNUSED_PARAM2(nArg, apUnused);
  sqlite3_result_text(pCtx, "fts5: 2021-10-04 11:10:15 8b24c177061c38361588f419eda9b7943b72a0c6b2855b6f39272451b8a1b813", -1, SQLITE_TRANSIENT);
}

/*
** Return true if zName is the extension on one of the shadow tables used
** by this module.
*/
static int fts5ShadowName(const char *zName){







|







233130
233131
233132
233133
233134
233135
233136
233137
233138
233139
233140
233141
233142
233143
233144
static void fts5SourceIdFunc(
  sqlite3_context *pCtx,          /* Function call context */
  int nArg,                       /* Number of args */
  sqlite3_value **apUnused        /* Function arguments */
){
  assert( nArg==0 );
  UNUSED_PARAM2(nArg, apUnused);
  sqlite3_result_text(pCtx, "fts5: 2021-12-09 20:06:18 633bfeeea2bccdd44126acf3f61ecca163c9d933bdc787a2c18a697dc9406882", -1, SQLITE_TRANSIENT);
}

/*
** Return true if zName is the extension on one of the shadow tables used
** by this module.
*/
static int fts5ShadowName(const char *zName){
231999
232000
232001
232002
232003
232004
232005


232006
232007
232008
232009
232010
232011


232012
232013
232014
232015
232016
232017
232018
  ctx.pStorage = p;
  ctx.iCol = -1;
  rc = sqlite3Fts5IndexBeginWrite(p->pIndex, 1, iDel);
  for(iCol=1; rc==SQLITE_OK && iCol<=pConfig->nCol; iCol++){
    if( pConfig->abUnindexed[iCol-1]==0 ){
      const char *zText;
      int nText;


      if( pSeek ){
        zText = (const char*)sqlite3_column_text(pSeek, iCol);
        nText = sqlite3_column_bytes(pSeek, iCol);
      }else{
        zText = (const char*)sqlite3_value_text(apVal[iCol-1]);
        nText = sqlite3_value_bytes(apVal[iCol-1]);


      }
      ctx.szCol = 0;
      rc = sqlite3Fts5Tokenize(pConfig, FTS5_TOKENIZE_DOCUMENT,
          zText, nText, (void*)&ctx, fts5StorageInsertCallback
      );
      p->aTotalSize[iCol-1] -= (i64)ctx.szCol;
      if( p->aTotalSize[iCol-1]<0 ){







>
>



|


>
>







233681
233682
233683
233684
233685
233686
233687
233688
233689
233690
233691
233692
233693
233694
233695
233696
233697
233698
233699
233700
233701
233702
233703
233704
  ctx.pStorage = p;
  ctx.iCol = -1;
  rc = sqlite3Fts5IndexBeginWrite(p->pIndex, 1, iDel);
  for(iCol=1; rc==SQLITE_OK && iCol<=pConfig->nCol; iCol++){
    if( pConfig->abUnindexed[iCol-1]==0 ){
      const char *zText;
      int nText;
      assert( pSeek==0 || apVal==0 );
      assert( pSeek!=0 || apVal!=0 );
      if( pSeek ){
        zText = (const char*)sqlite3_column_text(pSeek, iCol);
        nText = sqlite3_column_bytes(pSeek, iCol);
      }else if( ALWAYS(apVal) ){
        zText = (const char*)sqlite3_value_text(apVal[iCol-1]);
        nText = sqlite3_value_bytes(apVal[iCol-1]);
      }else{
        continue;
      }
      ctx.szCol = 0;
      rc = sqlite3Fts5Tokenize(pConfig, FTS5_TOKENIZE_DOCUMENT,
          zText, nText, (void*)&ctx, fts5StorageInsertCallback
      );
      p->aTotalSize[iCol-1] -= (i64)ctx.szCol;
      if( p->aTotalSize[iCol-1]<0 ){
232640
232641
232642
232643
232644
232645
232646
232647
232648

232649
232650
232651
232652
232653
232654
232655
232656
232657
232658
232659
232660


232661
232662
232663
232664
232665
232666
232667
static int sqlite3Fts5StorageDocsize(Fts5Storage *p, i64 iRowid, int *aCol){
  int nCol = p->pConfig->nCol;    /* Number of user columns in table */
  sqlite3_stmt *pLookup = 0;      /* Statement to query %_docsize */
  int rc;                         /* Return Code */

  assert( p->pConfig->bColumnsize );
  rc = fts5StorageGetStmt(p, FTS5_STMT_LOOKUP_DOCSIZE, &pLookup, 0);
  if( rc==SQLITE_OK ){
    int bCorrupt = 1;

    sqlite3_bind_int64(pLookup, 1, iRowid);
    if( SQLITE_ROW==sqlite3_step(pLookup) ){
      const u8 *aBlob = sqlite3_column_blob(pLookup, 0);
      int nBlob = sqlite3_column_bytes(pLookup, 0);
      if( 0==fts5StorageDecodeSizeArray(aCol, nCol, aBlob, nBlob) ){
        bCorrupt = 0;
      }
    }
    rc = sqlite3_reset(pLookup);
    if( bCorrupt && rc==SQLITE_OK ){
      rc = FTS5_CORRUPT;
    }


  }

  return rc;
}

static int sqlite3Fts5StorageSize(Fts5Storage *p, int iCol, i64 *pnToken){
  int rc = fts5StorageLoadTotals(p, 0);







|

>












>
>







234326
234327
234328
234329
234330
234331
234332
234333
234334
234335
234336
234337
234338
234339
234340
234341
234342
234343
234344
234345
234346
234347
234348
234349
234350
234351
234352
234353
234354
234355
234356
static int sqlite3Fts5StorageDocsize(Fts5Storage *p, i64 iRowid, int *aCol){
  int nCol = p->pConfig->nCol;    /* Number of user columns in table */
  sqlite3_stmt *pLookup = 0;      /* Statement to query %_docsize */
  int rc;                         /* Return Code */

  assert( p->pConfig->bColumnsize );
  rc = fts5StorageGetStmt(p, FTS5_STMT_LOOKUP_DOCSIZE, &pLookup, 0);
  if( pLookup ){
    int bCorrupt = 1;
    assert( rc==SQLITE_OK );
    sqlite3_bind_int64(pLookup, 1, iRowid);
    if( SQLITE_ROW==sqlite3_step(pLookup) ){
      const u8 *aBlob = sqlite3_column_blob(pLookup, 0);
      int nBlob = sqlite3_column_bytes(pLookup, 0);
      if( 0==fts5StorageDecodeSizeArray(aCol, nCol, aBlob, nBlob) ){
        bCorrupt = 0;
      }
    }
    rc = sqlite3_reset(pLookup);
    if( bCorrupt && rc==SQLITE_OK ){
      rc = FTS5_CORRUPT;
    }
  }else{
    assert( rc!=SQLITE_OK );
  }

  return rc;
}

static int sqlite3Fts5StorageSize(Fts5Storage *p, int iCol, i64 *pnToken){
  int rc = fts5StorageLoadTotals(p, 0);
235658
235659
235660
235661
235662
235663
235664
235665
235666
235667
235668
235669
235670
235671
235672
      }
    }else{
      rc = sqlite3Fts5FlushToDisk(pFts5);
    }
  }

  if( rc==SQLITE_OK ){
    int nByte = pFts5->pConfig->nCol * sizeof(i64)*2 + sizeof(Fts5VocabCursor);
    pCsr = (Fts5VocabCursor*)sqlite3Fts5MallocZero(&rc, nByte);
  }

  if( pCsr ){
    pCsr->pFts5 = pFts5;
    pCsr->pStmt = pStmt;
    pCsr->aCnt = (i64*)&pCsr[1];







|







237347
237348
237349
237350
237351
237352
237353
237354
237355
237356
237357
237358
237359
237360
237361
      }
    }else{
      rc = sqlite3Fts5FlushToDisk(pFts5);
    }
  }

  if( rc==SQLITE_OK ){
    i64 nByte = pFts5->pConfig->nCol * sizeof(i64)*2 + sizeof(Fts5VocabCursor);
    pCsr = (Fts5VocabCursor*)sqlite3Fts5MallocZero(&rc, nByte);
  }

  if( pCsr ){
    pCsr->pFts5 = pFts5;
    pCsr->pStmt = pStmt;
    pCsr->aCnt = (i64*)&pCsr[1];
Changes to src/sqlite3.h.
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
** been edited in any way since it was last checked in, then the last
** four hexadecimal digits of the hash may be modified.
**
** See also: [sqlite3_libversion()],
** [sqlite3_libversion_number()], [sqlite3_sourceid()],
** [sqlite_version()] and [sqlite_source_id()].
*/
#define SQLITE_VERSION        "3.37.0"
#define SQLITE_VERSION_NUMBER 3037000
#define SQLITE_SOURCE_ID      "2021-10-04 11:10:15 8b24c177061c38361588f419eda9b7943b72a0c6b2855b6f39272451b8a1b813"

/*
** CAPI3REF: Run-Time Library Version Numbers
** KEYWORDS: sqlite3_version sqlite3_sourceid
**
** These interfaces provide the same information as the [SQLITE_VERSION],
** [SQLITE_VERSION_NUMBER], and [SQLITE_SOURCE_ID] C preprocessor macros







|
|
|







142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
** been edited in any way since it was last checked in, then the last
** four hexadecimal digits of the hash may be modified.
**
** See also: [sqlite3_libversion()],
** [sqlite3_libversion_number()], [sqlite3_sourceid()],
** [sqlite_version()] and [sqlite_source_id()].
*/
#define SQLITE_VERSION        "3.38.0"
#define SQLITE_VERSION_NUMBER 3038000
#define SQLITE_SOURCE_ID      "2021-12-09 20:06:18 633bfeeea2bccdd44126acf3f61ecca163c9d933bdc787a2c18a697dc9406882"

/*
** CAPI3REF: Run-Time Library Version Numbers
** KEYWORDS: sqlite3_version sqlite3_sourceid
**
** These interfaces provide the same information as the [SQLITE_VERSION],
** [SQLITE_VERSION_NUMBER], and [SQLITE_SOURCE_ID] C preprocessor macros
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
#define SQLITE_BUSY_TIMEOUT            (SQLITE_BUSY   |  (3<<8))
#define SQLITE_CANTOPEN_NOTEMPDIR      (SQLITE_CANTOPEN | (1<<8))
#define SQLITE_CANTOPEN_ISDIR          (SQLITE_CANTOPEN | (2<<8))
#define SQLITE_CANTOPEN_FULLPATH       (SQLITE_CANTOPEN | (3<<8))
#define SQLITE_CANTOPEN_CONVPATH       (SQLITE_CANTOPEN | (4<<8))
#define SQLITE_CANTOPEN_DIRTYWAL       (SQLITE_CANTOPEN | (5<<8)) /* Not Used */
#define SQLITE_CANTOPEN_SYMLINK        (SQLITE_CANTOPEN | (6<<8))
#define SQLITE_CANTOPEN_EXISTS         (SQLITE_CANTOPEN | (7<<8))
#define SQLITE_CORRUPT_VTAB            (SQLITE_CORRUPT | (1<<8))
#define SQLITE_CORRUPT_SEQUENCE        (SQLITE_CORRUPT | (2<<8))
#define SQLITE_CORRUPT_INDEX           (SQLITE_CORRUPT | (3<<8))
#define SQLITE_READONLY_RECOVERY       (SQLITE_READONLY | (1<<8))
#define SQLITE_READONLY_CANTLOCK       (SQLITE_READONLY | (2<<8))
#define SQLITE_READONLY_ROLLBACK       (SQLITE_READONLY | (3<<8))
#define SQLITE_READONLY_DBMOVED        (SQLITE_READONLY | (4<<8))







<







535
536
537
538
539
540
541

542
543
544
545
546
547
548
#define SQLITE_BUSY_TIMEOUT            (SQLITE_BUSY   |  (3<<8))
#define SQLITE_CANTOPEN_NOTEMPDIR      (SQLITE_CANTOPEN | (1<<8))
#define SQLITE_CANTOPEN_ISDIR          (SQLITE_CANTOPEN | (2<<8))
#define SQLITE_CANTOPEN_FULLPATH       (SQLITE_CANTOPEN | (3<<8))
#define SQLITE_CANTOPEN_CONVPATH       (SQLITE_CANTOPEN | (4<<8))
#define SQLITE_CANTOPEN_DIRTYWAL       (SQLITE_CANTOPEN | (5<<8)) /* Not Used */
#define SQLITE_CANTOPEN_SYMLINK        (SQLITE_CANTOPEN | (6<<8))

#define SQLITE_CORRUPT_VTAB            (SQLITE_CORRUPT | (1<<8))
#define SQLITE_CORRUPT_SEQUENCE        (SQLITE_CORRUPT | (2<<8))
#define SQLITE_CORRUPT_INDEX           (SQLITE_CORRUPT | (3<<8))
#define SQLITE_READONLY_RECOVERY       (SQLITE_READONLY | (1<<8))
#define SQLITE_READONLY_CANTLOCK       (SQLITE_READONLY | (2<<8))
#define SQLITE_READONLY_ROLLBACK       (SQLITE_READONLY | (3<<8))
#define SQLITE_READONLY_DBMOVED        (SQLITE_READONLY | (4<<8))
571
572
573
574
575
576
577













578
579
580
581
582
583
584

/*
** CAPI3REF: Flags For File Open Operations
**
** These bit values are intended for use in the
** 3rd parameter to the [sqlite3_open_v2()] interface and
** in the 4th parameter to the [sqlite3_vfs.xOpen] method.













*/
#define SQLITE_OPEN_READONLY         0x00000001  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_READWRITE        0x00000002  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_CREATE           0x00000004  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_DELETEONCLOSE    0x00000008  /* VFS only */
#define SQLITE_OPEN_EXCLUSIVE        0x00000010  /* VFS only */
#define SQLITE_OPEN_AUTOPROXY        0x00000020  /* VFS only */







>
>
>
>
>
>
>
>
>
>
>
>
>







570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596

/*
** CAPI3REF: Flags For File Open Operations
**
** These bit values are intended for use in the
** 3rd parameter to the [sqlite3_open_v2()] interface and
** in the 4th parameter to the [sqlite3_vfs.xOpen] method.
**
** Only those flags marked as "Ok for sqlite3_open_v2()" may be
** used as the third argument to the [sqlite3_open_v2()] interface.
** The other flags have historically been ignored by sqlite3_open_v2(),
** though future versions of SQLite might change so that an error is
** raised if any of the disallowed bits are passed into sqlite3_open_v2().
** Applications should not depend on the historical behavior.
**
** Note in particular that passing the SQLITE_OPEN_EXCLUSIVE flag into
** [sqlite3_open_v2()] does *not* cause the underlying database file
** to be opened using O_EXCL.  Passing SQLITE_OPEN_EXCLUSIVE into
** [sqlite3_open_v2()] has historically be a no-op and might become an
** error in future versions of SQLite.
*/
#define SQLITE_OPEN_READONLY         0x00000001  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_READWRITE        0x00000002  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_CREATE           0x00000004  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_DELETEONCLOSE    0x00000008  /* VFS only */
#define SQLITE_OPEN_EXCLUSIVE        0x00000010  /* VFS only */
#define SQLITE_OPEN_AUTOPROXY        0x00000020  /* VFS only */
593
594
595
596
597
598
599

600
601
602
603
604
605
606
#define SQLITE_OPEN_SUPER_JOURNAL    0x00004000  /* VFS only */
#define SQLITE_OPEN_NOMUTEX          0x00008000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_FULLMUTEX        0x00010000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_SHAREDCACHE      0x00020000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_PRIVATECACHE     0x00040000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_WAL              0x00080000  /* VFS only */
#define SQLITE_OPEN_NOFOLLOW         0x01000000  /* Ok for sqlite3_open_v2() */


/* Reserved:                         0x00F00000 */
/* Legacy compatibility: */
#define SQLITE_OPEN_MASTER_JOURNAL   0x00004000  /* VFS only */


/*







>







605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
#define SQLITE_OPEN_SUPER_JOURNAL    0x00004000  /* VFS only */
#define SQLITE_OPEN_NOMUTEX          0x00008000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_FULLMUTEX        0x00010000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_SHAREDCACHE      0x00020000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_PRIVATECACHE     0x00040000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_WAL              0x00080000  /* VFS only */
#define SQLITE_OPEN_NOFOLLOW         0x01000000  /* Ok for sqlite3_open_v2() */
#define SQLITE_OPEN_EXRESCODE        0x02000000  /* Extended result codes */

/* Reserved:                         0x00F00000 */
/* Legacy compatibility: */
#define SQLITE_OPEN_MASTER_JOURNAL   0x00004000  /* VFS only */


/*
3412
3413
3414
3415
3416
3417
3418








3419
3420
3421
3422
3423
3424
3425
3426
3427
3428
3429
3430
3431
3432
3433








3434
3435
3436
3437
3438
3439
3440
** the default shared cache setting provided by
** [sqlite3_enable_shared_cache()].)^
**
** ^(<dt>[SQLITE_OPEN_PRIVATECACHE]</dt>
** <dd>The database is opened [shared cache] disabled, overriding
** the default shared cache setting provided by
** [sqlite3_enable_shared_cache()].)^








**
** [[OPEN_NOFOLLOW]] ^(<dt>[SQLITE_OPEN_NOFOLLOW]</dt>
** <dd>The database filename is not allowed to be a symbolic link</dd>
**
** [[OPEN_EXCLUSIVE]] ^(<dt>[SQLITE_OPEN_EXCLUSIVE]</dt>
** <dd>This flag causes the open to fail if the database file already
** exists.  The open will only be success if this flag is used in combination
** with the SQLITE_OPEN_CREATE and SQLITE_OPEN_READWRITE flags and if
** the file does not previously exist.</dd>
** </dl>)^
**
** If the 3rd parameter to sqlite3_open_v2() is not one of the
** required combinations shown above optionally combined with other
** [SQLITE_OPEN_READONLY | SQLITE_OPEN_* bits]
** then the behavior is undefined.








**
** ^The fourth parameter to sqlite3_open_v2() is the name of the
** [sqlite3_vfs] object that defines the operating system interface that
** the new database connection should use.  ^If the fourth parameter is
** a NULL pointer then the default [sqlite3_vfs] object is used.
**
** ^If the filename is ":memory:", then a private, temporary in-memory database







>
>
>
>
>
>
>
>



<
<
<
<
<
<





|
>
>
>
>
>
>
>
>







3425
3426
3427
3428
3429
3430
3431
3432
3433
3434
3435
3436
3437
3438
3439
3440
3441
3442






3443
3444
3445
3446
3447
3448
3449
3450
3451
3452
3453
3454
3455
3456
3457
3458
3459
3460
3461
3462
3463
** the default shared cache setting provided by
** [sqlite3_enable_shared_cache()].)^
**
** ^(<dt>[SQLITE_OPEN_PRIVATECACHE]</dt>
** <dd>The database is opened [shared cache] disabled, overriding
** the default shared cache setting provided by
** [sqlite3_enable_shared_cache()].)^
**
** [[OPEN_EXRESCODE]] ^(<dt>[SQLITE_OPEN_EXRESCODE]</dt>
** <dd>The database connection comes up in "extended result code mode".
** In other words, the database behaves has if
** [sqlite3_extended_result_codes(db,1)] where called on the database
** connection as soon as the connection is created. In addition to setting
** the extended result code mode, this flag also causes [sqlite3_open_v2()]
** to return an extended result code.</dd>
**
** [[OPEN_NOFOLLOW]] ^(<dt>[SQLITE_OPEN_NOFOLLOW]</dt>
** <dd>The database filename is not allowed to be a symbolic link</dd>






** </dl>)^
**
** If the 3rd parameter to sqlite3_open_v2() is not one of the
** required combinations shown above optionally combined with other
** [SQLITE_OPEN_READONLY | SQLITE_OPEN_* bits]
** then the behavior is undefined.  Historic versions of SQLite
** have silently ignored surplus bits in the flags parameter to
** sqlite3_open_v2(), however that behavior might not be carried through
** into future versions of SQLite and so applications should not rely
** upon it.  Note in particular that the SQLITE_OPEN_EXCLUSIVE flag is a no-op
** for sqlite3_open_v2().  The SQLITE_OPEN_EXCLUSIVE does *not* cause
** the open to fail if the database already exists.  The SQLITE_OPEN_EXCLUSIVE
** flag is intended for use by the [sqlite3_vfs|VFS interface] only, and not
** by sqlite3_open_v2().
**
** ^The fourth parameter to sqlite3_open_v2() is the name of the
** [sqlite3_vfs] object that defines the operating system interface that
** the new database connection should use.  ^If the fourth parameter is
** a NULL pointer then the default [sqlite3_vfs] object is used.
**
** ^If the filename is ":memory:", then a private, temporary in-memory database
6387
6388
6389
6390
6391
6392
6393


































































6394
6395
6396
6397
6398
6399
6400
** ^The rollback callback is not invoked if a transaction is
** automatically rolled back because the database connection is closed.
**
** See also the [sqlite3_update_hook()] interface.
*/
SQLITE_API void *sqlite3_commit_hook(sqlite3*, int(*)(void*), void*);
SQLITE_API void *sqlite3_rollback_hook(sqlite3*, void(*)(void *), void*);



































































/*
** CAPI3REF: Data Change Notification Callbacks
** METHOD: sqlite3
**
** ^The sqlite3_update_hook() interface registers a callback function
** with the [database connection] identified by the first argument







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







6410
6411
6412
6413
6414
6415
6416
6417
6418
6419
6420
6421
6422
6423
6424
6425
6426
6427
6428
6429
6430
6431
6432
6433
6434
6435
6436
6437
6438
6439
6440
6441
6442
6443
6444
6445
6446
6447
6448
6449
6450
6451
6452
6453
6454
6455
6456
6457
6458
6459
6460
6461
6462
6463
6464
6465
6466
6467
6468
6469
6470
6471
6472
6473
6474
6475
6476
6477
6478
6479
6480
6481
6482
6483
6484
6485
6486
6487
6488
6489
** ^The rollback callback is not invoked if a transaction is
** automatically rolled back because the database connection is closed.
**
** See also the [sqlite3_update_hook()] interface.
*/
SQLITE_API void *sqlite3_commit_hook(sqlite3*, int(*)(void*), void*);
SQLITE_API void *sqlite3_rollback_hook(sqlite3*, void(*)(void *), void*);

/*
** CAPI3REF: Autovacuum Compaction Amount Callback
** METHOD: sqlite3
**
** ^The sqlite3_autovacuum_pages(D,C,P,X) interface registers a callback
** function C that is invoked prior to each autovacuum of the database
** file.  ^The callback is passed a copy of the generic data pointer (P),
** the schema-name of the attached database that is being autovacuumed,
** the the size of the database file in pages, the number of free pages,
** and the number of bytes per page, respectively.  The callback should
** return the number of free pages that should be removed by the
** autovacuum.  ^If the callback returns zero, then no autovacuum happens.
** ^If the value returned is greater than or equal to the number of
** free pages, then a complete autovacuum happens.
**
** <p>^If there are multiple ATTACH-ed database files that are being
** modified as part of a transaction commit, then the autovacuum pages
** callback is invoked separately for each file.
**
** <p><b>The callback is not reentrant.</b> The callback function should
** not attempt to invoke any other SQLite interface.  If it does, bad
** things may happen, including segmentation faults and corrupt database
** files.  The callback function should be a simple function that
** does some arithmetic on its input parameters and returns a result.
**
** ^The X parameter to sqlite3_autovacuum_pages(D,C,P,X) is an optional
** destructor for the P parameter.  ^If X is not NULL, then X(P) is
** invoked whenever the database connection closes or when the callback
** is overwritten by another invocation of sqlite3_autovacuum_pages().
**
** <p>^There is only one autovacuum pages callback per database connection.
** ^Each call to the sqlite3_autovacuum_pages() interface overrides all
** previous invocations for that database connection.  ^If the callback
** argument (C) to sqlite3_autovacuum_pages(D,C,P,X) is a NULL pointer,
** then the autovacuum steps callback is cancelled.  The return value
** from sqlite3_autovacuum_pages() is normally SQLITE_OK, but might
** be some other error code if something goes wrong.  The current
** implementation will only return SQLITE_OK or SQLITE_MISUSE, but other
** return codes might be added in future releases.
**
** <p>If no autovacuum pages callback is specified (the usual case) or
** a NULL pointer is provided for the callback,
** then the default behavior is to vacuum all free pages.  So, in other
** words, the default behavior is the same as if the callback function
** were something like this:
**
** <blockquote><pre>
** &nbsp;   unsigned int demonstration_autovac_pages_callback(
** &nbsp;     void *pClientData,
** &nbsp;     const char *zSchema,
** &nbsp;     unsigned int nDbPage,
** &nbsp;     unsigned int nFreePage,
** &nbsp;     unsigned int nBytePerPage
** &nbsp;   ){
** &nbsp;     return nFreePage;
** &nbsp;   }
** </pre></blockquote>
*/
SQLITE_API int sqlite3_autovacuum_pages(
  sqlite3 *db,
  unsigned int(*)(void*,const char*,unsigned int,unsigned int,unsigned int),
  void*,
  void(*)(void*)
);


/*
** CAPI3REF: Data Change Notification Callbacks
** METHOD: sqlite3
**
** ^The sqlite3_update_hook() interface registers a callback function
** with the [database connection] identified by the first argument
7851
7852
7853
7854
7855
7856
7857

7858
7859
7860
7861
7862
7863
7864
7865
#define SQLITE_TESTCTRL_PARSER_COVERAGE         26
#define SQLITE_TESTCTRL_RESULT_INTREAL          27
#define SQLITE_TESTCTRL_PRNG_SEED               28
#define SQLITE_TESTCTRL_EXTRA_SCHEMA_CHECKS     29
#define SQLITE_TESTCTRL_SEEK_COUNT              30
#define SQLITE_TESTCTRL_TRACEFLAGS              31
#define SQLITE_TESTCTRL_TUNE                    32

#define SQLITE_TESTCTRL_LAST                    32  /* Largest TESTCTRL */

/*
** CAPI3REF: SQL Keyword Checking
**
** These routines provide access to the set of SQL language keywords
** recognized by SQLite.  Applications can uses these routines to determine
** whether or not a specific identifier needs to be escaped (for example,







>
|







7940
7941
7942
7943
7944
7945
7946
7947
7948
7949
7950
7951
7952
7953
7954
7955
#define SQLITE_TESTCTRL_PARSER_COVERAGE         26
#define SQLITE_TESTCTRL_RESULT_INTREAL          27
#define SQLITE_TESTCTRL_PRNG_SEED               28
#define SQLITE_TESTCTRL_EXTRA_SCHEMA_CHECKS     29
#define SQLITE_TESTCTRL_SEEK_COUNT              30
#define SQLITE_TESTCTRL_TRACEFLAGS              31
#define SQLITE_TESTCTRL_TUNE                    32
#define SQLITE_TESTCTRL_LOGEST                  33
#define SQLITE_TESTCTRL_LAST                    33  /* Largest TESTCTRL */

/*
** CAPI3REF: SQL Keyword Checking
**
** These routines provide access to the set of SQL language keywords
** recognized by SQLite.  Applications can uses these routines to determine
** whether or not a specific identifier needs to be escaped (for example,
8373
8374
8375
8376
8377
8378
8379










8380
8381
8382
8383
8384
8385
8386
8387
8388
8389
8390
8391
8392
8393
8394


8395
8396
8397
8398
8399
8400
8401
**
** [[SQLITE_STMTSTATUS_RUN]] <dt>SQLITE_STMTSTATUS_RUN</dt>
** <dd>^This is the number of times that the prepared statement has
** been run.  A single "run" for the purposes of this counter is one
** or more calls to [sqlite3_step()] followed by a call to [sqlite3_reset()].
** The counter is incremented on the first [sqlite3_step()] call of each
** cycle.










**
** [[SQLITE_STMTSTATUS_MEMUSED]] <dt>SQLITE_STMTSTATUS_MEMUSED</dt>
** <dd>^This is the approximate number of bytes of heap memory
** used to store the prepared statement.  ^This value is not actually
** a counter, and so the resetFlg parameter to sqlite3_stmt_status()
** is ignored when the opcode is SQLITE_STMTSTATUS_MEMUSED.
** </dd>
** </dl>
*/
#define SQLITE_STMTSTATUS_FULLSCAN_STEP     1
#define SQLITE_STMTSTATUS_SORT              2
#define SQLITE_STMTSTATUS_AUTOINDEX         3
#define SQLITE_STMTSTATUS_VM_STEP           4
#define SQLITE_STMTSTATUS_REPREPARE         5
#define SQLITE_STMTSTATUS_RUN               6


#define SQLITE_STMTSTATUS_MEMUSED           99

/*
** CAPI3REF: Custom Page Cache Object
**
** The sqlite3_pcache type is opaque.  It is implemented by
** the pluggable module.  The SQLite core has no knowledge of







>
>
>
>
>
>
>
>
>
>















>
>







8463
8464
8465
8466
8467
8468
8469
8470
8471
8472
8473
8474
8475
8476
8477
8478
8479
8480
8481
8482
8483
8484
8485
8486
8487
8488
8489
8490
8491
8492
8493
8494
8495
8496
8497
8498
8499
8500
8501
8502
8503
**
** [[SQLITE_STMTSTATUS_RUN]] <dt>SQLITE_STMTSTATUS_RUN</dt>
** <dd>^This is the number of times that the prepared statement has
** been run.  A single "run" for the purposes of this counter is one
** or more calls to [sqlite3_step()] followed by a call to [sqlite3_reset()].
** The counter is incremented on the first [sqlite3_step()] call of each
** cycle.
**
** [[SQLITE_STMTSTATUS_FILTER_MISS]]
** [[SQLITE_STMTSTATUS_FILTER HIT]]
** <dt>SQLITE_STMTSTATUS_FILTER_HIT<br>
** SQLITE_STMTSTATUS_FILTER_MISS</dt>
** <dd>^SQLITE_STMTSTATUS_FILTER_HIT is the number of times that a join
** step was bypassed because a Bloom filter returned not-found.  The
** corresponding SQLITE_STMTSTATUS_FILTER_MISS value is the number of
** times that the Bloom filter returned a find, and thus the join step
** had to be processed as normal.
**
** [[SQLITE_STMTSTATUS_MEMUSED]] <dt>SQLITE_STMTSTATUS_MEMUSED</dt>
** <dd>^This is the approximate number of bytes of heap memory
** used to store the prepared statement.  ^This value is not actually
** a counter, and so the resetFlg parameter to sqlite3_stmt_status()
** is ignored when the opcode is SQLITE_STMTSTATUS_MEMUSED.
** </dd>
** </dl>
*/
#define SQLITE_STMTSTATUS_FULLSCAN_STEP     1
#define SQLITE_STMTSTATUS_SORT              2
#define SQLITE_STMTSTATUS_AUTOINDEX         3
#define SQLITE_STMTSTATUS_VM_STEP           4
#define SQLITE_STMTSTATUS_REPREPARE         5
#define SQLITE_STMTSTATUS_RUN               6
#define SQLITE_STMTSTATUS_FILTER_MISS       7
#define SQLITE_STMTSTATUS_FILTER_HIT        8
#define SQLITE_STMTSTATUS_MEMUSED           99

/*
** CAPI3REF: Custom Page Cache Object
**
** The sqlite3_pcache type is opaque.  It is implemented by
** the pluggable module.  The SQLite core has no knowledge of
Changes to src/stash.c.
306
307
308
309
310
311
312
313


314
315
316
317
318
319
320
321
** Apply a stash to the current checkout.
*/
static void stash_apply(int stashid, int nConflict){
  int vid;
  Stmt q;
  db_prepare(&q,
     "SELECT blob.rid, isRemoved, isExec, isLink, origname, newname, delta"
     "  FROM stashfile, blob WHERE stashid=%d AND blob.uuid=stashfile.hash",


     stashid
  );
  vid = db_lget_int("checkout",0);
  db_multi_exec("CREATE TEMP TABLE sfile(pathname TEXT PRIMARY KEY %s)",
                filename_collation());
  while( db_step(&q)==SQLITE_ROW ){
    int rid = db_column_int(&q, 0);
    int isRemoved = db_column_int(&q, 1);







|
>
>
|







306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
** Apply a stash to the current checkout.
*/
static void stash_apply(int stashid, int nConflict){
  int vid;
  Stmt q;
  db_prepare(&q,
     "SELECT blob.rid, isRemoved, isExec, isLink, origname, newname, delta"
     "  FROM stashfile, blob WHERE stashid=%d AND blob.uuid=stashfile.hash"
     " UNION ALL SELECT 0, isRemoved, isExec, isLink, origname, newname, delta"
     "  FROM stashfile WHERE stashid=%d AND stashfile.hash IS NULL",
     stashid, stashid
  );
  vid = db_lget_int("checkout",0);
  db_multi_exec("CREATE TEMP TABLE sfile(pathname TEXT PRIMARY KEY %s)",
                filename_collation());
  while( db_step(&q)==SQLITE_ROW ){
    int rid = db_column_int(&q, 0);
    int isRemoved = db_column_int(&q, 1);
410
411
412
413
414
415
416
417


418
419
420
421
422
423
424
425
  Stmt q;
  Blob empty;
  int bWebpage = (pCfg->diffFlags & (DIFF_WEBPAGE|DIFF_JSON|DIFF_TCL))!=0;
  blob_zero(&empty);
  diff_begin(pCfg);
  db_prepare(&q,
     "SELECT blob.rid, isRemoved, isExec, isLink, origname, newname, delta"
     "  FROM stashfile, blob WHERE stashid=%d AND blob.uuid=stashfile.hash",


     stashid
  );
  while( db_step(&q)==SQLITE_ROW ){
    int rid = db_column_int(&q, 0);
    int isRemoved = db_column_int(&q, 1);
    int isLink = db_column_int(&q, 3);
    const char *zOrig = db_column_text(&q, 4);
    const char *zNew = db_column_text(&q, 5);







|
>
>
|







412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
  Stmt q;
  Blob empty;
  int bWebpage = (pCfg->diffFlags & (DIFF_WEBPAGE|DIFF_JSON|DIFF_TCL))!=0;
  blob_zero(&empty);
  diff_begin(pCfg);
  db_prepare(&q,
     "SELECT blob.rid, isRemoved, isExec, isLink, origname, newname, delta"
     "  FROM stashfile, blob WHERE stashid=%d AND blob.uuid=stashfile.hash"
     " UNION ALL SELECT 0, isRemoved, isExec, isLink, origname, newname, delta"
     "  FROM stashfile WHERE stashid=%d AND stashfile.hash IS NULL",
     stashid, stashid
  );
  while( db_step(&q)==SQLITE_ROW ){
    int rid = db_column_int(&q, 0);
    int isRemoved = db_column_int(&q, 1);
    int isLink = db_column_int(&q, 3);
    const char *zOrig = db_column_text(&q, 4);
    const char *zNew = db_column_text(&q, 5);
Changes to src/stat.c.
390
391
392
393
394
395
396
397


398


399
400
401
402
403
404
405

406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
      a = t/fsize;
      fossil_print("%*s%d:%d\n", colWidth, "compression-ratio:", a, b);
    }
    n = db_int(0, "SELECT COUNT(*) FROM event e WHERE e.type='ci'");
    fossil_print("%*s%,d\n", colWidth, "check-ins:", n);
    n = db_int(0, "SELECT count(*) FROM filename /*scan*/");
    fossil_print("%*s%,d across all branches\n", colWidth, "files:", n);
    n = db_int(0, "SELECT count(*) FROM tag  /*scan*/"


                  " WHERE tagname GLOB 'wiki-*'");


    m = db_int(0, "SELECT COUNT(*) FROM event WHERE type='w'");
    fossil_print("%*s%,d (%,d changes)\n", colWidth, "wiki-pages:", n, m);
    n = db_int(0, "SELECT count(*) FROM tag  /*scan*/"
                  " WHERE tagname GLOB 'tkt-*'");
    m = db_int(0, "SELECT COUNT(*) FROM event WHERE type='t'");
    fossil_print("%*s%,d (%,d changes)\n", colWidth, "tickets:", n, m);
    n = db_int(0, "SELECT COUNT(*) FROM event WHERE type='e'");

    if( db_table_exists("repository","forumpost") ){
      n = db_int(0, "SELECT count(*) FROM forumpost/*scan*/");
      if( n>0 ){
        int nThread = db_int(0, "SELECT count(*) FROM forumpost"
                                " WHERE froot=fpid");
        fossil_print("%*s%,d (on %,d threads)\n", colWidth, "forum-posts:",
                     n, nThread);
      }
    }
    fossil_print("%*s%,d\n", colWidth, "events:", n);
    n = db_int(0, "SELECT COUNT(*) FROM event WHERE type='g'");
    fossil_print("%*s%,d\n", colWidth, "tag-changes:", n);
    z = db_text(0, "SELECT datetime(mtime) || ' - about ' ||"
                   " CAST(julianday('now') - mtime AS INTEGER)"
                   " || ' days ago' FROM event "
                   " ORDER BY mtime DESC LIMIT 1");
    fossil_print("%*s%s\n", colWidth, "latest-change:", z);







|
>
>
|
>
>







>









<







390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419

420
421
422
423
424
425
426
      a = t/fsize;
      fossil_print("%*s%d:%d\n", colWidth, "compression-ratio:", a, b);
    }
    n = db_int(0, "SELECT COUNT(*) FROM event e WHERE e.type='ci'");
    fossil_print("%*s%,d\n", colWidth, "check-ins:", n);
    n = db_int(0, "SELECT count(*) FROM filename /*scan*/");
    fossil_print("%*s%,d across all branches\n", colWidth, "files:", n);
    n = db_int(0, "SELECT count(*) FROM ("
               "SELECT DISTINCT substr(tagname,6) "
               "FROM tag JOIN tagxref USING('tagid')"
               " WHERE tagname GLOB 'wiki-*'"
               " AND TYPEOF(tagxref.value+0)='integer'"
               ")");
    m = db_int(0, "SELECT COUNT(*) FROM event WHERE type='w'");
    fossil_print("%*s%,d (%,d changes)\n", colWidth, "wiki-pages:", n, m);
    n = db_int(0, "SELECT count(*) FROM tag  /*scan*/"
                  " WHERE tagname GLOB 'tkt-*'");
    m = db_int(0, "SELECT COUNT(*) FROM event WHERE type='t'");
    fossil_print("%*s%,d (%,d changes)\n", colWidth, "tickets:", n, m);
    n = db_int(0, "SELECT COUNT(*) FROM event WHERE type='e'");
    fossil_print("%*s%,d\n", colWidth, "events:", n);
    if( db_table_exists("repository","forumpost") ){
      n = db_int(0, "SELECT count(*) FROM forumpost/*scan*/");
      if( n>0 ){
        int nThread = db_int(0, "SELECT count(*) FROM forumpost"
                                " WHERE froot=fpid");
        fossil_print("%*s%,d (on %,d threads)\n", colWidth, "forum-posts:",
                     n, nThread);
      }
    }

    n = db_int(0, "SELECT COUNT(*) FROM event WHERE type='g'");
    fossil_print("%*s%,d\n", colWidth, "tag-changes:", n);
    z = db_text(0, "SELECT datetime(mtime) || ' - about ' ||"
                   " CAST(julianday('now') - mtime AS INTEGER)"
                   " || ' days ago' FROM event "
                   " ORDER BY mtime DESC LIMIT 1");
    fossil_print("%*s%s\n", colWidth, "latest-change:", z);
Changes to src/style.chat.css.
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62





















63
64
65
66
67
68
69
  padding: 0.25em 0.5em;
  margin-top: 0;
  min-width: 9em /*avoid unsightly "underlap" with the neighboring
                   .message-widget-tab element*/;
  white-space: normal;
}
body.chat.monospace-messages .message-widget-content,
/*body.chat.monospace-messages textarea,*/
/*body.chat.monospace-messages input[type=text],*/
body.chat.monospace-messages #chat-input-field{
  font-family: monospace;  
}
body.chat .message-widget-content > * {
  margin: 0;
  padding: 0;
}
body.chat .message-widget-content > pre {
  white-space: pre-wrap;
}
body.chat .message-widget-content > .markdown > *:first-child {
  margin-top: 0;
}
body.chat .message-widget-content > .markdown > *:last-child {
  margin-bottom: 0;
}





















/* User name and timestamp (a LEGEND-like element) */
body.chat .message-widget .message-widget-tab {
  border-radius: 0.25em 0.25em 0 0;
  margin: 0 0.25em 0em 0.15em;
  padding: 0 0.5em 0.15em 0.5em;
  cursor: pointer;
  white-space: nowrap;







<
<
|















>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







38
39
40
41
42
43
44


45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
  padding: 0.25em 0.5em;
  margin-top: 0;
  min-width: 9em /*avoid unsightly "underlap" with the neighboring
                   .message-widget-tab element*/;
  white-space: normal;
}
body.chat.monospace-messages .message-widget-content,


body.chat.monospace-messages .chat-input-field{
  font-family: monospace;  
}
body.chat .message-widget-content > * {
  margin: 0;
  padding: 0;
}
body.chat .message-widget-content > pre {
  white-space: pre-wrap;
}
body.chat .message-widget-content > .markdown > *:first-child {
  margin-top: 0;
}
body.chat .message-widget-content > .markdown > *:last-child {
  margin-bottom: 0;
}
body.chat .message-widget-content.error .buttons {
  display: flex;
  flex-direction: row;
  justify-content: space-around;
  flex-wrap: wrap;
}
body.chat .message-widget-content.error .buttons > button {
  margin: 0.25em;
}

body.chat .message-widget-content.error a {
  color: inherit;
}
body.chat .message-widget-content.error .failed-message {
  display: flex;
  flex-direction: column;
}
body.chat .message-widget-content.error .failed-message textarea {
  min-height: 5rem;
}

/* User name and timestamp (a LEGEND-like element) */
body.chat .message-widget .message-widget-tab {
  border-radius: 0.25em 0.25em 0 0;
  margin: 0 0.25em 0em 0.15em;
  padding: 0 0.5em 0.15em 0.5em;
  cursor: pointer;
  white-space: nowrap;
179
180
181
182
183
184
185
186
187
188
189


190

191
192
193
194











195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297

298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
}
body.chat:not(.chat-only-mode) #chat-input-area{
  /* Safari user reports that 2em is necessary to keep the file selection
     widget from overlapping the page footer, whereas a margin of 0 is fine
     for FF/Chrome (and 2em is a *huge* waste of space for those). */
  margin-bottom: 0;
}
#chat-input-field {
  display: inline-block/*supposed workaround for Chrome weirdness*/;
  padding: 0.2em;
  flex: 10 1 auto;


  background-color: rgba(156,156,156,0.3);

  overflow: auto;
  resize: vertical;
}
#chat-input-field:empty::before {











  content: attr(data-placeholder);
  opacity: 0.6;
}
#chat-input-field:not(:focus){
  border-width: 1px;
  border-style: solid;
  border-radius: 0.25em;
}
#chat-input-field:focus{
  /* This transparent border helps avoid the text shifting around
     when the contenteditable attribute causes a border (which we
     apparently cannot style) to be added. */
  border-width: 1px;
  border-style: solid;
  border-color: transparent;
  border-radius: 0.25em;
}
/* Widget holding the chat message input field, send button, and
   settings button. */
body.chat #chat-input-line {
  display: flex;
  flex-direction: row;
  align-items: stretch;
  flex-wrap: nowrap;
}
/*body.chat #chat-input-line:not(.compact) {
  flex-wrap: nowrap;
}*/
body.chat #chat-input-line.compact {
  /* "The problem" with wrapping, together with a contenteditable input
     field, is that the latter grows as the user types, so causes
     wrapping to happen while they type, then to unwrap as soon as the
     input field is cleared (when the message is sent). When we stay
     wrapped in compact mode, the wrapped buttons simply take up too
     much space. */
  /*flex-wrap: wrap;
  justify-content: flex-end;*/
  flex-direction: column;
  /**
     We "really do" need column orientation here because it's the
     only way to eliminate the possibility that (A) the buttons
     get truncated in very narrow windows and (B) that they keep
     stable positions.
 */
}
body.chat #chat-input-line.compact #chat-input-field {
}

body.chat #chat-buttons-wrapper {
  flex: 0 1 auto;
  display: flex;
  flex-direction: column;
  align-items: center;
  min-width: 4em;
  min-height: 1.5em;
  align-self: flex-end
  /*keep buttons stable at bottom/right even when input field
    resizes */;
}
body.chat #chat-input-line.compact #chat-buttons-wrapper {
  flex-direction: row;
  flex: 1 1 auto;
  align-self: stretch;
  justify-content: flex-end;
  /*flex-wrap: wrap;*/
  /* Wrapping would be ideal except that the edit widget
     grows in width as the user types, moving the buttons
     around */
}
body.chat #chat-buttons-wrapper > .cbutton {
  padding: 0;
  display: inline-block;
  border-width: 1px;
  border-style: solid;
  border-radius: 0.25em;
  min-width: 4ex;
  max-width: 4ex;
  min-height: 4ex;
  max-height: 4ex;
  margin: 0.125em;
  display: inline-flex;
  justify-content: center;
  align-items: center;
  cursor: pointer;
  font-size: 130%;
}
body.chat #chat-buttons-wrapper > .cbutton:hover {
  background-color: rgba(200,200,200,0.3);
}
body.chat #chat-input-line.compact #chat-buttons-wrapper > .cbutton {
  margin: 2px 0.125em 0 0.125em;
  min-width: 6ex;
  max-width: 6ex;
  min-height: 2.3ex;
  max-height: 2.3ex;
  font-size: 120%;
}
body.chat #chat-input-line.compact #chat-buttons-wrapper #chat-button-submit {
  min-width: 12ex;
}
body.chat #chat-input-line:not(.compact) #chat-input-field {
  /*border-left-style: double;
  border-left-width: 3px;

  border-right-style: double;
  border-right-width: 3px;*/
  min-height: 4rem;
  /*max-height: 50rem;*/
/*
  Problems related to max-height:

  - If we do NOT set a max-height then pasting/typing a large amount
  of text can cause this element to grow without bounds, larger than
  the window, and there's no way to navigate it sensibly.  In this
  case, manually resizing the element (desktop only - mobile doesn't
  offer that) will force it to stay at the selected size even if more
  content is added to it later.

  - If we DO set a max-height then its growth is bounded but it also
  cannot manually expanded by the user.

  The lesser of the two evils seems to be to rely on the browser
  feature that a manual resize of the element will pin its sits.
*/
}

body.chat #chat-input-line > #chat-button-settings{
  margin: 0 0 0 0.25em;
  max-width: 2em;
}
body.chat #chat-input-line > input[type=text],
body.chat #chat-input-line > textarea {
  flex: 20 1 auto;
  max-width: revert;
  min-width: 20em;
}
body.chat #chat-input-line.compact > input[type=text] {
  margin: 0 0 0.25em 0/* gap for if/when buttons wrap*/;
}
/* Widget holding the file selection control and preview */
body.chat #chat-input-file-area  {
  display: flex;
  flex-direction: row;
  margin: 0;







|
<
<

>
>
|
>



|
>
>
>
>
>
>
>
>
>
>
>



|




|










|





|


|
















|













|

















|
|










|







|


|
<
|
>
|
|

<














|



|



|
|




|







198
199
200
201
202
203
204
205


206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326

327
328
329
330
331

332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
}
body.chat:not(.chat-only-mode) #chat-input-area{
  /* Safari user reports that 2em is necessary to keep the file selection
     widget from overlapping the page footer, whereas a margin of 0 is fine
     for FF/Chrome (and 2em is a *huge* waste of space for those). */
  margin-bottom: 0;
}
.chat-input-field {


  flex: 10 1 auto;
  margin: 0;
}
#chat-input-field-x,
#chat-input-field-multi {
  overflow: auto;
  resize: vertical;
}
#chat-input-field-x {
  display: inline-block/*supposed workaround for Chrome weirdness*/;
  padding: 0.2em;
  background-color: rgba(156,156,156,0.3);
  white-space: pre-wrap;
  /* ^^^ Firefox, when pasting plain text into a contenteditable field,
     loses all newlines unless we explicitly set this. Chrome does not. */
  cursor: text;
  /* ^^^ In some browsers the cursor may not change for a contenteditable
     element until it has focus, causing potential confusion. */
}
#chat-input-field-x:empty::before {
  content: attr(data-placeholder);
  opacity: 0.6;
}
.chat-input-field:not(:focus){
  border-width: 1px;
  border-style: solid;
  border-radius: 0.25em;
}
.chat-input-field:focus{
  /* This transparent border helps avoid the text shifting around
     when the contenteditable attribute causes a border (which we
     apparently cannot style) to be added. */
  border-width: 1px;
  border-style: solid;
  border-color: transparent;
  border-radius: 0.25em;
}
/* Widget holding the chat message input field, send button, and
   settings button. */
body.chat #chat-input-line-wrapper {
  display: flex;
  flex-direction: row;
  align-items: stretch;
  flex-wrap: nowrap;
}
/*body.chat #chat-input-line-wrapper:not(.compact) {
  flex-wrap: nowrap;
}*/
body.chat #chat-input-line-wrapper.compact {
  /* "The problem" with wrapping, together with a contenteditable input
     field, is that the latter grows as the user types, so causes
     wrapping to happen while they type, then to unwrap as soon as the
     input field is cleared (when the message is sent). When we stay
     wrapped in compact mode, the wrapped buttons simply take up too
     much space. */
  /*flex-wrap: wrap;
  justify-content: flex-end;*/
  flex-direction: column;
  /**
     We "really do" need column orientation here because it's the
     only way to eliminate the possibility that (A) the buttons
     get truncated in very narrow windows and (B) that they keep
     stable positions.
 */
}
body.chat #chat-input-line-wrapper.compact #chat-input-field-x {
}

body.chat #chat-buttons-wrapper {
  flex: 0 1 auto;
  display: flex;
  flex-direction: column;
  align-items: center;
  min-width: 4em;
  min-height: 1.5em;
  align-self: flex-end
  /*keep buttons stable at bottom/right even when input field
    resizes */;
}
body.chat #chat-input-line-wrapper.compact #chat-buttons-wrapper {
  flex-direction: row;
  flex: 1 1 auto;
  align-self: stretch;
  justify-content: flex-end;
  /*flex-wrap: wrap;*/
  /* Wrapping would be ideal except that the edit widget
     grows in width as the user types, moving the buttons
     around */
}
body.chat #chat-buttons-wrapper > .cbutton {
  padding: 0;
  display: inline-block;
  border-width: 1px;
  border-style: solid;
  border-radius: 0.25em;
  min-width: 4ex;
  max-width: 4ex;
  min-height: 3ex;
  max-height: 3ex;
  margin: 0.125em;
  display: inline-flex;
  justify-content: center;
  align-items: center;
  cursor: pointer;
  font-size: 130%;
}
body.chat #chat-buttons-wrapper > .cbutton:hover {
  background-color: rgba(200,200,200,0.3);
}
body.chat #chat-input-line-wrapper.compact #chat-buttons-wrapper > .cbutton {
  margin: 2px 0.125em 0 0.125em;
  min-width: 6ex;
  max-width: 6ex;
  min-height: 2.3ex;
  max-height: 2.3ex;
  font-size: 120%;
}
body.chat #chat-input-line-wrapper.compact #chat-buttons-wrapper #chat-button-submit {
  min-width: 12ex;
}
.chat-input-field {

  font-family: inherit
}
body.chat #chat-input-line-wrapper:not(.compact) #chat-input-field-multi,
body.chat #chat-input-line-wrapper:not(.compact) #chat-input-field-x {
  min-height: 4rem;

/*
  Problems related to max-height:

  - If we do NOT set a max-height then pasting/typing a large amount
  of text can cause this element to grow without bounds, larger than
  the window, and there's no way to navigate it sensibly.  In this
  case, manually resizing the element (desktop only - mobile doesn't
  offer that) will force it to stay at the selected size even if more
  content is added to it later.

  - If we DO set a max-height then its growth is bounded but it also
  cannot manually expanded by the user.

  The lesser of the two evils seems to be to rely on the browser
  feature that a manual resize of the element will pin its size.
*/
}

body.chat #chat-input-line-wrapper > #chat-button-settings{
  margin: 0 0 0 0.25em;
  max-width: 2em;
}
body.chat #chat-input-line-wrapper > input[type=text],
body.chat #chat-input-line-wrapper > textarea {
  flex: 20 1 auto;
  max-width: revert;
  min-width: 20em;
}
body.chat #chat-input-line-wrapper.compact > input[type=text] {
  margin: 0 0 0.25em 0/* gap for if/when buttons wrap*/;
}
/* Widget holding the file selection control and preview */
body.chat #chat-input-file-area  {
  display: flex;
  flex-direction: row;
  margin: 0;
359
360
361
362
363
364
365



366
367
368
369
370
371
372
373
body.chat #chat-drop-details {
  padding: 0 1em;
  white-space: pre;
  font-family: monospace;
  margin: auto;
  flex: 0;
}




body.chat #chat-drop-details img {
  max-width: 45%;
  max-height: 45%;
}
body.chat .chat-view {
  flex: 20 1 auto
  /*ensure that these grow more than the non-.chat-view elements.







>
>
>
|







389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
body.chat #chat-drop-details {
  padding: 0 1em;
  white-space: pre;
  font-family: monospace;
  margin: auto;
  flex: 0;
}
body.chat #chat-drop-details:empty {
  padding: 0;
  margin: 0;
}
body.chat #chat-drop-details img {
  max-width: 45%;
  max-height: 45%;
}
body.chat .chat-view {
  flex: 20 1 auto
  /*ensure that these grow more than the non-.chat-view elements.
387
388
389
390
391
392
393

394
395
396
397
398
399
400


401
402








403
404
405











406

407
408















409
410

411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
}
body.chat #chat-config #chat-config-options {
  /* /chat config options go here */
  flex: 1 1 auto;
  display: flex;
  flex-direction: column;
  overflow: auto;

}
body.chat #chat-config #chat-config-options .menu-entry {
  display: flex;
  align-items: baseline;
  flex-direction: row;
  flex-wrap: nowrap;
  padding: 1em;


}
body.chat #chat-config #chat-config-options .menu-entry label[for] {








  cursor: pointer;
}
body.chat #chat-config #chat-config-options .menu-entry > *:first-child {











  min-width: 1.5rem;

}
body.chat #chat-config #chat-config-options .menu-entry span.hint {















  /* Config menu hint text */
  font-size: 80%;

  white-space: pre-wrap;
  display: inline-block;
}
body.chat #chat-config #chat-config-options .menu-entry:first-child {
}
body.chat #chat-config #chat-config-options .menu-entry div.label-wrapper {
  display: flex;
  flex-direction: column;
  align-self: baseline;
  margin-left: 1em;
}
body.chat #chat-config #chat-config-options .menu-entry select {
}
body.chat #chat-preview #chat-preview-content {
  overflow: auto;
  flex: 1 1 auto;
  padding: 0.5em;







>



|
|


>
>

|
>
>
>
>
>
>
>
>
|

|
>
>
>
>
>
>
>
>
>
>
>

>

|
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>

|
>


<
<
<
<
|
<
<
<







420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484




485



486
487
488
489
490
491
492
}
body.chat #chat-config #chat-config-options {
  /* /chat config options go here */
  flex: 1 1 auto;
  display: flex;
  flex-direction: column;
  overflow: auto;
  align-items: stretch;
}
body.chat #chat-config #chat-config-options .menu-entry {
  display: flex;
  align-items: center;
  flex-direction: row-reverse;
  flex-wrap: nowrap;
  padding: 1em;
  flex: 1 1 auto;
  align-self: stretch;
}
body.chat #chat-config #chat-config-options .menu-entry.parent{
  border-radius: 1em 1em 0 1em;
  margin-top: 1em;
}
body.chat #chat-config #chat-config-options .menu-entry.child {
  /*padding-left: 2.5em;*/
  margin-left: 2em;
}
body.chat #chat-config #chat-config-options .menu-entry:nth-of-type(even){
  background-color: rgba(175,175,175,0.15);
}
body.chat #chat-config #chat-config-options .menu-entry:nth-of-type(odd){
  background-color: rgba(175,175,175,0.35);
}
body.chat #chat-config #chat-config-options .menu-entry:first-child {
  /* Config list header */
  border-radius: 0 0 1em 1em;
}
body.chat #chat-config #chat-config-options .menu-entry:first-child .label-wrapper {
  align-items: start;
}
body.chat #chat-config #chat-config-options .menu-entry > .toggle-wrapper {
  /* Holder for a checkbox, if any */
  min-width: 1.5rem;
  margin-right: 1rem;
}
body.chat #chat-config #chat-config-options .menu-entry .label-wrapper {
  /* Wrapper for a LABEL and a .hint element. */
  display: flex;
  flex-direction: column;
  align-self: baseline;
  flex: 1 1 auto;
}
body.chat #chat-config #chat-config-options .menu-entry label {
  /* Config option label. */
  font-weight: bold;
  white-space: initial;
}
body.chat #chat-config #chat-config-options .menu-entry label[for] {
  cursor: pointer;
}
body.chat #chat-config #chat-config-options .menu-entry .hint {
  /* Config menu hint text */
  font-size: 85%;
  font-weight: normal;
  white-space: pre-wrap;
  display: inline-block;




  opacity: 0.85;



}
body.chat #chat-config #chat-config-options .menu-entry select {
}
body.chat #chat-preview #chat-preview-content {
  overflow: auto;
  flex: 1 1 auto;
  padding: 0.5em;
Changes to src/sync.c.
16
17
18
19
20
21
22










































































23
24
25
26
27
28
29
*******************************************************************************
**
** This file contains code used to push, pull, and sync a repository
*/
#include "config.h"
#include "sync.h"
#include <assert.h>











































































/*
** If the repository is configured for autosyncing, then do an
** autosync.  Bits of the "flags" parameter determine details of behavior:
**
**   SYNC_PULL           Pull content from the server to the local repo
**   SYNC_PUSH           Push content from local up to the server







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
*******************************************************************************
**
** This file contains code used to push, pull, and sync a repository
*/
#include "config.h"
#include "sync.h"
#include <assert.h>

/*
** Explain what type of sync operation is about to occur
*/
static void sync_explain(unsigned syncFlags){
  if( g.url.isAlias ){
    if( (syncFlags & (SYNC_PUSH|SYNC_PULL))==(SYNC_PUSH|SYNC_PULL) ){
      fossil_print("Sync with %s\n", g.url.canonical);
    }else if( syncFlags & SYNC_PUSH ){
      fossil_print("Push to %s\n", g.url.canonical);
    }else if( syncFlags & SYNC_PULL ){
      fossil_print("Pull from %s\n", g.url.canonical);
    }
  }
}


/*
** Call client_sync() one or more times in order to complete a
** sync operation.  Usually, client_sync() is called only once, though
** is can be called multiple times if the SYNC_ALLURL flags is set.
*/
static int client_sync_all_urls(
  unsigned syncFlags,      /* Mask of SYNC_* flags */
  unsigned configRcvMask,  /* Receive these configuration items */
  unsigned configSendMask, /* Send these configuration items */
  const char *zAltPCode    /* Alternative project code (usually NULL) */
){
  int nErr;
  int nOther;
  char **azOther;
  int i;
  Stmt q;

  sync_explain(syncFlags);
  nErr = client_sync(syncFlags, configRcvMask, configSendMask, zAltPCode);
  if( nErr==0 ) url_remember();
  if( (syncFlags & SYNC_ALLURL)==0 ) return nErr;
  nOther = 0;
  azOther = 0;
  db_prepare(&q,
    "SELECT substr(name,10) FROM config"
    " WHERE name glob 'sync-url:*'"
    "   AND value<>(SELECT value FROM config WHERE name='last-sync-url')"
  );
  while( db_step(&q)==SQLITE_ROW ){
    const char *zUrl = db_column_text(&q, 0);
    azOther = fossil_realloc(azOther, sizeof(*azOther)*(nOther+1));
    azOther[nOther++] = fossil_strdup(zUrl);
  }
  db_finalize(&q);
  for(i=0; i<nOther; i++){
    int rc;
    url_unparse(&g.url);
    url_parse(azOther[i], URL_PROMPT_PW|URL_ASK_REMEMBER_PW);
    sync_explain(syncFlags);
    rc = client_sync(syncFlags, configRcvMask, configSendMask, zAltPCode);
    nErr += rc;
    if( (g.url.flags & URL_REMEMBER_PW)!=0 && rc==0 ){
      char *zKey = mprintf("sync-pw:%s", azOther[i]);
      char *zPw = obscure(g.url.passwd);
      if( zPw && zPw[0] ){
        db_set(zKey/*works-like:""*/, zPw, 0);
      }
      fossil_free(zPw);
      fossil_free(zKey);
    }
    fossil_free(azOther[i]);
    azOther[i] = 0;
  }
  fossil_free(azOther);
  return nErr;
}


/*
** If the repository is configured for autosyncing, then do an
** autosync.  Bits of the "flags" parameter determine details of behavior:
**
**   SYNC_PULL           Pull content from the server to the local repo
**   SYNC_PUSH           Push content from local up to the server
46
47
48
49
50
51
52
53


54
55
56

57
58
59
60
61
62
63
64



65
66
67
68
69

70
71
72
73
74
75
76
  int configSync = 0;       /* configuration changes transferred */
  if( g.fNoSync ){
    return 0;
  }
  zAutosync = db_get("autosync", 0);
  if( zAutosync==0 ) zAutosync = "on";  /* defend against misconfig */
  if( is_false(zAutosync) ) return 0;
  if( db_get_boolean("dont-push",0) || fossil_strncmp(zAutosync,"pull",4)==0 ){


    flags &= ~SYNC_CKIN_LOCK;
    if( flags & SYNC_PUSH ) return 0;
  }

  url_parse(0, URL_REMEMBER);
  if( g.url.protocol==0 ) return 0;
  if( g.url.user!=0 && g.url.passwd==0 ){
    g.url.passwd = unobscure(db_get("last-sync-pw", 0));
    g.url.flags |= URL_PROMPT_PW;
    url_prompt_for_password();
  }
  g.zHttpAuth = get_httpauth();



  url_remember();
  if( find_option("verbose","v",0)!=0 ) flags |= SYNC_VERBOSE;
  fossil_print("Autosync:  %s\n", g.url.canonical);
  url_enable_proxy("via proxy: ");
  rc = client_sync(flags, configSync, 0, 0);

  return rc;
}

/*
** This routine will try a number of times to perform autosync with a
** 0.5 second sleep between attempts.
**







|
>
>



>








>
>
>
|
|
<
|
|
>







120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146

147
148
149
150
151
152
153
154
155
156
  int configSync = 0;       /* configuration changes transferred */
  if( g.fNoSync ){
    return 0;
  }
  zAutosync = db_get("autosync", 0);
  if( zAutosync==0 ) zAutosync = "on";  /* defend against misconfig */
  if( is_false(zAutosync) ) return 0;
  if( db_get_boolean("dont-push",0) 
   || sqlite3_strglob("*pull*", zAutosync)==0
  ){
    flags &= ~SYNC_CKIN_LOCK;
    if( flags & SYNC_PUSH ) return 0;
  }
  if( find_option("verbose","v",0)!=0 ) flags |= SYNC_VERBOSE;
  url_parse(0, URL_REMEMBER);
  if( g.url.protocol==0 ) return 0;
  if( g.url.user!=0 && g.url.passwd==0 ){
    g.url.passwd = unobscure(db_get("last-sync-pw", 0));
    g.url.flags |= URL_PROMPT_PW;
    url_prompt_for_password();
  }
  g.zHttpAuth = get_httpauth();
  if( sqlite3_strglob("*all*", zAutosync)==0 ){
    rc = client_sync_all_urls(flags|SYNC_ALLURL, configSync, 0, 0);
  }else{
    url_remember();
    sync_explain(flags);

    url_enable_proxy("via proxy: ");
    rc = client_sync(flags, configSync, 0, 0);
  }
  return rc;
}

/*
** This routine will try a number of times to perform autosync with a
** 0.5 second sleep between attempts.
**
147
148
149
150
151
152
153



154
155
156
157
158
159
160
161




162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191

192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209

210
211
212
213
214
215
216
  }
  if( find_option("verbose","v",0)!=0 ){
    *pSyncFlags |= SYNC_VERBOSE;
  }
  if( find_option("no-http-compression",0,0)!=0 ){
    *pSyncFlags |= SYNC_NOHTTPCOMPRESS;
  }



  url_proxy_options();
  clone_ssh_find_options();
  if( !uvOnly ) db_find_and_open_repository(0, 0);
  db_open_config(0, 1);
  if( g.argc==2 ){
    if( db_get_boolean("auto-shun",0) ) configSync = CONFIGSET_SHUN;
  }else if( g.argc==3 ){
    zUrl = g.argv[2];




  }
  if( ((*pSyncFlags) & (SYNC_PUSH|SYNC_PULL))==(SYNC_PUSH|SYNC_PULL)
   && db_get_boolean("uv-sync",0)
  ){
    *pSyncFlags |= SYNC_UNVERSIONED;
  }
  urlFlags &= ~urlOmitFlags;
  if( urlFlags & URL_REMEMBER ){
    clone_ssh_db_set_options();
  }
  url_parse(zUrl, urlFlags);
  remember_or_get_http_auth(zHttpAuth, urlFlags & URL_REMEMBER, zUrl);
  url_remember();
  if( g.url.protocol==0 ){
    if( urlOptional ) fossil_exit(0);
    usage("URL");
  }
  user_select();
  if( g.url.isAlias ){
    if( ((*pSyncFlags) & (SYNC_PUSH|SYNC_PULL))==(SYNC_PUSH|SYNC_PULL) ){
      fossil_print("Sync with %s\n", g.url.canonical);
    }else if( (*pSyncFlags) & SYNC_PUSH ){
      fossil_print("Push to %s\n", g.url.canonical);
    }else if( (*pSyncFlags) & SYNC_PULL ){
      fossil_print("Pull from %s\n", g.url.canonical);
    }
  }
  url_enable_proxy("via proxy: ");
  *pConfigFlags |= configSync;
}


/*
** COMMAND: pull
**
** Usage: %fossil pull ?URL? ?options?
**
** Pull all sharable changes from a remote repository into the local
** repository.  Sharable changes include public check-ins, edits to
** wiki pages, tickets, tech-notes, and forum posts.  Add
** the --private option to pull private branches.  Use the
** "configuration pull" command to pull website configuration details.
**
** If URL is not specified, then the URL from the most recent clone, push,
** pull, remote, or sync command is used.  See "fossil help clone" for
** details on the URL formats.
**
** Options:
**

**   -B|--httpauth USER:PASS    Credentials for the simple HTTP auth protocol,
**                              if required by the remote website
**   --from-parent-project      Pull content from the parent project
**   --ipv4                     Use only IPv4, not IPv6
**   --no-http-compression      Do not compress HTTP traffic
**   --once                     Do not remember URL for subsequent syncs
**   --private                  Pull private branches too







>
>
>








>
>
>
>












<





<
<
<
<
<
<
<
<
<



>


















>







227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260

261
262
263
264
265









266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
  }
  if( find_option("verbose","v",0)!=0 ){
    *pSyncFlags |= SYNC_VERBOSE;
  }
  if( find_option("no-http-compression",0,0)!=0 ){
    *pSyncFlags |= SYNC_NOHTTPCOMPRESS;
  }
  if( find_option("all",0,0)!=0 ){
    *pSyncFlags |= SYNC_ALLURL;
  }
  url_proxy_options();
  clone_ssh_find_options();
  if( !uvOnly ) db_find_and_open_repository(0, 0);
  db_open_config(0, 1);
  if( g.argc==2 ){
    if( db_get_boolean("auto-shun",0) ) configSync = CONFIGSET_SHUN;
  }else if( g.argc==3 ){
    zUrl = g.argv[2];
    if( (*pSyncFlags) & SYNC_ALLURL ){
      fossil_fatal("cannot use both the --all option and specific URL \"%s\"",
          zUrl);
    }
  }
  if( ((*pSyncFlags) & (SYNC_PUSH|SYNC_PULL))==(SYNC_PUSH|SYNC_PULL)
   && db_get_boolean("uv-sync",0)
  ){
    *pSyncFlags |= SYNC_UNVERSIONED;
  }
  urlFlags &= ~urlOmitFlags;
  if( urlFlags & URL_REMEMBER ){
    clone_ssh_db_set_options();
  }
  url_parse(zUrl, urlFlags);
  remember_or_get_http_auth(zHttpAuth, urlFlags & URL_REMEMBER, zUrl);

  if( g.url.protocol==0 ){
    if( urlOptional ) fossil_exit(0);
    usage("URL");
  }
  user_select();









  url_enable_proxy("via proxy: ");
  *pConfigFlags |= configSync;
}


/*
** COMMAND: pull
**
** Usage: %fossil pull ?URL? ?options?
**
** Pull all sharable changes from a remote repository into the local
** repository.  Sharable changes include public check-ins, edits to
** wiki pages, tickets, tech-notes, and forum posts.  Add
** the --private option to pull private branches.  Use the
** "configuration pull" command to pull website configuration details.
**
** If URL is not specified, then the URL from the most recent clone, push,
** pull, remote, or sync command is used.  See "fossil help clone" for
** details on the URL formats.
**
** Options:
**
**   --all                      Pull from all remotes, not just the default
**   -B|--httpauth USER:PASS    Credentials for the simple HTTP auth protocol,
**                              if required by the remote website
**   --from-parent-project      Pull content from the parent project
**   --ipv4                     Use only IPv4, not IPv6
**   --no-http-compression      Do not compress HTTP traffic
**   --once                     Do not remember URL for subsequent syncs
**   --private                  Pull private branches too
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261

262
263
264
265
266
267
268
  }
  if( zAltPCode ) urlOmitFlags = URL_REMEMBER;
  process_sync_args(&configFlags, &syncFlags, 0, urlOmitFlags);

  /* We should be done with options.. */
  verify_all_options();

  client_sync(syncFlags, configFlags, 0, zAltPCode);
}

/*
** COMMAND: push
**
** Usage: %fossil push ?URL? ?options?
**
** Push all sharable changes from the local repository to a remote
** repository.  Sharable changes include public check-ins, edits to
** wiki pages, tickets, tech-notes, and forum posts.  Use
** --private to also push private branches.  Use the "configuration
** push" command to push website configuration details.
**
** If URL is not specified, then the URL from the most recent clone, push,
** pull, remote, or sync command is used.  See "fossil help clone" for
** details on the URL formats.
**
** Options:
**

**   -B|--httpauth USER:PASS    Credentials for the simple HTTP auth protocol,
**                              if required by the remote website
**   --ipv4                     Use only IPv4, not IPv6
**   --no-http-compression      Do not compress HTTP traffic
**   --once                     Do not remember URL for subsequent syncs
**   --proxy PROXY              Use the specified HTTP proxy
**   --private                  Push private branches too







|



















>







314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
  }
  if( zAltPCode ) urlOmitFlags = URL_REMEMBER;
  process_sync_args(&configFlags, &syncFlags, 0, urlOmitFlags);

  /* We should be done with options.. */
  verify_all_options();

  client_sync_all_urls(syncFlags, configFlags, 0, zAltPCode);
}

/*
** COMMAND: push
**
** Usage: %fossil push ?URL? ?options?
**
** Push all sharable changes from the local repository to a remote
** repository.  Sharable changes include public check-ins, edits to
** wiki pages, tickets, tech-notes, and forum posts.  Use
** --private to also push private branches.  Use the "configuration
** push" command to push website configuration details.
**
** If URL is not specified, then the URL from the most recent clone, push,
** pull, remote, or sync command is used.  See "fossil help clone" for
** details on the URL formats.
**
** Options:
**
**   --all                      Push to all remotes, not just the default
**   -B|--httpauth USER:PASS    Credentials for the simple HTTP auth protocol,
**                              if required by the remote website
**   --ipv4                     Use only IPv4, not IPv6
**   --no-http-compression      Do not compress HTTP traffic
**   --once                     Do not remember URL for subsequent syncs
**   --proxy PROXY              Use the specified HTTP proxy
**   --private                  Push private branches too
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307

308
309
310
311
312
313
314

  /* We should be done with options.. */
  verify_all_options();

  if( db_get_boolean("dont-push",0) ){
    fossil_fatal("pushing is prohibited: the 'dont-push' option is set");
  }
  client_sync(syncFlags, 0, 0, 0);
}


/*
** COMMAND: sync
**
** Usage: %fossil sync ?URL? ?options?
**
** Synchronize all sharable changes between the local repository and a
** remote repository.  Sharable changes include public check-ins and
** edits to wiki pages, tickets, forum posts, and technical notes.
**
** If URL is not specified, then the URL from the most recent clone, push,
** pull, remote, or sync command is used.  See "fossil help clone" for
** details on the URL formats.
**
** Options:
**

**   -B|--httpauth USER:PASS    Credentials for the simple HTTP auth protocol,
**                              if required by the remote website
**   --ipv4                     Use only IPv4, not IPv6
**   --no-http-compression      Do not compress HTTP traffic
**   --once                     Do not remember URL for subsequent syncs
**   --proxy PROXY              Use the specified HTTP proxy
**   --private                  Sync private branches too







|


















>







362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395

  /* We should be done with options.. */
  verify_all_options();

  if( db_get_boolean("dont-push",0) ){
    fossil_fatal("pushing is prohibited: the 'dont-push' option is set");
  }
  client_sync_all_urls(syncFlags, 0, 0, 0);
}


/*
** COMMAND: sync
**
** Usage: %fossil sync ?URL? ?options?
**
** Synchronize all sharable changes between the local repository and a
** remote repository.  Sharable changes include public check-ins and
** edits to wiki pages, tickets, forum posts, and technical notes.
**
** If URL is not specified, then the URL from the most recent clone, push,
** pull, remote, or sync command is used.  See "fossil help clone" for
** details on the URL formats.
**
** Options:
**
**   --all                      Sync with all remotes, not just the default
**   -B|--httpauth USER:PASS    Credentials for the simple HTTP auth protocol,
**                              if required by the remote website
**   --ipv4                     Use only IPv4, not IPv6
**   --no-http-compression      Do not compress HTTP traffic
**   --once                     Do not remember URL for subsequent syncs
**   --proxy PROXY              Use the specified HTTP proxy
**   --private                  Sync private branches too
330
331
332
333
334
335
336
337
338
339
340

341
342
343
344
345
346
347
  }
  process_sync_args(&configFlags, &syncFlags, 0, 0);

  /* We should be done with options.. */
  verify_all_options();

  if( db_get_boolean("dont-push",0) ) syncFlags &= ~SYNC_PUSH;
  client_sync(syncFlags, configFlags, 0, 0);
  if( (syncFlags & SYNC_PUSH)==0 ){
    fossil_warning("pull only: the 'dont-push' option is set");
  }

}

/*
** Handle the "fossil unversioned sync" and "fossil unversioned revert"
** commands.
*/
void sync_unversioned(unsigned syncFlags){







<



>







411
412
413
414
415
416
417

418
419
420
421
422
423
424
425
426
427
428
  }
  process_sync_args(&configFlags, &syncFlags, 0, 0);

  /* We should be done with options.. */
  verify_all_options();

  if( db_get_boolean("dont-push",0) ) syncFlags &= ~SYNC_PUSH;

  if( (syncFlags & SYNC_PUSH)==0 ){
    fossil_warning("pull only: the 'dont-push' option is set");
  }
  client_sync_all_urls(syncFlags, configFlags, 0, 0);
}

/*
** Handle the "fossil unversioned sync" and "fossil unversioned revert"
** commands.
*/
void sync_unversioned(unsigned syncFlags){
400
401
402
403
404
405
406






407
408
409
410
411
412
413
414
415
416
417
418





















419
420
421
422
423
424
425
**     Forget the default sync URL, disabling autosync.  Combined with
**     named sync URLs, it allows canceling this "airplane mode" with
**     "fossil remote NAME" to select a previously-set named URL.
**
**     To disable use of the default remote without forgetting its URL,
**     say "fossil set autosync 0" instead.
**






** > fossil remote REF
**
**     Make REF the new default URL, replacing the prior default.
**     REF may be a URL or a NAME from a prior "add".
*/
void remote_url_cmd(void){
  char *zUrl, *zArg;
  int nArg;
  db_find_and_open_repository(0, 0);

  /* We should be done with options.. */
  verify_all_options();






















  if( g.argc==2 ){
    /* "fossil remote" with no arguments:  Show the last sync URL. */
    zUrl = db_get("last-sync-url", 0);
    if( zUrl==0 ){
      fossil_print("off\n");
    }else{







>
>
>
>
>
>












>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
**     Forget the default sync URL, disabling autosync.  Combined with
**     named sync URLs, it allows canceling this "airplane mode" with
**     "fossil remote NAME" to select a previously-set named URL.
**
**     To disable use of the default remote without forgetting its URL,
**     say "fossil set autosync 0" instead.
**
** > fossil remote scrub
**
**     Forget any saved passwords for remote repositories, but continue
**     to remember the URLs themselves.  You will be prompted for the
**     password the next time it is needed.
**
** > fossil remote REF
**
**     Make REF the new default URL, replacing the prior default.
**     REF may be a URL or a NAME from a prior "add".
*/
void remote_url_cmd(void){
  char *zUrl, *zArg;
  int nArg;
  db_find_and_open_repository(0, 0);

  /* We should be done with options.. */
  verify_all_options();

  /* 2021-10-25: A note about data structures.
  **
  ** The remote URLs are stored in the CONFIG table.  The URL is stored
  ** separately from the password.  The password is obscured using the
  ** obscure() function.
  **
  ** Originally, Fossil only preserved a single remote URL.  That URL
  ** is stored in "last-sync-url" and the password in "last-sync-pw".  The
  ** ability to have multiple remotes was added later so these names
  ** were retained for backwards compatibility.  The other remotes are
  ** stored in "sync-url:NAME" and "sync-pw:NAME" where NAME is the name
  ** of the remote.
  **
  ** The last-sync-url is called "default" for the display list.
  **
  ** The last-sync-url might be duplicated into one of the sync-url:NAME
  ** entries.  Thus, when doing a "fossil sync --all" or an autosync with
  ** autosync=all, each sync-url:NAME entry is checked to see if it is the
  ** same as last-sync-url and if it is then that entry is skipped.
  */ 

  if( g.argc==2 ){
    /* "fossil remote" with no arguments:  Show the last sync URL. */
    zUrl = db_get("last-sync-url", 0);
    if( zUrl==0 ){
      fossil_print("off\n");
    }else{
493
494
495
496
497
498
499







































500
501
502
503
504
505
506
    db_begin_write();
    db_unprotect(PROTECT_CONFIG);
    db_multi_exec("DELETE FROM config WHERE name glob 'sync-url:%q'", zName);
    db_multi_exec("DELETE FROM config WHERE name glob 'sync-pw:%q'", zName);
    db_protect_pop();
    db_commit_transaction();
    return;







































  }
  if( sqlite3_strlike("http://%",zArg,0)==0
   || sqlite3_strlike("https://%",zArg,0)==0
   || sqlite3_strlike("ssh:%",zArg,0)==0
   || sqlite3_strlike("file:%",zArg,0)==0
   || db_exists("SELECT 1 FROM config WHERE name='sync-url:%q'",zArg)
  ){







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
    db_begin_write();
    db_unprotect(PROTECT_CONFIG);
    db_multi_exec("DELETE FROM config WHERE name glob 'sync-url:%q'", zName);
    db_multi_exec("DELETE FROM config WHERE name glob 'sync-pw:%q'", zName);
    db_protect_pop();
    db_commit_transaction();
    return;
  }
  if( strncmp(zArg, "scrub", nArg)==0 ){
    if( g.argc!=3 ) usage("scrub");
    db_begin_write();
    db_unprotect(PROTECT_CONFIG);
    db_multi_exec("DELETE FROM config WHERE name glob 'sync-pw:*'");
    db_multi_exec("DELETE FROM config WHERE name = 'last-sync-pw'");
    db_protect_pop();
    db_commit_transaction();
    return;
  }
  if( strncmp(zArg, "config-data", nArg)==0 ){
    /* Undocumented command:  "fossil remote config-data"
    **
    ** Show the CONFIG table entries that relate to remembering remote URLs
    */
    Stmt q;
    int n;
    n = db_int(13,
       "SELECT max(length(name))"
       "  FROM config"
       " WHERE name GLOB 'sync-*:*' OR name GLOB 'last-sync-*'"
    );
    db_prepare(&q,
       "SELECT name,"
       "       CASE WHEN name LIKE '%%sync-pw%%'"
                  " THEN printf('%%.*c',length(value),'*') ELSE value END"
       "  FROM config"
       " WHERE name GLOB 'sync-*:*' OR name GLOB 'last-sync-*'"
       " ORDER BY name LIKE '%%sync-pw%%', name"
    );
    while( db_step(&q)==SQLITE_ROW ){
      fossil_print("%-*s  %s\n",
        n, db_column_text(&q,0),
        db_column_text(&q,1)
      );
    }
    db_finalize(&q);
    return;
  }
  if( sqlite3_strlike("http://%",zArg,0)==0
   || sqlite3_strlike("https://%",zArg,0)==0
   || sqlite3_strlike("ssh:%",zArg,0)==0
   || sqlite3_strlike("file:%",zArg,0)==0
   || db_exists("SELECT 1 FROM config WHERE name='sync-url:%q'",zArg)
  ){
Changes to src/tktsetup.c.
535
536
537
538
539
540
541

542
543
544
545
546

547
548
549
550
551
552
553
@   if {$seenRow} {
@     html "<hr />\n"
@   } else {
@     html "<tr><td class='tktDspLabel'>User Comments:</td></tr>\n"
@     html "<tr><td colspan='5' class='tktDspValue'>\n"
@     set seenRow 1
@   }

@   html "[htmlize $xlogin]"
@   if {$xlogin ne $xusername && [string length $xusername]>0} {
@     html " (claiming to be [htmlize $xusername])"
@   }
@   html " added on $xdate:\n"

@   if {$alwaysPlaintext || $xmimetype eq "text/plain"} {
@     set r [randhex]
@     if {$xmimetype ne "text/plain"} {html "([htmlize $xmimetype])\n"}
@     wiki "<verbatim-$r>[string trimright $xcomment]</verbatim-$r>\n"
@   } elseif {$xmimetype eq "text/x-fossil-wiki"} {
@     wiki "<p>\n[string trimright $xcomment]\n</p>\n"
@   } elseif {$xmimetype eq "text/x-markdown"} {







>




|
>







535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
@   if {$seenRow} {
@     html "<hr />\n"
@   } else {
@     html "<tr><td class='tktDspLabel'>User Comments:</td></tr>\n"
@     html "<tr><td colspan='5' class='tktDspValue'>\n"
@     set seenRow 1
@   }
@   html "<span class='tktDspCommenter'>"
@   html "[htmlize $xlogin]"
@   if {$xlogin ne $xusername && [string length $xusername]>0} {
@     html " (claiming to be [htmlize $xusername])"
@   }
@   html " added on $xdate:"
@   html "</span>\n"
@   if {$alwaysPlaintext || $xmimetype eq "text/plain"} {
@     set r [randhex]
@     if {$xmimetype ne "text/plain"} {html "([htmlize $xmimetype])\n"}
@     wiki "<verbatim-$r>[string trimright $xcomment]</verbatim-$r>\n"
@   } elseif {$xmimetype eq "text/x-fossil-wiki"} {
@     wiki "<p>\n[string trimright $xcomment]\n</p>\n"
@   } elseif {$xmimetype eq "text/x-markdown"} {
Changes to src/unversioned.c.
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
void uvlist_json_page(void){
  Stmt q;
  char *zSep = "[";
  Blob json;

  login_check_credentials();
  if( !g.perm.Read ){ login_needed(g.anon.Read); return; }
  cgi_set_content_type("text/json");
  etag_check(ETAG_DATA,0);
  if( !db_table_exists("repository","unversioned") ){
    blob_init(&json, "[]", -1);
    cgi_set_content(&json);
    return;
  }
  blob_init(&json, 0, 0);







|







655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
void uvlist_json_page(void){
  Stmt q;
  char *zSep = "[";
  Blob json;

  login_check_credentials();
  if( !g.perm.Read ){ login_needed(g.anon.Read); return; }
  cgi_set_content_type("application/json");
  etag_check(ETAG_DATA,0);
  if( !db_table_exists("repository","unversioned") ){
    blob_init(&json, "[]", -1);
    cgi_set_content(&json);
    return;
  }
  blob_init(&json, 0, 0);
Changes to src/url.c.
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
#define URL_PROMPTED         0x010  /* Prompted for PW already */
#define URL_OMIT_USER        0x020  /* Omit the user name from URL */

/*
** The URL related data used with this subsystem.
*/
struct UrlData {
  int isFile;      /* True if a "file:" url */
  int isHttps;     /* True if a "https:" url */
  int isSsh;       /* True if an "ssh:" url */
  int isAlias;     /* Input URL was an alias */
  char *name;      /* Hostname for http: or filename for file: */
  char *hostname;  /* The HOST: parameter on http headers */
  const char *protocol; /* "http" or "https" or "ssh" or "file" */
  int port;        /* TCP port number for http: or https: */
  int dfltPort;    /* The default port for the given protocol */
  char *path;      /* Pathname for http: */
  char *user;      /* User id for http: */
  char *passwd;    /* Password for http: */
  char *canonical; /* Canonical representation of the URL */
  char *proxyAuth; /* Proxy-Authorizer: string */
  char *fossil;    /* The fossil query parameter on ssh: */
  unsigned flags;  /* Boolean flags controlling URL processing */
  int useProxy;    /* Used to remember that a proxy is in use */
  char *proxyUrlPath;
  int proxyOrigPort; /* Tunneled port number for https through proxy */
};
#endif /* INTERFACE */


/*
** Parse the given URL.  Or if zUrl is NULL, parse the URL in the
** last-sync-url setting using last-sync-pw as the password.  Store







|
|
|
|
|
|

|
|
|
|
|
|
|
|
|
|

|







42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
#define URL_PROMPTED         0x010  /* Prompted for PW already */
#define URL_OMIT_USER        0x020  /* Omit the user name from URL */

/*
** The URL related data used with this subsystem.
*/
struct UrlData {
  int isFile;           /* True if a "file:" url */
  int isHttps;          /* True if a "https:" url */
  int isSsh;            /* True if an "ssh:" url */
  int isAlias;          /* Input URL was an alias */
  char *name;           /* Hostname for http: or filename for file: */
  char *hostname;       /* The HOST: parameter on http headers */
  const char *protocol; /* "http" or "https" or "ssh" or "file" */
  int port;             /* TCP port number for http: or https: */
  int dfltPort;         /* The default port for the given protocol */
  char *path;           /* Pathname for http: */
  char *user;           /* User id for http: */
  char *passwd;         /* Password for http: */
  char *canonical;      /* Canonical representation of the URL */
  char *proxyAuth;      /* Proxy-Authorizer: string */
  char *fossil;         /* The fossil query parameter on ssh: */
  unsigned flags;       /* Boolean flags controlling URL processing */
  int useProxy;         /* Used to remember that a proxy is in use */
  char *proxyUrlPath;
  int proxyOrigPort;    /* Tunneled port number for https through proxy */
};
#endif /* INTERFACE */


/*
** Parse the given URL.  Or if zUrl is NULL, parse the URL in the
** last-sync-url setting using last-sync-pw as the password.  Store
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
      pUrlData->protocol = "https";
      pUrlData->dfltPort = 443;
      iStart = 8;
    }else if( zUrl[0]=='s' ){
      pUrlData->isSsh = 1;
      pUrlData->protocol = "ssh";
      pUrlData->dfltPort = 22;
      pUrlData->fossil = "fossil";
      iStart = 6;
    }else{
      pUrlData->isHttps = 0;
      pUrlData->protocol = "http";
      pUrlData->dfltPort = 80;
      iStart = 7;
    }







|







139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
      pUrlData->protocol = "https";
      pUrlData->dfltPort = 443;
      iStart = 8;
    }else if( zUrl[0]=='s' ){
      pUrlData->isSsh = 1;
      pUrlData->protocol = "ssh";
      pUrlData->dfltPort = 22;
      pUrlData->fossil = fossil_strdup("fossil");
      iStart = 6;
    }else{
      pUrlData->isHttps = 0;
      pUrlData->protocol = "http";
      pUrlData->dfltPort = 80;
      iStart = 7;
    }
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252




253
254
255
256
257
258
259
        while( pUrlData->path[i] && pUrlData->path[i]!='&' ){ i++; }
      }
      if( pUrlData->path[i] ){
        pUrlData->path[i] = 0;
        i++;
      }
      if( fossil_strcmp(zName,"fossil")==0 ){
        pUrlData->fossil = zValue;
        dehttpize(pUrlData->fossil);
        fossil_free(zExe);
        zExe = mprintf("%cfossil=%T", cQuerySep, pUrlData->fossil);
        cQuerySep = '&';
      }
    }

    dehttpize(pUrlData->path);
    if( pUrlData->dfltPort==pUrlData->port ){
      pUrlData->canonical = mprintf(
        "%s://%s%T%T%z",
        pUrlData->protocol, zLogin, pUrlData->name, pUrlData->path, zExe
      );
    }else{
      pUrlData->canonical = mprintf(
        "%s://%s%T:%d%T%z",
        pUrlData->protocol, zLogin, pUrlData->name, pUrlData->port,
        pUrlData->path, zExe
      );
    }
    if( pUrlData->isSsh && pUrlData->path[1] ) pUrlData->path++;




    free(zLogin);
  }else if( strncmp(zUrl, "file:", 5)==0 ){
    pUrlData->isFile = 1;
    if( zUrl[5]=='/' && zUrl[6]=='/' ){
      i = 7;
    }else{
      i = 5;







|




















|
>
>
>
>







224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
        while( pUrlData->path[i] && pUrlData->path[i]!='&' ){ i++; }
      }
      if( pUrlData->path[i] ){
        pUrlData->path[i] = 0;
        i++;
      }
      if( fossil_strcmp(zName,"fossil")==0 ){
        pUrlData->fossil = fossil_strdup(zValue);
        dehttpize(pUrlData->fossil);
        fossil_free(zExe);
        zExe = mprintf("%cfossil=%T", cQuerySep, pUrlData->fossil);
        cQuerySep = '&';
      }
    }

    dehttpize(pUrlData->path);
    if( pUrlData->dfltPort==pUrlData->port ){
      pUrlData->canonical = mprintf(
        "%s://%s%T%T%z",
        pUrlData->protocol, zLogin, pUrlData->name, pUrlData->path, zExe
      );
    }else{
      pUrlData->canonical = mprintf(
        "%s://%s%T:%d%T%z",
        pUrlData->protocol, zLogin, pUrlData->name, pUrlData->port,
        pUrlData->path, zExe
      );
    }
    if( pUrlData->isSsh && pUrlData->path[1] ){
      char *zOld = pUrlData->path;
      pUrlData->path = mprintf("%s", zOld+1);
      fossil_free(zOld);
    }
    free(zLogin);
  }else if( strncmp(zUrl, "file:", 5)==0 ){
    pUrlData->isFile = 1;
    if( zUrl[5]=='/' && zUrl[6]=='/' ){
      i = 7;
    }else{
      i = 5;
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
  if( pUrlData->isFile ){
    Blob cfile;
    dehttpize(zFile);
    file_canonical_name(zFile, &cfile, 0);
    free(zFile);
    zFile = 0;
    pUrlData->protocol = "file";
    pUrlData->path = "";
    pUrlData->name = mprintf("%b", &cfile);
    pUrlData->canonical = mprintf("file://%T", pUrlData->name);
    blob_reset(&cfile);
  }else if( pUrlData->user!=0 && pUrlData->passwd==0 
         && (urlFlags & URL_PROMPT_PW)!=0 ){
    url_prompt_for_password_local(pUrlData);
  }else if( pUrlData->user!=0 && ( urlFlags & URL_ASK_REMEMBER_PW ) ){







|







282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
  if( pUrlData->isFile ){
    Blob cfile;
    dehttpize(zFile);
    file_canonical_name(zFile, &cfile, 0);
    free(zFile);
    zFile = 0;
    pUrlData->protocol = "file";
    pUrlData->path = mprintf("");
    pUrlData->name = mprintf("%b", &cfile);
    pUrlData->canonical = mprintf("file://%T", pUrlData->name);
    blob_reset(&cfile);
  }else if( pUrlData->user!=0 && pUrlData->passwd==0 
         && (urlFlags & URL_PROMPT_PW)!=0 ){
    url_prompt_for_password_local(pUrlData);
  }else if( pUrlData->user!=0 && ( urlFlags & URL_ASK_REMEMBER_PW ) ){
308
309
310
311
312
313
314

315
316
317
318
319
320
321
    p = &g.url;
  }
  fossil_free(p->canonical);
  fossil_free(p->name);
  fossil_free(p->path);
  fossil_free(p->user);
  fossil_free(p->passwd);

  memset(p, 0, sizeof(*p));
}

/*
** Parse the given URL, which describes a sync server.  Populate variables
** in the global "g.url" structure as shown below.  If zUrl is NULL, then
** parse the URL given in the last-sync-url setting, taking the password







>







312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
    p = &g.url;
  }
  fossil_free(p->canonical);
  fossil_free(p->name);
  fossil_free(p->path);
  fossil_free(p->user);
  fossil_free(p->passwd);
  fossil_free(p->fossil);
  memset(p, 0, sizeof(*p));
}

/*
** Parse the given URL, which describes a sync server.  Populate variables
** in the global "g.url" structure as shown below.  If zUrl is NULL, then
** parse the URL given in the last-sync-url setting, taking the password
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
void url_prompt_for_password_local(UrlData *pUrlData){
  if( pUrlData->isSsh || pUrlData->isFile ) return;
  if( isatty(fileno(stdin))
   && (pUrlData->flags & URL_PROMPT_PW)!=0
   && (pUrlData->flags & URL_PROMPTED)==0
  ){
    pUrlData->flags |= URL_PROMPTED;
    pUrlData->passwd = prompt_for_user_password(pUrlData->user);
    if( pUrlData->passwd[0]
     && (pUrlData->flags & (URL_REMEMBER|URL_ASK_REMEMBER_PW))!=0
    ){
      if( save_password_prompt(pUrlData->passwd) ){
        pUrlData->flags |= URL_REMEMBER_PW;
      }else{
        pUrlData->flags &= ~URL_REMEMBER_PW;







|







602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
void url_prompt_for_password_local(UrlData *pUrlData){
  if( pUrlData->isSsh || pUrlData->isFile ) return;
  if( isatty(fileno(stdin))
   && (pUrlData->flags & URL_PROMPT_PW)!=0
   && (pUrlData->flags & URL_PROMPTED)==0
  ){
    pUrlData->flags |= URL_PROMPTED;
    pUrlData->passwd = prompt_for_user_password(pUrlData->canonical);
    if( pUrlData->passwd[0]
     && (pUrlData->flags & (URL_REMEMBER|URL_ASK_REMEMBER_PW))!=0
    ){
      if( save_password_prompt(pUrlData->passwd) ){
        pUrlData->flags |= URL_REMEMBER_PW;
      }else{
        pUrlData->flags &= ~URL_REMEMBER_PW;
Changes to src/user.c.
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285

/*
** Prompt to save Fossil user password
*/
int save_password_prompt(const char *passwd){
  Blob x;
  char c;
  const char *old = db_get("last-sync-pw", 0);
  if( (old!=0) && fossil_strcmp(unobscure(old), passwd)==0 ){
     return 0;
  }
  if( fossil_security_level()>=1 ) return 0;
  prompt_user("remember password (Y/n)? ", &x);
  c = blob_str(&x)[0];
  blob_reset(&x);
  return ( c!='n' && c!='N' );
}








<
<
<
<







268
269
270
271
272
273
274




275
276
277
278
279
280
281

/*
** Prompt to save Fossil user password
*/
int save_password_prompt(const char *passwd){
  Blob x;
  char c;




  if( fossil_security_level()>=1 ) return 0;
  prompt_user("remember password (Y/n)? ", &x);
  c = blob_str(&x)[0];
  blob_reset(&x);
  return ( c!='n' && c!='N' );
}

Changes to src/wiki.c.
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
    int w, h;
    char *zOut = pikchr(zPikchr, "pikchr", 0, &w, &h);
    if( w>0 ){
      @ <div class="pikchr-svg" style="max-width:%d(w)px">
      @ %s(zOut)
      @ </div>
    }else{
      @ <pre class='error'>\n">
      @ %s(zOut);
      @ </pre>
    }
    free(zOut);
  }else{
    @ <pre class='textPlain'>
    @ %h(blob_str(pWiki))
    @ </pre>







|
|







209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
    int w, h;
    char *zOut = pikchr(zPikchr, "pikchr", 0, &w, &h);
    if( w>0 ){
      @ <div class="pikchr-svg" style="max-width:%d(w)px">
      @ %s(zOut)
      @ </div>
    }else{
      @ <pre class='error'>
      @ %h(zOut)
      @ </pre>
    }
    free(zOut);
  }else{
    @ <pre class='textPlain'>
    @ %h(blob_str(pWiki))
    @ </pre>
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
}

/*
** Given a mimetype, return its common name.
*/
static const char *mimetype_common_name(const char *zMimetype){
  int i;
  for(i=4; i>=2; i-=2){
    if( zMimetype && fossil_strcmp(zMimetype, azStyles[i])==0 ){
      return azStyles[i+1];
    }
  }
  return azStyles[1];
}








|







664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
}

/*
** Given a mimetype, return its common name.
*/
static const char *mimetype_common_name(const char *zMimetype){
  int i;
  for(i=6; i>=0; i-=3){
    if( zMimetype && fossil_strcmp(zMimetype, azStyles[i])==0 ){
      return azStyles[i+1];
    }
  }
  return azStyles[1];
}

1590
1591
1592
1593
1594
1595
1596
1597
1598
1599
1600
1601
1602


1603
1604




1605
1606
1607
1608
1609
1610
1611
1612
1613
1614
1615
1616

1617
1618
1619
1620
1621
1622
1623
1624

1625
1626
1627
1628
1629
1630
1631
1632
1633
1634
1635
1636
1637
1638
1639
1640
1641
1642
1643
1644
1645
1646
1647
1648
1649
1650
1651
1652
1653
1654
1655
1656
1657
1658
1659
1660
1661
1662
1663
1664
1665
1666
1667
1668
1669
1670

1671

1672
1673

1674
1675
1676
1677
1678
1679
1680
1681
1682




1683
1684
1685
1686
1687
1688
1689
1690
** URL: /wikiappend?name=PAGENAME&mimetype=MIMETYPE
**
** Append text to the end of a wiki page.
*/
void wikiappend_page(void){
  char *zTag;
  int rid = 0;
  int isSandbox;
  const char *zPageName;
  const char *zUser;
  const char *zMimetype;
  int goodCaptcha = 1;
  const char *zFormat;



  login_check_credentials();




  zPageName = PD("name","");
  zMimetype = wiki_filter_mimetypes(P("mimetype"));
  if( check_name(zPageName) ) return;
  isSandbox = is_sandbox(zPageName);
  if( !isSandbox ){
    zTag = mprintf("wiki-%s", zPageName);
    rid = db_int(0,
      "SELECT rid FROM tagxref"
      " WHERE tagid=(SELECT tagid FROM tag WHERE tagname=%Q)"
      " ORDER BY mtime DESC", zTag
    );
    free(zTag);

    if( !rid ){
      fossil_redirect_home();
      return;
    }
  }
  if( !g.perm.ApndWiki ){
    login_needed(g.anon.ApndWiki);
    return;

  }
  if( P("submit")!=0 && P("r")!=0 && P("u")!=0
   && (goodCaptcha = captcha_is_correct(0))
  ){
    char *zDate;
    Blob cksum;
    Blob body;
    Blob wiki;
    Manifest *pWiki = 0;

    blob_zero(&body);
    if( isSandbox ){
      blob_append(&body, db_get("sandbox",""), -1);
      appendRemark(&body, zMimetype);
      db_set("sandbox", blob_str(&body), 0);
    }else{
      login_verify_csrf_secret();
      pWiki = manifest_get(rid, CFTYPE_WIKI, 0);
      if( pWiki ){
        blob_append(&body, pWiki->zWiki, -1);
        manifest_destroy(pWiki);
      }
      blob_zero(&wiki);
      db_begin_transaction();
      zDate = date_in_standard_format("now");
      blob_appendf(&wiki, "D %s\n", zDate);
      blob_appendf(&wiki, "L %F\n", zPageName);
      if( fossil_strcmp(zMimetype, "text/x-fossil-wiki")!=0 ){
        blob_appendf(&wiki, "N %s\n", zMimetype);
      }
      if( rid ){
        char *zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
        blob_appendf(&wiki, "P %s\n", zUuid);
        free(zUuid);
      }
      if( !login_is_nobody() ){
        blob_appendf(&wiki, "U %F\n", login_name());
      }
      appendRemark(&body, zMimetype);
      blob_appendf(&wiki, "W %d\n%s\n", blob_size(&body), blob_str(&body));
      md5sum_blob(&wiki, &cksum);
      blob_appendf(&wiki, "Z %b\n", &cksum);
      blob_reset(&cksum);
      wiki_put(&wiki, rid, wiki_need_moderation(0));
      db_end_transaction(0);
    }

    cgi_redirectf("wiki?name=%T", zPageName);

  }
  if( P("cancel")!=0 ){

    cgi_redirectf("wiki?name=%T", zPageName);
    return;
  }
  style_set_current_page("%T?name=%T", g.zPath, zPageName);
  style_set_current_feature("wiki");
  style_header("Append Comment To: %s", zPageName);
  if( !goodCaptcha ){
    @ <p class="generalError">Error: Incorrect security code.</p>
  }




  if( P("preview")!=0 ){
    Blob preview;
    blob_zero(&preview);
    appendRemark(&preview, zMimetype);
    @ Preview:<hr />
    safe_html_context(DOCSRC_WIKI);
    wiki_render_by_mimetype(&preview, zMimetype);
    @ <hr />







<





>
>


>
>
>
>




|







>
|



<
|
<
<
>

|






<


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

>

|
>









>
>
>
>
|







1590
1591
1592
1593
1594
1595
1596

1597
1598
1599
1600
1601
1602
1603
1604
1605
1606
1607
1608
1609
1610
1611
1612
1613
1614
1615
1616
1617
1618
1619
1620
1621
1622
1623
1624
1625
1626

1627


1628
1629
1630
1631
1632
1633
1634
1635
1636

1637
1638





1639


1640


1641
1642
1643
1644
1645
1646
1647
1648
1649
1650
1651
1652
1653
1654
1655
1656
1657
1658
1659
1660
1661
1662
1663

1664
1665
1666
1667
1668
1669
1670
1671
1672
1673
1674
1675
1676
1677
1678
1679
1680
1681
1682
1683
1684
1685
1686
1687
1688
1689
1690
** URL: /wikiappend?name=PAGENAME&mimetype=MIMETYPE
**
** Append text to the end of a wiki page.
*/
void wikiappend_page(void){
  char *zTag;
  int rid = 0;

  const char *zPageName;
  const char *zUser;
  const char *zMimetype;
  int goodCaptcha = 1;
  const char *zFormat;
  Manifest *pWiki = 0;
  int isSandbox;

  login_check_credentials();
  if( !g.perm.ApndWiki ){
    login_needed(g.anon.ApndWiki);
    return;
  }
  zPageName = PD("name","");
  zMimetype = wiki_filter_mimetypes(P("mimetype"));
  if( check_name(zPageName) ) return;
  isSandbox = is_sandbox(zPageName);
  if(!isSandbox){
    zTag = mprintf("wiki-%s", zPageName);
    rid = db_int(0,
      "SELECT rid FROM tagxref"
      " WHERE tagid=(SELECT tagid FROM tag WHERE tagname=%Q)"
      " ORDER BY mtime DESC", zTag
    );
    free(zTag);
    pWiki = rid ? manifest_get(rid, CFTYPE_WIKI, 0) : 0;
    if( !pWiki ){
      fossil_redirect_home();
      return;
    }

    zMimetype = wiki_filter_mimetypes(pWiki->zMimetype)


      /* see https://fossil-scm.org/forum/forumpost/0acfdaac80 */;
  }
  if( !isSandbox && P("submit")!=0 && P("r")!=0 && P("u")!=0
   && (goodCaptcha = captcha_is_correct(0))
  ){
    char *zDate;
    Blob cksum;
    Blob body;
    Blob wiki;


    blob_zero(&body);





    login_verify_csrf_secret();


    blob_append(&body, pWiki->zWiki, -1);


    blob_zero(&wiki);
    db_begin_transaction();
    zDate = date_in_standard_format("now");
    blob_appendf(&wiki, "D %s\n", zDate);
    blob_appendf(&wiki, "L %F\n", zPageName);
    if( fossil_strcmp(zMimetype, "text/x-fossil-wiki")!=0 ){
      blob_appendf(&wiki, "N %s\n", zMimetype);
    }
    if( rid ){
      char *zUuid = db_text(0, "SELECT uuid FROM blob WHERE rid=%d", rid);
      blob_appendf(&wiki, "P %s\n", zUuid);
      free(zUuid);
    }
    if( !login_is_nobody() ){
      blob_appendf(&wiki, "U %F\n", login_name());
    }
    appendRemark(&body, zMimetype);
    blob_appendf(&wiki, "W %d\n%s\n", blob_size(&body), blob_str(&body));
    md5sum_blob(&wiki, &cksum);
    blob_appendf(&wiki, "Z %b\n", &cksum);
    blob_reset(&cksum);
    wiki_put(&wiki, rid, wiki_need_moderation(0));
    db_end_transaction(0);

    manifest_destroy(pWiki);
    cgi_redirectf("wiki?name=%T", zPageName);
    return;
  }
  if( !isSandbox && P("cancel")!=0 ){
    manifest_destroy(pWiki);
    cgi_redirectf("wiki?name=%T", zPageName);
    return;
  }
  style_set_current_page("%T?name=%T", g.zPath, zPageName);
  style_set_current_feature("wiki");
  style_header("Append Comment To: %s", zPageName);
  if( !goodCaptcha ){
    @ <p class="generalError">Error: Incorrect security code.</p>
  }
  if( isSandbox ){
    @ <p class="generalError">Error: the Sandbox page may not
    @ be appended to.</p>
  }
  if( !isSandbox && P("preview")!=0 ){
    Blob preview;
    blob_zero(&preview);
    appendRemark(&preview, zMimetype);
    @ Preview:<hr />
    safe_html_context(DOCSRC_WIKI);
    wiki_render_by_mimetype(&preview, zMimetype);
    @ <hr />
1703
1704
1705
1706
1707
1708
1709

1710
1711
1712
1713
1714
1715
1716
  @  rows="10" wrap="virtual">%h(PD("r",""))</textarea>
  @ <br />
  @ <input type="submit" name="preview" value="Preview Your Comment" />
  @ <input type="submit" name="submit" value="Append Your Changes" />
  @ <input type="submit" name="cancel" value="Cancel" />
  captcha_generate(0);
  @ </form>

  style_finish_page();
}

/*
** WEBPAGE: whistory
** URL: /whistory?name=PAGENAME
**







>







1703
1704
1705
1706
1707
1708
1709
1710
1711
1712
1713
1714
1715
1716
1717
  @  rows="10" wrap="virtual">%h(PD("r",""))</textarea>
  @ <br />
  @ <input type="submit" name="preview" value="Preview Your Comment" />
  @ <input type="submit" name="submit" value="Append Your Changes" />
  @ <input type="submit" name="cancel" value="Cancel" />
  captcha_generate(0);
  @ </form>
  manifest_destroy(pWiki);
  style_finish_page();
}

/*
** WEBPAGE: whistory
** URL: /whistory?name=PAGENAME
**
Changes to src/winhttp.c.
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
**
**              Sets the start type of the service. TYPE can be "manual",
**              which means you need to start the service yourself with the
**              'fossil winsrv start' command or with the "net start" command
**              from the operating system. If TYPE is set to "auto", the service
**              will be started automatically by the system during startup.
**
**         -U|--username USERNAME
**
**              Specifies the user account which will be used to run the
**              service. The account needs the "Logon as a service" right
**              enabled in its profile. Specify local accounts as follows:
**              ".\\USERNAME". By default, the "LocalSystem" account will be
**              used.
**







|







947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
**
**              Sets the start type of the service. TYPE can be "manual",
**              which means you need to start the service yourself with the
**              'fossil winsrv start' command or with the "net start" command
**              from the operating system. If TYPE is set to "auto", the service
**              will be started automatically by the system during startup.
**
**         --username USERNAME
**
**              Specifies the user account which will be used to run the
**              service. The account needs the "Logon as a service" right
**              enabled in its profile. Specify local accounts as follows:
**              ".\\USERNAME". By default, the "LocalSystem" account will be
**              used.
**
1051
1052
1053
1054
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
    SC_HANDLE hSvc;
    SERVICE_DESCRIPTIONW
      svcDescr = {L"Fossil - Distributed Software Configuration Management"};
    DWORD dwStartType = SERVICE_DEMAND_START;
    const char *zAltBase    = find_option("baseurl", 0, 1);
    const char *zDisplay    = find_option("display", "D", 1);
    const char *zStart      = find_option("start", "S", 1);
    const char *zUsername   = find_option("username", "U", 1);
    const char *zPassword   = find_option("password", "W", 1);
    const char *zPort       = find_option("port", "P", 1);
    const char *zNotFound   = find_option("notfound", 0, 1);
    const char *zFileGlob   = find_option("files", 0, 1);
    const char *zLocalAuth  = find_option("localauth", 0, 0);
    const char *zRepository = find_repository_option();
    int useSCGI             = find_option("scgi", 0, 0)!=0;







|







1051
1052
1053
1054
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
    SC_HANDLE hSvc;
    SERVICE_DESCRIPTIONW
      svcDescr = {L"Fossil - Distributed Software Configuration Management"};
    DWORD dwStartType = SERVICE_DEMAND_START;
    const char *zAltBase    = find_option("baseurl", 0, 1);
    const char *zDisplay    = find_option("display", "D", 1);
    const char *zStart      = find_option("start", "S", 1);
    const char *zUsername   = find_option("username", 0, 1);
    const char *zPassword   = find_option("password", "W", 1);
    const char *zPort       = find_option("port", "P", 1);
    const char *zNotFound   = find_option("notfound", 0, 1);
    const char *zFileGlob   = find_option("files", 0, 1);
    const char *zLocalAuth  = find_option("localauth", 0, 0);
    const char *zRepository = find_repository_option();
    int useSCGI             = find_option("scgi", 0, 0)!=0;
Changes to src/xfer.c.
1819
1820
1821
1822
1823
1824
1825

1826
1827
1828
1829
1830
1831
1832
#define SYNC_UNVERSIONED    0x0100    /* Sync unversioned content */
#define SYNC_UV_REVERT      0x0200    /* Copy server unversioned to client */
#define SYNC_UV_TRACE       0x0400    /* Describe UV activities */
#define SYNC_UV_DRYRUN      0x0800    /* Do not actually exchange files */
#define SYNC_IFABLE         0x1000    /* Inability to sync is not fatal */
#define SYNC_CKIN_LOCK      0x2000    /* Lock the current check-in */
#define SYNC_NOHTTPCOMPRESS 0x4000    /* Do not compression HTTP messages */

#endif

/*
** Floating-point absolute value
*/
static double fossil_fabs(double x){
  return x>0.0 ? x : -x;







>







1819
1820
1821
1822
1823
1824
1825
1826
1827
1828
1829
1830
1831
1832
1833
#define SYNC_UNVERSIONED    0x0100    /* Sync unversioned content */
#define SYNC_UV_REVERT      0x0200    /* Copy server unversioned to client */
#define SYNC_UV_TRACE       0x0400    /* Describe UV activities */
#define SYNC_UV_DRYRUN      0x0800    /* Do not actually exchange files */
#define SYNC_IFABLE         0x1000    /* Inability to sync is not fatal */
#define SYNC_CKIN_LOCK      0x2000    /* Lock the current check-in */
#define SYNC_NOHTTPCOMPRESS 0x4000    /* Do not compression HTTP messages */
#define SYNC_ALLURL         0x8000    /* The --all flag - sync to all URLs */
#endif

/*
** Floating-point absolute value
*/
static double fossil_fabs(double x){
  return x>0.0 ? x : -x;
Changes to www/bugtheory.wiki.
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
to repopulate the table using the new column names.  Note that the TICKET
table schema and content is part of the local state of a repository
and is not shared with other repositories during a sync, push, or pull.

Each repository also defines scripts used to generate web pages for
creating new tickets, viewing existing tickets, and modifying an
existing ticket.  These scripts consist of HTML with an embedded
scripts written a Tcl-like language called "TH1".  Every new fossil
repository is created with default scripts.  Paul Ruizendaal has written
documentation on the TH1 language that is available at
[http://www.sqliteconcepts.org/THManual.pdf].  Administrators wishing to
customize their ticket entry, viewing, and editing screens should
modify the default scripts to suit their needs.  These screen generator
scripts are part of the local state of a repository and are not shared
with other repositories during a sync, push, or pull.

<i>To be continued...</i>







|
|
<
<






110
111
112
113
114
115
116
117
118


119
120
121
122
123
124
to repopulate the table using the new column names.  Note that the TICKET
table schema and content is part of the local state of a repository
and is not shared with other repositories during a sync, push, or pull.

Each repository also defines scripts used to generate web pages for
creating new tickets, viewing existing tickets, and modifying an
existing ticket.  These scripts consist of HTML with an embedded
scripts written a Tcl-like language called "[./th1.md|TH1]".  Every new fossil
repository is created with default scripts. Administrators wishing to


customize their ticket entry, viewing, and editing screens should
modify the default scripts to suit their needs.  These screen generator
scripts are part of the local state of a repository and are not shared
with other repositories during a sync, push, or pull.

<i>To be continued...</i>
Changes to www/changes.wiki.
1
2






3

4
5
6
7
8
9
10
<title>Change Log</title>







<h2 id='v2_17'>Changes for version 2.17 (pending)</h2>

  *  Major improvements to the "diff" subsystem, including: <ul>
     <li> Added new [/help?cmd=diff|formatting options]: --by, -b, --webpage, --json, --tcl.
     <li> Partial-line matching for unified diffs
     <li> Better partial-line matching for side-by-side diffs
     <li> Buttons on web-based diffs to show more context
     <li> Performance improvements
     </ul>


>
>
>
>
>
>
|
>







1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
<title>Change Log</title>

<h2 id='v2_18'>Changes for version 2.18 (pending)</h2>
  *  [/help?cmd=/chat|The /chat page] input options have been reworked
     again for better cross-browser portability.
  *  When sending a [/help?cmd=/chat|/chat] message fails, it is no longer
     immediately lost and sending may optionally be retried.

<h2 id='v2_17'>Changes for version 2.17 (2021-10-09)</h2>

  *  Major improvements to the "diff" subsystem, including: <ul>
     <li> Added new [/help?cmd=diff|formatting options]: --by, -b, --webpage, --json, --tcl.
     <li> Partial-line matching for unified diffs
     <li> Better partial-line matching for side-by-side diffs
     <li> Buttons on web-based diffs to show more context
     <li> Performance improvements
     </ul>
Changes to www/chat.md.
119
120
121
122
123
124
125
































126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
who performed the deletion, not the author of the deleted
comment). That can potentially lead to odd corner cases where a user
shows up in the list but has no messages which are currently visible
because they were deleted, or an admin user who has not posted
anything but deleted a message. That is a known minor cosmetic-only
bug with a resolution of "will not fix."


































## Implementation Details

*You do not need to understand how Fossil chat works in order to use it.
But many developers prefer to know how their tools work.
This section is provided for the benefit of those curious developers.*

The [/chat](/help?cmd=/chat) webpage downloads a small amount of HTML
and a small amount of javascript to run the chat session.  The
javascript uses XMLHttpRequest (XHR) to download chat content, post
new content, or delete historical messages.  The following web
interfaces are used by the XHR:

  *  **/chat-poll** &rarr;
     Downloads chat content as JSON.
     Chat messages are numbered sequentially.
     The client tells the server the largest chat message it currently
     holds, and the server sends back subsequent messages.  If there
     are no subsequent messages, the /chat-poll page blocks until new
     messages are available.

  *  **/chat-send** &rarr;
     Sends a new chat message to the server.

  *  **/chat-delete** &rarr;
     Deletes a chat message.

Fossil chat uses the venerable "hanging GET" or 
"[long polling](wikipedia:/wiki/Push_technology#Long_polling)"
technique to recieve asynchronous notification of new messages.
This is done because long polling works well with CGI and SCGI,
which are the usual mechanisms for setting up a Fossil server.
More advanced notification techniques such as 
[Server-sent events](wikipedia:/wiki/Server-sent_events) and especially
[WebSockets](wikipedia:/wiki/WebSocket) might seem more appropriate for
a chat system, but those technologies are not compatible with CGI.

Downloading of posted files and images uses a separate, non-XHR interface:

  * **/chat-download** &rarr;
    Fetches the file content associated with a post (one file per
    post, maximum). In the UI, this is accessed via links to uploaded
    files and via inlined image tags.

Chat messages are stored on the server-side in the CHAT table of
the repository.

~~~
   CREATE TABLE repository.chat(
      msgid INTEGER PRIMARY KEY AUTOINCREMENT,
      mtime JULIANDAY,
      ltime TEXT,
      xfrom TEXT,
      xmsg  TEXT,
      fname TEXT,
      fmime TEXT,
      mdel  INT,
      file  BLOB)
    );
~~~

The CHAT table is not cross-linked with any other tables in the repository
schema.  An administrator can "DROP TABLE chat;" at any time, without
harm (apart from deleting all chat history, of course).  The CHAT table
is dropped when running [fossil scrub --verily](/help?cmd=scrub).








>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>













|







|


|














|







|
|
|
|
|
|
|
|
|
|
|
|







119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
who performed the deletion, not the author of the deleted
comment). That can potentially lead to odd corner cases where a user
shows up in the list but has no messages which are currently visible
because they were deleted, or an admin user who has not posted
anything but deleted a message. That is a known minor cosmetic-only
bug with a resolution of "will not fix."

### <a id="cli"></a> The `fossil chat` Command

Type [fossil chat](/help?cmd=chat) from within any open check-out
to bring up a chatroom for the project that is in that checkout.
The new chat window will attempt to connect to the default sync
target for that check-out (the server whose URL is shown by the
[fossil remote](/help?cmd=remote) command).

### <a id="robots"></a> Chat Messages From Robots

The [fossil chat send](/help?cmd=chat) can be used by project-specific
robots to send notifications to the chatroom.  For example, on the
[SQLite project](https://sqlite.org/) (for which the Fossil chatroom
feature, and indeed all of Fossil, was invented) there are long-running
fuzz servers that sometimes run across obscure problems.  Whenever this
happens, a message is sent to the SQLite developers chatroom altering
them to the problem.

The recommended way to allow robots to send chat messages is to create
a new user on the server for each robot.  Give each such robot account
the "C" privilege only.  That means that the robot user account will be 
able to send chat messages, but not do anything else.  Then, in the
program or script that runs the robot, when it wants to send a chat
message, have it run a command like this:

> ~~~~
fossil chat send --remote https://robot:PASSWORD@project.org/fossil \
  --message 'MESSAGE TEXT' --file file-to-attach.txt
~~~~

Substitute the appropriate project URL, robot account
name and password, message text and file attachment, of course.

## Implementation Details

*You do not need to understand how Fossil chat works in order to use it.
But many developers prefer to know how their tools work.
This section is provided for the benefit of those curious developers.*

The [/chat](/help?cmd=/chat) webpage downloads a small amount of HTML
and a small amount of javascript to run the chat session.  The
javascript uses XMLHttpRequest (XHR) to download chat content, post
new content, or delete historical messages.  The following web
interfaces are used by the XHR:

  *  [/chat-poll](/help?name=/chat-poll) &rarr;
     Downloads chat content as JSON.
     Chat messages are numbered sequentially.
     The client tells the server the largest chat message it currently
     holds, and the server sends back subsequent messages.  If there
     are no subsequent messages, the /chat-poll page blocks until new
     messages are available.

  *  [/chat-send](/help?name=/chat-send) &rarr;
     Sends a new chat message to the server.

  *  [/chat-delete](/help?name=/chat-delete) &rarr;
     Deletes a chat message.

Fossil chat uses the venerable "hanging GET" or 
"[long polling](wikipedia:/wiki/Push_technology#Long_polling)"
technique to recieve asynchronous notification of new messages.
This is done because long polling works well with CGI and SCGI,
which are the usual mechanisms for setting up a Fossil server.
More advanced notification techniques such as 
[Server-sent events](wikipedia:/wiki/Server-sent_events) and especially
[WebSockets](wikipedia:/wiki/WebSocket) might seem more appropriate for
a chat system, but those technologies are not compatible with CGI.

Downloading of posted files and images uses a separate, non-XHR interface:

  * [/chat-download](/help?name=/chat-download) &rarr;
    Fetches the file content associated with a post (one file per
    post, maximum). In the UI, this is accessed via links to uploaded
    files and via inlined image tags.

Chat messages are stored on the server-side in the CHAT table of
the repository.

> ~~~
CREATE TABLE repository.chat(
  msgid INTEGER PRIMARY KEY AUTOINCREMENT,
  mtime JULIANDAY,  -- Time for this entry - Julianday Zulu
  lmtime TEXT,      -- Client YYYY-MM-DDZHH:MM:SS when message originally sent
  xfrom TEXT,       -- Login of the sender
  xmsg  TEXT,       -- Raw, unformatted text of the message
  fname TEXT,       -- Filename of the uploaded file, or NULL
  fmime TEXT,       -- MIMEType of the upload file, or NULL
  mdel INT,         -- msgid of another message to delete
  file  BLOB        -- Text of the uploaded file, or NULL
);
~~~

The CHAT table is not cross-linked with any other tables in the repository
schema.  An administrator can "DROP TABLE chat;" at any time, without
harm (apart from deleting all chat history, of course).  The CHAT table
is dropped when running [fossil scrub --verily](/help?cmd=scrub).

Changes to www/concepts.wiki.
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
to setup and operate.

This document is intended as a quick introduction to the concepts
behind Fossil.

See also:

  *  [./whyusefossil.wiki#definitions|Definitions]
  *  [./quickstart.wiki|Quick start guide]

<h2>2.0 Composition Of A Project</h2>

<verbatim type="pikchr float-right">
R1: cylinder "Remote" "Repository" fill 0xadd8e6 rad 70%
R2: cylinder same "Remote" "Repository" at 2.5*R1.wid right of R1
    spline <-> from R1.e to 0.6<R1.se,R2.sw> then to 0.4<R1.ne,R2.nw> then to R2.w
    text "HTTP" at .5<R1.ne,R2.nw>
R3: cylinder same "Local" "Repository" fill 0x90ee90 \
    at dist(R1.e,R2.w) below .5<R1,R2>
    spline <-> from .5<R1.s,R1.se> to 0.6<R1.s,R3.w> to 0.5<R1.se,R3.n> to .5<R3.nw,R3.n> "HTTP" \
      behind R1
    spline <-> from R2.sw to .6<R2.sw,R3.n> to .5<R2.s,R3.e> to R3.ne "HTTP" ljust
T1: line from 1.0cm heading 200 from R3.sw go 2.2cm heading 150 then 2.2cm west close \
       fill 0xffff00 "Local" below "Source Tree" below
T2: line from 1.0cm heading 160 from R3.se same "Local" below "Source Tree" below
    line <-> from R3.sw to T1.start
    line <-> from R3.se to T2.start
</verbatim>








|
|







|


|
|
|







13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
to setup and operate.

This document is intended as a quick introduction to the concepts
behind Fossil.

See also:

  *  [./glossary.md | Glossary]
  *  [./quickstart.wiki | Quick start guide]

<h2>2.0 Composition Of A Project</h2>

<verbatim type="pikchr float-right">
R1: cylinder "Remote" "Repository" fill 0xadd8e6 rad 70%
R2: cylinder same "Remote" "Repository" at 2.5*R1.wid right of R1
    spline <-> from R1.e to 0.6<R1.se,R2.sw> then to 0.4<R1.ne,R2.nw> then to R2.w
    text "HTTPS" at .5<R1.ne,R2.nw>
R3: cylinder same "Local" "Repository" fill 0x90ee90 \
    at dist(R1.e,R2.w) below .5<R1,R2>
    spline <-> from .5<R1.s,R1.se> to 0.6<R1.s,R3.w> to 0.5<R1.se,R3.n> to .5<R3.nw,R3.n> \
      "HTTPS" above behind R1
    spline <-> from R2.sw to .6<R2.sw,R3.n> to .5<R2.s,R3.e> to R3.ne "HTTPS" ljust
T1: line from 1.0cm heading 200 from R3.sw go 2.2cm heading 150 then 2.2cm west close \
       fill 0xffff00 "Local" below "Source Tree" below
T2: line from 1.0cm heading 160 from R3.se same "Local" below "Source Tree" below
    line <-> from R3.sw to T1.start
    line <-> from R3.se to T2.start
</verbatim>

89
90
91
92
93
94
95
96

97
98
99
100
101
102
103
remote repository into a local repository.  Or one can do a "sync"
which is a shortcut for doing both a push and a pull at the same time.
Fossil also has the concept of "cloning".  A "clone" is like a "pull",
except that instead of beginning with an existing local repository,
a clone begins with nothing and creates a new local repository that
is a duplicate of a remote repository.

Communication between repositories is via HTTP.  Remote

repositories are identified by URL.  You can also point a web browser
at a repository and get human-readable status, history, and tracking
information about the project.

<h3 id="artifacts">2.1 Identification Of Artifacts</h3>

A particular version of a particular file is called an "artifact".  Each







|
>







89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
remote repository into a local repository.  Or one can do a "sync"
which is a shortcut for doing both a push and a pull at the same time.
Fossil also has the concept of "cloning".  A "clone" is like a "pull",
except that instead of beginning with an existing local repository,
a clone begins with nothing and creates a new local repository that
is a duplicate of a remote repository.

Communication between repositories is normally via HTTPS.  (SSH is also
supported, as is unencrypted HTTP.) Remote
repositories are identified by URL.  You can also point a web browser
at a repository and get human-readable status, history, and tracking
information about the project.

<h3 id="artifacts">2.1 Identification Of Artifacts</h3>

A particular version of a particular file is called an "artifact".  Each
Changes to www/contribute.wiki.
25
26
27
28
29
30
31




32
33
34
35
36
37
38

<h2>2.0 Submitting Patches</h2>

Suggested changes or bug fixes can be submitted by creating a patch
against the current source tree:

    <tt>fossil diff -i > my-change.patch</tt>





Post patches to
[https://fossil-scm.org/forum | the forum] or email them to
<a href="mailto:drh@sqlite.org">drh@sqlite.org</a>.  Be sure to
describe in detail what the patch does and which version of Fossil
it is written against. It's best to make patches against tip-of-trunk
rather than against past releases.







>
>
>
>







25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42

<h2>2.0 Submitting Patches</h2>

Suggested changes or bug fixes can be submitted by creating a patch
against the current source tree:

    <tt>fossil diff -i > my-change.patch</tt>

Alternatively, you can create a binary patch:

    <tt>fossil patch create my-change.db</tt>

Post patches to
[https://fossil-scm.org/forum | the forum] or email them to
<a href="mailto:drh@sqlite.org">drh@sqlite.org</a>.  Be sure to
describe in detail what the patch does and which version of Fossil
it is written against. It's best to make patches against tip-of-trunk
rather than against past releases.
Changes to www/gitusers.md.
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
We think this is a more sensible command design than `git pull` vs
`git checkout`. ([…vs `git checkout` vs `git checkout`!][gcokoan])

[fpull]:   /help?cmd=pull
[gpull]:   https://git-scm.com/docs/git-pull
[gcokoan]: https://stevelosh.com/blog/2013/04/git-koans/#s2-one-thing-well


#### <a id="rname"></a> Naming Repositories

The Fossil repository database file can be named anything
you want, with a single exception: if you’re going to use the
[`fossil server DIRECTORY`][server] feature, the repositories you wish
to serve need to be stored together in a flat directory and have
"`.fossil`" suffixes. That aside, you can follow any other convention that
makes sense to you.

This author uses a scheme like the following on mobile machines that
shuttle between home and the office:

``` pikchr toggle indent
scale=0.8
box "~/museum/" fit
move right 0.1
line right dotted
move right 0.05
box invis "where one stores valuable fossils" ljust

arrow down 50% from first box.s then right 50%
box "work/" fit
move right 0.1
line dotted
move right 0.05
box invis "projects from $dayjob" ljust

arrow down 50% from 2nd vertex of previous arrow then right 50%
box "home/" fit
move right 0.1
line dotted right until even with previous line.end
move right 0.05
box invis "personal at-home projects" ljust

arrow down 50% from 2nd vertex of previous arrow then right 50%
box "other/" fit
move right 0.1
line dotted right until even with previous line.end
move right 0.05
box invis "clones of Fossil itself, SQLite, etc." ljust
```

On a Windows box, you might instead choose "`C:\Fossils`"
and do without the subdirectory scheme, for example.


#### <a id="close" name="dotfile"></a> Closing a Check-Out

The [`fossil close`][close] command dissociates a check-out directory from the
Fossil repository database, nondestructively inverting [`fossil open`][open].
(Contrast [its closest inverse](#worktree), `git worktree remove`, which *is*
destructive in Git!) This Fossil command does not







<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<







128
129
130
131
132
133
134














































135
136
137
138
139
140
141
We think this is a more sensible command design than `git pull` vs
`git checkout`. ([…vs `git checkout` vs `git checkout`!][gcokoan])

[fpull]:   /help?cmd=pull
[gpull]:   https://git-scm.com/docs/git-pull
[gcokoan]: https://stevelosh.com/blog/2013/04/git-koans/#s2-one-thing-well
















































#### <a id="close" name="dotfile"></a> Closing a Check-Out

The [`fossil close`][close] command dissociates a check-out directory from the
Fossil repository database, nondestructively inverting [`fossil open`][open].
(Contrast [its closest inverse](#worktree), `git worktree remove`, which *is*
destructive in Git!) This Fossil command does not
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
you’re following [the directory scheme exemplified above](#rname). That said, it
does emphasize an earlier point: Fossil doesn’t care where you put the
repo DB file or what you name it.


[clone]:  /help?cmd=clone
[close]:  /help?cmd=close
[gloss]:  ./whyusefossil.wiki#definitions
[open]:   /help?cmd=open
[set]:    /help?cmd=setting
[server]: /help?cmd=server
[stash]:  /help?cmd=stash
[undo]:   /help?cmd=undo









|







276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
you’re following [the directory scheme exemplified above](#rname). That said, it
does emphasize an earlier point: Fossil doesn’t care where you put the
repo DB file or what you name it.


[clone]:  /help?cmd=clone
[close]:  /help?cmd=close
[gloss]:  ./glossary.md
[open]:   /help?cmd=open
[set]:    /help?cmd=setting
[server]: /help?cmd=server
[stash]:  /help?cmd=stash
[undo]:   /help?cmd=undo


484
485
486
487
488
489
490
491
492
493
494
495

496


497
498
499

500
501



502
503
504
505
506
507
508
509
510
in Fossil, because the indexes always let us find our way back into the
hash tree.


## <a id="slcom"></a> Summary Line Convention In Commit Comments

The Git convention of a [length-limited summary line][lsl] at the start
of commit comments has no equivalent in Fossil. You’re welcome to style
your commit comments thus, but the convention isn’t used or enforced
anywhere in Fossil. For instance, setting `EDITOR=vim` and making a
commit doesn’t do syntax highlighting on the commit message to warn that
you’ve gone over the conventional limit on the first line, and the

Fossil web timeline display doesn’t show the summary line in bold.



If you wish to follow such conventions in a Fossil project, you may want
to enable the “Allow block-markup in timeline” setting under Admin →

Timeline in the web UI to prevent Fossil from showing the message as a
single paragraph, sans line breaks. [Skin customization][cskin] would



allow you to style the first line of the commit message in bold in
`/timeline` views.

[cskin]: ./customskin.md
[lsl]:   https://chris.beams.io/posts/git-commit/#limit-50



<a id="staging"></a>







|
|
<
<
|
>
|
>
>

|
<
>
|
<
>
>
>
|
<







438
439
440
441
442
443
444
445
446


447
448
449
450
451
452
453

454
455

456
457
458
459

460
461
462
463
464
465
466
in Fossil, because the indexes always let us find our way back into the
hash tree.


## <a id="slcom"></a> Summary Line Convention In Commit Comments

The Git convention of a [length-limited summary line][lsl] at the start
of commit comments is not enforced or obeyed by default in Fossil.
However, there is a setting under Admin → Timeline → “Truncate comment


at first blank line (Git-style)” to change this for `/timeline`
displays.  Alternately, you could enable the “Allow block-markup in
timeline setting under Admin → Timeline, then apply [local skin
customizations][cskin] to put that first comment in in bold or whatever
suits.

Because this isn’t a typical Fossil convention, you’re likely to find

other odd differences between it and Git-based infrastructure.  For
instance, Vim doesn’t ship with syntax support for Fossil commit

messages if you set `EDITOR=vim` in your shell environment, so you won’t
get over-limit highlighting for first-line text beyond the 50th
character and such, because it doesn’t recognize Fossil commit messages
and apply similar rules as to Git commit messages.


[cskin]: ./customskin.md
[lsl]:   https://chris.beams.io/posts/git-commit/#limit-50



<a id="staging"></a>
Added www/glossary.md.
















































































































































































































































































































































































































































































































































































































>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
# Glossary

There are several terms-of-art in Fossil that have specific meanings
which are either not immediately obvious to an outsider or which have
technical associations that can lead someone to either use the terms
incorrectly or to get the wrong idea from someone using those terms
correctly. We hope to teach users how to properly “speak Fossil” with
this glossary.

Each definition is followed by a bullet-point list of clarifying
details. These are not part of the definition itself.


## <a id="project"></a>Project

A collection of one or more computer files that serve some conceptually
unified purpose, which purpose changes and evolves over time, with the
history of that project being a valuable record.

*   We qualify the Fossil definition of this common word like this to
    set aside cases where a zip file or tarball would suffice. If you
    can pack your project up into such an archive once and be done with
    it, Fossil is overkill.

    And yet that is often just the beginning, since there is often a
    need for something to be changed, so now you have “version 2” of the
    archive file. If you can foresee yourself creating versioned archive
    files for your project, then you probably should be using Fossil for
    it instead, then using Fossil’s [zip] or [tarball] command to
    automatically produce archives of the latest version rather than
    manually produce and track versions of the archive. The web version
    of these commands ([`/zip`][zw] and [`/tarball`][tw]) are
    particularly useful for public distribution of the latest version of
    a project’s files.

*   Fossil was designed to host the SQLite software project, which is
    comprised of source code, makefiles, scripts, documentation files,
    and so forth. Fossil is also useful for many other purposes, such as
    a fiction book project where each chapter is held in a separate file
    and assembled into a finished whole deliverable.

*   We speak of projects being more than one file because even though
    Fossil can be made to track the history of a single file, it is far
    more often the case that when you get to something of a scale
    sufficient to be called a “project,” there is more than one
    version-tracked file involved, if not at the start, then certainly
    by the end of the project.

    We used the example of a fiction book above, with one chapter per
    file.  That implies scripts for combining those chapters into the
    finished book and converting that into PDF and ePub outputs, each of
    which benefit from being version-tracked.

    You could instead use a Word DOCX file for the entire book project,
    with these implicit scripts replaced by Word menu commands. Fossil
    will happily track that single file’s evolution for you, though
    there are [good reasons](./image-format-vs-repo-size.md) to *not* do
    that.

    Let us say you choose to solve the primary problems brought up in
    that document by using a format like AsciiDoc instead. You could
    still use a single file for the entire book’s prose content, but
    even then you’re still likely to want separate files for a style
    sheet, a script to convert the HTML to PDF and ePub in a reliably
    repeatable fashion, cover artwork files, instructions to the
    printing house, and so forth.

*   Fossil requires that all the files for a project be collected into a
    single directory hierarchy, owned by a single user with full rights
    to modify those files. Fossil is not a good choice for managing a
    project that has files scattered hither and yon all over the file
    system, nor of collections of files with complicated ownership and
    access rights.

    A good mental model for a Fossil project is a versioned zip file or
    tarball. If you cannot easily conceive of creating or extracting
    such an archive for your project, Fossil is probably not a good fit.

    As a counterexample, a project made of an operating system
    installation’s configuration file set is not a good use of Fossil,
    because you’ll have all of your OS’s *other* files intermixed.
    Worse, Fossil doesn’t track OS permissions, so even if you were to
    try to use Fossil as a system deployment tool by archiving versions
    of the OS configuration files and then unpacking them on a new
    system, the extracted project files would have read/write access by
    the user who did the extraction, which probably isn’t want you were
    wanting.

    And as a counter-counterexample, a project made of your user’s [Vim]
    configuration is a much better use of Fossil, because it’s all held
    within `~/.vim`, and your user has full rights to that subdirectory.

[tarball]: /help?cmd=tarball
[tw]:      /help?cmd=/tarball
[Vim]:     https://www.vim.org/
[zip]:     /help?cmd=zip
[zw]:      /help?cmd=/zip


## Repository <a id="repository" name="repo"></a>

A single file that contains all historical versions of all files in a
project, which can be [cloned] to other machines and
[synchronized][sync] with them. Jargon: repo.

*   A Fossil repo is similar to a zip archive in that it is a single
    file that stores compressed versions of one or more files.  Files can be
    extracted from the repo, and new files can be added to the repo,
    just as with a zip archive, but a Fossil repo has other capabilities
    above and beyond what simple archive formats can do.

*   Fossil does not care what you name your repository files, though
    we do suggest appending “`.fossil` as a standard extension. There is
    only one place in Fossil where that’s required, being the “directory
    name” form of [the `fossil server DIRECTORY` command][svrcmd].

*   Cloned and synced repos redundantly store all available information
    about that project, so if any one repo is lost, all of the cloned
    historical content of the project as of the last sync is preserved
    in each surviving repo.

    Each user generally clones the project repository down to each
    computer they use to participate in that project, and there is
    usually at least one central host for the project as well, so there
    is usually plenty of redundancy in any given Fossil-based project.

    That said, a Fossil repository clone is a backup only in a limited
    sense, because some information can’t be cloned, some doesn’t sync
    by default, and some data is neither clonable nor syncable. We cover
    these limitations and the workarounds for them in a separate
    document, [Backing Up a Remote Fossil Repository][backup].

*   Rather than be a backup, a Fossil repository clone is a
    communication method for coordinating work on the project among
    multiple machines and users: local work done against one repository
    is communicated up to its parent repository on the next sync, and
    work done on other repositories that were previously synced up to
    that parent get pulled down into the local repo clone.

    This bidirectional sync is automatic and on by default in Fossil.
    You can [disable it][asdis], or you can [push] or [pull]
    unidirectionally, if you wish.

    The Fossil philosophy is that all project information resides in
    each clone of the repository. In the ideal world, this would occur
    instantly and automatically, but in actual use, Fossil falls
    somewhat short of that mark. Some limitations are simply
    technological: a given clone may be temporarily out of communication
    with its parent repository, network delays exist, and so forth.
    Fossil is [an AP mode system][CAP]. (This is sometimes called
    “eventual consistency.”) Other cases come down to administrative
    necessity, as covered in [the backup doc][backup].

*   Fossil doesn’t require that you have redundant clones. Whether you
    do or not is a local decision based on usage needs, communication
    requirements, desire for backups, and so forth.

*   Fossil doesn’t care where the repositories are stored, but we
    recommend keeping them all in a single subdirectory such as
    "`~/fossils`" or "`%USERPROFILE%\Fossils`". A flat set of files
    suffices for simple purposes, but you may have use for something
    more complicated. This author uses a scheme like the following on
    mobile machines that shuttle between home and the office:

``` pikchr toggle indent
scale=0.8
box "~/museum/" fit
move right 0.1
line right dotted
move right 0.05
box invis "where one stores valuable fossils" ljust

arrow down 50% from first box.s then right 50%
box "work/" fit
move right 0.1
line dotted
move right 0.05
box invis "projects from $DAYJOB" ljust

arrow down 50% from 2nd vertex of previous arrow then right 50%
box "home/" fit
move right 0.1
line dotted right until even with previous line.end
move right 0.05
box invis "personal at-home projects" ljust

arrow down 50% from 2nd vertex of previous arrow then right 50%
box "other/" fit
move right 0.1
line dotted right until even with previous line.end
move right 0.05
box invis "clones of Fossil itself, SQLite, etc." ljust
```

[asdis]:   /help?cmd=autosync
[backup]: ./backup.md
[CAP]:    ./cap-theorem.md
[cloned]: /help?cmd=clone
[pull]:   /help?cmd=pull
[push]:   /help?cmd=push
[svrcmd]: /help?cmd=server
[sync]:   /help?cmd=sync


## Check-in <a id="check-in" name="ci"></a>

A version of the project’s files that have been committed to the
repository. It is a snapshot of the project at an instant in time, as
seen from a single [check-out’s](#co) perspective. Synonyms: version,
snapshot, revision, commit. Sometimes styled “`CHECKIN`”, especially in
command documentation where any [valid checkin name][ciname] can be
used.

*   The long list of synonyms is confusing to new Fossil users,
    particularly the noun sense of the word “commit,” but it’s easy
    enough to internalize the concepts. [Committing][commit] creates a
    *commit.*  It may also be said to create a checked-in *version* of a
    particular *revision* of the project’s files, thus creating an
    immutable *snapshot* of the project’s state at the time of the
    commit.  Fossil users find each of these different words for the
    same concept useful for expressive purposes among ourselves, but to
    Fossil proper, they all mean the same thing.

    You will find all of these synonyms used in the Fossil documentation.
    Some day we may settle on a single term, but it doesn’t seem likely.

*   Check-ins are immutable.

*   Check-ins exist only inside the repository. Contrast a
    [check-out](#co).

*   Check-ins may have [one or more names][ciname], but only the SHA
    hash is globally unique, across all time; we call it the check-in’s
    canonical name. The other names are either imprecise, contextual, or
    change their meaning over time and across [repositories](#repo).

[ciname]: ./checkin_names.wiki



## Check-out <a id="check-out" name="co"></a>

A set of files extracted from a [repository](#repo) that represent a
particular [check-in](#ci) of the [project](#project).

*   Unlike a check-in, a check-out is mutable. It may start out as a
    version of a particular check-in extracted from the repository, but
    the user is then free to make modifications to the checked-out
    files. Once those changes are formally [committed][commit], they
    become a new immutable check-in, derived from its parent check-in.

*   You can switch from one check-in to another within a check-out
    directory by passing those names to [the `fossil update`
    command][update].

*   Check-outs relate to repositories in a one-to-many fashion: it is
    common to have a single repo clone on a machine but to have it
    [open] in [multiple working directories][mwd]. Check-out directories
    are associated with the repos they were created from by settings
    stored in the check-out drectory. This is in the `.fslckout` file on
    POSIX type systems, but for historical compatibility reasons, it’s
    called `_FOSSIL_` by native Windows builds of Fossil.

    (Contrast the Cygwin and WSL Fossil binaries, which use POSIX file
    naming rules.)

*   In the same way that one cannot extract files from a zip archive
    without having a copy of that zip file, one cannot make check-outs
    without access to the repository file or a clone thereof.

*   Because a Fossil repository is a SQLite database file, the same
    rules for avoiding data corruption apply to it. In particular, it is
    [nearly a hard requirement][h2cflp] that the repository clone be on
    the same machine as the one where you make check-outs and the
    subsequent check-ins.

    That said, the relative locations of the repo and the check-out
    within the local file system are arbitrary.  The repository may be
    located inside the folder holding the check-out, but it certainly
    does not have to be, and it usually is not. As an example, [the
    Fossil plugin for Visual Studio Code][fpvsc] defaults to storing the
    repo clone within the project directory as a file called `.fsl`, but
    this is because VSCode’s version control features assume it’s being
    used with Git, where the repository is the `.git` subdirectory
    contents. With Fossil, [different check-out workflows][cwork] are
    preferred.

[commit]: /help?cmd=commit
[cwork]:  ./ckout-workflows.md
[h2cflp]: https://www.sqlite.org/howtocorrupt.html#_file_locking_problems
[fpvsc]:  https://marketplace.visualstudio.com/items?itemName=koog1000.fossil
[open]:   /help?cmd=open
[mwd]:    ./ckout-workflows.md#mcw
[update]: /help?cmd=update

<div style="height:50em" id="this-space-intentionally-left-blank"></div>
Changes to www/index.wiki.
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
      atomic even if interrupted by a power loss or system crash.
      Automatic [./selfcheck.wiki | self-checks] verify that all aspects of
      the repository are consistent prior to each commit.

  8.  <b>Free and Open-Source</b> - [../COPYRIGHT-BSD2.txt|2-clause BSD license].

<hr>
<h3>Latest Release: 2.16 ([/timeline?c=version-2.16|2021-07-02])</h3>

  *  [/uv/download.html|Download]
  *  [./changes.wiki#v2_16|Change Summary]
  *  [/timeline?p=version-2.16&bt=version-2.15&y=ci|Check-ins in version 2.16]
  *  [/timeline?df=version-2.16&y=ci|Check-ins derived from the 2.16 release]
  *  [/timeline?t=release|Timeline of all past releases]

<hr>
<h3>Quick Start</h3>

  1.  [/uv/download.html|Download] or install using a package manager or
      [./build.wiki|compile from sources].







|


|
|
|







81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
      atomic even if interrupted by a power loss or system crash.
      Automatic [./selfcheck.wiki | self-checks] verify that all aspects of
      the repository are consistent prior to each commit.

  8.  <b>Free and Open-Source</b> - [../COPYRIGHT-BSD2.txt|2-clause BSD license].

<hr>
<h3>Latest Release: 2.17 ([/timeline?c=version-2.17|2021-10-09])</h3>

  *  [/uv/download.html|Download]
  *  [./changes.wiki#v2_17|Change Summary]
  *  [/timeline?p=version-2.17&bt=version-2.16&y=ci|Check-ins in version 2.17]
  *  [/timeline?df=version-2.17&y=ci|Check-ins derived from the 2.17 release]
  *  [/timeline?t=release|Timeline of all past releases]

<hr>
<h3>Quick Start</h3>

  1.  [/uv/download.html|Download] or install using a package manager or
      [./build.wiki|compile from sources].
Changes to www/interwiki.md.
109
110
111
112
113
114
115
116
117
118
The intermap is stored in the CONFIG table of the repository database,
in entries with names of the form "<tt>interwiki:</tt><i>Tag</i>".  The
value for each such entry is a JSON string that defines the base URL
and extensions for Hash and Wiki links.

## See Also

  1. [](https://en.wikipedia.org/wiki/Interwiki_links)
  2. [](https://www.mediawiki.org/wiki/Manual:Interwiki)
  3. [](https://duckduckgo.com/?q=interwiki+links&ia=web)







<
|
|
109
110
111
112
113
114
115

116
117
The intermap is stored in the CONFIG table of the repository database,
in entries with names of the form "<tt>interwiki:</tt><i>Tag</i>".  The
value for each such entry is a JSON string that defines the base URL
and extensions for Hash and Wiki links.

## See Also


  1. [](https://www.mediawiki.org/wiki/Manual:Interwiki)
  2. [](https://duckduckgo.com/?q=interwiki+links&ia=web)
Changes to www/mkindex.tcl.
60
61
62
63
64
65
66

67
68
69
70
71
72
73
74
75
  fiveminutes.wiki {Up and Running in 5 Minutes as a Single User}
  forum.wiki {Fossil Forums}
  foss-cklist.wiki {Checklist For Successful Open-Source Projects}
  fossil-from-msvc.wiki {Integrating Fossil in the Microsoft Express 2010 IDE}
  fossil-is-not-relational.md {Introduction to the (Non-relational) Fossil Data Model}
  fossil_prompt.wiki {Fossilized Bash Prompt}
  fossil-v-git.wiki {Fossil Versus Git}

  globs.md {File Name Glob Patterns}
  gitusers.md {Git to Fossil Translation Guide}
  grep.md {Fossil grep vs POSIX grep}
  hacker-howto.wiki {Hacker How-To}
  hacker-howto.wiki {Fossil Developers Guide}
  hashes.md {Hashes: Fossil Artifact Identification}
  hashpolicy.wiki {Hash Policy: Choosing Between SHA1 and SHA3-256}
  /help {Lists of Commands and Webpages}
  hints.wiki {Fossil Tips And Usage Hints}







>

|







60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
  fiveminutes.wiki {Up and Running in 5 Minutes as a Single User}
  forum.wiki {Fossil Forums}
  foss-cklist.wiki {Checklist For Successful Open-Source Projects}
  fossil-from-msvc.wiki {Integrating Fossil in the Microsoft Express 2010 IDE}
  fossil-is-not-relational.md {Introduction to the (Non-relational) Fossil Data Model}
  fossil_prompt.wiki {Fossilized Bash Prompt}
  fossil-v-git.wiki {Fossil Versus Git}
  gitusers.md {Git to Fossil Translation Guide}
  globs.md {File Name Glob Patterns}
  glossary.md {Glossary}
  grep.md {Fossil grep vs POSIX grep}
  hacker-howto.wiki {Hacker How-To}
  hacker-howto.wiki {Fossil Developers Guide}
  hashes.md {Hashes: Fossil Artifact Identification}
  hashpolicy.wiki {Hash Policy: Choosing Between SHA1 and SHA3-256}
  /help {Lists of Commands and Webpages}
  hints.wiki {Fossil Tips And Usage Hints}
Changes to www/newrepo.wiki.
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
a branch or experimental code.

Making your repository available over the web is trivial to do. We
assume you have some web space where you can store your fossil file
and run a CGI script. If not, then this option is not for you. If
you do, then here's how...

Copy copy the fossil repository file to your web server (it doesn't
matter where, really).

In your <tt>cgi-bin</tt> (or equivalent) directory, create a file
which looks like this:

<verbatim>
#!/path/to/fossil







|







110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
a branch or experimental code.

Making your repository available over the web is trivial to do. We
assume you have some web space where you can store your fossil file
and run a CGI script. If not, then this option is not for you. If
you do, then here's how...

Copy the fossil repository file to your web server (it doesn't
matter where, really).

In your <tt>cgi-bin</tt> (or equivalent) directory, create a file
which looks like this:

<verbatim>
#!/path/to/fossil
Changes to www/password.wiki.
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
Fossil self-hosting repository.  Then the value of USER.PW
for alice would be the SHA1 hash of

<blockquote>
CE59BB9F186226D80E49D1FA2DB29F935CCA0333/alice/asdfg
</blockquote>

That hash value is "f1b699cc9af3eeb98e5de244ca7802ae38e77bae".  Note
that by including the project-code and the login as part of the hash,
a different USER.PW value results even if two or more users on the
repository select the same "asdfg" password or if user alice reuses the
same password on multiple projects.

Whenever a password is changed using the web interface or using the
"user" command-line method, the new password is stored using the SHA1
encoding.  Thus, cleartext passwords will gradually migrate to become
SHA1 passwords.  All remaining cleartext passwords can be converted to
SHA1 passwords using the following command:








<
|
|
|
|







24
25
26
27
28
29
30

31
32
33
34
35
36
37
38
39
40
41
Fossil self-hosting repository.  Then the value of USER.PW
for alice would be the SHA1 hash of

<blockquote>
CE59BB9F186226D80E49D1FA2DB29F935CCA0333/alice/asdfg
</blockquote>


Note that by including the project-code and the login as part of the
hash, a different USER.PW value results even if two or more users on
the repository select the same "asdfg" password or if user alice
reuses the same password on multiple projects.

Whenever a password is changed using the web interface or using the
"user" command-line method, the new password is stored using the SHA1
encoding.  Thus, cleartext passwords will gradually migrate to become
SHA1 passwords.  All remaining cleartext passwords can be converted to
SHA1 passwords using the following command:

75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
address of the client is stored in the USER.COOKIE and USER.IPADDR fields
of the USER table on the server.
The USER.CEXPIRE field holds an expiration date
for the cookie, encoded as a Julian day number.  On all subsequent
HTTP requests, the cookie value is matched against the USER table to
enable access to the repository.

A login cookie will only work if the IP address matches.  This feature
is designed to make it more difficult for an attacker to sniff the cookie
and take over the connection.  A cookie-sniffing attack will only work
if the attacker is able to send and receive from the same IP address as
the original login.  However, we found that doing an exact IP match
caused problems for some users who are behind proxy firewalls where the proxy
might use a different IP address for each query.  To work around this
problem, newer versions of fossil only check the first 16 bits of the
32-bit IP address.  This makes a cookie sniffing attack easier since now
the attacker only has to send and receive from any IP address in a range
of IPs that are similar to the initial login.  But that is seen as an
acceptable compromise in exchange for ease of use.  If higher security
is really needed, then HTTPS can be used instead of HTTP.

Note that in order to log into a Fossil server, it is necessary to
write information into the repository database.  Hence, login is not
possible on a Fossil repository with a read-only database file.

The user password is sent over the wire as cleartext on the initial
login attempt.  The plan moving forward is to compute the SHA1 hash of
the password on the client using JavaScript and then send only the hash







<
<
<
<
<
<
<
<
<
<
<
<
<
<







74
75
76
77
78
79
80














81
82
83
84
85
86
87
address of the client is stored in the USER.COOKIE and USER.IPADDR fields
of the USER table on the server.
The USER.CEXPIRE field holds an expiration date
for the cookie, encoded as a Julian day number.  On all subsequent
HTTP requests, the cookie value is matched against the USER table to
enable access to the repository.















Note that in order to log into a Fossil server, it is necessary to
write information into the repository database.  Hence, login is not
possible on a Fossil repository with a read-only database file.

The user password is sent over the wire as cleartext on the initial
login attempt.  The plan moving forward is to compute the SHA1 hash of
the password on the client using JavaScript and then send only the hash
Changes to www/permutedindex.html.
67
68
69
70
71
72
73

74
75
76
77
78
79
80
<li><a href="selfhost.wiki">Fossil Self Hosting Repositories</a></li>
<li><a href="settings.wiki">Fossil Settings</a></li>
<li><a href="hints.wiki">Fossil Tips And Usage Hints</a></li>
<li><a href="fossil-v-git.wiki">Fossil Versus Git</a></li>
<li><a href="fossil_prompt.wiki">Fossilized Bash Prompt</a></li>
<li><a href="faq.wiki">Frequently Asked Questions</a></li>
<li><a href="gitusers.md">Git to Fossil Translation Guide</a></li>

<li><a href="hacker-howto.wiki">Hacker How-To</a></li>
<li><a href="adding_code.wiki">Hacking Fossil</a></li>
<li><a href="hashpolicy.wiki">Hash Policy: Choosing Between SHA1 and SHA3-256</a></li>
<li><a href="hashes.md">Hashes: Fossil Artifact Identification</a></li>
<li><a href="index.wiki">Home Page</a></li>
<li><a href="aboutcgi.wiki">How CGI Works In Fossil</a></li>
<li><a href="aboutdownload.wiki">How The Download Page Works</a></li>







>







67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
<li><a href="selfhost.wiki">Fossil Self Hosting Repositories</a></li>
<li><a href="settings.wiki">Fossil Settings</a></li>
<li><a href="hints.wiki">Fossil Tips And Usage Hints</a></li>
<li><a href="fossil-v-git.wiki">Fossil Versus Git</a></li>
<li><a href="fossil_prompt.wiki">Fossilized Bash Prompt</a></li>
<li><a href="faq.wiki">Frequently Asked Questions</a></li>
<li><a href="gitusers.md">Git to Fossil Translation Guide</a></li>
<li><a href="glossary.md">Glossary</a></li>
<li><a href="hacker-howto.wiki">Hacker How-To</a></li>
<li><a href="adding_code.wiki">Hacking Fossil</a></li>
<li><a href="hashpolicy.wiki">Hash Policy: Choosing Between SHA1 and SHA3-256</a></li>
<li><a href="hashes.md">Hashes: Fossil Artifact Identification</a></li>
<li><a href="index.wiki">Home Page</a></li>
<li><a href="aboutcgi.wiki">How CGI Works In Fossil</a></li>
<li><a href="aboutdownload.wiki">How The Download Page Works</a></li>
Changes to www/quickstart.wiki.
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
</blockquote>

<h2 id="workflow" name="fslclone">General Work Flow</h2>

<p>Fossil works with repository files (a database in a single file with the project's
complete history) and with checked-out local trees (the working directory
you use to do your work). 
(See [./whyusefossil.wiki#definitions | definitions] for more background.)
The workflow looks like this:</p>

<ul>
    <li>Create or clone a repository file.  ([/help/init|fossil init] or
        [/help/clone | fossil clone])
    <li>Check out a local tree.  ([/help/open | fossil open])
    <li>Perform operations on the repository (including repository







|







23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
</blockquote>

<h2 id="workflow" name="fslclone">General Work Flow</h2>

<p>Fossil works with repository files (a database in a single file with the project's
complete history) and with checked-out local trees (the working directory
you use to do your work). 
(See [./glossary.md | the glossary] for more background.)
The workflow looks like this:</p>

<ul>
    <li>Create or clone a repository file.  ([/help/init|fossil init] or
        [/help/clone | fossil clone])
    <li>Check out a local tree.  ([/help/open | fossil open])
    <li>Perform operations on the repository (including repository
Changes to www/server/any/cgi.md.
66
67
68
69
70
71
72



















73
Once deployed, a URL like: <b>http://mydomain.org/cgi-bin/repo/XYZ</b>
will serve up the repository `/home/fossil/repos/XYZ.fossil` if it
exists.

Additional options available to the CGI script are [documented
separately](../../cgi.wiki).




















*[Return to the top-level Fossil server article.](../)*







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>

66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
Once deployed, a URL like: <b>http://mydomain.org/cgi-bin/repo/XYZ</b>
will serve up the repository `/home/fossil/repos/XYZ.fossil` if it
exists.

Additional options available to the CGI script are [documented
separately](../../cgi.wiki).

#### CGI with Apache behind an Nginx proxy

For the case where the Fossil repositories live on a computer, itself behind
an Internet-facing machine that employs Nginx to reverse proxy HTTP(S) requests
and take care of the TLS part of the connections in a transparent manner for
the downstream web servers, the CGI parameter `HTTPS=on` might not be set.
However, Fossil in CGI mode needs it in order to generate the correct links.

Apache can be instructed to pass this parameter further to the CGI scripts for
TLS connections with a stanza like

        SetEnvIf X-Forwarded-Proto "https" HTTPS=on
        
in its config file section for CGI, provided that

        proxy_set_header  X-Forwarded-Proto $scheme;
        
has been be added in the relevant proxying section of the Nginx config file.

*[Return to the top-level Fossil server article.](../)*
Changes to www/sync.wiki.
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
the client because the client login lacks the "write-unversioned"
permission.</p>

<li><p><b>uv-push-ok</b></i>
<p>A server sends the uv-push-ok pragma to the client in response
to a uv-hash pragma with a mismatched content hash argument.  This
pragma indicates that there are differences in unversioned content
between the client and server and that content can only be transferred
in either direction.  The server is willing to accept content from
the client because the client login has the "write-unversioned"
permission.</p>

<li><p><b>ci-lock</b> <i>CHECKIN-HASH CLIENT-ID</i></p>
<p>A client sends the "ci-lock" pragma to the server to indicate
that it is about to add a new check-in as a child of the
CHECKIN-HASH check-in and on the same branch as CHECKIN-HASH.
If some other client has already indicated that it was also
trying to commit against CHECKIN-HASH, that indicates that a
fork is about to occur, and the server will reply with
a "ci-lock-fail" pragma (see below).  Check-in locks
automatically expire when the check-in actually occurs, or
after a timeout (currently 24-hours but subject to change).

<li><p><b>ci-lock-fail</b> <i>LOGIN MTIME</i></p>
<p>When a server receives two or more "ci-lock" pragma messages
for the same check-in but from different clients, the second a
subsequent ci-lock will provoke a ci-lock-fail pragma in the
reply to let the client know that it if continues with the
check-in it will likely generate a fork.  The LOGIN and MTIME







|













|







702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
the client because the client login lacks the "write-unversioned"
permission.</p>

<li><p><b>uv-push-ok</b></i>
<p>A server sends the uv-push-ok pragma to the client in response
to a uv-hash pragma with a mismatched content hash argument.  This
pragma indicates that there are differences in unversioned content
between the client and server and that content can be transferred
in either direction.  The server is willing to accept content from
the client because the client login has the "write-unversioned"
permission.</p>

<li><p><b>ci-lock</b> <i>CHECKIN-HASH CLIENT-ID</i></p>
<p>A client sends the "ci-lock" pragma to the server to indicate
that it is about to add a new check-in as a child of the
CHECKIN-HASH check-in and on the same branch as CHECKIN-HASH.
If some other client has already indicated that it was also
trying to commit against CHECKIN-HASH, that indicates that a
fork is about to occur, and the server will reply with
a "ci-lock-fail" pragma (see below).  Check-in locks
automatically expire when the check-in actually occurs, or
after a timeout (currently one minute but subject to change).

<li><p><b>ci-lock-fail</b> <i>LOGIN MTIME</i></p>
<p>When a server receives two or more "ci-lock" pragma messages
for the same check-in but from different clients, the second a
subsequent ci-lock will provoke a ci-lock-fail pragma in the
reply to let the client know that it if continues with the
check-in it will likely generate a fork.  The LOGIN and MTIME
Changes to www/userlinks.wiki.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<title>Links For Fossil Users:</title>

  *  [./permutedindex.html | Documentation index] with [/search?c=d | full text search].
  *  [./reviews.wiki | Testimonials] from satisfied Fossil users and
     [./quotes.wiki | Quotes] about Fossil and other DVCSes.
  *  [./faq.wiki | Frequently Asked Questions]
  *  The [./concepts.wiki | concepts] behind Fossil.
     [./whyusefossil.wiki#definitions | Another viewpoint].
  *  [./quickstart.wiki | Quick Start] guide to using Fossil.
  *  [./qandc.wiki | Questions &amp; Criticisms] directed at Fossil.
  *  [./build.wiki | Compiling and Installing]
  *  Fossil supports [./embeddeddoc.wiki | embedded documentation]
     that is versioned along with project source code.
  *  Fossil uses an [./fileformat.wiki | enduring file format] that is
     designed to be readable, searchable, and extensible by people







|







1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<title>Links For Fossil Users:</title>

  *  [./permutedindex.html | Documentation index] with [/search?c=d | full text search].
  *  [./reviews.wiki | Testimonials] from satisfied Fossil users and
     [./quotes.wiki | Quotes] about Fossil and other DVCSes.
  *  [./faq.wiki | Frequently Asked Questions]
  *  The [./concepts.wiki | concepts] behind Fossil.
     [./glossary.md | Another viewpoint].
  *  [./quickstart.wiki | Quick Start] guide to using Fossil.
  *  [./qandc.wiki | Questions &amp; Criticisms] directed at Fossil.
  *  [./build.wiki | Compiling and Installing]
  *  Fossil supports [./embeddeddoc.wiki | embedded documentation]
     that is versioned along with project source code.
  *  Fossil uses an [./fileformat.wiki | enduring file format] that is
     designed to be readable, searchable, and extensible by people
Changes to www/whyusefossil.wiki.
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
     <li>Avoid wasting time doing manual file copying
     <li>Avoid human errors during manual backups
     </ol>
  </ol>

<p id="definitions"><b>II. Definitions</b></p>

<ul>
<li><p><b>Project</b> &rarr;
  a collection of computer files that serve some common
  purpose.  Often the project is a software application and the
  individual files are source code together with makefiles, scripts, and
  "README.txt" files.  Other examples of projects include books or
  manuals in which each chapter or section is held in a separate file.
 <ul>
 <li><p>Projects change and evolve.  The whole purpose of version
     control is to track and manage that evolution.
 <li><p>Most projects contain many files, but it is possible
     to have a project consisting of just a single file.
 <li><p>Fossil requires that
     all the files for a project must be collected into a single
     directory hierarchy - a single folder possibly with layers
     of subfolders.  Fossil is not a good choice for managing a
     project that has files scattered hither and yon all over
     the disk.  In other words, Fossil only works for projects
     where the files are laid out such that they can be archived
     into a ZIP file or tarball.
 </ul>
<li><p><b>Repository</b> &rarr;
 (also called "repo") a single file that contains
 all historical versions of all files in a project.  A repo is similar
 to a ZIP archive in that it is a single file that stores compressed
 versions of many other files.  Files can be extracted from the
 repo and new files can be added to the repo, just as with a ZIP
 archive.  But a repo has other capabilities above and beyond
 what a ZIP archive can do.
 <ul>
 <li><p>Fossil does not care what you name your repository files,
     though names ending with ".fossil" are recommended.
 <li><p>A single project typically has multiple, redundant repositories on
 separate machines.
 <li><p>All repositories stay synchronized with one another by exchanging
     information via HTTP or SSH.
 <li><p>All repos for a single project redundantly store all information
     about that project.  So if any one repo is lost due to a disk
     crash, all content is preserved in the surviving repos.
 <li><p>The usual arrangement is one repository per user.  And since
     most users these days have their own computer, that means one
     repository per computer.  But this is not a requirement.  It is
     ok to have multiple copies of the same repository on the same
     computer.
 <li><p>Fossil works fine with just a single copy of the repository.
     But in that case there is no redundancy.  If that one repository
     file is lost due to a hardware malfunction, then there is no way
     to recover the project.
 <li><p>Best practice is to keep all repositories for a user in a single
     folder.  Folders such as "~/Fossils" or "%USERPROFILE%\Fossils"
     are recommended.  Fossil itself does not care where the repositories
     are stored.  Nor does Fossil require repositories to be
     kept in the same folder.  But it is easier to organize your work
     if all repositories are kept in the same place.
 </ul>
<li><p><b>Check-out</b> &rarr;
 a set of files that have been extracted from a
 repository and that represent a particular version or snapshot of
 the project.
 <ul>
 <li><p>Check-outs must be on the same computer as the repository from
     which they are extracted.  This is just like with a ZIP archive:
     one must have the ZIP archive file on the local machine before
     extracting files from ZIP archive.
 <li><p>There can be multiple check-outs (in different folders) from
     the same repository.
 <li><p>The repository must be on the same computer as the check-out, but
     the relative locations of the repo and the check-out are arbitrary.
     The repository may be located inside the folder holding the
     check-out, but it certainly does not have to be and usually is
     not.
 <li><p>A special file exists in every check-out that tells Fossil from
 which repository the check-out was extracted, and which version of
 the project the check-out represents.  This is the ".fslckout" file
 on unix systems or the "_FOSSIL_" file on Windows.
 </ul>
<li><p><b>Check-in</b> &rarr;
 another name for a particular version of the project.
 A check-in is a collection of files inside of a repository that
 represent a snapshot of the project for an instant in time.
 Check-ins exist only inside of the repository.  This contrasts with
 a check-out which is a collection of files outside of the repository.
 <ul>
 <li><p>Every check-out knows the check-in from which it was derived.
     But check-outs might have been edited and so might not exactly
     match their associated check-in.
 <li><p>Check-ins are immutable.  They can never be changed.  But
     check-outs are collections of ordinary files on disk.  The
     files of a check-out can be edited just like any other file.
 <li><p>A check-in can be thought of as an historical snapshot of a
     check-out.
 <li><p>"Check-in", "version", "snapshot", and "revision" are synonyms.
 <li><p> When used as a noun, the word "commit" is another synonym
     for "check-in".  When used as a verb, the word "commit"
     means to create a new check-in.
 </ul>
</ul>

<p><b>III. Basic Fossil commands</b>

 <ul>
 <li><p><b>clone</b> &rarr;
     Make a copy of a repository.  The original repository
     is usually (but not always) on a remote machine and the copy is on







<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
|
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<







37
38
39
40
41
42
43

































44































































45
46
47
48
49
50
51
     <li>Avoid wasting time doing manual file copying
     <li>Avoid human errors during manual backups
     </ol>
  </ol>

<p id="definitions"><b>II. Definitions</b></p>


































Moved to [./glossary.md | a separate document].
































































<p><b>III. Basic Fossil commands</b>

 <ul>
 <li><p><b>clone</b> &rarr;
     Make a copy of a repository.  The original repository
     is usually (but not always) on a remote machine and the copy is on