/ Check-in [0e14fe1b]
Login

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

Overview
Comment:Merge all recent trunk enhancements into the apple-osx branch.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | apple-osx
Files: files | file ages | folders
SHA1: 0e14fe1b986abf1449d727fbe04c6a939ed209a2
User & Date: drh 2017-01-27 16:39:38
Context
2017-02-04
15:29
Merge recent trunk enhancements. check-in: 6c3f0902 user: drh tags: apple-osx
2017-01-27
16:39
Merge all recent trunk enhancements into the apple-osx branch. check-in: 0e14fe1b user: drh tags: apple-osx
13:14
Alternative ICU fix (compare to check-in [50e60cb4]) that avoids casting integers to pointers. check-in: d9752c8f user: drh tags: trunk
2017-01-06
17:01
Merge the changes for version 3.16.2. check-in: c59c8880 user: drh tags: apple-osx
Changes
Hide Diffs Side-by-Side Diffs Ignore Whitespace Patch

Changes to Makefile.in.

  1186   1186   
  1187   1187   LogEst$(TEXE):	$(TOP)/tool/logest.c sqlite3.h
  1188   1188   	$(LTLINK) -I. -o $@ $(TOP)/tool/logest.c
  1189   1189   
  1190   1190   wordcount$(TEXE):	$(TOP)/test/wordcount.c sqlite3.lo
  1191   1191   	$(LTLINK) -o $@ $(TOP)/test/wordcount.c sqlite3.lo $(TLIBS)
  1192   1192   
  1193         -speedtest1$(TEXE):	$(TOP)/test/speedtest1.c sqlite3.lo
  1194         -	$(LTLINK) -o $@ $(TOP)/test/speedtest1.c sqlite3.lo $(TLIBS)
         1193  +speedtest1$(TEXE):	$(TOP)/test/speedtest1.c sqlite3.c
         1194  +	$(LTLINK) $(ST_OPT) -o $@ $(TOP)/test/speedtest1.c sqlite3.c $(TLIBS)
         1195  +
         1196  +KV_OPT += -DSQLITE_DIRECT_OVERFLOW_READ
         1197  +
         1198  +kvtest$(TEXE):	$(TOP)/test/kvtest.c sqlite3.c
         1199  +	$(LTLINK) $(KV_OPT) -o $@ $(TOP)/test/kvtest.c sqlite3.c $(TLIBS)
  1195   1200   
  1196   1201   rbu$(EXE): $(TOP)/ext/rbu/rbu.c $(TOP)/ext/rbu/sqlite3rbu.c sqlite3.lo 
  1197   1202   	$(LTLINK) -I. -o $@ $(TOP)/ext/rbu/rbu.c sqlite3.lo $(TLIBS)
  1198   1203   
  1199   1204   loadfts$(EXE): $(TOP)/tool/loadfts.c libsqlite3.la
  1200   1205   	$(LTLINK) $(TOP)/tool/loadfts.c libsqlite3.la -o $@ $(TLIBS)
  1201   1206   

Changes to VERSION.

     1         -3.16.2
            1  +3.17.0

Changes to configure.

     1      1   #! /bin/sh
     2      2   # Guess values for system-dependent variables and create Makefiles.
     3         -# Generated by GNU Autoconf 2.69 for sqlite 3.16.2.
            3  +# Generated by GNU Autoconf 2.69 for sqlite 3.17.0.
     4      4   #
     5      5   #
     6      6   # Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc.
     7      7   #
     8      8   #
     9      9   # This configure script is free software; the Free Software Foundation
    10     10   # gives unlimited permission to copy, distribute and modify it.
................................................................................
   722    722   subdirs=
   723    723   MFLAGS=
   724    724   MAKEFLAGS=
   725    725   
   726    726   # Identity of this package.
   727    727   PACKAGE_NAME='sqlite'
   728    728   PACKAGE_TARNAME='sqlite'
   729         -PACKAGE_VERSION='3.16.2'
   730         -PACKAGE_STRING='sqlite 3.16.2'
          729  +PACKAGE_VERSION='3.17.0'
          730  +PACKAGE_STRING='sqlite 3.17.0'
   731    731   PACKAGE_BUGREPORT=''
   732    732   PACKAGE_URL=''
   733    733   
   734    734   # Factoring default headers for most tests.
   735    735   ac_includes_default="\
   736    736   #include <stdio.h>
   737    737   #ifdef HAVE_SYS_TYPES_H
................................................................................
  1459   1459   #
  1460   1460   # Report the --help message.
  1461   1461   #
  1462   1462   if test "$ac_init_help" = "long"; then
  1463   1463     # Omit some internal or obsolete options to make the list less imposing.
  1464   1464     # This message is too long to be a string in the A/UX 3.1 sh.
  1465   1465     cat <<_ACEOF
  1466         -\`configure' configures sqlite 3.16.2 to adapt to many kinds of systems.
         1466  +\`configure' configures sqlite 3.17.0 to adapt to many kinds of systems.
  1467   1467   
  1468   1468   Usage: $0 [OPTION]... [VAR=VALUE]...
  1469   1469   
  1470   1470   To assign environment variables (e.g., CC, CFLAGS...), specify them as
  1471   1471   VAR=VALUE.  See below for descriptions of some of the useful variables.
  1472   1472   
  1473   1473   Defaults for the options are specified in brackets.
................................................................................
  1524   1524     --build=BUILD     configure for building on BUILD [guessed]
  1525   1525     --host=HOST       cross-compile to build programs to run on HOST [BUILD]
  1526   1526   _ACEOF
  1527   1527   fi
  1528   1528   
  1529   1529   if test -n "$ac_init_help"; then
  1530   1530     case $ac_init_help in
  1531         -     short | recursive ) echo "Configuration of sqlite 3.16.2:";;
         1531  +     short | recursive ) echo "Configuration of sqlite 3.17.0:";;
  1532   1532      esac
  1533   1533     cat <<\_ACEOF
  1534   1534   
  1535   1535   Optional Features:
  1536   1536     --disable-option-checking  ignore unrecognized --enable/--with options
  1537   1537     --disable-FEATURE       do not include FEATURE (same as --enable-FEATURE=no)
  1538   1538     --enable-FEATURE[=ARG]  include FEATURE [ARG=yes]
................................................................................
  1648   1648       cd "$ac_pwd" || { ac_status=$?; break; }
  1649   1649     done
  1650   1650   fi
  1651   1651   
  1652   1652   test -n "$ac_init_help" && exit $ac_status
  1653   1653   if $ac_init_version; then
  1654   1654     cat <<\_ACEOF
  1655         -sqlite configure 3.16.2
         1655  +sqlite configure 3.17.0
  1656   1656   generated by GNU Autoconf 2.69
  1657   1657   
  1658   1658   Copyright (C) 2012 Free Software Foundation, Inc.
  1659   1659   This configure script is free software; the Free Software Foundation
  1660   1660   gives unlimited permission to copy, distribute and modify it.
  1661   1661   _ACEOF
  1662   1662     exit
................................................................................
  2067   2067     eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
  2068   2068   
  2069   2069   } # ac_fn_c_check_header_mongrel
  2070   2070   cat >config.log <<_ACEOF
  2071   2071   This file contains any messages produced by compilers while
  2072   2072   running configure, to aid debugging if configure makes a mistake.
  2073   2073   
  2074         -It was created by sqlite $as_me 3.16.2, which was
         2074  +It was created by sqlite $as_me 3.17.0, which was
  2075   2075   generated by GNU Autoconf 2.69.  Invocation command line was
  2076   2076   
  2077   2077     $ $0 $@
  2078   2078   
  2079   2079   _ACEOF
  2080   2080   exec 5>>config.log
  2081   2081   {
................................................................................
 12147  12147   test $as_write_fail = 0 && chmod +x $CONFIG_STATUS || ac_write_fail=1
 12148  12148   
 12149  12149   cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
 12150  12150   # Save the log message, to keep $0 and so on meaningful, and to
 12151  12151   # report actual input values of CONFIG_FILES etc. instead of their
 12152  12152   # values after options handling.
 12153  12153   ac_log="
 12154         -This file was extended by sqlite $as_me 3.16.2, which was
        12154  +This file was extended by sqlite $as_me 3.17.0, which was
 12155  12155   generated by GNU Autoconf 2.69.  Invocation command line was
 12156  12156   
 12157  12157     CONFIG_FILES    = $CONFIG_FILES
 12158  12158     CONFIG_HEADERS  = $CONFIG_HEADERS
 12159  12159     CONFIG_LINKS    = $CONFIG_LINKS
 12160  12160     CONFIG_COMMANDS = $CONFIG_COMMANDS
 12161  12161     $ $0 $@
................................................................................
 12213  12213   
 12214  12214   Report bugs to the package provider."
 12215  12215   
 12216  12216   _ACEOF
 12217  12217   cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
 12218  12218   ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"
 12219  12219   ac_cs_version="\\
 12220         -sqlite config.status 3.16.2
        12220  +sqlite config.status 3.17.0
 12221  12221   configured by $0, generated by GNU Autoconf 2.69,
 12222  12222     with options \\"\$ac_cs_config\\"
 12223  12223   
 12224  12224   Copyright (C) 2012 Free Software Foundation, Inc.
 12225  12225   This config.status script is free software; the Free Software Foundation
 12226  12226   gives unlimited permission to copy, distribute and modify it."
 12227  12227   

Changes to ext/fts5/fts5_expr.c.

  1597   1597     char *z = 0;
  1598   1598   
  1599   1599     memset(&sCtx, 0, sizeof(TokenCtx));
  1600   1600     sCtx.pPhrase = pAppend;
  1601   1601   
  1602   1602     rc = fts5ParseStringFromToken(pToken, &z);
  1603   1603     if( rc==SQLITE_OK ){
  1604         -    int flags = FTS5_TOKENIZE_QUERY | (bPrefix ? FTS5_TOKENIZE_QUERY : 0);
         1604  +    int flags = FTS5_TOKENIZE_QUERY | (bPrefix ? FTS5_TOKENIZE_PREFIX : 0);
  1605   1605       int n;
  1606   1606       sqlite3Fts5Dequote(z);
  1607   1607       n = (int)strlen(z);
  1608   1608       rc = sqlite3Fts5Tokenize(pConfig, flags, z, n, &sCtx, fts5ParseTokenize);
  1609   1609     }
  1610   1610     sqlite3_free(z);
  1611   1611     if( rc || (rc = sCtx.rc) ){

Changes to ext/fts5/test/fts5synonym.test.

   148    148   reset_db
   149    149   fts5_tclnum_register db
   150    150   
   151    151   foreach {tn expr res} {
   152    152     1  {abc}                           {"abc"}
   153    153     2  {one}                           {"one"|"i"|"1"}
   154    154     3  {3}                             {"3"|"iii"|"three"}
   155         -  4  {3*}                            {"3"|"iii"|"three" *}
          155  +  4  {3*}                            {"3" *}
   156    156   } {
   157    157     do_execsql_test 4.1.$tn {
   158    158       SELECT fts5_expr($expr, 'tokenize=tclnum')
   159    159     } [list $res]
   160    160   }
   161    161   
   162    162   do_execsql_test 4.2.1 {

Changes to ext/fts5/test/fts5tokenizer.test.

   257    257     INSERT INTO e6 VALUES('theAquickBbrownCfoxDjumpedWoverXtheYlazyZdog');
   258    258     CREATE VIRTUAL TABLE e7 USING fts5vocab(e6, 'row');
   259    259     SELECT term FROM e7;
   260    260     ROLLBACK;
   261    261   } {
   262    262     brown dog fox jump lazi over quick the
   263    263   }
          264  +
          265  +#-------------------------------------------------------------------------
          266  +# Check that the FTS5_TOKENIZE_PREFIX flag is passed to the tokenizer
          267  +# implementation.
          268  +#
          269  +reset_db
          270  +proc tcl_create {args} { return "tcl_tokenize" }
          271  +sqlite3_fts5_create_tokenizer db tcl tcl_create
          272  +set ::flags [list]
          273  +proc tcl_tokenize {tflags text} {
          274  +  lappend ::flags $tflags
          275  +  foreach {w iStart iEnd} [fts5_tokenize_split $text] {
          276  +    sqlite3_fts5_token $w $iStart $iEnd
          277  +  }
          278  +}
          279  +
          280  +do_execsql_test 9.1.1 {
          281  +  CREATE VIRTUAL TABLE t1 USING fts5(a, tokenize=tcl);
          282  +  INSERT INTO t1 VALUES('abc');
          283  +  INSERT INTO t1 VALUES('xyz');
          284  +} {}
          285  +do_test 9.1.2 { set ::flags } {document document}
          286  +
          287  +set ::flags [list]
          288  +do_execsql_test 9.2.1 { SELECT * FROM t1('abc'); } {abc}
          289  +do_test 9.2.2 { set ::flags } {query}
          290  +
          291  +set ::flags [list]
          292  +do_execsql_test 9.3.1 { SELECT * FROM t1('ab*'); } {abc}
          293  +do_test 9.3.2 { set ::flags } {prefixquery}
          294  +
          295  +set ::flags [list]
          296  +do_execsql_test 9.4.1 { SELECT * FROM t1('"abc xyz" *'); } {}
          297  +do_test 9.4.2 { set ::flags } {prefixquery}
          298  +
          299  +set ::flags [list]
          300  +do_execsql_test 9.5.1 { SELECT * FROM t1('"abc xyz*"'); } {}
          301  +do_test 9.5.2 { set ::flags } {query}
          302  +
   264    303   
   265    304   finish_test
   266    305   

Changes to ext/icu/icu.c.

   489    489     }
   490    490   }
   491    491   
   492    492   /*
   493    493   ** Register the ICU extension functions with database db.
   494    494   */
   495    495   int sqlite3IcuInit(sqlite3 *db){
   496         -  struct IcuScalar {
          496  +  static const struct IcuScalar {
   497    497       const char *zName;                        /* Function name */
   498         -    int nArg;                                 /* Number of arguments */
   499         -    int enc;                                  /* Optimal text encoding */
   500         -    void *pContext;                           /* sqlite3_user_data() context */
          498  +    unsigned char nArg;                       /* Number of arguments */
          499  +    unsigned short enc;                       /* Optimal text encoding */
          500  +    unsigned char iContext;                   /* sqlite3_user_data() context */
   501    501       void (*xFunc)(sqlite3_context*,int,sqlite3_value**);
   502    502     } scalars[] = {
   503         -    {"regexp", 2, SQLITE_ANY|SQLITE_DETERMINISTIC,          0, icuRegexpFunc},
   504         -
   505         -    {"lower",  1, SQLITE_UTF16|SQLITE_DETERMINISTIC,        0, icuCaseFunc16},
   506         -    {"lower",  2, SQLITE_UTF16|SQLITE_DETERMINISTIC,        0, icuCaseFunc16},
   507         -    {"upper",  1, SQLITE_UTF16|SQLITE_DETERMINISTIC, (void*)1, icuCaseFunc16},
   508         -    {"upper",  2, SQLITE_UTF16|SQLITE_DETERMINISTIC, (void*)1, icuCaseFunc16},
   509         -
   510         -    {"lower",  1, SQLITE_UTF8|SQLITE_DETERMINISTIC,         0, icuCaseFunc16},
   511         -    {"lower",  2, SQLITE_UTF8|SQLITE_DETERMINISTIC,         0, icuCaseFunc16},
   512         -    {"upper",  1, SQLITE_UTF8|SQLITE_DETERMINISTIC,  (void*)1, icuCaseFunc16},
   513         -    {"upper",  2, SQLITE_UTF8|SQLITE_DETERMINISTIC,  (void*)1, icuCaseFunc16},
   514         -
   515         -    {"like",   2, SQLITE_UTF8|SQLITE_DETERMINISTIC,         0, icuLikeFunc},
   516         -    {"like",   3, SQLITE_UTF8|SQLITE_DETERMINISTIC,         0, icuLikeFunc},
   517         -
   518         -    {"icu_load_collation",  2, SQLITE_UTF8, (void*)db, icuLoadCollation},
          503  +    {"icu_load_collation",  2, SQLITE_UTF8,                1, icuLoadCollation},
          504  +    {"regexp", 2, SQLITE_ANY|SQLITE_DETERMINISTIC,         0, icuRegexpFunc},
          505  +    {"lower",  1, SQLITE_UTF16|SQLITE_DETERMINISTIC,       0, icuCaseFunc16},
          506  +    {"lower",  2, SQLITE_UTF16|SQLITE_DETERMINISTIC,       0, icuCaseFunc16},
          507  +    {"upper",  1, SQLITE_UTF16|SQLITE_DETERMINISTIC,       1, icuCaseFunc16},
          508  +    {"upper",  2, SQLITE_UTF16|SQLITE_DETERMINISTIC,       1, icuCaseFunc16},
          509  +    {"lower",  1, SQLITE_UTF8|SQLITE_DETERMINISTIC,        0, icuCaseFunc16},
          510  +    {"lower",  2, SQLITE_UTF8|SQLITE_DETERMINISTIC,        0, icuCaseFunc16},
          511  +    {"upper",  1, SQLITE_UTF8|SQLITE_DETERMINISTIC,        1, icuCaseFunc16},
          512  +    {"upper",  2, SQLITE_UTF8|SQLITE_DETERMINISTIC,        1, icuCaseFunc16},
          513  +    {"like",   2, SQLITE_UTF8|SQLITE_DETERMINISTIC,        0, icuLikeFunc},
          514  +    {"like",   3, SQLITE_UTF8|SQLITE_DETERMINISTIC,        0, icuLikeFunc},
   519    515     };
   520         -
   521    516     int rc = SQLITE_OK;
   522    517     int i;
   523    518   
          519  +  
   524    520     for(i=0; rc==SQLITE_OK && i<(int)(sizeof(scalars)/sizeof(scalars[0])); i++){
   525         -    struct IcuScalar *p = &scalars[i];
          521  +    const struct IcuScalar *p = &scalars[i];
   526    522       rc = sqlite3_create_function(
   527         -        db, p->zName, p->nArg, p->enc, p->pContext, p->xFunc, 0, 0
          523  +        db, p->zName, p->nArg, p->enc, 
          524  +        p->iContext ? (void*)db : (void*)0,
          525  +        p->xFunc, 0, 0
   528    526       );
   529    527     }
   530    528   
   531    529     return rc;
   532    530   }
   533    531   
   534    532   #if !SQLITE_CORE

Changes to ext/misc/json1.c.

    18     18   ** For the time being, all JSON is stored as pure text.  (We might add
    19     19   ** a JSONB type in the future which stores a binary encoding of JSON in
    20     20   ** a BLOB, but there is no support for JSONB in the current implementation.
    21     21   ** This implementation parses JSON text at 250 MB/s, so it is hard to see
    22     22   ** how JSONB might improve on that.)
    23     23   */
    24     24   #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_JSON1)
    25         -#if !defined(_SQLITEINT_H_)
           25  +#if !defined(SQLITEINT_H)
    26     26   #include "sqlite3ext.h"
    27     27   #endif
    28     28   SQLITE_EXTENSION_INIT1
    29     29   #include <assert.h>
    30     30   #include <string.h>
    31     31   #include <stdlib.h>
    32     32   #include <stdarg.h>

Changes to ext/misc/vtshim.c.

    91     91     if( pNew==0 ) return SQLITE_NOMEM;
    92     92     memset(pNew, 0, sizeof(*pNew));
    93     93     rc = pAux->pMod->xCreate(db, pAux->pChildAux, argc, argv,
    94     94                              &pNew->pChild, pzErr);
    95     95     if( rc ){
    96     96       sqlite3_free(pNew);
    97     97       *ppVtab = 0;
           98  +    return rc;
    98     99     }
    99    100     pNew->pAux = pAux;
   100    101     pNew->ppPrev = &pAux->pAllVtab;
   101    102     pNew->pNext = pAux->pAllVtab;
   102    103     if( pAux->pAllVtab ) pAux->pAllVtab->ppPrev = &pNew->pNext;
   103    104     pAux->pAllVtab = pNew;
   104    105     return rc;
................................................................................
   129    130     if( pNew==0 ) return SQLITE_NOMEM;
   130    131     memset(pNew, 0, sizeof(*pNew));
   131    132     rc = pAux->pMod->xConnect(db, pAux->pChildAux, argc, argv,
   132    133                               &pNew->pChild, pzErr);
   133    134     if( rc ){
   134    135       sqlite3_free(pNew);
   135    136       *ppVtab = 0;
          137  +    return rc;
   136    138     }
   137    139     pNew->pAux = pAux;
   138    140     pNew->ppPrev = &pAux->pAllVtab;
   139    141     pNew->pNext = pAux->pAllVtab;
   140    142     if( pAux->pAllVtab ) pAux->pAllVtab->ppPrev = &pNew->pNext;
   141    143     pAux->pAllVtab = pNew;
   142    144     return rc;

Added ext/rbu/rbufault4.test.

            1  +# 2014 October 22
            2  +#
            3  +# The author disclaims copyright to this source code.  In place of
            4  +# a legal notice, here is a blessing:
            5  +#
            6  +#    May you do good and not evil.
            7  +#    May you find forgiveness for yourself and forgive others.
            8  +#    May you share freely, never taking more than you give.
            9  +#
           10  +#***********************************************************************
           11  +#
           12  +
           13  +if {![info exists testdir]} {
           14  +  set testdir [file join [file dirname [info script]] .. .. test]
           15  +}
           16  +source $testdir/tester.tcl
           17  +source $testdir/malloc_common.tcl
           18  +set ::testprefix rbufault4
           19  +
           20  +for {set tn 1} {1} {incr tn} {
           21  +  reset_db
           22  +  do_execsql_test 1.0 {
           23  +    CREATE TABLE t1(a INTEGER PRIMARY KEY, b, c);
           24  +    CREATE INDEX i1b ON t1(b);
           25  +    CREATE INDEX i1c ON t1(c);
           26  +    INSERT INTO t1 VALUES(1, 2, 3);
           27  +    INSERT INTO t1 VALUES(4, 5, 6);
           28  +  }
           29  +
           30  +  forcedelete test.db2
           31  +  sqlite3rbu_vacuum rbu test.db test.db2
           32  +  for {set i 0} {$i < $tn} {incr i} { rbu step }
           33  +  set rc [rbu close]
           34  +  if {$rc!="SQLITE_OK"} { 
           35  +    if {$rc!="SQLITE_DONE"} {error $rc}
           36  +    break
           37  +  }
           38  +  faultsim_save
           39  +
           40  +  do_faultsim_test $tn -faults oom-t* -prep {
           41  +    faultsim_restore
           42  +  } -body {
           43  +    sqlite3rbu_vacuum rbu test.db test.db2
           44  +    while 1 {
           45  +      set rc [rbu step]
           46  +      if {$rc=="SQLITE_DONE"} break
           47  +      if {$rc!="SQLITE_OK"} { error $rc }
           48  +    }
           49  +  } -test {
           50  +    catch {rbu close}
           51  +    faultsim_test_result {0 {}} {1 SQLITE_NOMEM} {1 SQLITE_IOERR_NOMEM}
           52  +
           53  +    sqlite3rbu_vacuum rbu test.db test.db2
           54  +    while {[rbu step]=="SQLITE_OK"} {}
           55  +    set trc [rbu close]
           56  +    if {$trc!="SQLITE_DONE"} { error "Got $trc instead of SQLITE_DONE!" }
           57  +
           58  +    set rc [db one {PRAGMA integrity_check}]
           59  +    if {$rc!="ok"} { error "Got $rc instead of ok!" }
           60  +  }
           61  +}
           62  +
           63  +
           64  +
           65  +finish_test
           66  +

Added ext/rbu/rburesume.test.

            1  +# 2017 January 13
            2  +#
            3  +# The author disclaims copyright to this source code.  In place of
            4  +# a legal notice, here is a blessing:
            5  +#
            6  +#    May you do good and not evil.
            7  +#    May you find forgiveness for yourself and forgive others.
            8  +#    May you share freely, never taking more than you give.
            9  +#
           10  +#***********************************************************************
           11  +#
           12  +# This file contains tests for resumption of RBU operations in the
           13  +# case where the previous RBU process crashed.
           14  +#
           15  +
           16  +source [file join [file dirname [info script]] rbu_common.tcl]
           17  +set ::testprefix rburesume
           18  +
           19  +forcedelete test.db-shm test.db-oal
           20  +do_execsql_test 1.0 {
           21  +  CREATE TABLE t1(a PRIMARY KEY, b, c);
           22  +  CREATE INDEX t1a ON t1(a);
           23  +  CREATE INDEX t1b ON t1(b);
           24  +  CREATE INDEX t1c ON t1(c);
           25  +  WITH s(i) AS (
           26  +    VALUES(1) UNION ALL SELECT i+1 FROM s WHERE i<50
           27  +  )
           28  +  INSERT INTO t1 SELECT randomblob(50), randomblob(75), randomblob(100) FROM s;
           29  +}
           30  +db_save_and_close
           31  +
           32  +do_test 1.1 {
           33  +  list [file exists test.db] \
           34  +       [file exists test.db-wal] \
           35  +       [file exists test.db-shm] \
           36  +       [file exists test.db-oal]
           37  +} {1 0 0 0}
           38  +
           39  +# Each iteration of the following loop:
           40  +#
           41  +#   1. Restores the db to the state it was in following test case 1.0
           42  +#   2. Opens an RBU vacuum and steps it $n times.
           43  +#   3. Closes the RBU vacuum handled opened in (2).
           44  +#   4. Opens a second RBU vacuum handle, resumes and completes the vacuum op. 
           45  +#
           46  +# The loop runs until $n is large enough that step (2) vacuums the entire
           47  +# database.
           48  +#
           49  +for {set n 1} {$n < 5000} {incr n} {
           50  +  db_restore
           51  +  forcedelete state.db
           52  +  sqlite3rbu_vacuum rbu test.db state.db
           53  +  for {set i 0} {$i<$n} {incr i} {
           54  +    set rc [rbu step]
           55  +    if {$rc == "SQLITE_DONE"} break
           56  +  }
           57  +  rbu close
           58  +  if {$rc == "SQLITE_DONE"} break
           59  +
           60  +  do_test 1.2.$n.1 {
           61  +    sqlite3rbu_vacuum rbu test.db state.db
           62  +    while {[rbu step]=="SQLITE_OK"} {}
           63  +    rbu close
           64  +  } {SQLITE_DONE}
           65  +
           66  +  do_test 1.2.$n.2 {
           67  +    sqlite3 db2 test.db
           68  +    db2 eval { 
           69  +      SELECT count(*) FROM t1;
           70  +      PRAGMA integrity_check;
           71  +    }
           72  +  } {50 ok}
           73  +  db2 close
           74  +}
           75  +
           76  +# Each iteration of this loop:
           77  +#
           78  +#   1. Restores the db to the state it was in following test case 1.0
           79  +#   2. Opens an RBU vacuum and steps it $n times.
           80  +#   3. Takes a copy of all database files and the state db.
           81  +#   4. Opens a second RBU vacuum handle on the copy, resumes and completes the
           82  +#      vacuum op. 
           83  +#
           84  +# The loop runs until $n is large enough that step (2) vacuums the entire
           85  +# database.
           86  +#
           87  +for {set n 1} {$n < 5000} {incr n} {
           88  +  db_restore
           89  +  forcedelete state.db state.db-shm state.db-oal state.db-wal
           90  +  sqlite3rbu_vacuum rbu test.db state.db
           91  +  for {set i 0} {$i<$n} {incr i} {
           92  +    set rc [rbu step]
           93  +    if {$rc == "SQLITE_DONE"} break
           94  +  }
           95  +  if {$rc == "SQLITE_DONE"} {
           96  +    rbu close
           97  +    break
           98  +  }
           99  +
          100  +  foreach f {test.db test.db-oal test.db-wal test.db-shm test.db-vacuum} {
          101  +    set f2 [string map [list test.db test.db2] $f]
          102  +    if {[file exists $f]} {
          103  +      forcecopy $f $f2
          104  +    } else {
          105  +      forcedelete $f2
          106  +    }
          107  +  }
          108  +  forcecopy state.db state.db2
          109  +  rbu close
          110  +
          111  +  do_test 1.3.$n.1 {
          112  +    sqlite3rbu_vacuum rbu test.db2 state.db2
          113  +    while {[rbu step]=="SQLITE_OK"} {}
          114  +    rbu close
          115  +  } {SQLITE_DONE}
          116  +
          117  +  do_test 1.3.$n.2 {
          118  +    sqlite3 db2 test.db2
          119  +    db2 eval { 
          120  +      SELECT count(*) FROM t1;
          121  +      PRAGMA integrity_check;
          122  +    }
          123  +  } {50 ok}
          124  +  db2 close
          125  +}
          126  +
          127  +# Each iteration of this loop:
          128  +#
          129  +#   1. Restores the db to the state it was in following test case 1.0
          130  +#   2. Opens an RBU vacuum and steps it 10 times. Then closes it.
          131  +#   2. Opens an RBU vacuum and steps it $n times.
          132  +#   3. Takes a copy of all database files and the state db.
          133  +#   4. Opens a second RBU vacuum handle on the copy, resumes and completes the
          134  +#      vacuum op. 
          135  +#
          136  +# The loop runs until $n is large enough that step (3) vacuums the entire
          137  +# database.
          138  +#
          139  +for {set n 1} {$n < 5000} {incr n} {
          140  +  db_restore
          141  +  forcedelete state.db state.db-shm state.db-oal state.db-wal
          142  +
          143  +  sqlite3rbu_vacuum rbu test.db state.db
          144  +  for {set i 0} {$i<10} {incr i} {
          145  +    rbu step
          146  +  }
          147  +  rbu close
          148  +
          149  +  sqlite3rbu_vacuum rbu test.db state.db
          150  +  for {set i 0} {$i<$n} {incr i} {
          151  +    set rc [rbu step]
          152  +    if {$rc == "SQLITE_DONE"} break
          153  +  }
          154  +  if {$rc == "SQLITE_DONE"} {
          155  +    rbu close
          156  +    break
          157  +  }
          158  +
          159  +  foreach f {test.db test.db-oal test.db-wal test.db-shm test.db-vacuum} {
          160  +    set f2 [string map [list test.db test.db2] $f]
          161  +    if {[file exists $f]} {
          162  +      forcecopy $f $f2
          163  +    } else {
          164  +      forcedelete $f2
          165  +    }
          166  +  }
          167  +  forcecopy state.db state.db2
          168  +  rbu close
          169  +
          170  +  do_test 1.4.$n.1 {
          171  +    sqlite3rbu_vacuum rbu test.db2 state.db2
          172  +    while {[rbu step]=="SQLITE_OK"} {}
          173  +    rbu close
          174  +  } {SQLITE_DONE}
          175  +
          176  +  do_test 1.4.$n.2 {
          177  +    sqlite3 db2 test.db2
          178  +    db2 eval { 
          179  +      SELECT count(*) FROM t1;
          180  +      PRAGMA integrity_check;
          181  +    }
          182  +  } {50 ok}
          183  +  db2 close
          184  +}
          185  +
          186  +forcedelete rbu.db
          187  +do_test 2.0 {
          188  +  sqlite3 db2 rbu.db
          189  +  db2 eval {
          190  +    CREATE TABLE data_t1(a, b, c, rbu_control);
          191  +    WITH s(i) AS (
          192  +        VALUES(1) UNION ALL SELECT i+1 FROM s WHERE i<10
          193  +    )
          194  +    INSERT INTO data_t1 
          195  +      SELECT randomblob(50), randomblob(75), randomblob(100), 0 FROM s;
          196  +  }
          197  +  db2 close
          198  +} {}
          199  +
          200  +# Each iteration of this loop:
          201  +#
          202  +#   1. Restores the db to the state it was in following test case 1.0
          203  +#   2. Opens an RBU handle to apply the RBU update created in test case 2.0.
          204  +#   3. Steps the RBU handle $n times.
          205  +#   4. Takes a copy of all database files and the state db.
          206  +#   5. Opens a second RBU handle on the copy, resumes and completes the
          207  +#      RBU op. Checks it worked as expected.
          208  +#
          209  +# The loop runs until $n is large enough that step (3) applies the entire
          210  +# update.
          211  +#
          212  +for {set n 1} {$n < 5000} {incr n} {
          213  +  db_restore
          214  +  forcedelete state.db state.db-shm state.db-oal state.db-wal
          215  +  sqlite3rbu rbu test.db rbu.db state.db
          216  +
          217  +  for {set i 0} {$i<$n} {incr i} {
          218  +    set rc [rbu step]
          219  +    if {$rc == "SQLITE_DONE"} break
          220  +  }
          221  +  if {$rc == "SQLITE_DONE"} {
          222  +    rbu close
          223  +    break
          224  +  }
          225  +
          226  +  foreach f {test.db test.db-oal test.db-wal test.db-shm test.db-vacuum} {
          227  +    set f2 [string map [list test.db test.db2] $f]
          228  +    if {[file exists $f]} {
          229  +      forcecopy $f $f2
          230  +    } else {
          231  +      forcedelete $f2
          232  +    }
          233  +  }
          234  +  forcecopy state.db state.db2
          235  +  rbu close
          236  +
          237  +  do_test 2.$n.1 {
          238  +    sqlite3rbu rbu test.db2 rbu.db state.db2
          239  +    while {[rbu step]=="SQLITE_OK"} {}
          240  +    rbu close
          241  +  } {SQLITE_DONE}
          242  +
          243  +  do_test 2.$n.2 {
          244  +    sqlite3 db2 test.db2
          245  +    db2 eval { 
          246  +      SELECT count(*) FROM t1;
          247  +      PRAGMA integrity_check;
          248  +    }
          249  +  } {60 ok}
          250  +  db2 close
          251  +}
          252  +
          253  +finish_test
          254  +

Changes to ext/rbu/rbuvacuum2.test.

   195    195   
   196    196       do_test 5.$tn.2 { file exists test.db-vacuum } 1
   197    197       do_test 5.$tn.3 { file attributes test.db-vacuum -permissions} $perm
   198    198       rbu close
   199    199     }
   200    200   }
   201    201   
          202  +#-------------------------------------------------------------------------
          203  +# Test the outcome of some other connection running a checkpoint while
          204  +# the incremental checkpoint is suspended.
          205  +#
          206  +reset_db
          207  +do_execsql_test 6.0 {
          208  +  CREATE TABLE t1(a INTEGER PRIMARY KEY, b, c);
          209  +  CREATE INDEX i1b ON t1(b);
          210  +  CREATE INDEX i1c ON t1(c);
          211  +  INSERT INTO t1 VALUES(1, 2, 3);
          212  +  INSERT INTO t1 VALUES(4, 5, 6);
          213  +}
          214  +forcedelete test.db2
          215  +
          216  +do_test 6.1 {
          217  +  sqlite3rbu_vacuum rbu test.db test.db2
          218  +  while {[rbu state]!="checkpoint"} { rbu step }
          219  +  rbu close
          220  +} {SQLITE_OK}
          221  +
          222  +do_execsql_test 6.2 {
          223  +  SELECT 1 FROM sqlite_master LIMIT 1;
          224  +  PRAGMA wal_checkpoint;
          225  +} {1 0 4 4}
          226  +
          227  +do_test 6.3 {
          228  +  sqlite3rbu_vacuum rbu test.db test.db2
          229  +  while {[rbu step]!="SQLITE_DONE"} { rbu step }
          230  +  rbu close
          231  +  execsql { PRAGMA integrity_check }
          232  +} {ok}
   202    233   
   203    234   finish_test
   204    235   

Changes to ext/rbu/sqlite3rbu.c.

  2329   2329   }
  2330   2330   
  2331   2331   
  2332   2332   /*
  2333   2333   ** Open the database handle and attach the RBU database as "rbu". If an
  2334   2334   ** error occurs, leave an error code and message in the RBU handle.
  2335   2335   */
  2336         -static void rbuOpenDatabase(sqlite3rbu *p){
         2336  +static void rbuOpenDatabase(sqlite3rbu *p, int *pbRetry){
  2337   2337     assert( p->rc || (p->dbMain==0 && p->dbRbu==0) );
  2338   2338     assert( p->rc || rbuIsVacuum(p) || p->zTarget!=0 );
  2339   2339   
  2340   2340     /* Open the RBU database */
  2341   2341     p->dbRbu = rbuOpenDbhandle(p, p->zRbu, 1);
  2342   2342   
  2343   2343     if( p->rc==SQLITE_OK && rbuIsVacuum(p) ){
................................................................................
  2404   2404       rc = sqlite3_file_control(p->dbRbu, "main", SQLITE_FCNTL_RBUCNT, (void*)p);
  2405   2405       if( rc!=SQLITE_NOTFOUND ) p->rc = rc;
  2406   2406       if( p->eStage>=RBU_STAGE_MOVE ){
  2407   2407         bOpen = 1;
  2408   2408       }else{
  2409   2409         RbuState *pState = rbuLoadState(p);
  2410   2410         if( pState ){
  2411         -        bOpen = (pState->eStage>RBU_STAGE_MOVE);
         2411  +        bOpen = (pState->eStage>=RBU_STAGE_MOVE);
  2412   2412           rbuFreeState(pState);
  2413   2413         }
  2414   2414       }
  2415   2415       if( bOpen ) p->dbMain = rbuOpenDbhandle(p, p->zRbu, p->nRbu<=1);
  2416   2416     }
  2417   2417   
  2418   2418     p->eStage = 0;
  2419   2419     if( p->rc==SQLITE_OK && p->dbMain==0 ){
  2420   2420       if( !rbuIsVacuum(p) ){
  2421   2421         p->dbMain = rbuOpenDbhandle(p, p->zTarget, 1);
  2422   2422       }else if( p->pRbuFd->pWalFd ){
         2423  +      if( pbRetry ){
         2424  +        p->pRbuFd->bNolock = 0;
         2425  +        sqlite3_close(p->dbRbu);
         2426  +        sqlite3_close(p->dbMain);
         2427  +        p->dbMain = 0;
         2428  +        p->dbRbu = 0;
         2429  +        *pbRetry = 1;
         2430  +        return;
         2431  +      }
  2423   2432         p->rc = SQLITE_ERROR;
  2424   2433         p->zErrmsg = sqlite3_mprintf("cannot vacuum wal mode database");
  2425   2434       }else{
  2426   2435         char *zTarget;
  2427   2436         char *zExtra = 0;
  2428   2437         if( strlen(p->zRbu)>=5 && 0==memcmp("file:", p->zRbu, 5) ){
  2429   2438           zExtra = &p->zRbu[5];
................................................................................
  2596   2605     if( p->rc==SQLITE_OK ){
  2597   2606       int rc2;
  2598   2607       p->eStage = RBU_STAGE_CAPTURE;
  2599   2608       rc2 = sqlite3_exec(p->dbMain, "PRAGMA main.wal_checkpoint=restart", 0, 0,0);
  2600   2609       if( rc2!=SQLITE_INTERNAL ) p->rc = rc2;
  2601   2610     }
  2602   2611   
  2603         -  if( p->rc==SQLITE_OK ){
         2612  +  if( p->rc==SQLITE_OK && p->nFrame>0 ){
  2604   2613       p->eStage = RBU_STAGE_CKPT;
  2605   2614       p->nStep = (pState ? pState->nRow : 0);
  2606   2615       p->aBuf = rbuMalloc(p, p->pgsz);
  2607   2616       p->iWalCksum = rbuShmChecksum(p);
  2608   2617     }
  2609   2618   
  2610         -  if( p->rc==SQLITE_OK && pState && pState->iWalCksum!=p->iWalCksum ){
  2611         -    p->rc = SQLITE_DONE;
  2612         -    p->eStage = RBU_STAGE_DONE;
         2619  +  if( p->rc==SQLITE_OK ){
         2620  +    if( p->nFrame==0 || (pState && pState->iWalCksum!=p->iWalCksum) ){
         2621  +      p->rc = SQLITE_DONE;
         2622  +      p->eStage = RBU_STAGE_DONE;
         2623  +    }
  2613   2624     }
  2614   2625   }
  2615   2626   
  2616   2627   /*
  2617   2628   ** Called when iAmt bytes are read from offset iOff of the wal file while
  2618   2629   ** the rbu object is in capture mode. Record the frame number of the frame
  2619   2630   ** being read in the aFrame[] array.
................................................................................
  2778   2789           }
  2779   2790         }
  2780   2791   #else
  2781   2792         p->rc = rename(zOal, zWal) ? SQLITE_IOERR : SQLITE_OK;
  2782   2793   #endif
  2783   2794   
  2784   2795         if( p->rc==SQLITE_OK ){
  2785         -        rbuOpenDatabase(p);
         2796  +        rbuOpenDatabase(p, 0);
  2786   2797           rbuSetupCheckpoint(p, 0);
  2787   2798         }
  2788   2799       }
  2789   2800     }
  2790   2801   
  2791   2802     sqlite3_free(zWal);
  2792   2803     sqlite3_free(zOal);
................................................................................
  3489   3500       /* Create the custom VFS. */
  3490   3501       memset(p, 0, sizeof(sqlite3rbu));
  3491   3502       rbuCreateVfs(p);
  3492   3503   
  3493   3504       /* Open the target, RBU and state databases */
  3494   3505       if( p->rc==SQLITE_OK ){
  3495   3506         char *pCsr = (char*)&p[1];
         3507  +      int bRetry = 0;
  3496   3508         if( zTarget ){
  3497   3509           p->zTarget = pCsr;
  3498   3510           memcpy(p->zTarget, zTarget, nTarget+1);
  3499   3511           pCsr += nTarget+1;
  3500   3512         }
  3501   3513         p->zRbu = pCsr;
  3502   3514         memcpy(p->zRbu, zRbu, nRbu+1);
  3503   3515         pCsr += nRbu+1;
  3504   3516         if( zState ){
  3505   3517           p->zState = rbuMPrintf(p, "%s", zState);
  3506   3518         }
  3507         -      rbuOpenDatabase(p);
         3519  +
         3520  +      /* If the first attempt to open the database file fails and the bRetry
         3521  +      ** flag it set, this means that the db was not opened because it seemed
         3522  +      ** to be a wal-mode db. But, this may have happened due to an earlier
         3523  +      ** RBU vacuum operation leaving an old wal file in the directory.
         3524  +      ** If this is the case, it will have been checkpointed and deleted
         3525  +      ** when the handle was closed and a second attempt to open the 
         3526  +      ** database may succeed.  */
         3527  +      rbuOpenDatabase(p, &bRetry);
         3528  +      if( bRetry ){
         3529  +        rbuOpenDatabase(p, 0);
         3530  +      }
  3508   3531       }
  3509   3532   
  3510   3533       if( p->rc==SQLITE_OK ){
  3511   3534         pState = rbuLoadState(p);
  3512   3535         assert( pState || p->rc!=SQLITE_OK );
  3513   3536         if( p->rc==SQLITE_OK ){
  3514   3537   

Changes to ext/userauth/userauth.c.

    18     18   **
    19     19   ** To compile with the user-authentication feature, append this file to
    20     20   ** end of an SQLite amalgamation, then add the SQLITE_USER_AUTHENTICATION
    21     21   ** compile-time option.  See the user-auth.txt file in the same source
    22     22   ** directory as this file for additional information.
    23     23   */
    24     24   #ifdef SQLITE_USER_AUTHENTICATION
    25         -#ifndef _SQLITEINT_H_
           25  +#ifndef SQLITEINT_H
    26     26   # include "sqliteInt.h"
    27     27   #endif
    28     28   
    29     29   /*
    30     30   ** Prepare an SQL statement for use by the user authentication logic.
    31     31   ** Return a pointer to the prepared statement on success.  Return a
    32     32   ** NULL pointer if there is an error of any kind.

Changes to main.mk.

   462    462   #
   463    463   SHELL_OPT = -DSQLITE_ENABLE_JSON1 -DSQLITE_ENABLE_FTS4 -DSQLITE_ENABLE_FTS5
   464    464   SHELL_OPT += -DSQLITE_ENABLE_EXPLAIN_COMMENTS
   465    465   SHELL_OPT += -DSQLITE_ENABLE_UNKNOWN_SQL_FUNCTION
   466    466   FUZZERSHELL_OPT = -DSQLITE_ENABLE_JSON1
   467    467   FUZZCHECK_OPT = -DSQLITE_ENABLE_JSON1 -DSQLITE_ENABLE_MEMSYS5
   468    468   DBFUZZ_OPT =
          469  +KV_OPT = -DSQLITE_THREADSAFE=0 -DSQLITE_DIRECT_OVERFLOW_READ
          470  +ST_OPT = -DSQLITE_THREADSAFE=0
   469    471   
   470    472   # This is the default Makefile target.  The objects listed here
   471    473   # are what get build when you type just "make" with no arguments.
   472    474   #
   473    475   all:	sqlite3.h libsqlite3.a sqlite3$(EXE)
   474    476   
   475    477   libsqlite3.a:	$(LIBOBJ)
................................................................................
   876    878   LogEst$(EXE):	$(TOP)/tool/logest.c sqlite3.h
   877    879   	$(TCC) -o LogEst$(EXE) $(TOP)/tool/logest.c
   878    880   
   879    881   wordcount$(EXE):	$(TOP)/test/wordcount.c sqlite3.c
   880    882   	$(TCC) -DSQLITE_THREADSAFE=0 -DSQLITE_OMIT_LOAD_EXTENSION -o wordcount$(EXE) \
   881    883   		$(TOP)/test/wordcount.c sqlite3.c
   882    884   
   883         -speedtest1$(EXE):	$(TOP)/test/speedtest1.c sqlite3.o
   884         -	$(TCC) -I. $(OTAFLAGS) -o speedtest1$(EXE) $(TOP)/test/speedtest1.c sqlite3.o $(THREADLIB) 
          885  +speedtest1$(EXE):	$(TOP)/test/speedtest1.c sqlite3.c
          886  +	$(TCCX) -I. $(ST_OPT) -o speedtest1$(EXE) $(TOP)/test/speedtest1.c sqlite3.c $(THREADLIB) 
          887  +
          888  +kvtest$(EXE):	$(TOP)/test/kvtest.c sqlite3.c
          889  +	$(TCCX) -I. $(KV+OPT) -o kvtest$(EXE) $(TOP)/test/kvtest.c sqlite3.c $(THREADLIB) 
   885    890   
   886    891   rbu$(EXE): $(TOP)/ext/rbu/rbu.c $(TOP)/ext/rbu/sqlite3rbu.c sqlite3.o 
   887    892   	$(TCC) -I. -o rbu$(EXE) $(TOP)/ext/rbu/rbu.c sqlite3.o \
   888    893   	  $(THREADLIB)
   889    894   
   890    895   loadfts: $(TOP)/tool/loadfts.c libsqlite3.a
   891    896   	$(TCC) $(TOP)/tool/loadfts.c libsqlite3.a -o loadfts $(THREADLIB)

Changes to src/analyze.c.

  1611   1611            || aSample[i].anDLt[iCol]!=aSample[i+1].anDLt[iCol] 
  1612   1612           ){
  1613   1613             sumEq += aSample[i].anEq[iCol];
  1614   1614             nSum100 += 100;
  1615   1615           }
  1616   1616         }
  1617   1617   
  1618         -      if( nDist100>nSum100 ){
         1618  +      if( nDist100>nSum100 && sumEq<nRow ){
  1619   1619           avgEq = ((i64)100 * (nRow - sumEq))/(nDist100 - nSum100);
  1620   1620         }
  1621   1621         if( avgEq==0 ) avgEq = 1;
  1622   1622         pIdx->aAvgEq[iCol] = avgEq;
  1623   1623       }
  1624   1624     }
  1625   1625   }

Changes to src/attach.c.

   133    133       return;
   134    134     }
   135    135     assert( pVfs );
   136    136     flags |= SQLITE_OPEN_MAIN_DB;
   137    137     rc = sqlite3BtreeOpen(pVfs, zPath, db, &aNew->pBt, 0, flags);
   138    138     sqlite3_free( zPath );
   139    139     db->nDb++;
          140  +  db->skipBtreeMutex = 0;
   140    141     if( rc==SQLITE_CONSTRAINT ){
   141    142       rc = SQLITE_ERROR;
   142    143       zErrDyn = sqlite3MPrintf(db, "database is already attached");
   143    144     }else if( rc==SQLITE_OK ){
   144    145       Pager *pPager;
   145    146       aNew->pSchema = sqlite3SchemaGet(db, aNew->pBt);
   146    147       if( !aNew->pSchema ){

Changes to src/btmutex.c.

   179    179   ** There is a corresponding leave-all procedures.
   180    180   **
   181    181   ** Enter the mutexes in accending order by BtShared pointer address
   182    182   ** to avoid the possibility of deadlock when two threads with
   183    183   ** two or more btrees in common both try to lock all their btrees
   184    184   ** at the same instant.
   185    185   */
   186         -void sqlite3BtreeEnterAll(sqlite3 *db){
          186  +static void SQLITE_NOINLINE btreeEnterAll(sqlite3 *db){
   187    187     int i;
          188  +  int skipOk = 1;
   188    189     Btree *p;
   189    190     assert( sqlite3_mutex_held(db->mutex) );
   190    191     for(i=0; i<db->nDb; i++){
   191    192       p = db->aDb[i].pBt;
   192         -    if( p ) sqlite3BtreeEnter(p);
          193  +    if( p && p->sharable ){
          194  +      sqlite3BtreeEnter(p);
          195  +      skipOk = 0;
          196  +    }
   193    197     }
          198  +  db->skipBtreeMutex = skipOk;
          199  +}
          200  +void sqlite3BtreeEnterAll(sqlite3 *db){
          201  +  if( db->skipBtreeMutex==0 ) btreeEnterAll(db);
   194    202   }
   195         -void sqlite3BtreeLeaveAll(sqlite3 *db){
          203  +static void SQLITE_NOINLINE btreeLeaveAll(sqlite3 *db){
   196    204     int i;
   197    205     Btree *p;
   198    206     assert( sqlite3_mutex_held(db->mutex) );
   199    207     for(i=0; i<db->nDb; i++){
   200    208       p = db->aDb[i].pBt;
   201    209       if( p ) sqlite3BtreeLeave(p);
   202    210     }
   203    211   }
          212  +void sqlite3BtreeLeaveAll(sqlite3 *db){
          213  +  if( db->skipBtreeMutex==0 ) btreeLeaveAll(db);
          214  +}
   204    215   
   205    216   #ifndef NDEBUG
   206    217   /*
   207    218   ** Return true if the current thread holds the database connection
   208    219   ** mutex and all required BtShared mutexes.
   209    220   **
   210    221   ** This routine is used inside assert() statements only.

Changes to src/btree.c.

  3358   3358       nCell = pPage->nCell;
  3359   3359   
  3360   3360       for(i=0; i<nCell; i++){
  3361   3361         u8 *pCell = findCell(pPage, i);
  3362   3362         if( eType==PTRMAP_OVERFLOW1 ){
  3363   3363           CellInfo info;
  3364   3364           pPage->xParseCell(pPage, pCell, &info);
  3365         -        if( info.nLocal<info.nPayload
  3366         -         && pCell+info.nSize-1<=pPage->aData+pPage->maskPage
  3367         -         && iFrom==get4byte(pCell+info.nSize-4)
  3368         -        ){
  3369         -          put4byte(pCell+info.nSize-4, iTo);
  3370         -          break;
         3365  +        if( info.nLocal<info.nPayload ){
         3366  +          if( pCell+info.nSize > pPage->aData+pPage->pBt->usableSize ){
         3367  +            return SQLITE_CORRUPT_BKPT;
         3368  +          }
         3369  +          if( iFrom==get4byte(pCell+info.nSize-4) ){
         3370  +            put4byte(pCell+info.nSize-4, iTo);
         3371  +            break;
         3372  +          }
  3371   3373           }
  3372   3374         }else{
  3373   3375           if( get4byte(pCell)==iFrom ){
  3374   3376             put4byte(pCell, iTo);
  3375   3377             break;
  3376   3378           }
  3377   3379         }
................................................................................
  4424   4426   /*
  4425   4427   ** This function is used to read or overwrite payload information
  4426   4428   ** for the entry that the pCur cursor is pointing to. The eOp
  4427   4429   ** argument is interpreted as follows:
  4428   4430   **
  4429   4431   **   0: The operation is a read. Populate the overflow cache.
  4430   4432   **   1: The operation is a write. Populate the overflow cache.
  4431         -**   2: The operation is a read. Do not populate the overflow cache.
  4432   4433   **
  4433   4434   ** A total of "amt" bytes are read or written beginning at "offset".
  4434   4435   ** Data is read to or from the buffer pBuf.
  4435   4436   **
  4436   4437   ** The content being read or written might appear on the main page
  4437   4438   ** or be scattered out on multiple overflow pages.
  4438   4439   **
  4439         -** If the current cursor entry uses one or more overflow pages and the
  4440         -** eOp argument is not 2, this function may allocate space for and lazily 
  4441         -** populates the overflow page-list cache array (BtCursor.aOverflow). 
         4440  +** If the current cursor entry uses one or more overflow pages
         4441  +** this function may allocate space for and lazily populate
         4442  +** the overflow page-list cache array (BtCursor.aOverflow). 
  4442   4443   ** Subsequent calls use this cache to make seeking to the supplied offset 
  4443   4444   ** more efficient.
  4444   4445   **
  4445         -** Once an overflow page-list cache has been allocated, it may be
         4446  +** Once an overflow page-list cache has been allocated, it must be
  4446   4447   ** invalidated if some other cursor writes to the same table, or if
  4447   4448   ** the cursor is moved to a different row. Additionally, in auto-vacuum
  4448   4449   ** mode, the following events may invalidate an overflow page-list cache.
  4449   4450   **
  4450   4451   **   * An incremental vacuum,
  4451   4452   **   * A commit in auto_vacuum="full" mode,
  4452   4453   **   * Creating a table (may require moving an overflow page).
................................................................................
  4460   4461   ){
  4461   4462     unsigned char *aPayload;
  4462   4463     int rc = SQLITE_OK;
  4463   4464     int iIdx = 0;
  4464   4465     MemPage *pPage = pCur->apPage[pCur->iPage]; /* Btree page of current entry */
  4465   4466     BtShared *pBt = pCur->pBt;                  /* Btree this cursor belongs to */
  4466   4467   #ifdef SQLITE_DIRECT_OVERFLOW_READ
  4467         -  unsigned char * const pBufStart = pBuf;
  4468         -  int bEnd;                                 /* True if reading to end of data */
         4468  +  unsigned char * const pBufStart = pBuf;     /* Start of original out buffer */
  4469   4469   #endif
  4470   4470   
  4471   4471     assert( pPage );
         4472  +  assert( eOp==0 || eOp==1 );
  4472   4473     assert( pCur->eState==CURSOR_VALID );
  4473   4474     assert( pCur->aiIdx[pCur->iPage]<pPage->nCell );
  4474   4475     assert( cursorHoldsMutex(pCur) );
  4475         -  assert( eOp!=2 || offset==0 );    /* Always start from beginning for eOp==2 */
  4476   4476   
  4477   4477     getCellInfo(pCur);
  4478   4478     aPayload = pCur->info.pPayload;
  4479         -#ifdef SQLITE_DIRECT_OVERFLOW_READ
  4480         -  bEnd = offset+amt==pCur->info.nPayload;
  4481         -#endif
  4482   4479     assert( offset+amt <= pCur->info.nPayload );
  4483   4480   
  4484   4481     assert( aPayload > pPage->aData );
  4485   4482     if( (uptr)(aPayload - pPage->aData) > (pBt->usableSize - pCur->info.nLocal) ){
  4486   4483       /* Trying to read or write past the end of the data is an error.  The
  4487   4484       ** conditional above is really:
  4488   4485       **    &aPayload[pCur->info.nLocal] > &pPage->aData[pBt->usableSize]
................................................................................
  4493   4490   
  4494   4491     /* Check if data must be read/written to/from the btree page itself. */
  4495   4492     if( offset<pCur->info.nLocal ){
  4496   4493       int a = amt;
  4497   4494       if( a+offset>pCur->info.nLocal ){
  4498   4495         a = pCur->info.nLocal - offset;
  4499   4496       }
  4500         -    rc = copyPayload(&aPayload[offset], pBuf, a, (eOp & 0x01), pPage->pDbPage);
         4497  +    rc = copyPayload(&aPayload[offset], pBuf, a, eOp, pPage->pDbPage);
  4501   4498       offset = 0;
  4502   4499       pBuf += a;
  4503   4500       amt -= a;
  4504   4501     }else{
  4505   4502       offset -= pCur->info.nLocal;
  4506   4503     }
  4507   4504   
................................................................................
  4509   4506     if( rc==SQLITE_OK && amt>0 ){
  4510   4507       const u32 ovflSize = pBt->usableSize - 4;  /* Bytes content per ovfl page */
  4511   4508       Pgno nextPage;
  4512   4509   
  4513   4510       nextPage = get4byte(&aPayload[pCur->info.nLocal]);
  4514   4511   
  4515   4512       /* If the BtCursor.aOverflow[] has not been allocated, allocate it now.
  4516         -    ** Except, do not allocate aOverflow[] for eOp==2.
  4517   4513       **
  4518   4514       ** The aOverflow[] array is sized at one entry for each overflow page
  4519   4515       ** in the overflow chain. The page number of the first overflow page is
  4520   4516       ** stored in aOverflow[0], etc. A value of 0 in the aOverflow[] array
  4521   4517       ** means "not yet known" (the cache is lazily populated).
  4522   4518       */
  4523         -    if( eOp!=2 && (pCur->curFlags & BTCF_ValidOvfl)==0 ){
         4519  +    if( (pCur->curFlags & BTCF_ValidOvfl)==0 ){
  4524   4520         int nOvfl = (pCur->info.nPayload-pCur->info.nLocal+ovflSize-1)/ovflSize;
  4525   4521         if( nOvfl>pCur->nOvflAlloc ){
  4526   4522           Pgno *aNew = (Pgno*)sqlite3Realloc(
  4527   4523               pCur->aOverflow, nOvfl*2*sizeof(Pgno)
  4528   4524           );
  4529   4525           if( aNew==0 ){
  4530         -          rc = SQLITE_NOMEM_BKPT;
         4526  +          return SQLITE_NOMEM_BKPT;
  4531   4527           }else{
  4532   4528             pCur->nOvflAlloc = nOvfl*2;
  4533   4529             pCur->aOverflow = aNew;
  4534   4530           }
  4535   4531         }
  4536         -      if( rc==SQLITE_OK ){
  4537         -        memset(pCur->aOverflow, 0, nOvfl*sizeof(Pgno));
  4538         -        pCur->curFlags |= BTCF_ValidOvfl;
         4532  +      memset(pCur->aOverflow, 0, nOvfl*sizeof(Pgno));
         4533  +      pCur->curFlags |= BTCF_ValidOvfl;
         4534  +    }else{
         4535  +      /* If the overflow page-list cache has been allocated and the
         4536  +      ** entry for the first required overflow page is valid, skip
         4537  +      ** directly to it.
         4538  +      */
         4539  +      if( pCur->aOverflow[offset/ovflSize] ){
         4540  +        iIdx = (offset/ovflSize);
         4541  +        nextPage = pCur->aOverflow[iIdx];
         4542  +        offset = (offset%ovflSize);
  4539   4543         }
  4540   4544       }
  4541   4545   
  4542         -    /* If the overflow page-list cache has been allocated and the
  4543         -    ** entry for the first required overflow page is valid, skip
  4544         -    ** directly to it.
  4545         -    */
  4546         -    if( (pCur->curFlags & BTCF_ValidOvfl)!=0
  4547         -     && pCur->aOverflow[offset/ovflSize]
  4548         -    ){
  4549         -      iIdx = (offset/ovflSize);
  4550         -      nextPage = pCur->aOverflow[iIdx];
  4551         -      offset = (offset%ovflSize);
  4552         -    }
  4553         -
  4554         -    for( ; rc==SQLITE_OK && amt>0 && nextPage; iIdx++){
  4555         -
         4546  +    assert( rc==SQLITE_OK && amt>0 );
         4547  +    while( nextPage ){
  4556   4548         /* If required, populate the overflow page-list cache. */
  4557         -      if( (pCur->curFlags & BTCF_ValidOvfl)!=0 ){
  4558         -        assert( pCur->aOverflow[iIdx]==0
  4559         -                || pCur->aOverflow[iIdx]==nextPage
  4560         -                || CORRUPT_DB );
  4561         -        pCur->aOverflow[iIdx] = nextPage;
  4562         -      }
         4549  +      assert( pCur->aOverflow[iIdx]==0
         4550  +              || pCur->aOverflow[iIdx]==nextPage
         4551  +              || CORRUPT_DB );
         4552  +      pCur->aOverflow[iIdx] = nextPage;
  4563   4553   
  4564   4554         if( offset>=ovflSize ){
  4565   4555           /* The only reason to read this page is to obtain the page
  4566   4556           ** number for the next page in the overflow chain. The page
  4567   4557           ** data is not required. So first try to lookup the overflow
  4568   4558           ** page-list cache, if any, then fall back to the getOverflowPage()
  4569   4559           ** function.
  4570         -        **
  4571         -        ** Note that the aOverflow[] array must be allocated because eOp!=2
  4572         -        ** here.  If eOp==2, then offset==0 and this branch is never taken.
  4573   4560           */
  4574         -        assert( eOp!=2 );
  4575   4561           assert( pCur->curFlags & BTCF_ValidOvfl );
  4576   4562           assert( pCur->pBtree->db==pBt->db );
  4577   4563           if( pCur->aOverflow[iIdx+1] ){
  4578   4564             nextPage = pCur->aOverflow[iIdx+1];
  4579   4565           }else{
  4580   4566             rc = getOverflowPage(pBt, nextPage, 0, &nextPage);
  4581   4567           }
  4582   4568           offset -= ovflSize;
  4583   4569         }else{
  4584   4570           /* Need to read this page properly. It contains some of the
  4585   4571           ** range of data that is being read (eOp==0) or written (eOp!=0).
  4586   4572           */
  4587   4573   #ifdef SQLITE_DIRECT_OVERFLOW_READ
  4588         -        sqlite3_file *fd;
         4574  +        sqlite3_file *fd;      /* File from which to do direct overflow read */
  4589   4575   #endif
  4590   4576           int a = amt;
  4591   4577           if( a + offset > ovflSize ){
  4592   4578             a = ovflSize - offset;
  4593   4579           }
  4594   4580   
  4595   4581   #ifdef SQLITE_DIRECT_OVERFLOW_READ
  4596   4582           /* If all the following are true:
  4597   4583           **
  4598   4584           **   1) this is a read operation, and 
  4599   4585           **   2) data is required from the start of this overflow page, and
  4600         -        **   3) the database is file-backed, and
  4601         -        **   4) there is no open write-transaction, and
  4602         -        **   5) the database is not a WAL database,
  4603         -        **   6) all data from the page is being read.
  4604         -        **   7) at least 4 bytes have already been read into the output buffer 
         4586  +        **   3) there is no open write-transaction, and
         4587  +        **   4) the database is file-backed, and
         4588  +        **   5) the page is not in the WAL file
         4589  +        **   6) at least 4 bytes have already been read into the output buffer 
  4605   4590           **
  4606   4591           ** then data can be read directly from the database file into the
  4607   4592           ** output buffer, bypassing the page-cache altogether. This speeds
  4608   4593           ** up loading large records that span many overflow pages.
  4609   4594           */
  4610         -        if( (eOp&0x01)==0                                      /* (1) */
         4595  +        if( eOp==0                                             /* (1) */
  4611   4596            && offset==0                                          /* (2) */
  4612         -         && (bEnd || a==ovflSize)                              /* (6) */
  4613         -         && pBt->inTransaction==TRANS_READ                     /* (4) */
  4614         -         && (fd = sqlite3PagerFile(pBt->pPager))->pMethods     /* (3) */
  4615         -         && 0==sqlite3PagerUseWal(pBt->pPager)                 /* (5) */
  4616         -         && &pBuf[-4]>=pBufStart                               /* (7) */
         4597  +         && pBt->inTransaction==TRANS_READ                     /* (3) */
         4598  +         && (fd = sqlite3PagerFile(pBt->pPager))->pMethods     /* (4) */
         4599  +         && 0==sqlite3PagerUseWal(pBt->pPager, nextPage)       /* (5) */
         4600  +         && &pBuf[-4]>=pBufStart                               /* (6) */
  4617   4601           ){
  4618   4602             u8 aSave[4];
  4619   4603             u8 *aWrite = &pBuf[-4];
  4620         -          assert( aWrite>=pBufStart );                         /* hence (7) */
         4604  +          assert( aWrite>=pBufStart );                         /* due to (6) */
  4621   4605             memcpy(aSave, aWrite, 4);
  4622   4606             rc = sqlite3OsRead(fd, aWrite, a+4, (i64)pBt->pageSize*(nextPage-1));
  4623   4607             nextPage = get4byte(aWrite);
  4624   4608             memcpy(aWrite, aSave, 4);
  4625   4609           }else
  4626   4610   #endif
  4627   4611   
  4628   4612           {
  4629   4613             DbPage *pDbPage;
  4630   4614             rc = sqlite3PagerGet(pBt->pPager, nextPage, &pDbPage,
  4631         -              ((eOp&0x01)==0 ? PAGER_GET_READONLY : 0)
         4615  +              (eOp==0 ? PAGER_GET_READONLY : 0)
  4632   4616             );
  4633   4617             if( rc==SQLITE_OK ){
  4634   4618               aPayload = sqlite3PagerGetData(pDbPage);
  4635   4619               nextPage = get4byte(aPayload);
  4636         -            rc = copyPayload(&aPayload[offset+4], pBuf, a, (eOp&0x01), pDbPage);
         4620  +            rc = copyPayload(&aPayload[offset+4], pBuf, a, eOp, pDbPage);
  4637   4621               sqlite3PagerUnref(pDbPage);
  4638   4622               offset = 0;
  4639   4623             }
  4640   4624           }
  4641   4625           amt -= a;
         4626  +        if( amt==0 ) return rc;
  4642   4627           pBuf += a;
  4643   4628         }
         4629  +      if( rc ) break;
         4630  +      iIdx++;
  4644   4631       }
  4645   4632     }
  4646   4633   
  4647   4634     if( rc==SQLITE_OK && amt>0 ){
  4648         -    return SQLITE_CORRUPT_BKPT;
         4635  +    return SQLITE_CORRUPT_BKPT; /* Overflow chain ends prematurely */
  4649   4636     }
  4650   4637     return rc;
  4651   4638   }
  4652   4639   
  4653   4640   /*
  4654   4641   ** Read part of the payload for the row at which that cursor pCur is currently
  4655   4642   ** pointing.  "amt" bytes will be transferred into pBuf[].  The transfer
................................................................................
  4670   4657   int sqlite3BtreePayload(BtCursor *pCur, u32 offset, u32 amt, void *pBuf){
  4671   4658     assert( cursorHoldsMutex(pCur) );
  4672   4659     assert( pCur->eState==CURSOR_VALID );
  4673   4660     assert( pCur->iPage>=0 && pCur->apPage[pCur->iPage] );
  4674   4661     assert( pCur->aiIdx[pCur->iPage]<pCur->apPage[pCur->iPage]->nCell );
  4675   4662     return accessPayload(pCur, offset, amt, (unsigned char*)pBuf, 0);
  4676   4663   }
         4664  +
         4665  +/*
         4666  +** This variant of sqlite3BtreePayload() works even if the cursor has not
         4667  +** in the CURSOR_VALID state.  It is only used by the sqlite3_blob_read()
         4668  +** interface.
         4669  +*/
  4677   4670   #ifndef SQLITE_OMIT_INCRBLOB
  4678         -int sqlite3BtreePayloadChecked(BtCursor *pCur, u32 offset, u32 amt, void *pBuf){
         4671  +static SQLITE_NOINLINE int accessPayloadChecked(
         4672  +  BtCursor *pCur,
         4673  +  u32 offset,
         4674  +  u32 amt,
         4675  +  void *pBuf
         4676  +){
  4679   4677     int rc;
  4680   4678     if ( pCur->eState==CURSOR_INVALID ){
  4681   4679       return SQLITE_ABORT;
  4682   4680     }
  4683   4681     assert( cursorOwnsBtShared(pCur) );
  4684         -  rc = restoreCursorPosition(pCur);
  4685         -  if( rc==SQLITE_OK ){
  4686         -    assert( pCur->eState==CURSOR_VALID );
  4687         -    assert( pCur->iPage>=0 && pCur->apPage[pCur->iPage] );
  4688         -    assert( pCur->aiIdx[pCur->iPage]<pCur->apPage[pCur->iPage]->nCell );
  4689         -    rc = accessPayload(pCur, offset, amt, pBuf, 0);
         4682  +  rc = btreeRestoreCursorPosition(pCur);
         4683  +  return rc ? rc : accessPayload(pCur, offset, amt, pBuf, 0);
         4684  +}
         4685  +int sqlite3BtreePayloadChecked(BtCursor *pCur, u32 offset, u32 amt, void *pBuf){
         4686  +  if( pCur->eState==CURSOR_VALID ){
         4687  +    assert( cursorOwnsBtShared(pCur) );
         4688  +    return accessPayload(pCur, offset, amt, pBuf, 0);
         4689  +  }else{
         4690  +    return accessPayloadChecked(pCur, offset, amt, pBuf);
  4690   4691     }
  4691         -  return rc;
  4692   4692   }
  4693   4693   #endif /* SQLITE_OMIT_INCRBLOB */
  4694   4694   
  4695   4695   /*
  4696   4696   ** Return a pointer to payload information from the entry that the 
  4697   4697   ** pCur cursor is pointing to.  The pointer is to the beginning of
  4698   4698   ** the key if index btrees (pPage->intKey==0) and is the data for
................................................................................
  5090   5090     if( pIdxKey==0
  5091   5091      && pCur->eState==CURSOR_VALID && (pCur->curFlags & BTCF_ValidNKey)!=0
  5092   5092     ){
  5093   5093       if( pCur->info.nKey==intKey ){
  5094   5094         *pRes = 0;
  5095   5095         return SQLITE_OK;
  5096   5096       }
  5097         -    if( (pCur->curFlags & BTCF_AtLast)!=0 && pCur->info.nKey<intKey ){
  5098         -      *pRes = -1;
  5099         -      return SQLITE_OK;
         5097  +    if( pCur->info.nKey<intKey ){
         5098  +      if( (pCur->curFlags & BTCF_AtLast)!=0 ){
         5099  +        *pRes = -1;
         5100  +        return SQLITE_OK;
         5101  +      }
         5102  +      /* If the requested key is one more than the previous key, then
         5103  +      ** try to get there using sqlite3BtreeNext() rather than a full
         5104  +      ** binary search.  This is an optimization only.  The correct answer
         5105  +      ** is still obtained without this ase, only a little more slowely */
         5106  +      if( pCur->info.nKey+1==intKey && !pCur->skipNext ){
         5107  +        *pRes = 0;
         5108  +        rc = sqlite3BtreeNext(pCur, pRes);
         5109  +        if( rc ) return rc;
         5110  +        if( *pRes==0 ){
         5111  +          getCellInfo(pCur);
         5112  +          if( pCur->info.nKey==intKey ){
         5113  +            return SQLITE_OK;
         5114  +          }
         5115  +        }
         5116  +      }
  5100   5117       }
  5101   5118     }
  5102   5119   
  5103   5120     if( pIdxKey ){
  5104   5121       xRecordCompare = sqlite3VdbeFindCompare(pIdxKey);
  5105   5122       pIdxKey->errCode = 0;
  5106   5123       assert( pIdxKey->default_rc==1 
................................................................................
  5228   5245             }
  5229   5246             pCellKey = sqlite3Malloc( nCell+18 );
  5230   5247             if( pCellKey==0 ){
  5231   5248               rc = SQLITE_NOMEM_BKPT;
  5232   5249               goto moveto_finish;
  5233   5250             }
  5234   5251             pCur->aiIdx[pCur->iPage] = (u16)idx;
  5235         -          rc = accessPayload(pCur, 0, nCell, (unsigned char*)pCellKey, 2);
         5252  +          rc = accessPayload(pCur, 0, nCell, (unsigned char*)pCellKey, 0);
         5253  +          pCur->curFlags &= ~BTCF_ValidOvfl;
  5236   5254             if( rc ){
  5237   5255               sqlite3_free(pCellKey);
  5238   5256               goto moveto_finish;
  5239   5257             }
  5240   5258             c = xRecordCompare(nCell, pCellKey, pIdxKey);
  5241   5259             sqlite3_free(pCellKey);
  5242   5260           }
................................................................................
  7271   7289     ** usableSpace: Number of bytes of space available on each sibling.
  7272   7290     ** 
  7273   7291     */
  7274   7292     usableSpace = pBt->usableSize - 12 + leafCorrection;
  7275   7293     for(i=0; i<nOld; i++){
  7276   7294       MemPage *p = apOld[i];
  7277   7295       szNew[i] = usableSpace - p->nFree;
  7278         -    if( szNew[i]<0 ){ rc = SQLITE_CORRUPT_BKPT; goto balance_cleanup; }
  7279   7296       for(j=0; j<p->nOverflow; j++){
  7280   7297         szNew[i] += 2 + p->xCellSize(p, p->apOvfl[j]);
  7281   7298       }
  7282   7299       cntNew[i] = cntOld[i];
  7283   7300     }
  7284   7301     k = nOld;
  7285   7302     for(i=0; i<k; i++){
................................................................................
  7950   7967   ** if pX->nMem is non-zero, then pX->aMem contains pointers to the unpacked
  7951   7968   ** key values and pX->aMem can be used instead of pX->pKey to avoid having
  7952   7969   ** to decode the key.
  7953   7970   */
  7954   7971   int sqlite3BtreeInsert(
  7955   7972     BtCursor *pCur,                /* Insert data into the table of this cursor */
  7956   7973     const BtreePayload *pX,        /* Content of the row to be inserted */
  7957         -  int appendBias,                /* True if this is likely an append */
         7974  +  int flags,                     /* True if this is likely an append */
  7958   7975     int seekResult                 /* Result of prior MovetoUnpacked() call */
  7959   7976   ){
  7960   7977     int rc;
  7961   7978     int loc = seekResult;          /* -1: before desired location  +1: after */
  7962   7979     int szNew = 0;
  7963   7980     int idx;
  7964   7981     MemPage *pPage;
  7965   7982     Btree *p = pCur->pBtree;
  7966   7983     BtShared *pBt = p->pBt;
  7967   7984     unsigned char *oldCell;
  7968   7985     unsigned char *newCell = 0;
         7986  +
         7987  +  assert( (flags & (BTREE_SAVEPOSITION|BTREE_APPEND))==flags );
  7969   7988   
  7970   7989     if( pCur->eState==CURSOR_FAULT ){
  7971   7990       assert( pCur->skipNext!=SQLITE_OK );
  7972   7991       return pCur->skipNext;
  7973   7992     }
  7974   7993   
  7975   7994     assert( cursorOwnsBtShared(pCur) );
................................................................................
  8003   8022   
  8004   8023     if( pCur->pKeyInfo==0 ){
  8005   8024       assert( pX->pKey==0 );
  8006   8025       /* If this is an insert into a table b-tree, invalidate any incrblob 
  8007   8026       ** cursors open on the row being replaced */
  8008   8027       invalidateIncrblobCursors(p, pX->nKey, 0);
  8009   8028   
         8029  +    /* If BTREE_SAVEPOSITION is set, the cursor must already be pointing 
         8030  +    ** to a row with the same key as the new entry being inserted.  */
         8031  +    assert( (flags & BTREE_SAVEPOSITION)==0 || 
         8032  +            ((pCur->curFlags&BTCF_ValidNKey)!=0 && pX->nKey==pCur->info.nKey) );
         8033  +
  8010   8034       /* If the cursor is currently on the last row and we are appending a
  8011   8035       ** new row onto the end, set the "loc" to avoid an unnecessary
  8012   8036       ** btreeMoveto() call */
  8013   8037       if( (pCur->curFlags&BTCF_ValidNKey)!=0 && pX->nKey==pCur->info.nKey ){
  8014   8038         loc = 0;
  8015   8039       }else if( (pCur->curFlags&BTCF_ValidNKey)!=0 && pX->nKey>0
  8016   8040                  && pCur->info.nKey==pX->nKey-1 ){
  8017   8041         loc = -1;
  8018   8042       }else if( loc==0 ){
  8019         -      rc = sqlite3BtreeMovetoUnpacked(pCur, 0, pX->nKey, appendBias, &loc);
         8043  +      rc = sqlite3BtreeMovetoUnpacked(pCur, 0, pX->nKey, flags!=0, &loc);
  8020   8044         if( rc ) return rc;
  8021   8045       }
  8022         -  }else if( loc==0 ){
         8046  +  }else if( loc==0 && (flags & BTREE_SAVEPOSITION)==0 ){
  8023   8047       if( pX->nMem ){
  8024   8048         UnpackedRecord r;
  8025   8049         r.pKeyInfo = pCur->pKeyInfo;
  8026   8050         r.aMem = pX->aMem;
  8027   8051         r.nField = pX->nMem;
  8028   8052         r.default_rc = 0;
  8029   8053         r.errCode = 0;
  8030   8054         r.r1 = 0;
  8031   8055         r.r2 = 0;
  8032   8056         r.eqSeen = 0;
  8033         -      rc = sqlite3BtreeMovetoUnpacked(pCur, &r, 0, appendBias, &loc);
         8057  +      rc = sqlite3BtreeMovetoUnpacked(pCur, &r, 0, flags!=0, &loc);
  8034   8058       }else{
  8035         -      rc = btreeMoveto(pCur, pX->pKey, pX->nKey, appendBias, &loc);
         8059  +      rc = btreeMoveto(pCur, pX->pKey, pX->nKey, flags!=0, &loc);
  8036   8060       }
  8037   8061       if( rc ) return rc;
  8038   8062     }
  8039   8063     assert( pCur->eState==CURSOR_VALID || (pCur->eState==CURSOR_INVALID && loc) );
  8040   8064   
  8041   8065     pPage = pCur->apPage[pCur->iPage];
  8042   8066     assert( pPage->intKey || pX->nKey>=0 );
................................................................................
  8116   8140   
  8117   8141       /* Must make sure nOverflow is reset to zero even if the balance()
  8118   8142       ** fails. Internal data structure corruption will result otherwise. 
  8119   8143       ** Also, set the cursor state to invalid. This stops saveCursorPosition()
  8120   8144       ** from trying to save the current position of the cursor.  */
  8121   8145       pCur->apPage[pCur->iPage]->nOverflow = 0;
  8122   8146       pCur->eState = CURSOR_INVALID;
         8147  +    if( (flags & BTREE_SAVEPOSITION) && rc==SQLITE_OK ){
         8148  +      rc = moveToRoot(pCur);
         8149  +      if( pCur->pKeyInfo ){
         8150  +        assert( pCur->pKey==0 );
         8151  +        pCur->pKey = sqlite3Malloc( pX->nKey );
         8152  +        if( pCur->pKey==0 ){
         8153  +          rc = SQLITE_NOMEM;
         8154  +        }else{
         8155  +          memcpy(pCur->pKey, pX->pKey, pX->nKey);
         8156  +        }
         8157  +      }
         8158  +      pCur->eState = CURSOR_REQUIRESEEK;
         8159  +      pCur->nKey = pX->nKey;
         8160  +    }
  8123   8161     }
  8124   8162     assert( pCur->apPage[pCur->iPage]->nOverflow==0 );
  8125   8163   
  8126   8164   end_insert:
  8127   8165     return rc;
  8128   8166   }
  8129   8167   

Changes to src/btree.h.

   245    245     int bias,
   246    246     int *pRes
   247    247   );
   248    248   int sqlite3BtreeCursorHasMoved(BtCursor*);
   249    249   int sqlite3BtreeCursorRestore(BtCursor*, int*);
   250    250   int sqlite3BtreeDelete(BtCursor*, u8 flags);
   251    251   
   252         -/* Allowed flags for the 2nd argument to sqlite3BtreeDelete() */
          252  +/* Allowed flags for sqlite3BtreeDelete() and sqlite3BtreeInsert() */
   253    253   #define BTREE_SAVEPOSITION 0x02  /* Leave cursor pointing at NEXT or PREV */
   254    254   #define BTREE_AUXDELETE    0x04  /* not the primary delete operation */
          255  +#define BTREE_APPEND       0x08  /* Insert is likely an append */
   255    256   
   256    257   /* An instance of the BtreePayload object describes the content of a single
   257    258   ** entry in either an index or table btree.
   258    259   **
   259    260   ** Index btrees (used for indexes and also WITHOUT ROWID tables) contain
   260    261   ** an arbitrary key and no data.  These btrees have pKey,nKey set to their
   261    262   ** key and pData,nData,nZero set to zero.
................................................................................
   278    279     struct Mem *aMem;       /* First of nMem value in the unpacked pKey */
   279    280     u16 nMem;               /* Number of aMem[] value.  Might be zero */
   280    281     int nData;              /* Size of pData.  0 if none. */
   281    282     int nZero;              /* Extra zero data appended after pData,nData */
   282    283   };
   283    284   
   284    285   int sqlite3BtreeInsert(BtCursor*, const BtreePayload *pPayload,
   285         -                       int bias, int seekResult);
          286  +                       int flags, int seekResult);
   286    287   int sqlite3BtreeFirst(BtCursor*, int *pRes);
   287    288   int sqlite3BtreeLast(BtCursor*, int *pRes);
   288    289   int sqlite3BtreeNext(BtCursor*, int *pRes);
   289    290   int sqlite3BtreeEof(BtCursor*);
   290    291   int sqlite3BtreePrevious(BtCursor*, int *pRes);
   291    292   i64 sqlite3BtreeIntegerKey(BtCursor*);
   292    293   int sqlite3BtreePayload(BtCursor*, u32 offset, u32 amt, void*);

Changes to src/delete.c.

   515    515         if( eOnePass==ONEPASS_SINGLE && sqlite3IsToplevel(pParse) ){
   516    516           pParse->isMultiWrite = 0;
   517    517         }
   518    518       }else
   519    519   #endif
   520    520       {
   521    521         int count = (pParse->nested==0);    /* True to count changes */
   522         -      int iIdxNoSeek = -1;
   523         -      if( bComplex==0 && aiCurOnePass[1]!=iDataCur ){
   524         -        iIdxNoSeek = aiCurOnePass[1];
   525         -      }
   526    522         sqlite3GenerateRowDelete(pParse, pTab, pTrigger, iDataCur, iIdxCur,
   527         -          iKey, nKey, count, OE_Default, eOnePass, iIdxNoSeek);
          523  +          iKey, nKey, count, OE_Default, eOnePass, aiCurOnePass[1]);
   528    524       }
   529    525     
   530    526       /* End of the loop over all rowids/primary-keys. */
   531    527       if( eOnePass!=ONEPASS_OFF ){
   532    528         sqlite3VdbeResolveLabel(v, addrBypass);
   533    529         sqlite3WhereEnd(pWInfo);
   534    530       }else if( pPk ){
................................................................................
   600    596   **   ONEPASS_MULTI.  If eMode is not ONEPASS_OFF, then the cursor
   601    597   **   iDataCur already points to the row to delete. If eMode is ONEPASS_OFF
   602    598   **   then this function must seek iDataCur to the entry identified by iPk
   603    599   **   and nPk before reading from it.
   604    600   **
   605    601   **   If eMode is ONEPASS_MULTI, then this call is being made as part
   606    602   **   of a ONEPASS delete that affects multiple rows. In this case, if 
   607         -**   iIdxNoSeek is a valid cursor number (>=0), then its position should
   608         -**   be preserved following the delete operation. Or, if iIdxNoSeek is not
   609         -**   a valid cursor number, the position of iDataCur should be preserved
   610         -**   instead.
          603  +**   iIdxNoSeek is a valid cursor number (>=0) and is not the same as
          604  +**   iDataCur, then its position should be preserved following the delete
          605  +**   operation. Or, if iIdxNoSeek is not a valid cursor number, the
          606  +**   position of iDataCur should be preserved instead.
   611    607   **
   612    608   ** iIdxNoSeek:
   613         -**   If iIdxNoSeek is a valid cursor number (>=0), then it identifies an
   614         -**   index cursor (from within array of cursors starting at iIdxCur) that
   615         -**   already points to the index entry to be deleted.
          609  +**   If iIdxNoSeek is a valid cursor number (>=0) not equal to iDataCur,
          610  +**   then it identifies an index cursor (from within array of cursors
          611  +**   starting at iIdxCur) that already points to the index entry to be deleted.
          612  +**   Except, this optimization is disabled if there are BEFORE triggers since
          613  +**   the trigger body might have moved the cursor.
   616    614   */
   617    615   void sqlite3GenerateRowDelete(
   618    616     Parse *pParse,     /* Parsing context */
   619    617     Table *pTab,       /* Table containing the row to be deleted */
   620    618     Trigger *pTrigger, /* List of triggers to (potentially) fire */
   621    619     int iDataCur,      /* Cursor from which column data is extracted */
   622    620     int iIdxCur,       /* First index cursor */
................................................................................
   679    677       addrStart = sqlite3VdbeCurrentAddr(v);
   680    678       sqlite3CodeRowTrigger(pParse, pTrigger, 
   681    679           TK_DELETE, 0, TRIGGER_BEFORE, pTab, iOld, onconf, iLabel
   682    680       );
   683    681   
   684    682       /* If any BEFORE triggers were coded, then seek the cursor to the 
   685    683       ** row to be deleted again. It may be that the BEFORE triggers moved
   686         -    ** the cursor or of already deleted the row that the cursor was
          684  +    ** the cursor or already deleted the row that the cursor was
   687    685       ** pointing to.
          686  +    **
          687  +    ** Also disable the iIdxNoSeek optimization since the BEFORE trigger
          688  +    ** may have moved that cursor.
   688    689       */
   689    690       if( addrStart<sqlite3VdbeCurrentAddr(v) ){
   690    691         sqlite3VdbeAddOp4Int(v, opSeek, iDataCur, iLabel, iPk, nPk);
   691    692         VdbeCoverageIf(v, opSeek==OP_NotExists);
   692    693         VdbeCoverageIf(v, opSeek==OP_NotFound);
          694  +      testcase( iIdxNoSeek>=0 );
          695  +      iIdxNoSeek = -1;
   693    696       }
   694    697   
   695    698       /* Do FK processing. This call checks that any FK constraints that
   696    699       ** refer to this table (i.e. constraints attached to other tables) 
   697    700       ** are not violated by deleting this row.  */
   698    701       sqlite3FkCheck(pParse, pTab, iOld, 0, 0, 0);
   699    702     }
................................................................................
   712    715       u8 p5 = 0;
   713    716       sqlite3GenerateRowIndexDelete(pParse, pTab, iDataCur, iIdxCur,0,iIdxNoSeek);
   714    717       sqlite3VdbeAddOp2(v, OP_Delete, iDataCur, (count?OPFLAG_NCHANGE:0));
   715    718       sqlite3VdbeAppendP4(v, (char*)pTab, P4_TABLE);
   716    719       if( eMode!=ONEPASS_OFF ){
   717    720         sqlite3VdbeChangeP5(v, OPFLAG_AUXDELETE);
   718    721       }
   719         -    if( iIdxNoSeek>=0 ){
          722  +    if( iIdxNoSeek>=0 && iIdxNoSeek!=iDataCur ){
   720    723         sqlite3VdbeAddOp1(v, OP_Delete, iIdxNoSeek);
   721    724       }
   722    725       if( eMode==ONEPASS_MULTI ) p5 |= OPFLAG_SAVEPOSITION;
   723    726       sqlite3VdbeChangeP5(v, p5);
   724    727     }
   725    728   
   726    729     /* Do any ON CASCADE, SET NULL or SET DEFAULT operations required to
................................................................................
   866    869       ** But we are getting ready to store this value back into an index, where
   867    870       ** it should be converted by to INTEGER again.  So omit the OP_RealAffinity
   868    871       ** opcode if it is present */
   869    872       sqlite3VdbeDeletePriorOpcode(v, OP_RealAffinity);
   870    873     }
   871    874     if( regOut ){
   872    875       sqlite3VdbeAddOp3(v, OP_MakeRecord, regBase, nCol, regOut);
          876  +    if( pIdx->pTable->pSelect ){
          877  +      const char *zAff = sqlite3IndexAffinityStr(pParse->db, pIdx);
          878  +      sqlite3VdbeChangeP4(v, -1, zAff, P4_TRANSIENT);
          879  +    }
   873    880     }
   874    881     sqlite3ReleaseTempRange(pParse, regBase, nCol);
   875    882     return regBase;
   876    883   }
   877    884   
   878    885   /*
   879    886   ** If a prior call to sqlite3GenerateIndexKey() generated a jump-over label

Changes to src/expr.c.

  1499   1499   ** pColumns and pExpr form a vector assignment which is part of the SET
  1500   1500   ** clause of an UPDATE statement.  Like this:
  1501   1501   **
  1502   1502   **        (a,b,c) = (expr1,expr2,expr3)
  1503   1503   ** Or:    (a,b,c) = (SELECT x,y,z FROM ....)
  1504   1504   **
  1505   1505   ** For each term of the vector assignment, append new entries to the
  1506         -** expression list pList.  In the case of a subquery on the LHS, append
         1506  +** expression list pList.  In the case of a subquery on the RHS, append
  1507   1507   ** TK_SELECT_COLUMN expressions.
  1508   1508   */
  1509   1509   ExprList *sqlite3ExprListAppendVector(
  1510   1510     Parse *pParse,         /* Parsing context */
  1511   1511     ExprList *pList,       /* List to which to append. Might be NULL */
  1512   1512     IdList *pColumns,      /* List of names of LHS of the assignment */
  1513   1513     Expr *pExpr            /* Vector expression to be appended. Might be NULL */
................................................................................
  3608   3608         const char *zId;       /* The function name */
  3609   3609         u32 constMask = 0;     /* Mask of function arguments that are constant */
  3610   3610         int i;                 /* Loop counter */
  3611   3611         sqlite3 *db = pParse->db;  /* The database connection */
  3612   3612         u8 enc = ENC(db);      /* The text encoding used by this database */
  3613   3613         CollSeq *pColl = 0;    /* A collating sequence */
  3614   3614   
         3615  +      if( ConstFactorOk(pParse) && sqlite3ExprIsConstantNotJoin(pExpr) ){
         3616  +        /* SQL functions can be expensive. So try to move constant functions
         3617  +        ** out of the inner loop, even if that means an extra OP_Copy. */
         3618  +        return sqlite3ExprCodeAtInit(pParse, pExpr, -1);
         3619  +      }
  3615   3620         assert( !ExprHasProperty(pExpr, EP_xIsSelect) );
  3616   3621         if( ExprHasProperty(pExpr, EP_TokenOnly) ){
  3617   3622           pFarg = 0;
  3618   3623         }else{
  3619   3624           pFarg = pExpr->x.pList;
  3620   3625         }
  3621   3626         nFarg = pFarg ? pFarg->nExpr : 0;
................................................................................
  3655   3660         /* The UNLIKELY() function is a no-op.  The result is the value
  3656   3661         ** of the first argument.
  3657   3662         */
  3658   3663         if( pDef->funcFlags & SQLITE_FUNC_UNLIKELY ){
  3659   3664           assert( nFarg>=1 );
  3660   3665           return sqlite3ExprCodeTarget(pParse, pFarg->a[0].pExpr, target);
  3661   3666         }
         3667  +
         3668  +#ifdef SQLITE_DEBUG
         3669  +      /* The AFFINITY() function evaluates to a string that describes
         3670  +      ** the type affinity of the argument.  This is used for testing of
         3671  +      ** the SQLite type logic.
         3672  +      */
         3673  +      if( pDef->funcFlags & SQLITE_FUNC_AFFINITY ){
         3674  +        const char *azAff[] = { "blob", "text", "numeric", "integer", "real" };
         3675  +        char aff;
         3676  +        assert( nFarg==1 );
         3677  +        aff = sqlite3ExprAffinity(pFarg->a[0].pExpr);
         3678  +        sqlite3VdbeLoadString(v, target, 
         3679  +                              aff ? azAff[aff-SQLITE_AFF_BLOB] : "none");
         3680  +        return target;
         3681  +      }
         3682  +#endif
  3662   3683   
  3663   3684         for(i=0; i<nFarg; i++){
  3664   3685           if( i<32 && sqlite3ExprIsConstant(pFarg->a[i].pExpr) ){
  3665   3686             testcase( i==31 );
  3666   3687             constMask |= MASKBIT32(i);
  3667   3688           }
  3668   3689           if( (pDef->funcFlags & SQLITE_FUNC_NEEDCOLL)!=0 && !pColl ){
................................................................................
  3972   3993     sqlite3ReleaseTempReg(pParse, regFree1);
  3973   3994     sqlite3ReleaseTempReg(pParse, regFree2);
  3974   3995     return inReg;
  3975   3996   }
  3976   3997   
  3977   3998   /*
  3978   3999   ** Factor out the code of the given expression to initialization time.
         4000  +**
         4001  +** If regDest>=0 then the result is always stored in that register and the
         4002  +** result is not reusable.  If regDest<0 then this routine is free to 
         4003  +** store the value whereever it wants.  The register where the expression 
         4004  +** is stored is returned.  When regDest<0, two identical expressions will
         4005  +** code to the same register.
  3979   4006   */
  3980         -void sqlite3ExprCodeAtInit(
         4007  +int sqlite3ExprCodeAtInit(
  3981   4008     Parse *pParse,    /* Parsing context */
  3982   4009     Expr *pExpr,      /* The expression to code when the VDBE initializes */
  3983         -  int regDest,      /* Store the value in this register */
  3984         -  u8 reusable       /* True if this expression is reusable */
         4010  +  int regDest       /* Store the value in this register */
  3985   4011   ){
  3986   4012     ExprList *p;
  3987   4013     assert( ConstFactorOk(pParse) );
  3988   4014     p = pParse->pConstExpr;
         4015  +  if( regDest<0 && p ){
         4016  +    struct ExprList_item *pItem;
         4017  +    int i;
         4018  +    for(pItem=p->a, i=p->nExpr; i>0; pItem++, i--){
         4019  +      if( pItem->reusable && sqlite3ExprCompare(pItem->pExpr,pExpr,-1)==0 ){
         4020  +        return pItem->u.iConstExprReg;
         4021  +      }
         4022  +    }
         4023  +  }
  3989   4024     pExpr = sqlite3ExprDup(pParse->db, pExpr, 0);
  3990   4025     p = sqlite3ExprListAppend(pParse, p, pExpr);
  3991   4026     if( p ){
  3992   4027        struct ExprList_item *pItem = &p->a[p->nExpr-1];
         4028  +     pItem->reusable = regDest<0;
         4029  +     if( regDest<0 ) regDest = ++pParse->nMem;
  3993   4030        pItem->u.iConstExprReg = regDest;
  3994         -     pItem->reusable = reusable;
  3995   4031     }
  3996   4032     pParse->pConstExpr = p;
         4033  +  return regDest;
  3997   4034   }
  3998   4035   
  3999   4036   /*
  4000   4037   ** Generate code to evaluate an expression and store the results
  4001   4038   ** into a register.  Return the register number where the results
  4002   4039   ** are stored.
  4003   4040   **
................................................................................
  4012   4049   int sqlite3ExprCodeTemp(Parse *pParse, Expr *pExpr, int *pReg){
  4013   4050     int r2;
  4014   4051     pExpr = sqlite3ExprSkipCollate(pExpr);
  4015   4052     if( ConstFactorOk(pParse)
  4016   4053      && pExpr->op!=TK_REGISTER
  4017   4054      && sqlite3ExprIsConstantNotJoin(pExpr)
  4018   4055     ){
  4019         -    ExprList *p = pParse->pConstExpr;
  4020         -    int i;
  4021   4056       *pReg  = 0;
  4022         -    if( p ){
  4023         -      struct ExprList_item *pItem;
  4024         -      for(pItem=p->a, i=p->nExpr; i>0; pItem++, i--){
  4025         -        if( pItem->reusable && sqlite3ExprCompare(pItem->pExpr,pExpr,-1)==0 ){
  4026         -          return pItem->u.iConstExprReg;
  4027         -        }
  4028         -      }
  4029         -    }
  4030         -    r2 = ++pParse->nMem;
  4031         -    sqlite3ExprCodeAtInit(pParse, pExpr, r2, 1);
         4057  +    r2 = sqlite3ExprCodeAtInit(pParse, pExpr, -1);
  4032   4058     }else{
  4033   4059       int r1 = sqlite3GetTempReg(pParse);
  4034   4060       r2 = sqlite3ExprCodeTarget(pParse, pExpr, r1);
  4035   4061       if( r2==r1 ){
  4036   4062         *pReg = r1;
  4037   4063       }else{
  4038   4064         sqlite3ReleaseTempReg(pParse, r1);
................................................................................
  4078   4104   ** Generate code that will evaluate expression pExpr and store the
  4079   4105   ** results in register target.  The results are guaranteed to appear
  4080   4106   ** in register target.  If the expression is constant, then this routine
  4081   4107   ** might choose to code the expression at initialization time.
  4082   4108   */
  4083   4109   void sqlite3ExprCodeFactorable(Parse *pParse, Expr *pExpr, int target){
  4084   4110     if( pParse->okConstFactor && sqlite3ExprIsConstant(pExpr) ){
  4085         -    sqlite3ExprCodeAtInit(pParse, pExpr, target, 0);
         4111  +    sqlite3ExprCodeAtInit(pParse, pExpr, target);
  4086   4112     }else{
  4087   4113       sqlite3ExprCode(pParse, pExpr, target);
  4088   4114     }
  4089   4115   }
  4090   4116   
  4091   4117   /*
  4092   4118   ** Generate code that evaluates the given expression and puts the result
................................................................................
  4150   4176         if( flags & SQLITE_ECEL_OMITREF ){
  4151   4177           i--;
  4152   4178           n--;
  4153   4179         }else{
  4154   4180           sqlite3VdbeAddOp2(v, copyOp, j+srcReg-1, target+i);
  4155   4181         }
  4156   4182       }else if( (flags & SQLITE_ECEL_FACTOR)!=0 && sqlite3ExprIsConstant(pExpr) ){
  4157         -      sqlite3ExprCodeAtInit(pParse, pExpr, target+i, 0);
         4183  +      sqlite3ExprCodeAtInit(pParse, pExpr, target+i);
  4158   4184       }else{
  4159   4185         int inReg = sqlite3ExprCodeTarget(pParse, pExpr, target+i);
  4160   4186         if( inReg!=target+i ){
  4161   4187           VdbeOp *pOp;
  4162   4188           if( copyOp==OP_Copy
  4163   4189            && (pOp=sqlite3VdbeGetOp(v, -1))->opcode==OP_Copy
  4164   4190            && pOp->p1+pOp->p3+1==inReg

Changes to src/func.c.

  1771   1771   #ifndef SQLITE_OMIT_COMPILEOPTION_DIAGS
  1772   1772       DFUNCTION(sqlite_compileoption_used,1, 0, 0, compileoptionusedFunc  ),
  1773   1773       DFUNCTION(sqlite_compileoption_get, 1, 0, 0, compileoptiongetFunc  ),
  1774   1774   #endif /* SQLITE_OMIT_COMPILEOPTION_DIAGS */
  1775   1775       FUNCTION2(unlikely,          1, 0, 0, noopFunc,  SQLITE_FUNC_UNLIKELY),
  1776   1776       FUNCTION2(likelihood,        2, 0, 0, noopFunc,  SQLITE_FUNC_UNLIKELY),
  1777   1777       FUNCTION2(likely,            1, 0, 0, noopFunc,  SQLITE_FUNC_UNLIKELY),
         1778  +#ifdef SQLITE_DEBUG
         1779  +    FUNCTION2(affinity,          1, 0, 0, noopFunc,  SQLITE_FUNC_AFFINITY),
         1780  +#endif
  1778   1781       FUNCTION(ltrim,              1, 1, 0, trimFunc         ),
  1779   1782       FUNCTION(ltrim,              2, 1, 0, trimFunc         ),
  1780   1783       FUNCTION(rtrim,              1, 2, 0, trimFunc         ),
  1781   1784       FUNCTION(rtrim,              2, 2, 0, trimFunc         ),
  1782   1785       FUNCTION(trim,               1, 3, 0, trimFunc         ),
  1783   1786       FUNCTION(trim,               2, 3, 0, trimFunc         ),
  1784   1787       FUNCTION(min,               -1, 0, 1, minmaxFunc       ),

Changes to src/global.c.

   164    164   ** memory.  (The statement journal is also always held entirely in memory
   165    165   ** if journal_mode=MEMORY or if temp_store=MEMORY, regardless of this
   166    166   ** setting.)
   167    167   */
   168    168   #ifndef SQLITE_STMTJRNL_SPILL 
   169    169   # define SQLITE_STMTJRNL_SPILL (64*1024)
   170    170   #endif
          171  +
          172  +/*
          173  +** The default lookaside-configuration, the format "SZ,N".  SZ is the
          174  +** number of bytes in each lookaside slot (should be a multiple of 8)
          175  +** and N is the number of slots.  The lookaside-configuration can be
          176  +** changed as start-time using sqlite3_config(SQLITE_CONFIG_LOOKASIDE)
          177  +** or at run-time for an individual database connection using
          178  +** sqlite3_db_config(db, SQLITE_DBCONFIG_LOOKASIDE);
          179  +*/
          180  +#ifndef SQLITE_DEFAULT_LOOKASIDE
          181  +# define SQLITE_DEFAULT_LOOKASIDE 1200,100
          182  +#endif
          183  +
   171    184   
   172    185   /*
   173    186   ** The following singleton contains the global configuration for
   174    187   ** the SQLite library.
   175    188   */
   176    189   SQLITE_WSD struct Sqlite3Config sqlite3Config = {
   177    190      SQLITE_DEFAULT_MEMSTATUS,  /* bMemstat */
   178    191      1,                         /* bCoreMutex */
   179    192      SQLITE_THREADSAFE==1,      /* bFullMutex */
   180    193      SQLITE_USE_URI,            /* bOpenUri */
   181    194      SQLITE_ALLOW_COVERING_INDEX_SCAN,   /* bUseCis */
   182    195      0x7ffffffe,                /* mxStrlen */
   183    196      0,                         /* neverCorrupt */
   184         -   512,                       /* szLookaside */
   185         -   125,                       /* nLookaside */
          197  +   SQLITE_DEFAULT_LOOKASIDE,  /* szLookaside, nLookaside */
   186    198      SQLITE_STMTJRNL_SPILL,     /* nStmtSpill */
   187    199      {0,0,0,0,0,0,0,0},         /* m */
   188    200      {0,0,0,0,0,0,0,0,0},       /* mutex */
   189    201      {0,0,0,0,0,0,0,0,0,0,0,0,0},/* pcache2 */
   190    202      (void*)0,                  /* pHeap */
   191    203      0,                         /* nHeap */
   192    204      0, 0,                      /* mnHeap, mxHeap */

Changes to src/insert.c.

  1647   1647           assert( onError==OE_Replace );
  1648   1648           sqlite3MultiWrite(pParse);
  1649   1649           if( db->flags&SQLITE_RecTriggers ){
  1650   1650             pTrigger = sqlite3TriggersExist(pParse, pTab, TK_DELETE, 0, 0);
  1651   1651           }
  1652   1652           sqlite3GenerateRowDelete(pParse, pTab, pTrigger, iDataCur, iIdxCur,
  1653   1653               regR, nPkField, 0, OE_Replace,
  1654         -            (pIdx==pPk ? ONEPASS_SINGLE : ONEPASS_OFF), -1);
         1654  +            (pIdx==pPk ? ONEPASS_SINGLE : ONEPASS_OFF), iThisCur);
  1655   1655           seenReplace = 1;
  1656   1656           break;
  1657   1657         }
  1658   1658       }
  1659   1659       sqlite3VdbeResolveLabel(v, addrUniqueOk);
  1660   1660       if( regR!=regIdx ) sqlite3ReleaseTempRange(pParse, regR, nPkField);
  1661   1661     }
................................................................................
  1663   1663       sqlite3VdbeGoto(v, ipkTop+1);
  1664   1664       sqlite3VdbeJumpHere(v, ipkBottom);
  1665   1665     }
  1666   1666     
  1667   1667     *pbMayReplace = seenReplace;
  1668   1668     VdbeModuleComment((v, "END: GenCnstCks(%d)", seenReplace));
  1669   1669   }
         1670  +
         1671  +#ifdef SQLITE_ENABLE_NULL_TRIM
         1672  +/*
         1673  +** Change the P5 operand on the last opcode (which should be an OP_MakeRecord)
         1674  +** to be the number of columns in table pTab that must not be NULL-trimmed.
         1675  +**
         1676  +** Or if no columns of pTab may be NULL-trimmed, leave P5 at zero.
         1677  +*/
         1678  +void sqlite3SetMakeRecordP5(Vdbe *v, Table *pTab){
         1679  +  u16 i;
         1680  +
         1681  +  /* Records with omitted columns are only allowed for schema format
         1682  +  ** version 2 and later (SQLite version 3.1.4, 2005-02-20). */
         1683  +  if( pTab->pSchema->file_format<2 ) return;
         1684  +
         1685  +  for(i=pTab->nCol; i>1 && pTab->aCol[i-1].pDflt==0; i--){}
         1686  +  sqlite3VdbeChangeP5(v, i);
         1687  +}
         1688  +#endif
  1670   1689   
  1671   1690   /*
  1672   1691   ** This routine generates code to finish the INSERT or UPDATE operation
  1673   1692   ** that was started by a prior call to sqlite3GenerateConstraintChecks.
  1674   1693   ** A consecutive range of registers starting at regNewData contains the
  1675   1694   ** rowid and the content to be inserted.
  1676   1695   **
................................................................................
  1680   1699   void sqlite3CompleteInsertion(
  1681   1700     Parse *pParse,      /* The parser context */
  1682   1701     Table *pTab,        /* the table into which we are inserting */
  1683   1702     int iDataCur,       /* Cursor of the canonical data source */
  1684   1703     int iIdxCur,        /* First index cursor */
  1685   1704     int regNewData,     /* Range of content */
  1686   1705     int *aRegIdx,       /* Register used by each index.  0 for unused indices */
  1687         -  int isUpdate,       /* True for UPDATE, False for INSERT */
         1706  +  int update_flags,   /* True for UPDATE, False for INSERT */
  1688   1707     int appendBias,     /* True if this is likely to be an append */
  1689   1708     int useSeekResult   /* True to set the USESEEKRESULT flag on OP_[Idx]Insert */
  1690   1709   ){
  1691   1710     Vdbe *v;            /* Prepared statements under construction */
  1692   1711     Index *pIdx;        /* An index being inserted or updated */
  1693   1712     u8 pik_flags;       /* flag values passed to the btree insert */
  1694   1713     int regData;        /* Content registers (after the rowid) */
  1695   1714     int regRec;         /* Register holding assembled record for the table */
  1696   1715     int i;              /* Loop counter */
  1697   1716     u8 bAffinityDone = 0; /* True if OP_Affinity has been run already */
         1717  +
         1718  +  assert( update_flags==0
         1719  +       || update_flags==OPFLAG_ISUPDATE
         1720  +       || update_flags==(OPFLAG_ISUPDATE|OPFLAG_SAVEPOSITION)
         1721  +  );
  1698   1722   
  1699   1723     v = sqlite3GetVdbe(pParse);
  1700   1724     assert( v!=0 );
  1701   1725     assert( pTab->pSelect==0 );  /* This table is not a VIEW */
  1702   1726     for(i=0, pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext, i++){
  1703   1727       if( aRegIdx[i]==0 ) continue;
  1704   1728       bAffinityDone = 1;
................................................................................
  1710   1734                            aRegIdx[i]+1,
  1711   1735                            pIdx->uniqNotNull ? pIdx->nKeyCol: pIdx->nColumn);
  1712   1736       pik_flags = 0;
  1713   1737       if( useSeekResult ) pik_flags = OPFLAG_USESEEKRESULT;
  1714   1738       if( IsPrimaryKeyIndex(pIdx) && !HasRowid(pTab) ){
  1715   1739         assert( pParse->nested==0 );
  1716   1740         pik_flags |= OPFLAG_NCHANGE;
         1741  +      pik_flags |= (update_flags & OPFLAG_SAVEPOSITION);
  1717   1742       }
  1718   1743       sqlite3VdbeChangeP5(v, pik_flags);
  1719   1744     }
  1720   1745     if( !HasRowid(pTab) ) return;
  1721   1746     regData = regNewData + 1;
  1722   1747     regRec = sqlite3GetTempReg(pParse);
  1723   1748     sqlite3VdbeAddOp3(v, OP_MakeRecord, regData, pTab->nCol, regRec);
         1749  +  sqlite3SetMakeRecordP5(v, pTab);
  1724   1750     if( !bAffinityDone ){
  1725   1751       sqlite3TableAffinity(v, pTab, 0);
  1726   1752       sqlite3ExprCacheAffinityChange(pParse, regData, pTab->nCol);
  1727   1753     }
  1728   1754     if( pParse->nested ){
  1729   1755       pik_flags = 0;
  1730   1756     }else{
  1731   1757       pik_flags = OPFLAG_NCHANGE;
  1732         -    pik_flags |= (isUpdate?OPFLAG_ISUPDATE:OPFLAG_LASTROWID);
         1758  +    pik_flags |= (update_flags?update_flags:OPFLAG_LASTROWID);
  1733   1759     }
  1734   1760     if( appendBias ){
  1735   1761       pik_flags |= OPFLAG_APPEND;
  1736   1762     }
  1737   1763     if( useSeekResult ){
  1738   1764       pik_flags |= OPFLAG_USESEEKRESULT;
  1739   1765     }
................................................................................
  2134   2160         autoIncStep(pParse, regAutoinc, regRowid);
  2135   2161       }else if( pDest->pIndex==0 ){
  2136   2162         addr1 = sqlite3VdbeAddOp2(v, OP_NewRowid, iDest, regRowid);
  2137   2163       }else{
  2138   2164         addr1 = sqlite3VdbeAddOp2(v, OP_Rowid, iSrc, regRowid);
  2139   2165         assert( (pDest->tabFlags & TF_Autoincrement)==0 );
  2140   2166       }
  2141         -    sqlite3VdbeAddOp2(v, OP_RowData, iSrc, regData);
         2167  +    sqlite3VdbeAddOp3(v, OP_RowData, iSrc, regData, 1);
  2142   2168       if( db->flags & SQLITE_Vacuum ){
  2143   2169         sqlite3VdbeAddOp3(v, OP_Last, iDest, 0, -1);
  2144   2170         insFlags = OPFLAG_NCHANGE|OPFLAG_LASTROWID|
  2145   2171                              OPFLAG_APPEND|OPFLAG_USESEEKRESULT;
  2146   2172       }else{
  2147   2173         insFlags = OPFLAG_NCHANGE|OPFLAG_LASTROWID|OPFLAG_APPEND;
  2148   2174       }
................................................................................
  2166   2192       sqlite3VdbeSetP4KeyInfo(pParse, pSrcIdx);
  2167   2193       VdbeComment((v, "%s", pSrcIdx->zName));
  2168   2194       sqlite3VdbeAddOp3(v, OP_OpenWrite, iDest, pDestIdx->tnum, iDbDest);
  2169   2195       sqlite3VdbeSetP4KeyInfo(pParse, pDestIdx);
  2170   2196       sqlite3VdbeChangeP5(v, OPFLAG_BULKCSR);
  2171   2197       VdbeComment((v, "%s", pDestIdx->zName));
  2172   2198       addr1 = sqlite3VdbeAddOp2(v, OP_Rewind, iSrc, 0); VdbeCoverage(v);
  2173         -    sqlite3VdbeAddOp2(v, OP_RowData, iSrc, regData);
         2199  +    sqlite3VdbeAddOp3(v, OP_RowData, iSrc, regData, 1);
  2174   2200       if( db->flags & SQLITE_Vacuum ){
  2175   2201         /* This INSERT command is part of a VACUUM operation, which guarantees
  2176   2202         ** that the destination table is empty. If all indexed columns use
  2177   2203         ** collation sequence BINARY, then it can also be assumed that the
  2178   2204         ** index will be populated by inserting keys in strictly sorted 
  2179   2205         ** order. In this case, instead of seeking within the b-tree as part
  2180   2206         ** of every OP_IdxInsert opcode, an OP_Last is added before the

Changes to src/loadext.c.

    14     14   */
    15     15   
    16     16   #ifndef SQLITE_CORE
    17     17     #define SQLITE_CORE 1  /* Disable the API redefinition in sqlite3ext.h */
    18     18   #endif
    19     19   #include "sqlite3ext.h"
    20     20   #include "sqliteInt.h"
    21         -#include <string.h>
    22     21   
    23     22   #ifndef SQLITE_OMIT_LOAD_EXTENSION
    24     23   /*
    25     24   ** Some API routines are omitted when various features are
    26     25   ** excluded from a build of SQLite.  Substitute a NULL pointer
    27     26   ** for any missing APIs.
    28     27   */

Changes to src/malloc.c.

   213    213     sqlite3_mutex_enter(mem0.mutex);
   214    214   }
   215    215   
   216    216   /*
   217    217   ** Do a memory allocation with statistics and alarms.  Assume the
   218    218   ** lock is already held.
   219    219   */
   220         -static int mallocWithAlarm(int n, void **pp){
   221         -  int nFull;
          220  +static void mallocWithAlarm(int n, void **pp){
   222    221     void *p;
          222  +  int nFull = 0;
   223    223     assert( sqlite3_mutex_held(mem0.mutex) );
   224         -  nFull = sqlite3GlobalConfig.m.xRoundup(n);
   225    224     sqlite3StatusHighwater(SQLITE_STATUS_MALLOC_SIZE, n);
   226    225     if( mem0.alarmThreshold>0 ){
   227    226       sqlite3_int64 nUsed = sqlite3StatusValue(SQLITE_STATUS_MEMORY_USED);
          227  +    nFull = sqlite3GlobalConfig.m.xRoundup(n);
   228    228       if( nUsed >= mem0.alarmThreshold - nFull ){
   229    229         mem0.nearlyFull = 1;
   230    230         sqlite3MallocAlarm(nFull);
   231    231       }else{
   232    232         mem0.nearlyFull = 0;
   233    233       }
   234    234     }
   235         -  p = sqlite3GlobalConfig.m.xMalloc(nFull);
          235  +  p = sqlite3GlobalConfig.m.xMalloc(n);
   236    236   #ifdef SQLITE_ENABLE_MEMORY_MANAGEMENT
   237    237     if( p==0 && mem0.alarmThreshold>0 ){
   238    238       sqlite3MallocAlarm(nFull);
   239         -    p = sqlite3GlobalConfig.m.xMalloc(nFull);
          239  +    p = sqlite3GlobalConfig.m.xMalloc(n);
   240    240     }
   241    241   #endif
   242    242     if( p ){
   243    243       nFull = sqlite3MallocSize(p);
   244    244       sqlite3StatusUp(SQLITE_STATUS_MEMORY_USED, nFull);
   245    245       sqlite3StatusUp(SQLITE_STATUS_MALLOC_COUNT, 1);
   246    246     }
   247    247     *pp = p;
   248         -  return nFull;
   249    248   }
   250    249   
   251    250   /*
   252    251   ** Allocate memory.  This routine is like sqlite3_malloc() except that it
   253    252   ** assumes the memory subsystem has already been initialized.
   254    253   */
   255    254   void *sqlite3Malloc(u64 n){

Changes to src/pager.c.

   810    810   ** instead of
   811    811   **
   812    812   **   if( pPager->jfd->pMethods ){ ...
   813    813   */
   814    814   #define isOpen(pFd) ((pFd)->pMethods!=0)
   815    815   
   816    816   /*
   817         -** Return true if this pager uses a write-ahead log instead of the usual
   818         -** rollback journal. Otherwise false.
          817  +** Return true if this pager uses a write-ahead log to read page pgno.
          818  +** Return false if the pager reads pgno directly from the database.
   819    819   */
          820  +#if !defined(SQLITE_OMIT_WAL) && defined(SQLITE_DIRECT_OVERFLOW_READ)
          821  +int sqlite3PagerUseWal(Pager *pPager, Pgno pgno){
          822  +  u32 iRead = 0;
          823  +  int rc;
          824  +  if( pPager->pWal==0 ) return 0;
          825  +  rc = sqlite3WalFindFrame(pPager->pWal, pgno, &iRead);
          826  +  return rc || iRead;
          827  +}
          828  +#endif
   820    829   #ifndef SQLITE_OMIT_WAL
   821         -int sqlite3PagerUseWal(Pager *pPager){
   822         -  return (pPager->pWal!=0);
   823         -}
   824         -# define pagerUseWal(x) sqlite3PagerUseWal(x)
          830  +# define pagerUseWal(x) ((x)->pWal!=0)
   825    831   #else
   826    832   # define pagerUseWal(x) 0
   827    833   # define pagerRollbackWal(x) 0
   828    834   # define pagerWalFrames(v,w,x,y) 0
   829    835   # define pagerOpenWalIfPresent(z) SQLITE_OK
   830    836   # define pagerBeginReadTransaction(z) SQLITE_OK
   831    837   #endif

Changes to src/pager.h.

   174    174   
   175    175   #ifndef SQLITE_OMIT_WAL
   176    176     int sqlite3PagerCheckpoint(Pager *pPager, sqlite3*, int, int*, int*);
   177    177     int sqlite3PagerWalSupported(Pager *pPager);
   178    178     int sqlite3PagerWalCallback(Pager *pPager);
   179    179     int sqlite3PagerOpenWal(Pager *pPager, int *pisOpen);
   180    180     int sqlite3PagerCloseWal(Pager *pPager, sqlite3*);
   181         -  int sqlite3PagerUseWal(Pager *pPager);
          181  +# ifdef SQLITE_DIRECT_OVERFLOW_READ
          182  +  int sqlite3PagerUseWal(Pager *pPager, Pgno);
          183  +# endif
   182    184   # ifdef SQLITE_ENABLE_SNAPSHOT
   183    185     int sqlite3PagerSnapshotGet(Pager *pPager, sqlite3_snapshot **ppSnapshot);
   184    186     int sqlite3PagerSnapshotOpen(Pager *pPager, sqlite3_snapshot *pSnapshot);
   185    187     int sqlite3PagerSnapshotRecover(Pager *pPager);
   186    188   # endif
   187    189   #else
   188         -# define sqlite3PagerUseWal(x) 0
          190  +# define sqlite3PagerUseWal(x,y) 0
   189    191   #endif
   190    192   
   191    193   #ifdef SQLITE_ENABLE_ZIPVFS
   192    194     int sqlite3PagerWalFramesize(Pager *pPager);
   193    195   #endif
   194    196   
   195    197   /* Functions used to query pager state and configuration. */

Changes to src/printf.c.

    55     55     etByte prefix;           /* Offset into aPrefix[] of the prefix string */
    56     56   } et_info;
    57     57   
    58     58   /*
    59     59   ** Allowed values for et_info.flags
    60     60   */
    61     61   #define FLAG_SIGNED  1     /* True if the value to convert is signed */
    62         -#define FLAG_INTERN  2     /* True if for internal use only */
    63     62   #define FLAG_STRING  4     /* Allow infinity precision */
    64     63   
    65     64   
    66     65   /*
    67     66   ** The following table is searched linearly, so it is good to put the
    68     67   ** most frequently used conversion types first.
    69     68   */
................................................................................
    89     88     {  'G',  0, 1, etGENERIC,    14, 0 },
    90     89   #endif
    91     90     {  'i', 10, 1, etRADIX,      0,  0 },
    92     91     {  'n',  0, 0, etSIZE,       0,  0 },
    93     92     {  '%',  0, 0, etPERCENT,    0,  0 },
    94     93     {  'p', 16, 0, etPOINTER,    0,  1 },
    95     94   
    96         -/* All the rest have the FLAG_INTERN bit set and are thus for internal
    97         -** use only */
    98         -  {  'T',  0, 2, etTOKEN,      0,  0 },
    99         -  {  'S',  0, 2, etSRCLIST,    0,  0 },
   100         -  {  'r', 10, 3, etORDINAL,    0,  0 },
           95  +  /* All the rest are undocumented and are for internal use only */
           96  +  {  'T',  0, 0, etTOKEN,      0,  0 },
           97  +  {  'S',  0, 0, etSRCLIST,    0,  0 },
           98  +  {  'r', 10, 1, etORDINAL,    0,  0 },
   101     99   };
   102    100   
   103    101   /*
   104    102   ** If SQLITE_OMIT_FLOATING_POINT is defined, then none of the floating point
   105    103   ** conversions will work.
   106    104   */
   107    105   #ifndef SQLITE_OMIT_FLOATING_POINT
................................................................................
   187    185     etByte flag_altform2;      /* True if "!" flag is present */
   188    186     etByte flag_zeropad;       /* True if field width constant starts with zero */
   189    187     etByte flag_long;          /* True if "l" flag is present */
   190    188     etByte flag_longlong;      /* True if the "ll" flag is present */
   191    189     etByte done;               /* Loop termination flag */
   192    190     etByte xtype = etINVALID;  /* Conversion paradigm */
   193    191     u8 bArgList;               /* True for SQLITE_PRINTF_SQLFUNC */
   194         -  u8 useIntern;              /* Ok to use internal conversions (ex: %T) */
   195    192     char prefix;               /* Prefix character.  "+" or "-" or " " or '\0'. */
   196    193     sqlite_uint64 longvalue;   /* Value for integer types */
   197    194     LONGDOUBLE_TYPE realvalue; /* Value for real types */
   198    195     const et_info *infop;      /* Pointer to the appropriate info structure */
   199    196     char *zOut;                /* Rendering buffer */
   200    197     int nOut;                  /* Size of the rendering buffer */
   201    198     char *zExtra = 0;          /* Malloced memory used by some conversion */
................................................................................
   206    203     etByte flag_dp;            /* True if decimal point should be shown */
   207    204     etByte flag_rtz;           /* True if trailing zeros should be removed */
   208    205   #endif
   209    206     PrintfArguments *pArgList = 0; /* Arguments for SQLITE_PRINTF_SQLFUNC */
   210    207     char buf[etBUFSIZE];       /* Conversion buffer */
   211    208   
   212    209     bufpt = 0;
   213         -  if( pAccum->printfFlags ){
   214         -    if( (bArgList = (pAccum->printfFlags & SQLITE_PRINTF_SQLFUNC))!=0 ){
   215         -      pArgList = va_arg(ap, PrintfArguments*);
   216         -    }
   217         -    useIntern = pAccum->printfFlags & SQLITE_PRINTF_INTERNAL;
          210  +  if( (pAccum->printfFlags & SQLITE_PRINTF_SQLFUNC)!=0 ){
          211  +    pArgList = va_arg(ap, PrintfArguments*);
          212  +    bArgList = 1;
   218    213     }else{
   219         -    bArgList = useIntern = 0;
          214  +    bArgList = 0;
   220    215     }
   221    216     for(; (c=(*fmt))!=0; ++fmt){
   222    217       if( c!='%' ){
   223    218         bufpt = (char *)fmt;
   224    219   #if HAVE_STRCHRNUL
   225    220         fmt = strchrnul(fmt, '%');
   226    221   #else
................................................................................
   324    319       }
   325    320       /* Fetch the info entry for the field */
   326    321       infop = &fmtinfo[0];
   327    322       xtype = etINVALID;
   328    323       for(idx=0; idx<ArraySize(fmtinfo); idx++){
   329    324         if( c==fmtinfo[idx].fmttype ){
   330    325           infop = &fmtinfo[idx];
   331         -        if( useIntern || (infop->flags & FLAG_INTERN)==0 ){
   332         -          xtype = infop->type;
   333         -        }else{
   334         -          return;
   335         -        }
          326  +        xtype = infop->type;
   336    327           break;
   337    328         }
   338    329       }
   339    330   
   340    331       /*
   341    332       ** At this point, variables are initialized as follows:
   342    333       **
................................................................................
   697    688           length = j;
   698    689           /* The precision in %q and %Q means how many input characters to
   699    690           ** consume, not the length of the output...
   700    691           ** if( precision>=0 && precision<length ) length = precision; */
   701    692           break;
   702    693         }
   703    694         case etTOKEN: {
   704         -        Token *pToken = va_arg(ap, Token*);
          695  +        Token *pToken;
          696  +        if( (pAccum->printfFlags & SQLITE_PRINTF_INTERNAL)==0 ) return;
          697  +        pToken = va_arg(ap, Token*);
   705    698           assert( bArgList==0 );
   706    699           if( pToken && pToken->n ){
   707    700             sqlite3StrAccumAppend(pAccum, (const char*)pToken->z, pToken->n);
   708    701           }
   709    702           length = width = 0;
   710    703           break;
   711    704         }
   712    705         case etSRCLIST: {
   713         -        SrcList *pSrc = va_arg(ap, SrcList*);
   714         -        int k = va_arg(ap, int);
   715         -        struct SrcList_item *pItem = &pSrc->a[k];
          706  +        SrcList *pSrc;
          707  +        int k;
          708  +        struct SrcList_item *pItem;
          709  +        if( (pAccum->printfFlags & SQLITE_PRINTF_INTERNAL)==0 ) return;
          710  +        pSrc = va_arg(ap, SrcList*);
          711  +        k = va_arg(ap, int);
          712  +        pItem = &pSrc->a[k];
   716    713           assert( bArgList==0 );
   717    714           assert( k>=0 && k<pSrc->nSrc );
   718    715           if( pItem->zDatabase ){
   719    716             sqlite3StrAccumAppendAll(pAccum, pItem->zDatabase);
   720    717             sqlite3StrAccumAppend(pAccum, ".", 1);
   721    718           }
   722    719           sqlite3StrAccumAppendAll(pAccum, pItem->zName);
................................................................................
   730    727       }/* End switch over the format type */
   731    728       /*
   732    729       ** The text of the conversion is pointed to by "bufpt" and is
   733    730       ** "length" characters long.  The field width is "width".  Do
   734    731       ** the output.
   735    732       */
   736    733       width -= length;
   737         -    if( width>0 && !flag_leftjustify ) sqlite3AppendChar(pAccum, width, ' ');
   738         -    sqlite3StrAccumAppend(pAccum, bufpt, length);
   739         -    if( width>0 && flag_leftjustify ) sqlite3AppendChar(pAccum, width, ' ');
          734  +    if( width>0 ){
          735  +      if( !flag_leftjustify ) sqlite3AppendChar(pAccum, width, ' ');
          736  +      sqlite3StrAccumAppend(pAccum, bufpt, length);
          737  +      if( flag_leftjustify ) sqlite3AppendChar(pAccum, width, ' ');
          738  +    }else{
          739  +      sqlite3StrAccumAppend(pAccum, bufpt, length);
          740  +    }
   740    741   
   741    742       if( zExtra ){
   742    743         sqlite3DbFree(pAccum->db, zExtra);
   743    744         zExtra = 0;
   744    745       }
   745    746     }/* End for loop over the format string */
   746    747   } /* End of function */

Changes to src/resolve.c.

    11     11   *************************************************************************
    12     12   **
    13     13   ** This file contains routines used for walking the parser tree and
    14     14   ** resolve all identifiers by associating them with a particular
    15     15   ** table and column.
    16     16   */
    17     17   #include "sqliteInt.h"
    18         -#include <stdlib.h>
    19         -#include <string.h>
    20     18   
    21     19   /*
    22     20   ** Walk the expression tree pExpr and increase the aggregate function
    23     21   ** depth (the Expr.op2 field) by N on every TK_AGG_FUNCTION node.
    24     22   ** This needs to occur when copying a TK_AGG_FUNCTION node from an
    25     23   ** outer query into an inner subquery.
    26     24   **

Changes to src/select.c.

   653    653     int r1;
   654    654   
   655    655     v = pParse->pVdbe;
   656    656     r1 = sqlite3GetTempReg(pParse);
   657    657     sqlite3VdbeAddOp4Int(v, OP_Found, iTab, addrRepeat, iMem, N); VdbeCoverage(v);
   658    658     sqlite3VdbeAddOp3(v, OP_MakeRecord, iMem, N, r1);
   659    659     sqlite3VdbeAddOp4Int(v, OP_IdxInsert, iTab, r1, iMem, N);
          660  +  sqlite3VdbeChangeP5(v, OPFLAG_USESEEKRESULT);
   660    661     sqlite3ReleaseTempReg(pParse, r1);
   661    662   }
   662    663   
   663    664   /*
   664    665   ** This routine generates the code for the inside of the inner loop
   665    666   ** of a SELECT.
   666    667   **
................................................................................
  5647   5648           }
  5648   5649     
  5649   5650           /* This case runs if the aggregate has no GROUP BY clause.  The
  5650   5651           ** processing is much simpler since there is only a single row
  5651   5652           ** of output.
  5652   5653           */
  5653   5654           resetAccumulator(pParse, &sAggInfo);
  5654         -        pWInfo = sqlite3WhereBegin(pParse, pTabList, pWhere, pMinMax,0,flag,0);
         5655  +        pWInfo = sqlite3WhereBegin(pParse, pTabList, pWhere, pMinMax, 0,flag,0);
  5655   5656           if( pWInfo==0 ){
  5656   5657             sqlite3ExprListDelete(db, pDel);
  5657   5658             goto select_end;
  5658   5659           }
  5659   5660           updateAccumulator(pParse, &sAggInfo);
  5660   5661           assert( pMinMax==0 || pMinMax->nExpr==1 );
  5661   5662           if( sqlite3WhereIsOrdered(pWInfo)>0 ){

Changes to src/shell.c.

  4284   4284   
  4285   4285     if( c=='m' && strncmp(azArg[0], "mode", n)==0 ){
  4286   4286       const char *zMode = nArg>=2 ? azArg[1] : "";
  4287   4287       int n2 = (int)strlen(zMode);
  4288   4288       int c2 = zMode[0];
  4289   4289       if( c2=='l' && n2>2 && strncmp(azArg[1],"lines",n2)==0 ){
  4290   4290         p->mode = MODE_Line;
         4291  +      sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator, SEP_Row);
  4291   4292       }else if( c2=='c' && strncmp(azArg[1],"columns",n2)==0 ){
  4292   4293         p->mode = MODE_Column;
         4294  +      sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator, SEP_Row);
  4293   4295       }else if( c2=='l' && n2>2 && strncmp(azArg[1],"list",n2)==0 ){
  4294   4296         p->mode = MODE_List;
         4297  +      sqlite3_snprintf(sizeof(p->colSeparator), p->colSeparator, SEP_Column);
         4298  +      sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator, SEP_Row);
  4295   4299       }else if( c2=='h' && strncmp(azArg[1],"html",n2)==0 ){
  4296   4300         p->mode = MODE_Html;
  4297   4301       }else if( c2=='t' && strncmp(azArg[1],"tcl",n2)==0 ){
  4298   4302         p->mode = MODE_Tcl;
  4299   4303         sqlite3_snprintf(sizeof(p->colSeparator), p->colSeparator, SEP_Space);
         4304  +      sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator, SEP_Row);
  4300   4305       }else if( c2=='c' && strncmp(azArg[1],"csv",n2)==0 ){
  4301   4306         p->mode = MODE_Csv;
  4302   4307         sqlite3_snprintf(sizeof(p->colSeparator), p->colSeparator, SEP_Comma);
  4303   4308         sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator, SEP_CrLf);
  4304   4309       }else if( c2=='t' && strncmp(azArg[1],"tabs",n2)==0 ){
  4305   4310         p->mode = MODE_List;
  4306   4311         sqlite3_snprintf(sizeof(p->colSeparator), p->colSeparator, SEP_Tab);
................................................................................
  5293   5298     if( c=='v' && strncmp(azArg[0], "version", n)==0 ){
  5294   5299       utf8_printf(p->out, "SQLite %s %s\n" /*extra-version-info*/,
  5295   5300           sqlite3_libversion(), sqlite3_sourceid());
  5296   5301     }else
  5297   5302   
  5298   5303     if( c=='v' && strncmp(azArg[0], "vfsinfo", n)==0 ){
  5299   5304       const char *zDbName = nArg==2 ? azArg[1] : "main";
  5300         -    sqlite3_vfs *pVfs;
         5305  +    sqlite3_vfs *pVfs = 0;
  5301   5306       if( p->db ){
  5302   5307         sqlite3_file_control(p->db, zDbName, SQLITE_FCNTL_VFS_POINTER, &pVfs);
  5303   5308         if( pVfs ){
  5304   5309           utf8_printf(p->out, "vfs.zName      = \"%s\"\n", pVfs->zName);
  5305   5310           raw_printf(p->out, "vfs.iVersion   = %d\n", pVfs->iVersion);
  5306   5311           raw_printf(p->out, "vfs.szOsFile   = %d\n", pVfs->szOsFile);
  5307   5312           raw_printf(p->out, "vfs.mxPathname = %d\n", pVfs->mxPathname);

Changes to src/sqlite.h.in.

   255    255   ** ^The sqlite3_int64 and sqlite_int64 types can store integer values
   256    256   ** between -9223372036854775808 and +9223372036854775807 inclusive.  ^The
   257    257   ** sqlite3_uint64 and sqlite_uint64 types can store integer values 
   258    258   ** between 0 and +18446744073709551615 inclusive.
   259    259   */
   260    260   #ifdef SQLITE_INT64_TYPE
   261    261     typedef SQLITE_INT64_TYPE sqlite_int64;
   262         -  typedef unsigned SQLITE_INT64_TYPE sqlite_uint64;
          262  +# ifdef SQLITE_UINT64_TYPE
          263  +    typedef SQLITE_UINT64_TYPE sqlite_uint64;
          264  +# else  
          265  +    typedef unsigned SQLITE_INT64_TYPE sqlite_uint64;
          266  +# endif
   263    267   #elif defined(_MSC_VER) || defined(__BORLANDC__)
   264    268     typedef __int64 sqlite_int64;
   265    269     typedef unsigned __int64 sqlite_uint64;
   266    270   #else
   267    271     typedef long long int sqlite_int64;
   268    272     typedef unsigned long long int sqlite_uint64;
   269    273   #endif
................................................................................
   569    573   ** way around.  The SQLITE_IOCAP_SEQUENTIAL property means that
   570    574   ** information is written to disk in the same order as calls
   571    575   ** to xWrite().  The SQLITE_IOCAP_POWERSAFE_OVERWRITE property means that
   572    576   ** after reboot following a crash or power loss, the only bytes in a
   573    577   ** file that were written at the application level might have changed
   574    578   ** and that adjacent bytes, even bytes within the same sector are
   575    579   ** guaranteed to be unchanged.  The SQLITE_IOCAP_UNDELETABLE_WHEN_OPEN
   576         -** flag indicate that a file cannot be deleted when open.  The
          580  +** flag indicates that a file cannot be deleted when open.  The
   577    581   ** SQLITE_IOCAP_IMMUTABLE flag indicates that the file is on
   578    582   ** read-only media and cannot be changed even by processes with
   579    583   ** elevated privileges.
   580    584   */
   581    585   #define SQLITE_IOCAP_ATOMIC                 0x00000001
   582    586   #define SQLITE_IOCAP_ATOMIC512              0x00000002
   583    587   #define SQLITE_IOCAP_ATOMIC1K               0x00000004
................................................................................
   719    723   ** <li> [SQLITE_IOCAP_ATOMIC4K]
   720    724   ** <li> [SQLITE_IOCAP_ATOMIC8K]
   721    725   ** <li> [SQLITE_IOCAP_ATOMIC16K]
   722    726   ** <li> [SQLITE_IOCAP_ATOMIC32K]
   723    727   ** <li> [SQLITE_IOCAP_ATOMIC64K]
   724    728   ** <li> [SQLITE_IOCAP_SAFE_APPEND]
   725    729   ** <li> [SQLITE_IOCAP_SEQUENTIAL]
          730  +** <li> [SQLITE_IOCAP_UNDELETABLE_WHEN_OPEN]
          731  +** <li> [SQLITE_IOCAP_POWERSAFE_OVERWRITE]
          732  +** <li> [SQLITE_IOCAP_IMMUTABLE]
   726    733   ** </ul>
   727    734   **
   728    735   ** The SQLITE_IOCAP_ATOMIC property means that all writes of
   729    736   ** any size are atomic.  The SQLITE_IOCAP_ATOMICnnn values
   730    737   ** mean that writes of blocks that are nnn bytes in size and
   731    738   ** are aligned to an address which is an integer multiple of
   732    739   ** nnn are atomic.  The SQLITE_IOCAP_SAFE_APPEND value means

Changes to src/sqliteInt.h.

   105    105   
   106    106   /* What version of GCC is being used.  0 means GCC is not being used */
   107    107   #ifdef __GNUC__
   108    108   # define GCC_VERSION (__GNUC__*1000000+__GNUC_MINOR__*1000+__GNUC_PATCHLEVEL__)
   109    109   #else
   110    110   # define GCC_VERSION 0
   111    111   #endif
          112  +
          113  +/* What version of CLANG is being used.  0 means CLANG is not being used */
          114  +#if defined(__clang__) && !defined(_WIN32)
          115  +# define CLANG_VERSION \
          116  +            (__clang_major__*1000000+__clang_minor__*1000+__clang_patchlevel__)
          117  +#else
          118  +# define CLANG_VERSION 0
          119  +#endif
   112    120   
   113    121   /* Needed for various definitions... */
   114    122   #if defined(__GNUC__) && !defined(_GNU_SOURCE)
   115    123   # define _GNU_SOURCE
   116    124   #endif
   117    125   
   118    126   #if defined(__OpenBSD__) && !defined(_BSD_SOURCE)
................................................................................
   499    507   #include "parse.h"
   500    508   #include <stdio.h>
   501    509   #include <stdlib.h>
   502    510   #include <string.h>
   503    511   #include <assert.h>
   504    512   #include <stddef.h>
   505    513   
          514  +/*
          515  +** Use a macro to replace memcpy() if compiled with SQLITE_INLINE_MEMCPY.
          516  +** This allows better measurements of where memcpy() is used when running
          517  +** cachegrind.  But this macro version of memcpy() is very slow so it
          518  +** should not be used in production.  This is a performance measurement
          519  +** hack only.
          520  +*/
          521  +#ifdef SQLITE_INLINE_MEMCPY
          522  +# define memcpy(D,S,N) {char*xxd=(char*)(D);const char*xxs=(const char*)(S);\
          523  +                        int xxn=(N);while(xxn-->0)*(xxd++)=*(xxs++);}
          524  +#endif
          525  +
   506    526   /*
   507    527   ** If compiling for a processor that lacks floating point support,
   508    528   ** substitute integer for floating-point
   509    529   */
   510    530   #ifdef SQLITE_OMIT_FLOATING_POINT
   511    531   # define double sqlite_int64
   512    532   # define float sqlite_int64
................................................................................
   583    603   #endif
   584    604   
   585    605   /*
   586    606   ** The default initial allocation for the pagecache when using separate
   587    607   ** pagecaches for each database connection.  A positive number is the
   588    608   ** number of pages.  A negative number N translations means that a buffer
   589    609   ** of -1024*N bytes is allocated and used for as many pages as it will hold.
          610  +**
          611  +** The default value of "20" was choosen to minimize the run-time of the
          612  +** speedtest1 test program with options: --shrink-memory --reprepare
   590    613   */
   591    614   #ifndef SQLITE_DEFAULT_PCACHE_INITSZ
   592         -# define SQLITE_DEFAULT_PCACHE_INITSZ 100
          615  +# define SQLITE_DEFAULT_PCACHE_INITSZ 20
   593    616   #endif
   594    617   
   595    618   /*
   596    619   ** GCC does not define the offsetof() macro so we'll have to do it
   597    620   ** ourselves.
   598    621   */
   599    622   #ifndef offsetof
................................................................................
  1292   1315     u8 bBenignMalloc;             /* Do not require OOMs if true */
  1293   1316     u8 dfltLockMode;              /* Default locking-mode for attached dbs */
  1294   1317     signed char nextAutovac;      /* Autovac setting after VACUUM if >=0 */
  1295   1318     u8 suppressErr;               /* Do not issue error messages if true */
  1296   1319     u8 vtabOnConflict;            /* Value to return for s3_vtab_on_conflict() */
  1297   1320     u8 isTransactionSavepoint;    /* True if the outermost savepoint is a TS */
  1298   1321     u8 mTrace;                    /* zero or more SQLITE_TRACE flags */
         1322  +  u8 skipBtreeMutex;            /* True if no shared-cache backends */
  1299   1323     int nextPagesize;             /* Pagesize after VACUUM if >0 */
  1300   1324     u32 magic;                    /* Magic number for detect library misuse */
  1301   1325     int nChange;                  /* Value returned by sqlite3_changes() */
  1302   1326     int nTotalChange;             /* Value returned by sqlite3_total_changes() */
  1303   1327     int aLimit[SQLITE_N_LIMIT];   /* Limits */
  1304   1328     int nMaxSorterMmap;           /* Maximum size of regions mapped by sorter */
  1305   1329     struct sqlite3InitInfo {      /* Information used during initialization */
................................................................................
  1557   1581   #define SQLITE_FUNC_COUNT    0x0100 /* Built-in count(*) aggregate */
  1558   1582   #define SQLITE_FUNC_COALESCE 0x0200 /* Built-in coalesce() or ifnull() */
  1559   1583   #define SQLITE_FUNC_UNLIKELY 0x0400 /* Built-in unlikely() function */
  1560   1584   #define SQLITE_FUNC_CONSTANT 0x0800 /* Constant inputs give a constant output */
  1561   1585   #define SQLITE_FUNC_MINMAX   0x1000 /* True for min() and max() aggregates */
  1562   1586   #define SQLITE_FUNC_SLOCHNG  0x2000 /* "Slow Change". Value constant during a
  1563   1587                                       ** single query - might change over time */
         1588  +#define SQLITE_FUNC_AFFINITY 0x4000 /* Built-in affinity() function */
  1564   1589   
  1565   1590   /*
  1566   1591   ** The following three macros, FUNCTION(), LIKEFUNC() and AGGREGATE() are
  1567   1592   ** used to create the initializers for the FuncDef structures.
  1568   1593   **
  1569   1594   **   FUNCTION(zName, nArg, iArg, bNC, xFunc)
  1570   1595   **     Used to create a scalar function definition of a function zName
................................................................................
  3024   3049   **    OPFLAG_FORDELETE    == BTREE_FORDELETE
  3025   3050   **    OPFLAG_SAVEPOSITION == BTREE_SAVEPOSITION
  3026   3051   **    OPFLAG_AUXDELETE    == BTREE_AUXDELETE
  3027   3052   */
  3028   3053   #define OPFLAG_NCHANGE       0x01    /* OP_Insert: Set to update db->nChange */
  3029   3054                                        /* Also used in P2 (not P5) of OP_Delete */
  3030   3055   #define OPFLAG_EPHEM         0x01    /* OP_Column: Ephemeral output is ok */
  3031         -#define OPFLAG_LASTROWID     0x02    /* Set to update db->lastRowid */
         3056  +#define OPFLAG_LASTROWID     0x20    /* Set to update db->lastRowid */
  3032   3057   #define OPFLAG_ISUPDATE      0x04    /* This OP_Insert is an sql UPDATE */
  3033   3058   #define OPFLAG_APPEND        0x08    /* This is likely to be an append */
  3034   3059   #define OPFLAG_USESEEKRESULT 0x10    /* Try to avoid a seek in BtreeInsert() */
  3035   3060   #ifdef SQLITE_ENABLE_PREUPDATE_HOOK
  3036   3061   #define OPFLAG_ISNOOP        0x40    /* OP_Delete does pre-update-hook only */
  3037   3062   #endif
  3038   3063   #define OPFLAG_LENGTHARG     0x40    /* OP_Column only used for length() */
  3039   3064   #define OPFLAG_TYPEOFARG     0x80    /* OP_Column only used for typeof() */
  3040   3065   #define OPFLAG_BULKCSR       0x01    /* OP_Open** used to open bulk cursor */
  3041   3066   #define OPFLAG_SEEKEQ        0x02    /* OP_Open** cursor uses EQ seek only */
  3042   3067   #define OPFLAG_FORDELETE     0x08    /* OP_Open should use BTREE_FORDELETE */
  3043   3068   #define OPFLAG_P2ISREG       0x10    /* P2 to OP_Open** is a register number */
  3044   3069   #define OPFLAG_PERMUTE       0x01    /* OP_Compare: use the permutation */
  3045         -#define OPFLAG_SAVEPOSITION  0x02    /* OP_Delete: keep cursor position */
         3070  +#define OPFLAG_SAVEPOSITION  0x02    /* OP_Delete/Insert: save cursor pos */
  3046   3071   #define OPFLAG_AUXDELETE     0x04    /* OP_Delete: index in a DELETE op */
  3047   3072   
  3048   3073   /*
  3049   3074    * Each trigger present in the database schema is stored as an instance of
  3050   3075    * struct Trigger.
  3051   3076    *
  3052   3077    * Pointers to instances of struct Trigger are stored in two ways.
................................................................................
  3699   3724   void sqlite3ExprCachePop(Parse*);
  3700   3725   void sqlite3ExprCacheRemove(Parse*, int, int);
  3701   3726   void sqlite3ExprCacheClear(Parse*);
  3702   3727   void sqlite3ExprCacheAffinityChange(Parse*, int, int);
  3703   3728   void sqlite3ExprCode(Parse*, Expr*, int);
  3704   3729   void sqlite3ExprCodeCopy(Parse*, Expr*, int);
  3705   3730   void sqlite3ExprCodeFactorable(Parse*, Expr*, int);
  3706         -void sqlite3ExprCodeAtInit(Parse*, Expr*, int, u8);
         3731  +int sqlite3ExprCodeAtInit(Parse*, Expr*, int);
  3707   3732   int sqlite3ExprCodeTemp(Parse*, Expr*, int*);
  3708   3733   int sqlite3ExprCodeTarget(Parse*, Expr*, int);
  3709   3734   void sqlite3ExprCodeAndCache(Parse*, Expr*, int);
  3710   3735   int sqlite3ExprCodeExprList(Parse*, ExprList*, int, int, u8);
  3711   3736   #define SQLITE_ECEL_DUP      0x01  /* Deep, not shallow copies */
  3712   3737   #define SQLITE_ECEL_FACTOR   0x02  /* Factor out constant terms */
  3713   3738   #define SQLITE_ECEL_REF      0x04  /* Use ExprList.u.x.iOrderByCol */
................................................................................
  3761   3786   void sqlite3GenerateRowDelete(
  3762   3787       Parse*,Table*,Trigger*,int,int,int,i16,u8,u8,u8,int);
  3763   3788   void sqlite3GenerateRowIndexDelete(Parse*, Table*, int, int, int*, int);
  3764   3789   int sqlite3GenerateIndexKey(Parse*, Index*, int, int, int, int*,Index*,int);
  3765   3790   void sqlite3ResolvePartIdxLabel(Parse*,int);
  3766   3791   void sqlite3GenerateConstraintChecks(Parse*,Table*,int*,int,int,int,int,
  3767   3792                                        u8,u8,int,int*,int*);
         3793  +#ifdef SQLITE_ENABLE_NULL_TRIM
         3794  +  void sqlite3SetMakeRecordP5(Vdbe*,Table*);
         3795  +#else
         3796  +# define sqlite3SetMakeRecordP5(A,B)
         3797  +#endif
  3768   3798   void sqlite3CompleteInsertion(Parse*,Table*,int,int,int,int*,int,int,int);
  3769   3799   int sqlite3OpenTableAndIndices(Parse*, Table*, int, u8, int, u8*, int*, int*);
  3770   3800   void sqlite3BeginWriteOperation(Parse*, int, int);
  3771   3801   void sqlite3MultiWrite(Parse*);
  3772   3802   void sqlite3MayAbort(Parse*);
  3773   3803   void sqlite3HaltConstraint(Parse*, int, int, char*, i8, u8);
  3774   3804   void sqlite3UniqueConstraint(Parse*, int, Index*);

Changes to src/table.c.

    13     13   ** interface routines.  These are just wrappers around the main
    14     14   ** interface routine of sqlite3_exec().
    15     15   **
    16     16   ** These routines are in a separate files so that they will not be linked
    17     17   ** if they are not used.
    18     18   */
    19     19   #include "sqliteInt.h"
    20         -#include <stdlib.h>
    21         -#include <string.h>
    22     20   
    23     21   #ifndef SQLITE_OMIT_GET_TABLE
    24     22   
    25     23   /*
    26     24   ** This structure is used to pass data from sqlite3_get_table() through
    27     25   ** to the callback function is uses to build the result.
    28     26   */

Changes to src/tclsqlite.c.

  2303   2303       if( rc ){
  2304   2304         Tcl_AppendResult(interp, "Error: ", sqlite3_errmsg(pDb->db), (char*)0);
  2305   2305         sqlite3_finalize(pStmt);
  2306   2306         return TCL_ERROR;
  2307   2307       }
  2308   2308       in = fopen(zFile, "rb");
  2309   2309       if( in==0 ){
  2310         -      Tcl_AppendResult(interp, "Error: cannot open file: ", zFile, NULL);
         2310  +      Tcl_AppendResult(interp, "Error: cannot open file: ", zFile, (char*)0);
  2311   2311         sqlite3_finalize(pStmt);
  2312   2312         return TCL_ERROR;
  2313   2313       }
  2314   2314       azCol = malloc( sizeof(azCol[0])*(nCol+1) );
  2315   2315       if( azCol==0 ) {
  2316   2316         Tcl_AppendResult(interp, "Error: can't malloc()", (char*)0);
  2317   2317         fclose(in);
................................................................................
  2532   2532         return TCL_ERROR;
  2533   2533       }
  2534   2534       for(i=3; i<(objc-1); i++){
  2535   2535         const char *z = Tcl_GetString(objv[i]);
  2536   2536         int n = strlen30(z);
  2537   2537         if( n>2 && strncmp(z, "-argcount",n)==0 ){
  2538   2538           if( i==(objc-2) ){
  2539         -          Tcl_AppendResult(interp, "option requires an argument: ", z, 0);
         2539  +          Tcl_AppendResult(interp, "option requires an argument: ", z,(char*)0);
  2540   2540             return TCL_ERROR;
  2541   2541           }
  2542   2542           if( Tcl_GetIntFromObj(interp, objv[i+1], &nArg) ) return TCL_ERROR;
  2543   2543           if( nArg<0 ){
  2544   2544             Tcl_AppendResult(interp, "number of arguments must be non-negative",
  2545   2545                              (char*)0);
  2546   2546             return TCL_ERROR;
................................................................................
  2547   2547           }
  2548   2548           i++;
  2549   2549         }else
  2550   2550         if( n>2 && strncmp(z, "-deterministic",n)==0 ){
  2551   2551           flags |= SQLITE_DETERMINISTIC;
  2552   2552         }else{
  2553   2553           Tcl_AppendResult(interp, "bad option \"", z,
  2554         -            "\": must be -argcount or -deterministic", 0
         2554  +            "\": must be -argcount or -deterministic", (char*)0
  2555   2555           );
  2556   2556           return TCL_ERROR;
  2557   2557         }
  2558   2558       }
  2559   2559   
  2560   2560       pScript = objv[objc-1];
  2561   2561       zName = Tcl_GetStringFromObj(objv[2], 0);
................................................................................
  3204   3204           }
  3205   3205   
  3206   3206           if( rc==SQLITE_OK ){
  3207   3207             Tcl_Obj *pObj;
  3208   3208             pObj = Tcl_NewStringObj((char*)sqlite3_value_text(pValue), -1);
  3209   3209             Tcl_SetObjResult(interp, pObj);
  3210   3210           }else{
  3211         -          Tcl_AppendResult(interp, sqlite3_errmsg(pDb->db), 0);
         3211  +          Tcl_AppendResult(interp, sqlite3_errmsg(pDb->db), (char*)0);
  3212   3212             return TCL_ERROR;
  3213   3213           }
  3214   3214         }
  3215   3215       }
  3216   3216   #endif /* SQLITE_ENABLE_PREUPDATE_HOOK */
  3217   3217       break;
  3218   3218     }

Changes to src/test_delete.c.

    76     76     return 0;
    77     77   }
    78     78   
    79     79   /*
    80     80   ** Delete the database file identified by the string argument passed to this
    81     81   ** function. The string must contain a filename, not an SQLite URI.
    82     82   */
    83         -int sqlite3_delete_database(
           83  +SQLITE_API int sqlite3_delete_database(
    84     84     const char *zFile               /* File to delete */
    85     85   ){
    86     86     char *zBuf;                     /* Buffer to sprintf() filenames to */
    87     87     int nBuf;                       /* Size of buffer in bytes */
    88     88     int rc = 0;                     /* System error code */
    89     89     int i;                          /* Iterate through azFmt[] and aMFile[] */
    90     90   

Changes to src/test_sqllog.c.

   309    309       if( zInit==0 ){
   310    310         int rc;
   311    311         sqlite3 *copy = 0;
   312    312         int iDb;
   313    313   
   314    314         /* Generate a file-name to use for the copy of this database */
   315    315         iDb = sqllogglobal.iNextDb++;
   316         -      zInit = sqlite3_mprintf("%s_%d.db", sqllogglobal.zPrefix, iDb);
          316  +      zInit = sqlite3_mprintf("%s_%02d.db", sqllogglobal.zPrefix, iDb);
   317    317   
   318    318         /* Create the backup */
   319    319         assert( sqllogglobal.bRec==0 );
   320    320         sqllogglobal.bRec = 1;
   321    321         rc = sqlite3_open(zInit, &copy);
   322    322         if( rc==SQLITE_OK ){
   323    323           sqlite3_backup *pBak;
................................................................................
   372    372       /* If it is still NULL, have global.zPrefix point to a copy of 
   373    373       ** environment variable $ENVIRONMENT_VARIABLE1_NAME.  */
   374    374       if( sqllogglobal.zPrefix[0]==0 ){
   375    375         FILE *fd;
   376    376         char *zVar = getenv(ENVIRONMENT_VARIABLE1_NAME);
   377    377         if( zVar==0 || strlen(zVar)+10>=(sizeof(sqllogglobal.zPrefix)) ) return;
   378    378         sqlite3_snprintf(sizeof(sqllogglobal.zPrefix), sqllogglobal.zPrefix,
   379         -                        "%s/sqllog_%d", zVar, getProcessId());
          379  +                        "%s/sqllog_%05d", zVar, getProcessId());
   380    380         sqlite3_snprintf(sizeof(sqllogglobal.zIdx), sqllogglobal.zIdx,
   381    381                           "%s.idx", sqllogglobal.zPrefix);
   382    382         if( getenv(ENVIRONMENT_VARIABLE2_NAME) ){
   383    383           sqllogglobal.bReuse = atoi(getenv(ENVIRONMENT_VARIABLE2_NAME));
   384    384         }
   385    385         fd = fopen(sqllogglobal.zIdx, "w");
   386    386         if( fd ) fclose(fd);
   387    387       }
   388    388   
   389    389       /* Open the log file */
   390         -    zLog = sqlite3_mprintf("%s_%d.sql", sqllogglobal.zPrefix, p->iLog);
          390  +    zLog = sqlite3_mprintf("%s_%05d.sql", sqllogglobal.zPrefix, p->iLog);
   391    391       p->fd = fopen(zLog, "w");
   392    392       sqlite3_free(zLog);
   393    393       if( p->fd==0 ){
   394    394         sqlite3_log(SQLITE_IOERR, "sqllogOpenlog(): Failed to open log file");
   395    395       }
   396    396     }
   397    397   }

Changes to src/test_windirent.c.

    59     59     memset(dirp, 0, sizeof(DIR));
    60     60   
    61     61     /* TODO: Remove this if Unix-style root paths are not used. */
    62     62     if( sqlite3_stricmp(dirname, "/")==0 ){
    63     63       dirname = windirent_getenv("SystemDrive");
    64     64     }
    65     65   
           66  +  memset(&data, 0, sizeof(struct _finddata_t));
    66     67     _snprintf(data.name, namesize, "%s\\*", dirname);
    67     68     dirp->d_handle = _findfirst(data.name, &data);
    68     69   
    69     70     if( dirp->d_handle==BAD_INTPTR_T ){
    70     71       closedir(dirp);
    71     72       return NULL;
    72     73     }
    73     74   
    74         -  /* TODO: Remove this block to allow hidden and system files. */
    75         -  if( data.attrib&_A_HIDDEN || data.attrib&_A_SYSTEM ){
           75  +  /* TODO: Remove this block to allow hidden and/or system files. */
           76  +  if( is_filtered(data) ){
           77  +next:
           78  +
           79  +    memset(&data, 0, sizeof(struct _finddata_t));
    76     80       if( _findnext(dirp->d_handle, &data)==-1 ){
    77     81         closedir(dirp);
    78     82         return NULL;
    79     83       }
           84  +
           85  +    /* TODO: Remove this block to allow hidden and/or system files. */
           86  +    if( is_filtered(data) ) goto next;
    80     87     }
    81     88   
    82     89     dirp->d_first.d_attributes = data.attrib;
    83     90     strncpy(dirp->d_first.d_name, data.name, NAME_MAX);
    84     91     dirp->d_first.d_name[NAME_MAX] = '\0';
    85     92   
    86     93     return dirp;
................................................................................
   101    108       dirp->d_next.d_ino++;
   102    109   
   103    110       return &dirp->d_first;
   104    111     }
   105    112   
   106    113   next:
   107    114   
          115  +  memset(&data, 0, sizeof(struct _finddata_t));
   108    116     if( _findnext(dirp->d_handle, &data)==-1 ) return NULL;
   109    117   
   110         -  /* TODO: Remove this block to allow hidden and system files. */
   111         -  if( data.attrib&_A_HIDDEN ) goto next;
   112         -  if( data.attrib&_A_SYSTEM ) goto next;
          118  +  /* TODO: Remove this block to allow hidden and/or system files. */
          119  +  if( is_filtered(data) ) goto next;
   113    120   
   114    121     dirp->d_next.d_ino++;
   115    122     dirp->d_next.d_attributes = data.attrib;
   116    123     strncpy(dirp->d_next.d_name, data.name, NAME_MAX);
   117    124     dirp->d_next.d_name[NAME_MAX] = '\0';
   118    125   
   119    126     return &dirp->d_next;
................................................................................
   142    149   
   143    150       *result = entry;
   144    151       return 0;
   145    152     }
   146    153   
   147    154   next:
   148    155   
          156  +  memset(&data, 0, sizeof(struct _finddata_t));
   149    157     if( _findnext(dirp->d_handle, &data)==-1 ){
   150    158       *result = NULL;
   151    159       return ENOENT;
   152    160     }
   153    161   
   154         -  /* TODO: Remove this block to allow hidden and system files. */
   155         -  if( data.attrib&_A_HIDDEN ) goto next;
   156         -  if( data.attrib&_A_SYSTEM ) goto next;
          162  +  /* TODO: Remove this block to allow hidden and/or system files. */
          163  +  if( is_filtered(data) ) goto next;
   157    164   
   158    165     entry->d_ino = (ino_t)-1; /* not available */
   159    166     entry->d_attributes = data.attrib;
   160    167     strncpy(entry->d_name, data.name, NAME_MAX);
   161    168     entry->d_name[NAME_MAX] = '\0';
   162    169   
   163    170     *result = entry;

Changes to src/test_windirent.h.

    88     88   
    89     89   struct DIR {
    90     90     intptr_t d_handle; /* Value returned by "_findfirst". */
    91     91     DIRENT d_first;    /* DIRENT constructed based on "_findfirst". */
    92     92     DIRENT d_next;     /* DIRENT constructed based on "_findnext". */
    93     93   };
    94     94   
           95  +/*
           96  +** Provide a macro, for use by the implementation, to determine if a
           97  +** particular directory entry should be skipped over when searching for
           98  +** the next directory entry that should be returned by the readdir() or
           99  +** readdir_r() functions.
          100  +*/
          101  +
          102  +#ifndef is_filtered
          103  +#  define is_filtered(a) ((((a).attrib)&_A_HIDDEN) || (((a).attrib)&_A_SYSTEM))
          104  +#endif
          105  +
    95    106   /*
    96    107   ** Provide the function prototype for the POSIX compatiable getenv()
    97    108   ** function.  This function is not thread-safe.
    98    109   */
    99    110   
   100    111   extern const char *windirent_getenv(const char *name);
   101    112   

Changes to src/update.c.

    67     67       VdbeComment((v, "%s.%s", pTab->zName, pCol->zName));
    68     68       assert( i<pTab->nCol );
    69     69       sqlite3ValueFromExpr(sqlite3VdbeDb(v), pCol->pDflt, enc, 
    70     70                            pCol->affinity, &pValue);
    71     71       if( pValue ){
    72     72         sqlite3VdbeAppendP4(v, pValue, P4_MEM);
    73     73       }
           74  +  }
    74     75   #ifndef SQLITE_OMIT_FLOATING_POINT
    75         -    if( pTab->aCol[i].affinity==SQLITE_AFF_REAL ){
    76         -      sqlite3VdbeAddOp1(v, OP_RealAffinity, iReg);
    77         -    }
           76  +  if( pTab->aCol[i].affinity==SQLITE_AFF_REAL ){
           77  +    sqlite3VdbeAddOp1(v, OP_RealAffinity, iReg);
           78  +  }
    78     79   #endif
    79         -  }
    80     80   }
    81     81   
    82     82   /*
    83     83   ** Process an UPDATE statement.
    84     84   **
    85     85   **   UPDATE OR IGNORE table_wxyz SET a=b, c=d WHERE e<5 AND f NOT NULL;
    86     86   **          \_______/ \________/     \______/       \________________/
................................................................................
   101    101     Index *pIdx;           /* For looping over indices */
   102    102     Index *pPk;            /* The PRIMARY KEY index for WITHOUT ROWID tables */
   103    103     int nIdx;              /* Number of indices that need updating */
   104    104     int iBaseCur;          /* Base cursor number */
   105    105     int iDataCur;          /* Cursor for the canonical data btree */
   106    106     int iIdxCur;           /* Cursor for the first index */
   107    107     sqlite3 *db;           /* The database structure */
   108         -  int *aRegIdx = 0;      /* One register assigned to each index to be updated */
          108  +  int *aRegIdx = 0;      /* First register in array assigned to each index */
   109    109     int *aXRef = 0;        /* aXRef[i] is the index in pChanges->a[] of the
   110    110                            ** an expression for the i-th column of the table.
   111    111                            ** aXRef[i]==-1 if the i-th column is not changed. */
   112    112     u8 *aToOpen;           /* 1 for tables and indices to be opened */
   113    113     u8 chngPk;             /* PRIMARY KEY changed in a WITHOUT ROWID table */
   114    114     u8 chngRowid;          /* Rowid changed in a normal table */
   115    115     u8 chngKey;            /* Either chngPk or chngRowid */
   116    116     Expr *pRowidExpr = 0;  /* Expression defining the new record number */
   117    117     AuthContext sContext;  /* The authorization context */
   118    118     NameContext sNC;       /* The name-context to resolve expressions in */
   119    119     int iDb;               /* Database containing the table being updated */
   120         -  int okOnePass;         /* True for one-pass algorithm without the FIFO */
          120  +  int eOnePass;          /* ONEPASS_XXX value from where.c */
   121    121     int hasFK;             /* True if foreign key processing is required */
   122    122     int labelBreak;        /* Jump here to break out of UPDATE loop */
   123    123     int labelContinue;     /* Jump here to continue next step of UPDATE loop */
          124  +  int flags;             /* Flags for sqlite3WhereBegin() */
   124    125   
   125    126   #ifndef SQLITE_OMIT_TRIGGER
   126    127     int isView;            /* True when updating a view (INSTEAD OF trigger) */
   127    128     Trigger *pTrigger;     /* List of triggers on pTab, if required */
   128    129     int tmask;             /* Mask of TRIGGER_BEFORE|TRIGGER_AFTER */
   129    130   #endif
   130    131     int newmask;           /* Mask of NEW.* columns accessed by BEFORE triggers */
   131    132     int iEph = 0;          /* Ephemeral table holding all primary key values */
   132    133     int nKey = 0;          /* Number of elements in regKey for WITHOUT ROWID */
   133    134     int aiCurOnePass[2];   /* The write cursors opened by WHERE_ONEPASS */
          135  +  int addrOpen = 0;      /* Address of OP_OpenEphemeral */
          136  +  int iPk = 0;           /* First of nPk cells holding PRIMARY KEY value */
          137  +  i16 nPk = 0;           /* Number of components of the PRIMARY KEY */
          138  +  int bReplace = 0;      /* True if REPLACE conflict resolution might happen */
   134    139   
   135    140     /* Register Allocations */
   136    141     int regRowCount = 0;   /* A count of rows changed */
   137    142     int regOldRowid = 0;   /* The old rowid */
   138    143     int regNewRowid = 0;   /* The new rowid */
   139    144     int regNew = 0;        /* Content of the NEW.* table in triggers */
   140    145     int regOld = 0;        /* Content of OLD.* table in triggers */
................................................................................
   286    291       }else{
   287    292         reg = 0;
   288    293         for(i=0; i<pIdx->nKeyCol; i++){
   289    294           i16 iIdxCol = pIdx->aiColumn[i];
   290    295           if( iIdxCol<0 || aXRef[iIdxCol]>=0 ){
   291    296             reg = ++pParse->nMem;
   292    297             pParse->nMem += pIdx->nColumn;
          298  +          if( (onError==OE_Replace)
          299  +           || (onError==OE_Default && pIdx->onError==OE_Replace) 
          300  +          ){
          301  +            bReplace = 1;
          302  +          }
   293    303             break;
   294    304           }
   295    305         }
   296    306       }
   297    307       if( reg==0 ) aToOpen[j+1] = 0;
   298    308       aRegIdx[j] = reg;
   299    309     }
          310  +  if( bReplace ){
          311  +    /* If REPLACE conflict resolution might be invoked, open cursors on all 
          312  +    ** indexes in case they are needed to delete records.  */
          313  +    memset(aToOpen, 1, nIdx+1);
          314  +  }
   300    315   
   301    316     /* Begin generating code. */
   302    317     v = sqlite3GetVdbe(pParse);
   303    318     if( v==0 ) goto update_cleanup;
   304    319     if( pParse->nested==0 ) sqlite3VdbeCountChanges(v);
   305    320     sqlite3BeginWriteOperation(pParse, 1, iDb);
   306    321   
................................................................................
   345    360     if( IsVirtual(pTab) ){
   346    361       updateVirtualTable(pParse, pTabList, pTab, pChanges, pRowidExpr, aXRef,
   347    362                          pWhere, onError);
   348    363       goto update_cleanup;
   349    364     }
   350    365   #endif
   351    366   
   352         -  /* Begin the database scan
   353         -  */
          367  +  /* Initialize the count of updated rows */
          368  +  if( (db->flags & SQLITE_CountRows) && !pParse->pTriggerTab ){
          369  +    regRowCount = ++pParse->nMem;
          370  +    sqlite3VdbeAddOp2(v, OP_Integer, 0, regRowCount);
          371  +  }
          372  +
   354    373     if( HasRowid(pTab) ){
   355    374       sqlite3VdbeAddOp3(v, OP_Null, 0, regRowSet, regOldRowid);
   356         -    pWInfo = sqlite3WhereBegin(
   357         -        pParse, pTabList, pWhere, 0, 0,
   358         -            WHERE_ONEPASS_DESIRED | WHERE_SEEK_TABLE, iIdxCur
   359         -    );
   360         -    if( pWInfo==0 ) goto update_cleanup;
   361         -    okOnePass = sqlite3WhereOkOnePass(pWInfo, aiCurOnePass);
   362         -  
   363         -    /* Remember the rowid of every item to be updated.
   364         -    */
   365         -    sqlite3VdbeAddOp2(v, OP_Rowid, iDataCur, regOldRowid);
   366         -    if( !okOnePass ){
   367         -      sqlite3VdbeAddOp2(v, OP_RowSetAdd, regRowSet, regOldRowid);
   368         -    }
   369         -  
   370         -    /* End the database scan loop.
   371         -    */
   372         -    sqlite3WhereEnd(pWInfo);
   373    375     }else{
   374         -    int iPk;         /* First of nPk memory cells holding PRIMARY KEY value */
   375         -    i16 nPk;         /* Number of components of the PRIMARY KEY */
   376         -    int addrOpen;    /* Address of the OpenEphemeral instruction */
   377         -
   378    376       assert( pPk!=0 );
   379    377       nPk = pPk->nKeyCol;
   380    378       iPk = pParse->nMem+1;
   381    379       pParse->nMem += nPk;
   382    380       regKey = ++pParse->nMem;
   383    381       iEph = pParse->nTab++;
          382  +
   384    383       sqlite3VdbeAddOp2(v, OP_Null, 0, iPk);
   385    384       addrOpen = sqlite3VdbeAddOp2(v, OP_OpenEphemeral, iEph, nPk);
   386    385       sqlite3VdbeSetP4KeyInfo(pParse, pPk);
   387         -    pWInfo = sqlite3WhereBegin(pParse, pTabList, pWhere, 0, 0, 
   388         -                               WHERE_ONEPASS_DESIRED, iIdxCur);
   389         -    if( pWInfo==0 ) goto update_cleanup;
   390         -    okOnePass = sqlite3WhereOkOnePass(pWInfo, aiCurOnePass);
          386  +  }
          387  +
          388  +  /* Begin the database scan. 
          389  +  **
          390  +  ** Do not consider a single-pass strategy for a multi-row update if
          391  +  ** there are any triggers or foreign keys to process, or rows may
          392  +  ** be deleted as a result of REPLACE conflict handling. Any of these
          393  +  ** things might disturb a cursor being used to scan through the table
          394  +  ** or index, causing a single-pass approach to malfunction.  */
          395  +  flags = WHERE_ONEPASS_DESIRED | WHERE_SEEK_TABLE;
          396  +  if( !pParse->nested && !pTrigger && !hasFK && !chngKey && !bReplace ){
          397  +    flags |= WHERE_ONEPASS_MULTIROW;
          398  +  }
          399  +  pWInfo = sqlite3WhereBegin(pParse, pTabList, pWhere, 0, 0, flags, iIdxCur);
          400  +  if( pWInfo==0 ) goto update_cleanup;
          401  +
          402  +  /* A one-pass strategy that might update more than one row may not
          403  +  ** be used if any column of the index used for the scan is being
          404  +  ** updated. Otherwise, if there is an index on "b", statements like
          405  +  ** the following could create an infinite loop:
          406  +  **
          407  +  **   UPDATE t1 SET b=b+1 WHERE b>?
          408  +  **
          409  +  ** Fall back to ONEPASS_OFF if where.c has selected a ONEPASS_MULTI
          410  +  ** strategy that uses an index for which one or more columns are being
          411  +  ** updated.  */
          412  +  eOnePass = sqlite3WhereOkOnePass(pWInfo, aiCurOnePass);
          413  +  if( eOnePass==ONEPASS_MULTI ){
          414  +    int iCur = aiCurOnePass[1];
          415  +    if( iCur>=0 && iCur!=iDataCur && aToOpen[iCur-iBaseCur] ){
          416  +      eOnePass = ONEPASS_OFF;
          417  +    }
          418  +    assert( iCur!=iDataCur || !HasRowid(pTab) );
          419  +  }
          420  +  
          421  +  if( HasRowid(pTab) ){
          422  +    /* Read the rowid of the current row of the WHERE scan. In ONEPASS_OFF
          423  +    ** mode, write the rowid into the FIFO. In either of the one-pass modes,
          424  +    ** leave it in register regOldRowid.  */
          425  +    sqlite3VdbeAddOp2(v, OP_Rowid, iDataCur, regOldRowid);
          426  +    if( eOnePass==ONEPASS_OFF ){
          427  +      sqlite3VdbeAddOp2(v, OP_RowSetAdd, regRowSet, regOldRowid);
          428  +    }
          429  +  }else{
          430  +    /* Read the PK of the current row into an array of registers. In
          431  +    ** ONEPASS_OFF mode, serialize the array into a record and store it in
          432  +    ** the ephemeral table. Or, in ONEPASS_SINGLE or MULTI mode, change
          433  +    ** the OP_OpenEphemeral instruction to a Noop (the ephemeral table 
          434  +    ** is not required) and leave the PK fields in the array of registers.  */
   391    435       for(i=0; i<nPk; i++){
   392    436         assert( pPk->aiColumn[i]>=0 );
   393         -      sqlite3ExprCodeGetColumnOfTable(v, pTab, iDataCur, pPk->aiColumn[i],
   394         -                                      iPk+i);
          437  +      sqlite3ExprCodeGetColumnOfTable(v, pTab, iDataCur,pPk->aiColumn[i],iPk+i);
   395    438       }
   396         -    if( okOnePass ){
          439  +    if( eOnePass ){
   397    440         sqlite3VdbeChangeToNoop(v, addrOpen);
   398    441         nKey = nPk;
   399    442         regKey = iPk;
   400    443       }else{
   401    444         sqlite3VdbeAddOp4(v, OP_MakeRecord, iPk, nPk, regKey,
   402    445                           sqlite3IndexAffinityStr(db, pPk), nPk);
   403    446         sqlite3VdbeAddOp4Int(v, OP_IdxInsert, iEph, regKey, iPk, nPk);
   404    447       }
   405         -    sqlite3WhereEnd(pWInfo);
   406    448     }
   407    449   
   408         -  /* Initialize the count of updated rows
   409         -  */
   410         -  if( (db->flags & SQLITE_CountRows) && !pParse->pTriggerTab ){
   411         -    regRowCount = ++pParse->nMem;
   412         -    sqlite3VdbeAddOp2(v, OP_Integer, 0, regRowCount);
          450  +  if( eOnePass!=ONEPASS_MULTI ){
          451  +    sqlite3WhereEnd(pWInfo);
   413    452     }
   414    453   
   415    454     labelBreak = sqlite3VdbeMakeLabel(v);
   416    455     if( !isView ){
   417         -    /* 
   418         -    ** Open every index that needs updating.  Note that if any
   419         -    ** index could potentially invoke a REPLACE conflict resolution 
   420         -    ** action, then we need to open all indices because we might need
   421         -    ** to be deleting some records.
   422         -    */
   423         -    if( onError==OE_Replace ){
   424         -      memset(aToOpen, 1, nIdx+1);
   425         -    }else{
   426         -      for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){
   427         -        if( pIdx->onError==OE_Replace ){
   428         -          memset(aToOpen, 1, nIdx+1);
   429         -          break;
   430         -        }
   431         -      }
   432         -    }
   433         -    if( okOnePass ){
          456  +    int addrOnce = 0;
          457  +
          458  +    /* Open every index that needs updating. */
          459  +    if( eOnePass!=ONEPASS_OFF ){
   434    460         if( aiCurOnePass[0]>=0 ) aToOpen[aiCurOnePass[0]-iBaseCur] = 0;
   435    461         if( aiCurOnePass[1]>=0 ) aToOpen[aiCurOnePass[1]-iBaseCur] = 0;
   436    462       }
          463  +
          464  +    if( eOnePass==ONEPASS_MULTI && (nIdx-(aiCurOnePass[1]>=0))>0 ){
          465  +      addrOnce = sqlite3VdbeAddOp0(v, OP_Once); VdbeCoverage(v);
          466  +    }
   437    467       sqlite3OpenTableAndIndices(pParse, pTab, OP_OpenWrite, 0, iBaseCur, aToOpen,
   438    468                                  0, 0);
          469  +    if( addrOnce ) sqlite3VdbeJumpHere(v, addrOnce);
   439    470     }
   440    471   
   441    472     /* Top of the update loop */
   442         -  if( okOnePass ){
   443         -    if( aToOpen[iDataCur-iBaseCur] && !isView ){
          473  +  if( eOnePass!=ONEPASS_OFF ){
          474  +    if( !isView && aiCurOnePass[0]!=iDataCur && aiCurOnePass[1]!=iDataCur ){
   444    475         assert( pPk );
   445    476         sqlite3VdbeAddOp4Int(v, OP_NotFound, iDataCur, labelBreak, regKey, nKey);
   446    477         VdbeCoverageNeverTaken(v);
   447    478       }
   448         -    labelContinue = labelBreak;
          479  +    if( eOnePass==ONEPASS_SINGLE ){
          480  +      labelContinue = labelBreak;
          481  +    }else{
          482  +      labelContinue = sqlite3VdbeMakeLabel(v);
          483  +    }
   449    484       sqlite3VdbeAddOp2(v, OP_IsNull, pPk ? regKey : regOldRowid, labelBreak);
   450    485       VdbeCoverageIf(v, pPk==0);
   451    486       VdbeCoverageIf(v, pPk!=0);
   452    487     }else if( pPk ){
   453    488       labelContinue = sqlite3VdbeMakeLabel(v);
   454    489       sqlite3VdbeAddOp2(v, OP_Rewind, iEph, labelBreak); VdbeCoverage(v);
   455    490       addrTop = sqlite3VdbeAddOp2(v, OP_RowData, iEph, regKey);
................................................................................
   566    601           sqlite3ExprCodeGetColumnOfTable(v, pTab, iDataCur, i, regNew+i);
   567    602         }
   568    603       }
   569    604     }
   570    605   
   571    606     if( !isView ){
   572    607       int addr1 = 0;        /* Address of jump instruction */
   573         -    int bReplace = 0;     /* True if REPLACE conflict resolution might happen */
   574    608   
   575    609       /* Do constraint checks. */
   576    610       assert( regOldRowid>0 );
   577    611       sqlite3GenerateConstraintChecks(pParse, pTab, aRegIdx, iDataCur, iIdxCur,
   578    612           regNewRowid, regOldRowid, chngKey, onError, labelContinue, &bReplace,
   579    613           aXRef);
   580    614   
................................................................................
   602    636       ** pre-update hook. If the caller invokes preupdate_new(), the returned
   603    637       ** value is copied from memory cell (regNewRowid+1+iCol), where iCol
   604    638       ** is the column index supplied by the user.
   605    639       */
   606    640       assert( regNew==regNewRowid+1 );
   607    641   #ifdef SQLITE_ENABLE_PREUPDATE_HOOK
   608    642       sqlite3VdbeAddOp3(v, OP_Delete, iDataCur,
   609         -        OPFLAG_ISUPDATE | ((hasFK || chngKey || pPk!=0) ? 0 : OPFLAG_ISNOOP),
          643  +        OPFLAG_ISUPDATE | ((hasFK || chngKey) ? 0 : OPFLAG_ISNOOP),
   610    644           regNewRowid
   611    645       );
          646  +    if( eOnePass==ONEPASS_MULTI ){
          647  +      assert( hasFK==0 && chngKey==0 );
          648  +      sqlite3VdbeChangeP5(v, OPFLAG_SAVEPOSITION);
          649  +    }
   612    650       if( !pParse->nested ){
   613    651         sqlite3VdbeAppendP4(v, pTab, P4_TABLE);
   614    652       }
   615    653   #else
   616         -    if( hasFK || chngKey || pPk!=0 ){
          654  +    if( hasFK || chngKey ){
   617    655         sqlite3VdbeAddOp2(v, OP_Delete, iDataCur, 0);
   618    656       }
   619    657   #endif
   620    658       if( bReplace || chngKey ){
   621    659         sqlite3VdbeJumpHere(v, addr1);
   622    660       }
   623    661   
   624    662       if( hasFK ){
   625    663         sqlite3FkCheck(pParse, pTab, 0, regNewRowid, aXRef, chngKey);
   626    664       }
   627    665     
   628    666       /* Insert the new index entries and the new record. */
   629         -    sqlite3CompleteInsertion(pParse, pTab, iDataCur, iIdxCur,
   630         -                             regNewRowid, aRegIdx, 1, 0, 0);
          667  +    sqlite3CompleteInsertion(
          668  +        pParse, pTab, iDataCur, iIdxCur, regNewRowid, aRegIdx, 
          669  +        OPFLAG_ISUPDATE | (eOnePass==ONEPASS_MULTI ? OPFLAG_SAVEPOSITION : 0), 
          670  +        0, 0
          671  +    );
   631    672   
   632    673       /* Do any ON CASCADE, SET NULL or SET DEFAULT operations required to
   633    674       ** handle rows (possibly in other tables) that refer via a foreign key
   634    675       ** to the row just updated. */ 
   635    676       if( hasFK ){
   636    677         sqlite3FkActions(pParse, pTab, pChanges, regOldRowid, aXRef, chngKey);
   637    678       }
................................................................................
   645    686   
   646    687     sqlite3CodeRowTrigger(pParse, pTrigger, TK_UPDATE, pChanges, 
   647    688         TRIGGER_AFTER, pTab, regOldRowid, onError, labelContinue);
   648    689   
   649    690     /* Repeat the above with the next record to be updated, until
   650    691     ** all record selected by the WHERE clause have been updated.
   651    692     */
   652         -  if( okOnePass ){
          693  +  if( eOnePass==ONEPASS_SINGLE ){
   653    694       /* Nothing to do at end-of-loop for a single-pass */
          695  +  }else if( eOnePass==ONEPASS_MULTI ){
          696  +    sqlite3VdbeResolveLabel(v, labelContinue);
          697  +    sqlite3WhereEnd(pWInfo);
   654    698     }else if( pPk ){
   655    699       sqlite3VdbeResolveLabel(v, labelContinue);
   656    700       sqlite3VdbeAddOp2(v, OP_Next, iEph, addrTop); VdbeCoverage(v);
   657    701     }else{
   658    702       sqlite3VdbeGoto(v, labelContinue);
   659    703     }
   660    704     sqlite3VdbeResolveLabel(v, labelBreak);

Changes to src/util.c.

  1137   1137   */
  1138   1138   u32 sqlite3Get4byte(const u8 *p){
  1139   1139   #if SQLITE_BYTEORDER==4321
  1140   1140     u32 x;
  1141   1141     memcpy(&x,p,4);
  1142   1142     return x;
  1143   1143   #elif SQLITE_BYTEORDER==1234 && !defined(SQLITE_DISABLE_INTRINSIC) \
  1144         -    && defined(__GNUC__) && GCC_VERSION>=4003000
         1144  +    && (GCC_VERSION>=4003000 || CLANG_VERSION>=3000000)
  1145   1145     u32 x;
  1146   1146     memcpy(&x,p,4);
  1147   1147     return __builtin_bswap32(x);
  1148   1148   #elif SQLITE_BYTEORDER==1234 && !defined(SQLITE_DISABLE_INTRINSIC) \
  1149   1149       && defined(_MSC_VER) && _MSC_VER>=1300
  1150   1150     u32 x;
  1151   1151     memcpy(&x,p,4);
................................................................................
  1155   1155     return ((unsigned)p[0]<<24) | (p[1]<<16) | (p[2]<<8) | p[3];
  1156   1156   #endif
  1157   1157   }
  1158   1158   void sqlite3Put4byte(unsigned char *p, u32 v){
  1159   1159   #if SQLITE_BYTEORDER==4321
  1160   1160     memcpy(p,&v,4);
  1161   1161   #elif SQLITE_BYTEORDER==1234 && !defined(SQLITE_DISABLE_INTRINSIC) \
  1162         -    && defined(__GNUC__) && GCC_VERSION>=4003000
         1162  +    && (GCC_VERSION>=4003000 || CLANG_VERSION>=3000000)
  1163   1163     u32 x = __builtin_bswap32(v);
  1164   1164     memcpy(p,&x,4);
  1165   1165   #elif SQLITE_BYTEORDER==1234 && !defined(SQLITE_DISABLE_INTRINSIC) \
  1166   1166       && defined(_MSC_VER) && _MSC_VER>=1300
  1167   1167     u32 x = _byteswap_ulong(v);
  1168   1168     memcpy(p,&x,4);
  1169   1169   #else
................................................................................
  1275   1275   /*
  1276   1276   ** Attempt to add, substract, or multiply the 64-bit signed value iB against
  1277   1277   ** the other 64-bit signed integer at *pA and store the result in *pA.
  1278   1278   ** Return 0 on success.  Or if the operation would have resulted in an
  1279   1279   ** overflow, leave *pA unchanged and return 1.
  1280   1280   */
  1281   1281   int sqlite3AddInt64(i64 *pA, i64 iB){
         1282  +#if !defined(SQLITE_DISABLE_INTRINSIC) \
         1283  +    && (GCC_VERSION>=5004000 || CLANG_VERSION>=4000000)
         1284  +  return __builtin_add_overflow(*pA, iB, pA);
         1285  +#else
  1282   1286     i64 iA = *pA;
  1283   1287     testcase( iA==0 ); testcase( iA==1 );
  1284   1288     testcase( iB==-1 ); testcase( iB==0 );
  1285   1289     if( iB>=0 ){
  1286   1290       testcase( iA>0 && LARGEST_INT64 - iA == iB );
  1287   1291       testcase( iA>0 && LARGEST_INT64 - iA == iB - 1 );
  1288   1292       if( iA>0 && LARGEST_INT64 - iA < iB ) return 1;
................................................................................
  1289   1293     }else{
  1290   1294       testcase( iA<0 && -(iA + LARGEST_INT64) == iB + 1 );
  1291   1295       testcase( iA<0 && -(iA + LARGEST_INT64) == iB + 2 );
  1292   1296       if( iA<0 && -(iA + LARGEST_INT64) > iB + 1 ) return 1;
  1293   1297     }
  1294   1298     *pA += iB;
  1295   1299     return 0; 
         1300  +#endif
  1296   1301   }
  1297   1302   int sqlite3SubInt64(i64 *pA, i64 iB){
         1303  +#if !defined(SQLITE_DISABLE_INTRINSIC) \
         1304  +    && (GCC_VERSION>=5004000 || CLANG_VERSION>=4000000)
         1305  +  return __builtin_sub_overflow(*pA, iB, pA);
         1306  +#else
  1298   1307     testcase( iB==SMALLEST_INT64+1 );
  1299   1308     if( iB==SMALLEST_INT64 ){
  1300   1309       testcase( (*pA)==(-1) ); testcase( (*pA)==0 );
  1301   1310       if( (*pA)>=0 ) return 1;
  1302   1311       *pA -= iB;
  1303   1312       return 0;
  1304   1313     }else{
  1305   1314       return sqlite3AddInt64(pA, -iB);
  1306   1315     }
         1316  +#endif
  1307   1317   }
  1308   1318   int sqlite3MulInt64(i64 *pA, i64 iB){
         1319  +#if !defined(SQLITE_DISABLE_INTRINSIC) \
         1320  +    && (GCC_VERSION>=5004000 || CLANG_VERSION>=4000000)
         1321  +  return __builtin_mul_overflow(*pA, iB, pA);
         1322  +#else
  1309   1323     i64 iA = *pA;
  1310   1324     if( iB>0 ){
  1311   1325       if( iA>LARGEST_INT64/iB ) return 1;
  1312   1326       if( iA<SMALLEST_INT64/iB ) return 1;
  1313   1327     }else if( iB<0 ){
  1314   1328       if( iA>0 ){
  1315   1329         if( iB<SMALLEST_INT64/iA ) return 1;
................................................................................
  1317   1331         if( iB==SMALLEST_INT64 ) return 1;
  1318   1332         if( iA==SMALLEST_INT64 ) return 1;
  1319   1333         if( -iA>LARGEST_INT64/-iB ) return 1;
  1320   1334       }
  1321   1335     }
  1322   1336     *pA = iA*iB;
  1323   1337     return 0;
         1338  +#endif
  1324   1339   }
  1325   1340   
  1326   1341   /*
  1327   1342   ** Compute the absolute value of a 32-bit signed integer, of possible.  Or 
  1328   1343   ** if the integer has a value of -2147483648, return +2147483647
  1329   1344   */
  1330   1345   int sqlite3AbsInt32(int x){

Changes to src/vdbe.c.

   579    579     unsigned nProgressLimit = 0;/* Invoke xProgress() when nVmStep reaches this */
   580    580   #endif
   581    581     Mem *aMem = p->aMem;       /* Copy of p->aMem */
   582    582     Mem *pIn1 = 0;             /* 1st input operand */
   583    583     Mem *pIn2 = 0;             /* 2nd input operand */
   584    584     Mem *pIn3 = 0;             /* 3rd input operand */
   585    585     Mem *pOut = 0;             /* Output operand */
   586         -  int *aPermute = 0;         /* Permutation of columns for OP_Compare */
   587         -  i64 lastRowid = db->lastRowid;  /* Saved value of the last insert ROWID */
   588    586   #ifdef VDBE_PROFILE
   589    587     u64 start;                 /* CPU clock count at start of opcode */
   590    588   #endif
   591    589     /*** INSERT STACK UNION HERE ***/
   592    590   
   593    591     assert( p->magic==VDBE_MAGIC_RUN );  /* sqlite3_step() verifies this */
   594    592     sqlite3VdbeEnter(p);
................................................................................
   957    955     if( pOp->p1==SQLITE_OK && p->pFrame ){
   958    956       /* Halt the sub-program. Return control to the parent frame. */
   959    957       pFrame = p->pFrame;
   960    958       p->pFrame = pFrame->pParent;
   961    959       p->nFrame--;
   962    960       sqlite3VdbeSetChanges(db, p->nChange);
   963    961       pcx = sqlite3VdbeFrameRestore(pFrame);
   964         -    lastRowid = db->lastRowid;
   965    962       if( pOp->p2==OE_Ignore ){
   966    963         /* Instruction pcx is the OP_Program that invoked the sub-program 
   967    964         ** currently being halted. If the p2 instruction of this OP_Halt
   968    965         ** instruction is set to OE_Ignore, then the sub-program is throwing
   969    966         ** an IGNORE exception. In this case jump to the address specified
   970    967         ** as the p2 of the calling OP_Program.  */
   971    968         pcx = p->aOp[pcx].p2-1;
................................................................................
  1192   1189   
  1193   1190     assert( pOp->p1>0 && pOp->p1<=p->nVar );
  1194   1191     assert( pOp->p4.z==0 || pOp->p4.z==sqlite3VListNumToName(p->pVList,pOp->p1) );
  1195   1192     pVar = &p->aVar[pOp->p1 - 1];
  1196   1193     if( sqlite3VdbeMemTooBig(pVar) ){
  1197   1194       goto too_big;
  1198   1195     }
  1199         -  pOut = out2Prerelease(p, pOp);
         1196  +  pOut = &aMem[pOp->p2];
  1200   1197     sqlite3VdbeMemShallowCopy(pOut, pVar, MEM_Static);
  1201   1198     UPDATE_MAX_BLOBSIZE(pOut);
  1202   1199     break;
  1203   1200   }
  1204   1201   
  1205   1202   /* Opcode: Move P1 P2 P3 * *
  1206   1203   ** Synopsis: r[P2@P3]=r[P1@P3]
................................................................................
  1679   1676     for(i=0; i<pCtx->argc; i++){
  1680   1677       assert( memIsValid(pCtx->argv[i]) );
  1681   1678       REGISTER_TRACE(pOp->p2+i, pCtx->argv[i]);
  1682   1679     }
  1683   1680   #endif
  1684   1681     MemSetTypeFlag(pCtx->pOut, MEM_Null);
  1685   1682     pCtx->fErrorOrAux = 0;
  1686         -  db->lastRowid = lastRowid;
  1687   1683     (*pCtx->pFunc->xSFunc)(pCtx, pCtx->argc, pCtx->argv);/* IMP: R-24505-23230 */
  1688         -  lastRowid = db->lastRowid;  /* Remember rowid changes made by xSFunc */
  1689   1684   
  1690   1685     /* If the function returned an error, throw an exception */
  1691   1686     if( pCtx->fErrorOrAux ){
  1692   1687       if( pCtx->isError ){
  1693   1688         sqlite3VdbeError(p, "%s", sqlite3_value_text(pCtx->pOut));
  1694   1689         rc = pCtx->isError;
  1695   1690       }
................................................................................
  2137   2132     if( iCompare!=0 ) goto jump_to_p2;
  2138   2133     break;
  2139   2134   }
  2140   2135   
  2141   2136   
  2142   2137   /* Opcode: Permutation * * * P4 *
  2143   2138   **
  2144         -** Set the permutation used by the OP_Compare operator to be the array
  2145         -** of integers in P4.
         2139  +** Set the permutation used by the OP_Compare operator in the next
         2140  +** instruction.  The permutation is stored in the P4 operand.
  2146   2141   **
  2147   2142   ** The permutation is only valid until the next OP_Compare that has
  2148   2143   ** the OPFLAG_PERMUTE bit set in P5. Typically the OP_Permutation should 
  2149   2144   ** occur immediately prior to the OP_Compare.
  2150   2145   **
  2151   2146   ** The first integer in the P4 integer array is the length of the array
  2152   2147   ** and does not become part of the permutation.
  2153   2148   */
  2154   2149   case OP_Permutation: {
  2155   2150     assert( pOp->p4type==P4_INTARRAY );
  2156   2151     assert( pOp->p4.ai );
  2157         -  aPermute = pOp->p4.ai + 1;
         2152  +  assert( pOp[1].opcode==OP_Compare );
         2153  +  assert( pOp[1].p5 & OPFLAG_PERMUTE );
  2158   2154     break;
  2159   2155   }
  2160   2156   
  2161   2157   /* Opcode: Compare P1 P2 P3 P4 P5
  2162   2158   ** Synopsis: r[P1@P3] <-> r[P2@P3]
  2163   2159   **
  2164   2160   ** Compare two vectors of registers in reg(P1)..reg(P1+P3-1) (call this
................................................................................
  2183   2179     int i;
  2184   2180     int p1;
  2185   2181     int p2;
  2186   2182     const KeyInfo *pKeyInfo;
  2187   2183     int idx;
  2188   2184     CollSeq *pColl;    /* Collating sequence to use on this term */
  2189   2185     int bRev;          /* True for DESCENDING sort order */
         2186  +  int *aPermute;     /* The permutation */
  2190   2187   
  2191         -  if( (pOp->p5 & OPFLAG_PERMUTE)==0 ) aPermute = 0;
         2188  +  if( (pOp->p5 & OPFLAG_PERMUTE)==0 ){
         2189  +    aPermute = 0;
         2190  +  }else{
         2191  +    assert( pOp>aOp );
         2192  +    assert( pOp[-1].opcode==OP_Permutation );
         2193  +    assert( pOp[-1].p4type==P4_INTARRAY );
         2194  +    aPermute = pOp[-1].p4.ai + 1;
         2195  +    assert( aPermute!=0 );
         2196  +  }
  2192   2197     n = pOp->p3;
  2193   2198     pKeyInfo = pOp->p4.pKeyInfo;
  2194   2199     assert( n>0 );
  2195   2200     assert( pKeyInfo!=0 );
  2196   2201     p1 = pOp->p1;
  2197   2202     p2 = pOp->p2;
  2198   2203   #if SQLITE_DEBUG
................................................................................
  2217   2222       bRev = pKeyInfo->aSortOrder[i];
  2218   2223       iCompare = sqlite3MemCompare(&aMem[p1+idx], &aMem[p2+idx], pColl);
  2219   2224       if( iCompare ){
  2220   2225         if( bRev ) iCompare = -iCompare;
  2221   2226         break;
  2222   2227       }
  2223   2228     }
  2224         -  aPermute = 0;
  2225   2229     break;
  2226   2230   }
  2227   2231   
  2228   2232   /* Opcode: Jump P1 P2 P3 * *
  2229   2233   **
  2230   2234   ** Jump to the instruction at address P1, P2, or P3 depending on whether
  2231   2235   ** in the most recent OP_Compare instruction the P1 vector was less than
................................................................................
  2773   2777     if( zAffinity ){
  2774   2778       pRec = pData0;
  2775   2779       do{
  2776   2780         applyAffinity(pRec++, *(zAffinity++), encoding);
  2777   2781         assert( zAffinity[0]==0 || pRec<=pLast );
  2778   2782       }while( zAffinity[0] );
  2779   2783     }
         2784  +
         2785  +#ifdef SQLITE_ENABLE_NULL_TRIM
         2786  +  /* NULLs can be safely trimmed from the end of the record, as long as
         2787  +  ** as the schema format is 2 or more and none of the omitted columns
         2788  +  ** have a non-NULL default value.  Also, the record must be left with
         2789  +  ** at least one field.  If P5>0 then it will be one more than the
         2790  +  ** index of the right-most column with a non-NULL default value */
         2791  +  if( pOp->p5 ){
         2792  +    while( (pLast->flags & MEM_Null)!=0 && nField>pOp->p5 ){
         2793  +      pLast--;
         2794  +      nField--;
         2795  +    }
         2796  +  }
         2797  +#endif
  2780   2798   
  2781   2799     /* Loop through the elements that will make up the record to figure
  2782   2800     ** out how much space is required for the new record.
  2783   2801     */
  2784   2802     pRec = pLast;
  2785   2803     do{
  2786   2804       assert( memIsValid(pRec) );
................................................................................
  4401   4419      && !(pOp->p5 & OPFLAG_ISUPDATE)
  4402   4420     ){
  4403   4421       sqlite3VdbePreUpdateHook(p, pC, SQLITE_INSERT, zDb, pTab, x.nKey, pOp->p2);
  4404   4422     }
  4405   4423   #endif
  4406   4424   
  4407   4425     if( pOp->p5 & OPFLAG_NCHANGE ) p->nChange++;
  4408         -  if( pOp->p5 & OPFLAG_LASTROWID ) db->lastRowid = lastRowid = x.nKey;
         4426  +  if( pOp->p5 & OPFLAG_LASTROWID ) db->lastRowid = x.nKey;
  4409   4427     if( pData->flags & MEM_Null ){
  4410   4428       x.pData = 0;
  4411   4429       x.nData = 0;
  4412   4430     }else{
  4413   4431       assert( pData->flags & (MEM_Blob|MEM_Str) );
  4414   4432       x.pData = pData->z;
  4415   4433       x.nData = pData->n;
................................................................................
  4418   4436     if( pData->flags & MEM_Zero ){
  4419   4437       x.nZero = pData->u.nZero;
  4420   4438     }else{
  4421   4439       x.nZero = 0;
  4422   4440     }
  4423   4441     x.pKey = 0;
  4424   4442     rc = sqlite3BtreeInsert(pC->uc.pCursor, &x,
  4425         -                          (pOp->p5 & OPFLAG_APPEND)!=0, seekResult
         4443  +      (pOp->p5 & (OPFLAG_APPEND|OPFLAG_SAVEPOSITION)), seekResult
  4426   4444     );
  4427   4445     pC->deferredMoveto = 0;
  4428   4446     pC->cacheStatus = CACHE_STALE;
  4429   4447   
  4430   4448     /* Invoke the update-hook if required. */
  4431   4449     if( rc ) goto abort_due_to_error;
  4432   4450     if( db->xUpdateCallback && op ){
................................................................................
  4629   4647     assert( rc!=SQLITE_OK || (pOut->flags & MEM_Blob) );
  4630   4648     assert( pOp->p1>=0 && pOp->p1<p->nCursor );
  4631   4649     if( rc ) goto abort_due_to_error;
  4632   4650     p->apCsr[pOp->p3]->cacheStatus = CACHE_STALE;
  4633   4651     break;
  4634   4652   }
  4635   4653   
  4636         -/* Opcode: RowData P1 P2 * * *
         4654  +/* Opcode: RowData P1 P2 P3 * *
  4637   4655   ** Synopsis: r[P2]=data
  4638   4656   **
  4639   4657   ** Write into register P2 the complete row content for the row at 
  4640   4658   ** which cursor P1 is currently pointing.
  4641   4659   ** There is no interpretation of the data.  
  4642   4660   ** It is just copied onto the P2 register exactly as 
  4643   4661   ** it is found in the database file.
  4644   4662   **
  4645   4663   ** If cursor P1 is an index, then the content is the key of the row.
  4646   4664   ** If cursor P2 is a table, then the content extracted is the data.
  4647   4665   **
  4648   4666   ** If the P1 cursor must be pointing to a valid row (not a NULL row)
  4649   4667   ** of a real table, not a pseudo-table.
         4668  +**
         4669  +** If P3!=0 then this opcode is allowed to make an ephermeral pointer
         4670  +** into the database page.  That means that the content of the output
         4671  +** register will be invalidated as soon as the cursor moves - including
         4672  +** moves caused by other cursors that "save" the the current cursors
         4673  +** position in order that they can write to the same table.  If P3==0
         4674  +** then a copy of the data is made into memory.  P3!=0 is faster, but
         4675  +** P3==0 is safer.
         4676  +**
         4677  +** If P3!=0 then the content of the P2 register is unsuitable for use
         4678  +** in OP_Result and any OP_Result will invalidate the P2 register content.
         4679  +** The P2 register content is invalidated by opcodes like OP_Function or
         4680  +** by any use of another cursor pointing to the same table.
  4650   4681   */
  4651   4682   case OP_RowData: {
  4652   4683     VdbeCursor *pC;
  4653   4684     BtCursor *pCrsr;
  4654   4685     u32 n;
  4655   4686   
  4656         -  pOut = &aMem[pOp->p2];
  4657         -  memAboutToChange(p, pOut);
         4687  +  pOut = out2Prerelease(p, pOp);
  4658   4688   
  4659   4689     assert( pOp->p1>=0 && pOp->p1<p->nCursor );
  4660   4690     pC = p->apCsr[pOp->p1];
  4661   4691     assert( pC!=0 );
  4662   4692     assert( pC->eCurType==CURTYPE_BTREE );
  4663   4693     assert( isSorter(pC)==0 );
  4664   4694     assert( pC->nullRow==0 );
................................................................................
  4681   4711   #endif
  4682   4712   
  4683   4713     n = sqlite3BtreePayloadSize(pCrsr);
  4684   4714     if( n>(u32)db->aLimit[SQLITE_LIMIT_LENGTH] ){
  4685   4715       goto too_big;
  4686   4716     }
  4687   4717     testcase( n==0 );
  4688         -  if( sqlite3VdbeMemClearAndResize(pOut, MAX(n,32)) ){
  4689         -    goto no_mem;
  4690         -  }
  4691         -  pOut->n = n;
  4692         -  MemSetTypeFlag(pOut, MEM_Blob);
  4693         -  rc = sqlite3BtreePayload(pCrsr, 0, n, pOut->z);
         4718  +  rc = sqlite3VdbeMemFromBtree(pCrsr, 0, n, pOut);
  4694   4719     if( rc ) goto abort_due_to_error;
  4695         -  pOut->enc = SQLITE_UTF8;  /* In case the blob is ever cast to text */
         4720  +  if( !pOp->p3 ) Deephemeralize(pOut);
  4696   4721     UPDATE_MAX_BLOBSIZE(pOut);
  4697   4722     REGISTER_TRACE(pOp->p2, pOut);
  4698   4723     break;
  4699   4724   }
  4700   4725   
  4701   4726   /* Opcode: Rowid P1 P2 * * *
  4702   4727   ** Synopsis: r[P2]=rowid
................................................................................
  5076   5101       rc = sqlite3VdbeSorterWrite(pC, pIn2);
  5077   5102     }else{
  5078   5103       x.nKey = pIn2->n;
  5079   5104       x.pKey = pIn2->z;
  5080   5105       x.aMem = aMem + pOp->p3;
  5081   5106       x.nMem = (u16)pOp->p4.i;
  5082   5107       rc = sqlite3BtreeInsert(pC->uc.pCursor, &x,
  5083         -         (pOp->p5 & OPFLAG_APPEND)!=0, 
         5108  +         (pOp->p5 & (OPFLAG_APPEND|OPFLAG_SAVEPOSITION)), 
  5084   5109           ((pOp->p5 & OPFLAG_USESEEKRESULT) ? pC->seekResult : 0)
  5085   5110           );
  5086   5111       assert( pC->deferredMoveto==0 );
  5087   5112       pC->cacheStatus = CACHE_STALE;
  5088   5113     }
  5089   5114     if( rc) goto abort_due_to_error;
  5090   5115     break;
................................................................................
  5198   5223         pTabCur->deferredMoveto = 1;
  5199   5224         assert( pOp->p4type==P4_INTARRAY || pOp->p4.ai==0 );
  5200   5225         pTabCur->aAltMap = pOp->p4.ai;
  5201   5226         pTabCur->pAltCursor = pC;
  5202   5227       }else{
  5203   5228         pOut = out2Prerelease(p, pOp);
  5204   5229         pOut->u.i = rowid;
  5205         -      pOut->flags = MEM_Int;
  5206   5230       }
  5207   5231     }else{
  5208   5232       assert( pOp->opcode==OP_IdxRowid );
  5209   5233       sqlite3VdbeMemSetNull(&aMem[pOp->p2]);
  5210   5234     }
  5211   5235     break;
  5212   5236   }
................................................................................
  5840   5864           || (pProgram->nCsr==0 && pProgram->nMem+1==pFrame->nChildMem) );
  5841   5865       assert( pProgram->nCsr==pFrame->nChildCsr );
  5842   5866       assert( (int)(pOp - aOp)==pFrame->pc );
  5843   5867     }
  5844   5868   
  5845   5869     p->nFrame++;
  5846   5870     pFrame->pParent = p->pFrame;
  5847         -  pFrame->lastRowid = lastRowid;
         5871  +  pFrame->lastRowid = db->lastRowid;
  5848   5872     pFrame->nChange = p->nChange;
  5849   5873     pFrame->nDbChange = p->db->nChange;
  5850   5874     assert( pFrame->pAuxData==0 );
  5851   5875     pFrame->pAuxData = p->pAuxData;
  5852   5876     p->pAuxData = 0;
  5853   5877     p->nChange = 0;
  5854   5878     p->pFrame = pFrame;
................................................................................
  6781   6805       }
  6782   6806       db->vtabOnConflict = pOp->p5;
  6783   6807       rc = pModule->xUpdate(pVtab, nArg, apArg, &rowid);
  6784   6808       db->vtabOnConflict = vtabOnConflict;
  6785   6809       sqlite3VtabImportErrmsg(p, pVtab);
  6786   6810       if( rc==SQLITE_OK && pOp->p1 ){
  6787   6811         assert( nArg>1 && apArg[0] && (apArg[0]->flags&MEM_Null) );
  6788         -      db->lastRowid = lastRowid = rowid;
         6812  +      db->lastRowid = rowid;
  6789   6813       }
  6790   6814       if( (rc&0xff)==SQLITE_CONSTRAINT && pOp->p4.pVtab->bConstraint ){
  6791   6815         if( pOp->p5==OE_Ignore ){
  6792   6816           rc = SQLITE_OK;
  6793   6817         }else{
  6794   6818           p->errorAction = ((pOp->p5==OE_Replace) ? OE_Abort : pOp->p5);
  6795   6819         }
................................................................................
  7017   7041       sqlite3ResetOneSchema(db, resetSchemaOnFault-1);
  7018   7042     }
  7019   7043   
  7020   7044     /* This is the only way out of this procedure.  We have to
  7021   7045     ** release the mutexes on btrees that were acquired at the
  7022   7046     ** top. */
  7023   7047   vdbe_return:
  7024         -  db->lastRowid = lastRowid;
  7025   7048     testcase( nVmStep>0 );
  7026   7049     p->aCounter[SQLITE_STMTSTATUS_VM_STEP] += (int)nVmStep;
  7027   7050     sqlite3VdbeLeave(p);
  7028   7051     assert( rc!=SQLITE_OK || nExtraDelete==0 
  7029   7052          || sqlite3_strlike("DELETE%",p->zSql,0)!=0 
  7030   7053     );
  7031   7054     return rc;

Changes to src/vdbe.h.

    37     37   ** A single instruction of the virtual machine has an opcode
    38     38   ** and as many as three operands.  The instruction is recorded
    39     39   ** as an instance of the following structure:
    40     40   */
    41     41   struct VdbeOp {
    42     42     u8 opcode;          /* What operation to perform */
    43     43     signed char p4type; /* One of the P4_xxx constants for p4 */
    44         -  u8 notUsed1;
    45         -  u8 p5;              /* Fifth parameter is an unsigned character */
           44  +  u16 p5;             /* Fifth parameter is an unsigned 16-bit integer */
    46     45     int p1;             /* First operand */
    47     46     int p2;             /* Second parameter (often the jump destination) */
    48     47     int p3;             /* The third parameter */
    49     48     union p4union {     /* fourth parameter */
    50     49       int i;                 /* Integer value if p4type==P4_INT32 */
    51     50       void *p;               /* Generic pointer */
    52     51       char *z;               /* Pointer to data for string (char array) types */
................................................................................
   190    189   #endif
   191    190   VdbeOp *sqlite3VdbeAddOpList(Vdbe*, int nOp, VdbeOpList const *aOp, int iLineno);
   192    191   void sqlite3VdbeAddParseSchemaOp(Vdbe*,int,char*);
   193    192   void sqlite3VdbeChangeOpcode(Vdbe*, u32 addr, u8);
   194    193   void sqlite3VdbeChangeP1(Vdbe*, u32 addr, int P1);
   195    194   void sqlite3VdbeChangeP2(Vdbe*, u32 addr, int P2);
   196    195   void sqlite3VdbeChangeP3(Vdbe*, u32 addr, int P3);
   197         -void sqlite3VdbeChangeP5(Vdbe*, u8 P5);
          196  +void sqlite3VdbeChangeP5(Vdbe*, u16 P5);
   198    197   void sqlite3VdbeJumpHere(Vdbe*, int addr);
   199    198   int sqlite3VdbeChangeToNoop(Vdbe*, int addr);
   200    199   int sqlite3VdbeDeletePriorOpcode(Vdbe*, u8 op);
   201    200   void sqlite3VdbeChangeP4(Vdbe*, int addr, const char *zP4, int N);
   202    201   void sqlite3VdbeAppendP4(Vdbe*, void *pP4, int p4type);
   203    202   void sqlite3VdbeSetP4KeyInfo(Parse*, Index*);
   204    203   void sqlite3VdbeUsesBtree(Vdbe*, int);

Changes to src/vdbeapi.c.

  1699   1699   
  1700   1700   /*
  1701   1701   ** This function is called from within a pre-update callback to retrieve
  1702   1702   ** a field of the row currently being updated or deleted.
  1703   1703   */
  1704   1704   int sqlite3_preupdate_old(sqlite3 *db, int iIdx, sqlite3_value **ppValue){
  1705   1705     PreUpdate *p = db->pPreUpdate;
         1706  +  Mem *pMem;
  1706   1707     int rc = SQLITE_OK;
  1707   1708   
  1708   1709     /* Test that this call is being made from within an SQLITE_DELETE or
  1709   1710     ** SQLITE_UPDATE pre-update callback, and that iIdx is within range. */
  1710   1711     if( !p || p->op==SQLITE_INSERT ){
  1711   1712       rc = SQLITE_MISUSE_BKPT;
  1712   1713       goto preupdate_old_out;
................................................................................
  1732   1733       if( rc!=SQLITE_OK ){
  1733   1734         sqlite3DbFree(db, aRec);
  1734   1735         goto preupdate_old_out;
  1735   1736       }
  1736   1737       p->aRecord = aRec;
  1737   1738     }
  1738   1739   
  1739         -  if( iIdx>=p->pUnpacked->nField ){
         1740  +  pMem = *ppValue = &p->pUnpacked->aMem[iIdx];
         1741  +  if( iIdx==p->pTab->iPKey ){
         1742  +    sqlite3VdbeMemSetInt64(pMem, p->iKey1);
         1743  +  }else if( iIdx>=p->pUnpacked->nField ){
  1740   1744       *ppValue = (sqlite3_value *)columnNullValue();
  1741         -  }else{
  1742         -    Mem *pMem = *ppValue = &p->pUnpacked->aMem[iIdx];
  1743         -    *ppValue = &p->pUnpacked->aMem[iIdx];
  1744         -    if( iIdx==p->pTab->iPKey ){
  1745         -      sqlite3VdbeMemSetInt64(pMem, p->iKey1);
  1746         -    }else if( p->pTab->aCol[iIdx].affinity==SQLITE_AFF_REAL ){
  1747         -      if( pMem->flags & MEM_Int ){
  1748         -        sqlite3VdbeMemRealify(pMem);
  1749         -      }
         1745  +  }else if( p->pTab->aCol[iIdx].affinity==SQLITE_AFF_REAL ){
         1746  +    if( pMem->flags & MEM_Int ){
         1747  +      sqlite3VdbeMemRealify(pMem);
  1750   1748       }
  1751   1749     }
  1752   1750   
  1753   1751    preupdate_old_out:
  1754   1752     sqlite3Error(db, rc);
  1755   1753     return sqlite3ApiExit(db, rc);
  1756   1754   }
................................................................................
  1815   1813         pUnpack = vdbeUnpackRecord(&p->keyinfo, pData->n, pData->z);
  1816   1814         if( !pUnpack ){
  1817   1815           rc = SQLITE_NOMEM;
  1818   1816           goto preupdate_new_out;
  1819   1817         }
  1820   1818         p->pNewUnpacked = pUnpack;
  1821   1819       }
  1822         -    if( iIdx>=pUnpack->nField ){
         1820  +    pMem = &pUnpack->aMem[iIdx];
         1821  +    if( iIdx==p->pTab->iPKey ){
         1822  +      sqlite3VdbeMemSetInt64(pMem, p->iKey2);
         1823  +    }else if( iIdx>=pUnpack->nField ){
  1823   1824         pMem = (sqlite3_value *)columnNullValue();
  1824         -    }else{
  1825         -      pMem = &pUnpack->aMem[iIdx];
  1826         -      if( iIdx==p->pTab->iPKey ){
  1827         -        sqlite3VdbeMemSetInt64(pMem, p->iKey2);
  1828         -      }
  1829   1825       }
  1830   1826     }else{
  1831   1827       /* For an UPDATE, memory cell (p->iNewReg+1+iIdx) contains the required
  1832   1828       ** value. Make a copy of the cell contents and return a pointer to it.
  1833   1829       ** It is not safe to return a pointer to the memory cell itself as the
  1834   1830       ** caller may modify the value text encoding.
  1835   1831       */

Changes to src/vdbeaux.c.

   660    660     int i;
   661    661     for(i=0; i<p->nOp; i++){
   662    662       assert( p->aOp[i].opcode!=OP_ResultRow );
   663    663     }
   664    664   }
   665    665   #endif
   666    666   
          667  +/*
          668  +** Verify that the VM passed as the only argument does not contain
          669  +** an OP_ResultRow opcode. Fail an assert() if it does. This is used
          670  +** by code in pragma.c to ensure that the implementation of certain
          671  +** pragmas comports with the flags specified in the mkpragmatab.tcl
          672  +** script.
          673  +*/
          674  +#if defined(SQLITE_DEBUG) && !defined(SQLITE_TEST_REALLOC_STRESS)
          675  +void sqlite3VdbeVerifyNoResultRow(Vdbe *p){
          676  +  int i;
          677  +  for(i=0; i<p->nOp; i++){
          678  +    assert( p->aOp[i].opcode!=OP_ResultRow );
          679  +  }
          680  +}
          681  +#endif
          682  +
   667    683   /*
   668    684   ** This function returns a pointer to the array of opcodes associated with
   669    685   ** the Vdbe passed as the first argument. It is the callers responsibility
   670    686   ** to arrange for the returned array to be eventually freed using the 
   671    687   ** vdbeFreeOpArray() function.
   672    688   **
   673    689   ** Before returning, *pnOp is set to the number of entries in the returned
................................................................................
   779    795   }
   780    796   void sqlite3VdbeChangeP2(Vdbe *p, u32 addr, int val){
   781    797     sqlite3VdbeGetOp(p,addr)->p2 = val;
   782    798   }
   783    799   void sqlite3VdbeChangeP3(Vdbe *p, u32 addr, int val){
   784    800     sqlite3VdbeGetOp(p,addr)->p3 = val;
   785    801   }
   786         -void sqlite3VdbeChangeP5(Vdbe *p, u8 p5){
          802  +void sqlite3VdbeChangeP5(Vdbe *p, u16 p5){
   787    803     assert( p->nOp>0 || p->db->mallocFailed );
   788    804     if( p->nOp>0 ) p->aOp[p->nOp-1].p5 = p5;
   789    805   }
   790    806   
   791    807   /*
   792    808   ** Change the P2 operand of instruction addr so that it points to
   793    809   ** the address of the next instruction to be coded.
................................................................................
  2493   2509   ** SAVEPOINT_RELEASE. If it is SAVEPOINT_ROLLBACK, then the statement
  2494   2510   ** transaction is rolled back. If eOp is SAVEPOINT_RELEASE, then the 
  2495   2511   ** statement transaction is committed.
  2496   2512   **
  2497   2513   ** If an IO error occurs, an SQLITE_IOERR_XXX error code is returned. 
  2498   2514   ** Otherwise SQLITE_OK.
  2499   2515   */
  2500         -int sqlite3VdbeCloseStatement(Vdbe *p, int eOp){
         2516  +static SQLITE_NOINLINE int vdbeCloseStatement(Vdbe *p, int eOp){
  2501   2517     sqlite3 *const db = p->db;
  2502   2518     int rc = SQLITE_OK;
         2519  +  int i;
         2520  +  const int iSavepoint = p->iStatement-1;
  2503   2521   
  2504         -  /* If p->iStatement is greater than zero, then this Vdbe opened a 
  2505         -  ** statement transaction that should be closed here. The only exception
  2506         -  ** is that an IO error may have occurred, causing an emergency rollback.
  2507         -  ** In this case (db->nStatement==0), and there is nothing to do.
  2508         -  */
  2509         -  if( db->nStatement && p->iStatement ){
  2510         -    int i;
  2511         -    const int iSavepoint = p->iStatement-1;
         2522  +  assert( eOp==SAVEPOINT_ROLLBACK || eOp==SAVEPOINT_RELEASE);
         2523  +  assert( db->nStatement>0 );
         2524  +  assert( p->iStatement==(db->nStatement+db->nSavepoint) );
  2512   2525   
  2513         -    assert( eOp==SAVEPOINT_ROLLBACK || eOp==SAVEPOINT_RELEASE);
  2514         -    assert( db->nStatement>0 );
  2515         -    assert( p->iStatement==(db->nStatement+db->nSavepoint) );
  2516         -
  2517         -    for(i=0; i<db->nDb; i++){ 
  2518         -      int rc2 = SQLITE_OK;
  2519         -      Btree *pBt = db->aDb[i].pBt;
  2520         -      if( pBt ){
  2521         -        if( eOp==SAVEPOINT_ROLLBACK ){
  2522         -          rc2 = sqlite3BtreeSavepoint(pBt, SAVEPOINT_ROLLBACK, iSavepoint);
  2523         -        }
  2524         -        if( rc2==SQLITE_OK ){
  2525         -          rc2 = sqlite3BtreeSavepoint(pBt, SAVEPOINT_RELEASE, iSavepoint);
  2526         -        }
  2527         -        if( rc==SQLITE_OK ){
  2528         -          rc = rc2;
  2529         -        }
  2530         -      }
  2531         -    }
  2532         -    db->nStatement--;
  2533         -    p->iStatement = 0;
  2534         -
  2535         -    if( rc==SQLITE_OK ){
         2526  +  for(i=0; i<db->nDb; i++){ 
         2527  +    int rc2 = SQLITE_OK;
         2528  +    Btree *pBt = db->aDb[i].pBt;
         2529  +    if( pBt ){
  2536   2530         if( eOp==SAVEPOINT_ROLLBACK ){
  2537         -        rc = sqlite3VtabSavepoint(db, SAVEPOINT_ROLLBACK, iSavepoint);
         2531  +        rc2 = sqlite3BtreeSavepoint(pBt, SAVEPOINT_ROLLBACK, iSavepoint);
         2532  +      }
         2533  +      if( rc2==SQLITE_OK ){
         2534  +        rc2 = sqlite3BtreeSavepoint(pBt, SAVEPOINT_RELEASE, iSavepoint);
  2538   2535         }
  2539   2536         if( rc==SQLITE_OK ){
  2540         -        rc = sqlite3VtabSavepoint(db, SAVEPOINT_RELEASE, iSavepoint);
         2537  +        rc = rc2;
  2541   2538         }
  2542   2539       }
         2540  +  }
         2541  +  db->nStatement--;
         2542  +  p->iStatement = 0;
  2543   2543   
  2544         -    /* If the statement transaction is being rolled back, also restore the 
  2545         -    ** database handles deferred constraint counter to the value it had when 
  2546         -    ** the statement transaction was opened.  */
         2544  +  if( rc==SQLITE_OK ){
  2547   2545       if( eOp==SAVEPOINT_ROLLBACK ){
  2548         -      db->nDeferredCons = p->nStmtDefCons;
  2549         -      db->nDeferredImmCons = p->nStmtDefImmCons;
         2546  +      rc = sqlite3VtabSavepoint(db, SAVEPOINT_ROLLBACK, iSavepoint);
  2550   2547       }
         2548  +    if( rc==SQLITE_OK ){
         2549  +      rc = sqlite3VtabSavepoint(db, SAVEPOINT_RELEASE, iSavepoint);
         2550  +    }
         2551  +  }
         2552  +
         2553  +  /* If the statement transaction is being rolled back, also restore the 
         2554  +  ** database handles deferred constraint counter to the value it had when 
         2555  +  ** the statement transaction was opened.  */
         2556  +  if( eOp==SAVEPOINT_ROLLBACK ){
         2557  +    db->nDeferredCons = p->nStmtDefCons;
         2558  +    db->nDeferredImmCons = p->nStmtDefImmCons;
  2551   2559     }
  2552   2560     return rc;
  2553   2561   }
         2562  +int sqlite3VdbeCloseStatement(Vdbe *p, int eOp){
         2563  +  if( p->db->nStatement && p->iStatement ){
         2564  +    return vdbeCloseStatement(p, eOp);
         2565  +  }
         2566  +  return SQLITE_OK;
         2567  +}
         2568  +
  2554   2569   
  2555   2570   /*
  2556   2571   ** This function is called when a transaction opened by the database 
  2557   2572   ** handle associated with the VM passed as an argument is about to be 
  2558   2573   ** committed. If there are outstanding deferred foreign key constraint
  2559   2574   ** violations, return SQLITE_ERROR. Otherwise, SQLITE_OK.
  2560   2575   **
................................................................................
  4581   4596   ** If the second argument is not NULL, release any allocations associated 
  4582   4597   ** with the memory cells in the p->aMem[] array. Also free the UnpackedRecord
  4583   4598   ** structure itself, using sqlite3DbFree().
  4584   4599   **
  4585   4600   ** This function is used to free UnpackedRecord structures allocated by
  4586   4601   ** the vdbeUnpackRecord() function found in vdbeapi.c.
  4587   4602   */
  4588         -static void vdbeFreeUnpacked(sqlite3 *db, UnpackedRecord *p){
         4603  +static void vdbeFreeUnpacked(sqlite3 *db, int nField, UnpackedRecord *p){
  4589   4604     if( p ){
  4590   4605       int i;
  4591         -    for(i=0; i<p->nField; i++){
         4606  +    for(i=0; i<nField; i++){
  4592   4607         Mem *pMem = &p->aMem[i];
  4593   4608         if( pMem->zMalloc ) sqlite3VdbeMemRelease(pMem);
  4594   4609       }
  4595   4610       sqlite3DbFree(db, p);
  4596   4611     }
  4597   4612   }
  4598   4613   #endif /* SQLITE_ENABLE_PREUPDATE_HOOK */
................................................................................
  4643   4658     preupdate.iKey2 = iKey2;
  4644   4659     preupdate.pTab = pTab;
  4645   4660   
  4646   4661     db->pPreUpdate = &preupdate;
  4647   4662     db->xPreUpdateCallback(db->pPreUpdateArg, db, op, zDb, zTbl, iKey1, iKey2);
  4648   4663     db->pPreUpdate = 0;
  4649   4664     sqlite3DbFree(db, preupdate.aRecord);
  4650         -  vdbeFreeUnpacked(db, preupdate.pUnpacked);
  4651         -  vdbeFreeUnpacked(db, preupdate.pNewUnpacked);
         4665  +  vdbeFreeUnpacked(db, preupdate.keyinfo.nField+1, preupdate.pUnpacked);
         4666  +  vdbeFreeUnpacked(db, preupdate.keyinfo.nField+1, preupdate.pNewUnpacked);
  4652   4667     if( preupdate.aNew ){
  4653   4668       int i;
  4654   4669       for(i=0; i<pCsr->nField; i++){
  4655   4670         sqlite3VdbeMemRelease(&preupdate.aNew[i]);
  4656   4671       }
  4657   4672       sqlite3DbFree(db, preupdate.aNew);
  4658   4673     }
  4659   4674   }
  4660   4675   #endif /* SQLITE_ENABLE_PREUPDATE_HOOK */

Changes to src/vdbeblob.c.

    19     19   #ifndef SQLITE_OMIT_INCRBLOB
    20     20   
    21     21   /*
    22     22   ** Valid sqlite3_blob* handles point to Incrblob structures.
    23     23   */
    24     24   typedef struct Incrblob Incrblob;
    25     25   struct Incrblob {
    26         -  int flags;              /* Copy of "flags" passed to sqlite3_blob_open() */
    27     26     int nByte;              /* Size of open blob, in bytes */
    28     27     int iOffset;            /* Byte offset of blob in cursor data */
    29         -  int iCol;               /* Table column this handle is open on */
           28  +  u16 iCol;               /* Table column this handle is open on */
    30     29     BtCursor *pCsr;         /* Cursor pointing at blob row */
    31     30     sqlite3_stmt *pStmt;    /* Statement holding cursor open */
    32     31     sqlite3 *db;            /* The associated database */
    33     32     char *zDb;              /* Database name */
    34     33     Table *pTab;            /* Table object */
    35     34   };
    36     35   
................................................................................
    52     51   ** calls to sqlite3_blob_read(), blob_write() or blob_reopen() will 
    53     52   ** immediately return SQLITE_ABORT.
    54     53   */
    55     54   static int blobSeekToRow(Incrblob *p, sqlite3_int64 iRow, char **pzErr){
    56     55     int rc;                         /* Error code */
    57     56     char *zErr = 0;                 /* Error message */
    58     57     Vdbe *v = (Vdbe *)p->pStmt;
           58  +  sqlite3 *db = v->db;
    59     59   
    60         -  /* Set the value of the SQL statements only variable to integer iRow. 
    61         -  ** This is done directly instead of using sqlite3_bind_int64() to avoid 
    62         -  ** triggering asserts related to mutexes.
           60  +  /* Set the value of register r[1] in the SQL statement to integer iRow. 
           61  +  ** This is done directly as a performance optimization
    63     62     */
    64         -  assert( v->aVar[0].flags&MEM_Int );
    65         -  v->aVar[0].u.i = iRow;
           63  +  v->aMem[1].flags = MEM_Int;
           64  +  v->aMem[1].u.i = iRow;
    66     65   
    67         -  rc = sqlite3_step(p->pStmt);
           66  +  /* If the statement has been run before (and is paused at the OP_ResultRow)
           67  +  ** then back it up to the point where it does the OP_SeekRowid.  This could
           68  +  ** have been down with an extra OP_Goto, but simply setting the program
           69  +  ** counter is faster. */
           70  +  if( v->pc>3 ){
           71  +    v->pc = 3;
           72  +    db->nVdbeExec++;
           73  +    rc = sqlite3VdbeExec((Vdbe*)p->pStmt);
           74  +    db->nVdbeExec--;
           75  +  }else{
           76  +    rc = sqlite3_step(p->pStmt);
           77  +  }
    68     78     if( rc==SQLITE_ROW ){
    69     79       VdbeCursor *pC = v->apCsr[0];
    70         -    u32 type = pC->aType[p->iCol];
           80  +    u32 type = pC->nHdrParsed>p->iCol ? pC->aType[p->iCol] : 0;
           81  +    testcase( pC->nHdrParsed==p->iCol );
           82  +    testcase( pC->nHdrParsed==p->iCol+1 );
    71     83       if( type<12 ){
    72     84         zErr = sqlite3MPrintf(p->db, "cannot open value of type %s",
    73     85             type==0?"null": type==7?"real": "integer"
    74     86         );
    75     87         rc = SQLITE_ERROR;
    76     88         sqlite3_finalize(p->pStmt);
    77     89         p->pStmt = 0;
................................................................................
   108    120   */
   109    121   int sqlite3_blob_open(
   110    122     sqlite3* db,            /* The database connection */
   111    123     const char *zDb,        /* The attached database containing the blob */
   112    124     const char *zTable,     /* The table containing the blob */
   113    125     const char *zColumn,    /* The column containing the blob */
   114    126     sqlite_int64 iRow,      /* The row containing the glob */
   115         -  int flags,              /* True -> read/write access, false -> read-only */
          127  +  int wrFlag,             /* True -> read/write access, false -> read-only */
   116    128     sqlite3_blob **ppBlob   /* Handle for accessing the blob returned here */
   117    129   ){
   118    130     int nAttempt = 0;
   119    131     int iCol;               /* Index of zColumn in row-record */
   120    132     int rc = SQLITE_OK;
   121    133     char *zErr = 0;
   122    134     Table *pTab;
................................................................................
   130    142   #endif
   131    143     *ppBlob = 0;
   132    144   #ifdef SQLITE_ENABLE_API_ARMOR
   133    145     if( !sqlite3SafetyCheckOk(db) || zTable==0 ){
   134    146       return SQLITE_MISUSE_BKPT;
   135    147     }
   136    148   #endif
   137         -  flags = !!flags;                /* flags = (flags ? 1 : 0); */
          149  +  wrFlag = !!wrFlag;                /* wrFlag = (wrFlag ? 1 : 0); */
   138    150   
   139    151     sqlite3_mutex_enter(db->mutex);
   140    152   
   141    153     pBlob = (Incrblob *)sqlite3DbMallocZero(db, sizeof(Incrblob));
   142    154     if( !pBlob ) goto blob_open_out;
   143    155     pParse = sqlite3StackAllocRaw(db, sizeof(*pParse));
   144    156     if( !pParse ) goto blob_open_out;
................................................................................
   190    202         rc = SQLITE_ERROR;
   191    203         sqlite3BtreeLeaveAll(db);
   192    204         goto blob_open_out;
   193    205       }
   194    206   
   195    207       /* If the value is being opened for writing, check that the
   196    208       ** column is not indexed, and that it is not part of a foreign key. 
   197         -    ** It is against the rules to open a column to which either of these
   198         -    ** descriptions applies for writing.  */
   199         -    if( flags ){
          209  +    */
          210  +    if( wrFlag ){
   200    211         const char *zFault = 0;
   201    212         Index *pIdx;
   202    213   #ifndef SQLITE_OMIT_FOREIGN_KEY
   203    214         if( db->flags&SQLITE_ForeignKeys ){
   204    215           /* Check that the column is not part of an FK child key definition. It
   205    216           ** is not necessary to check if it is part of a parent key, as parent
   206    217           ** key columns must be indexed. The check below will pick up this 
................................................................................
   253    264         ** which closes the b-tree cursor and (possibly) commits the 
   254    265         ** transaction.
   255    266         */
   256    267         static const int iLn = VDBE_OFFSET_LINENO(2);
   257    268         static const VdbeOpList openBlob[] = {
   258    269           {OP_TableLock,      0, 0, 0},  /* 0: Acquire a read or write lock */
   259    270           {OP_OpenRead,       0, 0, 0},  /* 1: Open a cursor */
   260         -        {OP_Variable,       1, 1, 0},  /* 2: Move ?1 into reg[1] */
   261         -        {OP_NotExists,      0, 7, 1},  /* 3: Seek the cursor */
   262         -        {OP_Column,         0, 0, 1},  /* 4  */
   263         -        {OP_ResultRow,      1, 0, 0},  /* 5  */
   264         -        {OP_Goto,           0, 2, 0},  /* 6  */
   265         -        {OP_Halt,           0, 0, 0},  /* 7  */
          271  +        /* blobSeekToRow() will initialize r[1] to the desired rowid */
          272  +        {OP_NotExists,      0, 5, 1},  /* 2: Seek the cursor to rowid=r[1] */
          273  +        {OP_Column,         0, 0, 1},  /* 3  */
          274  +        {OP_ResultRow,      1, 0, 0},  /* 4  */
          275  +        {OP_Halt,           0, 0, 0},  /* 5  */
   266    276         };
   267    277         Vdbe *v = (Vdbe *)pBlob->pStmt;
   268    278         int iDb = sqlite3SchemaToIndex(db, pTab->pSchema);
   269    279         VdbeOp *aOp;
   270    280   
   271         -      sqlite3VdbeAddOp4Int(v, OP_Transaction, iDb, flags, 
          281  +      sqlite3VdbeAddOp4Int(v, OP_Transaction, iDb, wrFlag, 
   272    282                              pTab->pSchema->schema_cookie,
   273    283                              pTab->pSchema->iGeneration);
   274    284         sqlite3VdbeChangeP5(v, 1);     
   275    285         aOp = sqlite3VdbeAddOpList(v, ArraySize(openBlob), openBlob, iLn);
   276    286   
   277    287         /* Make sure a mutex is held on the table to be accessed */
   278    288         sqlite3VdbeUsesBtree(v, iDb); 
................................................................................
   281    291           assert( aOp!=0 );
   282    292           /* Configure the OP_TableLock instruction */
   283    293   #ifdef SQLITE_OMIT_SHARED_CACHE
   284    294           aOp[0].opcode = OP_Noop;
   285    295   #else
   286    296           aOp[0].p1 = iDb;
   287    297           aOp[0].p2 = pTab->tnum;
   288         -        aOp[0].p3 = flags;
          298  +        aOp[0].p3 = wrFlag;
   289    299           sqlite3VdbeChangeP4(v, 1, pTab->zName, P4_TRANSIENT);
   290    300         }
   291    301         if( db->mallocFailed==0 ){
   292    302   #endif
   293    303   
   294    304           /* Remove either the OP_OpenWrite or OpenRead. Set the P2 
   295    305           ** parameter of the other to pTab->tnum.  */
   296         -        if( flags ) aOp[1].opcode = OP_OpenWrite;
          306  +        if( wrFlag ) aOp[1].opcode = OP_OpenWrite;
   297    307           aOp[1].p2 = pTab->tnum;
   298    308           aOp[1].p3 = iDb;   
   299    309   
   300    310           /* Configure the number of columns. Configure the cursor to
   301    311           ** think that the table has one more column than it really
   302    312           ** does. An OP_Column to retrieve this imaginary column will
   303    313           ** always return an SQL NULL. This is useful because it means
   304    314           ** we can invoke OP_Column to fill in the vdbe cursors type 
   305    315           ** and offset cache without causing any IO.
   306    316           */
   307    317           aOp[1].p4type = P4_INT32;
   308    318           aOp[1].p4.i = pTab->nCol+1;
   309         -        aOp[4].p2 = pTab->nCol;
          319  +        aOp[3].p2 = pTab->nCol;
   310    320   
   311         -        pParse->nVar = 1;
          321  +        pParse->nVar = 0;
   312    322           pParse->nMem = 1;
   313    323           pParse->nTab = 1;
   314    324           sqlite3VdbeMakeReady(v, pParse);
   315    325         }
   316    326       }
   317    327      
   318         -    pBlob->flags = flags;
   319    328       pBlob->iCol = iCol;
   320    329       pBlob->db = db;
   321    330       sqlite3BtreeLeaveAll(db);
   322    331       if( db->mallocFailed ){
   323    332         goto blob_open_out;
   324    333       }
   325         -    sqlite3_bind_int64(pBlob->pStmt, 1, iRow);
   326    334       rc = blobSeekToRow(pBlob, iRow, &zErr);
   327    335     } while( (++nAttempt)<SQLITE_MAX_SCHEMA_RETRY && rc==SQLITE_SCHEMA );
   328    336   
   329    337   blob_open_out:
   330    338     if( rc==SQLITE_OK && db->mallocFailed==0 ){
   331    339       *ppBlob = (sqlite3_blob *)pBlob;
   332    340     }else{

Changes to src/where.c.

  4945   4945               assert( x>=0 );
  4946   4946             }
  4947   4947             x = sqlite3ColumnOfIndex(pIdx, x);
  4948   4948             if( x>=0 ){
  4949   4949               pOp->p2 = x;
  4950   4950               pOp->p1 = pLevel->iIdxCur;
  4951   4951             }
  4952         -          assert( (pLoop->wsFlags & WHERE_IDX_ONLY)==0 || x>=0 );
         4952  +          assert( (pLoop->wsFlags & WHERE_IDX_ONLY)==0 || x>=0 
         4953  +              || pWInfo->eOnePass );
  4953   4954           }else if( pOp->opcode==OP_Rowid ){
  4954   4955             pOp->p1 = pLevel->iIdxCur;
  4955   4956             pOp->opcode = OP_IdxRowid;
  4956   4957           }
  4957   4958         }
  4958   4959       }
  4959   4960     }

Changes to src/whereexpr.c.

   909    909     Expr *pStr1 = 0;                 /* RHS of LIKE/GLOB operator */
   910    910     int isComplete = 0;              /* RHS of LIKE/GLOB ends with wildcard */
   911    911     int noCase = 0;                  /* uppercase equivalent to lowercase */
   912    912     int op;                          /* Top-level operator.  pExpr->op */
   913    913     Parse *pParse = pWInfo->pParse;  /* Parsing context */
   914    914     sqlite3 *db = pParse->db;        /* Database connection */
   915    915     unsigned char eOp2;              /* op2 value for LIKE/REGEXP/GLOB */
          916  +  int nLeft;                       /* Number of elements on left side vector */
   916    917   
   917    918     if( db->mallocFailed ){
   918    919       return;
   919    920     }
   920    921     pTerm = &pWC->a[idxTerm];
   921    922     pMaskSet = &pWInfo->sMaskSet;
   922    923     pExpr = pTerm->pExpr;
................................................................................
   938    939     }
   939    940     prereqAll = sqlite3WhereExprUsage(pMaskSet, pExpr);
   940    941     if( ExprHasProperty(pExpr, EP_FromJoin) ){
   941    942       Bitmask x = sqlite3WhereGetMask(pMaskSet, pExpr->iRightJoinTable);
   942    943       prereqAll |= x;
   943    944       extraRight = x-1;  /* ON clause terms may not be used with an index
   944    945                          ** on left table of a LEFT JOIN.  Ticket #3015 */
          946  +    if( (prereqAll>>1)>=x ){
          947  +      sqlite3ErrorMsg(pParse, "ON clause references tables to its right");
          948  +      return;
          949  +    }
   945    950     }
   946    951     pTerm->prereqAll = prereqAll;
   947    952     pTerm->leftCursor = -1;
   948    953     pTerm->iParent = -1;
   949    954     pTerm->eOperator = 0;
   950    955     if( allowedOp(op) ){
   951    956       int iCur, iColumn;
................................................................................
  1180   1185     ** new terms completely replace the original vector comparison, which is
  1181   1186     ** no longer used.
  1182   1187     **
  1183   1188     ** This is only required if at least one side of the comparison operation
  1184   1189     ** is not a sub-select.  */
  1185   1190     if( pWC->op==TK_AND 
  1186   1191     && (pExpr->op==TK_EQ || pExpr->op==TK_IS)
  1187         -  && sqlite3ExprIsVector(pExpr->pLeft)
         1192  +  && (nLeft = sqlite3ExprVectorSize(pExpr->pLeft))>1
         1193  +  && sqlite3ExprVectorSize(pExpr->pRight)==nLeft
  1188   1194     && ( (pExpr->pLeft->flags & EP_xIsSelect)==0 
  1189         -    || (pExpr->pRight->flags & EP_xIsSelect)==0
  1190         -  )){
  1191         -    int nLeft = sqlite3ExprVectorSize(pExpr->pLeft);
         1195  +    || (pExpr->pRight->flags & EP_xIsSelect)==0)
         1196  +  ){
  1192   1197       int i;
  1193         -    assert( nLeft==sqlite3ExprVectorSize(pExpr->pRight) );
  1194   1198       for(i=0; i<nLeft; i++){
  1195   1199         int idxNew;
  1196   1200         Expr *pNew;
  1197   1201         Expr *pLeft = sqlite3ExprForVectorField(pParse, pExpr->pLeft, i);
  1198   1202         Expr *pRight = sqlite3ExprForVectorField(pParse, pExpr->pRight, i);
  1199   1203   
  1200   1204         pNew = sqlite3PExpr(pParse, pExpr->op, pLeft, pRight);

Added test/affinity3.test.

            1  +# 2017-01-16
            2  +#
            3  +# The author disclaims copyright to this source code.  In place of
            4  +# a legal notice, here is a blessing:
            5  +#
            6  +#    May you do good and not evil.
            7  +#    May you find forgiveness for yourself and forgive others.
            8  +#    May you share freely, never taking more than you give.
            9  +#
           10  +#***********************************************************************
           11  +#
           12  +# Test cases for bugs:
           13  +#
           14  +#    https://www.sqlite.org/src/info/91e2e8ba6ff2e2
           15  +#    https://www.sqlite.org/src/info/7ffd1ca1d2ad4ecf
           16  +#
           17  +
           18  +set testdir [file dirname $argv0]
           19  +source $testdir/tester.tcl
           20  +
           21  +# Ticket https://www.sqlite.org/src/info/91e2e8ba6ff2e2 (2011-09-19)
           22  +# Automatic index causes undesired type conversions
           23  +#
           24  +do_execsql_test affinity3-100 {
           25  +  CREATE TABLE customer (id INT PRIMARY KEY);
           26  +  CREATE TABLE apr (id INT PRIMARY KEY, apr REAL);
           27  +  
           28  +  CREATE VIEW v1 AS
           29  +  SELECT c.id, i.apr
           30  +  FROM customer c
           31  +  LEFT JOIN apr i ON i.id=c.id;
           32  +  
           33  +  CREATE VIEW v2 AS
           34  +  SELECT c.id, v1.apr
           35  +  FROM customer c
           36  +  LEFT JOIN v1 ON v1.id=c.id;
           37  +  
           38  +  INSERT INTO customer (id) VALUES (1);
           39  +  INSERT INTO apr (id, apr) VALUES (1, 12);
           40  +  INSERT INTO customer (id) VALUES (2);
           41  +  INSERT INTO apr (id, apr) VALUES (2, 12.01);
           42  +}
           43  +do_execsql_test affinity3-110 {
           44  +  PRAGMA automatic_index=ON;
           45  +  SELECT id, (apr / 100), typeof(apr) apr_type  FROM v1;
           46  +} {1 0.12 real 2 0.1201 real}
           47  +do_execsql_test affinity3-120 {
           48  +  SELECT id, (apr / 100), typeof(apr) apr_type  FROM v2;
           49  +} {1 0.12 real 2 0.1201 real}
           50  +do_execsql_test affinity3-130 {
           51  +  PRAGMA automatic_index=OFF;
           52  +  SELECT id, (apr / 100), typeof(apr) apr_type  FROM v1;
           53  +} {1 0.12 real 2 0.1201 real}
           54  +do_execsql_test affinity3-140 {
           55  +  SELECT id, (apr / 100), typeof(apr) apr_type  FROM v2;
           56  +} {1 0.12 real 2 0.1201 real}
           57  +
           58  +# Ticket https://www.sqlite.org/src/info/7ffd1ca1d2ad4ecf  (2017-01-16)
           59  +# Incorrect affinity when using automatic indexes 
           60  +#
           61  +do_execsql_test affinity3-200 {
           62  +  CREATE TABLE map_integer (id INT, name);
           63  +  INSERT INTO map_integer VALUES(1,'a');
           64  +  CREATE TABLE map_text (id TEXT, name);
           65  +  INSERT INTO map_text VALUES('4','e');
           66  +  CREATE TABLE data (id TEXT, name);
           67  +  INSERT INTO data VALUES(1,'abc');
           68  +  INSERT INTO data VALUES('4','xyz');
           69  +  CREATE VIEW idmap as
           70  +      SELECT * FROM map_integer
           71  +      UNION SELECT * FROM map_text;
           72  +  CREATE TABLE mzed AS SELECT * FROM idmap;
           73  +}
           74  +
           75  +do_execsql_test affinity3-210 {
           76  +  PRAGMA automatic_index=ON;
           77  +  SELECT * FROM data JOIN idmap USING(id);
           78  +} {1 abc a 4 xyz e}
           79  +do_execsql_test affinity3-220 {
           80  +  SELECT * FROM data JOIN mzed USING(id);
           81  +} {1 abc a 4 xyz e}
           82  +
           83  +do_execsql_test affinity3-250 {
           84  +  PRAGMA automatic_index=OFF;
           85  +  SELECT * FROM data JOIN idmap USING(id);
           86  +} {1 abc a 4 xyz e}
           87  +do_execsql_test affinity3-260 {
           88  +  SELECT * FROM data JOIN mzed USING(id);
           89  +} {1 abc a 4 xyz e}
           90  +
           91  +finish_test

Changes to test/cursorhint2.test.

    87     87   
    88     88   do_extract_hints_test 1.6 {
    89     89     SELECT * FROM t1 LEFT JOIN t2 ON (a=c) LEFT JOIN t3 ON (d=f);
    90     90   } {
    91     91     t2 {EQ(r[2],c0)} t3 {EQ(r[6],c1)}
    92     92   }
    93     93   
    94         -do_extract_hints_test 1.7 {
    95         -  SELECT * FROM t1 LEFT JOIN t2 ON (a=c AND d=e) LEFT JOIN t3 ON (d=f);
    96         -} {
    97         -  t2 {EQ(r[2],c0)} t3 {AND(EQ(r[6],c0),EQ(r[7],c1))}
           94  +if 0 {
           95  +  do_extract_hints_test 1.7 {
           96  +    SELECT * FROM t1 LEFT JOIN t2 ON (a=c AND d=e) LEFT JOIN t3 ON (d=f);
           97  +  } {
           98  +    t2 {EQ(r[2],c0)} t3 {AND(EQ(r[6],c0),EQ(r[7],c1))}
           99  +  }
    98    100   }
    99    101   
   100    102   #-------------------------------------------------------------------------
   101    103   #
   102    104   do_execsql_test 2.0 {
   103    105     CREATE TABLE x1(x, y);
   104    106     CREATE TABLE x2(a, b);

Changes to test/exclusive2.test.

   117    117   # allocation of 24 pages (shared between all pagers). This is not enough for
   118    118   # this test.
   119    119   #
   120    120   do_test exclusive2-1.1 {
   121    121     execsql {
   122    122       BEGIN;
   123    123       CREATE TABLE t1(a, b);
   124         -    INSERT INTO t1(a) VALUES(randstr(10, 400));
   125         -    INSERT INTO t1(a) VALUES(randstr(10, 400));
   126         -    INSERT INTO t1(a) SELECT randstr(10, 400) FROM t1;
   127         -    INSERT INTO t1(a) SELECT randstr(10, 400) FROM t1;
   128         -    INSERT INTO t1(a) SELECT randstr(10, 400) FROM t1;
   129         -    INSERT INTO t1(a) SELECT randstr(10, 400) FROM t1;
   130         -    INSERT INTO t1(a) SELECT randstr(10, 400) FROM t1;
          124  +    INSERT INTO t1(a, b) VALUES(randstr(10, 400), 0);
          125  +    INSERT INTO t1(a, b) VALUES(randstr(10, 400), 0);
          126  +    INSERT INTO t1(a, b) SELECT randstr(10, 400), 0 FROM t1;
          127  +    INSERT INTO t1(a, b) SELECT randstr(10, 400), 0 FROM t1;
          128  +    INSERT INTO t1(a, b) SELECT randstr(10, 400), 0 FROM t1;
          129  +    INSERT INTO t1(a, b) SELECT randstr(10, 400), 0 FROM t1;
          130  +    INSERT INTO t1(a, b) SELECT randstr(10, 400), 0 FROM t1;
   131    131       COMMIT;
   132    132       SELECT count(*) FROM t1;
   133    133     }
   134    134   } {64}
   135    135   do_test exclusive2-1.2.1 {
   136    136     # Make sure the pager cache is large enough to store the 
   137    137     # entire database.
................................................................................
   150    150   } $::sig
   151    151   do_test exclusive2-1.4 {
   152    152     sqlite3 db2 test.db
   153    153     t1sig db2
   154    154   } $::sig
   155    155   do_test exclusive2-1.5 {
   156    156     execsql {
   157         -    UPDATE t1 SET b=a, a=NULL;
          157  +    UPDATE t1 SET b=a, a=0;
   158    158     } db2
   159    159     expr {[t1sig db2] eq $::sig}
   160    160   } 0
   161    161   do_test exclusive2-1.6 {
   162    162     readPagerChangeCounter test.db
   163    163   } {2}
   164    164   do_test exclusive2-1.7 {

Changes to test/hook.test.

   849    849   }
   850    850   
   851    851   # No preupdate callbacks for modifying sqlite_master.
   852    852   do_preupdate_test 8.1 {
   853    853     CREATE TABLE x1(x, y);
   854    854   } {
   855    855   }
          856  +
          857  +#-------------------------------------------------------------------------
          858  +reset_db
          859  +db preupdate hook preupdate_hook
          860  +do_execsql_test 9.0 {
          861  +  CREATE TABLE t1(a INTEGER PRIMARY KEY, b, c);
          862  +  CREATE TABLE t2(a, b INTEGER PRIMARY KEY);
          863  +}
          864  +do_preupdate_test 9.1 {
          865  +  INSERT INTO t1 VALUES(456, NULL, NULL);
          866  +} {
          867  +  INSERT main t1 456 456  0  456 {} {}
          868  +}
          869  +do_execsql_test 9.2 {
          870  +  ALTER TABLE t1 ADD COLUMN d;
          871  +}
          872  +do_preupdate_test 9.3 {
          873  +  INSERT INTO t1(a, b, c) VALUES(457, NULL, NULL);
          874  +} {
          875  +  INSERT main t1 457 457  0  457 {} {} {}
          876  +}
          877  +do_preupdate_test 9.4 {
          878  +  DELETE FROM t1 WHERE a=456
          879  +} {
          880  +  DELETE main t1 456 456  0  456 {} {} {}
          881  +}
          882  +do_preupdate_test 9.5 {
          883  +  INSERT INTO t2 DEFAULT VALUES;
          884  +} {
          885  +  INSERT main t2 1 1  0  {} 1
          886  +} 
          887  +do_preupdate_test 9.6 {
          888  +  INSERT INTO t1 DEFAULT VALUES;
          889  +} {
          890  +  INSERT main t1 458 458  0  458 {} {} {}
          891  +} 
          892  +
          893  +
          894  +do_execsql_test 10.0 {
          895  +  CREATE TABLE t3(a, b INTEGER PRIMARY KEY);
          896  +}
          897  +do_preupdate_test 10.1 {
          898  +  INSERT INTO t3 DEFAULT VALUES
          899  +} {
          900  +  INSERT main t3 1 1 0 {} 1
          901  +}
          902  +do_execsql_test 10.2 { SELECT * FROM t3 } {{} 1}
          903  +do_preupdate_test 10.3 {
          904  +  DELETE FROM t3 WHERE b=1
          905  +} {DELETE main t3 1 1 0 {} 1}
          906  +
   856    907   
   857    908   finish_test

Changes to test/join2.test.

     8      8   #    May you share freely, never taking more than you give.
     9      9   #
    10     10   #***********************************************************************
    11     11   # This file implements regression tests for SQLite library.
    12     12   #
    13     13   # This file implements tests for joins, including outer joins.
    14     14   #
    15         -# $Id: join2.test,v 1.2 2005/01/21 03:12:16 danielk1977 Exp $
    16     15   
    17     16   set testdir [file dirname $argv0]
    18     17   source $testdir/tester.tcl
           18  +set testprefix join2
    19     19   
    20     20   do_test join2-1.1 {
    21     21     execsql {
    22     22       CREATE TABLE t1(a,b);
    23     23       INSERT INTO t1 VALUES(1,11);
    24     24       INSERT INTO t1 VALUES(2,22);
    25     25       INSERT INTO t1 VALUES(3,33);
................................................................................
    67     67     do_test join2-1.7 {
    68     68       execsql {
    69     69         SELECT * FROM
    70     70           t1 NATURAL LEFT OUTER JOIN (t2 NATURAL JOIN t3)
    71     71       }
    72     72     } {1 11 111 1111 2 22 {} {} 3 33 {} {}}
    73     73   }
           74  +
           75  +#-------------------------------------------------------------------------
           76  +# Check that ticket [25e335f802ddc] has been resolved. It should be an
           77  +# error for the ON clause of a LEFT JOIN to refer to a table to its right.
           78  +#
           79  +do_execsql_test 2.0 {
           80  +  CREATE TABLE aa(a);
           81  +  CREATE TABLE bb(b);
           82  +  CREATE TABLE cc(c);
           83  +  INSERT INTO aa VALUES('one');
           84  +  INSERT INTO bb VALUES('one');
           85  +  INSERT INTO cc VALUES('one');
           86  +}
           87  +
           88  +do_catchsql_test 2.1 {
           89  +  SELECT * FROM aa LEFT JOIN cc ON (a=b) JOIN bb ON (b=c);
           90  +} {1 {ON clause references tables to its right}}
           91  +do_catchsql_test 2.2 {
           92  +  SELECT * FROM aa JOIN cc ON (a=b) JOIN bb ON (b=c);
           93  +} {0 {one one one}}
    74     94   
    75     95   finish_test

Changes to test/kvtest.c.

    57     57   **       ./kvtest init x1.db --count 100000 --size 10000
    58     58   **       mkdir x1
    59     59   **       ./kvtest export x1.db x1
    60     60   **       ./kvtest run x1.db --count 10000 --max-id 1000000
    61     61   **       ./kvtest run x1 --count 10000 --max-id 1000000
    62     62   */
    63     63   static const char zHelp[] = 
    64         -"Usage: kvhelp COMMAND ARGS...\n"
           64  +"Usage: kvtest COMMAND ARGS...\n"
    65     65   "\n"
    66         -"   kvhelp init DBFILE --count N --size M --pagesize X\n"
           66  +"   kvtest init DBFILE --count N --size M --pagesize X\n"
    67     67   "\n"
    68     68   "        Generate a new test database file named DBFILE containing N\n"
    69     69   "        BLOBs each of size M bytes.  The page size of the new database\n"
    70     70   "        file will be X\n"
    71     71   "\n"
    72         -"   kvhelp export DBFILE DIRECTORY\n"
           72  +"   kvtest export DBFILE DIRECTORY\n"
    73     73   "\n"
    74     74   "        Export all the blobs in the kv table of DBFILE into separate\n"
    75     75   "        files in DIRECTORY.\n"
    76     76   "\n"
    77         -"   kvhelp run DBFILE [options]\n"
           77  +"   kvtest run DBFILE [options]\n"
    78     78   "\n"
    79     79   "        Run a performance test.  DBFILE can be either the name of a\n"
    80     80   "        database or a directory containing sample files.  Options:\n"
    81     81   "\n"
    82         -"             --asc                Read blobs in ascending order\n"
    83         -"             --blob-api           Use the BLOB API\n"
    84         -"             --cache-size N       Database cache size\n"
    85         -"             --count N            Read N blobs\n"
    86         -"             --desc               Read blobs in descending order\n"
    87         -"             --max-id N           Maximum blob key to use\n"
    88         -"             --random             Read blobs in a random order\n"
    89         -"             --start N            Start reading with this blob key\n"
           82  +"           --asc                  Read blobs in ascending order\n"
           83  +"           --blob-api             Use the BLOB API\n"
           84  +"           --cache-size N         Database cache size\n"
           85  +"           --count N              Read N blobs\n"
           86  +"           --desc                 Read blobs in descending order\n"
           87  +"           --max-id N             Maximum blob key to use\n"
           88  +"           --mmap N               Mmap as much as N bytes of DBFILE\n"
           89  +"           --jmode MODE           Set MODE journal mode prior to starting\n"
           90  +"           --random               Read blobs in a random order\n"
           91  +"           --start N              Start reading with this blob key\n"
           92  +"           --stats                Output operating stats before exiting\n"
    90     93   ;
    91     94   
    92     95   /* Reference resources used */
    93     96   #include <stdio.h>
    94     97   #include <stdlib.h>
    95     98   #include <sys/types.h>
    96     99   #include <sys/stat.h>
................................................................................
   126    129     fprintf(stdout, "ERROR: ");
   127    130     va_start(ap, zFormat);
   128    131     vfprintf(stdout, zFormat, ap);
   129    132     va_end(ap);
   130    133     fprintf(stdout, "\n");
   131    134     exit(1);
   132    135   }
          136  +
          137  +/*
          138  +** Return the value of a hexadecimal digit.  Return -1 if the input
          139  +** is not a hex digit.
          140  +*/
          141  +static int hexDigitValue(char c){
          142  +  if( c>='0' && c<='9' ) return c - '0';
          143  +  if( c>='a' && c<='f' ) return c - 'a' + 10;
          144  +  if( c>='A' && c<='F' ) return c - 'A' + 10;
          145  +  return -1;
          146  +}
          147  +
          148  +/*
          149  +** Interpret zArg as an integer value, possibly with suffixes.
          150  +*/
          151  +static int integerValue(const char *zArg){
          152  +  int v = 0;
          153  +  static const struct { char *zSuffix; int iMult; } aMult[] = {
          154  +    { "KiB", 1024 },
          155  +    { "MiB", 1024*1024 },
          156  +    { "GiB", 1024*1024*1024 },
          157  +    { "KB",  1000 },
          158  +    { "MB",  1000000 },
          159  +    { "GB",  1000000000 },
          160  +    { "K",   1000 },
          161  +    { "M",   1000000 },
          162  +    { "G",   1000000000 },
          163  +  };
          164  +  int i;
          165  +  int isNeg = 0;
          166  +  if( zArg[0]=='-' ){
          167  +    isNeg = 1;
          168  +    zArg++;
          169  +  }else if( zArg[0]=='+' ){
          170  +    zArg++;
          171  +  }
          172  +  if( zArg[0]=='0' && zArg[1]=='x' ){
          173  +    int x;
          174  +    zArg += 2;
          175  +    while( (x = hexDigitValue(zArg[0]))>=0 ){
          176  +      v = (v<<4) + x;
          177  +      zArg++;
          178  +    }
          179  +  }else{
          180  +    while( zArg[0]>='0' && zArg[0]<='9' ){
          181  +      v = v*10 + zArg[0] - '0';
          182  +      zArg++;
          183  +    }
          184  +  }
          185  +  for(i=0; i<sizeof(aMult)/sizeof(aMult[0]); i++){
          186  +    if( sqlite3_stricmp(aMult[i].zSuffix, zArg)==0 ){
          187  +      v *= aMult[i].iMult;
          188  +      break;
          189  +    }
          190  +  }
          191  +  return isNeg? -v : v;
          192  +}
          193  +
   133    194   
   134    195   /*
   135    196   ** Check the filesystem object zPath.  Determine what it is:
   136    197   **
   137    198   **    PATH_DIR     A directory
   138    199   **    PATH_DB      An SQLite database
   139    200   **    PATH_NEXIST  Does not exist
................................................................................
   200    261     zDb = argv[2];
   201    262     for(i=3; i<argc; i++){
   202    263       char *z = argv[i];
   203    264       if( z[0]!='-' ) fatalError("unknown argument: \"%s\"", z);
   204    265       if( z[1]=='-' ) z++;
   205    266       if( strcmp(z, "-count")==0 ){
   206    267         if( i==argc-1 ) fatalError("missing argument on \"%s\"", argv[i]);
   207         -      nCount = atoi(argv[++i]);
          268  +      nCount = integerValue(argv[++i]);
   208    269         if( nCount<1 ) fatalError("the --count must be positive");
   209    270         continue;
   210    271       }
   211    272       if( strcmp(z, "-size")==0 ){
   212    273         if( i==argc-1 ) fatalError("missing argument on \"%s\"", argv[i]);
   213         -      sz = atoi(argv[++i]);
          274  +      sz = integerValue(argv[++i]);
   214    275         if( sz<1 ) fatalError("the --size must be positive");
   215    276         continue;
   216    277       }
   217    278       if( strcmp(z, "-pagesize")==0 ){
   218    279         if( i==argc-1 ) fatalError("missing argument on \"%s\"", argv[i]);
   219         -      pgsz = atoi(argv[++i]);
          280  +      pgsz = integerValue(argv[++i]);
   220    281         if( pgsz<512 || pgsz>65536 || ((pgsz-1)&pgsz)!=0 ){
   221    282           fatalError("the --pagesize must be power of 2 between 512 and 65536");
   222    283         }
   223    284         continue;
   224    285       }
   225    286       fatalError("unknown option: \"%s\"", argv[i]);
   226    287     }
................................................................................
   364    425     }else{
   365    426       double r;
   366    427       clockVfs->xCurrentTime(clockVfs, &r);
   367    428       t = (sqlite3_int64)(r*86400000.0);
   368    429     }
   369    430     return t;
   370    431   }
          432  +
          433  +#ifdef __linux__
          434  +/*
          435  +** Attempt to display I/O stats on Linux using /proc/PID/io
          436  +*/
          437  +static void displayLinuxIoStats(FILE *out){
          438  +  FILE *in;
          439  +  char z[200];
          440  +  sqlite3_snprintf(sizeof(z), z, "/proc/%d/io", getpid());
          441  +  in = fopen(z, "rb");
          442  +  if( in==0 ) return;
          443  +  while( fgets(z, sizeof(z), in)!=0 ){
          444  +    static const struct {
          445  +      const char *zPattern;
          446  +      const char *zDesc;
          447  +    } aTrans[] = {
          448  +      { "rchar: ",                  "Bytes received by read():" },
          449  +      { "wchar: ",                  "Bytes sent to write():"    },
          450  +      { "syscr: ",                  "Read() system calls:"      },
          451  +      { "syscw: ",                  "Write() system calls:"     },
          452  +      { "read_bytes: ",             "Bytes read from storage:"  },
          453  +      { "write_bytes: ",            "Bytes written to storage:" },
          454  +      { "cancelled_write_bytes: ",  "Cancelled write bytes:"    },
          455  +    };
          456  +    int i;
          457  +    for(i=0; i<sizeof(aTrans)/sizeof(aTrans[0]); i++){
          458  +      int n = (int)strlen(aTrans[i].zPattern);
          459  +      if( strncmp(aTrans[i].zPattern, z, n)==0 ){
          460  +        fprintf(out, "%-36s %s", aTrans[i].zDesc, &z[n]);
          461  +        break;
          462  +      }
          463  +    }
          464  +  }
          465  +  fclose(in);
          466  +}
          467  +#endif
          468  +
          469  +/*
          470  +** Display memory stats.
          471  +*/
          472  +static int display_stats(
          473  +  sqlite3 *db,                    /* Database to query */
          474  +  int bReset                      /* True to reset SQLite stats */
          475  +){
          476  +  int iCur;
          477  +  int iHiwtr;
          478  +  FILE *out = stdout;
          479  +
          480  +  fprintf(out, "\n");
          481  +
          482  +  iHiwtr = iCur = -1;
          483  +  sqlite3_status(SQLITE_STATUS_MEMORY_USED, &iCur, &iHiwtr, bReset);
          484  +  fprintf(out,
          485  +          "Memory Used:                         %d (max %d) bytes\n",
          486  +          iCur, iHiwtr);
          487  +  iHiwtr = iCur = -1;
          488  +  sqlite3_status(SQLITE_STATUS_MALLOC_COUNT, &iCur, &iHiwtr, bReset);
          489  +  fprintf(out, "Number of Outstanding Allocations:   %d (max %d)\n",
          490  +          iCur, iHiwtr);
          491  +  iHiwtr = iCur = -1;
          492  +  sqlite3_status(SQLITE_STATUS_PAGECACHE_USED, &iCur, &iHiwtr, bReset);
          493  +  fprintf(out,
          494  +      "Number of Pcache Pages Used:         %d (max %d) pages\n",
          495  +      iCur, iHiwtr);
          496  +  iHiwtr = iCur = -1;
          497  +  sqlite3_status(SQLITE_STATUS_PAGECACHE_OVERFLOW, &iCur, &iHiwtr, bReset);
          498  +  fprintf(out,
          499  +          "Number of Pcache Overflow Bytes:     %d (max %d) bytes\n",
          500  +          iCur, iHiwtr);
          501  +  iHiwtr = iCur = -1;
          502  +  sqlite3_status(SQLITE_STATUS_SCRATCH_USED, &iCur, &iHiwtr, bReset);
          503  +  fprintf(out,
          504  +      "Number of Scratch Allocations Used:  %d (max %d)\n",
          505  +      iCur, iHiwtr);
          506  +  iHiwtr = iCur = -1;
          507  +  sqlite3_status(SQLITE_STATUS_SCRATCH_OVERFLOW, &iCur, &iHiwtr, bReset);
          508  +  fprintf(out,
          509  +          "Number of Scratch Overflow Bytes:    %d (max %d) bytes\n",
          510  +          iCur, iHiwtr);
          511  +  iHiwtr = iCur = -1;
          512  +  sqlite3_status(SQLITE_STATUS_MALLOC_SIZE, &iCur, &iHiwtr, bReset);
          513  +  fprintf(out, "Largest Allocation:                  %d bytes\n",
          514  +          iHiwtr);
          515  +  iHiwtr = iCur = -1;
          516  +  sqlite3_status(SQLITE_STATUS_PAGECACHE_SIZE, &iCur, &iHiwtr, bReset);
          517  +  fprintf(out, "Largest Pcache Allocation:           %d bytes\n",
          518  +          iHiwtr);
          519  +  iHiwtr = iCur = -1;
          520  +  sqlite3_status(SQLITE_STATUS_SCRATCH_SIZE, &iCur, &iHiwtr, bReset);
          521  +  fprintf(out, "Largest Scratch Allocation:          %d bytes\n",
          522  +          iHiwtr);
          523  +
          524  +  iHiwtr = iCur = -1;
          525  +  sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_USED, &iCur, &iHiwtr, bReset);
          526  +  fprintf(out, "Pager Heap Usage:                    %d bytes\n",
          527  +      iCur);
          528  +  iHiwtr = iCur = -1;
          529  +  sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_HIT, &iCur, &iHiwtr, 1);
          530  +  fprintf(out, "Page cache hits:                     %d\n", iCur);
          531  +  iHiwtr = iCur = -1;
          532  +  sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_MISS, &iCur, &iHiwtr, 1);
          533  +  fprintf(out, "Page cache misses:                   %d\n", iCur);
          534  +  iHiwtr = iCur = -1;
          535  +  sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_WRITE, &iCur, &iHiwtr, 1);
          536  +  fprintf(out, "Page cache writes:                   %d\n", iCur);
          537  +  iHiwtr = iCur = -1;
          538  +
          539  +#ifdef __linux__
          540  +  displayLinuxIoStats(out);
          541  +#endif
          542  +
          543  +  return 0;
          544  +}
   371    545   
   372    546   /* Blob access order */
   373    547   #define ORDER_ASC     1
   374    548   #define ORDER_DESC    2
   375    549   #define ORDER_RANDOM  3
          550  +
   376    551   
   377    552   /*
   378    553   ** Run a performance test
   379    554   */
   380    555   static int runMain(int argc, char **argv){
   381    556     int eType;                  /* Is zDb a database or a directory? */
   382    557     char *zDb;                  /* Database or directory name */
   383    558     int i;                      /* Loop counter */
   384    559     int rc;                     /* Return code from SQLite calls */
   385    560     int nCount = 1000;          /* Number of blob fetch operations */
   386    561     int nExtra = 0;             /* Extra cycles */
   387    562     int iKey = 1;               /* Next blob key */
   388         -  int iMax = 1000;            /* Largest allowed key */
          563  +  int iMax = 0;               /* Largest allowed key */
   389    564     int iPagesize = 0;          /* Database page size */
   390    565     int iCache = 1000;          /* Database cache size in kibibytes */
   391    566     int bBlobApi = 0;           /* Use the incremental blob I/O API */
          567  +  int bStats = 0;             /* Print stats before exiting */
   392    568     int eOrder = ORDER_ASC;     /* Access order */
   393    569     sqlite3 *db = 0;            /* Database connection */
   394    570     sqlite3_stmt *pStmt = 0;    /* Prepared statement for SQL access */
   395    571     sqlite3_blob *pBlob = 0;    /* Handle for incremental Blob I/O */
   396    572     sqlite3_int64 tmStart;      /* Start time */
   397    573     sqlite3_int64 tmElapsed;    /* Elapsed time */
          574  +  int mmapSize = 0;           /* --mmap N argument */
   398    575     int nData = 0;              /* Bytes of data */
   399    576     sqlite3_int64 nTotal = 0;   /* Total data read */
   400         -  unsigned char *pData;       /* Content of the blob */
          577  +  unsigned char *pData = 0;   /* Content of the blob */
          578  +  int nAlloc = 0;             /* Space allocated for pData[] */
          579  +  const char *zJMode = 0;     /* Journal mode */
   401    580     
   402    581   
   403    582     assert( strcmp(argv[1],"run")==0 );
   404    583     assert( argc>=3 );
   405    584     zDb = argv[2];
   406    585     eType = pathType(zDb);
   407    586     if( eType==PATH_OTHER ) fatalError("unknown object type: \"%s\"", zDb);
................................................................................
   408    587     if( eType==PATH_NEXIST ) fatalError("object does not exist: \"%s\"", zDb);
   409    588     for(i=3; i<argc; i++){
   410    589       char *z = argv[i];
   411    590       if( z[0]!='-' ) fatalError("unknown argument: \"%s\"", z);
   412    591       if( z[1]=='-' ) z++;
   413    592       if( strcmp(z, "-count")==0 ){
   414    593         if( i==argc-1 ) fatalError("missing argument on \"%s\"", argv[i]);
   415         -      nCount = atoi(argv[++i]);
          594  +      nCount = integerValue(argv[++i]);
   416    595         if( nCount<1 ) fatalError("the --count must be positive");
   417    596         continue;
          597  +    }
          598  +    if( strcmp(z, "-mmap")==0 ){
          599  +      if( i==argc-1 ) fatalError("missing argument on \"%s\"", argv[i]);
          600  +      mmapSize = integerValue(argv[++i]);
          601  +      if( nCount<0 ) fatalError("the --mmap must be non-negative");
          602  +      continue;
   418    603       }
   419    604       if( strcmp(z, "-max-id")==0 ){
   420    605         if( i==argc-1 ) fatalError("missing argument on \"%s\"", argv[i]);
   421         -      iMax = atoi(argv[++i]);
   422         -      if( iMax<1 ) fatalError("the --max-id must be positive");
          606  +      iMax = integerValue(argv[++i]);
   423    607         continue;
   424    608       }
   425    609       if( strcmp(z, "-start")==0 ){
   426    610         if( i==argc-1 ) fatalError("missing argument on \"%s\"", argv[i]);
   427         -      iKey = atoi(argv[++i]);
          611  +      iKey = integerValue(argv[++i]);
   428    612         if( iKey<1 ) fatalError("the --start must be positive");
   429    613         continue;
   430    614       }
   431    615       if( strcmp(z, "-cache-size")==0 ){
   432    616         if( i==argc-1 ) fatalError("missing argument on \"%s\"", argv[i]);
   433         -      iCache = atoi(argv[++i]);
          617  +      iCache = integerValue(argv[++i]);
          618  +      continue;
          619  +    }
          620  +    if( strcmp(z, "-jmode")==0 ){
          621  +      if( i==argc-1 ) fatalError("missing argument on \"%s\"", argv[i]);
          622  +      zJMode = argv[++i];
   434    623         continue;
   435    624       }
   436    625       if( strcmp(z, "-random")==0 ){
   437    626         eOrder = ORDER_RANDOM;
   438    627         continue;
   439    628       }
   440    629       if( strcmp(z, "-asc")==0 ){
................................................................................
   444    633       if( strcmp(z, "-desc")==0 ){
   445    634         eOrder = ORDER_DESC;
   446    635         continue;
   447    636       }
   448    637       if( strcmp(z, "-blob-api")==0 ){
   449    638         bBlobApi = 1;
   450    639         continue;
          640  +    }
          641  +    if( strcmp(z, "-stats")==0 ){
          642  +      bStats = 1;
          643  +      continue;
   451    644       }
   452    645       fatalError("unknown option: \"%s\"", argv[i]);
   453    646     }
   454    647     tmStart = timeOfDay();
   455    648     if( eType==PATH_DB ){
   456    649       char *zSql;
   457    650       rc = sqlite3_open(zDb, &db);
   458    651       if( rc ){
   459    652         fatalError("cannot open database \"%s\": %s", zDb, sqlite3_errmsg(db));
   460    653       }
          654  +    zSql = sqlite3_mprintf("PRAGMA mmap_size=%d", mmapSize);
          655  +    sqlite3_exec(db, zSql, 0, 0, 0);
   461    656       zSql = sqlite3_mprintf("PRAGMA cache_size=%d", iCache);
   462    657       sqlite3_exec(db, zSql, 0, 0, 0);
   463    658       sqlite3_free(zSql);
   464    659       pStmt = 0;
   465    660       sqlite3_prepare_v2(db, "PRAGMA page_size", -1, &pStmt, 0);
   466    661       if( sqlite3_step(pStmt)==SQLITE_ROW ){
   467    662         iPagesize = sqlite3_column_int(pStmt, 0);
................................................................................
   470    665       sqlite3_prepare_v2(db, "PRAGMA cache_size", -1, &pStmt, 0);
   471    666       if( sqlite3_step(pStmt)==SQLITE_ROW ){
   472    667         iCache = sqlite3_column_int(pStmt, 0);
   473    668       }else{
   474    669         iCache = 0;
   475    670       }
   476    671       sqlite3_finalize(pStmt);
          672  +    pStmt = 0;
          673  +    if( zJMode ){
          674  +      zSql = sqlite3_mprintf("PRAGMA journal_mode=%Q", zJMode);
          675  +      sqlite3_exec(db, zSql, 0, 0, 0);
          676  +      sqlite3_free(zSql);
          677  +    }
          678  +    sqlite3_prepare_v2(db, "PRAGMA journal_mode", -1, &pStmt, 0);
          679  +    if( sqlite3_step(pStmt)==SQLITE_ROW ){
          680  +      zJMode = sqlite3_mprintf("%s", sqlite3_column_text(pStmt, 0));
          681  +    }else{
          682  +      zJMode = "???";
          683  +    }
          684  +    sqlite3_finalize(pStmt);
          685  +    if( iMax<=0 ){
          686  +      sqlite3_prepare_v2(db, "SELECT max(k) FROM kv", -1, &pStmt, 0);
          687  +      if( sqlite3_step(pStmt)==SQLITE_ROW ){
          688  +        iMax = sqlite3_column_int(pStmt, 0);
          689  +      }
          690  +      sqlite3_finalize(pStmt);
          691  +    }
   477    692       pStmt = 0;
   478    693       sqlite3_exec(db, "BEGIN", 0, 0, 0);
   479    694     }
          695  +  if( iMax<=0 ) iMax = 1000;
   480    696     for(i=0; i<nCount; i++){
   481    697       if( eType==PATH_DIR ){
   482    698         /* CASE 1: Reading blobs out of separate files */
   483    699         char *zKey;
   484    700         zKey = sqlite3_mprintf("%s/%06d", zDb, iKey);
   485    701         nData = 0;
   486    702         pData = readFile(zKey, &nData);
................................................................................
   495    711                        sqlite3_errmsg(db));
   496    712           }
   497    713         }else{
   498    714           rc = sqlite3_blob_reopen(pBlob, iKey);
   499    715         }
   500    716         if( rc==SQLITE_OK ){
   501    717           nData = sqlite3_blob_bytes(pBlob);
   502         -        pData = sqlite3_malloc( nData+1 );
          718  +        if( nAlloc<nData+1 ){
          719  +          nAlloc = nData+100;
          720  +          pData = sqlite3_realloc(pData, nAlloc);
          721  +        }
   503    722           if( pData==0 ) fatalError("cannot allocate %d bytes", nData+1);
   504    723           rc = sqlite3_blob_read(pBlob, pData, nData, 0);
   505    724           if( rc!=SQLITE_OK ){
   506    725             fatalError("could not read the blob at %d: %s", iKey,
   507    726                        sqlite3_errmsg(db));
   508    727           }
   509         -        sqlite3_free(pData);
   510    728         }
   511    729       }else{
   512    730         /* CASE 3: Reading from database using SQL */
   513    731         if( pStmt==0 ){
   514    732           rc = sqlite3_prepare_v2(db, 
   515    733                  "SELECT v FROM kv WHERE k=?1", -1, &pStmt, 0);
   516    734           if( rc ){
................................................................................
   536    754         if( iKey<=0 ) iKey = iMax;
   537    755       }else{
   538    756         iKey = (randInt()%iMax)+1;
   539    757       }
   540    758       nTotal += nData;
   541    759       if( nData==0 ){ nCount++; nExtra++; }
   542    760     }
          761  +  if( nAlloc ) sqlite3_free(pData);
   543    762     if( pStmt ) sqlite3_finalize(pStmt);
   544    763     if( pBlob ) sqlite3_blob_close(pBlob);
          764  +  if( bStats ){
          765  +    display_stats(db, 0);
          766  +  }
   545    767     if( db ) sqlite3_close(db);
   546    768     tmElapsed = timeOfDay() - tmStart;
   547    769     if( nExtra ){
   548    770       printf("%d cycles due to %d misses\n", nCount, nExtra);
   549    771     }
   550    772     if( eType==PATH_DB ){
   551    773       printf("SQLite version: %s\n", sqlite3_libversion());
   552    774     }
   553    775     printf("--count %d --max-id %d", nCount-nExtra, iMax);
   554         -  if( eType==PATH_DB ){
   555         -    printf(" --cache-size %d", iCache);
   556         -  }
   557    776     switch( eOrder ){
   558    777       case ORDER_RANDOM:  printf(" --random\n");  break;
   559    778       case ORDER_DESC:    printf(" --desc\n");    break;
   560    779       default:            printf(" --asc\n");     break;
   561    780     }
          781  +  if( eType==PATH_DB ){
          782  +    printf("--cache-size %d --jmode %s\n", iCache, zJMode);
          783  +    printf("--mmap %d%s\n", mmapSize, bBlobApi ? " --blob-api" : "");
          784  +  }
   562    785     if( iPagesize ) printf("Database page size: %d\n", iPagesize);
   563    786     printf("Total elapsed time: %.3f\n", tmElapsed/1000.0);
   564    787     printf("Microseconds per BLOB read: %.3f\n", tmElapsed*1000.0/nCount);
   565    788     printf("Content read rate: %.1f MB/s\n", nTotal/(1000.0*tmElapsed));
   566    789     return 0;
   567    790   }
   568    791   

Changes to test/rowvalue.test.

   350    350     UPDATE t16b SET x=7;
   351    351     SELECT * FROM t16a;
   352    352   } {7 8 9}
   353    353   do_execsql_test 16.2 {
   354    354     UPDATE t16b SET x=97;
   355    355     SELECT * FROM t16a;
   356    356   } {97 98 99}
          357  +
          358  +do_execsql_test 16.3 {
          359  +  CREATE TABLE t16c(a, b, c, d, e);
          360  +  INSERT INTO t16c VALUES(1, 'a', 'b', 'c', 'd');
          361  +  CREATE TRIGGER t16c1 AFTER INSERT ON t16c BEGIN
          362  +    UPDATE t16c SET (c, d) = (SELECT 'A', 'B'), (e, b) = (SELECT 'C', 'D')
          363  +      WHERE a = new.a-1;
          364  +  END;
          365  +
          366  +  SELECT * FROM t16c;
          367  +} {1 a b c d}
          368  +
          369  +do_execsql_test 16.4 {
          370  +  INSERT INTO t16c VALUES(2, 'w', 'x', 'y', 'z');
          371  +  SELECT * FROM t16c;
          372  +} {
          373  +  1 D A B C 
          374  +  2 w x y z
          375  +}
          376  +
          377  +do_execsql_test 16.5 {
          378  +  DROP TRIGGER t16c1;
          379  +  PRAGMA recursive_triggers = 1;
          380  +  INSERT INTO t16c VALUES(3, 'i', 'ii', 'iii', 'iv');
          381  +  CREATE TRIGGER t16c1 AFTER UPDATE ON t16c WHEN new.a>1 BEGIN
          382  +    UPDATE t16c SET (e, d) = (
          383  +      SELECT b, c FROM t16c WHERE a = new.a-1
          384  +    ), (c, b) = (
          385  +      SELECT d, e FROM t16c WHERE a = new.a-1
          386  +    ) WHERE a = new.a-1;
          387  +  END;
          388  +
          389  +  UPDATE t16c SET a=a WHERE a=3;
          390  +  SELECT * FROM t16c;
          391  +} {
          392  +  1 C B A D
          393  +  2 z y x w
          394  +  3 i ii iii iv
          395  +}
   357    396   
   358    397   finish_test

Changes to test/speedtest1.c.

    46     46   #include "sqlite3.h"
    47     47   #include <assert.h>
    48     48   #include <stdio.h>
    49     49   #include <stdlib.h>
    50     50   #include <stdarg.h>
    51     51   #include <string.h>
    52     52   #include <ctype.h>
    53         -#include <unistd.h>
           53  +#ifndef _WIN32
           54  +# include <unistd.h>
           55  +#else
           56  +# include <io.h>
           57  +#endif
    54     58   #define ISSPACE(X) isspace((unsigned char)(X))
    55     59   #define ISDIGIT(X) isdigit((unsigned char)(X))
    56     60   
    57     61   #if SQLITE_VERSION_NUMBER<3005000
    58     62   # define sqlite3_int64 sqlite_int64
    59     63   #endif
    60         -#ifdef SQLITE_ENABLE_RBU
    61         -# include "sqlite3rbu.h"
    62         -#endif
    63     64   
    64     65   /* All global state is held in this structure */
    65     66   static struct Global {
    66     67     sqlite3 *db;               /* The open database connection */
    67     68     sqlite3_stmt *pStmt;       /* Current SQL statement */
    68     69     sqlite3_int64 iStart;      /* Start-time for the current test */
    69     70     sqlite3_int64 iTotal;      /* Total time */
................................................................................
  1173   1174   ** A testset for the R-Tree virtual table
  1174   1175   */
  1175   1176   void testset_rtree(int p1, int p2){
  1176   1177     unsigned i, n;
  1177   1178     unsigned mxCoord;
  1178   1179     unsigned x0, x1, y0, y1, z0, z1;
  1179   1180     unsigned iStep;
  1180         -  int *aCheck = sqlite3_malloc( sizeof(int)*g.szTest*100 );
         1181  +  int *aCheck = sqlite3_malloc( sizeof(int)*g.szTest*500 );
  1181   1182   
  1182   1183     mxCoord = 15000;
  1183         -  n = g.szTest*100;
         1184  +  n = g.szTest*500;
  1184   1185     speedtest1_begin_test(100, "%d INSERTs into an r-tree", n);
  1185   1186     speedtest1_exec("BEGIN");
  1186   1187     speedtest1_exec("CREATE VIRTUAL TABLE rt1 USING rtree(id,x0,x1,y0,y1,z0,z1)");
  1187   1188     speedtest1_prepare("INSERT INTO rt1(id,x0,x1,y0,y1,z0,z1)"
  1188   1189                        "VALUES(?1,?2,?3,?4,?5,?6,?7)");
  1189   1190     for(i=1; i<=n; i++){
  1190   1191       twoCoords(p1, p2, mxCoord, &x0, &x1);
................................................................................
  1199   1200       sqlite3_bind_int(g.pStmt, 7, z1);
  1200   1201       speedtest1_run();
  1201   1202     }
  1202   1203     speedtest1_exec("COMMIT");
  1203   1204     speedtest1_end_test();
  1204   1205   
  1205   1206     speedtest1_begin_test(101, "Copy from rtree to a regular table");
  1206         -  speedtest1_exec(" TABLE t1(id INTEGER PRIMARY KEY,x0,x1,y0,y1,z0,z1)");
         1207  +  speedtest1_exec("CREATE TABLE t1(id INTEGER PRIMARY KEY,x0,x1,y0,y1,z0,z1)");
  1207   1208     speedtest1_exec("INSERT INTO t1 SELECT * FROM rt1");
  1208   1209     speedtest1_end_test();
  1209   1210   
  1210         -  n = g.szTest*20;
         1211  +  n = g.szTest*100;
  1211   1212     speedtest1_begin_test(110, "%d one-dimensional intersect slice queries", n);
  1212   1213     speedtest1_prepare("SELECT count(*) FROM rt1 WHERE x0>=?1 AND x1<=?2");
  1213   1214     iStep = mxCoord/n;
  1214   1215     for(i=0; i<n; i++){
  1215   1216       sqlite3_bind_int(g.pStmt, 1, i*iStep);
  1216   1217       sqlite3_bind_int(g.pStmt, 2, (i+1)*iStep);
  1217   1218       speedtest1_run();
  1218   1219       aCheck[i] = atoi(g.zResult);
  1219   1220     }
  1220   1221     speedtest1_end_test();
  1221   1222   
  1222   1223     if( g.bVerify ){
  1223         -    n = g.szTest*20;
         1224  +    n = g.szTest*100;
  1224   1225       speedtest1_begin_test(111, "Verify result from 1-D intersect slice queries");
  1225   1226       speedtest1_prepare("SELECT count(*) FROM t1 WHERE x0>=?1 AND x1<=?2");
  1226   1227       iStep = mxCoord/n;
  1227   1228       for(i=0; i<n; i++){
  1228   1229         sqlite3_bind_int(g.pStmt, 1, i*iStep);
  1229   1230         sqlite3_bind_int(g.pStmt, 2, (i+1)*iStep);
  1230   1231         speedtest1_run();
................................................................................
  1232   1233           fatal_error("Count disagree step %d: %d..%d.  %d vs %d",
  1233   1234                       i, i*iStep, (i+1)*iStep, aCheck[i], atoi(g.zResult));
  1234   1235         }
  1235   1236       }
  1236   1237       speedtest1_end_test();
  1237   1238     }
  1238   1239     
  1239         -  n = g.szTest*20;
         1240  +  n = g.szTest*100;
  1240   1241     speedtest1_begin_test(120, "%d one-dimensional overlap slice queries", n);
  1241   1242     speedtest1_prepare("SELECT count(*) FROM rt1 WHERE y1>=?1 AND y0<=?2");
  1242   1243     iStep = mxCoord/n;
  1243   1244     for(i=0; i<n; i++){
  1244   1245       sqlite3_bind_int(g.pStmt, 1, i*iStep);
  1245   1246       sqlite3_bind_int(g.pStmt, 2, (i+1)*iStep);
  1246   1247       speedtest1_run();
  1247   1248       aCheck[i] = atoi(g.zResult);
  1248   1249     }
  1249   1250     speedtest1_end_test();
  1250   1251   
  1251   1252     if( g.bVerify ){
  1252         -    n = g.szTest*20;
         1253  +    n = g.szTest*100;
  1253   1254       speedtest1_begin_test(121, "Verify result from 1-D overlap slice queries");
  1254   1255       speedtest1_prepare("SELECT count(*) FROM t1 WHERE y1>=?1 AND y0<=?2");
  1255   1256       iStep = mxCoord/n;
  1256   1257       for(i=0; i<n; i++){
  1257   1258         sqlite3_bind_int(g.pStmt, 1, i*iStep);
  1258   1259         sqlite3_bind_int(g.pStmt, 2, (i+1)*iStep);
  1259   1260         speedtest1_run();
................................................................................
  1262   1263                       i, i*iStep, (i+1)*iStep, aCheck[i], atoi(g.zResult));
  1263   1264         }
  1264   1265       }
  1265   1266       speedtest1_end_test();
  1266   1267     }
  1267   1268     
  1268   1269   
  1269         -  n = g.szTest*20;
         1270  +  n = g.szTest*100;
  1270   1271     speedtest1_begin_test(125, "%d custom geometry callback queries", n);
  1271   1272     sqlite3_rtree_geometry_callback(g.db, "xslice", xsliceGeometryCallback, 0);
  1272   1273     speedtest1_prepare("SELECT count(*) FROM rt1 WHERE id MATCH xslice(?1,?2)");
  1273   1274     iStep = mxCoord/n;
  1274   1275     for(i=0; i<n; i++){
  1275   1276       sqlite3_bind_int(g.pStmt, 1, i*iStep);
  1276   1277       sqlite3_bind_int(g.pStmt, 2, (i+1)*iStep);
................................................................................
  1278   1279       if( aCheck[i]!=atoi(g.zResult) ){
  1279   1280         fatal_error("Count disagree step %d: %d..%d.  %d vs %d",
  1280   1281                     i, i*iStep, (i+1)*iStep, aCheck[i], atoi(g.zResult));
  1281   1282       }
  1282   1283     }
  1283   1284     speedtest1_end_test();
  1284   1285   
  1285         -  n = g.szTest*80;
         1286  +  n = g.szTest*400;
  1286   1287     speedtest1_begin_test(130, "%d three-dimensional intersect box queries", n);
  1287   1288     speedtest1_prepare("SELECT count(*) FROM rt1 WHERE x1>=?1 AND x0<=?2"
  1288   1289                        " AND y1>=?1 AND y0<=?2 AND z1>=?1 AND z0<=?2");
  1289   1290     iStep = mxCoord/n;
  1290   1291     for(i=0; i<n; i++){
  1291   1292       sqlite3_bind_int(g.pStmt, 1, i*iStep);
  1292   1293       sqlite3_bind_int(g.pStmt, 2, (i+1)*iStep);
  1293   1294       speedtest1_run();
  1294   1295       aCheck[i] = atoi(g.zResult);
  1295   1296     }
  1296   1297     speedtest1_end_test();
  1297   1298   
  1298         -  n = g.szTest*100;
         1299  +  n = g.szTest*500;
  1299   1300     speedtest1_begin_test(140, "%d rowid queries", n);
  1300   1301     speedtest1_prepare("SELECT * FROM rt1 WHERE id=?1");
  1301   1302     for(i=1; i<=n; i++){
  1302   1303       sqlite3_bind_int(g.pStmt, 1, i);
  1303   1304       speedtest1_run();
  1304   1305     }
  1305   1306     speedtest1_end_test();
................................................................................
  1370   1371     int doAutovac = 0;            /* True for --autovacuum */
  1371   1372     int cacheSize = 0;            /* Desired cache size.  0 means default */
  1372   1373     int doExclusive = 0;          /* True for --exclusive */
  1373   1374     int nHeap = 0, mnHeap = 0;    /* Heap size from --heap */
  1374   1375     int doIncrvac = 0;            /* True for --incrvacuum */
  1375   1376     const char *zJMode = 0;       /* Journal mode */
  1376   1377     const char *zKey = 0;         /* Encryption key */
  1377         -  int nLook = 0, szLook = 0;    /* --lookaside configuration */
         1378  +  int nLook = -1, szLook = 0;   /* --lookaside configuration */
  1378   1379     int noSync = 0;               /* True for --nosync */
  1379   1380     int pageSize = 0;             /* Desired page size.  0 means default */
  1380   1381     int nPCache = 0, szPCache = 0;/* --pcache configuration */
  1381   1382     int doPCache = 0;             /* True if --pcache is seen */
  1382   1383     int nScratch = 0, szScratch=0;/* --scratch configuration */
  1383   1384     int showStats = 0;            /* True for --stats */
  1384   1385     int nThread = 0;              /* --threads value */
................................................................................
  1450   1451           if( i>=argc-1 ) fatal_error("missing argument on %s\n", argv[i]);
  1451   1452           mmapSize = integerValue(argv[++i]);
  1452   1453    #endif
  1453   1454         }else if( strcmp(z,"nosync")==0 ){
  1454   1455           noSync = 1;
  1455   1456         }else if( strcmp(z,"notnull")==0 ){
  1456   1457           g.zNN = "NOT NULL";
  1457         -#ifdef SQLITE_ENABLE_RBU
  1458         -      }else if( strcmp(z,"rbu")==0 ){
  1459         -        sqlite3ota_create_vfs("rbu", 0);
  1460         -        sqlite3_vfs_register(sqlite3_vfs_find("rbu"), 1);
  1461         -#endif
  1462   1458         }else if( strcmp(z,"pagesize")==0 ){
  1463   1459           if( i>=argc-1 ) fatal_error("missing argument on %s\n", argv[i]);
  1464   1460           pageSize = integerValue(argv[++i]);
  1465   1461         }else if( strcmp(z,"pcache")==0 ){
  1466   1462           if( i>=argc-2 ) fatal_error("missing arguments on %s\n", argv[i]);
  1467   1463           nPCache = integerValue(argv[i+1]);
  1468   1464           szPCache = integerValue(argv[i+2]);
................................................................................
  1554   1550     if( nScratch>0 && szScratch>0 ){
  1555   1551       pScratch = malloc( nScratch*(sqlite3_int64)szScratch );
  1556   1552       if( pScratch==0 ) fatal_error("cannot allocate %lld-byte scratch\n",
  1557   1553                                    nScratch*(sqlite3_int64)szScratch);
  1558   1554       rc = sqlite3_config(SQLITE_CONFIG_SCRATCH, pScratch, szScratch, nScratch);
  1559   1555       if( rc ) fatal_error("scratch configuration failed: %d\n", rc);
  1560   1556     }
  1561         -  if( nLook>0 ){
         1557  +  if( nLook>=0 ){
  1562   1558       sqlite3_config(SQLITE_CONFIG_LOOKASIDE, 0, 0);
  1563   1559     }
  1564   1560   #endif
  1565   1561    
  1566   1562     /* Open the database and the input file */
  1567   1563     if( sqlite3_open(zDbName, &g.db) ){
  1568   1564       fatal_error("Cannot open database file: %s\n", zDbName);

Changes to test/tester.tcl.

   457    457           foreach {dummy cmdlinearg(malloctrace)} [split $a =] break
   458    458           if {$cmdlinearg(malloctrace)} {
   459    459             sqlite3_memdebug_log start
   460    460           }
   461    461         }
   462    462         {^-+backtrace=.+$} {
   463    463           foreach {dummy cmdlinearg(backtrace)} [split $a =] break
   464         -        sqlite3_memdebug_backtrace $value
          464  +        sqlite3_memdebug_backtrace $cmdlinearg(backtrace)
   465    465         }
   466    466         {^-+binarylog=.+$} {
   467    467           foreach {dummy cmdlinearg(binarylog)} [split $a =] break
   468    468           set cmdlinearg(binarylog) [file normalize $cmdlinearg(binarylog)]
   469    469         }
   470    470         {^-+soak=.+$} {
   471    471           foreach {dummy cmdlinearg(soak)} [split $a =] break

Added test/update2.test.

            1  +# 2017 January 9
            2  +#
            3  +# The author disclaims copyright to this source code.  In place of
            4  +# a legal notice, here is a blessing:
            5  +#
            6  +#    May you do good and not evil.
            7  +#    May you find forgiveness for yourself and forgive others.
            8  +#    May you share freely, never taking more than you give.
            9  +#
           10  +#***********************************************************************
           11  +#
           12  +
           13  +set testdir [file dirname $argv0]
           14  +source $testdir/tester.tcl
           15  +set testprefix update2
           16  +
           17  +db func repeat [list string repeat]
           18  +
           19  +#-------------------------------------------------------------------------
           20  +# 1.1.* A one-pass UPDATE that does balance() operations on the IPK index
           21  +#       that it is scanning.
           22  +#
           23  +# 1.2.* Same again, but with a WITHOUT ROWID table.
           24  +#
           25  +set nrow [expr 10]
           26  +do_execsql_test 1.1.0 {
           27  +  CREATE TABLE t1(a INTEGER PRIMARY KEY, b);
           28  +  CREATE TABLE t2(a INTEGER PRIMARY KEY, b);
           29  +  WITH s(i) AS ( SELECT 0 UNION ALL SELECT i+1 FROM s WHERE i<$nrow )
           30  +  INSERT INTO t1(b) SELECT char((i % 26) + 65) FROM s;
           31  +  INSERT INTO t2 SELECT * FROM t1;
           32  +}
           33  +
           34  +do_execsql_test 1.1.1 {
           35  +  UPDATE t1 SET b = repeat(b, 100)
           36  +}
           37  +
           38  +do_execsql_test 1.1.2 {
           39  +  SELECT * FROM t1;
           40  +} [db eval { SELECT a, repeat(b, 100) FROM t2 }]
           41  +
           42  +do_execsql_test 1.2.0 {
           43  +  DROP TABLE t1;
           44  +  CREATE TABLE t1(a INT PRIMARY KEY, b) WITHOUT ROWID;
           45  +  WITH s(i) AS ( SELECT 0 UNION ALL SELECT i+1 FROM s WHERE i<$nrow )
           46  +  INSERT INTO t1(a, b) SELECT i+1, char((i % 26) + 65) FROM s;
           47  +}
           48  +
           49  +#explain_i { UPDATE t1 SET b = repeat(b, 100) }
           50  +do_execsql_test 1.2.1 {
           51  +  UPDATE t1 SET b = repeat(b, 100)
           52  +}
           53  +
           54  +do_execsql_test 1.2.2 {
           55  +  SELECT * FROM t1;
           56  +} [db eval { SELECT a, repeat(b, 100) FROM t2 }]
           57  +
           58  +
           59  +#-------------------------------------------------------------------------
           60  +# A one-pass UPDATE that does balance() operations on the IPK index
           61  +# that it is scanning.
           62  +#
           63  +do_execsql_test 2.1 {
           64  +  CREATE TABLE t3(a PRIMARY KEY, b, c);
           65  +  CREATE INDEX t3i ON t3(b);
           66  +} {}
           67  +do_execsql_test 2.2 { UPDATE t3 SET c=1 WHERE b=?      } {}
           68  +do_execsql_test 2.3 { UPDATE t3 SET c=1 WHERE rowid=?  } {}
           69  +
           70  +#-------------------------------------------------------------------------
           71  +#
           72  +do_execsql_test 3.0 {
           73  +  CREATE TABLE t4(a PRIMARY KEY, b, c) WITHOUT ROWID;
           74  +  CREATE INDEX t4c ON t4(c);
           75  +  INSERT INTO t4 VALUES(1, 2, 3);
           76  +  INSERT INTO t4 VALUES(2, 3, 4);
           77  +}
           78  +
           79  +do_execsql_test 3.1 {
           80  +  UPDATE t4 SET c=c+2 WHERE c>2;
           81  +  SELECT a, c FROM t4 ORDER BY a;
           82  +} {1 5 2 6}
           83  +
           84  +#-------------------------------------------------------------------------
           85  +#
           86  +foreach {tn sql} {
           87  +  1 { 
           88  +    CREATE TABLE b1(a INTEGER PRIMARY KEY, b, c);
           89  +    CREATE TABLE c1(a INTEGER PRIMARY KEY, b, c, d)
           90  +  }
           91  +  2 { 
           92  +    CREATE TABLE b1(a INT PRIMARY KEY, b, c) WITHOUT ROWID;
           93  +    CREATE TABLE c1(a INT PRIMARY KEY, b, c, d) WITHOUT ROWID;
           94  +  }
           95  +} {
           96  +  execsql { DROP TABLE IF EXISTS b1; DROP TABLE IF EXISTS c1; }
           97  +  execsql $sql
           98  +
           99  +  do_execsql_test 4.$tn.0 {
          100  +    CREATE UNIQUE INDEX b1c ON b1(c);
          101  +    INSERT INTO b1 VALUES(1, 'a', 1);
          102  +    INSERT INTO b1 VALUES(2, 'b', 15);
          103  +    INSERT INTO b1 VALUES(3, 'c', 3);
          104  +    INSERT INTO b1 VALUES(4, 'd', 4);
          105  +    INSERT INTO b1 VALUES(5, 'e', 5);
          106  +    INSERT INTO b1 VALUES(6, 'f', 6);
          107  +    INSERT INTO b1 VALUES(7, 'g', 7);
          108  +  }
          109  +
          110  +  do_execsql_test 4.$tn.1 {
          111  +    UPDATE OR REPLACE b1 SET c=c+10 WHERE a BETWEEN 4 AND 7;
          112  +    SELECT * FROM b1 ORDER BY a;
          113  +  } {
          114  +    1 a 1
          115  +    3 c 3
          116  +    4 d 14
          117  +    5 e 15
          118  +    6 f 16
          119  +    7 g 17
          120  +  }
          121  +
          122  +  do_execsql_test 4.$tn.2 {
          123  +    CREATE INDEX c1d ON c1(d, b);
          124  +    CREATE UNIQUE INDEX c1c ON c1(c, b);
          125  +
          126  +    INSERT INTO c1 VALUES(1, 'a', 1,  1);
          127  +    INSERT INTO c1 VALUES(2, 'a', 15, 2);
          128  +    INSERT INTO c1 VALUES(3, 'a', 3,  3);
          129  +    INSERT INTO c1 VALUES(4, 'a', 4,  4);
          130  +    INSERT INTO c1 VALUES(5, 'a', 5,  5);
          131  +    INSERT INTO c1 VALUES(6, 'a', 6,  6);
          132  +    INSERT INTO c1 VALUES(7, 'a', 7,  7);
          133  +  }
          134  +
          135  +  do_execsql_test 4.$tn.3 {
          136  +    UPDATE OR REPLACE c1 SET c=c+10 WHERE d BETWEEN 4 AND 7;
          137  +    SELECT * FROM c1 ORDER BY a;
          138  +  } {
          139  +    1 a 1 1
          140  +    3 a 3 3
          141  +    4 a 14 4
          142  +    5 a 15 5
          143  +    6 a 16 6
          144  +    7 a 17 7
          145  +  }
          146  +
          147  +  do_execsql_test 4.$tn.4 { PRAGMA integrity_check } ok
          148  +
          149  +  do_execsql_test 4.$tn.5 {
          150  +    DROP INDEX c1d;
          151  +    DROP INDEX c1c;
          152  +    DELETE FROM c1;
          153  +
          154  +    INSERT INTO c1 VALUES(1, 'a', 1,  1);
          155  +    INSERT INTO c1 VALUES(2, 'a', 15, 2);
          156  +    INSERT INTO c1 VALUES(3, 'a', 3,  3);
          157  +    INSERT INTO c1 VALUES(4, 'a', 4,  4);
          158  +    INSERT INTO c1 VALUES(5, 'a', 5,  5);
          159  +    INSERT INTO c1 VALUES(6, 'a', 6,  6);
          160  +    INSERT INTO c1 VALUES(7, 'a', 7,  7);
          161  +
          162  +    CREATE INDEX c1d ON c1(d);
          163  +    CREATE UNIQUE INDEX c1c ON c1(c);
          164  +  }
          165  +
          166  +  do_execsql_test 4.$tn.6 {
          167  +    UPDATE OR REPLACE c1 SET c=c+10 WHERE d BETWEEN 4 AND 7;
          168  +    SELECT * FROM c1 ORDER BY a;
          169  +  } {
          170  +    1 a 1 1
          171  +    3 a 3 3
          172  +    4 a 14 4
          173  +    5 a 15 5
          174  +    6 a 16 6
          175  +    7 a 17 7
          176  +  }
          177  +}
          178  +
          179  +finish_test
          180  +

Changes to test/vtabH.test.

   116    116       [regexp -nocase -- {^[A-Z]:} $drive]} {
   117    117     reset_db
   118    118     register_fs_module db
   119    119     do_execsql_test 3.0 {
   120    120       SELECT name FROM fsdir WHERE dir = '.' AND name = 'test.db';
   121    121       SELECT name FROM fsdir WHERE dir = '.' AND name = '.'
   122    122     } {test.db .}
          123  +
          124  +  proc sort_files { names {nocase false} } {
          125  +    if {$nocase && $::tcl_platform(platform) eq "windows"} {
          126  +      return [lsort -nocase $names]
          127  +    } else {
          128  +      return [lsort $names]
          129  +    }
          130  +  }
   123    131   
   124    132     proc list_root_files {} {
   125    133       if {$::tcl_platform(platform) eq "windows"} {
   126         -      set res [list]
   127         -      foreach name [glob -directory $::env(fstreeDrive)/ -- *] {
          134  +      set res [list]; set dir $::env(fstreeDrive)/; set names [list]
          135  +      eval lappend names [glob -nocomplain -directory $dir -- *]
          136  +      foreach name $names {
   128    137           if {[string index [file tail $name] 0] eq "."} continue
          138  +        if {[file attributes $name -hidden]} continue
          139  +        if {[file attributes $name -system]} continue
   129    140           lappend res $name
   130    141         }
   131         -      return $res
          142  +      return [sort_files $res true]
   132    143       } else {
   133         -      return [string map {/ {}} [glob /*]]
          144  +      return [sort_files [string map {/ {}} [glob -nocomplain -- /*]]]
   134    145       }
   135    146     }
   136    147   
   137    148     proc list_files { pattern } {
   138    149       if {$::tcl_platform(platform) eq "windows"} {
   139         -      set res [list]
   140         -      foreach name [glob -nocomplain $pattern] {
          150  +      set res [list]; set names [list]
          151  +      eval lappend names [glob -nocomplain -- $pattern]
          152  +      foreach name $names {
   141    153           if {[string index [file tail $name] 0] eq "."} continue
          154  +        if {[file attributes $name -hidden]} continue
          155  +        if {[file attributes $name -system]} continue
   142    156           lappend res $name
   143    157         }
   144         -      return $res
          158  +      return [sort_files $res]
   145    159       } else {
   146         -      return [glob -nocomplain $pattern]
          160  +      return [sort_files [glob -nocomplain -- $pattern]]
   147    161       }
   148    162     }
   149    163   
   150    164     # Read the first 5 entries from the root directory.  Except, ignore
   151    165     # files that contain the "$" character in their names as these are
   152    166     # special files on some Windows platforms.
   153    167     #
   154    168     set res [list]
   155    169     set root_files [list_root_files]
   156         -  set num_root_files [llength $root_files]
   157         -  set lim_root_files [expr {$num_root_files > 5 ? 5 : $num_root_files}]
   158         -  foreach p [lrange $root_files 0 [expr {$lim_root_files - 1}]] {
          170  +  foreach p $root_files {
   159    171       if {$::tcl_platform(platform) eq "windows"} {
   160         -      if {[regexp {\$} $p]} {incr lim_root_files -1} else {lappend res $p}
          172  +      if {![regexp {\$} $p]} {lappend res $p}
   161    173       } else {
   162    174         lappend res "/$p"
   163    175       }
   164    176     }
   165         -  do_execsql_test 3.1 [subst {
   166         -    SELECT path FROM fstree WHERE path NOT GLOB '*\$*' LIMIT $lim_root_files;
   167         -  }] $res
          177  +  set num_root_files [llength $root_files]
          178  +  do_test 3.1 {
          179  +    sort_files [execsql {
          180  +      SELECT path FROM fstree WHERE path NOT GLOB '*\$*' LIMIT $num_root_files;
          181  +    }] true
          182  +  } [sort_files $res true]
   168    183   
   169    184     # Read all entries in the current directory.
   170    185     #
   171    186     proc contents {pattern} {
   172    187       set res [list]
   173    188       foreach f [list_files $pattern] {
   174    189         lappend res $f
................................................................................
   178    193       }
   179    194       set res
   180    195     }
   181    196     set pwd "[pwd]/*"
   182    197     set res [contents $pwd]
   183    198     do_execsql_test 3.2 {
   184    199       SELECT path FROM fstree WHERE path GLOB $pwd ORDER BY 1
   185         -  } [lsort $res]
          200  +  } [sort_files $res]
   186    201   
   187    202     # Add some sub-directories and files to the current directory.
   188    203     #
   189    204     do_test 3.3 {
   190    205       catch { file delete -force subdir }
   191    206       foreach {path sz} {
   192    207         subdir/x1.txt     143

Changes to test/wordcount.c.

     9      9   **     wordcount DATABASE INPUTFILE
    10     10   **
    11     11   ** The INPUTFILE name can be omitted, in which case input it taken from
    12     12   ** standard input.
    13     13   **
    14     14   ** Option:
    15     15   **
    16         -**     --without-rowid      Use a WITHOUT ROWID table to store the words.
    17         -**     --insert             Use INSERT mode (the default)
    18         -**     --replace            Use REPLACE mode
    19         -**     --select             Use SELECT mode
    20         -**     --update             Use UPDATE mode
    21         -**     --delete             Use DELETE mode
    22         -**     --query              Use QUERY mode
    23         -**     --nocase             Add the NOCASE collating sequence to the words.
    24         -**     --trace              Enable sqlite3_trace() output.
    25         -**     --summary            Show summary information on the collected data.
    26         -**     --stats              Show sqlite3_status() results at the end.
    27         -**     --pagesize NNN       Use a page size of NNN
    28         -**     --cachesize NNN      Use a cache size of NNN
    29         -**     --commit NNN         Commit after every NNN operations
    30         -**     --nosync             Use PRAGMA synchronous=OFF
    31         -**     --journal MMMM       Use PRAGMA journal_mode=MMMM
    32         -**     --timer              Time the operation of this program
    33         -**     --tag NAME           Tag all output using NAME.  Use only stdout.
    34     16   **
    35     17   ** Modes:
    36     18   **
    37     19   ** Insert mode means:
    38     20   **    (1) INSERT OR IGNORE INTO wordcount VALUES($new,1)
    39     21   **    (2) UPDATE wordcount SET cnt=cnt+1 WHERE word=$new -- if (1) is a noop
    40     22   **
................................................................................
    77     59   */
    78     60   #include <stdio.h>
    79     61   #include <string.h>
    80     62   #include <ctype.h>
    81     63   #include <stdlib.h>
    82     64   #include <stdarg.h>
    83     65   #include "sqlite3.h"
           66  +#ifndef _WIN32
           67  +# include <unistd.h>
           68  +#else
           69  +# include <io.h>
           70  +#endif
    84     71   #define ISALPHA(X) isalpha((unsigned char)(X))
           72  +
           73  +const char zHelp[] = 
           74  +"Usage: wordcount [OPTIONS] DATABASE [INPUT]\n"
           75  +" --all                Repeat the test for all test modes\n"
           76  +" --cachesize NNN      Use a cache size of NNN\n"
           77  +" --commit NNN         Commit after every NNN operations\n"
           78  +" --delete             Use DELETE mode\n"
           79  +" --insert             Use INSERT mode (the default)\n"
           80  +" --journal MMMM       Use PRAGMA journal_mode=MMMM\n"
           81  +" --nocase             Add the NOCASE collating sequence to the words.\n"
           82  +" --nosync             Use PRAGMA synchronous=OFF\n"
           83  +" --pagesize NNN       Use a page size of NNN\n"
           84  +" --query              Use QUERY mode\n"
           85  +" --replace            Use REPLACE mode\n"
           86  +" --select             Use SELECT mode\n"
           87  +" --stats              Show sqlite3_status() results at the end.\n"
           88  +" --summary            Show summary information on the collected data.\n"
           89  +" --tag NAME           Tag all output using NAME.  Use only stdout.\n"
           90  +" --timer              Time the operation of this program\n"
           91  +" --trace              Enable sqlite3_trace() output.\n"
           92  +" --update             Use UPDATE mode\n"
           93  +" --without-rowid      Use a WITHOUT ROWID table to store the words.\n"
           94  +;
    85     95   
    86     96   /* Output tag */
    87     97   char *zTag = "--";
    88     98   
    89     99   /* Return the current wall-clock time */
    90    100   static sqlite3_int64 realTime(void){
    91    101     static sqlite3_vfs *clockVfs = 0;
................................................................................
   105    115   static void fatal_error(const char *zMsg, ...){
   106    116     va_list ap;
   107    117     va_start(ap, zMsg);
   108    118     vfprintf(stderr, zMsg, ap);
   109    119     va_end(ap);
   110    120     exit(1);
   111    121   }
          122  +
          123  +/* Print a usage message and quit */
          124  +static void usage(void){
          125  +  printf("%s",zHelp);
          126  +  exit(0);
          127  +}
   112    128   
   113    129   /* The sqlite3_trace() callback function */
   114    130   static void traceCallback(void *NotUsed, const char *zSql){
   115    131     printf("%s;\n", zSql);
   116    132   }
   117    133   
   118    134   /* An sqlite3_exec() callback that prints results on standard output,
................................................................................
   185    201     a = sqlite3_aggregate_context(context, 0);
   186    202     if( a ){
   187    203       finalHash(a, zResult);
   188    204       sqlite3_result_text(context, zResult, -1, SQLITE_TRANSIENT);
   189    205     }
   190    206   }
   191    207   
   192         -
   193    208   /* Define operating modes */
   194    209   #define MODE_INSERT     0
   195    210   #define MODE_REPLACE    1
   196    211   #define MODE_SELECT     2
   197    212   #define MODE_UPDATE     3
   198    213   #define MODE_DELETE     4
   199    214   #define MODE_QUERY      5
          215  +#define MODE_COUNT      6
          216  +#define MODE_ALL      (-1)
          217  +
          218  +/* Mode names */
          219  +static const char *azMode[] = {
          220  +  "--insert",
          221  +  "--replace",
          222  +  "--select",
          223  +  "--update",
          224  +  "--delete",
          225  +  "--query"
          226  +};
          227  +
          228  +/*
          229  +** Determine if another iteration of the test is required.  Return true
          230  +** if so.  Return zero if all iterations have finished.
          231  +*/
          232  +static int allLoop(
          233  +  int iMode,                /* The selected test mode */
          234  +  int *piLoopCnt,           /* Iteration loop counter */
          235  +  int *piMode2,             /* The test mode to use on the next iteration */
          236  +  int *pUseWithoutRowid     /* Whether or not to use --without-rowid */
          237  +){
          238  +  int i;
          239  +  if( iMode!=MODE_ALL ){
          240  +    if( *piLoopCnt ) return 0;
          241  +    *piMode2 = iMode;
          242  +    *piLoopCnt = 1;
          243  +    return 1;
          244  +  }
          245  +  if( (*piLoopCnt)>=MODE_COUNT*2 ) return 0;
          246  +  i = (*piLoopCnt)++;
          247  +  *pUseWithoutRowid = i&1;
          248  +  *piMode2 = i>>1;
          249  +  return 1;
          250  +}
   200    251   
   201    252   int main(int argc, char **argv){
   202    253     const char *zFileToRead = 0;  /* Input file.  NULL for stdin */
   203    254     const char *zDbName = 0;      /* Name of the database file to create */
   204    255     int useWithoutRowid = 0;      /* True for --without-rowid */
   205    256     int iMode = MODE_INSERT;      /* One of MODE_xxxxx */
          257  +  int iMode2;                   /* Mode to use for current --all iteration */
          258  +  int iLoopCnt = 0;             /* Which iteration when running --all */
   206    259     int useNocase = 0;            /* True for --nocase */
   207    260     int doTrace = 0;              /* True for --trace */
   208    261     int showStats = 0;            /* True for --stats */
   209    262     int showSummary = 0;          /* True for --summary */
   210    263     int showTimer = 0;            /* True for --timer */
   211    264     int cacheSize = 0;            /* Desired cache size.  0 means default */
   212    265     int pageSize = 0;             /* Desired page size.  0 means default */
................................................................................
   222    275     sqlite3_stmt *pSelect = 0;    /* The SELECT statement */
   223    276     sqlite3_stmt *pDelete = 0;    /* The DELETE statement */
   224    277     FILE *in;                     /* The open input file */
   225    278     int rc;                       /* Return code from an SQLite interface */
   226    279     int iCur, iHiwtr;             /* Statistics values, current and "highwater" */
   227    280     FILE *pTimer = stderr;        /* Output channel for the timer */
   228    281     sqlite3_int64 sumCnt = 0;     /* Sum in QUERY mode */
   229         -  sqlite3_int64 startTime;
          282  +  sqlite3_int64 startTime;      /* Time of start */
          283  +  sqlite3_int64 totalTime = 0;  /* Total time */
   230    284     char zInput[2000];            /* A single line of input */
   231    285   
   232    286     /* Process command-line arguments */
   233    287     for(i=1; i<argc; i++){
   234    288       const char *z = argv[i];
   235    289       if( z[0]=='-' ){
   236    290         do{ z++; }while( z[0]=='-' );
................................................................................
   244    298           iMode = MODE_INSERT;
   245    299         }else if( strcmp(z,"update")==0 ){
   246    300           iMode = MODE_UPDATE;
   247    301         }else if( strcmp(z,"delete")==0 ){
   248    302           iMode = MODE_DELETE;
   249    303         }else if( strcmp(z,"query")==0 ){
   250    304           iMode = MODE_QUERY;
          305  +      }else if( strcmp(z,"all")==0 ){
          306  +        iMode = MODE_ALL;
          307  +        showTimer = -99;
   251    308         }else if( strcmp(z,"nocase")==0 ){
   252    309           useNocase = 1;
   253    310         }else if( strcmp(z,"trace")==0 ){
   254    311           doTrace = 1;
   255    312         }else if( strcmp(z,"nosync")==0 ){
   256    313           noSync = 1;
   257    314         }else if( strcmp(z,"stats")==0 ){
................................................................................
   270    327           i++;
   271    328           commitInterval = atoi(argv[i]);
   272    329         }else if( strcmp(z,"journal")==0 && i<argc-1 ){
   273    330           zJMode = argv[++i];
   274    331         }else if( strcmp(z,"tag")==0 && i<argc-1 ){
   275    332           zTag = argv[++i];
   276    333           pTimer = stdout;
          334  +      }else if( strcmp(z, "help")==0 || strcmp(z,"?")==0 ){
          335  +        usage();
   277    336         }else{
   278         -        fatal_error("unknown option: %s\n", argv[i]);
          337  +        fatal_error("unknown option: \"%s\"\n"
          338  +                    "Use --help for a list of options\n",
          339  +                    argv[i]);
   279    340         }
   280    341       }else if( zDbName==0 ){
   281    342         zDbName = argv[i];
   282    343       }else if( zFileToRead==0 ){
   283    344         zFileToRead = argv[i];
   284    345       }else{
   285         -      fatal_error("surplus argument: %s\n", argv[i]);
          346  +      fatal_error("surplus argument: \"%s\"\n", argv[i]);
   286    347       }
   287    348     }
   288    349     if( zDbName==0 ){
   289         -    fatal_error("Usage: %s [--options] DATABASE [INPUTFILE]\n", argv[0]);
          350  +    usage();
   290    351     }
   291    352     startTime = realTime();
   292    353   
   293    354     /* Open the database and the input file */
          355  +  if( zDbName[0] && strcmp(zDbName,":memory:")!=0 ){
          356  +    unlink(zDbName);
          357  +  }
   294    358     if( sqlite3_open(zDbName, &db) ){
   295    359       fatal_error("Cannot open database file: %s\n", zDbName);
   296    360     }
   297    361     if( zFileToRead ){
   298    362       in = fopen(zFileToRead, "rb");
   299    363       if( in==0 ){
   300    364         fatal_error("Could not open input file \"%s\"\n", zFileToRead);
   301    365       }
   302    366     }else{
          367  +    if( iMode==MODE_ALL ){
          368  +      fatal_error("The --all mode cannot be used with stdin\n");
          369  +    }
   303    370       in = stdin;
   304    371     }
   305    372   
   306    373     /* Set database connection options */
   307    374     if( doTrace ) sqlite3_trace(db, traceCallback, 0);
   308    375     if( pageSize ){
   309    376       zSql = sqlite3_mprintf("PRAGMA page_size=%d", pageSize);
................................................................................
   318    385     if( noSync ) sqlite3_exec(db, "PRAGMA synchronous=OFF", 0, 0, 0);
   319    386     if( zJMode ){
   320    387       zSql = sqlite3_mprintf("PRAGMA journal_mode=%s", zJMode);
   321    388       sqlite3_exec(db, zSql, 0, 0, 0);
   322    389       sqlite3_free(zSql);
   323    390     }
   324    391   
   325         -
   326         -  /* Construct the "wordcount" table into which to put the words */
   327         -  if( sqlite3_exec(db, "BEGIN IMMEDIATE", 0, 0, 0) ){
   328         -    fatal_error("Could not start a transaction\n");
   329         -  }
   330         -  zSql = sqlite3_mprintf(
   331         -     "CREATE TABLE IF NOT EXISTS wordcount(\n"
   332         -     "  word TEXT PRIMARY KEY COLLATE %s,\n"
   333         -     "  cnt INTEGER\n"
   334         -     ")%s",
   335         -     useNocase ? "nocase" : "binary",
   336         -     useWithoutRowid ? " WITHOUT ROWID" : ""
   337         -  );
   338         -  if( zSql==0 ) fatal_error("out of memory\n");
   339         -  rc = sqlite3_exec(db, zSql, 0, 0, 0);
   340         -  if( rc ) fatal_error("Could not create the wordcount table: %s.\n",
   341         -                       sqlite3_errmsg(db));
   342         -  sqlite3_free(zSql);
   343         -
   344         -  /* Prepare SQL statements that will be needed */
   345         -  if( iMode==MODE_QUERY ){
   346         -    rc = sqlite3_prepare_v2(db,
   347         -          "SELECT cnt FROM wordcount WHERE word=?1",
   348         -          -1, &pSelect, 0);
   349         -    if( rc ) fatal_error("Could not prepare the SELECT statement: %s\n",
   350         -                          sqlite3_errmsg(db));
   351         -  }
   352         -  if( iMode==MODE_SELECT ){
   353         -    rc = sqlite3_prepare_v2(db,
   354         -          "SELECT 1 FROM wordcount WHERE word=?1",
   355         -          -1, &pSelect, 0);
   356         -    if( rc ) fatal_error("Could not prepare the SELECT statement: %s\n",
   357         -                          sqlite3_errmsg(db));
   358         -    rc = sqlite3_prepare_v2(db,
   359         -          "INSERT INTO wordcount(word,cnt) VALUES(?1,1)",
   360         -          -1, &pInsert, 0);
   361         -    if( rc ) fatal_error("Could not prepare the INSERT statement: %s\n",
          392  +  iLoopCnt = 0;
          393  +  while( allLoop(iMode, &iLoopCnt, &iMode2, &useWithoutRowid) ){
          394  +    /* Delete prior content in --all mode */
          395  +    if( iMode==MODE_ALL ){
          396  +      if( sqlite3_exec(db, "DROP TABLE IF EXISTS wordcount; VACUUM;",0,0,0) ){
          397  +        fatal_error("Could not clean up prior iteration\n");
          398  +      }
          399  +      startTime = realTime();
          400  +      rewind(in);
          401  +    }
          402  + 
          403  +    /* Construct the "wordcount" table into which to put the words */
          404  +    if( sqlite3_exec(db, "BEGIN IMMEDIATE", 0, 0, 0) ){
          405  +      fatal_error("Could not start a transaction\n");
          406  +    }
          407  +    zSql = sqlite3_mprintf(
          408  +       "CREATE TABLE IF NOT EXISTS wordcount(\n"
          409  +       "  word TEXT PRIMARY KEY COLLATE %s,\n"
          410  +       "  cnt INTEGER\n"
          411  +       ")%s",
          412  +       useNocase ? "nocase" : "binary",
          413  +       useWithoutRowid ? " WITHOUT ROWID" : ""
          414  +    );
          415  +    if( zSql==0 ) fatal_error("out of memory\n");
          416  +    rc = sqlite3_exec(db, zSql, 0, 0, 0);
          417  +    if( rc ) fatal_error("Could not create the wordcount table: %s.\n",
   362    418                            sqlite3_errmsg(db));
   363         -  }
   364         -  if( iMode==MODE_SELECT || iMode==MODE_UPDATE || iMode==MODE_INSERT ){
   365         -    rc = sqlite3_prepare_v2(db,
   366         -          "UPDATE wordcount SET cnt=cnt+1 WHERE word=?1",
   367         -          -1, &pUpdate, 0);
   368         -    if( rc ) fatal_error("Could not prepare the UPDATE statement: %s\n",
   369         -                         sqlite3_errmsg(db));
   370         -  }
   371         -  if( iMode==MODE_INSERT ){
   372         -    rc = sqlite3_prepare_v2(db,
   373         -          "INSERT OR IGNORE INTO wordcount(word,cnt) VALUES(?1,1)",
   374         -          -1, &pInsert, 0);
   375         -    if( rc ) fatal_error("Could not prepare the INSERT statement: %s\n",
   376         -                         sqlite3_errmsg(db));
   377         -  }
   378         -  if( iMode==MODE_UPDATE ){
   379         -    rc = sqlite3_prepare_v2(db,
   380         -          "INSERT OR IGNORE INTO wordcount(word,cnt) VALUES(?1,0)",
   381         -          -1, &pInsert, 0);
   382         -    if( rc ) fatal_error("Could not prepare the INSERT statement: %s\n",
   383         -                         sqlite3_errmsg(db));
   384         -  }
   385         -  if( iMode==MODE_REPLACE ){
   386         -    rc = sqlite3_prepare_v2(db,
          419  +    sqlite3_free(zSql);
          420  +  
          421  +    /* Prepare SQL statements that will be needed */
          422  +    if( iMode2==MODE_QUERY ){
          423  +      rc = sqlite3_prepare_v2(db,
          424  +            "SELECT cnt FROM wordcount WHERE word=?1",
          425  +            -1, &pSelect, 0);
          426  +      if( rc ) fatal_error("Could not prepare the SELECT statement: %s\n",
          427  +                            sqlite3_errmsg(db));
          428  +    }
          429  +    if( iMode2==MODE_SELECT ){
          430  +      rc = sqlite3_prepare_v2(db,
          431  +            "SELECT 1 FROM wordcount WHERE word=?1",
          432  +            -1, &pSelect, 0);
          433  +      if( rc ) fatal_error("Could not prepare the SELECT statement: %s\n",
          434  +                            sqlite3_errmsg(db));
          435  +      rc = sqlite3_prepare_v2(db,
          436  +            "INSERT INTO wordcount(word,cnt) VALUES(?1,1)",
          437  +            -1, &pInsert, 0);
          438  +      if( rc ) fatal_error("Could not prepare the INSERT statement: %s\n",
          439  +                           sqlite3_errmsg(db));
          440  +    }
          441  +    if( iMode2==MODE_SELECT || iMode2==MODE_UPDATE || iMode2==MODE_INSERT ){
          442  +      rc = sqlite3_prepare_v2(db,
          443  +            "UPDATE wordcount SET cnt=cnt+1 WHERE word=?1",
          444  +            -1, &pUpdate, 0);
          445  +      if( rc ) fatal_error("Could not prepare the UPDATE statement: %s\n",
          446  +                           sqlite3_errmsg(db));
          447  +    }
          448  +    if( iMode2==MODE_INSERT ){
          449  +      rc = sqlite3_prepare_v2(db,
          450  +            "INSERT OR IGNORE INTO wordcount(word,cnt) VALUES(?1,1)",
          451  +            -1, &pInsert, 0);
          452  +      if( rc ) fatal_error("Could not prepare the INSERT statement: %s\n",
          453  +                           sqlite3_errmsg(db));
          454  +    }
          455  +    if( iMode2==MODE_UPDATE ){
          456  +      rc = sqlite3_prepare_v2(db,
          457  +            "INSERT OR IGNORE INTO wordcount(word,cnt) VALUES(?1,0)",
          458  +            -1, &pInsert, 0);
          459  +      if( rc ) fatal_error("Could not prepare the INSERT statement: %s\n",
          460  +                           sqlite3_errmsg(db));
          461  +    }
          462  +    if( iMode2==MODE_REPLACE ){
          463  +      rc = sqlite3_prepare_v2(db,
   387    464             "REPLACE INTO wordcount(word,cnt)"
   388    465             "VALUES(?1,coalesce((SELECT cnt FROM wordcount WHERE word=?1),0)+1)",
   389    466             -1, &pInsert, 0);
   390         -    if( rc ) fatal_error("Could not prepare the REPLACE statement: %s\n",
   391         -                          sqlite3_errmsg(db));
   392         -  }
   393         -  if( iMode==MODE_DELETE ){
   394         -    rc = sqlite3_prepare_v2(db,
   395         -          "DELETE FROM wordcount WHERE word=?1",
   396         -          -1, &pDelete, 0);
   397         -    if( rc ) fatal_error("Could not prepare the DELETE statement: %s\n",
   398         -                         sqlite3_errmsg(db));
   399         -  }
   400         -
   401         -  /* Process the input file */
   402         -  while( fgets(zInput, sizeof(zInput), in) ){
   403         -    for(i=0; zInput[i]; i++){
   404         -      if( !ISALPHA(zInput[i]) ) continue;
   405         -      for(j=i+1; ISALPHA(zInput[j]); j++){}
   406         -
   407         -      /* Found a new word at zInput[i] that is j-i bytes long. 
   408         -      ** Process it into the wordcount table.  */
   409         -      if( iMode==MODE_DELETE ){
   410         -        sqlite3_bind_text(pDelete, 1, zInput+i, j-i, SQLITE_STATIC);
   411         -        if( sqlite3_step(pDelete)!=SQLITE_DONE ){
   412         -          fatal_error("DELETE failed: %s\n", sqlite3_errmsg(db));
   413         -        }
   414         -        sqlite3_reset(pDelete);
   415         -      }else if( iMode==MODE_SELECT ){
   416         -        sqlite3_bind_text(pSelect, 1, zInput+i, j-i, SQLITE_STATIC);
   417         -        rc = sqlite3_step(pSelect);
   418         -        sqlite3_reset(pSelect);
   419         -        if( rc==SQLITE_ROW ){
   420         -          sqlite3_bind_text(pUpdate, 1, zInput+i, j-i, SQLITE_STATIC);
   421         -          if( sqlite3_step(pUpdate)!=SQLITE_DONE ){
   422         -            fatal_error("UPDATE failed: %s\n", sqlite3_errmsg(db));
          467  +      if( rc ) fatal_error("Could not prepare the REPLACE statement: %s\n",
          468  +                            sqlite3_errmsg(db));
          469  +    }
          470  +    if( iMode2==MODE_DELETE ){
          471  +      rc = sqlite3_prepare_v2(db,
          472  +            "DELETE FROM wordcount WHERE word=?1",
          473  +            -1, &pDelete, 0);
          474  +      if( rc ) fatal_error("Could not prepare the DELETE statement: %s\n",
          475  +                           sqlite3_errmsg(db));
          476  +    }
          477  +  
          478  +    /* Process the input file */
          479  +    while( fgets(zInput, sizeof(zInput), in) ){
          480  +      for(i=0; zInput[i]; i++){
          481  +        if( !ISALPHA(zInput[i]) ) continue;
          482  +        for(j=i+1; ISALPHA(zInput[j]); j++){}
          483  +  
          484  +        /* Found a new word at zInput[i] that is j-i bytes long. 
          485  +        ** Process it into the wordcount table.  */
          486  +        if( iMode2==MODE_DELETE ){
          487  +          sqlite3_bind_text(pDelete, 1, zInput+i, j-i, SQLITE_STATIC);
          488  +          if( sqlite3_step(pDelete)!=SQLITE_DONE ){
          489  +            fatal_error("DELETE failed: %s\n", sqlite3_errmsg(db));
          490  +          }
          491  +          sqlite3_reset(pDelete);
          492  +        }else if( iMode2==MODE_SELECT ){
          493  +          sqlite3_bind_text(pSelect, 1, zInput+i, j-i, SQLITE_STATIC);
          494  +          rc = sqlite3_step(pSelect);
          495  +          sqlite3_reset(pSelect);
          496  +          if( rc==SQLITE_ROW ){
          497  +            sqlite3_bind_text(pUpdate, 1, zInput+i, j-i, SQLITE_STATIC);
          498  +            if( sqlite3_step(pUpdate)!=SQLITE_DONE ){
          499  +              fatal_error("UPDATE failed: %s\n", sqlite3_errmsg(db));
          500  +            }
          501  +            sqlite3_reset(pUpdate);
          502  +          }else if( rc==SQLITE_DONE ){
          503  +            sqlite3_bind_text(pInsert, 1, zInput+i, j-i, SQLITE_STATIC);
          504  +            if( sqlite3_step(pInsert)!=SQLITE_DONE ){
          505  +              fatal_error("Insert failed: %s\n", sqlite3_errmsg(db));
          506  +            }
          507  +            sqlite3_reset(pInsert);
          508  +          }else{
          509  +            fatal_error("SELECT failed: %s\n", sqlite3_errmsg(db));
          510  +          }
          511  +        }else if( iMode2==MODE_QUERY ){
          512  +          sqlite3_bind_text(pSelect, 1, zInput+i, j-i, SQLITE_STATIC);
          513  +          if( sqlite3_step(pSelect)==SQLITE_ROW ){
          514  +            sumCnt += sqlite3_column_int64(pSelect, 0);
   423    515             }
   424         -          sqlite3_reset(pUpdate);
   425         -        }else if( rc==SQLITE_DONE ){
          516  +          sqlite3_reset(pSelect);
          517  +        }else{
   426    518             sqlite3_bind_text(pInsert, 1, zInput+i, j-i, SQLITE_STATIC);
   427    519             if( sqlite3_step(pInsert)!=SQLITE_DONE ){
   428         -            fatal_error("Insert failed: %s\n", sqlite3_errmsg(db));
          520  +            fatal_error("INSERT failed: %s\n", sqlite3_errmsg(db));
   429    521             }
   430    522             sqlite3_reset(pInsert);
   431         -        }else{
   432         -          fatal_error("SELECT failed: %s\n", sqlite3_errmsg(db));
   433         -        }
   434         -      }else if( iMode==MODE_QUERY ){
   435         -        sqlite3_bind_text(pSelect, 1, zInput+i, j-i, SQLITE_STATIC);
   436         -        if( sqlite3_step(pSelect)==SQLITE_ROW ){
   437         -          sumCnt += sqlite3_column_int64(pSelect, 0);
          523  +          if( iMode2==MODE_UPDATE
          524  +           || (iMode2==MODE_INSERT && sqlite3_changes(db)==0)
          525  +          ){
          526  +            sqlite3_bind_text(pUpdate, 1, zInput+i, j-i, SQLITE_STATIC);
          527  +            if( sqlite3_step(pUpdate)!=SQLITE_DONE ){
          528  +              fatal_error("UPDATE failed: %s\n", sqlite3_errmsg(db));
          529  +            }
          530  +            sqlite3_reset(pUpdate);
          531  +          }
   438    532           }
   439         -        sqlite3_reset(pSelect);
   440         -      }else{
   441         -        sqlite3_bind_text(pInsert, 1, zInput+i, j-i, SQLITE_STATIC);
   442         -        if( sqlite3_step(pInsert)!=SQLITE_DONE ){
   443         -          fatal_error("INSERT failed: %s\n", sqlite3_errmsg(db));
   444         -        }
   445         -        sqlite3_reset(pInsert);
   446         -        if( iMode==MODE_UPDATE
   447         -         || (iMode==MODE_INSERT && sqlite3_changes(db)==0)
   448         -        ){
   449         -          sqlite3_bind_text(pUpdate, 1, zInput+i, j-i, SQLITE_STATIC);
   450         -          if( sqlite3_step(pUpdate)!=SQLITE_DONE ){
   451         -            fatal_error("UPDATE failed: %s\n", sqlite3_errmsg(db));
   452         -          }
   453         -          sqlite3_reset(pUpdate);
          533  +        i = j-1;
          534  +  
          535  +        /* Increment the operation counter.  Do a COMMIT if it is time. */
          536  +        nOp++;
          537  +        if( commitInterval>0 && (nOp%commitInterval)==0 ){
          538  +          sqlite3_exec(db, "COMMIT; BEGIN IMMEDIATE", 0, 0, 0);
   454    539           }
   455    540         }
   456         -      i = j-1;
   457         -
   458         -      /* Increment the operation counter.  Do a COMMIT if it is time. */
   459         -      nOp++;
   460         -      if( commitInterval>0 && (nOp%commitInterval)==0 ){
   461         -        sqlite3_exec(db, "COMMIT; BEGIN IMMEDIATE", 0, 0, 0);
          541  +    }
          542  +    sqlite3_exec(db, "COMMIT", 0, 0, 0);
          543  +    sqlite3_finalize(pInsert);  pInsert = 0;
          544  +    sqlite3_finalize(pUpdate);  pUpdate = 0;
          545  +    sqlite3_finalize(pSelect);  pSelect = 0;
          546  +    sqlite3_finalize(pDelete);  pDelete = 0;
          547  +  
          548  +    if( iMode2==MODE_QUERY && iMode!=MODE_ALL ){
          549  +      printf("%s sum of cnt: %lld\n", zTag, sumCnt);
          550  +      rc = sqlite3_prepare_v2(db,"SELECT sum(cnt*cnt) FROM wordcount", -1,
          551  +                              &pSelect, 0);
          552  +      if( rc==SQLITE_OK && sqlite3_step(pSelect)==SQLITE_ROW ){
          553  +        printf("%s double-check: %lld\n", zTag,sqlite3_column_int64(pSelect,0));
          554  +      }
          555  +      sqlite3_finalize(pSelect);
          556  +    }
          557  +  
          558  +  
          559  +    if( showTimer ){
          560  +      sqlite3_int64 elapseTime = realTime() - startTime;
          561  +      totalTime += elapseTime;
          562  +      fprintf(pTimer, "%3d.%03d wordcount", (int)(elapseTime/1000),
          563  +                                   (int)(elapseTime%1000));
          564  +      if( iMode==MODE_ALL ){
          565  +        fprintf(pTimer, " %s%s\n", azMode[iMode2],
          566  +                useWithoutRowid? " --without-rowid" : "");
          567  +      }else{
          568  +        for(i=1; i<argc; i++) if( i!=showTimer ) fprintf(pTimer," %s",argv[i]);
          569  +        fprintf(pTimer, "\n");
   462    570         }
   463    571       }
   464         -  }
   465         -  sqlite3_exec(db, "COMMIT", 0, 0, 0);
   466         -  if( zFileToRead ) fclose(in);
   467         -  sqlite3_finalize(pInsert);
   468         -  sqlite3_finalize(pUpdate);
   469         -  sqlite3_finalize(pSelect);
   470         -  sqlite3_finalize(pDelete);
   471         -
   472         -  if( iMode==MODE_QUERY ){
   473         -    printf("%s sum of cnt: %lld\n", zTag, sumCnt);
   474         -    rc = sqlite3_prepare_v2(db,"SELECT sum(cnt*cnt) FROM wordcount", -1,
   475         -                            &pSelect, 0);
   476         -    if( rc==SQLITE_OK && sqlite3_step(pSelect)==SQLITE_ROW ){
   477         -      printf("%s double-check: %lld\n", zTag, sqlite3_column_int64(pSelect, 0));
          572  +  
          573  +    if( showSummary ){
          574  +      sqlite3_create_function(db, "checksum", -1, SQLITE_UTF8, 0,
          575  +                              0, checksumStep, checksumFinalize);
          576  +      sqlite3_exec(db, 
          577  +        "SELECT 'count(*):  ', count(*) FROM wordcount;\n"
          578  +        "SELECT 'sum(cnt):  ', sum(cnt) FROM wordcount;\n"
          579  +        "SELECT 'max(cnt):  ', max(cnt) FROM wordcount;\n"
          580  +        "SELECT 'avg(cnt):  ', avg(cnt) FROM wordcount;\n"
          581  +        "SELECT 'sum(cnt=1):', sum(cnt=1) FROM wordcount;\n"
          582  +        "SELECT 'top 10:    ', group_concat(word, ', ') FROM "
          583  +           "(SELECT word FROM wordcount ORDER BY cnt DESC, word LIMIT 10);\n"
          584  +        "SELECT 'checksum:  ', checksum(word, cnt) FROM "
          585  +           "(SELECT word, cnt FROM wordcount ORDER BY word);\n"
          586  +        "PRAGMA integrity_check;\n",
          587  +        printResult, 0, 0);
   478    588       }
   479         -    sqlite3_finalize(pSelect);
   480         -  }
          589  +  } /* End the --all loop */
   481    590   
          591  +  /* Close the input file after the last read */
          592  +  if( zFileToRead ) fclose(in);
   482    593   
   483         -  if( showTimer ){
   484         -    sqlite3_int64 elapseTime = realTime() - startTime;
   485         -    fprintf(pTimer, "%3d.%03d wordcount", (int)(elapseTime/1000),
   486         -                                   (int)(elapseTime%1000));
   487         -    for(i=1; i<argc; i++) if( i!=showTimer ) fprintf(pTimer, " %s", argv[i]);
   488         -    fprintf(pTimer, "\n");
          594  +  /* In --all mode, so the total time */
          595  +  if( iMode==MODE_ALL && showTimer ){
          596  +    fprintf(pTimer, "%3d.%03d wordcount --all\n", (int)(totalTime/1000),
          597  +                                   (int)(totalTime%1000));
   489    598     }
   490         -
   491         -  if( showSummary ){
   492         -    sqlite3_create_function(db, "checksum", -1, SQLITE_UTF8, 0,
   493         -                            0, checksumStep, checksumFinalize);
   494         -    sqlite3_exec(db, 
   495         -      "SELECT 'count(*):  ', count(*) FROM wordcount;\n"
   496         -      "SELECT 'sum(cnt):  ', sum(cnt) FROM wordcount;\n"
   497         -      "SELECT 'max(cnt):  ', max(cnt) FROM wordcount;\n"
   498         -      "SELECT 'avg(cnt):  ', avg(cnt) FROM wordcount;\n"
   499         -      "SELECT 'sum(cnt=1):', sum(cnt=1) FROM wordcount;\n"
   500         -      "SELECT 'top 10:    ', group_concat(word, ', ') FROM "
   501         -         "(SELECT word FROM wordcount ORDER BY cnt DESC, word LIMIT 10);\n"
   502         -      "SELECT 'checksum:  ', checksum(word, cnt) FROM "
   503         -         "(SELECT word, cnt FROM wordcount ORDER BY word);\n"
   504         -      "PRAGMA integrity_check;\n",
   505         -      printResult, 0, 0);
   506         -  }
   507         -
          599  +  
   508    600     /* Database connection statistics printed after both prepared statements
   509    601     ** have been finalized */
   510    602     if( showStats ){
   511    603       sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_USED, &iCur, &iHiwtr, 0);
   512    604       printf("%s Lookaside Slots Used:        %d (max %d)\n", zTag, iCur,iHiwtr);
   513    605       sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_HIT, &iCur, &iHiwtr, 0);
   514    606       printf("%s Successful lookasides:       %d\n", zTag, iHiwtr);

Changes to tool/speed-check.sh.

    19     19     echo "Usage: $0 OUTPUTFILE [OPTIONS]"
    20     20     exit
    21     21   fi
    22     22   NAME=$1
    23     23   shift
    24     24   #CC_OPTS="-DSQLITE_ENABLE_RTREE -DSQLITE_ENABLE_MEMSYS5"
    25     25   CC_OPTS="-DSQLITE_ENABLE_MEMSYS5"
           26  +CC=gcc
    26     27   SPEEDTEST_OPTS="--shrink-memory --reprepare --stats --heap 10000000 64"
    27     28   SIZE=5
    28     29   LEAN_OPTS="-DSQLITE_THREADSAFE=0"
    29     30   LEAN_OPTS="$LEAN_OPTS -DSQLITE_DEFAULT_MEMSTATUS=0"
    30     31   LEAN_OPTS="$LEAN_OPTS -DSQLITE_DEFAULT_WAL_SYNCHRONOUS=1"
    31     32   LEAN_OPTS="$LEAN_OPTS -DSQLITE_LIKE_DOESNT_MATCH_BLOB"
    32     33   LEAN_OPTS="$LEAN_OPTS -DSQLITE_MAX_EXPR_DEPTH=0"
................................................................................
    76     77           rm -f vdbe_profile.out
    77     78           CC_OPTS="$CC_OPTS -DVDBE_PROFILE"
    78     79           doCachegrind=0
    79     80           ;;
    80     81       --lean)
    81     82           CC_OPTS="$CC_OPTS $LEAN_OPTS"
    82     83           ;;
           84  +    --clang)
           85  +        CC=clang
           86  +        ;;
    83     87       --heap)
    84     88           CC_OPTS="$CC_OPTS -DSQLITE_ENABLE_MEMSYS5"
    85     89           shift;
    86     90           SPEEDTEST_OPTS="$SPEEDTEST_OPTS --heap $1 64"
           91  +        ;;
           92  +    --lookaside)
           93  +        shift;
           94  +        SPEEDTEST_OPTS="$SPEEDTEST_OPTS --lookaside $1 $2"
           95  +        shift;
    87     96           ;;
    88     97       --repeat)
    89     98           CC_OPTS="$CC_OPTS -DSQLITE_ENABLE_RCACHE"
    90     99           shift;
    91    100           SPEEDTEST_OPTS="$SPEEDTEST_OPTS --repeat $1"
    92    101           ;;
    93    102       --mmap)
    94    103           shift;
    95    104           SPEEDTEST_OPTS="$SPEEDTEST_OPTS --mmap $1"
    96    105           ;;
          106  +    --rtree)
          107  +        SPEEDTEST_OPTS="$SPEEDTEST_OPTS --testset rtree"
          108  +        CC_OPTS="$CC_OPTS -DSQLITE_ENABLE_RTREE"
          109  +        ;;
    97    110       *)
    98    111           CC_OPTS="$CC_OPTS $1"
    99    112           ;;
   100    113     esac
   101    114     shift
   102    115   done
   103    116   SPEEDTEST_OPTS="$SPEEDTEST_OPTS --size $SIZE"
   104    117   echo "NAME           = $NAME" | tee summary-$NAME.txt
   105    118   echo "SPEEDTEST_OPTS = $SPEEDTEST_OPTS" | tee -a summary-$NAME.txt
   106    119   echo "CC_OPTS        = $CC_OPTS" | tee -a summary-$NAME.txt
   107    120   rm -f cachegrind.out.* speedtest1 speedtest1.db sqlite3.o
   108         -gcc -g -Os -Wall -I. $CC_OPTS -c sqlite3.c
          121  +$CC -g -Os -Wall -I. $CC_OPTS -c sqlite3.c
   109    122   size sqlite3.o | tee -a summary-$NAME.txt
   110    123   if test $doExplain -eq 1; then
   111         -  gcc -g -Os -Wall -I. $CC_OPTS \
          124  +  $CC -g -Os -Wall -I. $CC_OPTS \
   112    125        -DSQLITE_ENABLE_EXPLAIN_COMMENTS \
   113    126       ./shell.c ./sqlite3.c -o sqlite3 -ldl -lpthread
   114    127   fi
   115    128   SRC=./speedtest1.c
   116         -gcc -g -Os -Wall -I. $CC_OPTS $SRC ./sqlite3.o -o speedtest1 -ldl -lpthread
          129  +$CC -g -Os -Wall -I. $CC_OPTS $SRC ./sqlite3.o -o speedtest1 -ldl -lpthread
   117    130   ls -l speedtest1 | tee -a summary-$NAME.txt
   118    131   if test $doCachegrind -eq 1; then
   119    132     valgrind --tool=cachegrind ./speedtest1 speedtest1.db \
   120    133         $SPEEDTEST_OPTS 2>&1 | tee -a summary-$NAME.txt
   121    134   else
   122    135     ./speedtest1 speedtest1.db $SPEEDTEST_OPTS 2>&1 | tee -a summary-$NAME.txt
   123    136   fi