Compare commits
265 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 4a0baed049 | |||
| f736acd40c | |||
| d276b00554 | |||
| fd9a916c4a | |||
| 4ec163f7ae | |||
| 6c3e64e653 | |||
| 87f1670de8 | |||
| e68ffadbf4 | |||
| 9f908122af | |||
| 2e2bc60300 | |||
| d9cad97389 | |||
| 7f837b66fa | |||
| 241676abcc | |||
| c0905baac8 | |||
| 5facffbc70 | |||
| fda0867873 | |||
| 563d3242d7 | |||
| 4f46b58a2d | |||
| d6ec7a6ab3 | |||
| 2707b56334 | |||
| 86a1bf4815 | |||
| d98b4b24f2 | |||
| 92c01308cc | |||
| c0ec2f7762 | |||
| 8d3e15eec4 | |||
| 4f4e49a98b | |||
| 2e178d7321 | |||
| cc6cece39a | |||
| 92c7c98ac4 | |||
| b0e7fff492 | |||
| 7436f1e491 | |||
| 3993678d3d | |||
| cc398969e0 | |||
| b0b6f8783c | |||
| 57a93fa38c | |||
| a15a7c352c | |||
| ccc9acc059 | |||
| 57f29b7bfb | |||
| cf7c8370d1 | |||
| 136102beda | |||
| 57e3ba7623 | |||
| 62856465f2 | |||
| 26f625fbf4 | |||
| cbce846ea5 | |||
| c65faba468 | |||
| a224ee2a1b | |||
| e28eb64d09 | |||
| 091881bbb0 | |||
| a88b05361c | |||
| aac12cb868 | |||
| 19e6b8f496 | |||
| c551550808 | |||
| 713f34ace9 | |||
| 21f433e821 | |||
| 6d7ec6a1d0 | |||
| 4e8f3bbd95 | |||
| f4bc6c43d7 | |||
| 46e835a2c4 | |||
| 501ea05630 | |||
| ee269a60c9 | |||
| d9274a8ae3 | |||
| 0fae06fcb6 | |||
| 4e6e5cef6c | |||
| e2d27e0259 | |||
| 74a2e48329 | |||
| 2d29881283 | |||
| 109346f437 | |||
| a9abfb1e6c | |||
| 3f9402e115 | |||
| 4d1c6845ff | |||
| 715fc13296 | |||
| 522bb74ae1 | |||
| d446e79545 | |||
| e84c498be1 | |||
| c083cb4422 | |||
| 35043cc32a | |||
| 764d56b564 | |||
| 1db7db1f03 | |||
| 00c3ef2df9 | |||
| b3f58b8b30 | |||
| 087529aae4 | |||
| c86d82f27d | |||
| f313952097 | |||
| 510fea885e | |||
| 91347c066b | |||
| 54cfb492b7 | |||
| 2a86110a6c | |||
| b189e4101c | |||
| eab0e10304 | |||
| fa68815fa3 | |||
| bc6b8d7359 | |||
| 435666e26d | |||
| 561158937b | |||
| d1317095b5 | |||
| 60d72b9bab | |||
| 4b18c1d53a | |||
| 97f9059eee | |||
| 001f52ed7d | |||
| 3944cf8de3 | |||
| 1dff328119 | |||
| 668845bb0b | |||
| 15daa6b53e | |||
| 563ddbe54d | |||
| c3ef23a1c9 | |||
| 06b3bd5b7a | |||
| f8c3a2f3cf | |||
| cfaffad65c | |||
| 44091ed368 | |||
| 5cd253423b | |||
| 4ea48144f9 | |||
| 04a28c3b6d | |||
| 099fa84727 | |||
| 2f7260deba | |||
| fdcd9d4e6c | |||
| ea4125bbef | |||
| f8c4b99a02 | |||
| 8433e7166b | |||
| 26e731cc88 | |||
| a07aa8d397 | |||
| 26333ee3ca | |||
| 1822ebf9b1 | |||
| c9f3db33d5 | |||
| 33f10207aa | |||
| c86caa58cd | |||
| 33f763d154 | |||
| 8005d60587 | |||
| 4eb57ceffc | |||
| 8558ef2e19 | |||
| cad42838d7 | |||
| 9f8952390a | |||
| 1a0e5b37b2 | |||
| da6bc6792f | |||
| fe875027d7 | |||
| a8519d79b9 | |||
| 4d6d872c49 | |||
| a87f8ce262 | |||
| b9f4799b55 | |||
| 93117f0c4b | |||
| 9ccc0fd1f9 | |||
| 0aac5613d9 | |||
| 56f1774603 | |||
| 5347f3c111 | |||
| 588049cc99 | |||
| 21d5978422 | |||
| d15046ac08 | |||
| a916b57013 | |||
| 61d04974f0 | |||
| b8fff29c68 | |||
| 8d7f163015 | |||
| 176b3a09b2 | |||
| 7ea3469e53 | |||
| f09ac0b336 | |||
| fa3d785580 | |||
| b71aa0955b | |||
| 138d4f8de2 | |||
| 8bfe66a9c4 | |||
| 3a9b9b7749 | |||
| 88284b0dc3 | |||
| 2f94935409 | |||
| 1a3a308616 | |||
| 5a7da86f5b | |||
| 80db2d6521 | |||
| b8a0fb75db | |||
| cae5b9feac | |||
| e3ca3831ba | |||
| 4b3931ef33 | |||
| d1cccf19b5 | |||
| 1611e5a301 | |||
| 3dc9727782 | |||
| 3739f29807 | |||
| 61c758b53a | |||
| 26893c98d2 | |||
| b968518559 | |||
| f193937620 | |||
| 30fe26c47f | |||
| 98e2cb8bd1 | |||
| 5685257b83 | |||
| 824f28426a | |||
| 2879952faa | |||
| 8c9e30ba2f | |||
| 2d9e8c55da | |||
| 4a4532bbb7 | |||
| 4bd387495f | |||
| eb0b6f364e | |||
| 70bc717c0e | |||
| 0ed2fd8a25 | |||
| fff5367c24 | |||
| 194a17bbb7 | |||
| 0c2ba13e02 | |||
| ded2d99d73 | |||
| 2d620070b9 | |||
| 89fa746941 | |||
| a9be508a97 | |||
| b058d05452 | |||
| eb54500419 | |||
| f42884c307 | |||
| cdb60978b9 | |||
| 098728fc9c | |||
| 2483a111db | |||
| 69aedc8db4 | |||
| 2034353db4 | |||
| 76506cd3a7 | |||
| 9df81a2989 | |||
| 41fb367a2c | |||
| ce2fbd1b02 | |||
| 4ec6f3a075 | |||
| 5871318407 | |||
| 84ebe2b303 | |||
| 3f975373ce | |||
| f3e3dfe96c | |||
| 614efe2b4b | |||
| 6ac7303e1a | |||
| f225059b8b | |||
| afd4eef575 | |||
| 66a3a91aa6 | |||
| 6f390beb7f | |||
| 5e9bbe1924 | |||
| e4185bda9a | |||
| 24cd20ffa4 | |||
| 536c345107 | |||
| 9791313474 | |||
| df53b05e3c | |||
| 6c9dcc427d | |||
| 3c484e8c1f | |||
| a92a01a77e | |||
| 7f3bf8a9fb | |||
| 13c209330d | |||
| cc9c26a092 | |||
| d99c7b7bcb | |||
| ca7733b782 | |||
| e15c5e532a | |||
| 346606494a | |||
| 4bfd182939 | |||
| 410cad975f | |||
| 634c70fa15 | |||
| f2ed70e4de | |||
| 6c237b1fa7 | |||
| a5676c4d2d | |||
| a82c95b47d | |||
| e75d1f5290 | |||
| b376b3d6aa | |||
| a688ca5ea9 | |||
| 5af0698356 | |||
| 6116ee4eee | |||
| dc006e05aa | |||
| 7026bd6753 | |||
| 2c4df97591 | |||
| 9898c4a0c4 | |||
| c48e0271f6 | |||
| e2d22ffaa3 | |||
| 4297584d66 | |||
| 6b046be41a | |||
| f87ae41f52 | |||
| 8ee5d0fc05 | |||
| 128011a258 | |||
| cc234a4b66 | |||
| a8691309dd | |||
| 562f0c8e46 | |||
| 88a1d6b92c | |||
| 7c15ac1ada | |||
| d4bb7c180b | |||
| 4064a4cc58 | |||
| 1bc1e2fb5d | |||
| dcfbff9a86 | |||
| 98dfb2fc08 |
+3
-1
@@ -579,7 +579,8 @@ TESTOPTS = --verbose=file --output=test-out.txt
|
||||
# Extra compiler options for various shell tools
|
||||
#
|
||||
SHELL_OPT = -DSQLITE_ENABLE_JSON1 -DSQLITE_ENABLE_FTS4
|
||||
# SHELL_OPT += -DSQLITE_ENABLE_FTS5
|
||||
#SHELL_OPT += -DSQLITE_ENABLE_FTS5
|
||||
SHELL_OPT += -DSQLITE_ENABLE_RTREE
|
||||
SHELL_OPT += -DSQLITE_ENABLE_EXPLAIN_COMMENTS
|
||||
SHELL_OPT += -DSQLITE_ENABLE_UNKNOWN_SQL_FUNCTION
|
||||
SHELL_OPT += -DSQLITE_ENABLE_STMTVTAB
|
||||
@@ -590,6 +591,7 @@ SHELL_OPT += -DSQLITE_INTROSPECTION_PRAGMAS
|
||||
FUZZERSHELL_OPT = -DSQLITE_ENABLE_JSON1
|
||||
FUZZCHECK_OPT = -DSQLITE_ENABLE_JSON1 -DSQLITE_ENABLE_MEMSYS5 -DSQLITE_OSS_FUZZ
|
||||
FUZZCHECK_OPT += -DSQLITE_MAX_MEMORY=50000000
|
||||
FUZZCHECK_OPT += -DSQLITE_PRINTF_PRECISION_LIMIT=1000
|
||||
FUZZCHECK_SRC = $(TOP)/test/fuzzcheck.c $(TOP)/test/ossfuzz.c
|
||||
DBFUZZ_OPT =
|
||||
|
||||
|
||||
+5
-2
@@ -1494,6 +1494,7 @@ TESTEXT = \
|
||||
$(TOP)\ext\misc\eval.c \
|
||||
$(TOP)\ext\misc\fileio.c \
|
||||
$(TOP)\ext\misc\fuzzer.c \
|
||||
$(TOP)\ext\zonefile\zonefile.c \
|
||||
$(TOP)\ext\fts5\fts5_tcl.c \
|
||||
$(TOP)\ext\fts5\fts5_test_mi.c \
|
||||
$(TOP)\ext\fts5\fts5_test_tok.c \
|
||||
@@ -1607,6 +1608,7 @@ FUZZDATA = \
|
||||
SHELL_COMPILE_OPTS = $(SHELL_COMPILE_OPTS) -DSQLITE_ENABLE_JSON1 -DSQLITE_ENABLE_FTS4 -DSQLITE_ENABLE_EXPLAIN_COMMENTS -DSQLITE_ENABLE_STMTVTAB
|
||||
SHELL_COMPILE_OPTS = $(SHELL_COMPILE_OPTS) -DSQLITE_ENABLE_DBPAGE_VTAB -DSQLITE_ENABLE_DBSTAT_VTAB
|
||||
SHELL_COMPILE_OPTS = $(SHELL_COMPILE_OPTS) -DSQLITE_ENABLE_OFFSET_SQL_FUNC -DSQLITE_INTROSPECTION_PRAGMAS
|
||||
SHELL_COMPILE_OPTS = $(SHELL_COMPILE_OPTS) -DSQLITE_ENABLE_RTREE
|
||||
!ENDIF
|
||||
|
||||
# <<mark>>
|
||||
@@ -1614,7 +1616,7 @@ SHELL_COMPILE_OPTS = $(SHELL_COMPILE_OPTS) -DSQLITE_ENABLE_OFFSET_SQL_FUNC -DSQL
|
||||
#
|
||||
MPTESTER_COMPILE_OPTS = -DSQLITE_ENABLE_JSON1 -DSQLITE_ENABLE_FTS5
|
||||
FUZZERSHELL_COMPILE_OPTS = -DSQLITE_ENABLE_JSON1
|
||||
FUZZCHECK_COMPILE_OPTS = -DSQLITE_ENABLE_JSON1 -DSQLITE_ENABLE_MEMSYS5 -DSQLITE_OSS_FUZZ -DSQLITE_MAX_MEMORY=50000000
|
||||
FUZZCHECK_COMPILE_OPTS = -DSQLITE_ENABLE_JSON1 -DSQLITE_ENABLE_MEMSYS5 -DSQLITE_OSS_FUZZ -DSQLITE_MAX_MEMORY=50000000 -DSQLITE_PRINTF_PRECISION_LIMIT=1000
|
||||
FUZZCHECK_SRC = $(TOP)\test\fuzzcheck.c $(TOP)\test\ossfuzz.c
|
||||
OSSSHELL_SRC = $(TOP)\test\ossshell.c $(TOP)\test\ossfuzz.c
|
||||
DBFUZZ_COMPILE_OPTS = -DSQLITE_THREADSAFE=0 -DSQLITE_OMIT_LOAD_EXTENSION
|
||||
@@ -2251,6 +2253,7 @@ TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) -DSQLITE_SERIES_CONSTRAINT_VERIFY=1
|
||||
TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) -DSQLITE_DEFAULT_PAGE_SIZE=1024
|
||||
TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) -DSQLITE_ENABLE_STMTVTAB
|
||||
TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) -DSQLITE_ENABLE_DBPAGE_VTAB
|
||||
TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) -DSQLITE_ENABLE_JSON1
|
||||
TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) $(TEST_CCONV_OPTS)
|
||||
|
||||
TESTFIXTURE_SRC0 = $(TESTEXT) $(TESTSRC2)
|
||||
@@ -2340,7 +2343,7 @@ sqlite3_analyzer.exe: sqlite3_analyzer.c $(LIBRESOBJS)
|
||||
sqltclsh.c: sqlite3.c $(TOP)\src\tclsqlite.c $(TOP)\tool\sqltclsh.tcl $(TOP)\ext\misc\appendvfs.c $(TOP)\tool\mkccode.tcl $(TOP)\tool\sqltclsh.c.in
|
||||
$(TCLSH_CMD) $(TOP)\tool\mkccode.tcl $(TOP)\tool\sqltclsh.c.in >sqltclsh.c
|
||||
|
||||
sqltclsh.exe: sqltclsh.c
|
||||
sqltclsh.exe: sqltclsh.c $(SHELL_CORE_DEP) $(LIBRESOBJS)
|
||||
$(LTLINK) $(NO_WARN) -DBUILD_sqlite -I$(TCLINCDIR) sqltclsh.c \
|
||||
/link $(LDFLAGS) $(LTLINKOPTS) $(TCLLIBPATHS) $(LTLIBPATHS) $(LIBRESOBJS) $(TCLLIBS) $(LTLIBS) $(TLIBS)
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<h1 align="center">SQLite Source Repository</h1>
|
||||
|
||||
This repository contains the complete source code for the SQLite database
|
||||
engine. Some test scripts are also include. However, many other test scripts
|
||||
engine. Some test scripts are also included. However, many other test scripts
|
||||
and most of the documentation are managed separately.
|
||||
|
||||
If you are reading this on a Git mirror someplace, you are doing it wrong.
|
||||
@@ -14,15 +14,17 @@ SQLite sources are managed using the
|
||||
[Fossil](https://www.fossil-scm.org/), a distributed version control system
|
||||
that was specifically designed to support SQLite development.
|
||||
If you do not want to use Fossil, you can download tarballs or ZIP
|
||||
archives as follows:
|
||||
archives or [SQLite archives](https://sqlite.org/cli.html#sqlar) as follows:
|
||||
|
||||
* Lastest trunk check-in:
|
||||
<https://www.sqlite.org/src/tarball/sqlite.tar.gz> or
|
||||
<https://www.sqlite.org/src/zip/sqlite.zip>.
|
||||
* Lastest trunk check-in as
|
||||
[Tarball](https://www.sqlite.org/src/tarball/sqlite.tar.gz),
|
||||
[ZIP-archive](https://www.sqlite.org/src/zip/sqlite.zip), or
|
||||
[SQLite-archive](https://www.sqlite.org/src/sqlar/sqlite.sqlar).
|
||||
|
||||
* Latest release:
|
||||
<https://www.sqlite.org/src/tarball/sqlite.tar.gz?r=release> or
|
||||
<https://www.sqlite.org/src/zip/sqlite.zip?r=release>.
|
||||
* Latest release as
|
||||
[Tarball](https://www.sqlite.org/src/tarball/sqlite.tar.gz?r=release),
|
||||
[ZIP-archive](https://www.sqlite.org/src/zip/sqlite.zip?r=release), or
|
||||
[SQLite-archive](https://www.sqlite.org/src/sqlar/sqlite.sqlar?r=release).
|
||||
|
||||
* For other check-ins, substitute an appropriate branch name or
|
||||
tag or hash prefix for "release" in the URLs of the previous
|
||||
@@ -104,7 +106,6 @@ recommended.
|
||||
SQLite does not require [Tcl](http://www.tcl.tk/) to run, but a Tcl installation
|
||||
is required by the makefiles (including those for MSVC). SQLite contains
|
||||
a lot of generated code and Tcl is used to do much of that code generation.
|
||||
The makefiles also require AWK.
|
||||
|
||||
## Source Code Tour
|
||||
|
||||
@@ -116,7 +117,7 @@ The **src/** also contains the "shell.c" file
|
||||
which is the main program for the "sqlite3.exe"
|
||||
[command-line shell](https://sqlite.org/cli.html) and
|
||||
the "tclsqlite.c" file which implements the
|
||||
[TCL bindings](https://sqlite.org/tclsqlite.html) for SQLite.
|
||||
[Tcl bindings](https://sqlite.org/tclsqlite.html) for SQLite.
|
||||
(Historical note: SQLite began as a Tcl
|
||||
extension and only later escaped to the wild as an independent library.)
|
||||
|
||||
@@ -163,14 +164,14 @@ template for generating its parser.
|
||||
|
||||
Lemon also generates the **parse.h** header file, at the same time it
|
||||
generates parse.c. But the parse.h header file is
|
||||
modified further (to add additional symbols) using the ./addopcodes.awk
|
||||
AWK script.
|
||||
modified further (to add additional symbols) using the ./addopcodes.tcl
|
||||
Tcl script.
|
||||
|
||||
The **opcodes.h** header file contains macros that define the numbers
|
||||
corresponding to opcodes in the "VDBE" virtual machine. The opcodes.h
|
||||
file is generated by the scanning the src/vdbe.c source file. The
|
||||
AWK script at ./mkopcodeh.awk does this scan and generates opcodes.h.
|
||||
A second AWK script, ./mkopcodec.awk, then scans opcodes.h to generate
|
||||
Tcl script at ./mkopcodeh.tcl does this scan and generates opcodes.h.
|
||||
A second Tcl script, ./mkopcodec.tcl, then scans opcodes.h to generate
|
||||
the **opcodes.c** source file, which contains a reverse mapping from
|
||||
opcode-number to opcode-name that is used for EXPLAIN output.
|
||||
|
||||
@@ -280,7 +281,7 @@ Key files:
|
||||
|
||||
* **test*.c** - Files in the src/ folder that begin with "test" go into
|
||||
building the "testfixture.exe" program. The testfixture.exe program is
|
||||
an enhanced TCL shell. The testfixture.exe program runs scripts in the
|
||||
an enhanced Tcl shell. The testfixture.exe program runs scripts in the
|
||||
test/ folder to validate the core SQLite code. The testfixture program
|
||||
(and some other test programs too) is build and run when you type
|
||||
"make test".
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
|
||||
AM_CFLAGS = @THREADSAFE_FLAGS@ @DYNAMIC_EXTENSION_FLAGS@ @FTS5_FLAGS@ @JSON1_FLAGS@ @SESSION_FLAGS@ -DSQLITE_ENABLE_FTS3 -DSQLITE_ENABLE_RTREE
|
||||
AM_CFLAGS = @THREADSAFE_FLAGS@ @DYNAMIC_EXTENSION_FLAGS@ @FTS5_FLAGS@ @JSON1_FLAGS@ @ZLIB_FLAGS@ @SESSION_FLAGS@ -DSQLITE_ENABLE_FTS3 -DSQLITE_ENABLE_RTREE
|
||||
|
||||
lib_LTLIBRARIES = libsqlite3.la
|
||||
libsqlite3_la_SOURCES = sqlite3.c
|
||||
@@ -10,7 +10,7 @@ sqlite3_SOURCES = shell.c sqlite3.h
|
||||
EXTRA_sqlite3_SOURCES = sqlite3.c
|
||||
sqlite3_LDADD = @EXTRA_SHELL_OBJ@ @READLINE_LIBS@
|
||||
sqlite3_DEPENDENCIES = @EXTRA_SHELL_OBJ@
|
||||
sqlite3_CFLAGS = $(AM_CFLAGS) -DSQLITE_ENABLE_EXPLAIN_COMMENTS -DSQLITE_ENABLE_DBPAGE_VTAB -DSQLITE_ENABLE_STMTVTAB -DSQLITE_ENABLE_DBSTAT_VTAB
|
||||
sqlite3_CFLAGS = $(AM_CFLAGS) -DSQLITE_ENABLE_EXPLAIN_COMMENTS -DSQLITE_ENABLE_DBPAGE_VTAB -DSQLITE_ENABLE_STMTVTAB -DSQLITE_ENABLE_DBSTAT_VTAB $(SHELL_CFLAGS)
|
||||
|
||||
include_HEADERS = sqlite3.h sqlite3ext.h
|
||||
|
||||
|
||||
@@ -164,6 +164,13 @@ AC_SUBST(EXTRA_SHELL_OBJ)
|
||||
#-----------------------------------------------------------------------
|
||||
|
||||
AC_CHECK_FUNCS(posix_fallocate)
|
||||
AC_CHECK_HEADERS(zlib.h,[
|
||||
AC_SEARCH_LIBS(deflate,z,[ZLIB_FLAGS="-DSQLITE_HAVE_ZLIB"])
|
||||
])
|
||||
AC_SUBST(ZLIB_FLAGS)
|
||||
|
||||
AC_SEARCH_LIBS(system,,,[SHELL_CFLAGS="-DSQLITE_NOHAVE_SYSTEM"])
|
||||
AC_SUBST(SHELL_CFLAGS)
|
||||
|
||||
#-----------------------------------------------------------------------
|
||||
# UPDATE: Maybe it's better if users just set CFLAGS before invoking
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#! /bin/sh
|
||||
# Guess values for system-dependent variables and create Makefiles.
|
||||
# Generated by GNU Autoconf 2.69 for sqlite 3.22.0.
|
||||
# Generated by GNU Autoconf 2.69 for sqlite 3.23.0.
|
||||
#
|
||||
#
|
||||
# Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc.
|
||||
@@ -726,8 +726,8 @@ MAKEFLAGS=
|
||||
# Identity of this package.
|
||||
PACKAGE_NAME='sqlite'
|
||||
PACKAGE_TARNAME='sqlite'
|
||||
PACKAGE_VERSION='3.22.0'
|
||||
PACKAGE_STRING='sqlite 3.22.0'
|
||||
PACKAGE_VERSION='3.23.0'
|
||||
PACKAGE_STRING='sqlite 3.23.0'
|
||||
PACKAGE_BUGREPORT=''
|
||||
PACKAGE_URL=''
|
||||
|
||||
@@ -1465,7 +1465,7 @@ if test "$ac_init_help" = "long"; then
|
||||
# Omit some internal or obsolete options to make the list less imposing.
|
||||
# This message is too long to be a string in the A/UX 3.1 sh.
|
||||
cat <<_ACEOF
|
||||
\`configure' configures sqlite 3.22.0 to adapt to many kinds of systems.
|
||||
\`configure' configures sqlite 3.23.0 to adapt to many kinds of systems.
|
||||
|
||||
Usage: $0 [OPTION]... [VAR=VALUE]...
|
||||
|
||||
@@ -1530,7 +1530,7 @@ fi
|
||||
|
||||
if test -n "$ac_init_help"; then
|
||||
case $ac_init_help in
|
||||
short | recursive ) echo "Configuration of sqlite 3.22.0:";;
|
||||
short | recursive ) echo "Configuration of sqlite 3.23.0:";;
|
||||
esac
|
||||
cat <<\_ACEOF
|
||||
|
||||
@@ -1655,7 +1655,7 @@ fi
|
||||
test -n "$ac_init_help" && exit $ac_status
|
||||
if $ac_init_version; then
|
||||
cat <<\_ACEOF
|
||||
sqlite configure 3.22.0
|
||||
sqlite configure 3.23.0
|
||||
generated by GNU Autoconf 2.69
|
||||
|
||||
Copyright (C) 2012 Free Software Foundation, Inc.
|
||||
@@ -2074,7 +2074,7 @@ cat >config.log <<_ACEOF
|
||||
This file contains any messages produced by compilers while
|
||||
running configure, to aid debugging if configure makes a mistake.
|
||||
|
||||
It was created by sqlite $as_me 3.22.0, which was
|
||||
It was created by sqlite $as_me 3.23.0, which was
|
||||
generated by GNU Autoconf 2.69. Invocation command line was
|
||||
|
||||
$ $0 $@
|
||||
@@ -12242,7 +12242,7 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
|
||||
# report actual input values of CONFIG_FILES etc. instead of their
|
||||
# values after options handling.
|
||||
ac_log="
|
||||
This file was extended by sqlite $as_me 3.22.0, which was
|
||||
This file was extended by sqlite $as_me 3.23.0, which was
|
||||
generated by GNU Autoconf 2.69. Invocation command line was
|
||||
|
||||
CONFIG_FILES = $CONFIG_FILES
|
||||
@@ -12308,7 +12308,7 @@ _ACEOF
|
||||
cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
|
||||
ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"
|
||||
ac_cs_version="\\
|
||||
sqlite config.status 3.22.0
|
||||
sqlite config.status 3.23.0
|
||||
configured by $0, generated by GNU Autoconf 2.69,
|
||||
with options \\"\$ac_cs_config\\"
|
||||
|
||||
|
||||
@@ -23,6 +23,11 @@ if {![info exists testdir]} {
|
||||
source $testdir/tester.tcl
|
||||
set testprefix expert1
|
||||
|
||||
if {[info commands sqlite3_expert_new]==""} {
|
||||
finish_test
|
||||
return
|
||||
}
|
||||
|
||||
set CLI [test_binary_name sqlite3]
|
||||
set CMD [test_binary_name sqlite3_expert]
|
||||
|
||||
|
||||
@@ -15,6 +15,8 @@
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#ifndef SQLITE_OMIT_VIRTUALTABLE
|
||||
|
||||
typedef sqlite3_int64 i64;
|
||||
typedef sqlite3_uint64 u64;
|
||||
|
||||
@@ -495,7 +497,7 @@ static int expertBestIndex(sqlite3_vtab *pVtab, sqlite3_index_info *pIdxInfo){
|
||||
}
|
||||
}
|
||||
|
||||
pIdxInfo->estimatedCost = 1000000.0 / n;
|
||||
pIdxInfo->estimatedCost = 1000000.0 / (n+1);
|
||||
return rc;
|
||||
}
|
||||
|
||||
@@ -505,6 +507,10 @@ static int expertUpdate(
|
||||
sqlite3_value **azData,
|
||||
sqlite_int64 *pRowid
|
||||
){
|
||||
(void)pVtab;
|
||||
(void)nData;
|
||||
(void)azData;
|
||||
(void)pRowid;
|
||||
return SQLITE_OK;
|
||||
}
|
||||
|
||||
@@ -514,6 +520,7 @@ static int expertUpdate(
|
||||
static int expertOpen(sqlite3_vtab *pVTab, sqlite3_vtab_cursor **ppCursor){
|
||||
int rc = SQLITE_OK;
|
||||
ExpertCsr *pCsr;
|
||||
(void)pVTab;
|
||||
pCsr = idxMalloc(&rc, sizeof(ExpertCsr));
|
||||
*ppCursor = (sqlite3_vtab_cursor*)pCsr;
|
||||
return rc;
|
||||
@@ -563,6 +570,7 @@ static int expertNext(sqlite3_vtab_cursor *cur){
|
||||
** Virtual table module xRowid method.
|
||||
*/
|
||||
static int expertRowid(sqlite3_vtab_cursor *cur, sqlite_int64 *pRowid){
|
||||
(void)cur;
|
||||
*pRowid = 0;
|
||||
return SQLITE_OK;
|
||||
}
|
||||
@@ -593,6 +601,10 @@ static int expertFilter(
|
||||
sqlite3expert *pExpert = pVtab->pExpert;
|
||||
int rc;
|
||||
|
||||
(void)idxNum;
|
||||
(void)idxStr;
|
||||
(void)argc;
|
||||
(void)argv;
|
||||
rc = sqlite3_finalize(pCsr->pData);
|
||||
pCsr->pData = 0;
|
||||
if( rc==SQLITE_OK ){
|
||||
@@ -754,7 +766,7 @@ static char *idxAppendText(int *pRc, char *zIn, const char *zFmt, ...){
|
||||
zRet = (char*)sqlite3_malloc(nIn + nAppend + 1);
|
||||
}
|
||||
if( zAppend && zRet ){
|
||||
memcpy(zRet, zIn, nIn);
|
||||
if( nIn ) memcpy(zRet, zIn, nIn);
|
||||
memcpy(&zRet[nIn], zAppend, nAppend+1);
|
||||
}else{
|
||||
sqlite3_free(zRet);
|
||||
@@ -908,7 +920,7 @@ static int idxCreateFromCons(
|
||||
char *zCols = 0;
|
||||
char *zIdx = 0;
|
||||
IdxConstraint *pCons;
|
||||
int h = 0;
|
||||
unsigned int h = 0;
|
||||
const char *zFmt;
|
||||
|
||||
for(pCons=pEq; pCons; pCons=pCons->pLink){
|
||||
@@ -1003,7 +1015,7 @@ static int idxCreateFromWhere(
|
||||
** Create candidate indexes in database [dbm] based on the data in
|
||||
** linked-list pScan.
|
||||
*/
|
||||
static int idxCreateCandidates(sqlite3expert *p, char **pzErr){
|
||||
static int idxCreateCandidates(sqlite3expert *p){
|
||||
int rc = SQLITE_OK;
|
||||
IdxScan *pIter;
|
||||
|
||||
@@ -1166,6 +1178,8 @@ static int idxAuthCallback(
|
||||
const char *zTrigger
|
||||
){
|
||||
int rc = SQLITE_OK;
|
||||
(void)z4;
|
||||
(void)zTrigger;
|
||||
if( eOp==SQLITE_INSERT || eOp==SQLITE_UPDATE || eOp==SQLITE_DELETE ){
|
||||
if( sqlite3_stricmp(zDb, "main")==0 ){
|
||||
sqlite3expert *p = (sqlite3expert*)pCtx;
|
||||
@@ -1368,6 +1382,7 @@ static void idxSampleFunc(
|
||||
struct IdxSampleCtx *p = (struct IdxSampleCtx*)sqlite3_user_data(pCtx);
|
||||
int bRet;
|
||||
|
||||
(void)argv;
|
||||
assert( argc==0 );
|
||||
if( p->nRow==0.0 ){
|
||||
bRet = 1;
|
||||
@@ -1523,6 +1538,7 @@ static int idxPopulateOneStat1(
|
||||
);
|
||||
zOrder = idxAppendText(&rc, zOrder, "%s%d", zComma, ++nCol);
|
||||
}
|
||||
sqlite3_reset(pIndexXInfo);
|
||||
if( rc==SQLITE_OK ){
|
||||
if( p->iSample==100 ){
|
||||
zQuery = sqlite3_mprintf(
|
||||
@@ -1852,7 +1868,7 @@ int sqlite3_expert_analyze(sqlite3expert *p, char **pzErr){
|
||||
|
||||
/* Create candidate indexes within the in-memory database file */
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = idxCreateCandidates(p, pzErr);
|
||||
rc = idxCreateCandidates(p);
|
||||
}
|
||||
|
||||
/* Generate the stat1 data */
|
||||
@@ -1932,3 +1948,5 @@ void sqlite3_expert_destroy(sqlite3expert *p){
|
||||
sqlite3_free(p);
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* ifndef SQLITE_OMIT_VIRTUAL_TABLE */
|
||||
|
||||
@@ -26,6 +26,8 @@
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#ifndef SQLITE_OMIT_VIRTUALTABLE
|
||||
|
||||
/*
|
||||
** Extract an sqlite3* db handle from the object passed as the second
|
||||
** argument. If successful, set *pDb to point to the db handle and return
|
||||
@@ -195,7 +197,10 @@ static int SQLITE_TCLAPI test_sqlite3_expert_new(
|
||||
return rc;
|
||||
}
|
||||
|
||||
#endif /* ifndef SQLITE_OMIT_VIRTUALTABLE */
|
||||
|
||||
int TestExpert_Init(Tcl_Interp *interp){
|
||||
#ifndef SQLITE_OMIT_VIRTUALTABLE
|
||||
struct Cmd {
|
||||
const char *zCmd;
|
||||
Tcl_ObjCmdProc *xProc;
|
||||
@@ -208,7 +213,7 @@ int TestExpert_Init(Tcl_Interp *interp){
|
||||
struct Cmd *p = &aCmd[i];
|
||||
Tcl_CreateObjCommand(interp, p->zCmd, p->xProc, 0, 0);
|
||||
}
|
||||
|
||||
#endif
|
||||
return TCL_OK;
|
||||
}
|
||||
|
||||
|
||||
@@ -1908,6 +1908,7 @@ static int fts3WriteSegment(
|
||||
sqlite3_bind_blob(pStmt, 2, z, n, SQLITE_STATIC);
|
||||
sqlite3_step(pStmt);
|
||||
rc = sqlite3_reset(pStmt);
|
||||
sqlite3_bind_null(pStmt, 2);
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
@@ -1964,6 +1965,7 @@ static int fts3WriteSegdir(
|
||||
sqlite3_bind_blob(pStmt, 6, zRoot, nRoot, SQLITE_STATIC);
|
||||
sqlite3_step(pStmt);
|
||||
rc = sqlite3_reset(pStmt);
|
||||
sqlite3_bind_null(pStmt, 6);
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
@@ -3443,6 +3445,7 @@ static void fts3UpdateDocTotals(
|
||||
sqlite3_bind_blob(pStmt, 2, pBlob, nBlob, SQLITE_STATIC);
|
||||
sqlite3_step(pStmt);
|
||||
*pRC = sqlite3_reset(pStmt);
|
||||
sqlite3_bind_null(pStmt, 2);
|
||||
sqlite3_free(a);
|
||||
}
|
||||
|
||||
@@ -4631,6 +4634,7 @@ static int fts3TruncateSegment(
|
||||
sqlite3_bind_int(pChomp, 4, iIdx);
|
||||
sqlite3_step(pChomp);
|
||||
rc = sqlite3_reset(pChomp);
|
||||
sqlite3_bind_null(pChomp, 2);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4710,6 +4714,7 @@ static int fts3IncrmergeHintStore(Fts3Table *p, Blob *pHint){
|
||||
sqlite3_bind_blob(pReplace, 2, pHint->a, pHint->n, SQLITE_STATIC);
|
||||
sqlite3_step(pReplace);
|
||||
rc = sqlite3_reset(pReplace);
|
||||
sqlite3_bind_null(pReplace, 2);
|
||||
}
|
||||
|
||||
return rc;
|
||||
@@ -5524,7 +5529,6 @@ int sqlite3Fts3UpdateMethod(
|
||||
){
|
||||
Fts3Table *p = (Fts3Table *)pVtab;
|
||||
int rc = SQLITE_OK; /* Return Code */
|
||||
int isRemove = 0; /* True for an UPDATE or DELETE */
|
||||
u32 *aSzIns = 0; /* Sizes of inserted documents */
|
||||
u32 *aSzDel = 0; /* Sizes of deleted documents */
|
||||
int nChng = 0; /* Net change in number of documents */
|
||||
@@ -5622,7 +5626,6 @@ int sqlite3Fts3UpdateMethod(
|
||||
if( sqlite3_value_type(apVal[0])!=SQLITE_NULL ){
|
||||
assert( sqlite3_value_type(apVal[0])==SQLITE_INTEGER );
|
||||
rc = fts3DeleteByRowid(p, apVal[0], &nChng, aSzDel);
|
||||
isRemove = 1;
|
||||
}
|
||||
|
||||
/* If this is an INSERT or UPDATE operation, insert the new record. */
|
||||
@@ -5634,7 +5637,7 @@ int sqlite3Fts3UpdateMethod(
|
||||
rc = FTS_CORRUPT_VTAB;
|
||||
}
|
||||
}
|
||||
if( rc==SQLITE_OK && (!isRemove || *pRowid!=p->iPrevDocid ) ){
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = fts3PendingTermsDocid(p, 0, iLangid, *pRowid);
|
||||
}
|
||||
if( rc==SQLITE_OK ){
|
||||
|
||||
@@ -758,6 +758,7 @@ static void fts5DataWrite(Fts5Index *p, i64 iRowid, const u8 *pData, int nData){
|
||||
sqlite3_bind_blob(p->pWriter, 2, pData, nData, SQLITE_STATIC);
|
||||
sqlite3_step(p->pWriter);
|
||||
p->rc = sqlite3_reset(p->pWriter);
|
||||
sqlite3_bind_null(p->pWriter, 2);
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -2386,6 +2387,7 @@ static void fts5SegIterSeekInit(
|
||||
bDlidx = (val & 0x0001);
|
||||
}
|
||||
p->rc = sqlite3_reset(pIdxSelect);
|
||||
sqlite3_bind_null(pIdxSelect, 2);
|
||||
|
||||
if( iPg<pSeg->pgnoFirst ){
|
||||
iPg = pSeg->pgnoFirst;
|
||||
@@ -3598,6 +3600,7 @@ static int fts5AllocateSegid(Fts5Index *p, Fts5Structure *pStruct){
|
||||
sqlite3_bind_blob(pIdxSelect, 2, aBlob, 2, SQLITE_STATIC);
|
||||
assert( sqlite3_step(pIdxSelect)!=SQLITE_ROW );
|
||||
p->rc = sqlite3_reset(pIdxSelect);
|
||||
sqlite3_bind_null(pIdxSelect, 2);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
@@ -3724,6 +3727,7 @@ static void fts5WriteFlushBtree(Fts5Index *p, Fts5SegWriter *pWriter){
|
||||
sqlite3_bind_int64(p->pIdxWriter, 3, bFlag + ((i64)pWriter->iBtPage<<1));
|
||||
sqlite3_step(p->pIdxWriter);
|
||||
p->rc = sqlite3_reset(p->pIdxWriter);
|
||||
sqlite3_bind_null(p->pIdxWriter, 2);
|
||||
}
|
||||
pWriter->iBtPage = 0;
|
||||
}
|
||||
|
||||
@@ -458,6 +458,7 @@ static int fts5StorageInsertDocsize(
|
||||
sqlite3_bind_blob(pReplace, 2, pBuf->p, pBuf->n, SQLITE_STATIC);
|
||||
sqlite3_step(pReplace);
|
||||
rc = sqlite3_reset(pReplace);
|
||||
sqlite3_bind_null(pReplace, 2);
|
||||
}
|
||||
}
|
||||
return rc;
|
||||
@@ -1118,6 +1119,7 @@ int sqlite3Fts5StorageConfigValue(
|
||||
}
|
||||
sqlite3_step(pReplace);
|
||||
rc = sqlite3_reset(pReplace);
|
||||
sqlite3_bind_null(pReplace, 1);
|
||||
}
|
||||
if( rc==SQLITE_OK && pVal ){
|
||||
int iNew = p->pConfig->iCookie + 1;
|
||||
|
||||
+2
-2
@@ -482,7 +482,7 @@ static int SQLITE_TCLAPI xF5tApi(
|
||||
|
||||
rc = p->pApi->xPhraseFirstColumn(p->pFts, iPhrase, &iter, &iCol);
|
||||
if( rc!=SQLITE_OK ){
|
||||
Tcl_AppendResult(interp, sqlite3ErrName(rc), 0);
|
||||
Tcl_SetResult(interp, (char*)sqlite3ErrName(rc), TCL_VOLATILE);
|
||||
return TCL_ERROR;
|
||||
}
|
||||
for( ; iCol>=0; p->pApi->xPhraseNextColumn(p->pFts, &iter, &iCol)){
|
||||
@@ -924,7 +924,7 @@ static int SQLITE_TCLAPI f5tTokenizerReturn(
|
||||
|
||||
rc = p->xToken(p->pCtx, tflags, zToken, nToken, iStart, iEnd);
|
||||
Tcl_SetResult(interp, (char*)sqlite3ErrName(rc), TCL_VOLATILE);
|
||||
return TCL_OK;
|
||||
return rc==SQLITE_OK ? TCL_OK : TCL_ERROR;
|
||||
|
||||
usage:
|
||||
Tcl_WrongNumArgs(interp, 1, objv, "?-colocated? TEXT START END");
|
||||
|
||||
@@ -593,5 +593,5 @@ do_execsql_test 22.1 {
|
||||
|
||||
}
|
||||
|
||||
|
||||
expand_all_sql db
|
||||
finish_test
|
||||
|
||||
@@ -253,7 +253,7 @@ do_faultsim_test 5.2 -faults oom* -prep {
|
||||
SELECT rowid, mit(matchinfo(t1, 'x')) FROM t1 WHERE t1 MATCH 'a AND c'
|
||||
}
|
||||
} -test {
|
||||
faultsim_test_result [list 0 $::res]
|
||||
faultsim_test_result [list 0 $::res] {1 {SQL logic error}}
|
||||
}
|
||||
|
||||
do_faultsim_test 5.3 -faults oom* -prep {
|
||||
@@ -264,7 +264,7 @@ do_faultsim_test 5.3 -faults oom* -prep {
|
||||
SELECT count(*) FROM t1 WHERE t1 MATCH 'd AND e AND f'
|
||||
}
|
||||
} -test {
|
||||
faultsim_test_result {0 29}
|
||||
faultsim_test_result {0 29} {1 {SQL logic error}}
|
||||
}
|
||||
|
||||
do_faultsim_test 5.4 -faults oom* -prep {
|
||||
@@ -275,7 +275,7 @@ do_faultsim_test 5.4 -faults oom* -prep {
|
||||
SELECT count(*) FROM t1 WHERE t1 MATCH 'x + e'
|
||||
}
|
||||
} -test {
|
||||
faultsim_test_result {0 1}
|
||||
faultsim_test_result {0 1} {1 {SQL logic error}}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
|
||||
@@ -24,6 +24,8 @@ ifcapable !fts5 {
|
||||
|
||||
foreach_detail_mode $testprefix {
|
||||
|
||||
if {"%DETAIL%" != "none"} continue
|
||||
|
||||
fts5_aux_test_functions db
|
||||
|
||||
do_execsql_test 1.0 {
|
||||
@@ -98,14 +100,16 @@ do_faultsim_test 4.1 -faults oom-t* -body {
|
||||
execsql { SELECT rowid, fts5_test_collist(t4) FROM t4('2') }
|
||||
} -test {
|
||||
faultsim_test_result \
|
||||
{0 {1 {0.0 0.1 0.2} 2 {0.0 0.1 0.2} 3 {0.0 0.1 0.2}}} {1 SQLITE_NOMEM}
|
||||
{0 {1 {0.0 0.1 0.2} 2 {0.0 0.1 0.2} 3 {0.0 0.1 0.2}}} \
|
||||
{1 SQLITE_NOMEM} {1 SQLITE_ERROR} {1 {SQL logic error}}
|
||||
}
|
||||
|
||||
do_faultsim_test 4.2 -faults oom-t* -body {
|
||||
execsql { SELECT rowid, fts5_test_collist(t4) FROM t4('a5 OR b5 OR c5') }
|
||||
} -test {
|
||||
faultsim_test_result \
|
||||
{0 {4 {0.0 0.1 0.2} 5 {1.0 1.1 1.2} 6 {2.0 2.1 2.2}}} {1 SQLITE_NOMEM}
|
||||
{0 {4 {0.0 0.1 0.2} 5 {1.0 1.1 1.2} 6 {2.0 2.1 2.2}}} \
|
||||
{1 SQLITE_NOMEM} {1 SQLITE_ERROR} {1 {SQL logic error}}
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -14,11 +14,20 @@ as follows:
|
||||
It is a good example of how to go about implementing a custom
|
||||
[table-valued function](https://www.sqlite.org/vtab.html#tabfunc2).
|
||||
|
||||
* **csv.c** — A [virtual table](https://sqlite.org/vtab.html)
|
||||
for reading
|
||||
[Comma-Separated-Value (CSV) files](https://en.wikipedia.org/wiki/Comma-separated_values).
|
||||
|
||||
* **dbdump.c** — This is not actually a loadable extension, but
|
||||
rather a library that implements an approximate equivalent to the
|
||||
".dump" command of the
|
||||
[command-line shell](https://www.sqlite.org/cli.html).
|
||||
|
||||
* **json1.c** — Various SQL functions and table-valued functions
|
||||
for processing JSON. This extension is already built into the
|
||||
[SQLite amalgamation](https://sqlite.org/amalgamation.html). See
|
||||
<https://sqlite.org/json1.html> for additional information.
|
||||
|
||||
* **memvfs.c** — This file implements a custom
|
||||
[VFS](https://www.sqlite.org/vfs.html) that stores an entire database
|
||||
file in a single block of RAM. It serves as a good example of how
|
||||
@@ -38,3 +47,14 @@ as follows:
|
||||
on the source filename with digits removed, so if we used the name
|
||||
"sha3.c" then the entry point would conflict with the prior "sha1.c"
|
||||
extension.
|
||||
|
||||
* **unionvtab.c** — Implementation of the unionvtab and
|
||||
[swarmvtab](https://sqlite.org/swarmvtab.html) virtual tables.
|
||||
These virtual tables allow a single
|
||||
large table to be spread out across multiple database files. In the
|
||||
case of swarmvtab, the individual database files can be attached on
|
||||
demand.
|
||||
|
||||
* **zipfile.c** — A [virtual table](https://sqlite.org/vtab.html)
|
||||
that can read and write a
|
||||
[ZIP archive](https://en.wikipedia.org/wiki/Zip_%28file_format%29).
|
||||
|
||||
@@ -548,6 +548,8 @@ int sqlite3_appendvfs_init(
|
||||
int rc = SQLITE_OK;
|
||||
sqlite3_vfs *pOrig;
|
||||
SQLITE_EXTENSION_INIT2(pApi);
|
||||
(void)pzErrMsg;
|
||||
(void)db;
|
||||
pOrig = sqlite3_vfs_find(0);
|
||||
apnd_vfs.iVersion = pOrig->iVersion;
|
||||
apnd_vfs.pAppData = pOrig;
|
||||
|
||||
@@ -339,7 +339,8 @@ static int binfoColumn(
|
||||
sqlite3 *db = sqlite3_context_db_handle(ctx);
|
||||
int rc = binfoCompute(db, pgno, pCsr);
|
||||
if( rc ){
|
||||
return rc;
|
||||
pCursor->pVtab->zErrMsg = sqlite3_mprintf("%s", sqlite3_errmsg(db));
|
||||
return SQLITE_ERROR;
|
||||
}
|
||||
}
|
||||
switch( i ){
|
||||
|
||||
+64
-10
@@ -86,16 +86,18 @@ SQLITE_EXTENSION_INIT1
|
||||
# include <unistd.h>
|
||||
# include <dirent.h>
|
||||
# include <utime.h>
|
||||
# include <sys/time.h>
|
||||
#else
|
||||
# include "windows.h"
|
||||
# include <io.h>
|
||||
# include <direct.h>
|
||||
# include "test_windirent.h"
|
||||
# define dirent DIRENT
|
||||
# define timespec TIMESPEC
|
||||
# define stat _stat
|
||||
# ifndef stat
|
||||
# define stat _stat
|
||||
# endif
|
||||
# define mkdir(path,mode) _mkdir(path)
|
||||
# define lstat(path,buf) _stat(path,buf)
|
||||
# define lstat(path,buf) stat(path,buf)
|
||||
#endif
|
||||
#include <time.h>
|
||||
#include <errno.h>
|
||||
@@ -268,15 +270,20 @@ static int writeFile(
|
||||
SYSTEMTIME currentTime;
|
||||
LONGLONG intervals;
|
||||
HANDLE hFile;
|
||||
LPWSTR zUnicodeName;
|
||||
extern LPWSTR sqlite3_win32_utf8_to_unicode(const char*);
|
||||
|
||||
GetSystemTime(¤tTime);
|
||||
SystemTimeToFileTime(¤tTime, &lastAccess);
|
||||
intervals = Int32x32To64(mtime, 10000000) + 116444736000000000;
|
||||
lastWrite.dwLowDateTime = (DWORD)intervals;
|
||||
lastWrite.dwHighDateTime = intervals >> 32;
|
||||
hFile = CreateFile(
|
||||
zFile, FILE_WRITE_ATTRIBUTES, 0, NULL, OPEN_EXISTING,
|
||||
zUnicodeName = sqlite3_win32_utf8_to_unicode(zFile);
|
||||
hFile = CreateFileW(
|
||||
zUnicodeName, FILE_WRITE_ATTRIBUTES, 0, NULL, OPEN_EXISTING,
|
||||
FILE_FLAG_BACKUP_SEMANTICS, NULL
|
||||
);
|
||||
sqlite3_free(zUnicodeName);
|
||||
if( hFile!=INVALID_HANDLE_VALUE ){
|
||||
BOOL bResult = SetFileTime(hFile, NULL, &lastAccess, &lastWrite);
|
||||
CloseHandle(hFile);
|
||||
@@ -284,7 +291,7 @@ static int writeFile(
|
||||
}else{
|
||||
return 1;
|
||||
}
|
||||
#elif defined(AT_FDCWD)
|
||||
#elif defined(AT_FDCWD) && 0 /* utimensat() is not univerally available */
|
||||
/* Recent unix */
|
||||
struct timespec times[2];
|
||||
times[0].tv_nsec = times[1].tv_nsec = 0;
|
||||
@@ -356,6 +363,41 @@ static void writefileFunc(
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
** SQL function: lsmode(MODE)
|
||||
**
|
||||
** Given a numberic st_mode from stat(), convert it into a human-readable
|
||||
** text string in the style of "ls -l".
|
||||
*/
|
||||
static void lsModeFunc(
|
||||
sqlite3_context *context,
|
||||
int argc,
|
||||
sqlite3_value **argv
|
||||
){
|
||||
int i;
|
||||
int iMode = sqlite3_value_int(argv[0]);
|
||||
char z[16];
|
||||
(void)argc;
|
||||
if( S_ISLNK(iMode) ){
|
||||
z[0] = 'l';
|
||||
}else if( S_ISREG(iMode) ){
|
||||
z[0] = '-';
|
||||
}else if( S_ISDIR(iMode) ){
|
||||
z[0] = 'd';
|
||||
}else{
|
||||
z[0] = '?';
|
||||
}
|
||||
for(i=0; i<3; i++){
|
||||
int m = (iMode >> ((2-i)*3));
|
||||
char *a = &z[1 + i*3];
|
||||
a[0] = (m & 0x4) ? 'r' : '-';
|
||||
a[1] = (m & 0x2) ? 'w' : '-';
|
||||
a[2] = (m & 0x1) ? 'x' : '-';
|
||||
}
|
||||
z[10] = '\0';
|
||||
sqlite3_result_text(context, z, -1, SQLITE_TRANSIENT);
|
||||
}
|
||||
|
||||
#ifndef SQLITE_OMIT_VIRTUALTABLE
|
||||
|
||||
/*
|
||||
@@ -401,7 +443,10 @@ static int fsdirConnect(
|
||||
){
|
||||
fsdir_tab *pNew = 0;
|
||||
int rc;
|
||||
|
||||
(void)pAux;
|
||||
(void)argc;
|
||||
(void)argv;
|
||||
(void)pzErr;
|
||||
rc = sqlite3_declare_vtab(db, "CREATE TABLE x" FSDIR_SCHEMA);
|
||||
if( rc==SQLITE_OK ){
|
||||
pNew = (fsdir_tab*)sqlite3_malloc( sizeof(*pNew) );
|
||||
@@ -425,6 +470,7 @@ static int fsdirDisconnect(sqlite3_vtab *pVtab){
|
||||
*/
|
||||
static int fsdirOpen(sqlite3_vtab *p, sqlite3_vtab_cursor **ppCursor){
|
||||
fsdir_cursor *pCur;
|
||||
(void)p;
|
||||
pCur = sqlite3_malloc( sizeof(*pCur) );
|
||||
if( pCur==0 ) return SQLITE_NOMEM;
|
||||
memset(pCur, 0, sizeof(*pCur));
|
||||
@@ -445,6 +491,7 @@ static void fsdirResetCursor(fsdir_cursor *pCur){
|
||||
sqlite3_free(pLvl->zDir);
|
||||
}
|
||||
sqlite3_free(pCur->zPath);
|
||||
sqlite3_free(pCur->aLvl);
|
||||
pCur->aLvl = 0;
|
||||
pCur->zPath = 0;
|
||||
pCur->zBase = 0;
|
||||
@@ -460,7 +507,6 @@ static int fsdirClose(sqlite3_vtab_cursor *cur){
|
||||
fsdir_cursor *pCur = (fsdir_cursor*)cur;
|
||||
|
||||
fsdirResetCursor(pCur);
|
||||
sqlite3_free(pCur->aLvl);
|
||||
sqlite3_free(pCur);
|
||||
return SQLITE_OK;
|
||||
}
|
||||
@@ -628,7 +674,7 @@ static int fsdirFilter(
|
||||
){
|
||||
const char *zDir = 0;
|
||||
fsdir_cursor *pCur = (fsdir_cursor*)cur;
|
||||
|
||||
(void)idxStr;
|
||||
fsdirResetCursor(pCur);
|
||||
|
||||
if( idxNum==0 ){
|
||||
@@ -686,8 +732,9 @@ static int fsdirBestIndex(
|
||||
int i; /* Loop over constraints */
|
||||
int idx4 = -1;
|
||||
int idx5 = -1;
|
||||
|
||||
const struct sqlite3_index_constraint *pConstraint;
|
||||
|
||||
(void)tab;
|
||||
pConstraint = pIdxInfo->aConstraint;
|
||||
for(i=0; i<pIdxInfo->nConstraint; i++, pConstraint++){
|
||||
if( pConstraint->usable==0 ) continue;
|
||||
@@ -741,6 +788,9 @@ static int fsdirRegister(sqlite3 *db){
|
||||
0, /* xRollback */
|
||||
0, /* xFindMethod */
|
||||
0, /* xRename */
|
||||
0, /* xSavepoint */
|
||||
0, /* xRelease */
|
||||
0 /* xRollbackTo */
|
||||
};
|
||||
|
||||
int rc = sqlite3_create_module(db, "fsdir", &fsdirModule, 0);
|
||||
@@ -767,6 +817,10 @@ int sqlite3_fileio_init(
|
||||
rc = sqlite3_create_function(db, "writefile", -1, SQLITE_UTF8, 0,
|
||||
writefileFunc, 0, 0);
|
||||
}
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = sqlite3_create_function(db, "lsmode", 1, SQLITE_UTF8, 0,
|
||||
lsModeFunc, 0, 0);
|
||||
}
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = fsdirRegister(db);
|
||||
}
|
||||
|
||||
+527
-424
File diff suppressed because it is too large
Load Diff
@@ -484,14 +484,15 @@ static int unionDisconnect(sqlite3_vtab *pVtab){
|
||||
int i;
|
||||
for(i=0; i<pTab->nSrc; i++){
|
||||
UnionSrc *pSrc = &pTab->aSrc[i];
|
||||
if( pSrc->db ){
|
||||
int bHaveSrcDb = (pSrc->db!=0);
|
||||
sqlite3_close(pSrc->db);
|
||||
if( bHaveSrcDb ){
|
||||
unionInvokeOpenClose(pTab, pSrc, 1, 0);
|
||||
}
|
||||
sqlite3_free(pSrc->zDb);
|
||||
sqlite3_free(pSrc->zTab);
|
||||
sqlite3_free(pSrc->zFile);
|
||||
sqlite3_free(pSrc->zContext);
|
||||
sqlite3_close(pSrc->db);
|
||||
}
|
||||
sqlite3_finalize(pTab->pNotFound);
|
||||
sqlite3_finalize(pTab->pOpenClose);
|
||||
|
||||
+1398
-693
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,102 @@
|
||||
/*
|
||||
** 2018-02-09
|
||||
**
|
||||
** The author disclaims copyright to this source code. In place of
|
||||
** a legal notice, here is a blessing:
|
||||
**
|
||||
** May you do good and not evil.
|
||||
** May you find forgiveness for yourself and forgive others.
|
||||
** May you share freely, never taking more than you give.
|
||||
**
|
||||
******************************************************************************
|
||||
**
|
||||
** SQL functions for z-order (Morton code) transformations.
|
||||
**
|
||||
** zorder(X0,X0,..,xN) Generate an N+1 dimension Morton code
|
||||
**
|
||||
** unzorder(Z,N,I) Extract the I-th dimension from N-dimensional
|
||||
** Morton code Z.
|
||||
*/
|
||||
#include "sqlite3ext.h"
|
||||
SQLITE_EXTENSION_INIT1
|
||||
#include <assert.h>
|
||||
#include <string.h>
|
||||
|
||||
/*
|
||||
** Functions: zorder(X0,X1,....)
|
||||
**
|
||||
** Convert integers X0, X1, ... into morton code.
|
||||
**
|
||||
** The output is a signed 64-bit integer. If any argument is too large,
|
||||
** an error is thrown.
|
||||
*/
|
||||
static void zorderFunc(
|
||||
sqlite3_context *context,
|
||||
int argc,
|
||||
sqlite3_value **argv
|
||||
){
|
||||
sqlite3_int64 z, x[63];
|
||||
int i, j;
|
||||
z = 0;
|
||||
for(i=0; i<argc; i++){
|
||||
x[i] = sqlite3_value_int64(argv[i]);
|
||||
}
|
||||
if( argc>0 ){
|
||||
for(i=0; i<63; i++){
|
||||
j = i%argc;
|
||||
z |= (x[j]&1)<<i;
|
||||
x[j] >>= 1;
|
||||
}
|
||||
}
|
||||
sqlite3_result_int64(context, z);
|
||||
for(i=0; i<argc; i++){
|
||||
if( x[i] ){
|
||||
sqlite3_result_error(context, "parameter too large", -1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
** Functions: unzorder(Z,N,I)
|
||||
**
|
||||
** Assuming that Z is an N-dimensional Morton code, extract the I-th
|
||||
** dimension.
|
||||
*/
|
||||
static void unzorderFunc(
|
||||
sqlite3_context *context,
|
||||
int argc,
|
||||
sqlite3_value **argv
|
||||
){
|
||||
sqlite3_int64 z, n, i, x;
|
||||
int j, k;
|
||||
z = sqlite3_value_int64(argv[0]);
|
||||
n = sqlite3_value_int64(argv[1]);
|
||||
i = sqlite3_value_int64(argv[2]);
|
||||
x = 0;
|
||||
for(k=0, j=i; j<63; j+=n, k++){
|
||||
x |= ((z>>j)&1)<<k;
|
||||
}
|
||||
sqlite3_result_int64(context, x);
|
||||
}
|
||||
|
||||
|
||||
#ifdef _WIN32
|
||||
__declspec(dllexport)
|
||||
#endif
|
||||
int sqlite3_zorder_init(
|
||||
sqlite3 *db,
|
||||
char **pzErrMsg,
|
||||
const sqlite3_api_routines *pApi
|
||||
){
|
||||
int rc = SQLITE_OK;
|
||||
SQLITE_EXTENSION_INIT2(pApi);
|
||||
(void)pzErrMsg; /* Unused parameter */
|
||||
rc = sqlite3_create_function(db, "zorder", -1, SQLITE_UTF8, 0,
|
||||
zorderFunc, 0, 0);
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = sqlite3_create_function(db, "unzorder", 3, SQLITE_UTF8, 0,
|
||||
unzorderFunc, 0, 0);
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
@@ -0,0 +1,175 @@
|
||||
# 2018 January 11
|
||||
#
|
||||
# The author disclaims copyright to this source code. In place of
|
||||
# a legal notice, here is a blessing:
|
||||
#
|
||||
# May you do good and not evil.
|
||||
# May you find forgiveness for yourself and forgive others.
|
||||
# May you share freely, never taking more than you give.
|
||||
#
|
||||
#***********************************************************************
|
||||
#
|
||||
# This file contains tests of multiple RBU operations running
|
||||
# concurrently within the same process.
|
||||
#
|
||||
|
||||
source [file join [file dirname [info script]] rbu_common.tcl]
|
||||
set ::testprefix rbumulti
|
||||
|
||||
db close
|
||||
sqlite3_shutdown
|
||||
sqlite3_config_uri 1
|
||||
|
||||
autoinstall_test_functions
|
||||
|
||||
proc build_db {db} {
|
||||
$db eval {
|
||||
CREATE TABLE t1(a PRIMARY KEY, b, c);
|
||||
CREATE INDEX i1 ON t1(b);
|
||||
CREATE INDEX i2 ON t1(c);
|
||||
|
||||
WITH s(i) AS ( SELECT 1 UNION ALL SELECT i+1 FROM s WHERE i<500 )
|
||||
INSERT INTO t1
|
||||
SELECT randomblob(10), randomblob(100), randomblob(100) FROM s;
|
||||
}
|
||||
}
|
||||
|
||||
proc build_rbu {db} {
|
||||
$db eval {
|
||||
CREATE TABLE data_t1(a, b, c, rbu_control);
|
||||
WITH s(i) AS ( SELECT 1 UNION ALL SELECT i+1 FROM s WHERE i<100 )
|
||||
INSERT INTO data_t1
|
||||
SELECT randomblob(10), randomblob(100), randomblob(100), 0 FROM s;
|
||||
}
|
||||
}
|
||||
|
||||
proc step_rbu2 {bOpenClose openr1 openr2} {
|
||||
|
||||
forcedelete teststate.db1
|
||||
forcedelete teststate.db2
|
||||
|
||||
if {$bOpenClose!=0 && $bOpenClose!=1} { error $bOpenClose }
|
||||
if {$bOpenClose==0} {
|
||||
eval $openr1
|
||||
eval $openr2
|
||||
}
|
||||
|
||||
set b1 0
|
||||
set b2 0
|
||||
|
||||
while {$b1==0 || $b2==0} {
|
||||
if {$bOpenClose==1} {
|
||||
if {$b1==0} { eval $openr1 teststate.db1 }
|
||||
if {$b2==0} { eval $openr2 teststate.db2 }
|
||||
}
|
||||
if {$b1==0} {
|
||||
set rc1 [r1 step]
|
||||
if {$rc1 != "SQLITE_OK"} { set b1 1 }
|
||||
}
|
||||
if {$b2==0} {
|
||||
set rc2 [r2 step]
|
||||
if {$rc2 != "SQLITE_OK"} { set b2 1 }
|
||||
}
|
||||
if {$bOpenClose==1} {
|
||||
if {$b1==0} { r1 close }
|
||||
if {$b2==0} { r2 close }
|
||||
}
|
||||
}
|
||||
|
||||
set rc1 [r1 close]
|
||||
set rc2 [r2 close]
|
||||
|
||||
list $rc1 $rc2
|
||||
}
|
||||
|
||||
|
||||
for {set i 0} {$i<=3} {incr i} {
|
||||
|
||||
if {$i & 0x01} {
|
||||
sqlite3rbu_create_vfs -default myrbu ""
|
||||
}
|
||||
set bOpenClose [expr $i>>1]
|
||||
|
||||
forcedelete test.db
|
||||
forcedelete test.db2
|
||||
forcedelete rbu.db
|
||||
forcedelete rbu.db2
|
||||
|
||||
do_test 1.$i.0 {
|
||||
sqlite3 db test.db
|
||||
sqlite3 db2 test.db2
|
||||
build_db db
|
||||
build_db db2
|
||||
|
||||
sqlite3 rbu1 rbu.db
|
||||
sqlite3 rbu2 rbu.db2
|
||||
|
||||
build_rbu rbu1
|
||||
build_rbu rbu2
|
||||
|
||||
rbu1 close
|
||||
rbu2 close
|
||||
} {}
|
||||
|
||||
set m1 [db eval {SELECT md5sum(a, b, c) FROM t1}]
|
||||
set m2 [db2 eval {SELECT md5sum(a, b, c) FROM t1}]
|
||||
|
||||
do_test 1.$i.1 {
|
||||
step_rbu2 $bOpenClose {
|
||||
sqlite3rbu r1 test.db rbu.db
|
||||
} {
|
||||
sqlite3rbu r2 test.db2 rbu.db2
|
||||
}
|
||||
} {SQLITE_DONE SQLITE_DONE}
|
||||
|
||||
do_execsql_test -db db 1.$i.2.1 { PRAGMA integrity_check } ok
|
||||
do_execsql_test -db db2 1.$i.2.2 { PRAGMA integrity_check } ok
|
||||
|
||||
do_execsql_test -db db 1.$i.3.1 { SELECT md5sum(a, b, c)==$m1 FROM t1 } 0
|
||||
do_execsql_test -db db2 1.$i.3.2 { SELECT md5sum(a, b, c)==$m2 FROM t1 } 0
|
||||
|
||||
catch { db close }
|
||||
catch { db2 close }
|
||||
#-----------------------------------------------------------------------
|
||||
forcedelete test.db2
|
||||
forcedelete test.db
|
||||
forcedelete rbu.db2
|
||||
|
||||
do_test 1.$i.4 {
|
||||
sqlite3 db test.db
|
||||
sqlite3 db2 test.db2
|
||||
build_db db
|
||||
build_db db2
|
||||
sqlite3 rbu2 rbu.db2
|
||||
build_rbu rbu2
|
||||
rbu2 close
|
||||
} {}
|
||||
|
||||
set m1 [db eval {SELECT md5sum(a, b, c) FROM t1}]
|
||||
set m2 [db2 eval {SELECT md5sum(a, b, c) FROM t1}]
|
||||
|
||||
do_test 1.$i.5 {
|
||||
step_rbu2 $bOpenClose {
|
||||
sqlite3rbu_vacuum r1 test.db
|
||||
} {
|
||||
sqlite3rbu r2 test.db2 rbu.db2
|
||||
}
|
||||
} {SQLITE_DONE SQLITE_DONE}
|
||||
|
||||
do_execsql_test -db db 1.$i.6.1 { SELECT md5sum(a, b, c)==$m1 FROM t1 } 1
|
||||
do_execsql_test -db db2 1.$i.6.2 { SELECT md5sum(a, b, c)==$m2 FROM t1 } 0
|
||||
|
||||
do_execsql_test -db db 1.$i.7.1 { PRAGMA integrity_check } ok
|
||||
do_execsql_test -db db2 1.$i.7.2 { PRAGMA integrity_check } ok
|
||||
|
||||
catch { db close }
|
||||
catch { db2 close }
|
||||
if {$i & 0x01} {
|
||||
sqlite3rbu_destroy_vfs myrbu
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
finish_test
|
||||
|
||||
+3
-1
@@ -52,7 +52,8 @@
|
||||
** child page.
|
||||
*/
|
||||
|
||||
#if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_RTREE)
|
||||
#if !defined(SQLITE_CORE) \
|
||||
|| (defined(SQLITE_ENABLE_RTREE) && !defined(SQLITE_OMIT_VIRTUALTABLE))
|
||||
|
||||
#ifndef SQLITE_CORE
|
||||
#include "sqlite3ext.h"
|
||||
@@ -784,6 +785,7 @@ static int nodeWrite(Rtree *pRtree, RtreeNode *pNode){
|
||||
sqlite3_step(p);
|
||||
pNode->isDirty = 0;
|
||||
rc = sqlite3_reset(p);
|
||||
sqlite3_bind_null(p, 2);
|
||||
if( pNode->iNode==0 && rc==SQLITE_OK ){
|
||||
pNode->iNode = sqlite3_last_insert_rowid(pRtree->db);
|
||||
nodeHashInsert(pRtree, pNode);
|
||||
|
||||
@@ -15,6 +15,10 @@
|
||||
*/
|
||||
#include "sqlite3.h"
|
||||
|
||||
#ifdef SQLITE_OMIT_VIRTUALTABLE
|
||||
# undef SQLITE_ENABLE_RTREE
|
||||
#endif
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif /* __cplusplus */
|
||||
|
||||
@@ -609,4 +609,5 @@ do_execsql_test 15.2 {
|
||||
COMMIT;
|
||||
}
|
||||
|
||||
expand_all_sql db
|
||||
finish_test
|
||||
|
||||
@@ -250,4 +250,5 @@ for {set nDim 1} {$nDim<=5} {incr nDim} {
|
||||
do_rtree_integrity_test rtree4-$nDim.3 rx
|
||||
}
|
||||
|
||||
expand_all_sql db
|
||||
finish_test
|
||||
|
||||
@@ -79,4 +79,5 @@ do_test rtree5-1.13 {
|
||||
} {2 2147483643 2147483647 -2147483648 -2147483643}
|
||||
do_rtree_integrity_test rtree5-1.14 t1
|
||||
|
||||
expand_all_sql db
|
||||
finish_test
|
||||
|
||||
@@ -158,5 +158,5 @@ do_execsql_test rtree6-3.5 {
|
||||
x1>0.5 AND x1>0.5 AND x1>0.5 AND x1>0.5 AND x1>1.1
|
||||
} {}
|
||||
|
||||
|
||||
expand_all_sql db
|
||||
finish_test
|
||||
|
||||
@@ -59,6 +59,7 @@ do_test rtreeG-1.4log {
|
||||
set ::log
|
||||
} {}
|
||||
|
||||
expand_all_sql db
|
||||
db close
|
||||
sqlite3_shutdown
|
||||
test_sqlite3_log
|
||||
|
||||
@@ -221,5 +221,38 @@ do_test 4.2.2 {
|
||||
} {1 {SQLITE_SCHEMA - table schemas do not match}}
|
||||
S delete
|
||||
|
||||
do_test 4.3.1 {
|
||||
sqlite3session S db main
|
||||
S attach t4
|
||||
execsql { CREATE TABLE t4(i PRIMARY KEY, b) }
|
||||
list [catch { S diff ixua t4 } msg] $msg
|
||||
} {1 {SQLITE_SCHEMA - table schemas do not match}}
|
||||
S delete
|
||||
do_catchsql_test 4.3.2 {
|
||||
SELECT * FROM ixua.t4;
|
||||
} {1 {no such table: ixua.t4}}
|
||||
|
||||
do_test 4.4.1 {
|
||||
sqlite3session S db main
|
||||
S attach sqlite_stat1
|
||||
execsql { ANALYZE }
|
||||
execsql { DROP TABLE ixua.sqlite_stat1 }
|
||||
list [catch { S diff ixua sqlite_stat1 } msg] $msg
|
||||
} {1 {SQLITE_SCHEMA - table schemas do not match}}
|
||||
S delete
|
||||
do_catchsql_test 4.4.2 {
|
||||
SELECT * FROM ixua.sqlite_stat1;
|
||||
} {1 {no such table: ixua.sqlite_stat1}}
|
||||
|
||||
do_test 4.5.1 {
|
||||
sqlite3session S db main
|
||||
S attach t8
|
||||
list [catch { S diff ixua t8 } msg] $msg
|
||||
} {0 {}}
|
||||
S delete
|
||||
do_catchsql_test 4.5.2 {
|
||||
SELECT * FROM ixua.i8;
|
||||
} {1 {no such table: ixua.i8}}
|
||||
|
||||
finish_test
|
||||
|
||||
|
||||
@@ -173,5 +173,39 @@ do_test 4.3 {
|
||||
compare_db db db2
|
||||
} {}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
catch { db2 close }
|
||||
forcedelete test.db2
|
||||
sqlite3 db2 test.db2
|
||||
|
||||
do_execsql_test 5.0.1 {
|
||||
CREATE TABLE t1(a PRIMARY KEY, b, c);
|
||||
CREATE TABLE t2(a, b, c PRIMARY KEY);
|
||||
CREATE TABLE t3(a, b PRIMARY KEY, c);
|
||||
}
|
||||
do_execsql_test -db db2 5.0.2 {
|
||||
CREATE TABLE t1(a PRIMARY KEY, b, c);
|
||||
CREATE TABLE t2(a, b, c);
|
||||
CREATE TABLE t3(a, b PRIMARY KEY, c);
|
||||
}
|
||||
|
||||
do_test 5.1 {
|
||||
do_then_apply_sql {
|
||||
INSERT INTO t1 VALUES(1, 2, 3);
|
||||
INSERT INTO t2 VALUES(4, 5, 6);
|
||||
INSERT INTO t3 VALUES(7, 8, 9);
|
||||
}
|
||||
|
||||
db2 eval {
|
||||
SELECT * FROM t1;
|
||||
SELECT * FROM t2;
|
||||
SELECT * FROM t3;
|
||||
}
|
||||
} {1 2 3 7 8 9}
|
||||
|
||||
|
||||
|
||||
|
||||
finish_test
|
||||
|
||||
|
||||
@@ -0,0 +1,39 @@
|
||||
# 2018 January 18
|
||||
#
|
||||
# The author disclaims copyright to this source code. In place of
|
||||
# a legal notice, here is a blessing:
|
||||
#
|
||||
# May you do good and not evil.
|
||||
# May you find forgiveness for yourself and forgive others.
|
||||
# May you share freely, never taking more than you give.
|
||||
#
|
||||
#***********************************************************************
|
||||
#
|
||||
|
||||
if {![info exists testdir]} {
|
||||
set testdir [file join [file dirname [info script]] .. .. test]
|
||||
}
|
||||
source [file join [file dirname [info script]] session_common.tcl]
|
||||
source $testdir/tester.tcl
|
||||
ifcapable !session {finish_test; return}
|
||||
set testprefix sessionH
|
||||
|
||||
forcedelete test.db2
|
||||
sqlite3 db2 test.db2
|
||||
|
||||
do_test 1.0 {
|
||||
do_common_sql {
|
||||
CREATE TABLE t1(a, b, c, PRIMARY KEY(a, b));
|
||||
}
|
||||
do_then_apply_sql {
|
||||
WITH s(i) AS (
|
||||
VALUES(1) UNION ALL SELECT i+1 FROM s WHERe i<10000
|
||||
)
|
||||
INSERT INTO t1 SELECT 'abcde', randomblob(16), i FROM s;
|
||||
}
|
||||
compare_db db db2
|
||||
} {}
|
||||
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -241,5 +241,9 @@ eval [string map [list %WR% $trailing] {
|
||||
}]
|
||||
}
|
||||
|
||||
catch { db close }
|
||||
catch { db2 close }
|
||||
sqlite3_shutdown
|
||||
test_sqlite3_log
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -0,0 +1,311 @@
|
||||
# 2018 January 12
|
||||
#
|
||||
# The author disclaims copyright to this source code. In place of
|
||||
# a legal notice, here is a blessing:
|
||||
#
|
||||
# May you do good and not evil.
|
||||
# May you find forgiveness for yourself and forgive others.
|
||||
# May you share freely, never taking more than you give.
|
||||
#
|
||||
#***********************************************************************
|
||||
#
|
||||
|
||||
if {![info exists testdir]} {
|
||||
set testdir [file join [file dirname [info script]] .. .. test]
|
||||
}
|
||||
source [file join [file dirname [info script]] session_common.tcl]
|
||||
source $testdir/tester.tcl
|
||||
ifcapable !session {finish_test; return}
|
||||
|
||||
set testprefix sessionstat1
|
||||
|
||||
do_execsql_test 1.0 {
|
||||
CREATE TABLE t1(a PRIMARY KEY, b, c);
|
||||
CREATE INDEX t1b ON t1(b);
|
||||
CREATE INDEX t1c ON t1(c);
|
||||
|
||||
WITH s(i) AS (
|
||||
SELECT 0 UNION ALL SELECT i+1 FROM s WHERE (i+1)<32
|
||||
)
|
||||
INSERT INTO t1 SELECT i, i%8, i%2 FROM s;
|
||||
}
|
||||
|
||||
do_iterator_test 1.1 {} {
|
||||
ANALYZE
|
||||
} {
|
||||
{INSERT sqlite_stat1 0 XX. {} {t t1 t sqlite_autoindex_t1_1 t {32 1}}}
|
||||
{INSERT sqlite_stat1 0 XX. {} {t t1 t t1b t {32 4}}}
|
||||
{INSERT sqlite_stat1 0 XX. {} {t t1 t t1c t {32 16}}}
|
||||
}
|
||||
|
||||
do_execsql_test 1.2 {
|
||||
WITH s(i) AS (
|
||||
SELECT 32 UNION ALL SELECT i+1 FROM s WHERE (i+1)<64
|
||||
)
|
||||
INSERT INTO t1 SELECT i, i%8, i%2 FROM s;
|
||||
}
|
||||
|
||||
do_iterator_test 1.3 {} {
|
||||
ANALYZE
|
||||
} {
|
||||
{UPDATE sqlite_stat1 0 XX. {t t1 t sqlite_autoindex_t1_1 t {32 1}} {{} {} {} {} t {64 1}}}
|
||||
{UPDATE sqlite_stat1 0 XX. {t t1 t t1b t {32 4}} {{} {} {} {} t {64 8}}}
|
||||
{UPDATE sqlite_stat1 0 XX. {t t1 t t1c t {32 16}} {{} {} {} {} t {64 32}}}
|
||||
}
|
||||
|
||||
do_iterator_test 1.5 {} {
|
||||
DROP INDEX t1b;
|
||||
} {
|
||||
{DELETE sqlite_stat1 0 XX. {t t1 t t1b t {64 8}} {}}
|
||||
}
|
||||
|
||||
do_iterator_test 1.6 {} {
|
||||
DROP TABLE t1;
|
||||
} {
|
||||
{DELETE sqlite_stat1 0 XX. {t t1 t sqlite_autoindex_t1_1 t {64 1}} {}}
|
||||
{DELETE sqlite_stat1 0 XX. {t t1 t t1c t {64 32}} {}}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
#
|
||||
catch { db2 close }
|
||||
forcedelete test.db2
|
||||
sqlite3 db2 test.db2
|
||||
|
||||
do_test 2.0 {
|
||||
do_common_sql {
|
||||
CREATE TABLE t1(a PRIMARY KEY, b, c);
|
||||
CREATE INDEX t1b ON t1(b);
|
||||
CREATE INDEX t1c ON t1(c);
|
||||
ANALYZE;
|
||||
}
|
||||
} {}
|
||||
|
||||
do_test 2.1 {
|
||||
do_then_apply_sql {
|
||||
WITH s(i) AS (
|
||||
SELECT 0 UNION ALL SELECT i+1 FROM s WHERE (i+1)<32
|
||||
)
|
||||
INSERT INTO t1 SELECT i, i%8, i%2 FROM s;
|
||||
ANALYZE;
|
||||
}
|
||||
} {}
|
||||
|
||||
do_execsql_test -db db2 2.2 {
|
||||
SELECT * FROM sqlite_stat1
|
||||
} {
|
||||
t1 sqlite_autoindex_t1_1 {32 1}
|
||||
t1 t1b {32 4}
|
||||
t1 t1c {32 16}
|
||||
}
|
||||
|
||||
do_test 2.3 {
|
||||
do_then_apply_sql { DROP INDEX t1c }
|
||||
} {}
|
||||
|
||||
do_execsql_test -db db2 2.4 {
|
||||
SELECT * FROM sqlite_stat1
|
||||
} {
|
||||
t1 sqlite_autoindex_t1_1 {32 1}
|
||||
t1 t1b {32 4}
|
||||
}
|
||||
|
||||
do_test 2.3 {
|
||||
do_then_apply_sql { DROP TABLE t1 }
|
||||
} {}
|
||||
|
||||
do_execsql_test -db db2 2.4 {
|
||||
SELECT * FROM sqlite_stat1
|
||||
} {
|
||||
}
|
||||
|
||||
do_execsql_test -db db2 2.5 { SELECT count(*) FROM t1 } 32
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
db2 close
|
||||
forcedelete test.db2
|
||||
reset_db
|
||||
sqlite3 db2 test.db2
|
||||
|
||||
do_test 3.0 {
|
||||
do_common_sql {
|
||||
CREATE TABLE t1(a, b, c);
|
||||
ANALYZE;
|
||||
DELETE FROM sqlite_stat1;
|
||||
}
|
||||
execsql {
|
||||
INSERT INTO t1 VALUES(1, 1, 1);
|
||||
INSERT INTO t1 VALUES(2, 2, 2);
|
||||
INSERT INTO t1 VALUES(3, 3, 3);
|
||||
INSERT INTO t1 VALUES(4, 4, 4);
|
||||
}
|
||||
} {}
|
||||
|
||||
do_iterator_test 3.1 {} {
|
||||
ANALYZE
|
||||
} {
|
||||
{INSERT sqlite_stat1 0 XX. {} {t t1 b {} t 4}}
|
||||
}
|
||||
db null null
|
||||
db2 null null
|
||||
do_execsql_test 3.2 {
|
||||
SELECT * FROM sqlite_stat1;
|
||||
} {t1 null 4}
|
||||
do_test 3.3 {
|
||||
execsql { DELETE FROM sqlite_stat1 }
|
||||
do_then_apply_sql { ANALYZE }
|
||||
execsql { SELECT * FROM sqlite_stat1 } db2
|
||||
} {t1 null 4}
|
||||
do_test 3.4 {
|
||||
execsql { INSERT INTO t1 VALUES(5,5,5) }
|
||||
do_then_apply_sql { ANALYZE }
|
||||
execsql { SELECT * FROM sqlite_stat1 } db2
|
||||
} {t1 null 5}
|
||||
do_test 3.5 {
|
||||
do_then_apply_sql { DROP TABLE t1 }
|
||||
execsql { SELECT * FROM sqlite_stat1 } db2
|
||||
} {}
|
||||
|
||||
do_test 3.6.1 {
|
||||
execsql {
|
||||
CREATE TABLE t1(a, b, c);
|
||||
CREATE TABLE t2(x, y, z);
|
||||
INSERT INTO t1 VALUES(1,1,1), (2,2,2), (3,3,3), (4,4,4), (5,5,5);
|
||||
INSERT INTO t2 SELECT * FROM t1;
|
||||
DELETE FROM sqlite_stat1;
|
||||
}
|
||||
sqlite3session S db main
|
||||
S attach sqlite_stat1
|
||||
execsql { ANALYZE }
|
||||
} {}
|
||||
do_changeset_test 3.6.2 S {
|
||||
{INSERT sqlite_stat1 0 XX. {} {t t2 b {} t 5}}
|
||||
{INSERT sqlite_stat1 0 XX. {} {t t1 b {} t 5}}
|
||||
}
|
||||
do_changeset_invert_test 3.6.3 S {
|
||||
{DELETE sqlite_stat1 0 XX. {t t2 b {} t 5} {}}
|
||||
{DELETE sqlite_stat1 0 XX. {t t1 b {} t 5} {}}
|
||||
}
|
||||
do_test 3.6.4 { S delete } {}
|
||||
|
||||
proc sql_changeset_concat {args} {
|
||||
foreach sql $args {
|
||||
sqlite3session S db main
|
||||
S attach sqlite_stat1
|
||||
execsql $sql
|
||||
set change [S changeset]
|
||||
S delete
|
||||
|
||||
if {[info vars ret]!=""} {
|
||||
set ret [sqlite3changeset_concat $ret $change]
|
||||
} else {
|
||||
set ret $change
|
||||
}
|
||||
}
|
||||
|
||||
changeset_to_list $ret
|
||||
}
|
||||
|
||||
proc do_scc_test {tn args} {
|
||||
uplevel [list \
|
||||
do_test $tn [concat sql_changeset_concat [lrange $args 0 end-1]] \
|
||||
[list {*}[ lindex $args end ]]
|
||||
]
|
||||
}
|
||||
|
||||
do_execsql_test 3.7.0 {
|
||||
DELETE FROM sqlite_stat1;
|
||||
}
|
||||
do_scc_test 3.7.1 {
|
||||
ANALYZE;
|
||||
} {
|
||||
INSERT INTO t2 VALUES(6,6,6);
|
||||
ANALYZE;
|
||||
} {
|
||||
{INSERT sqlite_stat1 0 XX. {} {t t1 b {} t 5}}
|
||||
{INSERT sqlite_stat1 0 XX. {} {t t2 b {} t 6}}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
catch { db2 close }
|
||||
reset_db
|
||||
forcedelete test.db2
|
||||
sqlite3 db2 test.db2
|
||||
|
||||
do_test 4.1.0 {
|
||||
do_common_sql {
|
||||
CREATE TABLE t1(a, b);
|
||||
CREATE INDEX i1 ON t1(a);
|
||||
CREATE INDEX i2 ON t1(b);
|
||||
INSERT INTO t1 VALUES(1,1), (2,2);
|
||||
ANALYZE;
|
||||
}
|
||||
execsql { DELETE FROM sqlite_stat1 }
|
||||
} {}
|
||||
|
||||
do_test 4.1.1 {
|
||||
execsql { INSERT INTO t1 VALUES(3,3); }
|
||||
set C [changeset_from_sql {ANALYZE}]
|
||||
set ::c [list]
|
||||
proc xConflict {args} {
|
||||
lappend ::c $args
|
||||
return "OMIT"
|
||||
}
|
||||
sqlite3changeset_apply db2 $C xConflict
|
||||
set ::c
|
||||
} [list {*}{
|
||||
{INSERT sqlite_stat1 CONFLICT {t t1 t i1 t {3 1}} {t t1 t i1 t {2 1}}}
|
||||
{INSERT sqlite_stat1 CONFLICT {t t1 t i2 t {3 1}} {t t1 t i2 t {2 1}}}
|
||||
}]
|
||||
|
||||
do_execsql_test -db db2 4.1.2 {
|
||||
SELECT * FROM sqlite_stat1 ORDER BY 1,2;
|
||||
} {t1 i1 {2 1} t1 i2 {2 1}}
|
||||
|
||||
do_test 4.1.3 {
|
||||
proc xConflict {args} {
|
||||
return "REPLACE"
|
||||
}
|
||||
sqlite3changeset_apply db2 $C xConflict
|
||||
execsql { SELECT * FROM sqlite_stat1 ORDER BY 1,2 } db2
|
||||
} {t1 i1 {3 1} t1 i2 {3 1}}
|
||||
|
||||
do_test 4.2.0 {
|
||||
do_common_sql {
|
||||
DROP TABLE t1;
|
||||
CREATE TABLE t3(x,y);
|
||||
INSERT INTO t3 VALUES('a','a');
|
||||
INSERT INTO t3 VALUES('b','b');
|
||||
ANALYZE;
|
||||
}
|
||||
execsql { DELETE FROM sqlite_stat1 }
|
||||
} {}
|
||||
do_test 4.2.1 {
|
||||
execsql { INSERT INTO t3 VALUES('c','c'); }
|
||||
set C [changeset_from_sql {ANALYZE}]
|
||||
set ::c [list]
|
||||
proc xConflict {args} {
|
||||
lappend ::c $args
|
||||
return "OMIT"
|
||||
}
|
||||
sqlite3changeset_apply db2 $C xConflict
|
||||
set ::c
|
||||
} [list {*}{
|
||||
{INSERT sqlite_stat1 CONFLICT {t t3 b {} t 3} {t t3 b {} t 2}}
|
||||
}]
|
||||
|
||||
db2 null null
|
||||
do_execsql_test -db db2 4.2.2 {
|
||||
SELECT * FROM sqlite_stat1 ORDER BY 1,2;
|
||||
} {t3 null 2}
|
||||
|
||||
do_test 4.2.3 {
|
||||
proc xConflict {args} {
|
||||
return "REPLACE"
|
||||
}
|
||||
sqlite3changeset_apply db2 $C xConflict
|
||||
execsql { SELECT * FROM sqlite_stat1 ORDER BY 1,2 } db2
|
||||
} {t3 null 3}
|
||||
|
||||
finish_test
|
||||
|
||||
+195
-37
@@ -46,6 +46,7 @@ struct sqlite3_session {
|
||||
int rc; /* Non-zero if an error has occurred */
|
||||
void *pFilterCtx; /* First argument to pass to xTableFilter */
|
||||
int (*xTableFilter)(void *pCtx, const char *zTab);
|
||||
sqlite3_value *pZeroBlob; /* Value containing X'' */
|
||||
sqlite3_session *pNext; /* Next session object on same db. */
|
||||
SessionTable *pTable; /* List of attached tables */
|
||||
SessionHook hook; /* APIs to grab new and old data with */
|
||||
@@ -113,6 +114,7 @@ struct SessionTable {
|
||||
SessionTable *pNext;
|
||||
char *zName; /* Local name of table */
|
||||
int nCol; /* Number of columns in table zName */
|
||||
int bStat1; /* True if this is sqlite_stat1 */
|
||||
const char **azCol; /* Column names */
|
||||
u8 *abPK; /* Array of primary key flags */
|
||||
int nEntry; /* Total number of entries in hash table */
|
||||
@@ -496,6 +498,7 @@ static int sessionPreupdateHash(
|
||||
h = sessionHashAppendBlob(h, n, z);
|
||||
}else{
|
||||
assert( eType==SQLITE_NULL );
|
||||
assert( pTab->bStat1==0 || i!=1 );
|
||||
*pbNullPK = 1;
|
||||
}
|
||||
}
|
||||
@@ -838,7 +841,6 @@ static int sessionPreupdateEqual(
|
||||
}
|
||||
if( memcmp(a, z, n) ) return 0;
|
||||
a += n;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -894,9 +896,7 @@ static int sessionGrowHash(int bPatchset, SessionTable *pTab){
|
||||
|
||||
/*
|
||||
** This function queries the database for the names of the columns of table
|
||||
** zThis, in schema zDb. It is expected that the table has nCol columns. If
|
||||
** not, SQLITE_SCHEMA is returned and none of the output variables are
|
||||
** populated.
|
||||
** zThis, in schema zDb.
|
||||
**
|
||||
** Otherwise, if they are not NULL, variable *pnCol is set to the number
|
||||
** of columns in the database table and variable *pzTab is set to point to a
|
||||
@@ -917,9 +917,7 @@ static int sessionGrowHash(int bPatchset, SessionTable *pTab){
|
||||
** *pabPK = {1, 0, 0, 1}
|
||||
**
|
||||
** All returned buffers are part of the same single allocation, which must
|
||||
** be freed using sqlite3_free() by the caller. If pazCol was not NULL, then
|
||||
** pointer *pazCol should be freed to release all memory. Otherwise, pointer
|
||||
** *pabPK. It is illegal for both pazCol and pabPK to be NULL.
|
||||
** be freed using sqlite3_free() by the caller
|
||||
*/
|
||||
static int sessionTableInfo(
|
||||
sqlite3 *db, /* Database connection */
|
||||
@@ -944,7 +942,23 @@ static int sessionTableInfo(
|
||||
assert( pazCol && pabPK );
|
||||
|
||||
nThis = sqlite3Strlen30(zThis);
|
||||
zPragma = sqlite3_mprintf("PRAGMA '%q'.table_info('%q')", zDb, zThis);
|
||||
if( nThis==12 && 0==sqlite3_stricmp("sqlite_stat1", zThis) ){
|
||||
rc = sqlite3_table_column_metadata(db, zDb, zThis, 0, 0, 0, 0, 0, 0);
|
||||
if( rc==SQLITE_OK ){
|
||||
/* For sqlite_stat1, pretend that (tbl,idx) is the PRIMARY KEY. */
|
||||
zPragma = sqlite3_mprintf(
|
||||
"SELECT 0, 'tbl', '', 0, '', 1 UNION ALL "
|
||||
"SELECT 1, 'idx', '', 0, '', 2 UNION ALL "
|
||||
"SELECT 2, 'stat', '', 0, '', 0"
|
||||
);
|
||||
}else if( rc==SQLITE_ERROR ){
|
||||
zPragma = sqlite3_mprintf("");
|
||||
}else{
|
||||
return rc;
|
||||
}
|
||||
}else{
|
||||
zPragma = sqlite3_mprintf("PRAGMA '%q'.table_info('%q')", zDb, zThis);
|
||||
}
|
||||
if( !zPragma ) return SQLITE_NOMEM;
|
||||
|
||||
rc = sqlite3_prepare_v2(db, zPragma, -1, &pStmt, 0);
|
||||
@@ -1036,11 +1050,55 @@ static int sessionInitTable(sqlite3_session *pSession, SessionTable *pTab){
|
||||
break;
|
||||
}
|
||||
}
|
||||
if( 0==sqlite3_stricmp("sqlite_stat1", pTab->zName) ){
|
||||
pTab->bStat1 = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
return (pSession->rc || pTab->abPK==0);
|
||||
}
|
||||
|
||||
/*
|
||||
** Versions of the four methods in object SessionHook for use with the
|
||||
** sqlite_stat1 table. The purpose of this is to substitute a zero-length
|
||||
** blob each time a NULL value is read from the "idx" column of the
|
||||
** sqlite_stat1 table.
|
||||
*/
|
||||
typedef struct SessionStat1Ctx SessionStat1Ctx;
|
||||
struct SessionStat1Ctx {
|
||||
SessionHook hook;
|
||||
sqlite3_session *pSession;
|
||||
};
|
||||
static int sessionStat1Old(void *pCtx, int iCol, sqlite3_value **ppVal){
|
||||
SessionStat1Ctx *p = (SessionStat1Ctx*)pCtx;
|
||||
sqlite3_value *pVal = 0;
|
||||
int rc = p->hook.xOld(p->hook.pCtx, iCol, &pVal);
|
||||
if( rc==SQLITE_OK && iCol==1 && sqlite3_value_type(pVal)==SQLITE_NULL ){
|
||||
pVal = p->pSession->pZeroBlob;
|
||||
}
|
||||
*ppVal = pVal;
|
||||
return rc;
|
||||
}
|
||||
static int sessionStat1New(void *pCtx, int iCol, sqlite3_value **ppVal){
|
||||
SessionStat1Ctx *p = (SessionStat1Ctx*)pCtx;
|
||||
sqlite3_value *pVal = 0;
|
||||
int rc = p->hook.xNew(p->hook.pCtx, iCol, &pVal);
|
||||
if( rc==SQLITE_OK && iCol==1 && sqlite3_value_type(pVal)==SQLITE_NULL ){
|
||||
pVal = p->pSession->pZeroBlob;
|
||||
}
|
||||
*ppVal = pVal;
|
||||
return rc;
|
||||
}
|
||||
static int sessionStat1Count(void *pCtx){
|
||||
SessionStat1Ctx *p = (SessionStat1Ctx*)pCtx;
|
||||
return p->hook.xCount(p->hook.pCtx);
|
||||
}
|
||||
static int sessionStat1Depth(void *pCtx){
|
||||
SessionStat1Ctx *p = (SessionStat1Ctx*)pCtx;
|
||||
return p->hook.xDepth(p->hook.pCtx);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
** This function is only called from with a pre-update-hook reporting a
|
||||
** change on table pTab (attached to session pSession). The type of change
|
||||
@@ -1057,6 +1115,7 @@ static void sessionPreupdateOneChange(
|
||||
int iHash;
|
||||
int bNull = 0;
|
||||
int rc = SQLITE_OK;
|
||||
SessionStat1Ctx stat1 = {0};
|
||||
|
||||
if( pSession->rc ) return;
|
||||
|
||||
@@ -1076,6 +1135,25 @@ static void sessionPreupdateOneChange(
|
||||
return;
|
||||
}
|
||||
|
||||
if( pTab->bStat1 ){
|
||||
stat1.hook = pSession->hook;
|
||||
stat1.pSession = pSession;
|
||||
pSession->hook.pCtx = (void*)&stat1;
|
||||
pSession->hook.xNew = sessionStat1New;
|
||||
pSession->hook.xOld = sessionStat1Old;
|
||||
pSession->hook.xCount = sessionStat1Count;
|
||||
pSession->hook.xDepth = sessionStat1Depth;
|
||||
if( pSession->pZeroBlob==0 ){
|
||||
sqlite3_value *p = sqlite3ValueNew(0);
|
||||
if( p==0 ){
|
||||
rc = SQLITE_NOMEM;
|
||||
goto error_out;
|
||||
}
|
||||
sqlite3ValueSetStr(p, 0, "", 0, SQLITE_STATIC);
|
||||
pSession->pZeroBlob = p;
|
||||
}
|
||||
}
|
||||
|
||||
/* Calculate the hash-key for this change. If the primary key of the row
|
||||
** includes a NULL value, exit early. Such changes are ignored by the
|
||||
** session module. */
|
||||
@@ -1165,6 +1243,9 @@ static void sessionPreupdateOneChange(
|
||||
|
||||
/* If an error has occurred, mark the session object as failed. */
|
||||
error_out:
|
||||
if( pTab->bStat1 ){
|
||||
pSession->hook = stat1.hook;
|
||||
}
|
||||
if( rc!=SQLITE_OK ){
|
||||
pSession->rc = rc;
|
||||
}
|
||||
@@ -1501,7 +1582,6 @@ int sqlite3session_diff(
|
||||
if( abPK[i] ) bHasPk = 1;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
sqlite3_free((char*)azCol);
|
||||
if( bMismatch ){
|
||||
@@ -1627,6 +1707,7 @@ void sqlite3session_delete(sqlite3_session *pSession){
|
||||
}
|
||||
}
|
||||
sqlite3_mutex_leave(sqlite3_db_mutex(db));
|
||||
sqlite3ValueFree(pSession->pZeroBlob);
|
||||
|
||||
/* Delete all attached table objects. And the contents of their
|
||||
** associated hash-tables. */
|
||||
@@ -2094,28 +2175,41 @@ static int sessionSelectStmt(
|
||||
sqlite3_stmt **ppStmt /* OUT: Prepared SELECT statement */
|
||||
){
|
||||
int rc = SQLITE_OK;
|
||||
int i;
|
||||
const char *zSep = "";
|
||||
SessionBuffer buf = {0, 0, 0};
|
||||
char *zSql = 0;
|
||||
int nSql = -1;
|
||||
|
||||
sessionAppendStr(&buf, "SELECT * FROM ", &rc);
|
||||
sessionAppendIdent(&buf, zDb, &rc);
|
||||
sessionAppendStr(&buf, ".", &rc);
|
||||
sessionAppendIdent(&buf, zTab, &rc);
|
||||
sessionAppendStr(&buf, " WHERE ", &rc);
|
||||
for(i=0; i<nCol; i++){
|
||||
if( abPK[i] ){
|
||||
sessionAppendStr(&buf, zSep, &rc);
|
||||
sessionAppendIdent(&buf, azCol[i], &rc);
|
||||
sessionAppendStr(&buf, " = ?", &rc);
|
||||
sessionAppendInteger(&buf, i+1, &rc);
|
||||
zSep = " AND ";
|
||||
if( 0==sqlite3_stricmp("sqlite_stat1", zTab) ){
|
||||
zSql = sqlite3_mprintf(
|
||||
"SELECT tbl, ?2, stat FROM %Q.sqlite_stat1 WHERE tbl IS ?1 AND "
|
||||
"idx IS (CASE WHEN ?2=X'' THEN NULL ELSE ?2 END)", zDb
|
||||
);
|
||||
}else{
|
||||
int i;
|
||||
const char *zSep = "";
|
||||
SessionBuffer buf = {0, 0, 0};
|
||||
|
||||
sessionAppendStr(&buf, "SELECT * FROM ", &rc);
|
||||
sessionAppendIdent(&buf, zDb, &rc);
|
||||
sessionAppendStr(&buf, ".", &rc);
|
||||
sessionAppendIdent(&buf, zTab, &rc);
|
||||
sessionAppendStr(&buf, " WHERE ", &rc);
|
||||
for(i=0; i<nCol; i++){
|
||||
if( abPK[i] ){
|
||||
sessionAppendStr(&buf, zSep, &rc);
|
||||
sessionAppendIdent(&buf, azCol[i], &rc);
|
||||
sessionAppendStr(&buf, " IS ?", &rc);
|
||||
sessionAppendInteger(&buf, i+1, &rc);
|
||||
zSep = " AND ";
|
||||
}
|
||||
}
|
||||
zSql = (char*)buf.aBuf;
|
||||
nSql = buf.nBuf;
|
||||
}
|
||||
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = sqlite3_prepare_v2(db, (char *)buf.aBuf, buf.nBuf, ppStmt, 0);
|
||||
rc = sqlite3_prepare_v2(db, zSql, nSql, ppStmt, 0);
|
||||
}
|
||||
sqlite3_free(buf.aBuf);
|
||||
sqlite3_free(zSql);
|
||||
return rc;
|
||||
}
|
||||
|
||||
@@ -3284,7 +3378,7 @@ struct SessionApplyCtx {
|
||||
int nCol; /* Size of azCol[] and abPK[] arrays */
|
||||
const char **azCol; /* Array of column names */
|
||||
u8 *abPK; /* Boolean array - true if column is in PK */
|
||||
|
||||
int bStat1; /* True if table is sqlite_stat1 */
|
||||
int bDeferConstraints; /* True to defer constraints */
|
||||
SessionBuffer constraints; /* Deferred constraints are stored here */
|
||||
};
|
||||
@@ -3454,6 +3548,7 @@ static int sessionUpdateRow(
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
** Formulate and prepare an SQL statement to query table zTab by primary
|
||||
** key. Assuming the following table structure:
|
||||
@@ -3515,6 +3610,47 @@ static int sessionInsertRow(
|
||||
return rc;
|
||||
}
|
||||
|
||||
static int sessionPrepare(sqlite3 *db, sqlite3_stmt **pp, const char *zSql){
|
||||
return sqlite3_prepare_v2(db, zSql, -1, pp, 0);
|
||||
}
|
||||
|
||||
/*
|
||||
** Prepare statements for applying changes to the sqlite_stat1 table.
|
||||
** These are similar to those created by sessionSelectRow(),
|
||||
** sessionInsertRow(), sessionUpdateRow() and sessionDeleteRow() for
|
||||
** other tables.
|
||||
*/
|
||||
static int sessionStat1Sql(sqlite3 *db, SessionApplyCtx *p){
|
||||
int rc = sessionSelectRow(db, "sqlite_stat1", p);
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = sessionPrepare(db, &p->pInsert,
|
||||
"INSERT INTO main.sqlite_stat1 VALUES(?1, "
|
||||
"CASE WHEN length(?2)=0 AND typeof(?2)='blob' THEN NULL ELSE ?2 END, "
|
||||
"?3)"
|
||||
);
|
||||
}
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = sessionPrepare(db, &p->pUpdate,
|
||||
"UPDATE main.sqlite_stat1 SET "
|
||||
"tbl = CASE WHEN ?2 THEN ?3 ELSE tbl END, "
|
||||
"idx = CASE WHEN ?5 THEN ?6 ELSE idx END, "
|
||||
"stat = CASE WHEN ?8 THEN ?9 ELSE stat END "
|
||||
"WHERE tbl=?1 AND idx IS "
|
||||
"CASE WHEN length(?4)=0 AND typeof(?4)='blob' THEN NULL ELSE ?4 END "
|
||||
"AND (?10 OR ?8=0 OR stat IS ?7)"
|
||||
);
|
||||
}
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = sessionPrepare(db, &p->pDelete,
|
||||
"DELETE FROM main.sqlite_stat1 WHERE tbl=?1 AND idx IS "
|
||||
"CASE WHEN length(?2)=0 AND typeof(?2)='blob' THEN NULL ELSE ?2 END "
|
||||
"AND (?4 OR stat IS ?3)"
|
||||
);
|
||||
}
|
||||
assert( rc==SQLITE_OK );
|
||||
return rc;
|
||||
}
|
||||
|
||||
/*
|
||||
** A wrapper around sqlite3_bind_value() that detects an extra problem.
|
||||
** See comments in the body of this function for details.
|
||||
@@ -3845,11 +3981,25 @@ static int sessionApplyOneOp(
|
||||
|
||||
}else{
|
||||
assert( op==SQLITE_INSERT );
|
||||
rc = sessionBindRow(pIter, sqlite3changeset_new, nCol, 0, p->pInsert);
|
||||
if( rc!=SQLITE_OK ) return rc;
|
||||
if( p->bStat1 ){
|
||||
/* Check if there is a conflicting row. For sqlite_stat1, this needs
|
||||
** to be done using a SELECT, as there is no PRIMARY KEY in the
|
||||
** database schema to throw an exception if a duplicate is inserted. */
|
||||
rc = sessionSeekToRow(p->db, pIter, p->abPK, p->pSelect);
|
||||
if( rc==SQLITE_ROW ){
|
||||
rc = SQLITE_CONSTRAINT;
|
||||
sqlite3_reset(p->pSelect);
|
||||
}
|
||||
}
|
||||
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = sessionBindRow(pIter, sqlite3changeset_new, nCol, 0, p->pInsert);
|
||||
if( rc!=SQLITE_OK ) return rc;
|
||||
|
||||
sqlite3_step(p->pInsert);
|
||||
rc = sqlite3_reset(p->pInsert);
|
||||
}
|
||||
|
||||
sqlite3_step(p->pInsert);
|
||||
rc = sqlite3_reset(p->pInsert);
|
||||
if( (rc&0xff)==SQLITE_CONSTRAINT ){
|
||||
rc = sessionConflictHandler(
|
||||
SQLITE_CHANGESET_CONFLICT, p, pIter, xConflict, pCtx, pbReplace
|
||||
@@ -4082,12 +4232,20 @@ static int sessionChangesetApply(
|
||||
}
|
||||
else{
|
||||
sApply.nCol = nCol;
|
||||
if((rc = sessionSelectRow(db, zTab, &sApply))
|
||||
|| (rc = sessionUpdateRow(db, zTab, &sApply))
|
||||
|| (rc = sessionDeleteRow(db, zTab, &sApply))
|
||||
|| (rc = sessionInsertRow(db, zTab, &sApply))
|
||||
){
|
||||
break;
|
||||
if( 0==sqlite3_stricmp(zTab, "sqlite_stat1") ){
|
||||
if( (rc = sessionStat1Sql(db, &sApply) ) ){
|
||||
break;
|
||||
}
|
||||
sApply.bStat1 = 1;
|
||||
}else{
|
||||
if((rc = sessionSelectRow(db, zTab, &sApply))
|
||||
|| (rc = sessionUpdateRow(db, zTab, &sApply))
|
||||
|| (rc = sessionDeleteRow(db, zTab, &sApply))
|
||||
|| (rc = sessionInsertRow(db, zTab, &sApply))
|
||||
){
|
||||
break;
|
||||
}
|
||||
sApply.bStat1 = 0;
|
||||
}
|
||||
}
|
||||
nTab = sqlite3Strlen30(zTab);
|
||||
|
||||
@@ -147,6 +147,35 @@ int sqlite3session_indirect(sqlite3_session *pSession, int bIndirect);
|
||||
**
|
||||
** SQLITE_OK is returned if the call completes without error. Or, if an error
|
||||
** occurs, an SQLite error code (e.g. SQLITE_NOMEM) is returned.
|
||||
**
|
||||
** <h3>Special sqlite_stat1 Handling</h3>
|
||||
**
|
||||
** As of SQLite version 3.22.0, the "sqlite_stat1" table is an exception to
|
||||
** some of the rules above. In SQLite, the schema of sqlite_stat1 is:
|
||||
** <pre>
|
||||
** CREATE TABLE sqlite_stat1(tbl,idx,stat)
|
||||
** </pre>
|
||||
**
|
||||
** Even though sqlite_stat1 does not have a PRIMARY KEY, changes are
|
||||
** recorded for it as if the PRIMARY KEY is (tbl,idx). Additionally, changes
|
||||
** are recorded for rows for which (idx IS NULL) is true. However, for such
|
||||
** rows a zero-length blob (SQL value X'') is stored in the changeset or
|
||||
** patchset instead of a NULL value. This allows such changesets to be
|
||||
** manipulated by legacy implementations of sqlite3changeset_invert(),
|
||||
** concat() and similar.
|
||||
**
|
||||
** The sqlite3changeset_apply() function automatically converts the
|
||||
** zero-length blob back to a NULL value when updating the sqlite_stat1
|
||||
** table. However, if the application calls sqlite3changeset_new(),
|
||||
** sqlite3changeset_old() or sqlite3changeset_conflict on a changeset
|
||||
** iterator directly (including on a changeset iterator passed to a
|
||||
** conflict-handler callback) then the X'' value is returned. The application
|
||||
** must translate X'' to NULL itself if required.
|
||||
**
|
||||
** Legacy (older than 3.22.0) versions of the sessions module cannot capture
|
||||
** changes made to the sqlite_stat1 table. Legacy versions of the
|
||||
** sqlite3changeset_apply() function silently ignore any modifications to the
|
||||
** sqlite_stat1 table that are part of a changeset or patchset.
|
||||
*/
|
||||
int sqlite3session_attach(
|
||||
sqlite3_session *pSession, /* Session object */
|
||||
|
||||
@@ -0,0 +1,186 @@
|
||||
|
||||
# The Zonefile Extension
|
||||
|
||||
## Functionality
|
||||
|
||||
### Creating Zonefile Files
|
||||
|
||||
To create a new zonefile, first create a database table with the following
|
||||
schema:
|
||||
|
||||
> CREATE TABLE data(
|
||||
> k INTEGER PRIMARY KEY,
|
||||
> frame INTEGER DEFAULT -1, -- frame number. Automatic if -1
|
||||
> idx INTEGER DEFAULT -1, -- index of entry within frame. Auto if -1
|
||||
> v BLOB
|
||||
> );
|
||||
|
||||
The table may be created in a persistent or temporary database and may
|
||||
take any name, but must contain the columns above. The table must be
|
||||
populated with a row for each key intended to appear in the new zonefile
|
||||
file.
|
||||
|
||||
Once the table is populated, a zonefile is created using the following
|
||||
SQL:
|
||||
|
||||
> SELECT zonefile_write(<file>, <table> [, <parameters>]);
|
||||
|
||||
where <file> is the name of the file to create on disk, <table>
|
||||
is the name of the database table to read and optional argument
|
||||
<parameters> is a JSON object containing various attributes that
|
||||
influence creation of the zonefile file.
|
||||
|
||||
Currently, the following <parameters> attributes are supported:
|
||||
|
||||
<table border=1>
|
||||
<tr align=left><th>Attribute<th>Default<th>Interpretation
|
||||
<tr valign=top><td>maxAutoFrameSize<td>65536
|
||||
<td>The maximum uncompressed frame size in bytes for automatically generated
|
||||
zonefile frames.
|
||||
|
||||
<tr valign=top><td>compressionTypeContent<td>"none"
|
||||
<td>The compression type used to compress each frame in the zonefile.
|
||||
Valid values are "none" (no compression), "zstd", "zstd_global_dict",
|
||||
"zlib", "brotli", "lz4" and "lz4hc". Not all compression methods are
|
||||
supported by all builds. The compression method supported by a build
|
||||
depends on the combination of SQLITE_HAVE_ZSTD, SQLITE_HAVE_ZLIB,
|
||||
SQLITE_HAVE_BROTLI and SQLITE_HAVE_LZ4 pre-processor symbols defined
|
||||
at build time.
|
||||
|
||||
<tr valign=top><td>compressionTypeIndexData<td>"none"
|
||||
<td>The compression type used to compress the zonefile index structure.
|
||||
All values that are valid for the <i>compressionTypeContent</i> parameter,
|
||||
except for "zstd_global_dict", are also valid for this option.
|
||||
|
||||
<tr valign=top><td>encryptionType<td>"none"
|
||||
<td>The encryption type to use. At present the only valid values are
|
||||
"none" (no encryption) and "xor" (an insecure mock encryption method
|
||||
useful for testing only). Enhanced implementations may support any or
|
||||
all of the following encryption schemes:
|
||||
<ul>
|
||||
<li> "AES_128_CTR"
|
||||
<li> "AES_128_CBC"
|
||||
<li> "AES_256_CTR"
|
||||
<li> "AES_256_CBC"
|
||||
</ul>
|
||||
|
||||
<tr valign=top><td>encryptionKey<td>""
|
||||
<td>The encryption key to use. The encryption key must be specified as an
|
||||
even number of hexadecimal that will be converted to a binary key before
|
||||
use. It is the responsibility of the caller to specify a key of the optimal
|
||||
length for each encryption algorithm (e.g. 16 bytes (32 hex digits) for
|
||||
a 128-bit encryption, or 32 bytes (64 digits) for a 256-bit method).
|
||||
This option is ignored if <i>encryptionType</i> is set to "none".
|
||||
</table>
|
||||
|
||||
For example, to create a zonefile named "test.zonefile" based on the
|
||||
contents of database table "test_input", with a maximum automatic
|
||||
frame size of 4096 bytes and using "xor" encryption with a 128-bit key:
|
||||
|
||||
> SELECT zonefile_write('test.zonefile', 'test_input',
|
||||
> '{"maxAutoFrameSize":4096,
|
||||
> "encryptionType":"xor",
|
||||
> "encryptionKey":"e6e600bc063aad12f6387beab650c48a"
|
||||
> }'
|
||||
> );
|
||||
|
||||
### Using (Reading) Zonefile Files
|
||||
|
||||
To create a new zonefile table, one of the following:
|
||||
|
||||
> CREATE VIRTUAL TABLE z1 USING zonefile;
|
||||
> CREATE VIRTUAL TABLE z1 USING zonefile(cachesize=N);
|
||||
|
||||
where <i>N</i> is any non-zero positive integer. If the zonefile is used
|
||||
to access any files containing compressed or encrypted data, it maintains
|
||||
an LRU cache of uncompressed frame data <i>N</i> frames in size. The
|
||||
default value of <i>N</i> is 1.
|
||||
|
||||
Creating a "zonefile" virtual table actually creates two virtual tables in the
|
||||
database schema. One read-only table named "z1", with a schema equivalent to:
|
||||
|
||||
> CREATE TABLE z1( -- this whole table is read-only
|
||||
> k INTEGER PRIMARY KEY, -- key value
|
||||
> v BLOB, -- associated blob of data
|
||||
> fileid INTEGER, -- file id (rowid value for z1_files)
|
||||
> sz INTEGER -- size of blob of data in bytes
|
||||
> );
|
||||
|
||||
And a read-write table named "z1_files" with a schema like:
|
||||
|
||||
> CREATE TABLE z1_files(
|
||||
> filename TEXT PRIMARY KEY,
|
||||
> ekey BLOB, -- encryption key
|
||||
> header JSON HIDDEN -- read-only
|
||||
> );
|
||||
|
||||
Both tables are initially empty. To add a zonefile to the index, insert a
|
||||
row into the "z1_files" table:
|
||||
|
||||
> INSERT INTO z1_files(filename) VALUES(<filename>);
|
||||
|
||||
If the file is an encrypted file, then the encryption key (a blob) must
|
||||
be inserted into the "ekey" column. Encryption keys are not stored in the
|
||||
database, they are held in main-memory only. This means that each new
|
||||
connection must configure encryption key using UPDATE statements before
|
||||
accessing any encrypted files. For example:
|
||||
|
||||
> -- Add new encrypted file to database:
|
||||
> INSERT INTO z1_files(filename, ekey) VALUES(<filename>, <ekey>);
|
||||
>
|
||||
> -- Configure encryption key for existing file after opening database:
|
||||
> UPDATE z1_files SET ekey = <ekey> WHERE filename = <filename>;
|
||||
|
||||
Currently, values provided for any columns other than "filename" and
|
||||
"ekey" are ignored. Files are removed from the index by deleting rows
|
||||
from the z1_files table:
|
||||
|
||||
> DELETE FROM z1_files WHERE filename = <filename>;
|
||||
|
||||
Once zonefile files have been added to the index, their contents are
|
||||
visible in table "z1". To retrieve the value associated with a single
|
||||
key from one of the zonefile files in the index:
|
||||
|
||||
> SELECT v FROM z1 WHERE k = <key>;
|
||||
|
||||
|
||||
## Notes
|
||||
|
||||
* Contrary to the spec, the implementation uses 32-bit (not 16-bit) frame
|
||||
numbers. So the KeyOffsetPair structure becomes:
|
||||
|
||||
KeyOffsetPair
|
||||
{
|
||||
uint64 key;
|
||||
uint32 frameNo;
|
||||
uint32 frameByteOffset;
|
||||
};
|
||||
|
||||
Also, the ZonefileHeader.numFrames field is now 32-bit. Which makes
|
||||
the ZonefileHeader structure 26 bytes in size. The implementation
|
||||
pads this out to 32 bytes so that the ZoneFileIndex is 8-byte aligned.
|
||||
|
||||
* Multi-byte integer values are big-endian.
|
||||
|
||||
* The offsets in the ZoneFileIndex.byteOffsetZoneFrame[] array are
|
||||
relative to the offset in ZoneFileHeader.byteOffsetFrames. This is
|
||||
necessary as we may not know the offset of the start of the frame data
|
||||
until after the ZoneFileIndex structure is compressed.
|
||||
|
||||
* The offsets in the ZoneFileIndex.byteOffsetZoneFrame[] array are the
|
||||
offsets for the first byte past the end of the corresponding frame.
|
||||
For example, byteOffsetZoneFrame[] identifies the first byte of the
|
||||
second frame, and byteOffsetZoneFrame[numFrames-1] is one byte past
|
||||
the end of the last frame in the file.
|
||||
|
||||
This is better as if we store the starting offset of each frame, there
|
||||
is no way to determine the size of the last frame in the file without
|
||||
trusting the filesize itself.
|
||||
|
||||
* Currently there is no support at all for encryption.
|
||||
|
||||
* Zonefile currently uses json1 to parse the json argument to
|
||||
zonefile\_write(). And so must be used with an SQLITE\_ENABLE\_JSON1
|
||||
or otherwise json1-enabled SQLite.
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,644 @@
|
||||
# 2018 Feb 11
|
||||
#
|
||||
# The author disclaims copyright to this source code. In place of
|
||||
# a legal notice, here is a blessing:
|
||||
#
|
||||
# May you do good and not evil.
|
||||
# May you find forgiveness for yourself and forgive others.
|
||||
# May you share freely, never taking more than you give.
|
||||
#
|
||||
#***********************************************************************
|
||||
#
|
||||
# The focus of this file is testing the zonefile extension.
|
||||
#
|
||||
|
||||
if {![info exists testdir]} {
|
||||
set testdir [file join [file dirname [info script]] .. .. test]
|
||||
}
|
||||
source [file join $testdir tester.tcl]
|
||||
set testprefix zonefile1
|
||||
load_static_extension db zonefile
|
||||
|
||||
do_execsql_test 1.0 {
|
||||
CREATE TABLE zz(k INTEGER PRIMARY KEY, frame INTEGER, idx INTEGER, v BLOB);
|
||||
INSERT INTO zz VALUES(1, -1, -1, randomblob(100));
|
||||
INSERT INTO zz VALUES(2, -1, -1, randomblob(100));
|
||||
INSERT INTO zz VALUES(3, -1, -1, randomblob(100));
|
||||
}
|
||||
|
||||
do_execsql_test 1.1 {
|
||||
SELECT zonefile_write('test.zonefile', 'zz');
|
||||
} {{}}
|
||||
|
||||
do_execsql_test 1.2 {
|
||||
CREATE VIRTUAL TABLE z1 USING zonefile;
|
||||
SELECT name FROM sqlite_master WHERE name LIKE 'z1%' ORDER BY 1;
|
||||
} {z1 z1_files z1_shadow_file z1_shadow_idx}
|
||||
|
||||
do_execsql_test 1.3 {
|
||||
INSERT INTO z1_files(filename) VALUES('test.zonefile');
|
||||
SELECT filename,
|
||||
json_extract(header, '$.magicNumber'),
|
||||
json_extract(header, '$.numFrames'),
|
||||
json_extract(header, '$.numKeys')
|
||||
FROM z1_files;
|
||||
} {test.zonefile 1179332920 1 3}
|
||||
|
||||
do_execsql_test 1.4 { SELECT count(*) FROM z1_shadow_idx } 3
|
||||
|
||||
do_execsql_test 1.5.1 { SELECT k FROM z1 } {1 2 3}
|
||||
do_execsql_test 1.5.2 { SELECT fileid FROM z1 } {1 1 1}
|
||||
do_execsql_test 1.5.4 { SELECT sz FROM z1 } {100 100 100}
|
||||
|
||||
do_execsql_test 1.5.5 {
|
||||
SELECT zz.v==z1.v FROM zz, z1 WHERE zz.k=z1.k
|
||||
} {1 1 1}
|
||||
|
||||
do_execsql_test 1.5 {
|
||||
DELETE FROM z1_files;
|
||||
SELECT * FROM z1_files;
|
||||
} {}
|
||||
|
||||
do_execsql_test 1.6 { SELECT count(*) FROM z1_shadow_idx } 0
|
||||
|
||||
do_execsql_test 1.7 { DROP TABLE z1 }
|
||||
|
||||
do_execsql_test 1.8 {
|
||||
SELECT * FROM sqlite_master WHERE name LIKE 'z1%';
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
# Figure out which compression algorithms, if any, are supported by
|
||||
# this build. Populate the global list $COMPRESSION_METHODS with the
|
||||
# result.
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
do_execsql_test 2.0 {
|
||||
CREATE TABLE bb(
|
||||
k INTEGER PRIMARY KEY,
|
||||
frame INTEGER DEFAULT -1,
|
||||
idx INTEGER DEFAULT -1,
|
||||
v BLOB
|
||||
);
|
||||
INSERT INTO bb(k, v) VALUES(1, randomblob(100));
|
||||
}
|
||||
set COMPRESSION_METHODS [list]
|
||||
foreach cmp {
|
||||
none zlib zstd zstd_global_dict lz4 lz4hc brotli nosuchcmp
|
||||
} {
|
||||
set res [catchsql {
|
||||
WITH p(n,v) AS (
|
||||
VALUES('compressionTypeContent', $cmp)
|
||||
)
|
||||
SELECT zonefile_write('test.zonefile', 'bb', json_group_object(n,v)) FROM p;
|
||||
}]
|
||||
|
||||
if {[lindex $res 0]==0} {
|
||||
lappend COMPRESSION_METHODS $cmp
|
||||
}
|
||||
}
|
||||
|
||||
# Check that it is not possible to use zstd_global_dict to compress
|
||||
# the zonefile index.
|
||||
#
|
||||
if {[lsearch $COMPRESSION_METHODS zstd_global_dict]>=0} {
|
||||
do_catchsql_test 2.1 {
|
||||
WITH p(n,v) AS (
|
||||
VALUES('compressionTypeIndexData', 'zstd_global_dict')
|
||||
)
|
||||
SELECT zonefile_write('test.zonefile', 'bb', json_group_object(n,v)) FROM p;
|
||||
} {1 {compressor "zstd_global_dict" may not be used to compress the zonefile index}}
|
||||
}
|
||||
|
||||
set extra_header 0
|
||||
set cachesize 0
|
||||
foreach cmp $COMPRESSION_METHODS { foreach cmpidx $COMPRESSION_METHODS {
|
||||
if {$cmpidx == "zstd_global_dict"} continue
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
|
||||
set tn "$cmp/$cmpidx"
|
||||
set extra_header [expr {$extra_header ? 0 : 100}]
|
||||
set cachesize [expr {$cachesize ? 0 : 10}]
|
||||
|
||||
do_execsql_test 2.$tn.0.1 {
|
||||
CREATE TABLE zz(
|
||||
k INTEGER PRIMARY KEY,
|
||||
frame INTEGER DEFAULT -1,
|
||||
idx INTEGER DEFAULT -1,
|
||||
v BLOB
|
||||
);
|
||||
CREATE TABLE rt(k INTEGER PRIMARY KEY, v BLOB);
|
||||
}
|
||||
|
||||
do_execsql_test 2.$tn.0.2 "
|
||||
CREATE VIRTUAL TABLE zone USING zonefile(cachesize = $cachesize)
|
||||
" {}
|
||||
|
||||
set nMinByte 0
|
||||
set nMaxByte 444
|
||||
foreach {zonefile lKey} {
|
||||
test1.zonefile {195 1238 298 405 297}
|
||||
test2.zonefile {124 1624 82 1929}
|
||||
test3.zonefile {932 683 1751 410 41}
|
||||
test4.zonefile {427 1491}
|
||||
test5.zonefile {1004 473 801 394 1672 816 1577}
|
||||
test6.zonefile {1374 1454 1005}
|
||||
test7.zonefile {450 241 319 133}
|
||||
test8.zonefile {1414 900 1406 1917 127 673}
|
||||
test9.zonefile {1192 226 988 1292 718 1345 1675}
|
||||
test10.zonefile {314}
|
||||
test11.zonefile {1177 1597 60 532 291 1164 812}
|
||||
test12.zonefile {1168 1290 1585 939 1916}
|
||||
test13.zonefile {644 1784 1476 1283 433 506}
|
||||
test14.zonefile {1141 1547 1506 364}
|
||||
test15.zonefile {1756 1885 844 1880 1896 354}
|
||||
test16.zonefile {1383 1928 1371}
|
||||
test17.zonefile {93}
|
||||
test18.zonefile {1067}
|
||||
test19.zonefile {642}
|
||||
test20.zonefile {1380 1857}
|
||||
test21.zonefile {288 293 1968 1207 1739 231 300}
|
||||
test22.zonefile {651 1007 607 830 299 1431}
|
||||
test23.zonefile {81 1651 543 1949 256 119 1088}
|
||||
test24.zonefile {1278 2024 682 1115 194 636 1804}
|
||||
test25.zonefile {514 1155 171 2015 791}
|
||||
test26.zonefile {1615 1228 147 1464}
|
||||
test27.zonefile {55 1130 781 678 78}
|
||||
test28.zonefile {1981 1401 1178}
|
||||
test29.zonefile {1754 864 183 1953 1901}
|
||||
test30.zonefile {1461 817}
|
||||
test31.zonefile {1720 1722 686 1833}
|
||||
} {
|
||||
forcedelete $zonefile
|
||||
execsql { DELETE FROM zz; }
|
||||
foreach k $lKey {
|
||||
execsql { INSERT INTO zz(k, v) VALUES($k, randomblob($k)) }
|
||||
}
|
||||
execsql { INSERT INTO rt SELECT k, v FROM zz }
|
||||
execsql {
|
||||
WITH p(n,v) AS (
|
||||
VALUES('maxAutoFrameSize', 2000) UNION ALL
|
||||
VALUES('compressionTypeIndexData', $cmpidx) UNION ALL
|
||||
VALUES('compressionTypeContent', $cmp) UNION ALL
|
||||
VALUES('debugExtendedHeaderSize', $extra_header)
|
||||
)
|
||||
SELECT zonefile_write($zonefile, 'zz', json_group_object(n, v)) FROM p;
|
||||
INSERT INTO zone_files(filename) VALUES($zonefile);
|
||||
}
|
||||
}
|
||||
|
||||
do_execsql_test 2.$tn.1 {
|
||||
SELECT k FROM zone JOIN rt USING (k) WHERE zone.v!=rt.v
|
||||
}
|
||||
do_execsql_test 2.$tn.2 {
|
||||
SELECT count(*) FROM zone JOIN rt USING (k);
|
||||
} {135}
|
||||
do_execsql_test 2.$tn.3 {
|
||||
SELECT filename,
|
||||
json_extract(header, '$.numKeys'),
|
||||
json_extract(header, '$.numFrames')
|
||||
FROM zone_files
|
||||
WHERE filename IN ('test19.zonefile', 'test20.zonefile', 'test21.zonefile')
|
||||
ORDER BY 1
|
||||
} {
|
||||
test19.zonefile 1 1
|
||||
test20.zonefile 2 2
|
||||
test21.zonefile 7 4
|
||||
}
|
||||
}}
|
||||
|
||||
#--------------------------------------------------------------------------
|
||||
#
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
do_execsql_test 3.0 {
|
||||
CREATE TABLE dd(k INTEGER PRIMARY KEY, frame INTEGER, idx INTEGER, v BLOB);
|
||||
INSERT INTO dd VALUES(1000, 1, -1, randomblob(44));
|
||||
INSERT INTO dd VALUES(1001, 1, -1, randomblob(55));
|
||||
INSERT INTO dd VALUES(1002, 2, -1, randomblob(66));
|
||||
WITH p(n,v) AS (
|
||||
VALUES('maxAutoFrameSize', 2000) UNION ALL
|
||||
VALUES('encryptionType', 'xor') UNION ALL
|
||||
VALUES('debugEncryptionKeyText', 1) UNION ALL
|
||||
VALUES('encryptionKey', '0123456789')
|
||||
)
|
||||
SELECT zonefile_write('test.zonefile', 'dd', json_group_object(n, v)) FROM p;
|
||||
} {{}}
|
||||
|
||||
do_execsql_test 3.1 {
|
||||
CREATE VIRTUAL TABLE cc USING zonefile;
|
||||
INSERT INTO cc_files(filename,ekey) VALUES('test.zonefile','0123456789');
|
||||
SELECT quote(dd.v)==quote(cc.v) FROM cc JOIN dd USING (k)
|
||||
} {1 1 1}
|
||||
|
||||
do_execsql_test 3.2.1 {
|
||||
DELETE FROM cc_files;
|
||||
INSERT INTO cc_files(filename,ekey) VALUES('test.zonefile','abcdefghij');
|
||||
SELECT quote(dd.v)==quote(cc.v) FROM cc JOIN dd USING (k)
|
||||
} {0 0 0}
|
||||
|
||||
do_execsql_test 3.2.2 {
|
||||
SELECT rowid,sz FROM cc;
|
||||
} {1000 44 1001 55 1002 66}
|
||||
|
||||
do_execsql_test 3.3 {
|
||||
UPDATE cc_files SET ekey = '0123456789';
|
||||
SELECT quote(dd.v)==quote(cc.v) FROM cc JOIN dd USING (k)
|
||||
} {1 1 1}
|
||||
|
||||
close [open test.zonefile w+]
|
||||
do_catchsql_test 3.4 {
|
||||
SELECT header FROM cc_files
|
||||
} {1 {failed to read zonefile header from file "test.zonefile"}}
|
||||
|
||||
forcedelete test.zonefile
|
||||
do_catchsql_test 3.5 {
|
||||
SELECT header FROM cc_files
|
||||
} {1 {failed to open file "test.zonefile" for reading}}
|
||||
|
||||
do_execsql_test 3.6 {
|
||||
SELECT ekey FROM cc_files
|
||||
} {{}}
|
||||
|
||||
forcedelete test.zonefile
|
||||
do_catchsql_test 3.7 {
|
||||
SELECT * FROM cc;
|
||||
} {1 {failed to open file "test.zonefile" for reading}}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
# Check that a file that uses an unknown compression method is handled
|
||||
# correctly (an error is returned).
|
||||
#
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
do_execsql_test 4.0 {
|
||||
CREATE TABLE dd(k INTEGER PRIMARY KEY, frame INTEGER, idx INTEGER, v BLOB);
|
||||
INSERT INTO dd VALUES(1000, 1, -1, randomblob(44));
|
||||
INSERT INTO dd VALUES(1001, 1, -1, randomblob(55));
|
||||
INSERT INTO dd VALUES(1002, 2, -1, randomblob(66));
|
||||
SELECT zonefile_write('test.zonefile', 'dd');
|
||||
CREATE VIRTUAL TABLE x1 USING zonefile;
|
||||
} {{}}
|
||||
|
||||
do_test 4.1 {
|
||||
hexio_write test.zonefile 5 77
|
||||
} {1}
|
||||
do_execsql_test 4.2 {
|
||||
INSERT INTO x1_files(filename) VALUES('test.zonefile');
|
||||
} {}
|
||||
do_catchsql_test 4.3 {
|
||||
SELECT * FROM x1
|
||||
} {1 {unsupported compression method: 119}}
|
||||
do_test 4.4 {
|
||||
hexio_write test.zonefile 4 77
|
||||
} {1}
|
||||
do_catchsql_test 4.5 {
|
||||
DELETE FROM x1_files;
|
||||
INSERT INTO x1_files(filename) VALUES('test.zonefile');
|
||||
} {1 {unsupported compression method: 119}}
|
||||
|
||||
do_test 4.6 {
|
||||
hexio_write test.zonefile 0 00
|
||||
} {1}
|
||||
do_catchsql_test 4.7 {
|
||||
INSERT INTO x1_files(filename) VALUES('test.zonefile');
|
||||
} {1 {failed to read zonefile header from file "test.zonefile"}}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
# Test using various types in the "frame" field of an input table.
|
||||
#
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
if {[lsearch $COMPRESSION_METHODS zlib]>=0} {
|
||||
do_execsql_test 5.0 {
|
||||
CREATE TABLE "a b"(k INTEGER PRIMARY KEY,frame INTEGER,idx INTEGER,v BLOB);
|
||||
INSERT INTO "a b" VALUES(1, 0.5, -1, randomblob(44));
|
||||
INSERT INTO "a b" VALUES(2, 0.5, -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(3, 1.5, -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(4, 1.5, -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(5, 2, -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(6, 2, -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(7, 200, -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(8, 200, -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(9, 300, -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(10, 300, -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(11, NULL, -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(12, NULL, -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(13, 'f1', -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(14, 'f1', -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(15, 'frame2', -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(16, 'frame2', -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(17, x'1234', -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(18, x'1234', -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(19, x'abcd', -1, randomblob(55));
|
||||
INSERT INTO "a b" VALUES(20, x'abcd', -1, randomblob(55));
|
||||
|
||||
SELECT zonefile_write('test.zonefile', 'a b',
|
||||
'{"compressionTypeContent":"zlib"}'
|
||||
);
|
||||
} {{}}
|
||||
|
||||
do_execsql_test 5.1 {
|
||||
CREATE VIRTUAL TABLE abc USING zonefile;
|
||||
INSERT INTO abc_files(filename) VALUES('test.zonefile');
|
||||
SELECT group_concat(k) FROM abc_shadow_idx GROUP BY fofst
|
||||
} {
|
||||
11,12 1,2 3,4 5,6 7,8
|
||||
9,10 13,14 15,16 17,18 19,20
|
||||
}
|
||||
}
|
||||
|
||||
do_execsql_test 6.0 {
|
||||
CREATE TABLE "ab"(k INTEGER PRIMARY KEY,frame INTEGER,idx INTEGER,v BLOB);
|
||||
INSERT INTO "ab" VALUES(1, 0.5, -1, randomblob(44));
|
||||
INSERT INTO "ab" VALUES(2, 0.5, -1, randomblob(55));
|
||||
INSERT INTO "ab" VALUES(3, 1.5, -1, randomblob(55));
|
||||
INSERT INTO "ab" VALUES(4, 1.5, -1, randomblob(55));
|
||||
}
|
||||
do_catchsql_test 6.1.1 {
|
||||
SELECT zonefile_write('test.zonefile', 'ab',
|
||||
'{"debugExtendedHeaderSize":-1}'
|
||||
);
|
||||
} {1 {debugExtendedHeaderSize value out of range: -1}}
|
||||
do_catchsql_test 6.1.2 {
|
||||
SELECT zonefile_write('test.zonefile', 'ab',
|
||||
'{"debugExtendedHeaderSize":256}'
|
||||
);
|
||||
} {1 {debugExtendedHeaderSize value out of range: 256}}
|
||||
|
||||
do_catchsql_test 6.2 {
|
||||
SELECT zonefile_write('test.zonefile', 'ab',
|
||||
'{"unknown":256}'
|
||||
);
|
||||
} {1 {unknown parameter name: "unknown"}}
|
||||
|
||||
forcedelete test.dir
|
||||
file mkdir test.dir
|
||||
do_catchsql_test 6.3 {
|
||||
SELECT zonefile_write('test.dir', 'ab');
|
||||
} {1 {failed to open file "test.dir" for writing}}
|
||||
|
||||
do_catchsql_test 6.4 {
|
||||
CREATE VIRTUAL TABLE zzz USING zonefile;
|
||||
INSERT INTO zzz_files(filename) VALUES('nosuchfile.zonefile');
|
||||
} {1 {failed to open file "nosuchfile.zonefile" for reading}}
|
||||
|
||||
if {$tcl_platform(platform)=="windows"} {
|
||||
do_catchsql_test 6.5 {
|
||||
INSERT INTO zzz_files(filename) VALUES('test.dir');
|
||||
} {1 {failed to open file "test.dir" for reading}}
|
||||
} else {
|
||||
do_catchsql_test 6.5 {
|
||||
INSERT INTO zzz_files(filename) VALUES('test.dir');
|
||||
} {1 {failed to read zonefile header from file "test.dir"}}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
# Check that errors generated when building a dictionary are handled.
|
||||
# The zstd library routines for building a dictionary throw an error
|
||||
# if they are provided with too little data.
|
||||
#
|
||||
# Also test that zstd_global_dict cannot be used to compress the zonefile
|
||||
# index (as there is nowhere in the file format to store the dictionary
|
||||
# for this compression).
|
||||
#
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
if {[lsearch $COMPRESSION_METHODS zstd_global_dict]>=0} {
|
||||
do_execsql_test 7.0 {
|
||||
CREATE TABLE "ab"(k INTEGER PRIMARY KEY,frame INTEGER,idx INTEGER,v BLOB);
|
||||
INSERT INTO "ab" VALUES(1, -1, -1, 'abc');
|
||||
}
|
||||
|
||||
do_catchsql_test 7.1 {
|
||||
SELECT zonefile_write('test.zonefile', 'ab',
|
||||
'{"compressionTypeContent":"zstd_global_dict"}'
|
||||
);
|
||||
} {1 {error generating dictionary}}
|
||||
|
||||
do_catchsql_test 7.2 {
|
||||
SELECT zonefile_write('test.zonefile', 'ab',
|
||||
'{"compressionTypeIndexData":"zstd_global_dict"}'
|
||||
);
|
||||
} {1 {compressor "zstd_global_dict" may not be used to compress the zonefile index}}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
#
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
do_catchsql_test 8.1 {
|
||||
CREATE VIRTUAL TABLE one USING zonefile_files;
|
||||
} {1 {do not create zonefile_files tables directly!}}
|
||||
do_catchsql_test 8.2 {
|
||||
CREATE VIRTUAL TABLE onetwothree USING zonefile_files;
|
||||
} {1 {do not create zonefile_files tables directly!}}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
# A zone file containing zero keys.
|
||||
#
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
do_execsql_test 9.0 {
|
||||
CREATE TABLE s(k INTEGER PRIMARY KEY,frame INTEGER,idx INTEGER,v BLOB);
|
||||
SELECT zonefile_write('test.zonefile', 's');
|
||||
} {{}}
|
||||
do_execsql_test 9.1 {
|
||||
CREATE VIRTUAL TABLE ss USING zonefile;
|
||||
INSERT INTO ss_files(filename) VALUES('test.zonefile');
|
||||
SELECT * FROM ss;
|
||||
} {}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
# Test UPDATE and DELETE statements on the %_files virtual table.
|
||||
#
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
do_execsql_test 10.0 {
|
||||
CREATE TABLE data(k INTEGER PRIMARY KEY, v BLOB);
|
||||
INSERT INTO data(k, v) VALUES(1, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(2, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(3, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(4, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(5, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(6, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(7, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(8, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(9, randomblob(100));
|
||||
|
||||
CREATE VIEW v1 AS
|
||||
SELECT k, -1 AS frame, -1 AS idx, v
|
||||
FROM data WHERE k IN (1,2,3);
|
||||
SELECT zonefile_write('test1.zonefile', 'v1');
|
||||
|
||||
CREATE VIEW v2 AS
|
||||
SELECT k, -1 AS frame, -1 AS idx, v
|
||||
FROM data WHERE k IN (4,5,6);
|
||||
SELECT zonefile_write('test2.zonefile', 'v2');
|
||||
|
||||
CREATE VIEW v3 AS
|
||||
SELECT k, -1 AS frame, -1 AS idx, v
|
||||
FROM data WHERE k IN (7,8,9);
|
||||
SELECT zonefile_write('test3.zonefile', 'v3');
|
||||
} {{} {} {}}
|
||||
|
||||
do_execsql_test 10.1 {
|
||||
CREATE VIRTUAL TABLE "a b" USING zonefile;
|
||||
INSERT INTO "a b_files"(filename) VALUES('test1.zonefile');
|
||||
SELECT k FROM "a b"
|
||||
} {1 2 3}
|
||||
|
||||
do_execsql_test 10.2 {
|
||||
UPDATE "a b_files" SET filename = 'test2.zonefile';
|
||||
SELECT k FROM "a b"
|
||||
} {4 5 6}
|
||||
|
||||
do_execsql_test 10.3 {
|
||||
INSERT INTO "a b_files"(filename) VALUES('test1.zonefile');
|
||||
INSERT INTO "a b_files"(filename) VALUES('test3.zonefile');
|
||||
SELECT k FROM "a b"
|
||||
} {1 2 3 4 5 6 7 8 9}
|
||||
|
||||
do_execsql_test 10.4 {
|
||||
DELETE FROM "a b_files" WHERE filename = 'test2.zonefile';
|
||||
SELECT k FROM "a b"
|
||||
} {1 2 3 7 8 9}
|
||||
|
||||
do_execsql_test 10.5 {
|
||||
DELETE FROM "a b_files" WHERE filename = 'test1.zonefile';
|
||||
SELECT k FROM "a b"
|
||||
} {7 8 9}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
#
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
do_execsql_test 11.0 {
|
||||
CREATE TABLE data(k INTEGER PRIMARY KEY, v BLOB);
|
||||
INSERT INTO data(k, v) VALUES(-1, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(1000, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(-1000, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(9223372036854775807, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(-9223372036854775807, randomblob(100));
|
||||
INSERT INTO data(k, v) VALUES(-9223372036854775808, randomblob(100));
|
||||
|
||||
CREATE VIEW v1 AS SELECT k, -1 AS frame, -1 AS idx, v FROM data;
|
||||
SELECT zonefile_write('test1.zonefile', 'v1');
|
||||
} {{}}
|
||||
|
||||
do_execsql_test 11.1 {
|
||||
CREATE VIRTUAL TABLE one USING zonefile;
|
||||
INSERT INTO "one_files"(filename) VALUES('test1.zonefile');
|
||||
SELECT k FROM one
|
||||
} {-9223372036854775808 -9223372036854775807 -1000 -1 1000 9223372036854775807}
|
||||
|
||||
do_execsql_test 11.2 {
|
||||
SELECT count(*) FROM data JOIN one USING (k) WHERE one.v==data.v
|
||||
} 6
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
#
|
||||
do_catchsql_test 12.1 {
|
||||
CREATE VIRTUAL TABLE nm USING zonefile(abcd)
|
||||
} {1 {parse error in option: abcd}}
|
||||
do_catchsql_test 12.2 {
|
||||
CREATE VIRTUAL TABLE nm USING zonefile(a=b)
|
||||
} {1 {parse error in option: a=b}}
|
||||
do_catchsql_test 12.3 {
|
||||
CREATE VIRTUAL TABLE nm USING zonefile(cachesiza=b)
|
||||
} {1 {parse error in option: cachesiza=b}}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
#
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
do_execsql_test 13.0 {
|
||||
CREATE TABLE data(k INTEGER PRIMARY KEY, v BLOB);
|
||||
WITH s(i) AS (
|
||||
SELECT 1 UNION ALL SELECT i+1 FROM s WHERE i<250
|
||||
)
|
||||
INSERT INTO data SELECT i, randomblob(100) FROM s;
|
||||
CREATE VIEW v1 AS SELECT k, -1 AS frame, -1 AS idx, v FROM data;
|
||||
SELECT zonefile_write('test1.zonefile', 'v1');
|
||||
|
||||
CREATE VIRTUAL TABLE nm USING zonefile;
|
||||
INSERT INTO nm_files(filename) VALUES('test1.zonefile');
|
||||
} {{}}
|
||||
|
||||
foreach {tn cond} {
|
||||
1 "k > 30"
|
||||
2 "k >= 100"
|
||||
3 "k <= 100"
|
||||
4 "k < 55"
|
||||
5 "k LIKE '1%'"
|
||||
6 "k BETWEEN 10 AND 20"
|
||||
7 "k > 100 AND k < 200"
|
||||
} {
|
||||
do_execsql_test 13.1.$tn.1 [subst {
|
||||
SELECT count(*) FROM nm WHERE $cond
|
||||
}] [db one "SELECT count(*) FROM data WHERE $cond"]
|
||||
|
||||
do_execsql_test 13.1.$tn.2 [subst {
|
||||
SELECT count(*) FROM nm WHERE $cond AND
|
||||
v!=(SELECT v FROM data WHERE k=nm.k);
|
||||
}] 0
|
||||
}
|
||||
|
||||
close [open test1.zonefile w+]
|
||||
do_catchsql_test 13.2.1 {
|
||||
SELECT * FROM nm WHERE k=24;
|
||||
} {1 {SQL logic error}}
|
||||
forcedelete test1.zonefile
|
||||
do_catchsql_test 13.2.2 {
|
||||
SELECT * FROM nm WHERE k=24;
|
||||
} {1 {failed to open file "test1.zonefile" for reading}}
|
||||
|
||||
do_catchsql_test 13.3.1 {
|
||||
DELETE FROM nm_shadow_file;
|
||||
SELECT * FROM nm WHERE k=24;
|
||||
} {1 {database disk image is malformed}}
|
||||
do_catchsql_test 13.3.2 {
|
||||
DROP TABLE nm_shadow_file;
|
||||
SELECT * FROM nm WHERE k=24;
|
||||
} {1 {no such table: main.nm_shadow_file}}
|
||||
db close
|
||||
sqlite3 db test.db
|
||||
load_static_extension db zonefile
|
||||
do_catchsql_test 13.3.3 {
|
||||
SELECT * FROM nm WHERE k=24;
|
||||
} {1 {no such table: main.nm_shadow_file}}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
#
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
do_execsql_test 14.0 {
|
||||
CREATE TABLE data(k INTEGER PRIMARY KEY, frame, idx, v BLOB);
|
||||
INSERT INTO data VALUES(1, 1, -1, randomblob(200));
|
||||
INSERT INTO data VALUES(2, 2, -1, randomblob(200));
|
||||
INSERT INTO data VALUES(3, 3, -1, randomblob(200));
|
||||
SELECT zonefile_write('test.zonefile', 'data',
|
||||
'{"encryptionType":"xor","encryptionKey":"pass","debugEncryptionKeyText":1}'
|
||||
);
|
||||
|
||||
CREATE VIRTUAL TABLE nm USING zonefile(cachesize=2);
|
||||
INSERT INTO nm_files(filename,ekey) VALUES('test.zonefile','pass');
|
||||
} {{}}
|
||||
|
||||
set i 0
|
||||
foreach id {1 2 3 2 3 1} {
|
||||
do_execsql_test 14.1.$i {
|
||||
SELECT data.v=nm.v FROM data,nm WHERE data.k=$id AND nm.k=$id
|
||||
} 1
|
||||
incr i
|
||||
}
|
||||
|
||||
if {[file exists /dev/null]} {
|
||||
do_catchsql_test 14.2 {
|
||||
INSERT INTO nm_files(filename) VALUES('/dev/null');
|
||||
} {1 {failed to read zonefile header from file "/dev/null"}}
|
||||
}
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -0,0 +1,285 @@
|
||||
# 2018 Feb 11
|
||||
#
|
||||
# The author disclaims copyright to this source code. In place of
|
||||
# a legal notice, here is a blessing:
|
||||
#
|
||||
# May you do good and not evil.
|
||||
# May you find forgiveness for yourself and forgive others.
|
||||
# May you share freely, never taking more than you give.
|
||||
#
|
||||
#***********************************************************************
|
||||
#
|
||||
# The focus of this file is testing the zonefile extension.
|
||||
#
|
||||
|
||||
package require Tcl 8.6
|
||||
|
||||
if {![info exists testdir]} {
|
||||
set testdir [file join [file dirname [info script]] .. .. test]
|
||||
}
|
||||
source [file join $testdir tester.tcl]
|
||||
set testprefix zonefileenc
|
||||
|
||||
|
||||
foreach {tn code} {
|
||||
1 {
|
||||
set K {
|
||||
braking bramble brambles brambly
|
||||
bran branch branched branches
|
||||
branching branchings brand branded
|
||||
}
|
||||
set textkey 1
|
||||
}
|
||||
2 {
|
||||
set K {
|
||||
5e008542742ce0442e37cbf2512e9492 c91c26e0573ca3464e037568c51126da
|
||||
e90e17489c1aef80ac620c9059271a5a 163338707cbe4c72b18d1058a42c5c78
|
||||
5c6b1e7c7c9e8e4a8d8fdc30dfc11bea ff1012687828ecaac6c9ca86ea0f895e
|
||||
a203f25eb11d4c6afa841dfcf7cd0be0 b6c71e38ca914c460926ef90db39dba0
|
||||
b38255d031d026c258a0a41a9a75d46a adccca5e5ffa3a7625144a345713aef0
|
||||
cd423b38b73e42ce5894405e6d0e08c0 b460ad2e370a0386726d6ea46e7b0bac
|
||||
503b81de72cb3ef87d9346a850040000 369c290a464a6b88bfd9d1c4755afd42
|
||||
a8a9343efca528f2bf23a972be49dd66 e366b5226bfe3fd0010fa814aae3b996
|
||||
4cad7e80124c2cd447131bae377e60f6 4a0fd2f054e1b08cad0de2dc6aa93246
|
||||
8a23c85e3337da2c97d498f806870fa8 8d14e1f055fd9bec7d07cf0e8baae042
|
||||
7f6954b0dc373028ab3b030aaf44dd58 d220164c3898435a946de6bcbb478cc4
|
||||
566af7ea88ba4ff87fd868e858cf98ea a5405832235e8f601516f9c49767bdac
|
||||
1bd5b4dc6b54e5ca92ba67d20bf65740 59da30e203bf73840e38e108b83ddb82
|
||||
e516924c2cdf3114f10f2f0e1bdabbc6 b55dd27222a39764222838007e749984
|
||||
190ae9f81b86a5a024e3b97ee2a7121c 469660843a9a9e507d0fb43e92029296
|
||||
e6e600bc063aad12f6387beef650c48a 3097be5c3a52a2f00747587add01b550
|
||||
}
|
||||
set textkey 0
|
||||
}
|
||||
} {
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
set nFile 100
|
||||
eval $code
|
||||
|
||||
do_execsql_test 1.$tn.0 {
|
||||
CREATE TABLE zz(k INTEGER PRIMARY KEY, frame INTEGER, idx INTEGER, v BLOB);
|
||||
CREATE TABLE rr(k INTEGER PRIMARY KEY, v);
|
||||
}
|
||||
do_test 1.$tn.1 {
|
||||
for {set i 0} {$i < $nFile} {incr i} {
|
||||
set k [lindex $K [expr $i % [llength $K]]]
|
||||
execsql {
|
||||
DELETE FROM zz;
|
||||
INSERT INTO zz VALUES($i*10+1, 1, -1, randomblob(100));
|
||||
INSERT INTO zz VALUES($i*10+2, 2, -1, randomblob(100));
|
||||
INSERT INTO zz VALUES($i*10+3, 1, -1, randomblob(100));
|
||||
INSERT INTO rr SELECT k,v FROM zz;
|
||||
|
||||
WITH p(n,v) AS (
|
||||
VALUES('encryptionType', 'xor') UNION ALL
|
||||
VALUES('debugEncryptionKeyText', $textkey) UNION ALL
|
||||
VALUES('encryptionKey', $k)
|
||||
)
|
||||
SELECT zonefile_write('test' || $i || '.zonefile', 'zz',
|
||||
json_group_object(n, v)
|
||||
) FROM p;
|
||||
}
|
||||
}
|
||||
} {}
|
||||
|
||||
proc k {i} {
|
||||
set val [lindex $::K [expr $i % [llength $::K]]]
|
||||
if {$::textkey==0} {
|
||||
return [binary decode hex $val]
|
||||
}
|
||||
return $val
|
||||
}
|
||||
db func k k
|
||||
|
||||
do_execsql_test 1.$tn.2 {
|
||||
CREATE VIRTUAL TABLE gg USING zonefile;
|
||||
}
|
||||
for {set i 0} {$i < $nFile} {incr i} {
|
||||
do_execsql_test 1.$tn.2.$i {
|
||||
INSERT INTO gg_files(filename, ekey)
|
||||
VALUES('test' || $i || '.zonefile', k($i));
|
||||
SELECT count(*) FROM rr JOIN gg USING(k) WHERE rr.v!=gg.v;
|
||||
} 0
|
||||
}
|
||||
|
||||
db close
|
||||
sqlite3 db test.db
|
||||
load_static_extension db zonefile
|
||||
db func k k
|
||||
|
||||
do_catchsql_test 1.$tn.3 {
|
||||
SELECT count(*) FROM rr JOIN gg USING(k) WHERE rr.v!=gg.v;
|
||||
} {1 {missing encryption key for file "test0.zonefile"}}
|
||||
do_execsql_test 1.$tn.4 {
|
||||
UPDATE gg_files SET ekey = k(0) WHERE filename='test0.zonefile';
|
||||
}
|
||||
do_execsql_test 1.$tn.4.2 {
|
||||
SELECT count(*) FROM rr JOIN gg USING(k)
|
||||
WHERE rr.v==gg.v AND k IN (1,2,3);
|
||||
} {3}
|
||||
do_catchsql_test 1.5 {
|
||||
SELECT count(*) FROM rr JOIN gg USING(k) WHERE rr.v!=gg.v;
|
||||
} {1 {missing encryption key for file "test1.zonefile"}}
|
||||
|
||||
do_execsql_test 1.$tn.6 {
|
||||
UPDATE gg_files SET ekey = k(rowid-1);
|
||||
}
|
||||
do_execsql_test 1.$tn.7 {
|
||||
SELECT count(*) FROM rr JOIN gg USING(k) WHERE rr.v!=gg.v;
|
||||
} {0}
|
||||
do_execsql_test 1.$tn.8 {
|
||||
SELECT count(*) FROM rr JOIN gg USING(k) WHERE rr.v==gg.v;
|
||||
} {300}
|
||||
|
||||
forcedelete test.db2
|
||||
do_execsql_test 1.$tn.9.1 {
|
||||
ATTACH 'test.db2' AS maing;
|
||||
CREATE VIRTUAL TABLE maing.g USING zonefile;
|
||||
INSERT INTO g_files(filename) SELECT filename FROM gg_files;
|
||||
}
|
||||
do_catchsql_test 1.$tn.9.2 {
|
||||
SELECT count(*) FROM rr JOIN g USING(k) WHERE rr.v!=g.v;
|
||||
} {1 {missing encryption key for file "test0.zonefile"}}
|
||||
do_execsql_test 1.$tn.9.3 {
|
||||
UPDATE g_files SET ekey = k(rowid-1);
|
||||
SELECT count(*) FROM rr JOIN g USING(k) WHERE rr.v==g.v;
|
||||
} {300}
|
||||
|
||||
do_execsql_test 1.$tn.10 {
|
||||
SELECT count(*) FROM rr JOIN gg USING(k) WHERE rr.v==gg.v;
|
||||
} {300}
|
||||
}
|
||||
#-------------------------------------------------------------------------
|
||||
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
|
||||
do_execsql_test 2.0 {
|
||||
CREATE TABLE zz(k INTEGER PRIMARY KEY, frame INTEGER, idx INTEGER, v BLOB);
|
||||
}
|
||||
foreach {tn alg id} {
|
||||
1 aes_128_ctr 1
|
||||
2 aes_128_cbc 2
|
||||
3 AES_256_CTR 3
|
||||
4 Aes_256_CBC 4
|
||||
} {
|
||||
do_catchsql_test 2.1.$tn {
|
||||
WITH p(n,v) AS (
|
||||
VALUES('encryptionType', $alg) UNION ALL
|
||||
VALUES('debugEncryptionKeyText', 1) UNION ALL
|
||||
VALUES('encryptionKey', 'secret')
|
||||
)
|
||||
SELECT zonefile_write('test' || $i || '.zonefile', 'zz',
|
||||
json_group_object(n, v)
|
||||
) FROM p;
|
||||
} "1 {unsupported encryption method: $id}"
|
||||
}
|
||||
|
||||
foreach {tn alg} {
|
||||
1 nosuchmethod!
|
||||
} {
|
||||
do_catchsql_test 2.2.$tn {
|
||||
WITH p(n,v) AS (
|
||||
VALUES('encryptionType', $alg) UNION ALL
|
||||
VALUES('debugEncryptionKeyText', 1) UNION ALL
|
||||
VALUES('encryptionKey', 'secret')
|
||||
)
|
||||
SELECT zonefile_write('test' || $i || '.zonefile', 'zz',
|
||||
json_group_object(n, v)
|
||||
) FROM p;
|
||||
} "1 {unknown encryption method: $alg}"
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
# Test some hash collisions in the encryption key table.
|
||||
#
|
||||
|
||||
# This is the same hash function used internally to store keys.
|
||||
#
|
||||
proc hash {zDb zTab iFile} {
|
||||
binary scan $zDb c* A
|
||||
binary scan $zTab c* B
|
||||
set h 0
|
||||
foreach i $A { set h [expr ($h + ($h << 3) + $i) & 0xFFFFFFFF] }
|
||||
foreach i $B { set h [expr ($h + ($h << 3) + $i) & 0xFFFFFFFF] }
|
||||
return [expr $h ^ $iFile]
|
||||
}
|
||||
|
||||
do_test 3.0 {
|
||||
set h1 [expr [hash main zone 1] % 512]
|
||||
for {set i 0} {1} {incr i} {
|
||||
set h2 [expr [hash "aux$i" zone 1] % 512]
|
||||
if {$h1==$h2} break
|
||||
}
|
||||
set i
|
||||
} 52
|
||||
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
forcedelete test.db2
|
||||
|
||||
do_execsql_test 3.1 {
|
||||
CREATE TABLE zz(k INTEGER PRIMARY KEY, frame INTEGER, idx INTEGER, v BLOB);
|
||||
INSERT INTO zz VALUES(222, -1, -1, randomblob(60));
|
||||
WITH p(n,v) AS (
|
||||
VALUES('encryptionType', 'xor') UNION ALL
|
||||
VALUES('debugEncryptionKeyText', 1) UNION ALL
|
||||
VALUES('encryptionKey', 'pass')
|
||||
)
|
||||
SELECT zonefile_write('test1.zonefile', 'zz',
|
||||
json_group_object(n, v)
|
||||
) FROM p;
|
||||
|
||||
DELETE FROM zz;
|
||||
INSERT INTO zz VALUES(333, -1, -1, randomblob(80));
|
||||
WITH p(n,v) AS (
|
||||
VALUES('encryptionType', 'xor') UNION ALL
|
||||
VALUES('debugEncryptionKeyText', 1) UNION ALL
|
||||
VALUES('encryptionKey', 'pass')
|
||||
)
|
||||
SELECT zonefile_write('test2.zonefile', 'zz',
|
||||
json_group_object(n, v)
|
||||
) FROM p;
|
||||
} {{} {}}
|
||||
|
||||
do_execsql_test 3.2 {
|
||||
ATTACH 'test.db2' AS aux52;
|
||||
CREATE VIRTUAL TABLE main.zone USING zonefile;
|
||||
CREATE VIRTUAL TABLE aux52.zone USING zonefile;
|
||||
INSERT INTO main.zone_files(filename, ekey) VALUES('test1.zonefile', 'pass');
|
||||
INSERT INTO aux52.zone_files(filename, ekey) VALUES('test2.zonefile', 'pass');
|
||||
}
|
||||
|
||||
do_execsql_test 3.3 {
|
||||
SELECT v IS NULL FROM main.zone;
|
||||
SELECT v IS NULL FROM aux52.zone;
|
||||
} {0 0}
|
||||
|
||||
do_test 3.4 {
|
||||
set h1 [expr [hash main zone 1] % 512]
|
||||
for {set i 0} {1} {incr i} {
|
||||
set h2 [expr [hash "aux$i" zone 2] % 512]
|
||||
if {$h1==$h2} break
|
||||
}
|
||||
set i
|
||||
} 682
|
||||
|
||||
forcedelete test.db3
|
||||
do_execsql_test 3.5 {
|
||||
ATTACH 'test.db3' AS aux682;
|
||||
CREATE VIRTUAL TABLE aux682.zone USING zonefile;
|
||||
INSERT INTO aux682.zone_files(filename, ekey) VALUES('test1.zonefile','pass');
|
||||
INSERT INTO aux682.zone_files(filename, ekey) VALUES('test2.zonefile','pass');
|
||||
INSERT INTO main.zone_files(filename, ekey) VALUES('test2.zonefile','pass');
|
||||
}
|
||||
|
||||
do_execsql_test 3.6 {
|
||||
SELECT v IS NULL FROM main.zone;
|
||||
SELECT v IS NULL FROM aux682.zone;
|
||||
SELECT v IS NULL FROM main.zone;
|
||||
} {0 0 0 0 0 0}
|
||||
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -0,0 +1,251 @@
|
||||
# 2018 Feb 11
|
||||
#
|
||||
# The author disclaims copyright to this source code. In place of
|
||||
# a legal notice, here is a blessing:
|
||||
#
|
||||
# May you do good and not evil.
|
||||
# May you find forgiveness for yourself and forgive others.
|
||||
# May you share freely, never taking more than you give.
|
||||
#
|
||||
#***********************************************************************
|
||||
#
|
||||
# The focus of this file is testing the zonefile extension.
|
||||
#
|
||||
|
||||
if {![info exists testdir]} {
|
||||
set testdir [file join [file dirname [info script]] .. .. test]
|
||||
}
|
||||
source [file join $testdir tester.tcl]
|
||||
source [file join $testdir malloc_common.tcl]
|
||||
set testprefix zonefilefault
|
||||
load_static_extension db zonefile
|
||||
|
||||
do_execsql_test 1.0 {
|
||||
CREATE TABLE tt(k INTEGER PRIMARY KEY, frame INTEGER, idx INTEGER, v BLOB);
|
||||
INSERT INTO tt VALUES(1, -1, -1, randomblob(100));
|
||||
INSERT INTO tt VALUES(2, -1, -1, randomblob(200));
|
||||
INSERT INTO tt VALUES(3, 1, -1, randomblob(300));
|
||||
INSERT INTO tt VALUES(4, 2, -1, randomblob(400));
|
||||
}
|
||||
|
||||
do_faultsim_test 1.1 -faults oom* -prep {
|
||||
sqlite3 db test.db
|
||||
load_static_extension db zonefile
|
||||
} -body {
|
||||
execsql {
|
||||
SELECT zonefile_write('test.zonefile', 'tt',
|
||||
'{"encryptionType":"xor", "encryptionKey":"secret",
|
||||
"debugEncryptionKeyText":1
|
||||
}'
|
||||
);
|
||||
}
|
||||
} -test {
|
||||
faultsim_test_result {0 {{}}}
|
||||
}
|
||||
|
||||
set sql {
|
||||
SELECT zonefile_write('test.zonefile', 'tt',
|
||||
'{"compressionTypeContent":"zstd_global_dict"}'
|
||||
);
|
||||
}
|
||||
set HAVE_ZSTD 0
|
||||
if {[catch { db eval $sql }]==0} {
|
||||
set HAVE_ZSTD 1
|
||||
}
|
||||
|
||||
if {$HAVE_ZSTD} {
|
||||
do_faultsim_test 1.2 -faults oom* -prep {
|
||||
sqlite3 db test.db
|
||||
load_static_extension db zonefile
|
||||
} -body {
|
||||
execsql {
|
||||
SELECT zonefile_write('test.zonefile', 'tt',
|
||||
'{"compressionTypeContent":"zstd_global_dict"}'
|
||||
);
|
||||
}
|
||||
} -test {
|
||||
faultsim_test_result {0 {{}}}
|
||||
}
|
||||
}
|
||||
|
||||
do_execsql_test 1.3.0 { UPDATE tt SET frame = NULL; }
|
||||
do_faultsim_test 1.3 -faults oom* -prep {
|
||||
sqlite3 db test.db
|
||||
load_static_extension db zonefile
|
||||
} -body {
|
||||
execsql {
|
||||
SELECT zonefile_write('test.zonefile', 'tt');
|
||||
}
|
||||
} -test {
|
||||
faultsim_test_result {0 {{}}}
|
||||
}
|
||||
|
||||
do_execsql_test 1.4.0 {
|
||||
INSERT INTO tt VALUES(5, -1, -1, randomblob(100));
|
||||
INSERT INTO tt VALUES(6, -1, -1, randomblob(100));
|
||||
INSERT INTO tt VALUES(7, -1, -1, randomblob(100));
|
||||
INSERT INTO tt VALUES(8, -1, -1, randomblob(100));
|
||||
INSERT INTO tt VALUES(9, -1, -1, randomblob(100));
|
||||
CREATE VIRTUAL TABLE ttz USING zonefile;
|
||||
}
|
||||
if {$HAVE_ZSTD} {
|
||||
faultsim_save_and_close
|
||||
do_faultsim_test 1.4 -faults oom* -prep {
|
||||
faultsim_restore_and_reopen
|
||||
load_static_extension db zonefile
|
||||
} -body {
|
||||
execsql {
|
||||
SELECT zonefile_write('test.zonefile', 'tt',
|
||||
'{"compressionTypeIndexData":"zstd"}'
|
||||
);
|
||||
}
|
||||
} -test {
|
||||
faultsim_test_result {0 {{}}}
|
||||
}
|
||||
|
||||
faultsim_save_and_close
|
||||
do_faultsim_test 1.5 -faults oom* -prep {
|
||||
faultsim_restore_and_reopen
|
||||
load_static_extension db zonefile
|
||||
} -body {
|
||||
execsql {
|
||||
INSERT INTO ttz_files(filename) VALUES('test.zonefile');
|
||||
}
|
||||
} -test {
|
||||
faultsim_test_result {0 {}}
|
||||
}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
#
|
||||
do_execsql_test 2.0 {
|
||||
SELECT zonefile_write('test.zonefile', 'tt',
|
||||
'{"encryptionType":"xor", "encryptionKey":"secret",
|
||||
"debugEncryptionKeyText":1
|
||||
}'
|
||||
);
|
||||
CREATE VIRTUAL TABLE zz USING zonefile;
|
||||
} {{}}
|
||||
|
||||
faultsim_save_and_close
|
||||
do_faultsim_test 2.1 -faults oom* -prep {
|
||||
faultsim_restore_and_reopen
|
||||
load_static_extension db zonefile
|
||||
} -body {
|
||||
execsql {
|
||||
INSERT INTO zz_files(filename, ekey) VALUES('test.zonefile', 'secret')
|
||||
}
|
||||
} -test {
|
||||
faultsim_test_result {0 {}}
|
||||
}
|
||||
|
||||
faultsim_save_and_close
|
||||
do_faultsim_test 2.2 -faults oom* -prep {
|
||||
faultsim_restore_and_reopen
|
||||
load_static_extension db zonefile
|
||||
} -body {
|
||||
execsql { SELECT json_extract(header, '$.magicNumber') FROM zz_files }
|
||||
} -test {
|
||||
faultsim_test_result {0 1179332920}
|
||||
}
|
||||
|
||||
do_faultsim_test 2.3 -faults oom* -prep {
|
||||
faultsim_restore_and_reopen
|
||||
load_static_extension db zonefile
|
||||
} -body {
|
||||
execsql { DELETE FROM zz_files }
|
||||
} -test {
|
||||
faultsim_test_result {0 {}}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
#
|
||||
reset_db
|
||||
faultsim_save_and_close
|
||||
do_faultsim_test 3.1 -faults oom* -prep {
|
||||
faultsim_restore_and_reopen
|
||||
load_static_extension db zonefile
|
||||
} -body {
|
||||
execsql { CREATE VIRTUAL TABLE t1 USING zonefile(cachesize=5) }
|
||||
} -test {
|
||||
faultsim_test_result {0 {}}
|
||||
}
|
||||
|
||||
faultsim_save_and_close
|
||||
do_faultsim_test 3.2 -faults oom* -prep {
|
||||
faultsim_restore_and_reopen
|
||||
load_static_extension db zonefile
|
||||
} -body {
|
||||
execsql { DROP TABLE t1 }
|
||||
} -test {
|
||||
faultsim_test_result {0 {}}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
#
|
||||
reset_db
|
||||
load_static_extension db zonefile
|
||||
do_execsql_test 4.0 {
|
||||
CREATE TABLE zz(k INTEGER PRIMARY KEY, frame INTEGER, idx INTEGER, v BLOB);
|
||||
INSERT INTO zz VALUES(1, -1, -1, randomblob(100));
|
||||
INSERT INTO zz VALUES(2, -1, -1, randomblob(100));
|
||||
INSERT INTO zz VALUES(3, -1, -1, randomblob(100));
|
||||
SELECT zonefile_write('test.zonefile', 'zz');
|
||||
CREATE VIRTUAL TABLE zone USING zonefile;
|
||||
INSERT INTO zone_files(filename) VALUES('test.zonefile');
|
||||
} {{}}
|
||||
|
||||
faultsim_save_and_close
|
||||
do_faultsim_test 4.1 -faults oom* -prep {
|
||||
faultsim_restore_and_reopen
|
||||
load_static_extension db zonefile
|
||||
} -body {
|
||||
execsql { SELECT v IS NULL FROM zone WHERE k = 2 }
|
||||
} -test {
|
||||
faultsim_test_result {0 0}
|
||||
}
|
||||
|
||||
|
||||
if {$HAVE_ZSTD} {
|
||||
set params {
|
||||
{"encryptionType":"xor","encryptionKey":"pass",
|
||||
"compressionTypeContent":"zstd_global_dict",
|
||||
"debugEncryptionKeyText":1
|
||||
}
|
||||
}
|
||||
} else {
|
||||
set params {
|
||||
{"encryptionType":"xor","encryptionKey":"pass",
|
||||
"debugEncryptionKeyText":1
|
||||
}
|
||||
}
|
||||
}
|
||||
do_execsql_test 4.2 {
|
||||
SELECT zonefile_write('test.zonefile', 'zz', $params);
|
||||
CREATE VIRTUAL TABLE zone2 USING zonefile;
|
||||
INSERT INTO zone2_files(filename,ekey) VALUES('test.zonefile','pass');
|
||||
} {{}}
|
||||
|
||||
faultsim_save_and_close
|
||||
do_faultsim_test 4.3 -faults oom* -prep {
|
||||
faultsim_restore_and_reopen
|
||||
load_static_extension db zonefile
|
||||
execsql { UPDATE zone2_files SET ekey='pass' }
|
||||
} -body {
|
||||
execsql { SELECT v IS NULL FROM zone2 WHERE k = 2 }
|
||||
} -test {
|
||||
faultsim_test_result {0 0}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
do_faultsim_test 4.4 -faults oom* -prep {
|
||||
faultsim_restore_and_reopen
|
||||
} -body {
|
||||
load_static_extension db zonefile
|
||||
} -test {
|
||||
faultsim_test_result {0 {}} {1 {initialization of zonefile failed: }}
|
||||
}
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -372,9 +372,10 @@ TESTSRC += \
|
||||
$(TOP)/ext/misc/wholenumber.c \
|
||||
$(TOP)/ext/misc/vfslog.c \
|
||||
$(TOP)/ext/misc/zipfile.c \
|
||||
$(TOP)/ext/zonefile/zonefile.c \
|
||||
$(TOP)/ext/fts5/fts5_tcl.c \
|
||||
$(TOP)/ext/fts5/fts5_test_mi.c \
|
||||
$(TOP)/ext/fts5/fts5_test_tok.c
|
||||
$(TOP)/ext/fts5/fts5_test_tok.c
|
||||
|
||||
|
||||
#TESTSRC += $(TOP)/ext/fts2/fts2_tokenizer.c
|
||||
@@ -423,6 +424,7 @@ TESTSRC2 = \
|
||||
$(TOP)/ext/fts3/fts3_tokenizer.c \
|
||||
$(TOP)/ext/fts3/fts3_write.c \
|
||||
$(TOP)/ext/async/sqlite3async.c \
|
||||
$(TOP)/ext/misc/stmt.c \
|
||||
$(TOP)/ext/session/sqlite3session.c \
|
||||
$(TOP)/ext/session/test_session.c
|
||||
|
||||
@@ -507,6 +509,7 @@ TESTOPTS = --verbose=file --output=test-out.txt
|
||||
# Extra compiler options for various shell tools
|
||||
#
|
||||
SHELL_OPT += -DSQLITE_ENABLE_JSON1 -DSQLITE_ENABLE_FTS4 -DSQLITE_ENABLE_FTS5
|
||||
SHELL_OPT += -DSQLITE_ENABLE_RTREE
|
||||
SHELL_OPT += -DSQLITE_ENABLE_EXPLAIN_COMMENTS
|
||||
SHELL_OPT += -DSQLITE_ENABLE_UNKNOWN_SQL_FUNCTION
|
||||
SHELL_OPT += -DSQLITE_ENABLE_STMTVTAB
|
||||
@@ -517,6 +520,7 @@ SHELL_OPT += -DSQLITE_INTROSPECTION_PRAGMAS
|
||||
FUZZERSHELL_OPT = -DSQLITE_ENABLE_JSON1
|
||||
FUZZCHECK_OPT = -DSQLITE_ENABLE_JSON1 -DSQLITE_ENABLE_MEMSYS5
|
||||
FUZZCHECK_OPT += -DSQLITE_MAX_MEMORY=50000000
|
||||
FUZZCHECK_OPT += -DSQLITE_PRINTF_PRECISION_LIMIT=1000
|
||||
DBFUZZ_OPT =
|
||||
KV_OPT = -DSQLITE_THREADSAFE=0 -DSQLITE_DIRECT_OVERFLOW_READ
|
||||
ST_OPT = -DSQLITE_THREADSAFE=0
|
||||
|
||||
@@ -1,22 +1,22 @@
|
||||
C Test\scases\sfor\ssqlite3_normalize().
|
||||
D 2018-01-08T20:04:57.992
|
||||
C Update\szonefile\sREADME.md\sfile\sto\smention\sthe\sframe\scache.
|
||||
D 2018-02-27T20:09:45.338
|
||||
F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
|
||||
F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
|
||||
F Makefile.in 822052988bbf6204ca2c3e2665618b5a48acec24105d5afa8c4ebb59cb941d3e
|
||||
F Makefile.in a2d2fb8d17c39ab5ec52beb27850b903949080848236923f436156b72a958737
|
||||
F Makefile.linux-gcc 7bc79876b875010e8c8f9502eb935ca92aa3c434
|
||||
F Makefile.msc 0f2875c7d4cb93ae4dab661f58f9d68699d323cfb87ebd7d8dccbb9949979b83
|
||||
F README.md eeae1e552f93ef72ef7c5b8f6647b368a001c28820ad1df179d3dae602bef681
|
||||
F VERSION 0c10cdfed866fdd2d80434f64f042c3330f1daaed12e54287beb104f04b3faaf
|
||||
F Makefile.msc 738b130a37c8855f46c519cdeab968a483042017b8e90a04a8156e26d6a3769d
|
||||
F README.md 1d5342ebda97420f114283e604e5fe99b0da939d63b76d492eabbaae23488276
|
||||
F VERSION cdf91ac446255ecf3d8f6d8c3ee40d64123235ae5b3cef29d344e61b45ec3759
|
||||
F aclocal.m4 a5c22d164aff7ed549d53a90fa56d56955281f50
|
||||
F art/sqlite370.eps aa97a671332b432a54e1d74ff5e8775be34200c2
|
||||
F art/sqlite370.ico af56c1d00fee7cd4753e8631ed60703ed0fc6e90
|
||||
F art/sqlite370.jpg d512473dae7e378a67e28ff96a34da7cb331def2
|
||||
F autoconf/INSTALL 83e4a25da9fd053c7b3665eaaaf7919707915903
|
||||
F autoconf/Makefile.am 66c0befa511f0d95ba229e180067cf0357a9ebf8b3201b06d683c5ba6220fb39
|
||||
F autoconf/Makefile.am 2c274948734e03c51790ff51468f91db8d570bcca864284d9c6d6e777264cd7e
|
||||
F autoconf/Makefile.msc 2c50a59319af7da4eaca8c13e3240881b1bc245fd175845a055faab7d03d6e67
|
||||
F autoconf/README.first 6c4f34fe115ff55d4e8dbfa3cecf04a0188292f7
|
||||
F autoconf/README.txt 4f04b0819303aabaa35fff5f7b257fb0c1ef95f1
|
||||
F autoconf/configure.ac 8dd08ca564279fff091c9bfdd2599d8f992c9f1f70c5396de2126ad2bd1b3bed
|
||||
F autoconf/configure.ac 18fca06f884213be062dd5e07c5297079cc45893d9cd3f522ce426e715033e3d
|
||||
F autoconf/tea/Makefile.in b438a7020446c8a8156e8d97c8914a04833da6fd
|
||||
F autoconf/tea/README 3e9a3c060f29a44344ab50aec506f4db903fb873
|
||||
F autoconf/tea/aclocal.m4 52c47aac44ce0ddb1f918b6993e8beb8eee88f43
|
||||
@@ -32,7 +32,7 @@ F autoconf/tea/win/rules.vc c511f222b80064096b705dbeb97060ee1d6b6d63
|
||||
F config.guess 226d9a188c6196f3033ffc651cbc9dcee1a42977
|
||||
F config.h.in 6376abec766e9a0785178b1823b5a587e9f1ccbc
|
||||
F config.sub 9ebe4c3b3dab6431ece34f16828b594fb420da55
|
||||
F configure 9af547be0e0e1a8fca8553b82599b5a3be1528a3d78deb68cb49d3b611215cb7 x
|
||||
F configure 2c71f331b463e987567a2dd942f728534f1aa7a174551e08a7b31b328e9da4ff x
|
||||
F configure.ac d4529ebb26ae046269334f1dac65f2b1d6927c2efe22b2ec24dce24dfe4f83dd
|
||||
F contrib/sqlitecon.tcl 210a913ad63f9f991070821e599d600bd913e0ad
|
||||
F doc/lemon.html 278113807f49d12d04179a93fab92b5b917a08771152ca7949d34e928efa3941
|
||||
@@ -44,10 +44,10 @@ F ext/async/sqlite3async.c 0f3070cc3f5ede78f2b9361fb3b629ce200d7d74
|
||||
F ext/async/sqlite3async.h f489b080af7e72aec0e1ee6f1d98ab6cf2e4dcef
|
||||
F ext/expert/README.md b321c2762bb93c18ea102d5a5f7753a4b8bac646cb392b3b437f633caf2020c3
|
||||
F ext/expert/expert.c 4791c5e064aea81b2b829fa95228b22283380ee370ea88a1e580103b75516ebf
|
||||
F ext/expert/expert1.test 0c71a3453ce3a0b4dbe952713aec0ae8d416dd846820dd027b08f305f5278b30
|
||||
F ext/expert/sqlite3expert.c 252f3129f12a0e9df094a14711db98265c9c6d7afa033ec906d94e920f5c7ba7
|
||||
F ext/expert/expert1.test fd21496d8e52c817a7741f467f42b0502c0ac7e07dcdd1d6e15a3e8154ed4e41
|
||||
F ext/expert/sqlite3expert.c 1dfa561e64dc0f89d56b96e6afda87468c34b43604c2df50c47e3f4362778fb2
|
||||
F ext/expert/sqlite3expert.h af6354f8ee5c9e025024e63fec3bd640a802afcc3099a44d804752cf0791d811
|
||||
F ext/expert/test_expert.c 85f5c743a899063fa48296d21de2f32c26d09a21c8582b2a0bc482e8de183e7a
|
||||
F ext/expert/test_expert.c d56c194b769bdc90cf829a14c9ecbc1edca9c850b837a4d0b13be14095c32a72
|
||||
F ext/fts1/README.txt 20ac73b006a70bcfd80069bdaf59214b6cf1db5e
|
||||
F ext/fts1/ft_hash.c 3927bd880e65329bdc6f506555b228b28924921b
|
||||
F ext/fts1/ft_hash.h 06df7bba40dadd19597aa400a875dbc2fed705ea
|
||||
@@ -96,7 +96,7 @@ F ext/fts3/fts3_tokenizer.h 64c6ef6c5272c51ebe60fc607a896e84288fcbc3
|
||||
F ext/fts3/fts3_tokenizer1.c 5c98225a53705e5ee34824087478cf477bdb7004
|
||||
F ext/fts3/fts3_unicode.c 525a3bd9a7564603c5c061b7de55403a565307758a94600e8a2f6b00d1c40d9d
|
||||
F ext/fts3/fts3_unicode2.c cc04fc672bfd42b1e650398cb0bf71f64f9aae032cfe75bbcfe75b9cf966029c
|
||||
F ext/fts3/fts3_write.c a3f7bf869622d1d0aa66661ba71d88e6f9646d69a2c335f40a0addf25974db47
|
||||
F ext/fts3/fts3_write.c b583dede85eb0c3c3026f8d7ccb781ea4e845ae583754fecb2ca425b5907d87d
|
||||
F ext/fts3/fts3speed.tcl b54caf6a18d38174f1a6e84219950d85e98bb1e9
|
||||
F ext/fts3/mkfts3amal.tcl 252ecb7fe6467854f2aa237bf2c390b74e71f100
|
||||
F ext/fts3/tool/fts3cov.sh c331d006359456cf6f8f953e37f2b9c7d568f3863f00bb5f7eb87fea4ac01b73
|
||||
@@ -113,10 +113,10 @@ F ext/fts5/fts5_buffer.c 1dd1ec0446b3acfc2d7d407eb894762a461613e2695273f48e449bf
|
||||
F ext/fts5/fts5_config.c 5af9c360e99669d29f06492c370892394aba0857
|
||||
F ext/fts5/fts5_expr.c 01048018d21524e2c302b063ff5c3cdcf546e03297215e577205d85b47499deb
|
||||
F ext/fts5/fts5_hash.c 32be400cf761868c9db33efe81a06eb19a17c5402ad477ee9efb51301546dd55
|
||||
F ext/fts5/fts5_index.c 5fe14375a29e8a7aa8f3e863babe180a19269206c254c8f47b216821d4ac1e15
|
||||
F ext/fts5/fts5_index.c 22b71d0e9e4b3ddd123a39ae27174e0012da2806f91b64087a68584f13f189de
|
||||
F ext/fts5/fts5_main.c 24868f88ab2a865defbba7a92eebeb726cc991eb092b71b5f5508f180c72605b
|
||||
F ext/fts5/fts5_storage.c fb5ef3c27073f67ade2e1bea08405f9e43f68f5f3676ed0ab7013bce5ba10be6
|
||||
F ext/fts5/fts5_tcl.c b470467be4c5cab2d8b026992c05d86cd2293e7d8c4a10ba56d5f4f707981097
|
||||
F ext/fts5/fts5_storage.c 4bec8a1b3905978b22a67bca5f4a3cfdb94af234cf51efb36f4f2d733d278634
|
||||
F ext/fts5/fts5_tcl.c 39bcbae507f594aad778172fa914cad0f585bf92fd3b078c686e249282db0d95
|
||||
F ext/fts5/fts5_test_mi.c 65864ba1e5c34a61d409c4c587e0bbe0466eb4f8f478d85dc42a92caad1338e6
|
||||
F ext/fts5/fts5_test_tok.c ffd657dd67e7fcdb31bf63fb60b6d867299a581d0f46e97086abacd66c2a9b26
|
||||
F ext/fts5/fts5_tokenize.c 2ce7b44183538ec46b7907726262ee43ffdd39a8
|
||||
@@ -126,7 +126,7 @@ F ext/fts5/fts5_vocab.c 1cd79854cb21543e66507b25b0578bc1b20aa6a1349b7feceb8e8fed
|
||||
F ext/fts5/fts5parse.y eb526940f892ade5693f22ffd6c4f2702543a9059942772526eac1fde256bb05
|
||||
F ext/fts5/mkportersteps.tcl 5acf962d2e0074f701620bb5308155fa1e4a63ba
|
||||
F ext/fts5/test/fts5_common.tcl b01c584144b5064f30e6c648145a2dd6bc440841
|
||||
F ext/fts5/test/fts5aa.test cba3fae6466446980caf1b9f5f26df77f95a999d35db7d932d6e82ae7ba0ede9
|
||||
F ext/fts5/test/fts5aa.test 6e2fdb0ee667c05f41921e7ec345cae874be651670900918e9ccc539514b9356
|
||||
F ext/fts5/test/fts5ab.test 9205c839332c908aaad2b01ab8670ece8b161e8f2ec8a9fabf18ca9385880bb7
|
||||
F ext/fts5/test/fts5ac.test a7aa7e1fefc6e1918aa4d3111d5c44a09177168e962c5fd2cca9620de8a7ed6d
|
||||
F ext/fts5/test/fts5ad.test e8cf959dfcd57c8e46d6f5f25665686f3b6627130a9a981371dafdf6482790de
|
||||
@@ -165,10 +165,10 @@ F ext/fts5/test/fts5fault2.test 69c8fdbef830cd0d450908d4504d5bb86609e255af99c421
|
||||
F ext/fts5/test/fts5fault3.test da2f9e3e56ff5740d68ebdd6877c97089e7ed28ddff28a0da87a6afea27e5522
|
||||
F ext/fts5/test/fts5fault4.test 1c1db5fcfe59401e7833146100f1d8de284a0a686fac31ddac9fb56c459f725b
|
||||
F ext/fts5/test/fts5fault5.test a336e4e11847de24c9497f80cce18e00bb3fab7fb11f97d04eb9af898900a762
|
||||
F ext/fts5/test/fts5fault6.test 8a3c61402e36960ba46a419e73121fcefdc9160e0c04b6f5318c7fb0e3180dbc
|
||||
F ext/fts5/test/fts5fault6.test a0fc0a8f99e4b16500c31dfc7e38e1defe0f1693ac47650517ac7b723b1956f8
|
||||
F ext/fts5/test/fts5fault7.test 0acbec416edb24b8881f154e99c31e9ccf73f539cfcd164090be139e9e97ed4c
|
||||
F ext/fts5/test/fts5fault8.test 318238659d35f82ad215ecb57ca4c87486ea85d45dbeedaee42f148ff5105ee2
|
||||
F ext/fts5/test/fts5fault9.test 0111b229388bdf251b91cfead68580227801dd30960a19aa8fe9021a1e73cb6d
|
||||
F ext/fts5/test/fts5fault9.test 098e6b894bbdf9b2192f994a30f4043673fb3f338b6b8ab1624c704422f39119
|
||||
F ext/fts5/test/fts5faultA.test be4487576bff8c22cee6597d1893b312f306504a8c6ccd3c53ca85af12290c8c
|
||||
F ext/fts5/test/fts5faultB.test e6d04f9ea7b21be1d89abb8df2cb4baf65b0453b744d5a805fcd3ef45ff86a7e
|
||||
F ext/fts5/test/fts5faultD.test cc5d1225556e356615e719c612e845d41bff7d5a
|
||||
@@ -265,11 +265,11 @@ F ext/lsm1/lsm_win32.c 0a4acbd7e8d136dd3a5753f0a9e7a9802263a9d96cef3278cf120bcaa
|
||||
F ext/lsm1/test/lsm1_common.tcl 5ed4bab07c93be2e4f300ebe46007ecf4b3e20bc5fbe1dedaf04a8774a6d8d82
|
||||
F ext/lsm1/test/lsm1_simple.test ca949efefa102f4644231dcd9291d8cda7699a4ce1006b26e0e3fcb72233f422
|
||||
F ext/lsm1/tool/mklsm1c.tcl f31561bbee5349f0a554d1ad7236ac1991fc09176626f529f6078e07335398b0
|
||||
F ext/misc/README.md 8e008c8d2b02e09096b31dfba033253ac27c6c06a18aa5826e299fa7601d90b2
|
||||
F ext/misc/README.md d6dd0fe1d8af77040216798a6a2b0c46c73054d2f0ea544fbbcdccf6f238c240
|
||||
F ext/misc/amatch.c 6db4607cb17c54b853a2d7c7c36046d004853f65b9b733e6f019d543d5dfae87
|
||||
F ext/misc/anycollseq.c 5ffdfde9829eeac52219136ad6aa7cd9a4edb3b15f4f2532de52f4a22525eddb
|
||||
F ext/misc/appendvfs.c 4c65f0b79686ae5a483134233d7fd912f0f2d4fd76023404f96f2290fff13b19
|
||||
F ext/misc/btreeinfo.c d7fd9a2fe2fa33ba28488e2fce703ebecc759219ea9e0bb3b254784866c0a676
|
||||
F ext/misc/appendvfs.c 3777f22ec1057dc4e5fd89f2fbddcc7a29fbeef1ad038c736c54411bb1967af7
|
||||
F ext/misc/btreeinfo.c 78c8c57d325185ccc04b7679e5b020e34a4d9c87453e6b7ac943d0a26cee3256
|
||||
F ext/misc/carray.c ed96c218ea940b85c9a274c4d9c59fe9491c299147a38a8bba537687bd6c6005
|
||||
F ext/misc/closure.c 0d2a038df8fbae7f19de42e7c7d71f2e4dc88704
|
||||
F ext/misc/completion.c 52c3f01523e3e387eb321b4739a89d1fe47cbe6025aa1f2d8d3685e9e365df0f
|
||||
@@ -277,7 +277,7 @@ F ext/misc/compress.c dd4f8a6d0baccff3c694757db5b430f3bbd821d8686d1fc24df55cf9f0
|
||||
F ext/misc/csv.c 1a009b93650732e22334edc92459c4630b9fa703397cbb3c8ca279921a36ca11
|
||||
F ext/misc/dbdump.c 3509fa6b8932d04e932d6b6b827b6a82ca362781b8e8f3c77336f416793e215e
|
||||
F ext/misc/eval.c f971962e92ebb8b0a4e6b62949463ee454d88fa2
|
||||
F ext/misc/fileio.c 672e89e125846848e07e025cbe601dc370a93433d571d9422541a9cefbd12b76
|
||||
F ext/misc/fileio.c 4cad3a78bfbbea9b1414b4405fd704ee57fbe2621254b011888dae7b0ba8c513
|
||||
F ext/misc/fuzzer.c 7c64b8197bb77b7d64eff7cac7848870235d4c25
|
||||
F ext/misc/ieee754.c f190d0cc5182529acb15babd177781be1ac1718c
|
||||
F ext/misc/json1.c dbe086615b9546c156bf32b9378fc09383b58bd17513b866cfd24c1e15281984
|
||||
@@ -294,17 +294,18 @@ F ext/misc/series.c f3c0dba5c5c749ce1782b53076108f87cf0b71041eb6023f727a9c50681d
|
||||
F ext/misc/sha1.c 0b9e9b855354910d3ca467bf39099d570e73db56
|
||||
F ext/misc/shathree.c 9e960ba50483214c6a7a4b1517f8d8cef799e9db381195178c3fd3ad207e10c0
|
||||
F ext/misc/showauth.c 732578f0fe4ce42d577e1c86dc89dd14a006ab52
|
||||
F ext/misc/spellfix.c 41cf26c6b89fcaa8798ae10ae64d39c1f1d9d6995152e545bd491c13058b8fac
|
||||
F ext/misc/spellfix.c b3a644285cb008f3c10ed4cf04e17adcbc7d62c3911c79d786dfc91c177534f0
|
||||
F ext/misc/sqlar.c 57d5bc45cd5492208e451f697404be88f8612527d64c9d42f96b325b64983d74
|
||||
F ext/misc/stmt.c 6f16443abb3551e3f5813bb13ba19a30e7032830015b0f92fe0c0453045c0a11
|
||||
F ext/misc/totype.c 4a167594e791abeed95e0a8db028822b5e8fe512
|
||||
F ext/misc/unionvtab.c 2aa94902ea646e1aaf6c05eac944a14276cddd67735b2ad856030ffffbb6626c
|
||||
F ext/misc/unionvtab.c 0b3173f69b8899da640a13a345dc5ef1400199405f738abe6145b2454195b8ff
|
||||
F ext/misc/vfslog.c fe40fab5c077a40477f7e5eba994309ecac6cc95
|
||||
F ext/misc/vfsstat.c bf10ef0bc51e1ad6756629e1edb142f7a8db1178
|
||||
F ext/misc/vtablog.c 31d0d8f4406795679dcd3a67917c213d3a2a5fb3ea5de35f6e773491ed7e13c9
|
||||
F ext/misc/vtshim.c 1976e6dd68dd0d64508c91a6dfab8e75f8aaf6cd
|
||||
F ext/misc/wholenumber.c 784b12543d60702ebdd47da936e278aa03076212
|
||||
F ext/misc/zipfile.c 8075df9296beeebc344567927d114c6d3201110a29110013388d233fa7d4fb2c
|
||||
F ext/misc/zipfile.c bc88dbf9aa26c24595d158c1398208786ef34e7aee19ea29e8f0110c752fca03
|
||||
F ext/misc/zorder.c b0ff58fa643afa1d846786d51ea8d5c4b6b35aa0254ab5a82617db92f3adda64
|
||||
F ext/rbu/rbu.c ea7d1b7eb44c123a2a619332e19fe5313500705c4a58aaa1887905c0d83ffc2e
|
||||
F ext/rbu/rbu1.test 43836fac8c7179a358eaf38a8a1ef3d6e6285842
|
||||
F ext/rbu/rbu10.test 1846519a438697f45e9dcb246908af81b551c29e1078d0304fae83f1fed7e9ee
|
||||
@@ -331,6 +332,7 @@ F ext/rbu/rbufault2.test 9a7f19edd6ea35c4c9f807d8a3db0a03a5670c06
|
||||
F ext/rbu/rbufault3.test 0913c1aeaee266d9c36c33179341a5a504aad7d423d1979cfec43c8346a29899
|
||||
F ext/rbu/rbufault4.test 34e70701cbec51571ffbd9fbf9d4e0f2ec495ca7
|
||||
F ext/rbu/rbufts.test a2bbd202c9321fba15fb4a62a90add7d70e07bd8404e1e598135adbfff8a0508
|
||||
F ext/rbu/rbumulti.test 2cf153ab3d5861ff26517dc6cbaec430787a59f1d50e8771fe7a7529a0551cf1
|
||||
F ext/rbu/rbuprogress.test 1849d4e0e50616edf5ce75ce7db86622e656b5cf
|
||||
F ext/rbu/rburesume.test 8acb77f4a422ff55acfcfc9cc15a5cb210b1de83
|
||||
F ext/rbu/rbusave.test 0f43b6686084f426ddd040b878426452fd2c2f48
|
||||
@@ -350,14 +352,14 @@ F ext/repair/test/checkfreelist01.test 3e8aa6aeb4007680c94a8d07b41c339aa635cc782
|
||||
F ext/repair/test/checkindex01.test 6945d0ffc0c1dc993b2ce88036b26e0f5d6fcc65da70fc9df27c2647bb358b0f
|
||||
F ext/repair/test/test.tcl 686d76d888dffd021f64260abf29a55c57b2cedfa7fc69150b42b1d6119aac3c
|
||||
F ext/rtree/README 6315c0d73ebf0ec40dedb5aa0e942bc8b54e3761
|
||||
F ext/rtree/rtree.c 2111f685ae07988622c241f819b56fea60782f56e32f97e334473c59f6083481
|
||||
F ext/rtree/rtree.h 834dbcb82dc85b2481cde6a07cdadfddc99e9b9e
|
||||
F ext/rtree/rtree1.test 82a353747fcab1083d114b2ac84723dfefdbf86c1a6e1df57bf588c7d4285436
|
||||
F ext/rtree/rtree.c bc61010e978b5b8ae6dbb90274a2fbb5db5ff5e2880b5c6e8abd48eea77264db
|
||||
F ext/rtree/rtree.h 4a690463901cb5e6127cf05eb8e642f127012fd5003830dbc974eca5802d9412
|
||||
F ext/rtree/rtree1.test 47e2095bebea6813754fd7afa6a20e2b7b4ebcd5cb7dbcb6932b6c9f86bbf972
|
||||
F ext/rtree/rtree2.test 5f25b01acd03470067a2d52783b2eb0a50bf836803d4342d20ca39e541220fe2
|
||||
F ext/rtree/rtree3.test 2cafe8265d1ff28f206fce88d114f208349df482
|
||||
F ext/rtree/rtree4.test 67b021858ba4334c8d49b3449476942c2ce0e5ef7123538f2e9dd508ed03a12d
|
||||
F ext/rtree/rtree5.test 8aaa4bcdc42f718fe165572f5623e4732831aca95a2bc32482d33d4d2cf1325d
|
||||
F ext/rtree/rtree6.test 773a90db2dce6a8353dd0d5b64bca69b29761196
|
||||
F ext/rtree/rtree4.test 304de65d484540111b896827e4261815e5dca4ce28eeecd58be648cd73452c4b
|
||||
F ext/rtree/rtree5.test 49c9041d713d54560b315c2c7ef7207ee287eba1b20f8266968a06f2e55d3142
|
||||
F ext/rtree/rtree6.test 916a641d2beac01b9880871ff07612d56c1e466190a27c82ab36ffd58be03b9f
|
||||
F ext/rtree/rtree7.test c8fb2e555b128dd0f0bdb520c61380014f497f8a23c40f2e820acc9f9e4fdce5
|
||||
F ext/rtree/rtree8.test 649f5a37ec656028a4a32674b9b1183104285a7625a09d2a8f52a1cef72c93f2
|
||||
F ext/rtree/rtree9.test c646f12c8c1c68ef015c6c043d86a0c42488e2e68ed1bb1b0771a7ca246cbabf
|
||||
@@ -367,7 +369,7 @@ F ext/rtree/rtreeC.test d9d06dda1aee68b4dc227dfcc899f335f8b621e9d1920ee3d4e5dab8
|
||||
F ext/rtree/rtreeD.test fe46aa7f012e137bd58294409b16c0d43976c3bb92c8f710481e577c4a1100dc
|
||||
F ext/rtree/rtreeE.test e65d3fc625da1800b412fc8785817327d43ccfec5f5973912d8c9e471928caa9
|
||||
F ext/rtree/rtreeF.test 81ffa7ef51c4e4618d497a57328c265bf576990c7070633b623b23cd450ed331
|
||||
F ext/rtree/rtreeG.test fd3af1ca944a0bdb0cbb5455a4905c9f012e2fffcab6b791f07afa0dcbbcae0e
|
||||
F ext/rtree/rtreeG.test 1b9ca6e3effb48f4161edaa463ddeaa8fca4b2526d084f9cbf5dbe4e0184939c
|
||||
F ext/rtree/rtree_perf.tcl 6c18c1f23cd48e0f948930c98dfdd37dfccb5195
|
||||
F ext/rtree/rtree_util.tcl db734b4c5e75fed6acc56d9701f2235345acfdec750b5fc7b587936f5f6bceed
|
||||
F ext/rtree/rtreecheck.test 4d29103d1e16fcbf90135d1c637b833688492b063b2971dfb5dc6ba76555cfee
|
||||
@@ -387,27 +389,34 @@ F ext/session/session9.test 5409d90d8141881d08285ed1c2c0d8d10fb92069
|
||||
F ext/session/sessionA.test 1feeab0b8e03527f08f2f1defb442da25480138f
|
||||
F ext/session/sessionB.test 886252dcb7e692e62ef7e357456200912e367823
|
||||
F ext/session/sessionC.test 97556f5164ac29f2344b24bd7de6a3a35a95c390
|
||||
F ext/session/sessionD.test d4744c78334162851d2a2f285c7e603e31b49aa2
|
||||
F ext/session/sessionD.test d3617e29aa15c9413aee5286d99587633245d58d2ad28f3f331c822735418a22
|
||||
F ext/session/sessionE.test 0a616c4ad8fd2c05f23217ebb6212ef80b7fef30f5f086a6633a081f93e84637
|
||||
F ext/session/sessionF.test c2f178d4dfd723a5fd94a730ea2ccb44c669e3ce
|
||||
F ext/session/sessionG.test 01ef705096a9d3984eebdcca79807a211dee1b60
|
||||
F ext/session/sessionG.test 63f9a744341d670775af29e4f19c1ef09a4810798400f28cd76704803a2e56ff
|
||||
F ext/session/sessionH.test 332b60e4c2e0a680105e11936201cabe378216f307e2747803cea56fa7d9ebae
|
||||
F ext/session/session_common.tcl 7776eda579773113b30c7abfd4545c445228cb73
|
||||
F ext/session/session_speed_test.c edc1f96fd5e0e4b16eb03e2a73041013d59e8723
|
||||
F ext/session/sessionat.test feb7d22b3124882064b9d9df69f5484a9bb8c123dc9ddc6ffcd357521848139f
|
||||
F ext/session/sessionat.test efe88965e74ff1bc2af9c310b28358c02d420c1fb2705cc7a28f0c1cc142c3ec
|
||||
F ext/session/sessiondiff.test ad13dd65664bae26744e1f18eb3cbd5588349b7e9118851d8f9364248d67bcec
|
||||
F ext/session/sessionfault.test da273f2712b6411e85e71465a1733b8501dbf6f7
|
||||
F ext/session/sessionfault2.test 04aa0bc9aa70ea43d8de82c4f648db4de1e990b0
|
||||
F ext/session/sessionstat1.test 41cd97c2e48619a41cdf8ae749e1b25f34719de638689221aa43971be693bf4e
|
||||
F ext/session/sessionwor.test 2f3744236dc8b170a695b7d8ddc8c743c7e79fdc
|
||||
F ext/session/sqlite3session.c cc127222a9ea6f4eaa31281aa9da924f5244f6099be0ee526c950684fb3513a6
|
||||
F ext/session/sqlite3session.h cb4d860101ba6d3ac810f18684539b766d24d668fa2436cdde90d711af9464fb
|
||||
F ext/session/sqlite3session.c a5b7aed647abe7e366254b755597fce3f2719d82c98990cb0e1e07a3d203fe2b
|
||||
F ext/session/sqlite3session.h 01774161cbd328fe3d496323655b9cc142317ff1fb1ae15c1232075ea240e3a4
|
||||
F ext/session/test_session.c eb0bd6c1ea791c1d66ee4ef94c16500dad936386
|
||||
F ext/userauth/sqlite3userauth.h 7f3ea8c4686db8e40b0a0e7a8e0b00fac13aa7a3
|
||||
F ext/userauth/user-auth.txt e6641021a9210364665fe625d067617d03f27b04
|
||||
F ext/userauth/userauth.c 3410be31283abba70255d71fd24734e017a4497f
|
||||
F ext/zonefile/README.md 49bc392fe0dde788cc63b2ea71e26cfba02141b6ac192e245668d0b7b43b5750
|
||||
F ext/zonefile/zonefile.c ce917d60a62c8e384087954f482ab703b75a0660385e7a685bcafc0cff1c3038
|
||||
F ext/zonefile/zonefile1.test 3719e1d069064f4e12e915f8d9f6256c769b1582258b3997e0492076a01d5f36
|
||||
F ext/zonefile/zonefileenc.test e8624853ac224bfdeab8d2a231796499c3032e2a8bb1d2208f52fddf9507e38f
|
||||
F ext/zonefile/zonefilefault.test 6df281fc1ec7859d4ae2a3133d8783184a263edf6d081218958b6ae86b22ee13
|
||||
F install-sh 9d4de14ab9fb0facae2f48780b874848cbf2f895 x
|
||||
F ltmain.sh 3ff0879076df340d2e23ae905484d8c15d5fdea8
|
||||
F magic.txt 8273bf49ba3b0c8559cb2774495390c31fd61c60
|
||||
F main.mk c6b8ee2fa871e01ad6a460d750cd074010292464a60a37a2207930ae0df629dc
|
||||
F main.mk e5ac915f9959445602c07fd5aee00c5c09b4616658e67aa12e765399cd686763
|
||||
F mkso.sh fd21c06b063bb16a5d25deea1752c2da6ac3ed83
|
||||
F mptest/config01.test 3c6adcbc50b991866855f1977ff172eb6d901271
|
||||
F mptest/config02.test 4415dfe36c48785f751e16e32c20b077c28ae504
|
||||
@@ -420,37 +429,37 @@ F sqlite.pc.in 42b7bf0d02e08b9e77734a47798d1a55a9e0716b
|
||||
F sqlite3.1 fc7ad8990fc8409983309bb80de8c811a7506786
|
||||
F sqlite3.pc.in 48fed132e7cb71ab676105d2a4dc77127d8c1f3a
|
||||
F src/alter.c cf7a8af45cb0ace672f47a1b29ab24092a9e8cd8d945a9974e3b5d925f548594
|
||||
F src/analyze.c 0d0ccf7520a201d8747ea2f02c92c26e26f801bc161f714f27b9f7630dde0421
|
||||
F src/attach.c 84c477e856b24c2b9a0983b438a707c0cf4d616cee7a425401d418e58afec24c
|
||||
F src/analyze.c 6b42e36a5dcc2703a771f2411bd5e99524bd62c7ecde209bb88dfb04c72f046e
|
||||
F src/attach.c 79cb6b365d79b96b15dd429aa3e4c3b99335039e059baca8df28f1708fbff261
|
||||
F src/auth.c 6277d63837357549fe14e723490d6dc1a38768d71c795c5eb5c0f8a99f918f73
|
||||
F src/backup.c faf17e60b43233c214aae6a8179d24503a61e83b
|
||||
F src/bitvec.c 17ea48eff8ba979f1f5b04cc484c7bb2be632f33
|
||||
F src/btmutex.c 0e9ce2d56159b89b9bc8e197e023ee11e39ff8ca
|
||||
F src/btree.c 0a1f63b50ab1ac5d4b1637c30cb1ae123fbc162ec8cb6336ddb9491a0bc1e363
|
||||
F src/btree.c 18a53540aa35dbdf77f715ea928422a4ed9011dc16ea7b50f803fd1617fcc4f5
|
||||
F src/btree.h 0866c0a08255142ea0e754aabd211c843cab32045c978a592a43152405ed0c84
|
||||
F src/btreeInt.h 55b702efce17e5d1941865464227d3802cfc9c7c832fac81d4c94dced47a71fc
|
||||
F src/build.c a03eb5a1cfff74784c24a4478ba5455711571936f1ac9d43f94fa7df57509977
|
||||
F src/btreeInt.h 620ab4c7235f43572cf3ac2ac8723cbdf68073be4d29da24897c7b77dda5fd96
|
||||
F src/build.c 672022c06e1a5c2653f80c77a687de11f7e65ce81d20fe2825aadfa13a875c33
|
||||
F src/callback.c fe677cb5f5abb02f7a772a62a98c2f516426081df68856e8f2d5f950929b966a
|
||||
F src/complete.c a3634ab1e687055cd002e11b8f43eb75c17da23e
|
||||
F src/ctime.c ff1be3eed7bdd75aaca61ca8dc848f7c9f850ef2fb9cb56f2734e922a098f9c0
|
||||
F src/date.c ebe1dc7c8a347117bb02570f1a931c62dd78f4a2b1b516f4837d45b7d6426957
|
||||
F src/dbpage.c 8db4c97f630e7d83f884ea75caf1ffd0988c160e9d530194d93721c80821e0f6
|
||||
F src/dbstat.c 7a4ba8518b6369ef3600c49cf9c918ad979acba610b2aebef1b656d649b96720
|
||||
F src/delete.c 74667ad914ac143731a444a1bacf29ceb18f6eded8a0dd17aafae80baa07f8bb
|
||||
F src/expr.c ad6e7a9c34a4bab9d10cc857d647ae7ce370a633b5c0bfa71f1c29b81ae364b8
|
||||
F src/delete.c 20c8788451dc737a967c87ea53ad43544d617f5b57d32ccce8bd52a0daf9e89b
|
||||
F src/expr.c 9e06de431c09f144438aa6895ea4d4290fa3c6875bfcc3ba331012ca78deadf0
|
||||
F src/fault.c 460f3e55994363812d9d60844b2a6de88826e007
|
||||
F src/fkey.c d617daf66b5515e2b42c1405b2b4984c30ca50fb705ab164271a9bf66c69e331
|
||||
F src/func.c bd528d5ed68ce5cbf78a762e3b735fa75009f7197ff07fab07fd771f35ebaa1b
|
||||
F src/global.c ac3094f1dc59fbeb919aef7cc0cc827a8459d1fb1adb7972ef75bd9e0c10b75b
|
||||
F src/func.c 94f42cba2cc1c34aeaa441022ba0170ec3fec4bba54db4e0ded085c6dc0fdc51
|
||||
F src/global.c 01506976bd75e5e7b977207a6a05062e2dd0050012f8071be06bbea22ec6d69a
|
||||
F src/hash.c a12580e143f10301ed5166ea4964ae2853d3905a511d4e0c44497245c7ce1f7a
|
||||
F src/hash.h ab34c5c54a9e9de2e790b24349ba5aab3dbb4fd4
|
||||
F src/hwtime.h 747c1bbe9df21a92e9c50f3bbec1de841dc5e5da
|
||||
F src/in-operator.md 10cd8f4bcd225a32518407c2fb2484089112fd71
|
||||
F src/insert.c 14686083cedc198540b15a79586cdd4be2acf6d5fa97627e355f817ab07e9fee
|
||||
F src/legacy.c 134ab3e3fae00a0f67a5187981d6935b24b337bcf0f4b3e5c9fa5763da95bf4e
|
||||
F src/loadext.c 55bcc3c741059a1056859e8adaf133aa179e22be12215c0936b2f354ef71209b
|
||||
F src/main.c 690c4134f944cbd5b71d59dd6e61ce4131f6a50ab774f38108e57d07d79cf876
|
||||
F src/malloc.c 6f684fd039f53bf9195193eb0cde731a2954970fabc6ef054ba379b6052dc296
|
||||
F src/loadext.c f6e4e416a736369f9e80eba609f0acda97148a8b0453784d670c78d3eed2f302
|
||||
F src/main.c dc75b3585bab31a88962eda2abe35a38b58c2e4d648e1a11e249fe43174c783f
|
||||
F src/malloc.c 07295435093ce354c6d9063ac05a2eeae28bd251d2e63c48b3d67c12c76f7e18
|
||||
F src/mem0.c 6a55ebe57c46ca1a7d98da93aaa07f99f1059645
|
||||
F src/mem1.c c12a42539b1ba105e3707d0e628ad70e611040d8f5e38cf942cee30c867083de
|
||||
F src/mem2.c f1940d9e91948dd6a908fbb9ce3835c36b5d83c3
|
||||
@@ -461,40 +470,40 @@ F src/msvc.h 4942752b6a253116baaa8de75256c51a459a5e81
|
||||
F src/mutex.c b021263554c8a3995e9d53193b8194b96d1ed28e06c3b532dd7f7d29cf0c7d53
|
||||
F src/mutex.h 779d588e3b7756ec3ecf7d78cde1d84aba414f85
|
||||
F src/mutex_noop.c 9d4309c075ba9cc7249e19412d3d62f7f94839c4
|
||||
F src/mutex_unix.c 27bb6cc49485ee46711a6580ab7b3f1402211d23
|
||||
F src/mutex_w32.c a898fa969823b100c0f5fdc57e54c9a1e419ab4d
|
||||
F src/mutex_unix.c aaf9ebc3f89df28483c52208497a99a02cc3650011422fc9d4c57e4392f7fe58
|
||||
F src/mutex_w32.c 7670d770c94bbfe8289bec9d7f1394c5a00a57c37f892aab6b6612d085255235
|
||||
F src/notify.c 9711a7575036f0d3040ba61bc6e217f13a9888e7
|
||||
F src/os.c 22d31db3ca5a96a408fbf1ceeaaebcaf64c87024d2ff9fe1cf2ddbec3e75c104
|
||||
F src/os.h 48388821692e87da174ea198bf96b1b2d9d83be5dfc908f673ee21fafbe0d432
|
||||
F src/os_common.h b2f4707a603e36811d9b1a13278bffd757857b85
|
||||
F src/os_setup.h 0dbaea40a7d36bf311613d31342e0b99e2536586
|
||||
F src/os_unix.c 7fc2735390a7809d5d893ed735d994ff12521224b89738226fff6f1a0aa1c932
|
||||
F src/os_win.c 0a4afa35cc8e812000df3ea2f64b476131b39e29e75d8007d0504726e4761de4
|
||||
F src/os_unix.c 928586cbde31890538854f1657463392d63b2d7794f577774573ae53ec283d7b
|
||||
F src/os_win.c eb03c6d52f893bcd7fdd4c6006674c13c1b5e49543fec98d605201af2997171c
|
||||
F src/os_win.h 7b073010f1451abe501be30d12f6bc599824944a
|
||||
F src/pager.c 9b9cb4e06c03d43d62480a7a685a012d645fcf3a39e7767ccb505fb41ee083ec
|
||||
F src/pager.c 0b6bd5442733b2e08d0673de6cdafe3e7ab0b5715e4844ac836ab346b1d9ed89
|
||||
F src/pager.h 581698f2177e8bd4008fe4760898ce20b6133d1df22139b9101b5155f900df7a
|
||||
F src/parse.y 44cbbc3e132ea128258eff7be7f6d5c5dfa25522f89ec8b5501276966511bd50
|
||||
F src/parse.y 4e750e1b261ff9f1d0b6b5d40a829c66d691899f48953fde839d8b52d41aa148
|
||||
F src/pcache.c 7ae91a4557a43d77d449accbfdc68846e6516f8e2eda46e8bbe4536fb669b201
|
||||
F src/pcache.h 072f94d29281cffd99e46c1539849f248c4b56ae7684c1f36626797fee375170
|
||||
F src/pcache1.c 716975564c15eb6679e97f734cec1bfd6c16ac3d4010f05f1f8e509fc7d19880
|
||||
F src/pragma.c bea56df3ae0637768c0da4fbbb8f2492f780980d95000034a105ff291bf7ca69
|
||||
F src/pragma.h bb83728944b42f6d409c77f5838a8edbdb0fe83046c5496ffc9602b40340a324
|
||||
F src/prepare.c 259f4e7960c47082c9653f3d5f0c294abd68bb9c3aab86de7630700cba1c20fb
|
||||
F src/printf.c 9506b4b96e59c0467047155f09015750cb2878aeda3d39e5610c1192ddc3c41c
|
||||
F src/printf.c d3b7844ddeb11fbbdd38dd84d09c9c1ac171d21fb038473c3aa97981201cc660
|
||||
F src/random.c 80f5d666f23feb3e6665a6ce04c7197212a88384
|
||||
F src/resolve.c bbee7e31d369a18a2f4836644769882e9c5d40ef4a3af911db06410b65cb3730
|
||||
F src/rowset.c 7b7e7e479212e65b723bf40128c7b36dc5afdfac
|
||||
F src/select.c 8b22abe193e4d8243befa2038e4ae2405802fed1c446e5e502d11f652e09ba74
|
||||
F src/shell.c.in 0e20ac49a6c4458620084bf7715ad39cd9557d9116e447548d2282000e8ca361
|
||||
F src/sqlite.h.in 1f1a2da222ec57465794e8984d77f32d0bd0da80cdc136beadda461a0be9d80c
|
||||
F src/select.c f02352ac5cbb6fad3804add825743b924cfb6c742ba2e8666d726828a9985d73
|
||||
F src/shell.c.in c1b14bc0bc1fe73a97dfaad55ca09f5d6e44f6019977d94e7e3d1861616035e1
|
||||
F src/sqlite.h.in 235e942dd8c01b414c2996828b4d0d2500faf8850f8b24ae17d31c172f519e69
|
||||
F src/sqlite3.rc 5121c9e10c3964d5755191c80dd1180c122fc3a8
|
||||
F src/sqlite3ext.h c02d628cca67f3889c689d82d25c3eb45e2c155db08e4c6089b5840d64687d34
|
||||
F src/sqliteInt.h fd8702c65994d7de3e2d8f7d85d958731da1ed29476571fdfa2290fd8ec0bf80
|
||||
F src/sqlite3ext.h 83a3c4ce93d650bedfd1aa558cb85a516bd6d094445ee989740827d0d944368d
|
||||
F src/sqliteInt.h fd8943e9d6b8bd04b3a22ef806b843c2c06f022db3f37f1436ac3a9b04e5b8a1
|
||||
F src/sqliteLimit.h 1513bfb7b20378aa0041e7022d04acb73525de35b80b252f1b83fedb4de6a76b
|
||||
F src/status.c 9737ed017279a9e0c5da748701c3c7bf1e8ae0dae459aad20dd64fcff97a7e35
|
||||
F src/table.c b46ad567748f24a326d9de40e5b9659f96ffff34
|
||||
F src/tclsqlite.c 1833388c01e3b77f4c712185ee7250b9423ee0981ce6ae7e401e47db0319a696
|
||||
F src/test1.c 1ab7cbbb6693e08364c1a9241e2aee17f8c4925e4cc52396be77ae6845a05828
|
||||
F src/tclsqlite.c 11a2618c227fd13ccad73ee02d1199f9880c59db2b3144fd7432db1980a2577d
|
||||
F src/test1.c 6b0dfd4f0a1996805bc04381b45df71ead9ed84634d2a47a757ab292febf9026
|
||||
F src/test2.c 3efb99ab7f1fc8d154933e02ae1378bac9637da5
|
||||
F src/test3.c b8434949dfb8aff8dfa082c8b592109e77844c2135ed3c492113839b6956255b
|
||||
F src/test4.c 18ec393bb4d0ad1de729f0b94da7267270f3d8e6
|
||||
@@ -509,7 +518,7 @@ F src/test_backup.c bf5da90c9926df0a4b941f2d92825a01bbe090a0
|
||||
F src/test_bestindex.c 78809f11026f18a93fcfd798d9479cba37e1201c830260bf1edc674b2fa9b857
|
||||
F src/test_blob.c ae4a0620b478548afb67963095a7417cd06a4ec0a56adb453542203bfdcb31ce
|
||||
F src/test_btree.c 8b2dc8b8848cf3a4db93f11578f075e82252a274
|
||||
F src/test_config.c cc8a1d44648d9392a14f4ecfc841d027daaf61f952b9f70792edf11373aaa3dd
|
||||
F src/test_config.c 03df8eb9dc8d5ee96588dfa34fd989c75625d5a0daf59491e32b966da4010870
|
||||
F src/test_delete.c e2fe07646dff6300b48d49b2fee2fe192ed389e834dd635e3b3bac0ce0bf9f8f
|
||||
F src/test_demovfs.c a0c3bdd45ed044115c2c9f7779e56eafff18741e
|
||||
F src/test_devsym.c 1960abbb234b97e9b920f07e99503fc04b443f62bbc3c6ff2c2cea2133e3b8a2
|
||||
@@ -543,34 +552,34 @@ F src/test_thread.c 911d15fb14e19c0c542bdc8aabf981c2f10a4858
|
||||
F src/test_vfs.c f0186261a24de2671d080bcd8050732f0cb64f6e
|
||||
F src/test_vfstrace.c bab9594adc976cbe696ff3970728830b4c5ed698
|
||||
F src/test_windirent.c a895e2c068a06644eef91a7f0a32182445a893b9a0f33d0cdb4283dca2486ac1
|
||||
F src/test_windirent.h 8782864172ba5ae52c5c313c70faeadb324ff74de9c3dcc6b56a557dccaa1de6
|
||||
F src/test_windirent.h 90dfbe95442c9762357fe128dc7ae3dc199d006de93eb33ba3972e0a90484215
|
||||
F src/test_wsd.c 41cadfd9d97fe8e3e4e44f61a4a8ccd6f7ca8fe9
|
||||
F src/threads.c 4ae07fa022a3dc7c5beb373cf744a85d3c5c6c3c
|
||||
F src/tokenize.c 1003d6d90c6783206c711f0a9397656fa5b055209f4d092caa43bb3bf5215db5
|
||||
F src/tokenize.c 5b0c661a85f783d35b9883830736eeb63be4aefc4f6b7d9cd081d48782c041e2
|
||||
F src/treeview.c eae35972ff44f67064de2eaf35f04afe94e7aea3271a8b3bcebb3f954880fec3
|
||||
F src/trigger.c a34539c69433276d37b0da9a89c117726ff2d292c0902895af1f393a983cd3a1
|
||||
F src/update.c 961bd1265d4d1e5cd65c9a54fa5122fb7aefcb003fcf2de0c092fceb7e58972c
|
||||
F src/update.c a90a32ffc0100265b0693dbbdbe490756447af181f5ea2c138cce515b08c8795
|
||||
F src/utf.c 810fbfebe12359f10bc2a011520a6e10879ab2a163bcb26c74768eab82ea62a5
|
||||
F src/util.c 7315e97a8dc2c8e19ca64196c652cf0a65d13fd0a211b2cec082062372dc6261
|
||||
F src/vacuum.c 90839322fd5f00df9617eb21b68beda9b6e2a2937576b0d65985e4aeb1c53739
|
||||
F src/vdbe.c c70267613df80345ed9bbd9c249c365b53bb9cbbe9d3e78e6d5c049d00ef5501
|
||||
F src/vdbe.h d50cadf12bcf9fb99117ef392ce1ea283aa429270481426b6e8b0280c101fd97
|
||||
F src/vdbeInt.h 1fe00770144c12c4913128f35262d11527ef3284561baaab59b947a41c08d0d9
|
||||
F src/vdbeapi.c 9c670ca0dcc1cd86373aa353b747b26fe531ca5cd4331690c611d1f03842e2a1
|
||||
F src/vdbeaux.c 7ae48b180e5dd5d282e6752d155f1ab7929196d8e6577b82742044188152ca85
|
||||
F src/util.c d9eb0a6c4aae1b00a7369eadd7ca0bbe946cb4c953b6751aa20d357c2f482157
|
||||
F src/vacuum.c 762ee9bbf8733d87d8cd06f58d950e881982e416f8c767334a40ffd341b6bff5
|
||||
F src/vdbe.c 72f5a4b95be486170104779aeef000423acabf55ac0c661afdae889be72c8922
|
||||
F src/vdbe.h 134beb7a12a6213c00eba58febaede33447cc4441bc568a0d9c144b33fc3720a
|
||||
F src/vdbeInt.h 8d7d07f13cb3c4cbca91e22ba4a1920e542dda7c5d9299920432a0b3d5b009f5
|
||||
F src/vdbeapi.c fea41171884a4de119f8b10ab514c788674eeeb7f27218bb6d008e1310bfd07f
|
||||
F src/vdbeaux.c 2756ac68ac259c416554100598fc291870063288cd7e1af22847f57b3e130e56
|
||||
F src/vdbeblob.c f5c70f973ea3a9e915d1693278a5f890dc78594300cf4d54e64f2b0917c94191
|
||||
F src/vdbemem.c 8478f7fb1948bf8fdeec7c2cb59ea58155c31258b9cd43c56d485e03ed40bd07
|
||||
F src/vdbemem.c 21c1d00f0b901dda0a2eccf56bf0d86648cae1bde37de0606ae4e7cdb0ff6d3d
|
||||
F src/vdbesort.c 731a09e5cb9e96b70c394c1b7cf3860fbe84acca7682e178615eb941a3a0ef2f
|
||||
F src/vdbetrace.c 48e11ebe040c6b41d146abed2602e3d00d621d7ebe4eb29b0a0f1617fd3c2f6c
|
||||
F src/vtab.c 0e4885495172e1bdf54b12cce23b395ac74ef5729031f15e1bc1e3e6b360ed1a
|
||||
F src/vxworks.h d2988f4e5a61a4dfe82c6524dd3d6e4f2ce3cdb9
|
||||
F src/wal.c 5a3f464edd64596f601683ed321d12e6fd93c5fb9afdfb3653d6ffd0fee9c48f
|
||||
F src/wal.c 0ba9af2589b67c4bc60c773c7d2080491099037af21e73545f932bb29bf70b65
|
||||
F src/wal.h 8de5d2d3de0956d6f6cb48c83a4012d5f227b8fe940f3a349a4b7e85ebcb492a
|
||||
F src/walker.c da987a20d40145c0a03c07d8fefcb2ed363becc7680d0500d9c79915591f5b1f
|
||||
F src/where.c 36b92103f726609cc3dbe07c619426bd6886bede455de56ccff54c8e567f5582
|
||||
F src/where.c 7cae47e813393d70c6d327fdf000fcb30f76b1b0b5a5b52ff6402e0c658de32c
|
||||
F src/whereInt.h 82c04c5075308abbac59180c8bad5ecb45b07453981f60a53f3c7dee21e1e971
|
||||
F src/wherecode.c af1e79154aaa88cd802d6f2e5b945f67eaca7c958d1525fbf8ee19d5bd7b9020
|
||||
F src/whereexpr.c 427ea8e96ec24f2a7814c67b8024ad664a9c7656264c4566c34743cb23186e46
|
||||
F src/wherecode.c e1aaadd8fec650037cfbf27d1b3470338fb3b58fec34d11082df16fe9a08fbd7
|
||||
F src/whereexpr.c 53532be687e12f3cd314f1e204cd4fbdac7ad250e918a182b048121e16e828ae
|
||||
F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2
|
||||
F test/affinity2.test a6d901b436328bd67a79b41bb0ac2663918fe3bd
|
||||
F test/affinity3.test 6a101af2fc945ce2912f6fe54dd646018551710d
|
||||
@@ -664,13 +673,13 @@ F test/busy.test 510dc6daaad18bcbbc085bcc6217d6dc418def5e73f72ce1475eea0cb783472
|
||||
F test/cache.test 13bc046b26210471ca6f2889aceb1ea52dc717de
|
||||
F test/cacheflush.test af25bb1509df04c1da10e38d8f322d66eceedf61
|
||||
F test/cachespill.test 895997f84a25b323b166aecb69baab2d6380ea98f9e0bcc688c4493c535cfab9
|
||||
F test/capi2.test d3267a146df2251e7ad09a672d59e33e836d74c6fbeb843c18e87835ef646c12
|
||||
F test/capi3.test 986e57cea8ab423b3fc8c2e3b69330394252d3d2a4496122ff3749e258305695
|
||||
F test/capi2.test 34a1a9a96d543a2ec2c209696b11b164444f57253b1f2cba1c2e53fadede6c7b
|
||||
F test/capi3.test 36f5c859c91a9bb0075d6ddcfcf2476cad629b09f7bfd135776fb94b06c04706
|
||||
F test/capi3b.test efb2b9cfd127efa84433cd7a2d72ce0454ae0dc4
|
||||
F test/capi3c.test 7ebed1d8fa2f3190149d556fe8cff5a006be62af437c5c4640db614470126098
|
||||
F test/capi3d.test 485048dc5cd07bc68011e4917ad035ad6047ab82
|
||||
F test/capi3e.test 3d49c01ef2a1a55f41d73cba2b23b5059ec460fe
|
||||
F test/cast.test 4c275cbdc8202d6f9c54a3596701719868ac7dc3
|
||||
F test/cast.test 5ceb920718d280b61163500a7d29e0e0a86458b1cbd92d96f962c9d970aa3857
|
||||
F test/cffault.test 9d6b20606afe712374952eec4f8fd74b1a8097ef
|
||||
F test/check.test 33a698e8c63613449d85d624a38ef669bf20331daabebe3891c9405dd6df463a
|
||||
F test/close.test 799ea4599d2f5704b0a30f477d17c2c760d8523fa5d0c8be4a7df2a8cad787d8
|
||||
@@ -688,7 +697,7 @@ F test/collate9.test 3adcc799229545940df2f25308dd1ad65869145a
|
||||
F test/collateA.test b8218ab90d1fa5c59dcf156efabb1b2599c580d6
|
||||
F test/collateB.test 1e68906951b846570f29f20102ed91d29e634854ee47454d725f2151ecac0b95
|
||||
F test/colmeta.test 2c765ea61ee37bc43bbe6d6047f89004e6508eb1
|
||||
F test/colname.test 101aa39392a1f6883278f588836a3ab99178f8103f78032433400475cc05109f
|
||||
F test/colname.test fb28b3687e03625425bc216edf8b186ce974aa71008e2aa1f426a7dcb75a601d
|
||||
F test/conflict.test 029faa2d81a0d1cafb5f88614beb663d972c01db
|
||||
F test/conflict2.test bb0b94cf7196c64a3cbd815c66d3ee98c2fecd9c
|
||||
F test/conflict3.test a83db76a6c3503b2fa057c7bfb08c318d8a422202d8bc5b86226e078e5b49ff9
|
||||
@@ -723,7 +732,7 @@ F test/crash4.test fe2821baf37168dc59dd733dcf7dba2a401487bc
|
||||
F test/crash5.test 05dd3aa9dbb751a22d5cdaf22a9c49b6667aa219
|
||||
F test/crash6.test 4c56f1e40d0291e1110790a99807aa875b1647ba
|
||||
F test/crash7.test 1a194c4900a255258cf94b7fcbfd29536db572df
|
||||
F test/crash8.test a63907617d8e74fb54b4bff23eca8a4435625245
|
||||
F test/crash8.test 63cd5aea313222d7a69637cf7174c34d151676cc187d57193b66d4c89dedede3
|
||||
F test/crashM.test d95f59046fa749b0d0822edf18a717788c8f318d
|
||||
F test/crashtest1.c 09c1c7d728ccf4feb9e481671e29dda5669bbcc2
|
||||
F test/createtab.test b5de160630b209c4b8925bdcbbaf48cc90b67fe8
|
||||
@@ -743,7 +752,7 @@ F test/delete.test acc38fca8ee4851467705b1c2cfea64cd26667e5
|
||||
F test/delete2.test 3a03f2cca1f9a67ec469915cb8babd6485db43fa
|
||||
F test/delete3.test 555e84a00a99230b7d049d477a324a631126a6ab
|
||||
F test/delete4.test 21d2113217eeaacac2d99defe14fe6611615ae86
|
||||
F test/delete_db.test c70a43629dd4d3e1dd03fdaf7a22153af6a69d92
|
||||
F test/delete_db.test 096d828493c7907f9ea11a7098ea6a0f73edba89406487d5d6cc2228dc4ab8b0
|
||||
F test/descidx1.test 6d03b44c8538fe0eb4924e19fba10cdd8f3c9240
|
||||
F test/descidx2.test 9f1a0c83fd57f8667c82310ca21b30a350888b5d
|
||||
F test/descidx3.test 09ddbe3f5295f482d2f8b687cf6db8bad7acd9a2
|
||||
@@ -784,17 +793,17 @@ F test/enc4.test c8f1ce3618508fd0909945beb8b8831feef2c020
|
||||
F test/eqp.test 3fe051af50921284189d1970eb653f9fcf5117d2
|
||||
F test/errmsg.test eae9f091eb39ce7e20305de45d8e5d115b68fa856fba4ea6757b6ca3705ff7f9
|
||||
F test/eval.test a64c9105d6ff163df7cf09d6ac29cdad5922078c
|
||||
F test/exclusive.test 9a57bd66e39144b888ca75c309914fcdefb4e3f9
|
||||
F test/exclusive.test 1206b87e192497d78c7f35552e86a9d05421498da300fb1cce5ca5351ccde3c3
|
||||
F test/exclusive2.test 984090e8e9d1b331d2e8111daf6e5d61dda0bef7
|
||||
F test/exec.test e949714dc127eaa5ecc7d723efec1ec27118fdd7
|
||||
F test/exists.test 79a75323c78f02bbe9c251ea502a092f9ef63dac
|
||||
F test/expr.test 66a2c9ac34f74f036faa4092f5402c7d3162fc93
|
||||
F test/extension01.test 00d13cec817f331a687a243e0e5a2d87b0e358c9
|
||||
F test/extraquick.test cb254400bd42bfb777ff675356aabf3287978f79
|
||||
F test/fallocate.test 87b5e43c872b7e69cd80b7b8813eb102b571a75d45dda24e38b65537bcc85733
|
||||
F test/fallocate.test 07416bd593a116d5893cb244f45a94d5c6fe030561df3bd972e6135f8106e509
|
||||
F test/filectrl.test 6e871c2d35dead1d9a88e176e8d2ca094fec6bb3
|
||||
F test/filefmt.test f393e80c4b8d493b7a7f8f3809a8425bbf4292af1f5140f01cb1427798a2bbd4
|
||||
F test/fkey1.test 9d7e3a0d409e7f64ab077af3b4fc5e5ce1a4e8d8f1272b65b9d93480aeb1fa2b
|
||||
F test/fkey1.test d11dbb8a93ead9b5c46ae5d02da016d61245d47662fb2d844c99214f6163f768
|
||||
F test/fkey2.test 155809016fad6b2a1491facf2ac53a551bc57c2c
|
||||
F test/fkey3.test 76d475c80b84ee7a5d062e56ccb6ea68882e2b49
|
||||
F test/fkey4.test 86446017011273aad8f9a99c1a65019e7bd9ca9d
|
||||
@@ -842,7 +851,7 @@ F test/fts2r.test b154c30b63061d8725e320fba1a39e2201cadd5e
|
||||
F test/fts2token.test d8070b241a15ff13592a9ae4a8b7c171af6f445a
|
||||
F test/fts3.test 672a040ea57036fb4b6fdc09027c18d7d24ab654
|
||||
F test/fts3_common.tcl 99cf6659b87c0f74f55963c2aea03b3a7d66ceb0
|
||||
F test/fts3aa.test 39b65c11913d277c91d7426c62cfc1d147d1b4e9a48fecd9e38f60d0b5a5f505
|
||||
F test/fts3aa.test f267fcd6aca30fc70b81e5d82b68b34b38f581896020b57ed49e9777c7ebd85f
|
||||
F test/fts3ab.test 7f6cf260ae80dda064023df8e8e503e9a412b91f
|
||||
F test/fts3ac.test 636ed7486043055d4f126a0e385f2d5a82ebbf63
|
||||
F test/fts3ad.test e40570cb6f74f059129ad48bcef3d7cbc20dda49
|
||||
@@ -892,7 +901,7 @@ F test/fts3offsets.test b85fd382abdc78ebce721d8117bd552dfb75094c
|
||||
F test/fts3prefix.test fa794eaab0bdae466494947b0b153d7844478ab2
|
||||
F test/fts3prefix2.test e1f0a822ca661dced7f12ce392e14eaf65609dce
|
||||
F test/fts3query.test f33eb71a1fe1084ea585eeb7ee76b390729f5170
|
||||
F test/fts3rank.test e4d2e16a28c98cae95001a75e2b4b05b19b051ffd6aaab15491c5e0595127b9b
|
||||
F test/fts3rank.test cd99bc83a3c923c8d52afd90d86979cf05fc41849f892faeac3988055ef37b99
|
||||
F test/fts3rnd.test 1320d8826a845e38a96e769562bf83d7a92a15d0
|
||||
F test/fts3shared.test 57e26a801f21027b7530da77db54286a6fe4997e
|
||||
F test/fts3snippet.test 01a4231816e03a0660ae53ba2404fe69012fe0db
|
||||
@@ -914,16 +923,16 @@ F test/fts4merge2.test 5faa558d1b672f82b847d2a337465fa745e46891
|
||||
F test/fts4merge3.test 8d9ccb4a3d41c4c617a149d6c4b13ad02de797d0
|
||||
F test/fts4merge4.test d895b1057a7798b67e03455d0fa50e9ea836c47b
|
||||
F test/fts4noti.test 5553d7bb2e20bf4a06b23e849352efc022ce6309
|
||||
F test/fts4onepass.test 7319d61a2ed1325fc54afd0c060a0513b462303a
|
||||
F test/fts4onepass.test d69ddc4ee3415e40b0c5d1d0408488a87614d4f63ba9c44f3e52db541d6b7cc7
|
||||
F test/fts4opt.test fd6a11684b965e1999564ae763797b7fb9e34c96
|
||||
F test/fts4unicode.test ceca76422abc251818cb25dabe33d3c3970da5f7c90e1540f190824e6b3a7c95
|
||||
F test/full.test 6b3c8fb43c6beab6b95438c1675374b95fab245d
|
||||
F test/func.test ae97561957aba6ca9e3a7b8a13aac41830d701ef
|
||||
F test/func.test 09dda479bcfc568f99f3070413e9672a8eeedc1be9c5d819bf55d4788c2583b7
|
||||
F test/func2.test 772d66227e4e6684b86053302e2d74a2500e1e0f
|
||||
F test/func3.test d202a7606d23f90988a664e88e268aed1087c11c
|
||||
F test/func4.test 6beacdfcb0e18c358e6c2dcacf1b65d1fa80955f
|
||||
F test/func5.test cdd224400bc3e48d891827cc913a57051a426fa4
|
||||
F test/func6.test a4281c8fcd42b56f7a60f28e8e4d444e8b2256f9e82658b7ab87699f8318f564
|
||||
F test/func6.test 90e42b64c4f9fb6f04f44cb8a1da586c8542502e926b19c76504fe74ff2a9b7c
|
||||
F test/fuzz-oss1.test e58330d01cbbd8215ee636b17a03fe220b37dbfa
|
||||
F test/fuzz.test 96083052bf5765e4518c1ba686ce2bab785670d1
|
||||
F test/fuzz2.test 76dc35b32b6d6f965259508508abce75a6c4d7e1
|
||||
@@ -944,9 +953,9 @@ F test/genesis.tcl 1e2e2e8e5cc4058549a154ff1892fe5c9de19f98
|
||||
F test/having.test e4098a4b8962f9596035c3b87a8928a10648acc509f1bb8d6f96413bbf79a1b3
|
||||
F test/hexlit.test 4a6a5f46e3c65c4bf1fa06f5dd5a9507a5627751
|
||||
F test/hidden.test 23c1393a79e846d68fd902d72c85d5e5dcf98711
|
||||
F test/hook.test dbc0b87756e1e20e7497b56889c9e9cd2f8cc2b5
|
||||
F test/hook.test 1604b3b2f5931430087540404555c1b6be3618600b81558657c66b533ed70b13
|
||||
F test/hook2.test b9ff3b8c6519fb67f33192f1afe86e7782ee4ac8
|
||||
F test/icu.test 7fb00edc09e05d51e36be12b33e0af04e3394e3b02dbdcb2eefcb901203e28c4
|
||||
F test/icu.test 41aa8847745a879b897a7febea0f8f9efc8e67fe8bf680589b6e07c7b0a1569a
|
||||
F test/ieee754.test 806fc0ce7f305f57e3331eaceeddcfec9339e607
|
||||
F test/imposter1.test c3f1db2d3db2c24611a6596a3fc0ffc14f1466c8
|
||||
F test/in.test 2fa2dfba1afe30eb830f327e7131dfadaa7a701d677de0eb65f9303d99e18fe0
|
||||
@@ -975,7 +984,7 @@ F test/index7.test 7feababe16f2091b229c22aff2bcc1d4d6b9d2bb
|
||||
F test/index8.test bc2e3db70e8e62459aaa1bd7e4a9b39664f8f9d7
|
||||
F test/index9.test 0aa3e509dddf81f93380396e40e9bb386904c1054924ba8fa9bcdfe85a8e7721
|
||||
F test/indexedby.test faa585e315e868f09bce0eb39c41d6134649b13d2801638294d3ae616edf1609
|
||||
F test/indexexpr1.test ace1ad489adc25325ad298434f13b1a515b36bf5dca9fe2a4b66cdf17aea3fa0
|
||||
F test/indexexpr1.test 635261197bcdc19b9b2c59bbfa7227d525c00e9587faddb2d293c44d287ce60e
|
||||
F test/indexexpr2.test 13247bac49143196556eb3f65e97ef301bd3e993f4511558b5db322ddc370ea6
|
||||
F test/indexfault.test 31d4ab9a7d2f6e9616933eb079722362a883eb1d
|
||||
F test/init.test 15c823093fdabbf7b531fe22cf037134d09587a7
|
||||
@@ -991,25 +1000,25 @@ F test/interrupt.test 16ea879ec728cb76414c148c5f24afd5d1f91054
|
||||
F test/interrupt2.test e4408ca770a6feafbadb0801e54a0dcd1a8d108d
|
||||
F test/intpkey.test ac71107a49a06492b69b82aafaf225400598d3c8
|
||||
F test/io.test f95bca1783b01ea7761671560d023360d2dfa4cc
|
||||
F test/ioerr.test 2a24bd6ed5a8b062e64bfe1f6cf94fb25e92210d
|
||||
F test/ioerr.test 470fcc78e9cd352d162baf782fe301ea807d764241f58a48fc58109c2dfcdb6b
|
||||
F test/ioerr2.test 2593563599e2cc6b6b4fcf5878b177bdd5d8df26
|
||||
F test/ioerr3.test d3cec5e1a11ad6d27527d0d38573fbff14c71bdd
|
||||
F test/ioerr4.test f130fe9e71008577b342b8874d52984bd04ede2c
|
||||
F test/ioerr5.test 2edfa4fb0f896f733071303b42224df8bedd9da4
|
||||
F test/ioerr6.test a395a6ab144b26a9e3e21059a1ab6a7149cca65b
|
||||
F test/join.test 442c462eea85cf065d70a663c626b780a95af6e11585d909bb63b87598afe678
|
||||
F test/join2.test 1a0c26399910b015d9f8f95b884e9a079fd2cfdccd65f7b1603846508cae0dc6
|
||||
F test/join2.test f1b5ba94ba70a791df2d99e61adcebf62edacad1eca57881c97eb3e2ca718595
|
||||
F test/join3.test 6f0c774ff1ba0489e6c88a3e77b9d3528fb4fda0
|
||||
F test/join4.test 1a352e4e267114444c29266ce79e941af5885916
|
||||
F test/join5.test bc98ea4b4e5003f5b1453701ebb8cd7d1c01a550
|
||||
F test/join6.test cfe6503791ceb0cbb509966740286ec423cbf10b
|
||||
F test/journal1.test 69abc726c51b4a0409189f9a85191205297c0577
|
||||
F test/journal1.test c7b768041b7f494471531e17abc2f4f5ebf9e5096984f43ed17c4eb80ba34497
|
||||
F test/journal2.test 9dac6b4ba0ca79c3b21446bbae993a462c2397c4
|
||||
F test/journal3.test ff8af941f9e06161d3db1b46bb9f965ff0e7f307
|
||||
F test/jrnlmode.test 7864d59cf7f6e552b9b99ba0f38acd167edc10fa
|
||||
F test/jrnlmode2.test 81610545a4e6ed239ea8fa661891893385e23a1d
|
||||
F test/journal3.test c9c29883f5bf535ae82ae21c472df6263806a22e467b6db7cd0d6d545305b4f6
|
||||
F test/jrnlmode.test a6693f2bed4541a21e703aaa37bb3e10de154130645952933b82b2dec0a8b539
|
||||
F test/jrnlmode2.test 8759a1d4657c064637f8b079592651530db738419e1d649c6df7048cd724363d
|
||||
F test/jrnlmode3.test 556b447a05be0e0963f4311e95ab1632b11c9eaa
|
||||
F test/json101.test d7cdf3e6731d41e0c4bde1c88806abd17f1f478486a1409933c1d8eac9120095
|
||||
F test/json101.test 24e97954e3bd6404f3715888c7f8f835e36e19c7ae6513b5d9ab2d381498962d
|
||||
F test/json102.test eeb54efa221e50b74a2d6fb9259963b48d7414dca3ce2fdfdeed45cb28487bc1
|
||||
F test/json103.test c5f6b85e69de05f6b3195f9f9d5ce9cd179099a0
|
||||
F test/json104.test 877d5845f6303899b7889ea5dd1bea99076e3100574d5c536082245c5805dcaa
|
||||
@@ -1027,16 +1036,16 @@ F test/loadext2.test 0408380b57adca04004247179837a18e866a74f7
|
||||
F test/lock.test be4fe08118fb988fed741f429b7dd5d65e1c90db
|
||||
F test/lock2.test 5242d8ac4e2d59c403aebff606af449b455aceff
|
||||
F test/lock3.test f271375930711ae044080f4fe6d6eda930870d00
|
||||
F test/lock4.test e175ae13865bc87680607563bafba21f31a26f12
|
||||
F test/lock4.test 27143363eda1622f03c133efc8db808fc331afd973486cb571ea71cd717d37b8
|
||||
F test/lock5.test c6c5e0ebcb21c61a572870cc86c0cb9f14cede38
|
||||
F test/lock6.test ad5b387a3a8096afd3c68a55b9535056431b0cf5
|
||||
F test/lock7.test 49f1eaff1cdc491cc5dee3669f3c671d9f172431
|
||||
F test/lock_common.tcl 7ffb45accf6ee91c736df9bafe0806a44358f035
|
||||
F test/lookaside.test b17c99ae3aef96a8c9fa6f6be33cc75b93d657cb791d3827302b6835b71941f7
|
||||
F test/main.test bb75e406c9b64931f3dc7e7f04626633365bb22f
|
||||
F test/main.test 6bbb3999fd461eb8fb335cbab97409a3d7f91bbb8da60635e8be3e4a04a77772
|
||||
F test/make-where7.tcl 05c16b5d4f5d6512881dfec560cb793915932ef9
|
||||
F test/malloc.test 21c213365f2cca95ab2d7dc078dc8525f96065f8
|
||||
F test/malloc3.test e3b32c724b5a124b57cb0ed177f675249ad0c66a
|
||||
F test/malloc.test 18dd1c4188c81ca79cf123527c71b19ee0c31feb9947fdffb0dc6ceb1436816a
|
||||
F test/malloc3.test 6e88bae6312854a4adb4ecc2a6a5ea8c59b4db778b724ba718e1c43fc8c3c136
|
||||
F test/malloc4.test 957337613002b7058a85116493a262f679f3a261
|
||||
F test/malloc5.test f6eb6eca07a4c75f2897bf43a404689b6295bb95ab2e07d4b52eda743f925a27
|
||||
F test/malloc6.test 2f039d9821927eacae43e1831f815e157659a151
|
||||
@@ -1074,7 +1083,7 @@ F test/misc3.test cf3dda47d5dda3e53fc5804a100d3c82be736c9d
|
||||
F test/misc4.test 0d8be3466adf123a7791a66ba2bc8e8d229e87f3
|
||||
F test/misc5.test 60e1fc758a93cacd19eb2fafcd1d40d150a05047546c7a92389c98047d621901
|
||||
F test/misc6.test 953cc693924d88e6117aeba16f46f0bf5abede91
|
||||
F test/misc7.test edd0b63e2ee29a256900b0514f6fff27e19e9bb2
|
||||
F test/misc7.test 567e223b6497da2226a0340befaf2d663c91ad57a48aede21a35a984a2882d41
|
||||
F test/misc8.test ba03aaa08f02d62fbb8d3b2f5595c1b33aa9bbc5
|
||||
F test/misuse.test 9e7f78402005e833af71dcab32d048003869eca5abcaccc985d4f8dc1d86bcc7
|
||||
F test/mjournal.test 9d86e697dcbc5da2c4e8caba9b176b5765fe65e80c88c278b8c09a917e436795
|
||||
@@ -1091,13 +1100,13 @@ F test/multiplex4.test e8ae4c4bd70606a5727743241f13b5701990abe4
|
||||
F test/mutex1.test ea2cc74d97f077b9e74c84cbd024f14d79a8126f
|
||||
F test/mutex2.test bfeaeac2e73095b2ac32285d2756e3a65e681660
|
||||
F test/nan.test 437d40e6d0778b050d7750726c0cbd2c9936b81962926e8f8c48ca698f00f4d1
|
||||
F test/nockpt.test 9a436a7213ba5ef7a32304998d386d3ea3f76c9d
|
||||
F test/nockpt.test fd5473e30a84848b25ab06524750c05095383e191be83ccb4e6951c8beddfb5b
|
||||
F test/nolock.test f196cf8b8fbea4e2ca345140a2b3f3b0da45c76e
|
||||
F test/normalize.test 501630ab49b0b26b65c74124bf03e3374c1b57fa97aae750f84803609141d167
|
||||
F test/notify1.test 669b2b743618efdc18ca4b02f45423d5d2304abf
|
||||
F test/notify2.test 2ecabaa1305083856b7c39cf32816b612740c161
|
||||
F test/notify3.test 10ff25cde502e72a92053a2f215d64bece4ef934
|
||||
F test/notnull.test f8fcf58669ddba79274daa2770d61dfad8274f62
|
||||
F test/notnull.test b6999231221df3534827e45e2005dd7a815fdd5f2c2e1afb9be21ead410816f8
|
||||
F test/null.test 0dcce4f04284ec66108c503327ad6d224c0752b3
|
||||
F test/numcast.test 5d126f7f581432e86a90d1e35cac625164aec4a1
|
||||
F test/numindex1.test 20a5450d4b056e48cd5db30e659f13347a099823
|
||||
@@ -1113,14 +1122,14 @@ F test/orderby7.test 3d1383d52ade5b9eb3a173b3147fdd296f0202da
|
||||
F test/orderby8.test 23ef1a5d72bd3adcc2f65561c654295d1b8047bd
|
||||
F test/orderby9.test 87fb9548debcc2cd141c5299002dd94672fa76a3
|
||||
F test/oserror.test b32dc34f2363ef18532e3a0a7358e3e7e321974f
|
||||
F test/ossfuzz.c 7f5cc87a0280a5854c1bfa7d5c4d07d34731f08ec34dc9c916aa35ed292b1468
|
||||
F test/ossfuzz.c 3613bc516386234cf2e513fb94dc677ab3862eb7ebc5b3671c319a80f86839fb
|
||||
F test/ossshell.c 296ab63067841bd1b1e97b46a0b2af48ee7f69d50d1a723008bee12dd7122622
|
||||
F test/ovfl.test 199c482696defceacee8c8e0e0ef36da62726b2f
|
||||
F test/pager1.test 8149b2a8986fee667ab6a8171ab310be19e77ae215bebad0e90c857b0df1935c
|
||||
F test/pager1.test f596d3bd53ce96e1d87d44d223d2ae6c8867dd782c425e5eb28b5721fa6aaa97
|
||||
F test/pager2.test 67b8f40ae98112bcdba1f2b2d03ea83266418c71
|
||||
F test/pager3.test 3856d9c80839be0668efee1b74811b1b7f7fc95f
|
||||
F test/pager3.test 4e9a83d6ca0838d7c602c9eb93d1357562d9059c1e02ffb138a8271020838370
|
||||
F test/pager4.test a122e9e6925d5b23b31e3dfef8c6a44bbf19590e
|
||||
F test/pagerfault.test 263c5442c06caf0b9b9e3fe42acdeb11f254dcebe533f69f401aaef9111eaf20
|
||||
F test/pagerfault.test 63c5da625562c66345ab4528790327ca63db2f6f9cbae2aba8cb7c51de3d1628
|
||||
F test/pagerfault2.test caf4c7facb914fd3b03a17b31ae2b180c8d6ca1f
|
||||
F test/pagerfault3.test 1003fcda009bf48a8e22a516e193b6ef0dd1bbd8
|
||||
F test/pageropt.test 84e4cc5cbca285357f7906e99b21be4f2bf5abc0
|
||||
@@ -1137,7 +1146,7 @@ F test/pragma4.test 3046501bee2f652dc2a4f9c87781e2741361d6864439c8381aba6c3b774b
|
||||
F test/pragma5.test 824ce6ced5d6b7ec71abe37fc6005ff836fe39d638273dc5192b39864b9ee983
|
||||
F test/pragmafault.test 275edaf3161771d37de60e5c2b412627ac94cef11739236bec12ed1258b240f8
|
||||
F test/printf.test b3ff34e73d59124140eaf89f7672e21bc2ca5fcc
|
||||
F test/printf2.test 9e6db85f81c63f2367c34a9d7db384088bd374ad
|
||||
F test/printf2.test 30b5dd0b4b992dc5626496846ecce17ff592cacbcb11c3e589f3ac4d7e129dae
|
||||
F test/progress.test ebab27f670bd0d4eb9d20d49cef96e68141d92fb
|
||||
F test/ptrchng.test ef1aa72d6cf35a2bbd0869a649b744e9d84977fc
|
||||
F test/pushdown.test 5e72c51c5e33253ed639ccee1e01ce62d62b6eee5ca893cd82334e4ee7b1d7fc
|
||||
@@ -1156,13 +1165,13 @@ F test/regexp2.test 40e894223b3d6672655481493f1be12012f2b33c
|
||||
F test/reindex.test 44edd3966b474468b823d481eafef0c305022254
|
||||
F test/releasetest.tcl 6aaa853f7a7bbdc458d4cb42c0425228729b0f3e5769e9b41088c08eee999a49 x
|
||||
F test/resolver01.test f4022acafda7f4d40eca94dbf16bc5fc4ac30ceb
|
||||
F test/rollback.test f580934279800d480a19176c6b44909df31ce7ad45267ea475a541daa522f3d3
|
||||
F test/rollback.test 06680159bc6746d0f26276e339e3ae2f951c64812468308838e0a3362d911eaa
|
||||
F test/rollback2.test 8435d6ff0f13f51d2a4181c232e706005fa90fc5
|
||||
F test/rollbackfault.test 0e646aeab8840c399cfbfa43daab46fd609cf04a
|
||||
F test/rowallock.test 3f88ec6819489d0b2341c7a7528ae17c053ab7cc
|
||||
F test/rowhash.test 0bc1d31415e4575d10cacf31e1a66b5cc0f8be81
|
||||
F test/rowid.test 5b7509f384f4f6fae1af3c8c104c8ca299fea18d
|
||||
F test/rowvalue.test 44f3492f415cc9f374e8388a5eb61503eaca5230
|
||||
F test/rowvalue.test 32861d6a933ded868035f2ec79aeb993a2a46eb7a6d282ae13415a4c2e369463
|
||||
F test/rowvalue2.test 060d238b7e5639a7c5630cb5e63e311b44efef2b
|
||||
F test/rowvalue3.test 3068f508753af69884b12125995f023da0dbb256
|
||||
F test/rowvalue4.test 4b556d7de161a0dd8cff095c336e913986398bea
|
||||
@@ -1190,7 +1199,7 @@ F test/schema5.test 29699b4421f183c8f0e88bd28ce7d75d13ea653e
|
||||
F test/schema6.test e4bd1f23d368695eb9e7b51ef6e02ca0642ea2ab4a52579959826b5e7dce1f9b
|
||||
F test/securedel.test 2f70b2449186a1921bd01ec9da407fbfa98c3a7a5521854c300c194b2ff09384
|
||||
F test/securedel2.test 2d54c28e46eb1fd6902089958b20b1b056c6f1c5
|
||||
F test/select1.test 460a5824df01575b18f7fa4bd8e40d09de20c542e90c1543e164bc7d3b0a0bb7
|
||||
F test/select1.test 2e760bab8f3658b3b97debcf52860d0d2e20aa6cbe8b40e678ddb99871a15491
|
||||
F test/select2.test 352480e0e9c66eda9c3044e412abdf5be0215b56
|
||||
F test/select3.test 2ce595f8fb8e2ac10071d3b4e424cadd4634a054
|
||||
F test/select4.test 5389d9895968d1196c457d59b3ee6515d771d328
|
||||
@@ -1205,7 +1214,7 @@ F test/selectC.test e25243f8ca503e06f252eb0218976d07cfeceac3
|
||||
F test/selectD.test b0f02a04ef7737decb24e08be2c39b9664b43394
|
||||
F test/selectE.test a8730ca330fcf40ace158f134f4fe0eb00c7edbf
|
||||
F test/selectF.test 21c94e6438f76537b72532fa9fd4710cdd455fc3
|
||||
F test/selectG.test e8600e379589e85e9fefd2fe4d44a4cdd63f6982
|
||||
F test/selectG.test 089f7d3d7e6db91566f00b036cb353107a2cca6220eb1cb264085a836dae8840
|
||||
F test/server1.test 46803bd3fe8b99b30dbc5ff38ffc756f5c13a118
|
||||
F test/session.test 78fa2365e93d3663a6e933f86e7afc395adf18be
|
||||
F test/shared.test 1da9dbad400cee0d93f252ccf76e1ae007a63746
|
||||
@@ -1216,18 +1225,18 @@ F test/shared6.test 866bb4982c45ce216c61ded5e8fde4e7e2f3ffa9
|
||||
F test/shared7.test a81e99f83e6c51b02ac99c96fb3a2a7b5978c956
|
||||
F test/shared8.test 00a07bf5e1337ecf72e94542bdefdc330d7a2538
|
||||
F test/shared9.test 5f2a8f79b4d6c7d107a01ffa1ed05ae7e6333e21
|
||||
F test/sharedA.test 0cdf1a76dfa00e6beee66af5b534b1e8df2720f5
|
||||
F test/sharedA.test 49d87ec54ab640fbbc3786ee3c01de94aaa482a3a9f834ad3fe92770eb69e281
|
||||
F test/sharedB.test 16cc7178e20965d75278f410943109b77b2e645e
|
||||
F test/shared_err.test 32634e404a3317eeb94abc7a099c556a346fdb8fb3858dbe222a4cbb8926a939
|
||||
F test/sharedlock.test 5ede3c37439067c43b0198f580fd374ebf15d304
|
||||
F test/shell1.test 6d69e08039aea13f2c42749f162fe05eab7b5c93729f31d49d7d27cf36226e5a
|
||||
F test/shell1.test 9f8b8da05a79b134e252a5e1d8d411245ad83ac7126c262900b9f42b43108ffd
|
||||
F test/shell2.test e242a9912f44f4c23c3d1d802a83e934e84c853b
|
||||
F test/shell3.test 9b95ba643eaa228376f06a898fb410ee9b6e57c1
|
||||
F test/shell3.test ac8c2b744014c3e9a0e26bfd829ab65f00923dc1a91ffd044863e9423cc91494
|
||||
F test/shell4.test 89ad573879a745974ff2df20ff97c5d6ffffbd5d
|
||||
F test/shell5.test 23939a4c51f0421330ea61dbd3c74f9c215f5f8d3d1a94846da6ffc777a35458
|
||||
F test/shell6.test 1ceb51b2678c472ba6cf1e5da96679ce8347889fe2c3bf93a0e0fa73f00b00d3
|
||||
F test/shell7.test 115132f66d0463417f408562cc2cf534f6bbc6d83a6d50f0072a9eb171bae97f
|
||||
F test/shell8.test 7585847402452d594f0e5f93430d34ed63b2f34ca7e956f63db157f9327c6896
|
||||
F test/shell8.test 96be02ea0c21f05b24c1883d7b711a1fa8525a68ab7b636aacf6057876941013
|
||||
F test/shortread1.test bb591ef20f0fd9ed26d0d12e80eee6d7ac8897a3
|
||||
F test/show_speedtest1_rtree.tcl 32e6c5f073d7426148a6936a0408f4b5b169aba5
|
||||
F test/shrink.test 1b4330b1fd9e818c04726d45cb28db73087535ce
|
||||
@@ -1258,15 +1267,16 @@ F test/speed4.test abc0ad3399dcf9703abed2fff8705e4f8e416715
|
||||
F test/speed4p.explain 6b5f104ebeb34a038b2f714150f51d01143e59aa
|
||||
F test/speed4p.test 0e51908951677de5a969b723e03a27a1c45db38b
|
||||
F test/speedtest1.c a5faf4cbe5769eee4b721b3875cb3f12520a9b99d9026b1063b47c39603375b8
|
||||
F test/spellfix.test f9c1f431e2c096c8775fec032952320c0e4700db
|
||||
F test/spellfix.test 951a6405d49d1a23d6b78027d3877b4a33eeb8221dcab5704b499755bb4f552e
|
||||
F test/spellfix2.test dfc8f519a3fc204cb2dfa8b4f29821ae90f6f8c3
|
||||
F test/spellfix3.test 0f9efaaa502a0e0a09848028518a6fb096c8ad33
|
||||
F test/spellfix4.test 51c7c26514ade169855c66bcf130bd5acfb4d7fd090cc624645ab275ae6a41fb
|
||||
F test/sqldiff1.test 28cd737cf1b0078b1ec1bbf425e674c47785835e
|
||||
F test/sqllimits1.test a74ee2a3740b9f9c2437c246d8fb77354862a142
|
||||
F test/sqllog.test 6af6cb0b09f4e44e1917e06ce85be7670302517a
|
||||
F test/stat.test f8f1279ffffabe6df825723af18cc6e0ae70a893
|
||||
F test/statfault.test f525a7bf633e50afd027700e9a486090684b1ac1
|
||||
F test/stmt.test 64844332db69cf1a735fcb3e11548557fc95392f
|
||||
F test/stmt.test 54ed2cc0764bf3e48a058331813c3dbd19fc1d0827c3d8369914a5d8f564ec75
|
||||
F test/stmtvtab1.test 6873dfb24f8e79cbb5b799b95c2e4349060eb7a3b811982749a84b359468e2d5
|
||||
F test/subjournal.test 8d4e2572c0ee9a15549f0d8e40863161295107e52f07a3e8012a2e1fdd093c49
|
||||
F test/subquery.test d7268d193dd33d5505df965399d3a594e76ae13f
|
||||
@@ -1277,11 +1287,11 @@ F test/subtype1.test 7fe09496352f97053af1437150751be2d0a0cae8
|
||||
F test/superlock.test ec94f0556b6488d97f71c79f9061ae08d9ab8f12
|
||||
F test/swarmvtab.test 9a3fd5ab3e9b3c976ad1b3d7646aab725114f2ac26b59395d0778b33bab6cdaf
|
||||
F test/swarmvtab2.test c948cb2fdfc5b01d85e8f6d6504854202dc1a0782ab2a0ed61538f27cbd0aa5c
|
||||
F test/swarmvtab3.test c4c8d09e56ae99b90187ac225458f13f373873ea296fc442c7ad7511f25e7314
|
||||
F test/swarmvtab3.test 6cb664669630fcec4102a09333e52068734858fd2761eee3b0465c14cdbcee29
|
||||
F test/swarmvtabfault.test 00aec54665909490f5c383f3cae3b5d18bd97c12490b429ff8752a3027acfa42
|
||||
F test/symlink.test c9ebe7330d228249e447038276bfc8a7b22f4849
|
||||
F test/sync.test 2f84bdbc2b2df1fcb0220575b4b9f8cea94b7529
|
||||
F test/sync2.test 6be8ed007fa063b147773c1982b5bdba97a32badc536bdc6077eff5cf8710ece
|
||||
F test/symlink.test 0d816670325536b8973ec08d32b45136baddb80bd45fd178e0ce7a9e8153f3e7
|
||||
F test/sync.test 89539f4973c010eda5638407e71ca7fddbcd8e0594f4c9980229f804d4333092
|
||||
F test/sync2.test 8f9f7d4f6d5be8ca8941a8dadcc4299e558cb6a1ff653a9469146c7a76ef2039
|
||||
F test/syscall.test a39d9a36f852ae6e4800f861bc2f2e83f68bbc2112d9399931ecfadeabd2d69d
|
||||
F test/sysfault.test c9f2b0d8d677558f74de750c75e12a5454719d04
|
||||
F test/tabfunc01.test c47171c36b3d411df2bd49719dcaa5d034f8d277477fd41d253940723b969a51
|
||||
@@ -1289,14 +1299,14 @@ F test/table.test b708f3e5fa2542fa51dfab21fc07b36ea445cb2f
|
||||
F test/tableapi.test 2674633fa95d80da917571ebdd759a14d9819126
|
||||
F test/tableopts.test dba698ba97251017b7c80d738c198d39ab747930
|
||||
F test/tclsqlite.test c3d7ac9449634b9f17fd048a3c0212e88a7448be810a9c5bd051acc1ffa00d2f
|
||||
F test/tempdb.test bd92eba8f20e16a9136e434e20b280794de3cdb6
|
||||
F test/tempdb.test 4cdaa23ddd8acb4d79cbb1b68ccdfd09b0537aaba909ca69a876157c2a2cbd08
|
||||
F test/tempdb2.test 27e41ed540b2f9b056c2e77e9bddc1b875358507
|
||||
F test/tempfault.test 0c0d349c9a99bf5f374655742577f8712c647900
|
||||
F test/temptable.test d2c9b87a54147161bcd1822e30c1d1cd891e5b30
|
||||
F test/temptable2.test cd396beb41117a5302fff61767c35fa4270a0d5e
|
||||
F test/temptable3.test d11a0974e52b347e45ee54ef1923c91ed91e4637
|
||||
F test/temptrigger.test 38f0ca479b1822d3117069e014daabcaacefffcc
|
||||
F test/tester.tcl 3ed81b9e1d9718a8d9603596c8a877793d054294053c4277a3d3897eabab3866
|
||||
F test/tester.tcl 94901a4625d9a2229666dd5c44120ddf7f0fb639470710ef74a4cefc7b039e07
|
||||
F test/thread001.test 9f22fd3525a307ff42a326b6bc7b0465be1745a5
|
||||
F test/thread002.test e630504f8a06c00bf8bbe68528774dd96aeb2e58
|
||||
F test/thread003.test ee4c9efc3b86a6a2767516a37bd64251272560a7
|
||||
@@ -1416,7 +1426,7 @@ F test/tkt3357.test 77c37c6482b526fe89941ce951c22d011f5922ed
|
||||
F test/tkt3419.test 1bbf36d7ea03b638c15804251287c2391f5c1f6b
|
||||
F test/tkt3424.test 61f831bd2b071bd128fa5d00fbda57e656ca5812
|
||||
F test/tkt3442.test 53840ec5325bb94544792aad4c20476f81dc26b1
|
||||
F test/tkt3457.test 44e980fe5334753dcc27b94fa4deabc485a92f74
|
||||
F test/tkt3457.test 5651e2cbb94645b677ec663160b9e192b87b7d365aecdfb24e19f749575a6fc2
|
||||
F test/tkt3461.test 228ea328a5a21e8663f80ee3d212a6ad92549a19
|
||||
F test/tkt3493.test 1686cbde85f8721fc1bdc0ee72f2ef2f63139218
|
||||
F test/tkt3508.test d75704db9501625c7f7deec119fcaf1696aefb7d
|
||||
@@ -1490,7 +1500,7 @@ F test/unique2.test 3674e9f2a3f1fbbfd4772ac74b7a97090d0f77d2
|
||||
F test/unixexcl.test d936ba2b06794018e136418addd59a2354eeae97
|
||||
F test/unordered.test ca7adce0419e4ca0c50f039885e76ed2c531eda8
|
||||
F test/update.test 6c68446b8a0a33d522a7c72b320934596a2d7d32
|
||||
F test/update2.test fffc92e72ae568fe048588762e650cd8ccbd8c8b6e4fe9099231766bfe4b51de
|
||||
F test/update2.test 5e67667e1c54017d964e626db765cf8bedcf87483c184f4c575bdb8c1dd2313e
|
||||
F test/uri.test 3481026f00ade6dfe8adb7acb6e1e47b04369568
|
||||
F test/uri2.test 9d3ba7a53ee167572d53a298ee4a5d38ec4a8fb7
|
||||
F test/userauth01.test e740a2697a7b40d7c5003a7d7edaee16acd349a9
|
||||
@@ -1499,7 +1509,7 @@ F test/vacuum.test ce91c39f7f91a4273bf620efad21086b5aa6ef1d
|
||||
F test/vacuum2.test aa048abee196c16c9ba308465494009057b79f9b
|
||||
F test/vacuum3.test 77ecdd54592b45a0bcb133339f99f1ae0ae94d0d
|
||||
F test/vacuum4.test 7ea76b769fffeb41f925303b04cbcf5a5bbeabe55e4c60ae754ff24eeeb7c010
|
||||
F test/vacuum5.test c87234e8ca4107f349da4edbeda3e4ea5adc93f3
|
||||
F test/vacuum5.test 263b144d537e92ad8e9ca8a73cc6e1583f41cfd0dda9432b87f7806174a2f48c
|
||||
F test/vacuummem.test 7b42abb3208bd82dd23a7536588396f295a314f2
|
||||
F test/varint.test bbce22cda8fc4d135bcc2b589574be8410614e62
|
||||
F test/veryquick.test 57ab846bacf7b90cf4e9a672721ea5c5b669b661
|
||||
@@ -1526,7 +1536,7 @@ F test/vtab_alter.test 736e66fb5ec7b4fee58229aa3ada2f27ec58bc58c00edae4836890c37
|
||||
F test/vtab_err.test 0d4d8eb4def1d053ac7c5050df3024fd47a3fbd8
|
||||
F test/vtab_shared.test 5253bff2355a9a3f014c15337da7e177ab0ef8ad
|
||||
F test/wal.test 613efec03e517e1775d86b993a54877d2e29a477
|
||||
F test/wal2.test 2d81ffe2a02d9e5c7447b266f7153716cfcba7aecda5ed832db4544617399e29
|
||||
F test/wal2.test 155b9efa999bdb38ce1cd729b9a4fcdbffd6b88be27f039bad1d2929d287d918
|
||||
F test/wal3.test 2a93004bc0fb2b5c29888964024695bade278ab2
|
||||
F test/wal4.test 4744e155cd6299c6bd99d3eab1c82f77db9cdb3c
|
||||
F test/wal5.test 9c11da7aeccd83a46d79a556ad11a18d3cb15aa9
|
||||
@@ -1544,19 +1554,19 @@ F test/walcrash.test 21038858cc552077b0522f50b0fa87e38139306a
|
||||
F test/walcrash2.test a0edab4e5390f03b99a790de89aad15d6ec70b36
|
||||
F test/walcrash3.test e426aa58122d20f2b9fbe9a507f9eb8cab85b8af
|
||||
F test/walcrash4.test e7b6e7639a950a0cca8e210e248c8dad4d63bf20
|
||||
F test/walfault.test 1f8389f7709877e9b4cc679033d71d6fe529056b
|
||||
F test/walfault.test 09b8ad7e52d2f54bce50e31aa7ea51412bb9f70ac13c74e669ddcd8b48b0d98d
|
||||
F test/walhook.test ed00a40ba7255da22d6b66433ab61fab16a63483
|
||||
F test/walmode.test 4022fe03ae6e830583672caa101f046438a0473c
|
||||
F test/walmode.test cd6e7cff618eaaa5910ce57c3657aa50110397f86213886a2400afb9bfec7b7b
|
||||
F test/walnoshm.test 84ca10c544632a756467336b7c3b864d493ee496
|
||||
F test/waloverwrite.test dad2f26567f1b45174e54fbf9a8dc1cb876a7f03
|
||||
F test/walpersist.test 8c6b7e3ec1ba91b5e4dc4e0921d6d3f87cd356a6
|
||||
F test/walprotocol.test a112aba0b79e3adeaa485fed09484b32c654e97df58e454aa8489ac2cd57bf84
|
||||
F test/walro.test cb438d05ba0d191f10b688e39c4f0cd5b71569a1d1f4440e5bdf3c6880e08c20
|
||||
F test/walro2.test 5cd57d192ee334c3894330303b5f8cb6789fef49b2c83ad1b50b9b132d0f7ae1
|
||||
F test/walro2.test 0e79dd15cbdb4f482c01ea248373669c732414a726b357d04846a816afafb768
|
||||
F test/walrofault.test c70cb6e308c443867701856cce92ad8288cd99488fa52afab77cca6cfd51af68
|
||||
F test/walshared.test 0befc811dcf0b287efae21612304d15576e35417
|
||||
F test/walslow.test c05c68d4dc2700a982f89133ce103a1a84cc285f
|
||||
F test/walthread.test de8dbaf6d9e41481c460ba31ca61e163d7348f8e
|
||||
F test/walthread.test 14b20fcfa6ae152f5d8e12f5dc8a8a724b7ef189f5d8ef1e2ceab79f2af51747
|
||||
F test/where.test f0c325563acde44f2c4ea6ba348e9e29f7121757
|
||||
F test/where2.test 478d2170637b9211f593120648858593bf2445a1
|
||||
F test/where3.test 54cdeb02157acc979de41530b804ae7b09552bf1
|
||||
@@ -1571,7 +1581,7 @@ F test/whereB.test 0def95db3bdec220a731c7e4bec5930327c1d8c5
|
||||
F test/whereC.test cae295158703cb3fc23bf1a108a9ab730efff0f6
|
||||
F test/whereD.test 711d4df58d6d4fb9b3f5ce040b818564198be002
|
||||
F test/whereE.test b3a055eef928c992b0a33198a7b8dc10eea5ad2f
|
||||
F test/whereF.test d44b58338fe5ddd7286023e9bedb255aa264a6c4d2168b49591b167371c675c7
|
||||
F test/whereF.test 3d9412b1199d3e2bed34fcb76b4c48d0bf4df95d27e3f8dd27b6f8b4716d0d89
|
||||
F test/whereG.test dde4c52a97385a55be6a7cd46be8373f0cf35501
|
||||
F test/whereH.test e4b07f7a3c2f5d31195cd33710054c78667573b2
|
||||
F test/whereI.test eab5b226bbc344ac70d7dc09b963a064860ae6d7
|
||||
@@ -1587,8 +1597,9 @@ F test/win32lock.test fbf107c91d8f5512be5a5b87c4c42ab9fdd54972
|
||||
F test/win32longpath.test 169c75a3b2e43481f4a62122510210c67b08f26d
|
||||
F test/win32nolock.test ac4f08811a562e45a5755e661f45ca85892bdbbc
|
||||
F test/with1.test ca08e291249a810a2ec9b72ceef5575e07d5925b360fcf6652ae6fe06ac4dced
|
||||
F test/with2.test 2b40da883658eb74ad8ad06afabe11a408e7fb87
|
||||
F test/with2.test e0030e2f0267a910d6c0e4f46f2dfe941c1cc0d4f659ba69b3597728e7e8f1ab
|
||||
F test/with3.test e71604a0e53cba82bc04c703987cb1d6751ec0b6
|
||||
F test/with4.test 257be66c0c67fee1defbbac0f685c3465e2cad037f21ce65f23f86084f198205
|
||||
F test/withM.test 693b61765f2b387b5e3e24a4536e2e82de15ff64
|
||||
F test/without_rowid1.test 06b7215130882d6a072233820dd364c874c4fd69221e8fc756ec471009192874
|
||||
F test/without_rowid2.test af260339f79d13cb220288b67cd287fbcf81ad99
|
||||
@@ -1599,8 +1610,10 @@ F test/without_rowid6.test 1f99644e6508447fb050f73697350c7ceca3392e
|
||||
F test/wordcount.c cb589cec469a1d90add05b1f8cee75c7210338d87a5afd65260ed5c0f4bbf8ac
|
||||
F test/writecrash.test f1da7f7adfe8d7f09ea79b42e5ca6dcc41102f27f8e334ad71539501ddd910cc
|
||||
F test/zeroblob.test 3857870fe681b8185654414a9bccfde80b62a0fa
|
||||
F test/zerodamage.test e59a56443d6298ecf7435f618f0b27654f0c849e
|
||||
F test/zipfile.test a1dd0429294cb9487900fc2b29aa9921329f20a7314aa0921b668246172ac090
|
||||
F test/zerodamage.test 9c41628db7e8d9e8a0181e59ea5f189df311a9f6ce99cc376dc461f66db6f8dc
|
||||
F test/zipfile.test 44aa8af115cc3e8c905468768dc761260650a8fdfca57e10f9818f5f8008d340
|
||||
F test/zipfile2.test 67d5f08a202796d4b7a71dfa4b8dcb74aa7a9d1f42c5f17bedff9855c1ba7aa5
|
||||
F test/zipfilefault.test 050be76778d2ec83566a542800fc3967f65ce719671a819016ada8b654bc14f7
|
||||
F tool/GetFile.cs a15e08acb5dd7539b75ba23501581d7c2b462cb5
|
||||
F tool/GetTclKit.bat 8995df40c4209808b31f24de0b58f90930239a234f7591e3675d45bfbb990c5d
|
||||
F tool/Replace.cs 02c67258801c2fb5f63231e0ac0f220b4b36ba91
|
||||
@@ -1619,7 +1632,7 @@ F tool/genfkey.test 4196a8928b78f51d54ef58e99e99401ab2f0a7e5
|
||||
F tool/getlock.c f4c39b651370156cae979501a7b156bdba50e7ce
|
||||
F tool/kvtest-speed.sh 4761a9c4b3530907562314d7757995787f7aef8f
|
||||
F tool/lemon.c 7f7735326ca9c3b48327b241063cee52d35d44e20ebe1b3624a81658052a4d39
|
||||
F tool/lempar.c dddd4f592b8bad36aec4500d456c5db5fe42fefc4ee384913880439d8917f87a
|
||||
F tool/lempar.c 468a155e8729cfbccfe1d85bf60d064f1dab76167a51149ec5c7928a2de63953
|
||||
F tool/libvers.c caafc3b689638a1d88d44bc5f526c2278760d9b9
|
||||
F tool/loadfts.c c3c64e4d5e90e8ba41159232c2189dba4be7b862
|
||||
F tool/logest.c 11346aa019e2e77a00902aa7d0cabd27bd2e8cca
|
||||
@@ -1657,7 +1670,7 @@ F tool/showstat4.c 0682ebea7abf4d3657f53c4a243f2e7eab48eab344ed36a94bb75dcd19a5c
|
||||
F tool/showwal.c ad9d768f96ca6199ad3a8c9562d679680bd032dd01204ea3e5ea6fb931d81847
|
||||
F tool/soak1.tcl 8d407956e1a45b485a8e072470a3e629a27037fe
|
||||
F tool/spaceanal.tcl 4bfd19aad7eb3ce0372ef0255f58035e0bba4ff5e9acfd763a10c6fb365c8dec
|
||||
F tool/speed-check.sh 9ae425da8819e54e780cf494fc6d8175dfb16e109ae3214a45a5c9bb2b74e2c4
|
||||
F tool/speed-check.sh 4ff9b095cf1a7643f0264e7fb7d23f0b12b7cce587a9de315877c378e90eeaf4
|
||||
F tool/speedtest.tcl 06c76698485ccf597b9e7dbb1ac70706eb873355
|
||||
F tool/speedtest16.c ecb6542862151c3e6509bbc00509b234562ae81e
|
||||
F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff
|
||||
@@ -1666,7 +1679,7 @@ F tool/speedtest8inst1.c 7ce07da76b5e745783e703a834417d725b7d45fd
|
||||
F tool/split-sqlite3c.tcl 3efcd4240b738f6bb2b5af0aea7e1e0ef9bc1c61654f645076cec883030b710c
|
||||
F tool/sqldiff.c 30879bbc8de686df4624e86adce2d8981f500904c1cfb55b5d1eea2ffd9341eb
|
||||
F tool/sqlite3_analyzer.c.in 7eeaae8b0d7577662acaabbb11107af0659d1b41bc1dfdd4d91422de27127968
|
||||
F tool/sqltclsh.c.in 8b2529b6c3cdd8ad6aaff21e80eb58370c428cb207b4607d0da4def064dcec56
|
||||
F tool/sqltclsh.c.in 1bcc2e9da58fadf17b0bf6a50e68c1159e602ce057210b655d50bad5aaaef898
|
||||
F tool/sqltclsh.tcl 862f4cf1418df5e1315b5db3b5ebe88969e2a784525af5fbf9596592f14ed848
|
||||
F tool/srcck1.c 371de5363b70154012955544f86fdee8f6e5326f
|
||||
F tool/stack_usage.tcl f8e71b92cdb099a147dad572375595eae55eca43
|
||||
@@ -1699,7 +1712,7 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93
|
||||
F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc
|
||||
F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e
|
||||
F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0
|
||||
P db5d138e97f22ad4d4d11dbef96df93696ba0e557809066bc263ca3c3898f349
|
||||
R 5585a6831c91176202d5e0f81c59c944
|
||||
U drh
|
||||
Z ca698384a23dd84f9bb875fa9da10ba1
|
||||
P f11beb16a87cc967e896cf67121b1e4045e427ebdc6a424e9f009ffced955d36
|
||||
R ce086be2fa4585d5057d94c9c14e09e6
|
||||
U dan
|
||||
Z fcd96707fe4566207f6172155f7ee098
|
||||
|
||||
+1
-1
@@ -1 +1 @@
|
||||
658f42257d56a3562dfa8e55023c6e497f55c565cd751d942de3a9e0cb2fa708
|
||||
84e9351bbd0a9bf9e1d64a441366a90276c231b44548cbc947f7fb2842f82490
|
||||
@@ -234,6 +234,10 @@ static void openStatTable(
|
||||
"DELETE FROM %Q.%s WHERE %s=%Q",
|
||||
pDb->zDbSName, zTab, zWhereType, zWhere
|
||||
);
|
||||
#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
|
||||
}else if( db->xPreUpdateCallback ){
|
||||
sqlite3NestedParse(pParse, "DELETE FROM %Q.%s", pDb->zDbSName, zTab);
|
||||
#endif
|
||||
}else{
|
||||
/* The sqlite_stat[134] table already exists. Delete all rows. */
|
||||
sqlite3VdbeAddOp2(v, OP_Clear, aRoot[i], iDb);
|
||||
@@ -998,6 +1002,9 @@ static void analyzeOneTable(
|
||||
int regIdxname = iMem++; /* Register containing index name */
|
||||
int regStat1 = iMem++; /* Value for the stat column of sqlite_stat1 */
|
||||
int regPrev = iMem; /* MUST BE LAST (see below) */
|
||||
#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
|
||||
Table *pStat1 = 0;
|
||||
#endif
|
||||
|
||||
pParse->nMem = MAX(pParse->nMem, iMem);
|
||||
v = sqlite3GetVdbe(pParse);
|
||||
@@ -1023,6 +1030,18 @@ static void analyzeOneTable(
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
|
||||
if( db->xPreUpdateCallback ){
|
||||
pStat1 = (Table*)sqlite3DbMallocZero(db, sizeof(Table) + 13);
|
||||
if( pStat1==0 ) return;
|
||||
pStat1->zName = (char*)&pStat1[1];
|
||||
memcpy(pStat1->zName, "sqlite_stat1", 13);
|
||||
pStat1->nCol = 3;
|
||||
pStat1->iPKey = -1;
|
||||
sqlite3VdbeAddOp4(pParse->pVdbe, OP_Noop, 0, 0, 0,(char*)pStat1,P4_DYNBLOB);
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Establish a read-lock on the table at the shared-cache level.
|
||||
** Open a read-only cursor on the table. Also allocate a cursor number
|
||||
** to use for scanning indexes (iIdxCur). No index cursor is opened at
|
||||
@@ -1224,6 +1243,9 @@ static void analyzeOneTable(
|
||||
sqlite3VdbeAddOp4(v, OP_MakeRecord, regTabname, 3, regTemp, "BBB", 0);
|
||||
sqlite3VdbeAddOp2(v, OP_NewRowid, iStatCur, regNewRowid);
|
||||
sqlite3VdbeAddOp3(v, OP_Insert, iStatCur, regTemp, regNewRowid);
|
||||
#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
|
||||
sqlite3VdbeChangeP4(v, -1, (char*)pStat1, P4_TABLE);
|
||||
#endif
|
||||
sqlite3VdbeChangeP5(v, OPFLAG_APPEND);
|
||||
|
||||
/* Add the entries to the stat3 or stat4 table. */
|
||||
@@ -1287,6 +1309,9 @@ static void analyzeOneTable(
|
||||
sqlite3VdbeAddOp2(v, OP_NewRowid, iStatCur, regNewRowid);
|
||||
sqlite3VdbeAddOp3(v, OP_Insert, iStatCur, regTemp, regNewRowid);
|
||||
sqlite3VdbeChangeP5(v, OPFLAG_APPEND);
|
||||
#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
|
||||
sqlite3VdbeChangeP4(v, -1, (char*)pStat1, P4_TABLE);
|
||||
#endif
|
||||
sqlite3VdbeJumpHere(v, jZeroRows);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -504,6 +504,14 @@ int sqlite3FixSelect(
|
||||
if( sqlite3FixExpr(pFix, pSelect->pLimit) ){
|
||||
return 1;
|
||||
}
|
||||
if( pSelect->pWith ){
|
||||
int i;
|
||||
for(i=0; i<pSelect->pWith->nCte; i++){
|
||||
if( sqlite3FixSelect(pFix, pSelect->pWith->a[i].pSelect) ){
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
pSelect = pSelect->pPrior;
|
||||
}
|
||||
return 0;
|
||||
|
||||
+20
-9
@@ -123,9 +123,12 @@ int sqlite3_enable_shared_cache(int enable){
|
||||
*/
|
||||
#ifdef SQLITE_DEBUG
|
||||
int corruptPageError(int lineno, MemPage *p){
|
||||
char *zMsg = sqlite3_mprintf("database corruption page %d of %s",
|
||||
char *zMsg;
|
||||
sqlite3BeginBenignMalloc();
|
||||
zMsg = sqlite3_mprintf("database corruption page %d of %s",
|
||||
(int)p->pgno, sqlite3PagerFilename(p->pBt->pPager, 0)
|
||||
);
|
||||
sqlite3EndBenignMalloc();
|
||||
if( zMsg ){
|
||||
sqlite3ReportError(SQLITE_CORRUPT, lineno, zMsg);
|
||||
}
|
||||
@@ -4342,7 +4345,7 @@ int sqlite3BtreeCursorSize(void){
|
||||
** of run-time by skipping the initialization of those elements.
|
||||
*/
|
||||
void sqlite3BtreeCursorZero(BtCursor *p){
|
||||
memset(p, 0, offsetof(BtCursor, iPage));
|
||||
memset(p, 0, offsetof(BtCursor, BTCURSOR_FIRST_UNINIT));
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -4385,11 +4388,19 @@ int sqlite3BtreeCloseCursor(BtCursor *pCur){
|
||||
** Using this cache reduces the number of calls to btreeParseCell().
|
||||
*/
|
||||
#ifndef NDEBUG
|
||||
static int cellInfoEqual(CellInfo *a, CellInfo *b){
|
||||
if( a->nKey!=b->nKey ) return 0;
|
||||
if( a->pPayload!=b->pPayload ) return 0;
|
||||
if( a->nPayload!=b->nPayload ) return 0;
|
||||
if( a->nLocal!=b->nLocal ) return 0;
|
||||
if( a->nSize!=b->nSize ) return 0;
|
||||
return 1;
|
||||
}
|
||||
static void assertCellInfo(BtCursor *pCur){
|
||||
CellInfo info;
|
||||
memset(&info, 0, sizeof(info));
|
||||
btreeParseCell(pCur->pPage, pCur->ix, &info);
|
||||
assert( CORRUPT_DB || memcmp(&info, &pCur->info, sizeof(info))==0 );
|
||||
assert( CORRUPT_DB || cellInfoEqual(&info, &pCur->info) );
|
||||
}
|
||||
#else
|
||||
#define assertCellInfo(x)
|
||||
@@ -4665,14 +4676,15 @@ static int accessPayload(
|
||||
*/
|
||||
if( (pCur->curFlags & BTCF_ValidOvfl)==0 ){
|
||||
int nOvfl = (pCur->info.nPayload-pCur->info.nLocal+ovflSize-1)/ovflSize;
|
||||
if( nOvfl>pCur->nOvflAlloc ){
|
||||
if( pCur->aOverflow==0
|
||||
|| nOvfl*(int)sizeof(Pgno) > sqlite3MallocSize(pCur->aOverflow)
|
||||
){
|
||||
Pgno *aNew = (Pgno*)sqlite3Realloc(
|
||||
pCur->aOverflow, nOvfl*2*sizeof(Pgno)
|
||||
);
|
||||
if( aNew==0 ){
|
||||
return SQLITE_NOMEM_BKPT;
|
||||
}else{
|
||||
pCur->nOvflAlloc = nOvfl*2;
|
||||
pCur->aOverflow = aNew;
|
||||
}
|
||||
}
|
||||
@@ -6186,9 +6198,8 @@ static void freePage(MemPage *pPage, int *pRC){
|
||||
}
|
||||
|
||||
/*
|
||||
** Free any overflow pages associated with the given Cell. Write the
|
||||
** local Cell size (the number of bytes on the original page, omitting
|
||||
** overflow) into *pnSize.
|
||||
** Free any overflow pages associated with the given Cell. Store
|
||||
** size information about the cell in pInfo.
|
||||
*/
|
||||
static int clearCell(
|
||||
MemPage *pPage, /* The page that contains the Cell */
|
||||
@@ -7392,7 +7403,7 @@ static int balance_nonroot(
|
||||
}
|
||||
|
||||
/* Load b.apCell[] with pointers to all cells in pOld. If pOld
|
||||
** constains overflow cells, include them in the b.apCell[] array
|
||||
** contains overflow cells, include them in the b.apCell[] array
|
||||
** in the correct spot.
|
||||
**
|
||||
** Note that when there are multiple overflow cells, it is always the
|
||||
|
||||
+11
-11
@@ -503,20 +503,20 @@ struct BtCursor {
|
||||
u8 curFlags; /* zero or more BTCF_* flags defined below */
|
||||
u8 curPagerFlags; /* Flags to send to sqlite3PagerGet() */
|
||||
u8 hints; /* As configured by CursorSetHints() */
|
||||
int nOvflAlloc; /* Allocated size of aOverflow[] array */
|
||||
Btree *pBtree; /* The Btree to which this cursor belongs */
|
||||
BtShared *pBt; /* The BtShared this cursor points to */
|
||||
BtCursor *pNext; /* Forms a linked list of all cursors */
|
||||
Pgno *aOverflow; /* Cache of overflow page locations */
|
||||
CellInfo info; /* A parse of the cell we are pointing at */
|
||||
i64 nKey; /* Size of pKey, or last integer key */
|
||||
void *pKey; /* Saved key that was cursor last known position */
|
||||
Pgno pgnoRoot; /* The root page of this tree */
|
||||
int skipNext; /* Prev() is noop if negative. Next() is noop if positive.
|
||||
** Error code if eState==CURSOR_FAULT */
|
||||
Btree *pBtree; /* The Btree to which this cursor belongs */
|
||||
Pgno *aOverflow; /* Cache of overflow page locations */
|
||||
void *pKey; /* Saved key that was cursor last known position */
|
||||
/* All fields above are zeroed when the cursor is allocated. See
|
||||
** sqlite3BtreeCursorZero(). Fields that follow must be manually
|
||||
** initialized. */
|
||||
#define BTCURSOR_FIRST_UNINIT pBt /* Name of first uninitialized field */
|
||||
BtShared *pBt; /* The BtShared this cursor points to */
|
||||
BtCursor *pNext; /* Forms a linked list of all cursors */
|
||||
CellInfo info; /* A parse of the cell we are pointing at */
|
||||
i64 nKey; /* Size of pKey, or last integer key */
|
||||
Pgno pgnoRoot; /* The root page of this tree */
|
||||
i8 iPage; /* Index of current page in apPage */
|
||||
u8 curIntKey; /* Value of apPage[0]->intKey */
|
||||
u16 ix; /* Current index for apPage[iPage] */
|
||||
@@ -566,8 +566,8 @@ struct BtCursor {
|
||||
** Do nothing else with this cursor. Any attempt to use the cursor
|
||||
** should return the error code stored in BtCursor.skipNext
|
||||
*/
|
||||
#define CURSOR_INVALID 0
|
||||
#define CURSOR_VALID 1
|
||||
#define CURSOR_VALID 0
|
||||
#define CURSOR_INVALID 1
|
||||
#define CURSOR_SKIPNEXT 2
|
||||
#define CURSOR_REQUIRESEEK 3
|
||||
#define CURSOR_FAULT 4
|
||||
|
||||
+19
-3
@@ -1118,10 +1118,24 @@ void sqlite3AddColumn(Parse *pParse, Token *pName, Token *pType){
|
||||
*/
|
||||
void sqlite3AddNotNull(Parse *pParse, int onError){
|
||||
Table *p;
|
||||
Column *pCol;
|
||||
p = pParse->pNewTable;
|
||||
if( p==0 || NEVER(p->nCol<1) ) return;
|
||||
p->aCol[p->nCol-1].notNull = (u8)onError;
|
||||
pCol = &p->aCol[p->nCol-1];
|
||||
pCol->notNull = (u8)onError;
|
||||
p->tabFlags |= TF_HasNotNull;
|
||||
|
||||
/* Set the uniqNotNull flag on any UNIQUE or PK indexes already created
|
||||
** on this column. */
|
||||
if( pCol->colFlags & COLFLAG_UNIQUE ){
|
||||
Index *pIdx;
|
||||
for(pIdx=p->pIndex; pIdx; pIdx=pIdx->pNext){
|
||||
assert( pIdx->nKeyCol==1 && pIdx->onError!=OE_None );
|
||||
if( pIdx->aiColumn[0]==p->nCol-1 ){
|
||||
pIdx->uniqNotNull = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -2124,7 +2138,7 @@ void sqlite3CreateView(
|
||||
** the end.
|
||||
*/
|
||||
sEnd = pParse->sLastToken;
|
||||
assert( sEnd.z[0]!=0 );
|
||||
assert( sEnd.z[0]!=0 || sEnd.n==0 );
|
||||
if( sEnd.z[0]!=';' ){
|
||||
sEnd.z += sEnd.n;
|
||||
}
|
||||
@@ -3085,7 +3099,9 @@ void sqlite3CreateIndex(
|
||||
*/
|
||||
if( pList==0 ){
|
||||
Token prevCol;
|
||||
sqlite3TokenInit(&prevCol, pTab->aCol[pTab->nCol-1].zName);
|
||||
Column *pCol = &pTab->aCol[pTab->nCol-1];
|
||||
pCol->colFlags |= COLFLAG_UNIQUE;
|
||||
sqlite3TokenInit(&prevCol, pCol->zName);
|
||||
pList = sqlite3ExprListAppend(pParse, 0,
|
||||
sqlite3ExprAlloc(db, TK_ID, &prevCol, 0));
|
||||
if( pList==0 ) goto exit_create_index;
|
||||
|
||||
+1
-1
@@ -760,7 +760,7 @@ void sqlite3GenerateRowDelete(
|
||||
u8 p5 = 0;
|
||||
sqlite3GenerateRowIndexDelete(pParse, pTab, iDataCur, iIdxCur,0,iIdxNoSeek);
|
||||
sqlite3VdbeAddOp2(v, OP_Delete, iDataCur, (count?OPFLAG_NCHANGE:0));
|
||||
if( pParse->nested==0 ){
|
||||
if( pParse->nested==0 || 0==sqlite3_stricmp(pTab->zName, "sqlite_stat1") ){
|
||||
sqlite3VdbeAppendP4(v, (char*)pTab, P4_TABLE);
|
||||
}
|
||||
if( eMode!=ONEPASS_OFF ){
|
||||
|
||||
+3
-4
@@ -658,15 +658,15 @@ static void heightOfExprList(ExprList *p, int *pnHeight){
|
||||
}
|
||||
}
|
||||
}
|
||||
static void heightOfSelect(Select *p, int *pnHeight){
|
||||
if( p ){
|
||||
static void heightOfSelect(Select *pSelect, int *pnHeight){
|
||||
Select *p;
|
||||
for(p=pSelect; p; p=p->pPrior){
|
||||
heightOfExpr(p->pWhere, pnHeight);
|
||||
heightOfExpr(p->pHaving, pnHeight);
|
||||
heightOfExpr(p->pLimit, pnHeight);
|
||||
heightOfExprList(p->pEList, pnHeight);
|
||||
heightOfExprList(p->pGroupBy, pnHeight);
|
||||
heightOfExprList(p->pOrderBy, pnHeight);
|
||||
heightOfSelect(p->pPrior, pnHeight);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2764,7 +2764,6 @@ int sqlite3CodeSubselect(
|
||||
pSel->pLimit = sqlite3PExpr(pParse, TK_LIMIT, pLimit, 0);
|
||||
}
|
||||
pSel->iLimit = 0;
|
||||
pSel->selFlags &= ~SF_MultiValue;
|
||||
if( sqlite3Select(pParse, pSel, &dest) ){
|
||||
return 0;
|
||||
}
|
||||
|
||||
+37
-24
@@ -35,6 +35,8 @@ static CollSeq *sqlite3GetFuncCollSeq(sqlite3_context *context){
|
||||
** iteration of the aggregate loop.
|
||||
*/
|
||||
static void sqlite3SkipAccumulatorLoad(sqlite3_context *context){
|
||||
assert( context->isError<=0 );
|
||||
context->isError = -1;
|
||||
context->skipFlag = 1;
|
||||
}
|
||||
|
||||
@@ -101,8 +103,6 @@ static void lengthFunc(
|
||||
int argc,
|
||||
sqlite3_value **argv
|
||||
){
|
||||
int len;
|
||||
|
||||
assert( argc==1 );
|
||||
UNUSED_PARAMETER(argc);
|
||||
switch( sqlite3_value_type(argv[0]) ){
|
||||
@@ -114,13 +114,17 @@ static void lengthFunc(
|
||||
}
|
||||
case SQLITE_TEXT: {
|
||||
const unsigned char *z = sqlite3_value_text(argv[0]);
|
||||
const unsigned char *z0;
|
||||
unsigned char c;
|
||||
if( z==0 ) return;
|
||||
len = 0;
|
||||
while( *z ){
|
||||
len++;
|
||||
SQLITE_SKIP_UTF8(z);
|
||||
z0 = z;
|
||||
while( (c = *z)!=0 ){
|
||||
z++;
|
||||
if( c>=0xc0 ){
|
||||
while( (*z & 0xc0)==0x80 ){ z++; z0++; }
|
||||
}
|
||||
}
|
||||
sqlite3_result_int(context, len);
|
||||
sqlite3_result_int(context, (int)(z-z0));
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
@@ -1195,6 +1199,8 @@ static void replaceFunc(
|
||||
i64 nOut; /* Maximum size of zOut */
|
||||
int loopLimit; /* Last zStr[] that might match zPattern[] */
|
||||
int i, j; /* Loop counters */
|
||||
unsigned cntExpand; /* Number zOut expansions */
|
||||
sqlite3 *db = sqlite3_context_db_handle(context);
|
||||
|
||||
assert( argc==3 );
|
||||
UNUSED_PARAMETER(argc);
|
||||
@@ -1226,33 +1232,40 @@ static void replaceFunc(
|
||||
return;
|
||||
}
|
||||
loopLimit = nStr - nPattern;
|
||||
cntExpand = 0;
|
||||
for(i=j=0; i<=loopLimit; i++){
|
||||
if( zStr[i]!=zPattern[0] || memcmp(&zStr[i], zPattern, nPattern) ){
|
||||
zOut[j++] = zStr[i];
|
||||
}else{
|
||||
u8 *zOld;
|
||||
sqlite3 *db = sqlite3_context_db_handle(context);
|
||||
nOut += nRep - nPattern;
|
||||
testcase( nOut-1==db->aLimit[SQLITE_LIMIT_LENGTH] );
|
||||
testcase( nOut-2==db->aLimit[SQLITE_LIMIT_LENGTH] );
|
||||
if( nOut-1>db->aLimit[SQLITE_LIMIT_LENGTH] ){
|
||||
sqlite3_result_error_toobig(context);
|
||||
sqlite3_free(zOut);
|
||||
return;
|
||||
}
|
||||
zOld = zOut;
|
||||
zOut = sqlite3_realloc64(zOut, (int)nOut);
|
||||
if( zOut==0 ){
|
||||
sqlite3_result_error_nomem(context);
|
||||
sqlite3_free(zOld);
|
||||
return;
|
||||
if( nRep>nPattern ){
|
||||
nOut += nRep - nPattern;
|
||||
testcase( nOut-1==db->aLimit[SQLITE_LIMIT_LENGTH] );
|
||||
testcase( nOut-2==db->aLimit[SQLITE_LIMIT_LENGTH] );
|
||||
if( nOut-1>db->aLimit[SQLITE_LIMIT_LENGTH] ){
|
||||
sqlite3_result_error_toobig(context);
|
||||
sqlite3_free(zOut);
|
||||
return;
|
||||
}
|
||||
cntExpand++;
|
||||
if( (cntExpand&(cntExpand-1))==0 ){
|
||||
/* Grow the size of the output buffer only on substitutions
|
||||
** whose index is a power of two: 1, 2, 4, 8, 16, 32, ... */
|
||||
u8 *zOld;
|
||||
zOld = zOut;
|
||||
zOut = sqlite3_realloc64(zOut, (int)nOut + (nOut - nStr - 1));
|
||||
if( zOut==0 ){
|
||||
sqlite3_result_error_nomem(context);
|
||||
sqlite3_free(zOld);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
memcpy(&zOut[j], zRep, nRep);
|
||||
j += nRep;
|
||||
i += nPattern-1;
|
||||
}
|
||||
}
|
||||
assert( j+nStr-i+1==nOut );
|
||||
assert( j+nStr-i+1<=nOut );
|
||||
memcpy(&zOut[j], &zStr[i], nStr-i);
|
||||
j += nStr - i;
|
||||
assert( j<=nOut );
|
||||
|
||||
@@ -258,6 +258,13 @@ const Token sqlite3IntTokens[] = {
|
||||
{ "1", 1 }
|
||||
};
|
||||
|
||||
#ifdef VDBE_PROFILE
|
||||
/*
|
||||
** The following performance counter can be used in place of
|
||||
** sqlite3Hwtime() for profiling. This is a no-op on standard builds.
|
||||
*/
|
||||
sqlite3_uint64 sqlite3NProfileCnt = 0;
|
||||
#endif
|
||||
|
||||
/*
|
||||
** The value of the "pending" byte must be 0x40000000 (1 byte past the
|
||||
|
||||
+5
-1
@@ -430,7 +430,11 @@ static const sqlite3_api_routines sqlite3Apis = {
|
||||
sqlite3_prepare16_v3,
|
||||
sqlite3_bind_pointer,
|
||||
sqlite3_result_pointer,
|
||||
sqlite3_value_pointer
|
||||
sqlite3_value_pointer,
|
||||
/* Version 3.22.0 and later */
|
||||
sqlite3_vtab_nochange,
|
||||
sqlite3_value_nochange,
|
||||
sqlite3_vtab_collation
|
||||
};
|
||||
|
||||
/*
|
||||
|
||||
+11
@@ -1318,6 +1318,7 @@ const char *sqlite3ErrName(int rc){
|
||||
case SQLITE_READONLY_CANTINIT: zName = "SQLITE_READONLY_CANTINIT"; break;
|
||||
case SQLITE_READONLY_ROLLBACK: zName = "SQLITE_READONLY_ROLLBACK"; break;
|
||||
case SQLITE_READONLY_DBMOVED: zName = "SQLITE_READONLY_DBMOVED"; break;
|
||||
case SQLITE_READONLY_DIRECTORY: zName = "SQLITE_READONLY_DIRECTORY";break;
|
||||
case SQLITE_INTERRUPT: zName = "SQLITE_INTERRUPT"; break;
|
||||
case SQLITE_IOERR: zName = "SQLITE_IOERR"; break;
|
||||
case SQLITE_IOERR_READ: zName = "SQLITE_IOERR_READ"; break;
|
||||
@@ -1437,6 +1438,8 @@ const char *sqlite3ErrStr(int rc){
|
||||
/* SQLITE_FORMAT */ 0,
|
||||
/* SQLITE_RANGE */ "column index out of range",
|
||||
/* SQLITE_NOTADB */ "file is not a database",
|
||||
/* SQLITE_NOTICE */ "notification message",
|
||||
/* SQLITE_WARNING */ "warning message",
|
||||
};
|
||||
const char *zErr = "unknown error";
|
||||
switch( rc ){
|
||||
@@ -1444,6 +1447,14 @@ const char *sqlite3ErrStr(int rc){
|
||||
zErr = "abort due to ROLLBACK";
|
||||
break;
|
||||
}
|
||||
case SQLITE_ROW: {
|
||||
zErr = "another row available";
|
||||
break;
|
||||
}
|
||||
case SQLITE_DONE: {
|
||||
zErr = "no more rows available";
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
rc &= 0xff;
|
||||
if( ALWAYS(rc>=0) && rc<ArraySize(aMsg) && aMsg[rc]!=0 ){
|
||||
|
||||
+1
-1
@@ -636,7 +636,7 @@ char *sqlite3DbSpanDup(sqlite3 *db, const char *zStart, const char *zEnd){
|
||||
int n;
|
||||
while( sqlite3Isspace(zStart[0]) ) zStart++;
|
||||
n = (int)(zEnd - zStart);
|
||||
while( n>0 && sqlite3Isspace(zStart[n-1]) ) n--;
|
||||
while( ALWAYS(n>0) && sqlite3Isspace(zStart[n-1]) ) n--;
|
||||
return sqlite3DbStrNDup(db, zStart, n);
|
||||
}
|
||||
|
||||
|
||||
+23
-16
@@ -50,11 +50,12 @@ struct sqlite3_mutex {
|
||||
#endif
|
||||
};
|
||||
#if SQLITE_MUTEX_NREF
|
||||
#define SQLITE3_MUTEX_INITIALIZER {PTHREAD_MUTEX_INITIALIZER,0,0,(pthread_t)0,0}
|
||||
# define SQLITE3_MUTEX_INITIALIZER(id) \
|
||||
{PTHREAD_MUTEX_INITIALIZER,id,0,(pthread_t)0,0}
|
||||
#elif defined(SQLITE_ENABLE_API_ARMOR)
|
||||
#define SQLITE3_MUTEX_INITIALIZER { PTHREAD_MUTEX_INITIALIZER, 0 }
|
||||
# define SQLITE3_MUTEX_INITIALIZER(id) { PTHREAD_MUTEX_INITIALIZER, id }
|
||||
#else
|
||||
#define SQLITE3_MUTEX_INITIALIZER { PTHREAD_MUTEX_INITIALIZER }
|
||||
#define SQLITE3_MUTEX_INITIALIZER(id) { PTHREAD_MUTEX_INITIALIZER }
|
||||
#endif
|
||||
|
||||
/*
|
||||
@@ -151,18 +152,18 @@ static int pthreadMutexEnd(void){ return SQLITE_OK; }
|
||||
*/
|
||||
static sqlite3_mutex *pthreadMutexAlloc(int iType){
|
||||
static sqlite3_mutex staticMutexes[] = {
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER
|
||||
SQLITE3_MUTEX_INITIALIZER(2),
|
||||
SQLITE3_MUTEX_INITIALIZER(3),
|
||||
SQLITE3_MUTEX_INITIALIZER(4),
|
||||
SQLITE3_MUTEX_INITIALIZER(5),
|
||||
SQLITE3_MUTEX_INITIALIZER(6),
|
||||
SQLITE3_MUTEX_INITIALIZER(7),
|
||||
SQLITE3_MUTEX_INITIALIZER(8),
|
||||
SQLITE3_MUTEX_INITIALIZER(9),
|
||||
SQLITE3_MUTEX_INITIALIZER(10),
|
||||
SQLITE3_MUTEX_INITIALIZER(11),
|
||||
SQLITE3_MUTEX_INITIALIZER(12),
|
||||
SQLITE3_MUTEX_INITIALIZER(13)
|
||||
};
|
||||
sqlite3_mutex *p;
|
||||
switch( iType ){
|
||||
@@ -180,6 +181,9 @@ static sqlite3_mutex *pthreadMutexAlloc(int iType){
|
||||
pthread_mutexattr_settype(&recursiveAttr, PTHREAD_MUTEX_RECURSIVE);
|
||||
pthread_mutex_init(&p->mutex, &recursiveAttr);
|
||||
pthread_mutexattr_destroy(&recursiveAttr);
|
||||
#endif
|
||||
#if SQLITE_MUTEX_NREF || defined(SQLITE_ENABLE_API_ARMOR)
|
||||
p->id = SQLITE_MUTEX_RECURSIVE;
|
||||
#endif
|
||||
}
|
||||
break;
|
||||
@@ -188,6 +192,9 @@ static sqlite3_mutex *pthreadMutexAlloc(int iType){
|
||||
p = sqlite3MallocZero( sizeof(*p) );
|
||||
if( p ){
|
||||
pthread_mutex_init(&p->mutex, 0);
|
||||
#if SQLITE_MUTEX_NREF || defined(SQLITE_ENABLE_API_ARMOR)
|
||||
p->id = SQLITE_MUTEX_FAST;
|
||||
#endif
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -203,7 +210,7 @@ static sqlite3_mutex *pthreadMutexAlloc(int iType){
|
||||
}
|
||||
}
|
||||
#if SQLITE_MUTEX_NREF || defined(SQLITE_ENABLE_API_ARMOR)
|
||||
if( p ) p->id = iType;
|
||||
assert( p==0 || p->id==iType );
|
||||
#endif
|
||||
return p;
|
||||
}
|
||||
|
||||
+17
-17
@@ -40,7 +40,7 @@ struct sqlite3_mutex {
|
||||
#ifdef SQLITE_DEBUG
|
||||
volatile int nRef; /* Number of enterances */
|
||||
volatile DWORD owner; /* Thread holding this mutex */
|
||||
volatile int trace; /* True to trace changes */
|
||||
volatile LONG trace; /* True to trace changes */
|
||||
#endif
|
||||
};
|
||||
|
||||
@@ -52,10 +52,10 @@ struct sqlite3_mutex {
|
||||
#define SQLITE_W32_MUTEX_INITIALIZER { 0 }
|
||||
|
||||
#ifdef SQLITE_DEBUG
|
||||
#define SQLITE3_MUTEX_INITIALIZER { SQLITE_W32_MUTEX_INITIALIZER, 0, \
|
||||
#define SQLITE3_MUTEX_INITIALIZER(id) { SQLITE_W32_MUTEX_INITIALIZER, id, \
|
||||
0L, (DWORD)0, 0 }
|
||||
#else
|
||||
#define SQLITE3_MUTEX_INITIALIZER { SQLITE_W32_MUTEX_INITIALIZER, 0 }
|
||||
#define SQLITE3_MUTEX_INITIALIZER(id) { SQLITE_W32_MUTEX_INITIALIZER, id }
|
||||
#endif
|
||||
|
||||
#ifdef SQLITE_DEBUG
|
||||
@@ -98,18 +98,18 @@ void sqlite3MemoryBarrier(void){
|
||||
** Initialize and deinitialize the mutex subsystem.
|
||||
*/
|
||||
static sqlite3_mutex winMutex_staticMutexes[] = {
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER,
|
||||
SQLITE3_MUTEX_INITIALIZER
|
||||
SQLITE3_MUTEX_INITIALIZER(2),
|
||||
SQLITE3_MUTEX_INITIALIZER(3),
|
||||
SQLITE3_MUTEX_INITIALIZER(4),
|
||||
SQLITE3_MUTEX_INITIALIZER(5),
|
||||
SQLITE3_MUTEX_INITIALIZER(6),
|
||||
SQLITE3_MUTEX_INITIALIZER(7),
|
||||
SQLITE3_MUTEX_INITIALIZER(8),
|
||||
SQLITE3_MUTEX_INITIALIZER(9),
|
||||
SQLITE3_MUTEX_INITIALIZER(10),
|
||||
SQLITE3_MUTEX_INITIALIZER(11),
|
||||
SQLITE3_MUTEX_INITIALIZER(12),
|
||||
SQLITE3_MUTEX_INITIALIZER(13)
|
||||
};
|
||||
|
||||
static int winMutex_isInit = 0;
|
||||
@@ -239,15 +239,15 @@ static sqlite3_mutex *winMutexAlloc(int iType){
|
||||
}
|
||||
#endif
|
||||
p = &winMutex_staticMutexes[iType-2];
|
||||
p->id = iType;
|
||||
#ifdef SQLITE_DEBUG
|
||||
#ifdef SQLITE_WIN32_MUTEX_TRACE_STATIC
|
||||
p->trace = 1;
|
||||
InterlockedCompareExchange(&p->trace, 1, 0);
|
||||
#endif
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
}
|
||||
assert( p==0 || p->id==iType );
|
||||
return p;
|
||||
}
|
||||
|
||||
|
||||
+27
-19
@@ -468,7 +468,11 @@ static struct unix_syscall {
|
||||
#endif
|
||||
#define osFchown ((int(*)(int,uid_t,gid_t))aSyscall[20].pCurrent)
|
||||
|
||||
#if defined(HAVE_FCHOWN)
|
||||
{ "geteuid", (sqlite3_syscall_ptr)geteuid, 0 },
|
||||
#else
|
||||
{ "geteuid", (sqlite3_syscall_ptr)0, 0 },
|
||||
#endif
|
||||
#define osGeteuid ((uid_t(*)(void))aSyscall[21].pCurrent)
|
||||
|
||||
#if !defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0
|
||||
@@ -696,15 +700,16 @@ static int robust_open(const char *z, int f, mode_t m){
|
||||
** assert( unixMutexHeld() );
|
||||
** unixEnterLeave()
|
||||
*/
|
||||
static sqlite3_mutex *unixBigLock = 0;
|
||||
static void unixEnterMutex(void){
|
||||
sqlite3_mutex_enter(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1));
|
||||
sqlite3_mutex_enter(unixBigLock);
|
||||
}
|
||||
static void unixLeaveMutex(void){
|
||||
sqlite3_mutex_leave(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1));
|
||||
sqlite3_mutex_leave(unixBigLock);
|
||||
}
|
||||
#ifdef SQLITE_DEBUG
|
||||
static int unixMutexHeld(void) {
|
||||
return sqlite3_mutex_held(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1));
|
||||
return sqlite3_mutex_held(unixBigLock);
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -3950,7 +3955,7 @@ static void setDeviceCharacteristics(unixFile *pFile){
|
||||
pFile->sectorSize = SQLITE_DEFAULT_SECTOR_SIZE;
|
||||
pFile->deviceCharacteristics = 0;
|
||||
if( fstatvfs(pFile->h, &fsInfo) == -1 ) {
|
||||
return pFile->sectorSize;
|
||||
return;
|
||||
}
|
||||
|
||||
if( !strcmp(fsInfo.f_basetype, "tmp") ) {
|
||||
@@ -4175,12 +4180,10 @@ static int unixShmSystemLock(
|
||||
|
||||
if( pShmNode->h>=0 ){
|
||||
/* Initialize the locking parameters */
|
||||
memset(&f, 0, sizeof(f));
|
||||
f.l_type = lockType;
|
||||
f.l_whence = SEEK_SET;
|
||||
f.l_start = ofst;
|
||||
f.l_len = n;
|
||||
|
||||
rc = osFcntl(pShmNode->h, F_SETLK, &f);
|
||||
rc = (rc!=(-1)) ? SQLITE_OK : SQLITE_BUSY;
|
||||
}
|
||||
@@ -5846,7 +5849,6 @@ static int unixOpen(
|
||||
randomnessPid = osGetpid(0);
|
||||
sqlite3_randomness(0,0);
|
||||
}
|
||||
|
||||
memset(p, 0, sizeof(unixFile));
|
||||
|
||||
if( eType==SQLITE_OPEN_MAIN_DB ){
|
||||
@@ -5904,20 +5906,24 @@ static int unixOpen(
|
||||
fd = robust_open(zName, openFlags, openMode);
|
||||
OSTRACE(("OPENX %-3d %s 0%o\n", fd, zName, openFlags));
|
||||
assert( !isExclusive || (openFlags & O_CREAT)!=0 );
|
||||
if( fd<0 && errno!=EISDIR && isReadWrite ){
|
||||
/* Failed to open the file for read/write access. Try read-only. */
|
||||
flags &= ~(SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE);
|
||||
openFlags &= ~(O_RDWR|O_CREAT);
|
||||
flags |= SQLITE_OPEN_READONLY;
|
||||
openFlags |= O_RDONLY;
|
||||
isReadonly = 1;
|
||||
fd = robust_open(zName, openFlags, openMode);
|
||||
if( fd<0 ){
|
||||
if( isNewJrnl && errno==EACCES && osAccess(zName, F_OK) ){
|
||||
/* If unable to create a journal because the directory is not
|
||||
** writable, change the error code to indicate that. */
|
||||
rc = SQLITE_READONLY_DIRECTORY;
|
||||
}else if( errno!=EISDIR && isReadWrite ){
|
||||
/* Failed to open the file for read/write access. Try read-only. */
|
||||
flags &= ~(SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE);
|
||||
openFlags &= ~(O_RDWR|O_CREAT);
|
||||
flags |= SQLITE_OPEN_READONLY;
|
||||
openFlags |= O_RDONLY;
|
||||
isReadonly = 1;
|
||||
fd = robust_open(zName, openFlags, openMode);
|
||||
}
|
||||
}
|
||||
if( fd<0 ){
|
||||
rc = unixLogError(SQLITE_CANTOPEN_BKPT, "open", zName);
|
||||
/* If unable to create a journal, change the error code to
|
||||
** indicate that the directory permissions are wrong. */
|
||||
if( isNewJrnl && osAccess(zName, F_OK) ) rc = SQLITE_READONLY_DIRECTORY;
|
||||
int rc2 = unixLogError(SQLITE_CANTOPEN_BKPT, "open", zName);
|
||||
if( rc==SQLITE_OK ) rc = rc2;
|
||||
goto open_finished;
|
||||
}
|
||||
|
||||
@@ -7717,6 +7723,7 @@ int sqlite3_os_init(void){
|
||||
for(i=0; i<(sizeof(aVfs)/sizeof(sqlite3_vfs)); i++){
|
||||
sqlite3_vfs_register(&aVfs[i], i==0);
|
||||
}
|
||||
unixBigLock = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1);
|
||||
return SQLITE_OK;
|
||||
}
|
||||
|
||||
@@ -7728,6 +7735,7 @@ int sqlite3_os_init(void){
|
||||
** This routine is a no-op for unix.
|
||||
*/
|
||||
int sqlite3_os_end(void){
|
||||
unixBigLock = 0;
|
||||
return SQLITE_OK;
|
||||
}
|
||||
|
||||
|
||||
+39
-27
@@ -3631,15 +3631,16 @@ static SYSTEM_INFO winSysInfo;
|
||||
** assert( winShmMutexHeld() );
|
||||
** winShmLeaveMutex()
|
||||
*/
|
||||
static sqlite3_mutex *winBigLock = 0;
|
||||
static void winShmEnterMutex(void){
|
||||
sqlite3_mutex_enter(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1));
|
||||
sqlite3_mutex_enter(winBigLock);
|
||||
}
|
||||
static void winShmLeaveMutex(void){
|
||||
sqlite3_mutex_leave(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1));
|
||||
sqlite3_mutex_leave(winBigLock);
|
||||
}
|
||||
#ifndef NDEBUG
|
||||
static int winShmMutexHeld(void) {
|
||||
return sqlite3_mutex_held(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1));
|
||||
return sqlite3_mutex_held(winBigLock);
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -3865,7 +3866,6 @@ static int winOpenSharedMemory(winFile *pDbFd){
|
||||
struct winShm *p; /* The connection to be opened */
|
||||
winShmNode *pShmNode = 0; /* The underlying mmapped file */
|
||||
int rc = SQLITE_OK; /* Result code */
|
||||
int rc2 = SQLITE_ERROR; /* winOpen result code */
|
||||
winShmNode *pNew; /* Newly allocated winShmNode */
|
||||
int nName; /* Size of zName in bytes */
|
||||
|
||||
@@ -3899,6 +3899,9 @@ static int winOpenSharedMemory(winFile *pDbFd){
|
||||
if( pShmNode ){
|
||||
sqlite3_free(pNew);
|
||||
}else{
|
||||
int inFlags = SQLITE_OPEN_WAL;
|
||||
int outFlags = 0;
|
||||
|
||||
pShmNode = pNew;
|
||||
pNew = 0;
|
||||
((winFile*)(&pShmNode->hFile))->h = INVALID_HANDLE_VALUE;
|
||||
@@ -3914,25 +3917,19 @@ static int winOpenSharedMemory(winFile *pDbFd){
|
||||
}
|
||||
|
||||
if( 0==sqlite3_uri_boolean(pDbFd->zPath, "readonly_shm", 0) ){
|
||||
rc2 = winOpen(pDbFd->pVfs,
|
||||
pShmNode->zFilename,
|
||||
(sqlite3_file*)&pShmNode->hFile,
|
||||
SQLITE_OPEN_WAL|SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE,
|
||||
0);
|
||||
inFlags |= SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE;
|
||||
}else{
|
||||
inFlags |= SQLITE_OPEN_READONLY;
|
||||
}
|
||||
if( rc2!=SQLITE_OK ){
|
||||
rc2 = winOpen(pDbFd->pVfs,
|
||||
pShmNode->zFilename,
|
||||
(sqlite3_file*)&pShmNode->hFile,
|
||||
SQLITE_OPEN_WAL|SQLITE_OPEN_READONLY,
|
||||
0);
|
||||
if( rc2!=SQLITE_OK ){
|
||||
rc = winLogError(rc2, osGetLastError(), "winOpenShm",
|
||||
pShmNode->zFilename);
|
||||
goto shm_open_err;
|
||||
}
|
||||
pShmNode->isReadonly = 1;
|
||||
rc = winOpen(pDbFd->pVfs, pShmNode->zFilename,
|
||||
(sqlite3_file*)&pShmNode->hFile,
|
||||
inFlags, &outFlags);
|
||||
if( rc!=SQLITE_OK ){
|
||||
rc = winLogError(rc, osGetLastError(), "winOpenShm",
|
||||
pShmNode->zFilename);
|
||||
goto shm_open_err;
|
||||
}
|
||||
if( outFlags==SQLITE_OPEN_READONLY ) pShmNode->isReadonly = 1;
|
||||
|
||||
rc = winLockSharedMemory(pShmNode);
|
||||
if( rc!=SQLITE_OK && rc!=SQLITE_READONLY_CANTINIT ) goto shm_open_err;
|
||||
@@ -5118,8 +5115,10 @@ static int winOpen(
|
||||
&extendedParameters);
|
||||
if( h!=INVALID_HANDLE_VALUE ) break;
|
||||
if( isReadWrite ){
|
||||
int isRO = 0;
|
||||
int rc2 = winAccess(pVfs, zName, SQLITE_ACCESS_READ, &isRO);
|
||||
int rc2, isRO = 0;
|
||||
sqlite3BeginBenignMalloc();
|
||||
rc2 = winAccess(pVfs, zName, SQLITE_ACCESS_READ, &isRO);
|
||||
sqlite3EndBenignMalloc();
|
||||
if( rc2==SQLITE_OK && isRO ) break;
|
||||
}
|
||||
}while( winRetryIoerr(&cnt, &lastErrno) );
|
||||
@@ -5133,8 +5132,10 @@ static int winOpen(
|
||||
NULL);
|
||||
if( h!=INVALID_HANDLE_VALUE ) break;
|
||||
if( isReadWrite ){
|
||||
int isRO = 0;
|
||||
int rc2 = winAccess(pVfs, zName, SQLITE_ACCESS_READ, &isRO);
|
||||
int rc2, isRO = 0;
|
||||
sqlite3BeginBenignMalloc();
|
||||
rc2 = winAccess(pVfs, zName, SQLITE_ACCESS_READ, &isRO);
|
||||
sqlite3EndBenignMalloc();
|
||||
if( rc2==SQLITE_OK && isRO ) break;
|
||||
}
|
||||
}while( winRetryIoerr(&cnt, &lastErrno) );
|
||||
@@ -5151,8 +5152,10 @@ static int winOpen(
|
||||
NULL);
|
||||
if( h!=INVALID_HANDLE_VALUE ) break;
|
||||
if( isReadWrite ){
|
||||
int isRO = 0;
|
||||
int rc2 = winAccess(pVfs, zName, SQLITE_ACCESS_READ, &isRO);
|
||||
int rc2, isRO = 0;
|
||||
sqlite3BeginBenignMalloc();
|
||||
rc2 = winAccess(pVfs, zName, SQLITE_ACCESS_READ, &isRO);
|
||||
sqlite3EndBenignMalloc();
|
||||
if( rc2==SQLITE_OK && isRO ) break;
|
||||
}
|
||||
}while( winRetryIoerr(&cnt, &lastErrno) );
|
||||
@@ -6060,6 +6063,10 @@ int sqlite3_os_init(void){
|
||||
sqlite3_vfs_register(&winLongPathNolockVfs, 0);
|
||||
#endif
|
||||
|
||||
#ifndef SQLITE_OMIT_WAL
|
||||
winBigLock = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1);
|
||||
#endif
|
||||
|
||||
return SQLITE_OK;
|
||||
}
|
||||
|
||||
@@ -6070,6 +6077,11 @@ int sqlite3_os_end(void){
|
||||
sleepObj = NULL;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifndef SQLITE_OMIT_WAL
|
||||
winBigLock = 0;
|
||||
#endif
|
||||
|
||||
return SQLITE_OK;
|
||||
}
|
||||
|
||||
|
||||
+40
-34
@@ -1213,7 +1213,7 @@ static int jrnlBufferSize(Pager *pPager){
|
||||
#endif
|
||||
|
||||
#ifdef SQLITE_ENABLE_BATCH_ATOMIC_WRITE
|
||||
if( dc&SQLITE_IOCAP_BATCH_ATOMIC ){
|
||||
if( pPager->dbSize>0 && (dc&SQLITE_IOCAP_BATCH_ATOMIC) ){
|
||||
return -1;
|
||||
}
|
||||
#endif
|
||||
@@ -4102,6 +4102,30 @@ static void pagerFreeMapHdrs(Pager *pPager){
|
||||
}
|
||||
}
|
||||
|
||||
/* Verify that the database file has not be deleted or renamed out from
|
||||
** under the pager. Return SQLITE_OK if the database is still where it ought
|
||||
** to be on disk. Return non-zero (SQLITE_READONLY_DBMOVED or some other error
|
||||
** code from sqlite3OsAccess()) if the database has gone missing.
|
||||
*/
|
||||
static int databaseIsUnmoved(Pager *pPager){
|
||||
int bHasMoved = 0;
|
||||
int rc;
|
||||
|
||||
if( pPager->tempFile ) return SQLITE_OK;
|
||||
if( pPager->dbSize==0 ) return SQLITE_OK;
|
||||
assert( pPager->zFilename && pPager->zFilename[0] );
|
||||
rc = sqlite3OsFileControl(pPager->fd, SQLITE_FCNTL_HAS_MOVED, &bHasMoved);
|
||||
if( rc==SQLITE_NOTFOUND ){
|
||||
/* If the HAS_MOVED file-control is unimplemented, assume that the file
|
||||
** has not been moved. That is the historical behavior of SQLite: prior to
|
||||
** version 3.8.3, it never checked */
|
||||
rc = SQLITE_OK;
|
||||
}else if( rc==SQLITE_OK && bHasMoved ){
|
||||
rc = SQLITE_READONLY_DBMOVED;
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
** Shutdown the page cache. Free all memory and close all files.
|
||||
@@ -4118,8 +4142,7 @@ static void pagerFreeMapHdrs(Pager *pPager){
|
||||
** to the caller.
|
||||
*/
|
||||
int sqlite3PagerClose(Pager *pPager, sqlite3 *db){
|
||||
u8 *pTmp = (u8 *)pPager->pTmpSpace;
|
||||
|
||||
u8 *pTmp = (u8*)pPager->pTmpSpace;
|
||||
assert( db || pagerUseWal(pPager)==0 );
|
||||
assert( assert_pager_state(pPager) );
|
||||
disable_simulated_io_errors();
|
||||
@@ -4128,11 +4151,17 @@ int sqlite3PagerClose(Pager *pPager, sqlite3 *db){
|
||||
/* pPager->errCode = 0; */
|
||||
pPager->exclusiveMode = 0;
|
||||
#ifndef SQLITE_OMIT_WAL
|
||||
assert( db || pPager->pWal==0 );
|
||||
sqlite3WalClose(pPager->pWal, db, pPager->walSyncFlags, pPager->pageSize,
|
||||
(db && (db->flags & SQLITE_NoCkptOnClose) ? 0 : pTmp)
|
||||
);
|
||||
pPager->pWal = 0;
|
||||
{
|
||||
u8 *a = 0;
|
||||
assert( db || pPager->pWal==0 );
|
||||
if( db && 0==(db->flags & SQLITE_NoCkptOnClose)
|
||||
&& SQLITE_OK==databaseIsUnmoved(pPager)
|
||||
){
|
||||
a = pTmp;
|
||||
}
|
||||
sqlite3WalClose(pPager->pWal, db, pPager->walSyncFlags, pPager->pageSize,a);
|
||||
pPager->pWal = 0;
|
||||
}
|
||||
#endif
|
||||
pager_reset(pPager);
|
||||
if( MEMDB ){
|
||||
@@ -4967,30 +4996,6 @@ act_like_temp_file:
|
||||
}
|
||||
|
||||
|
||||
/* Verify that the database file has not be deleted or renamed out from
|
||||
** under the pager. Return SQLITE_OK if the database is still were it ought
|
||||
** to be on disk. Return non-zero (SQLITE_READONLY_DBMOVED or some other error
|
||||
** code from sqlite3OsAccess()) if the database has gone missing.
|
||||
*/
|
||||
static int databaseIsUnmoved(Pager *pPager){
|
||||
int bHasMoved = 0;
|
||||
int rc;
|
||||
|
||||
if( pPager->tempFile ) return SQLITE_OK;
|
||||
if( pPager->dbSize==0 ) return SQLITE_OK;
|
||||
assert( pPager->zFilename && pPager->zFilename[0] );
|
||||
rc = sqlite3OsFileControl(pPager->fd, SQLITE_FCNTL_HAS_MOVED, &bHasMoved);
|
||||
if( rc==SQLITE_NOTFOUND ){
|
||||
/* If the HAS_MOVED file-control is unimplemented, assume that the file
|
||||
** has not been moved. That is the historical behavior of SQLite: prior to
|
||||
** version 3.8.3, it never checked */
|
||||
rc = SQLITE_OK;
|
||||
}else if( rc==SQLITE_OK && bHasMoved ){
|
||||
rc = SQLITE_READONLY_DBMOVED;
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
** This function is called after transitioning from PAGER_UNLOCK to
|
||||
@@ -6499,8 +6504,9 @@ int sqlite3PagerCommitPhaseOne(
|
||||
if( bBatch ){
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = sqlite3OsFileControl(fd, SQLITE_FCNTL_COMMIT_ATOMIC_WRITE, 0);
|
||||
}else{
|
||||
sqlite3OsFileControl(fd, SQLITE_FCNTL_ROLLBACK_ATOMIC_WRITE, 0);
|
||||
}
|
||||
if( rc!=SQLITE_OK ){
|
||||
sqlite3OsFileControlHint(fd, SQLITE_FCNTL_ROLLBACK_ATOMIC_WRITE, 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+5
-2
@@ -31,8 +31,11 @@
|
||||
//
|
||||
%syntax_error {
|
||||
UNUSED_PARAMETER(yymajor); /* Silence some compiler warnings */
|
||||
assert( TOKEN.z[0] ); /* The tokenizer always gives us a token */
|
||||
sqlite3ErrorMsg(pParse, "near \"%T\": syntax error", &TOKEN);
|
||||
if( TOKEN.z[0] ){
|
||||
sqlite3ErrorMsg(pParse, "near \"%T\": syntax error", &TOKEN);
|
||||
}else{
|
||||
sqlite3ErrorMsg(pParse, "incomplete input");
|
||||
}
|
||||
}
|
||||
%stack_overflow {
|
||||
sqlite3ErrorMsg(pParse, "parser stack overflow");
|
||||
|
||||
+86
-15
@@ -206,6 +206,11 @@ void sqlite3VXPrintf(
|
||||
PrintfArguments *pArgList = 0; /* Arguments for SQLITE_PRINTF_SQLFUNC */
|
||||
char buf[etBUFSIZE]; /* Conversion buffer */
|
||||
|
||||
/* pAccum never starts out with an empty buffer that was obtained from
|
||||
** malloc(). This precondition is required by the mprintf("%z...")
|
||||
** optimization. */
|
||||
assert( pAccum->nChar>0 || (pAccum->printfFlags&SQLITE_PRINTF_MALLOCED)==0 );
|
||||
|
||||
bufpt = 0;
|
||||
if( (pAccum->printfFlags & SQLITE_PRINTF_SQLFUNC)!=0 ){
|
||||
pArgList = va_arg(ap, PrintfArguments*);
|
||||
@@ -624,9 +629,38 @@ void sqlite3VXPrintf(
|
||||
case etCHARX:
|
||||
if( bArgList ){
|
||||
bufpt = getTextArg(pArgList);
|
||||
c = bufpt ? bufpt[0] : 0;
|
||||
length = 1;
|
||||
if( bufpt ){
|
||||
buf[0] = c = *(bufpt++);
|
||||
if( (c&0xc0)==0xc0 ){
|
||||
while( length<4 && (bufpt[0]&0xc0)==0x80 ){
|
||||
buf[length++] = *(bufpt++);
|
||||
}
|
||||
}
|
||||
}else{
|
||||
buf[0] = 0;
|
||||
}
|
||||
}else{
|
||||
c = va_arg(ap,int);
|
||||
unsigned int ch = va_arg(ap,unsigned int);
|
||||
if( ch<0x00080 ){
|
||||
buf[0] = ch & 0xff;
|
||||
length = 1;
|
||||
}else if( ch<0x00800 ){
|
||||
buf[0] = 0xc0 + (u8)((ch>>6)&0x1f);
|
||||
buf[1] = 0x80 + (u8)(ch & 0x3f);
|
||||
length = 2;
|
||||
}else if( ch<0x10000 ){
|
||||
buf[0] = 0xe0 + (u8)((ch>>12)&0x0f);
|
||||
buf[1] = 0x80 + (u8)((ch>>6) & 0x3f);
|
||||
buf[2] = 0x80 + (u8)(ch & 0x3f);
|
||||
length = 3;
|
||||
}else{
|
||||
buf[0] = 0xf0 + (u8)((ch>>18) & 0x07);
|
||||
buf[1] = 0x80 + (u8)((ch>>12) & 0x3f);
|
||||
buf[2] = 0x80 + (u8)((ch>>6) & 0x3f);
|
||||
buf[3] = 0x80 + (u8)(ch & 0x3f);
|
||||
length = 4;
|
||||
}
|
||||
}
|
||||
if( precision>1 ){
|
||||
width -= precision-1;
|
||||
@@ -634,12 +668,13 @@ void sqlite3VXPrintf(
|
||||
sqlite3AppendChar(pAccum, width-1, ' ');
|
||||
width = 0;
|
||||
}
|
||||
sqlite3AppendChar(pAccum, precision-1, c);
|
||||
while( precision-- > 1 ){
|
||||
sqlite3StrAccumAppend(pAccum, buf, length);
|
||||
}
|
||||
}
|
||||
length = 1;
|
||||
buf[0] = c;
|
||||
bufpt = buf;
|
||||
break;
|
||||
flag_altform2 = 1;
|
||||
goto adjust_width_for_utf8;
|
||||
case etSTRING:
|
||||
case etDYNSTRING:
|
||||
if( bArgList ){
|
||||
@@ -651,17 +686,45 @@ void sqlite3VXPrintf(
|
||||
if( bufpt==0 ){
|
||||
bufpt = "";
|
||||
}else if( xtype==etDYNSTRING ){
|
||||
if( pAccum->nChar==0 && pAccum->mxAlloc && width==0 && precision<0 ){
|
||||
/* Special optimization for sqlite3_mprintf("%z..."):
|
||||
** Extend an existing memory allocation rather than creating
|
||||
** a new one. */
|
||||
assert( (pAccum->printfFlags&SQLITE_PRINTF_MALLOCED)==0 );
|
||||
pAccum->zText = bufpt;
|
||||
pAccum->nAlloc = sqlite3DbMallocSize(pAccum->db, bufpt);
|
||||
pAccum->nChar = 0x7fffffff & (int)strlen(bufpt);
|
||||
pAccum->printfFlags |= SQLITE_PRINTF_MALLOCED;
|
||||
length = 0;
|
||||
break;
|
||||
}
|
||||
zExtra = bufpt;
|
||||
}
|
||||
if( precision>=0 ){
|
||||
for(length=0; length<precision && bufpt[length]; length++){}
|
||||
if( flag_altform2 ){
|
||||
/* Set length to the number of bytes needed in order to display
|
||||
** precision characters */
|
||||
unsigned char *z = (unsigned char*)bufpt;
|
||||
while( precision-- > 0 && z[0] ){
|
||||
SQLITE_SKIP_UTF8(z);
|
||||
}
|
||||
length = (int)(z - (unsigned char*)bufpt);
|
||||
}else{
|
||||
for(length=0; length<precision && bufpt[length]; length++){}
|
||||
}
|
||||
}else{
|
||||
length = 0x7fffffff & (int)strlen(bufpt);
|
||||
}
|
||||
adjust_width_for_utf8:
|
||||
if( flag_altform2 && width>0 ){
|
||||
/* Adjust width to account for extra bytes in UTF-8 characters */
|
||||
int ii = length - 1;
|
||||
while( ii>=0 ) if( (bufpt[ii--] & 0xc0)==0x80 ) width++;
|
||||
}
|
||||
break;
|
||||
case etSQLESCAPE: /* Escape ' characters */
|
||||
case etSQLESCAPE2: /* Escape ' and enclose in '...' */
|
||||
case etSQLESCAPE3: { /* Escape " characters */
|
||||
case etSQLESCAPE: /* %q: Escape ' characters */
|
||||
case etSQLESCAPE2: /* %Q: Escape ' and enclose in '...' */
|
||||
case etSQLESCAPE3: { /* %w: Escape " characters */
|
||||
int i, j, k, n, isnull;
|
||||
int needQuote;
|
||||
char ch;
|
||||
@@ -675,9 +738,17 @@ void sqlite3VXPrintf(
|
||||
}
|
||||
isnull = escarg==0;
|
||||
if( isnull ) escarg = (xtype==etSQLESCAPE2 ? "NULL" : "(NULL)");
|
||||
/* For %q, %Q, and %w, the precision is the number of byte (or
|
||||
** characters if the ! flags is present) to use from the input.
|
||||
** Because of the extra quoting characters inserted, the number
|
||||
** of output characters may be larger than the precision.
|
||||
*/
|
||||
k = precision;
|
||||
for(i=n=0; k!=0 && (ch=escarg[i])!=0; i++, k--){
|
||||
if( ch==q ) n++;
|
||||
if( flag_altform2 && (ch&0xc0)==0xc0 ){
|
||||
while( (escarg[i+1]&0xc0)==0x80 ){ i++; }
|
||||
}
|
||||
}
|
||||
needQuote = !isnull && xtype==etSQLESCAPE2;
|
||||
n += i + 3;
|
||||
@@ -700,10 +771,7 @@ void sqlite3VXPrintf(
|
||||
if( needQuote ) bufpt[j++] = q;
|
||||
bufpt[j] = 0;
|
||||
length = j;
|
||||
/* The precision in %q and %Q means how many input characters to
|
||||
** consume, not the length of the output...
|
||||
** if( precision>=0 && precision<length ) length = precision; */
|
||||
break;
|
||||
goto adjust_width_for_utf8;
|
||||
}
|
||||
case etTOKEN: {
|
||||
Token *pToken;
|
||||
@@ -742,7 +810,10 @@ void sqlite3VXPrintf(
|
||||
/*
|
||||
** The text of the conversion is pointed to by "bufpt" and is
|
||||
** "length" characters long. The field width is "width". Do
|
||||
** the output.
|
||||
** the output. Both length and width are in bytes, not characters,
|
||||
** at this point. If the "!" flag was present on string conversions
|
||||
** indicating that width and precision should be expressed in characters,
|
||||
** then the values have been translated prior to reaching this point.
|
||||
*/
|
||||
width -= length;
|
||||
if( width>0 ){
|
||||
|
||||
+13
-5
@@ -1266,12 +1266,15 @@ static void generateSortTail(
|
||||
iSortTab = iTab;
|
||||
bSeq = 1;
|
||||
}
|
||||
for(i=0, iCol=nKey+bSeq; i<nSortData; i++){
|
||||
for(i=0, iCol=nKey+bSeq-1; i<nSortData; i++){
|
||||
if( aOutEx[i].u.x.iOrderByCol==0 ) iCol++;
|
||||
}
|
||||
for(i=nSortData-1; i>=0; i--){
|
||||
int iRead;
|
||||
if( aOutEx[i].u.x.iOrderByCol ){
|
||||
iRead = aOutEx[i].u.x.iOrderByCol-1;
|
||||
}else{
|
||||
iRead = iCol++;
|
||||
iRead = iCol--;
|
||||
}
|
||||
sqlite3VdbeAddOp3(v, OP_Column, iSortTab, iRead, regRow+i);
|
||||
VdbeComment((v, "%s", aOutEx[i].zName ? aOutEx[i].zName : aOutEx[i].zSpan));
|
||||
@@ -2184,9 +2187,14 @@ static int multiSelectOrderBy(
|
||||
** on a VALUES clause.
|
||||
**
|
||||
** Because the Select object originates from a VALUES clause:
|
||||
** (1) It has no LIMIT or OFFSET
|
||||
** (1) There is no LIMIT or OFFSET or else there is a LIMIT of exactly 1
|
||||
** (2) All terms are UNION ALL
|
||||
** (3) There is no ORDER BY clause
|
||||
**
|
||||
** The "LIMIT of exactly 1" case of condition (1) comes about when a VALUES
|
||||
** clause occurs within scalar expression (ex: "SELECT (VALUES(1),(2),(3))").
|
||||
** The sqlite3CodeSubselect will have added the LIMIT 1 clause in tht case.
|
||||
** Since the limit is exactly 1, we only need to evalutes the left-most VALUES.
|
||||
*/
|
||||
static int multiSelectValues(
|
||||
Parse *pParse, /* Parsing context */
|
||||
@@ -2194,13 +2202,13 @@ static int multiSelectValues(
|
||||
SelectDest *pDest /* What to do with query results */
|
||||
){
|
||||
Select *pPrior;
|
||||
Select *pRightmost = p;
|
||||
int nRow = 1;
|
||||
int rc = 0;
|
||||
assert( p->selFlags & SF_MultiValue );
|
||||
do{
|
||||
assert( p->selFlags & SF_Values );
|
||||
assert( p->op==TK_ALL || (p->op==TK_SELECT && p->pPrior==0) );
|
||||
assert( p->pLimit==0 );
|
||||
assert( p->pNext==0 || p->pEList->nExpr==p->pNext->pEList->nExpr );
|
||||
if( p->pPrior==0 ) break;
|
||||
assert( p->pPrior->pNext==p );
|
||||
@@ -2212,7 +2220,7 @@ static int multiSelectValues(
|
||||
p->pPrior = 0;
|
||||
rc = sqlite3Select(pParse, p, pDest);
|
||||
p->pPrior = pPrior;
|
||||
if( rc ) break;
|
||||
if( rc || pRightmost->pLimit ) break;
|
||||
p->nSelectRow = nRow;
|
||||
p = p->pNext;
|
||||
}
|
||||
|
||||
+667
-361
File diff suppressed because it is too large
Load Diff
+46
-75
@@ -510,7 +510,6 @@ int sqlite3_exec(
|
||||
#define SQLITE_CANTOPEN_ISDIR (SQLITE_CANTOPEN | (2<<8))
|
||||
#define SQLITE_CANTOPEN_FULLPATH (SQLITE_CANTOPEN | (3<<8))
|
||||
#define SQLITE_CANTOPEN_CONVPATH (SQLITE_CANTOPEN | (4<<8))
|
||||
#define SQLITE_CANTOPEN_DIRTYWAL (SQLITE_CANTOPEN | (5<<8))
|
||||
#define SQLITE_CORRUPT_VTAB (SQLITE_CORRUPT | (1<<8))
|
||||
#define SQLITE_READONLY_RECOVERY (SQLITE_READONLY | (1<<8))
|
||||
#define SQLITE_READONLY_CANTLOCK (SQLITE_READONLY | (2<<8))
|
||||
@@ -2497,16 +2496,16 @@ void sqlite3_free_table(char **result);
|
||||
**
|
||||
** These routines are work-alikes of the "printf()" family of functions
|
||||
** from the standard C library.
|
||||
** These routines understand most of the common K&R formatting options,
|
||||
** plus some additional non-standard formats, detailed below.
|
||||
** Note that some of the more obscure formatting options from recent
|
||||
** C-library standards are omitted from this implementation.
|
||||
** These routines understand most of the common formatting options from
|
||||
** the standard library printf()
|
||||
** plus some additional non-standard formats ([%q], [%Q], [%w], and [%z]).
|
||||
** See the [built-in printf()] documentation for details.
|
||||
**
|
||||
** ^The sqlite3_mprintf() and sqlite3_vmprintf() routines write their
|
||||
** results into memory obtained from [sqlite3_malloc()].
|
||||
** results into memory obtained from [sqlite3_malloc64()].
|
||||
** The strings returned by these two routines should be
|
||||
** released by [sqlite3_free()]. ^Both routines return a
|
||||
** NULL pointer if [sqlite3_malloc()] is unable to allocate enough
|
||||
** NULL pointer if [sqlite3_malloc64()] is unable to allocate enough
|
||||
** memory to hold the resulting string.
|
||||
**
|
||||
** ^(The sqlite3_snprintf() routine is similar to "snprintf()" from
|
||||
@@ -2530,71 +2529,7 @@ void sqlite3_free_table(char **result);
|
||||
**
|
||||
** ^The sqlite3_vsnprintf() routine is a varargs version of sqlite3_snprintf().
|
||||
**
|
||||
** These routines all implement some additional formatting
|
||||
** options that are useful for constructing SQL statements.
|
||||
** All of the usual printf() formatting options apply. In addition, there
|
||||
** is are "%q", "%Q", "%w" and "%z" options.
|
||||
**
|
||||
** ^(The %q option works like %s in that it substitutes a nul-terminated
|
||||
** string from the argument list. But %q also doubles every '\'' character.
|
||||
** %q is designed for use inside a string literal.)^ By doubling each '\''
|
||||
** character it escapes that character and allows it to be inserted into
|
||||
** the string.
|
||||
**
|
||||
** For example, assume the string variable zText contains text as follows:
|
||||
**
|
||||
** <blockquote><pre>
|
||||
** char *zText = "It's a happy day!";
|
||||
** </pre></blockquote>
|
||||
**
|
||||
** One can use this text in an SQL statement as follows:
|
||||
**
|
||||
** <blockquote><pre>
|
||||
** char *zSQL = sqlite3_mprintf("INSERT INTO table VALUES('%q')", zText);
|
||||
** sqlite3_exec(db, zSQL, 0, 0, 0);
|
||||
** sqlite3_free(zSQL);
|
||||
** </pre></blockquote>
|
||||
**
|
||||
** Because the %q format string is used, the '\'' character in zText
|
||||
** is escaped and the SQL generated is as follows:
|
||||
**
|
||||
** <blockquote><pre>
|
||||
** INSERT INTO table1 VALUES('It''s a happy day!')
|
||||
** </pre></blockquote>
|
||||
**
|
||||
** This is correct. Had we used %s instead of %q, the generated SQL
|
||||
** would have looked like this:
|
||||
**
|
||||
** <blockquote><pre>
|
||||
** INSERT INTO table1 VALUES('It's a happy day!');
|
||||
** </pre></blockquote>
|
||||
**
|
||||
** This second example is an SQL syntax error. As a general rule you should
|
||||
** always use %q instead of %s when inserting text into a string literal.
|
||||
**
|
||||
** ^(The %Q option works like %q except it also adds single quotes around
|
||||
** the outside of the total string. Additionally, if the parameter in the
|
||||
** argument list is a NULL pointer, %Q substitutes the text "NULL" (without
|
||||
** single quotes).)^ So, for example, one could say:
|
||||
**
|
||||
** <blockquote><pre>
|
||||
** char *zSQL = sqlite3_mprintf("INSERT INTO table VALUES(%Q)", zText);
|
||||
** sqlite3_exec(db, zSQL, 0, 0, 0);
|
||||
** sqlite3_free(zSQL);
|
||||
** </pre></blockquote>
|
||||
**
|
||||
** The code above will render a correct SQL statement in the zSQL
|
||||
** variable even if the zText variable is a NULL pointer.
|
||||
**
|
||||
** ^(The "%w" formatting option is like "%q" except that it expects to
|
||||
** be contained within double-quotes instead of single quotes, and it
|
||||
** escapes the double-quote character instead of the single-quote
|
||||
** character.)^ The "%w" formatting option is intended for safely inserting
|
||||
** table and column names into a constructed SQL statement.
|
||||
**
|
||||
** ^(The "%z" formatting option works like "%s" but with the
|
||||
** addition that after the string has been read and copied into
|
||||
** the result, [sqlite3_free()] is called on the input string.)^
|
||||
** See also: [built-in printf()], [printf() SQL function]
|
||||
*/
|
||||
char *sqlite3_mprintf(const char*,...);
|
||||
char *sqlite3_vmprintf(const char*, va_list);
|
||||
@@ -2952,8 +2887,8 @@ SQLITE_DEPRECATED void *sqlite3_profile(sqlite3*,
|
||||
** KEYWORDS: SQLITE_TRACE
|
||||
**
|
||||
** These constants identify classes of events that can be monitored
|
||||
** using the [sqlite3_trace_v2()] tracing logic. The third argument
|
||||
** to [sqlite3_trace_v2()] is an OR-ed combination of one or more of
|
||||
** using the [sqlite3_trace_v2()] tracing logic. The M argument
|
||||
** to [sqlite3_trace_v2(D,M,X,P)] is an OR-ed combination of one or more of
|
||||
** the following constants. ^The first argument to the trace callback
|
||||
** is one of the following constants.
|
||||
**
|
||||
@@ -3660,13 +3595,13 @@ int sqlite3_limit(sqlite3*, int id, int newVal);
|
||||
** or [GLOB] operator or if the parameter is compared to an indexed column
|
||||
** and the [SQLITE_ENABLE_STAT3] compile-time option is enabled.
|
||||
** </li>
|
||||
** </ol>
|
||||
**
|
||||
** <p>^sqlite3_prepare_v3() differs from sqlite3_prepare_v2() only in having
|
||||
** the extra prepFlags parameter, which is a bit array consisting of zero or
|
||||
** more of the [SQLITE_PREPARE_PERSISTENT|SQLITE_PREPARE_*] flags. ^The
|
||||
** sqlite3_prepare_v2() interface works exactly the same as
|
||||
** sqlite3_prepare_v3() with a zero prepFlags parameter.
|
||||
** </ol>
|
||||
*/
|
||||
int sqlite3_prepare(
|
||||
sqlite3 *db, /* Database handle */
|
||||
@@ -4799,6 +4734,9 @@ SQLITE_DEPRECATED int sqlite3_memory_alarm(void(*)(void*,sqlite3_int64,int),
|
||||
** datatype of the value
|
||||
** <tr><td><b>sqlite3_value_numeric_type </b>
|
||||
** <td>→ <td>Best numeric datatype of the value
|
||||
** <tr><td><b>sqlite3_value_nochange </b>
|
||||
** <td>→ <td>True if the column is unchanged in an UPDATE
|
||||
** against a virtual table.
|
||||
** </table></blockquote>
|
||||
**
|
||||
** <b>Details:</b>
|
||||
@@ -4847,6 +4785,19 @@ SQLITE_DEPRECATED int sqlite3_memory_alarm(void(*)(void*,sqlite3_int64,int),
|
||||
** then the conversion is performed. Otherwise no conversion occurs.
|
||||
** The [SQLITE_INTEGER | datatype] after conversion is returned.)^
|
||||
**
|
||||
** ^Within the [xUpdate] method of a [virtual table], the
|
||||
** sqlite3_value_nochange(X) interface returns true if and only if
|
||||
** the column corresponding to X is unchanged by the UPDATE operation
|
||||
** that the xUpdate method call was invoked to implement and if
|
||||
** and the prior [xColumn] method call that was invoked to extracted
|
||||
** the value for that column returned without setting a result (probably
|
||||
** because it queried [sqlite3_vtab_nochange()] and found that the column
|
||||
** was unchanging). ^Within an [xUpdate] method, any value for which
|
||||
** sqlite3_value_nochange(X) is true will in all other respects appear
|
||||
** to be a NULL value. If sqlite3_value_nochange(X) is invoked anywhere other
|
||||
** than within an [xUpdate] method call for an UPDATE statement, then
|
||||
** the return value is arbitrary and meaningless.
|
||||
**
|
||||
** Please pay particular attention to the fact that the pointer returned
|
||||
** from [sqlite3_value_blob()], [sqlite3_value_text()], or
|
||||
** [sqlite3_value_text16()] can be invalidated by a subsequent call to
|
||||
@@ -4869,6 +4820,7 @@ int sqlite3_value_bytes(sqlite3_value*);
|
||||
int sqlite3_value_bytes16(sqlite3_value*);
|
||||
int sqlite3_value_type(sqlite3_value*);
|
||||
int sqlite3_value_numeric_type(sqlite3_value*);
|
||||
int sqlite3_value_nochange(sqlite3_value*);
|
||||
|
||||
/*
|
||||
** CAPI3REF: Finding The Subtype Of SQL Values
|
||||
@@ -8297,6 +8249,25 @@ int sqlite3_vtab_config(sqlite3*, int op, ...);
|
||||
*/
|
||||
int sqlite3_vtab_on_conflict(sqlite3 *);
|
||||
|
||||
/*
|
||||
** CAPI3REF: Determine If Virtual Table Column Access Is For UPDATE
|
||||
**
|
||||
** If the sqlite3_vtab_nochange(X) routine is called within the [xColumn]
|
||||
** method of a [virtual table], then it returns true if and only if the
|
||||
** column is being fetched as part of an UPDATE operation during which the
|
||||
** column value will not change. Applications might use this to substitute
|
||||
** a lighter-weight value to return that the corresponding [xUpdate] method
|
||||
** understands as a "no-change" value.
|
||||
**
|
||||
** If the [xColumn] method calls sqlite3_vtab_nochange() and finds that
|
||||
** the column is not changed by the UPDATE statement, they the xColumn
|
||||
** method can optionally return without setting a result, without calling
|
||||
** any of the [sqlite3_result_int|sqlite3_result_xxxxx() interfaces].
|
||||
** In that case, [sqlite3_value_nochange(X)] will return true for the
|
||||
** same column in the [xUpdate] method.
|
||||
*/
|
||||
int sqlite3_vtab_nochange(sqlite3_context*);
|
||||
|
||||
/*
|
||||
** CAPI3REF: Determine The Collation For a Virtual Table Constraint
|
||||
**
|
||||
|
||||
@@ -292,6 +292,9 @@ struct sqlite3_api_routines {
|
||||
int (*bind_pointer)(sqlite3_stmt*,int,void*,const char*,void(*)(void*));
|
||||
void (*result_pointer)(sqlite3_context*,void*,const char*,void(*)(void*));
|
||||
void *(*value_pointer)(sqlite3_value*,const char*);
|
||||
int (*vtab_nochange)(sqlite3_context*);
|
||||
int (*value_nochange)(sqlite3_value*);
|
||||
const char *(*vtab_collation)(sqlite3_index_info*,int);
|
||||
};
|
||||
|
||||
/*
|
||||
@@ -558,6 +561,10 @@ typedef int (*sqlite3_loadext_entry)(
|
||||
#define sqlite3_bind_pointer sqlite3_api->bind_pointer
|
||||
#define sqlite3_result_pointer sqlite3_api->result_pointer
|
||||
#define sqlite3_value_pointer sqlite3_api->value_pointer
|
||||
/* Version 3.22.0 and later */
|
||||
#define sqlite3_vtab_nochange sqlite3_api->vtab_nochange
|
||||
#define sqlite3_value_nochange sqlite3_api->value_nochange
|
||||
#define sqlite3_vtab_collation sqlite3_api->vtab_collation
|
||||
#endif /* !defined(SQLITE_CORE) && !defined(SQLITE_OMIT_LOAD_EXTENSION) */
|
||||
|
||||
#if !defined(SQLITE_CORE) && !defined(SQLITE_OMIT_LOAD_EXTENSION)
|
||||
|
||||
@@ -1754,6 +1754,7 @@ struct Column {
|
||||
#define COLFLAG_PRIMKEY 0x0001 /* Column is part of the primary key */
|
||||
#define COLFLAG_HIDDEN 0x0002 /* A hidden column in a virtual table */
|
||||
#define COLFLAG_HASTYPE 0x0004 /* Type name follows column name */
|
||||
#define COLFLAG_UNIQUE 0x0008 /* Column def contains "UNIQUE" or "PK" */
|
||||
|
||||
/*
|
||||
** A "Collating Sequence" is defined by an instance of the following
|
||||
@@ -3117,6 +3118,7 @@ struct AuthContext {
|
||||
#define OPFLAG_PERMUTE 0x01 /* OP_Compare: use the permutation */
|
||||
#define OPFLAG_SAVEPOSITION 0x02 /* OP_Delete/Insert: save cursor pos */
|
||||
#define OPFLAG_AUXDELETE 0x04 /* OP_Delete: index in a DELETE op */
|
||||
#define OPFLAG_NOCHNG_MAGIC 0x6d /* OP_MakeRecord: serialtype 10 is ok */
|
||||
|
||||
/*
|
||||
* Each trigger present in the database schema is stored as an instance of
|
||||
@@ -4067,6 +4069,9 @@ extern FuncDefHash sqlite3BuiltinFunctions;
|
||||
extern int sqlite3PendingByte;
|
||||
#endif
|
||||
#endif
|
||||
#ifdef VDBE_PROFILE
|
||||
extern sqlite3_uint64 sqlite3NProfileCnt;
|
||||
#endif
|
||||
void sqlite3RootPageMoved(sqlite3*, int, int, int);
|
||||
void sqlite3Reindex(Parse*, Token*, Token*);
|
||||
void sqlite3AlterFunctions(void);
|
||||
|
||||
+3
-1
@@ -64,7 +64,9 @@
|
||||
# define GETPID getpid
|
||||
#elif !defined(_WIN32_WCE)
|
||||
# ifndef SQLITE_AMALGAMATION
|
||||
# define WIN32_LEAN_AND_MEAN
|
||||
# ifndef WIN32_LEAN_AND_MEAN
|
||||
# define WIN32_LEAN_AND_MEAN
|
||||
# endif
|
||||
# include <windows.h>
|
||||
# endif
|
||||
# define GETPID (int)GetCurrentProcessId
|
||||
|
||||
@@ -6992,6 +6992,7 @@ static int SQLITE_TCLAPI tclLoadStaticExtensionCmd(
|
||||
#ifdef SQLITE_HAVE_ZLIB
|
||||
extern int sqlite3_zipfile_init(sqlite3*,char**,const sqlite3_api_routines*);
|
||||
#endif
|
||||
extern int sqlite3_zonefile_init(sqlite3*,char**,const sqlite3_api_routines*);
|
||||
static const struct {
|
||||
const char *zExtName;
|
||||
int (*pInit)(sqlite3*,char**,const sqlite3_api_routines*);
|
||||
@@ -7016,6 +7017,7 @@ static int SQLITE_TCLAPI tclLoadStaticExtensionCmd(
|
||||
#ifdef SQLITE_HAVE_ZLIB
|
||||
{ "zipfile", sqlite3_zipfile_init },
|
||||
#endif
|
||||
{ "zonefile", sqlite3_zonefile_init },
|
||||
};
|
||||
sqlite3 *db;
|
||||
const char *zName;
|
||||
|
||||
@@ -501,6 +501,12 @@ Tcl_SetVar2(interp, "sqlite_options", "long_double",
|
||||
|
||||
Tcl_SetVar2(interp, "sqlite_options", "mergesort", "1", TCL_GLOBAL_ONLY);
|
||||
|
||||
#ifdef SQLITE_ENABLE_NULL_TRIM
|
||||
Tcl_SetVar2(interp, "sqlite_options", "null_trim", "1", TCL_GLOBAL_ONLY);
|
||||
#else
|
||||
Tcl_SetVar2(interp, "sqlite_options", "null_trim", "0", TCL_GLOBAL_ONLY);
|
||||
#endif
|
||||
|
||||
#ifdef SQLITE_OMIT_OR_OPTIMIZATION
|
||||
Tcl_SetVar2(interp, "sqlite_options", "or_opt", "0", TCL_GLOBAL_ONLY);
|
||||
#else
|
||||
|
||||
@@ -20,7 +20,10 @@
|
||||
** We need several data types from the Windows SDK header.
|
||||
*/
|
||||
|
||||
#ifndef WIN32_LEAN_AND_MEAN
|
||||
#define WIN32_LEAN_AND_MEAN
|
||||
#endif
|
||||
|
||||
#include "windows.h"
|
||||
|
||||
/*
|
||||
|
||||
+1
-1
@@ -526,7 +526,7 @@ int sqlite3RunParser(Parse *pParse, const char *zSql, char **pzErrMsg){
|
||||
}else{
|
||||
tokenType = TK_SEMI;
|
||||
}
|
||||
zSql -= n;
|
||||
n = 0;
|
||||
}
|
||||
if( tokenType>=TK_SPACE ){
|
||||
assert( tokenType==TK_SPACE || tokenType==TK_ILLEGAL );
|
||||
|
||||
+7
-1
@@ -807,7 +807,7 @@ static void updateVirtualTable(
|
||||
int bOnePass; /* True to use onepass strategy */
|
||||
int addr; /* Address of OP_OpenEphemeral */
|
||||
|
||||
/* Allocate nArg registers to martial the arguments to VUpdate. Then
|
||||
/* Allocate nArg registers in which to gather the arguments for VUpdate. Then
|
||||
** create and open the ephemeral table in which the records created from
|
||||
** these arguments will be temporarily stored. */
|
||||
assert( v );
|
||||
@@ -828,6 +828,7 @@ static void updateVirtualTable(
|
||||
sqlite3ExprCode(pParse, pChanges->a[aXRef[i]].pExpr, regArg+2+i);
|
||||
}else{
|
||||
sqlite3VdbeAddOp3(v, OP_VColumn, iCsr, i, regArg+2+i);
|
||||
sqlite3VdbeChangeP5(v, 1); /* Enable sqlite3_vtab_nochange() */
|
||||
}
|
||||
}
|
||||
if( HasRowid(pTab) ){
|
||||
@@ -862,6 +863,11 @@ static void updateVirtualTable(
|
||||
/* Create a record from the argument register contents and insert it into
|
||||
** the ephemeral table. */
|
||||
sqlite3VdbeAddOp3(v, OP_MakeRecord, regArg, nArg, regRec);
|
||||
#ifdef SQLITE_DEBUG
|
||||
/* Signal an assert() within OP_MakeRecord that it is allowed to
|
||||
** accept no-change records with serial_type 10 */
|
||||
sqlite3VdbeChangeP5(v, OPFLAG_NOCHNG_MAGIC);
|
||||
#endif
|
||||
sqlite3VdbeAddOp2(v, OP_NewRowid, ephemTab, regRowid);
|
||||
sqlite3VdbeAddOp3(v, OP_Insert, ephemTab, regRec, regRowid);
|
||||
}
|
||||
|
||||
+52
-21
@@ -327,6 +327,26 @@ int sqlite3_strnicmp(const char *zLeft, const char *zRight, int N){
|
||||
** This routine only works for values of E between 1 and 341.
|
||||
*/
|
||||
static LONGDOUBLE_TYPE sqlite3Pow10(int E){
|
||||
#if defined(_MSC_VER)
|
||||
static const LONGDOUBLE_TYPE x[] = {
|
||||
1.0e+001,
|
||||
1.0e+002,
|
||||
1.0e+004,
|
||||
1.0e+008,
|
||||
1.0e+016,
|
||||
1.0e+032,
|
||||
1.0e+064,
|
||||
1.0e+128,
|
||||
1.0e+256
|
||||
};
|
||||
LONGDOUBLE_TYPE r = 1.0;
|
||||
int i;
|
||||
assert( E>=0 && E<=307 );
|
||||
for(i=0; E!=0; i++, E >>=1){
|
||||
if( E & 1 ) r *= x[i];
|
||||
}
|
||||
return r;
|
||||
#else
|
||||
LONGDOUBLE_TYPE x = 10.0;
|
||||
LONGDOUBLE_TYPE r = 1.0;
|
||||
while(1){
|
||||
@@ -336,6 +356,7 @@ static LONGDOUBLE_TYPE sqlite3Pow10(int E){
|
||||
x *= x;
|
||||
}
|
||||
return r;
|
||||
#endif
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -574,7 +595,7 @@ static int compare2pow63(const char *zNum, int incr){
|
||||
** Returns:
|
||||
**
|
||||
** 0 Successful transformation. Fits in a 64-bit signed integer.
|
||||
** 1 Excess text after the integer value
|
||||
** 1 Excess non-space text after the integer value
|
||||
** 2 Integer too large for a 64-bit signed integer or is malformed
|
||||
** 3 Special case of 9223372036854775808
|
||||
**
|
||||
@@ -617,47 +638,57 @@ int sqlite3Atoi64(const char *zNum, i64 *pNum, int length, u8 enc){
|
||||
for(i=0; &zNum[i]<zEnd && (c=zNum[i])>='0' && c<='9'; i+=incr){
|
||||
u = u*10 + c - '0';
|
||||
}
|
||||
testcase( i==18*incr );
|
||||
testcase( i==19*incr );
|
||||
testcase( i==20*incr );
|
||||
if( u>LARGEST_INT64 ){
|
||||
/* This test and assignment is needed only to suppress UB warnings
|
||||
** from clang and -fsanitize=undefined. This test and assignment make
|
||||
** the code a little larger and slower, and no harm comes from omitting
|
||||
** them, but we must appaise the undefined-behavior pharisees. */
|
||||
*pNum = neg ? SMALLEST_INT64 : LARGEST_INT64;
|
||||
}else if( neg ){
|
||||
*pNum = -(i64)u;
|
||||
}else{
|
||||
*pNum = (i64)u;
|
||||
}
|
||||
testcase( i==18 );
|
||||
testcase( i==19 );
|
||||
testcase( i==20 );
|
||||
if( &zNum[i]<zEnd /* Extra bytes at the end */
|
||||
|| (i==0 && zStart==zNum) /* No digits */
|
||||
rc = 0;
|
||||
if( (i==0 && zStart==zNum) /* No digits */
|
||||
|| nonNum /* UTF16 with high-order bytes non-zero */
|
||||
){
|
||||
rc = 1;
|
||||
}else{
|
||||
rc = 0;
|
||||
}else if( &zNum[i]<zEnd ){ /* Extra bytes at the end */
|
||||
int jj = i;
|
||||
do{
|
||||
if( !sqlite3Isspace(zNum[jj]) ){
|
||||
rc = 1; /* Extra non-space text after the integer */
|
||||
break;
|
||||
}
|
||||
jj += incr;
|
||||
}while( &zNum[jj]<zEnd );
|
||||
}
|
||||
if( i>19*incr ){ /* Too many digits */
|
||||
/* zNum is empty or contains non-numeric text or is longer
|
||||
** than 19 digits (thus guaranteeing that it is too large) */
|
||||
return 2;
|
||||
}else if( i<19*incr ){
|
||||
if( i<19*incr ){
|
||||
/* Less than 19 digits, so we know that it fits in 64 bits */
|
||||
assert( u<=LARGEST_INT64 );
|
||||
return rc;
|
||||
}else{
|
||||
/* zNum is a 19-digit numbers. Compare it against 9223372036854775808. */
|
||||
c = compare2pow63(zNum, incr);
|
||||
c = i>19*incr ? 1 : compare2pow63(zNum, incr);
|
||||
if( c<0 ){
|
||||
/* zNum is less than 9223372036854775808 so it fits */
|
||||
assert( u<=LARGEST_INT64 );
|
||||
return rc;
|
||||
}else if( c>0 ){
|
||||
/* zNum is greater than 9223372036854775808 so it overflows */
|
||||
return 2;
|
||||
}else{
|
||||
/* zNum is exactly 9223372036854775808. Fits if negative. The
|
||||
** special case 2 overflow if positive */
|
||||
assert( u-1==LARGEST_INT64 );
|
||||
return neg ? rc : 3;
|
||||
*pNum = neg ? SMALLEST_INT64 : LARGEST_INT64;
|
||||
if( c>0 ){
|
||||
/* zNum is greater than 9223372036854775808 so it overflows */
|
||||
return 2;
|
||||
}else{
|
||||
/* zNum is exactly 9223372036854775808. Fits if negative. The
|
||||
** special case 2 overflow if positive */
|
||||
assert( u-1==LARGEST_INT64 );
|
||||
return neg ? rc : 3;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+2
-2
@@ -39,8 +39,8 @@ static int execSql(sqlite3 *db, char **pzErrMsg, const char *zSql){
|
||||
while( SQLITE_ROW==(rc = sqlite3_step(pStmt)) ){
|
||||
const char *zSubSql = (const char*)sqlite3_column_text(pStmt,0);
|
||||
assert( sqlite3_strnicmp(zSql,"SELECT",6)==0 );
|
||||
if( zSubSql ){
|
||||
assert( zSubSql[0]!='S' );
|
||||
assert( sqlite3_strnicmp(zSubSql,"SELECT",6)!=0 || CORRUPT_DB );
|
||||
if( zSubSql && zSubSql[0]!='S' ){
|
||||
rc = execSql(db, pzErrMsg, zSubSql);
|
||||
if( rc!=SQLITE_OK ) break;
|
||||
}
|
||||
|
||||
+90
-48
@@ -264,6 +264,11 @@ static void applyNumericAffinity(Mem *pRec, int bTryForInt){
|
||||
pRec->flags |= MEM_Real;
|
||||
if( bTryForInt ) sqlite3VdbeIntegerAffinity(pRec);
|
||||
}
|
||||
/* TEXT->NUMERIC is many->one. Hence, it is important to invalidate the
|
||||
** string representation after computing a numeric equivalent, because the
|
||||
** string representation might not be the canonical representation for the
|
||||
** numeric value. Ticket [343634942dd54ab57b7024] 2018-01-31. */
|
||||
pRec->flags &= ~MEM_Str;
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -464,7 +469,7 @@ static void memTracePrint(Mem *p){
|
||||
if( p->flags & MEM_Undefined ){
|
||||
printf(" undefined");
|
||||
}else if( p->flags & MEM_Null ){
|
||||
printf(" NULL");
|
||||
printf(p->flags & MEM_Zero ? " NULL-nochng" : " NULL");
|
||||
}else if( (p->flags & (MEM_Int|MEM_Str))==(MEM_Int|MEM_Str) ){
|
||||
printf(" si:%lld", p->u.i);
|
||||
}else if( p->flags & MEM_Int ){
|
||||
@@ -643,7 +648,7 @@ int sqlite3VdbeExec(
|
||||
|
||||
assert( pOp>=aOp && pOp<&aOp[p->nOp]);
|
||||
#ifdef VDBE_PROFILE
|
||||
start = sqlite3Hwtime();
|
||||
start = sqlite3NProfileCnt ? sqlite3NProfileCnt : sqlite3Hwtime();
|
||||
#endif
|
||||
nVmStep++;
|
||||
#ifdef SQLITE_ENABLE_STMT_SCANSTATUS
|
||||
@@ -2289,11 +2294,11 @@ case OP_IfNot: { /* jump, in1 */
|
||||
if( pIn1->flags & MEM_Null ){
|
||||
c = pOp->p3;
|
||||
}else{
|
||||
#ifdef SQLITE_OMIT_FLOATING_POINT
|
||||
c = sqlite3VdbeIntValue(pIn1)!=0;
|
||||
#else
|
||||
c = sqlite3VdbeRealValue(pIn1)!=0.0;
|
||||
#endif
|
||||
if( pIn1->flags & MEM_Int ){
|
||||
c = pIn1->u.i!=0;
|
||||
}else{
|
||||
c = sqlite3VdbeRealValue(pIn1)!=0.0;
|
||||
}
|
||||
if( pOp->opcode==OP_IfNot ) c = !c;
|
||||
}
|
||||
VdbeBranchTaken(c!=0, 2);
|
||||
@@ -2792,9 +2797,18 @@ case OP_MakeRecord: {
|
||||
pRec = pLast;
|
||||
do{
|
||||
assert( memIsValid(pRec) );
|
||||
pRec->uTemp = serial_type = sqlite3VdbeSerialType(pRec, file_format, &len);
|
||||
serial_type = sqlite3VdbeSerialType(pRec, file_format, &len);
|
||||
if( pRec->flags & MEM_Zero ){
|
||||
if( nData ){
|
||||
if( serial_type==0 ){
|
||||
/* Values with MEM_Null and MEM_Zero are created by xColumn virtual
|
||||
** table methods that never invoke sqlite3_result_xxxxx() while
|
||||
** computing an unchanging column value in an UPDATE statement.
|
||||
** Give such values a special internal-use-only serial-type of 10
|
||||
** so that they can be passed through to xUpdate and have
|
||||
** a true sqlite3_value_nochange(). */
|
||||
assert( pOp->p5==OPFLAG_NOCHNG_MAGIC || CORRUPT_DB );
|
||||
serial_type = 10;
|
||||
}else if( nData ){
|
||||
if( sqlite3VdbeMemExpandBlob(pRec) ) goto no_mem;
|
||||
}else{
|
||||
nZero += pRec->u.nZero;
|
||||
@@ -2805,6 +2819,7 @@ case OP_MakeRecord: {
|
||||
testcase( serial_type==127 );
|
||||
testcase( serial_type==128 );
|
||||
nHdr += serial_type<=127 ? 1 : sqlite3VarintLen(serial_type);
|
||||
pRec->uTemp = serial_type;
|
||||
if( pRec==pData0 ) break;
|
||||
pRec--;
|
||||
}while(1);
|
||||
@@ -4415,10 +4430,8 @@ case OP_InsertInt: {
|
||||
int seekResult; /* Result of prior seek or 0 if no USESEEKRESULT flag */
|
||||
const char *zDb; /* database name - used by the update hook */
|
||||
Table *pTab; /* Table structure - used by update and pre-update hooks */
|
||||
int op; /* Opcode for update hook: SQLITE_UPDATE or SQLITE_INSERT */
|
||||
BtreePayload x; /* Payload to be inserted */
|
||||
|
||||
op = 0;
|
||||
pData = &aMem[pOp->p2];
|
||||
assert( pOp->p1>=0 && pOp->p1<p->nCursor );
|
||||
assert( memIsValid(pData) );
|
||||
@@ -4446,19 +4459,21 @@ case OP_InsertInt: {
|
||||
zDb = db->aDb[pC->iDb].zDbSName;
|
||||
pTab = pOp->p4.pTab;
|
||||
assert( (pOp->p5 & OPFLAG_ISNOOP) || HasRowid(pTab) );
|
||||
op = ((pOp->p5 & OPFLAG_ISUPDATE) ? SQLITE_UPDATE : SQLITE_INSERT);
|
||||
}else{
|
||||
pTab = 0; /* Not needed. Silence a compiler warning. */
|
||||
pTab = 0;
|
||||
zDb = 0; /* Not needed. Silence a compiler warning. */
|
||||
}
|
||||
|
||||
#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
|
||||
/* Invoke the pre-update hook, if any */
|
||||
if( db->xPreUpdateCallback
|
||||
&& pOp->p4type==P4_TABLE
|
||||
&& !(pOp->p5 & OPFLAG_ISUPDATE)
|
||||
){
|
||||
sqlite3VdbePreUpdateHook(p, pC, SQLITE_INSERT, zDb, pTab, x.nKey, pOp->p2);
|
||||
if( pTab ){
|
||||
if( db->xPreUpdateCallback && !(pOp->p5 & OPFLAG_ISUPDATE) ){
|
||||
sqlite3VdbePreUpdateHook(p, pC, SQLITE_INSERT, zDb, pTab, x.nKey,pOp->p2);
|
||||
}
|
||||
if( db->xUpdateCallback==0 || pTab->aCol==0 ){
|
||||
/* Prevent post-update hook from running in cases when it should not */
|
||||
pTab = 0;
|
||||
}
|
||||
}
|
||||
if( pOp->p5 & OPFLAG_ISNOOP ) break;
|
||||
#endif
|
||||
@@ -4483,8 +4498,12 @@ case OP_InsertInt: {
|
||||
|
||||
/* Invoke the update-hook if required. */
|
||||
if( rc ) goto abort_due_to_error;
|
||||
if( db->xUpdateCallback && op ){
|
||||
db->xUpdateCallback(db->pUpdateArg, op, zDb, pTab->zName, x.nKey);
|
||||
if( pTab ){
|
||||
assert( db->xUpdateCallback!=0 );
|
||||
assert( pTab->aCol!=0 );
|
||||
db->xUpdateCallback(db->pUpdateArg,
|
||||
(pOp->p5 & OPFLAG_ISUPDATE) ? SQLITE_UPDATE : SQLITE_INSERT,
|
||||
zDb, pTab->zName, x.nKey);
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -6190,12 +6209,17 @@ case OP_AggStep0: {
|
||||
assert( pOp->p3>0 && pOp->p3<=(p->nMem+1 - p->nCursor) );
|
||||
assert( n==0 || (pOp->p2>0 && pOp->p2+n<=(p->nMem+1 - p->nCursor)+1) );
|
||||
assert( pOp->p3<pOp->p2 || pOp->p3>=pOp->p2+n );
|
||||
pCtx = sqlite3DbMallocRawNN(db, sizeof(*pCtx) + (n-1)*sizeof(sqlite3_value*));
|
||||
pCtx = sqlite3DbMallocRawNN(db, n*sizeof(sqlite3_value*) +
|
||||
(sizeof(pCtx[0]) + sizeof(Mem) - sizeof(sqlite3_value*)));
|
||||
if( pCtx==0 ) goto no_mem;
|
||||
pCtx->pMem = 0;
|
||||
pCtx->pOut = (Mem*)&(pCtx->argv[n]);
|
||||
sqlite3VdbeMemInit(pCtx->pOut, db, MEM_Null);
|
||||
pCtx->pFunc = pOp->p4.pFunc;
|
||||
pCtx->iOp = (int)(pOp - aOp);
|
||||
pCtx->pVdbe = p;
|
||||
pCtx->skipFlag = 0;
|
||||
pCtx->isError = 0;
|
||||
pCtx->argc = n;
|
||||
pOp->p4type = P4_FUNCCTX;
|
||||
pOp->p4.pCtx = pCtx;
|
||||
@@ -6206,7 +6230,6 @@ case OP_AggStep: {
|
||||
int i;
|
||||
sqlite3_context *pCtx;
|
||||
Mem *pMem;
|
||||
Mem t;
|
||||
|
||||
assert( pOp->p4type==P4_FUNCCTX );
|
||||
pCtx = pOp->p4.pCtx;
|
||||
@@ -6229,26 +6252,28 @@ case OP_AggStep: {
|
||||
#endif
|
||||
|
||||
pMem->n++;
|
||||
sqlite3VdbeMemInit(&t, db, MEM_Null);
|
||||
pCtx->pOut = &t;
|
||||
pCtx->fErrorOrAux = 0;
|
||||
pCtx->skipFlag = 0;
|
||||
assert( pCtx->pOut->flags==MEM_Null );
|
||||
assert( pCtx->isError==0 );
|
||||
assert( pCtx->skipFlag==0 );
|
||||
(pCtx->pFunc->xSFunc)(pCtx,pCtx->argc,pCtx->argv); /* IMP: R-24505-23230 */
|
||||
if( pCtx->fErrorOrAux ){
|
||||
if( pCtx->isError ){
|
||||
sqlite3VdbeError(p, "%s", sqlite3_value_text(&t));
|
||||
if( pCtx->isError ){
|
||||
if( pCtx->isError>0 ){
|
||||
sqlite3VdbeError(p, "%s", sqlite3_value_text(pCtx->pOut));
|
||||
rc = pCtx->isError;
|
||||
}
|
||||
sqlite3VdbeMemRelease(&t);
|
||||
if( pCtx->skipFlag ){
|
||||
assert( pOp[-1].opcode==OP_CollSeq );
|
||||
i = pOp[-1].p1;
|
||||
if( i ) sqlite3VdbeMemSetInt64(&aMem[i], 1);
|
||||
pCtx->skipFlag = 0;
|
||||
}
|
||||
sqlite3VdbeMemRelease(pCtx->pOut);
|
||||
pCtx->pOut->flags = MEM_Null;
|
||||
pCtx->isError = 0;
|
||||
if( rc ) goto abort_due_to_error;
|
||||
}else{
|
||||
assert( t.flags==MEM_Null );
|
||||
}
|
||||
if( pCtx->skipFlag ){
|
||||
assert( pOp[-1].opcode==OP_CollSeq );
|
||||
i = pOp[-1].p1;
|
||||
if( i ) sqlite3VdbeMemSetInt64(&aMem[i], 1);
|
||||
}
|
||||
assert( pCtx->pOut->flags==MEM_Null );
|
||||
assert( pCtx->skipFlag==0 );
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -6693,12 +6718,18 @@ case OP_VFilter: { /* jump */
|
||||
#endif /* SQLITE_OMIT_VIRTUALTABLE */
|
||||
|
||||
#ifndef SQLITE_OMIT_VIRTUALTABLE
|
||||
/* Opcode: VColumn P1 P2 P3 * *
|
||||
/* Opcode: VColumn P1 P2 P3 * P5
|
||||
** Synopsis: r[P3]=vcolumn(P2)
|
||||
**
|
||||
** Store the value of the P2-th column of
|
||||
** the row of the virtual-table that the
|
||||
** P1 cursor is pointing to into register P3.
|
||||
** Store in register P3 the value of the P2-th column of
|
||||
** the current row of the virtual-table of cursor P1.
|
||||
**
|
||||
** If the VColumn opcode is being used to fetch the value of
|
||||
** an unchanging column during an UPDATE operation, then the P5
|
||||
** value is 1. Otherwise, P5 is 0. The P5 value is returned
|
||||
** by sqlite3_vtab_nochange() routine can can be used
|
||||
** by virtual table implementations to return special "no-change"
|
||||
** marks which can be more efficient, depending on the virtual table.
|
||||
*/
|
||||
case OP_VColumn: {
|
||||
sqlite3_vtab *pVtab;
|
||||
@@ -6720,10 +6751,17 @@ case OP_VColumn: {
|
||||
assert( pModule->xColumn );
|
||||
memset(&sContext, 0, sizeof(sContext));
|
||||
sContext.pOut = pDest;
|
||||
MemSetTypeFlag(pDest, MEM_Null);
|
||||
if( pOp->p5 ){
|
||||
sqlite3VdbeMemSetNull(pDest);
|
||||
pDest->flags = MEM_Null|MEM_Zero;
|
||||
pDest->u.nZero = 0;
|
||||
}else{
|
||||
MemSetTypeFlag(pDest, MEM_Null);
|
||||
}
|
||||
rc = pModule->xColumn(pCur->uc.pVCur, &sContext, pOp->p2);
|
||||
sqlite3VtabImportErrmsg(p, pVtab);
|
||||
if( sContext.isError ){
|
||||
if( sContext.isError>0 ){
|
||||
sqlite3VdbeError(p, "%s", sqlite3_value_text(pDest));
|
||||
rc = sContext.isError;
|
||||
}
|
||||
sqlite3VdbeChangeEncoding(pDest, encoding);
|
||||
@@ -6988,6 +7026,7 @@ case OP_Function0: {
|
||||
pCtx->pFunc = pOp->p4.pFunc;
|
||||
pCtx->iOp = (int)(pOp - aOp);
|
||||
pCtx->pVdbe = p;
|
||||
pCtx->isError = 0;
|
||||
pCtx->argc = n;
|
||||
pOp->p4type = P4_FUNCCTX;
|
||||
pOp->p4.pCtx = pCtx;
|
||||
@@ -7022,16 +7061,17 @@ case OP_Function: {
|
||||
}
|
||||
#endif
|
||||
MemSetTypeFlag(pOut, MEM_Null);
|
||||
pCtx->fErrorOrAux = 0;
|
||||
assert( pCtx->isError==0 );
|
||||
(*pCtx->pFunc->xSFunc)(pCtx, pCtx->argc, pCtx->argv);/* IMP: R-24505-23230 */
|
||||
|
||||
/* If the function returned an error, throw an exception */
|
||||
if( pCtx->fErrorOrAux ){
|
||||
if( pCtx->isError ){
|
||||
if( pCtx->isError ){
|
||||
if( pCtx->isError>0 ){
|
||||
sqlite3VdbeError(p, "%s", sqlite3_value_text(pOut));
|
||||
rc = pCtx->isError;
|
||||
}
|
||||
sqlite3VdbeDeleteAuxData(db, &p->pAuxData, pCtx->iOp, pOp->p1);
|
||||
pCtx->isError = 0;
|
||||
if( rc ) goto abort_due_to_error;
|
||||
}
|
||||
|
||||
@@ -7073,8 +7113,10 @@ case OP_Function: {
|
||||
*/
|
||||
case OP_Trace:
|
||||
case OP_Init: { /* jump */
|
||||
char *zTrace;
|
||||
int i;
|
||||
#ifndef SQLITE_OMIT_TRACE
|
||||
char *zTrace;
|
||||
#endif
|
||||
|
||||
/* If the P4 argument is not NULL, then it must be an SQL comment string.
|
||||
** The "--" string is broken up to prevent false-positives with srcck1.c.
|
||||
@@ -7191,7 +7233,7 @@ default: { /* This is really OP_Noop and OP_Explain */
|
||||
|
||||
#ifdef VDBE_PROFILE
|
||||
{
|
||||
u64 endTime = sqlite3Hwtime();
|
||||
u64 endTime = sqlite3NProfileCnt ? sqlite3NProfileCnt : sqlite3Hwtime();
|
||||
if( endTime>start ) pOrigOp->cycles += endTime - start;
|
||||
pOrigOp->cnt++;
|
||||
}
|
||||
|
||||
@@ -127,6 +127,7 @@ typedef struct VdbeOpList VdbeOpList;
|
||||
#define P4_INT64 (-14) /* P4 is a 64-bit signed integer */
|
||||
#define P4_INTARRAY (-15) /* P4 is a vector of 32-bit integers */
|
||||
#define P4_FUNCCTX (-16) /* P4 is a pointer to an sqlite3_context object */
|
||||
#define P4_DYNBLOB (-17) /* Pointer to memory from sqliteMalloc() */
|
||||
|
||||
/* Error message codes for OP_Halt */
|
||||
#define P5_ConstraintNotNull 1
|
||||
|
||||
@@ -317,7 +317,6 @@ struct sqlite3_context {
|
||||
int iOp; /* Instruction number of OP_Function */
|
||||
int isError; /* Error code returned by the function. */
|
||||
u8 skipFlag; /* Skip accumulator loading if true */
|
||||
u8 fErrorOrAux; /* isError!=0 or pVdbe->pAuxData modified */
|
||||
u8 argc; /* Number of arguments */
|
||||
sqlite3_value *argv[1]; /* Argument set */
|
||||
};
|
||||
|
||||
+26
-10
@@ -268,6 +268,11 @@ int sqlite3_value_type(sqlite3_value* pVal){
|
||||
return aType[pVal->flags&MEM_AffMask];
|
||||
}
|
||||
|
||||
/* Return true if a parameter to xUpdate represents an unchanged column */
|
||||
int sqlite3_value_nochange(sqlite3_value *pVal){
|
||||
return (pVal->flags&(MEM_Null|MEM_Zero))==(MEM_Null|MEM_Zero);
|
||||
}
|
||||
|
||||
/* Make a copy of an sqlite3_value object
|
||||
*/
|
||||
sqlite3_value *sqlite3_value_dup(const sqlite3_value *pOrig){
|
||||
@@ -367,14 +372,12 @@ void sqlite3_result_double(sqlite3_context *pCtx, double rVal){
|
||||
void sqlite3_result_error(sqlite3_context *pCtx, const char *z, int n){
|
||||
assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) );
|
||||
pCtx->isError = SQLITE_ERROR;
|
||||
pCtx->fErrorOrAux = 1;
|
||||
sqlite3VdbeMemSetStr(pCtx->pOut, z, n, SQLITE_UTF8, SQLITE_TRANSIENT);
|
||||
}
|
||||
#ifndef SQLITE_OMIT_UTF16
|
||||
void sqlite3_result_error16(sqlite3_context *pCtx, const void *z, int n){
|
||||
assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) );
|
||||
pCtx->isError = SQLITE_ERROR;
|
||||
pCtx->fErrorOrAux = 1;
|
||||
sqlite3VdbeMemSetStr(pCtx->pOut, z, n, SQLITE_UTF16NATIVE, SQLITE_TRANSIENT);
|
||||
}
|
||||
#endif
|
||||
@@ -480,8 +483,7 @@ int sqlite3_result_zeroblob64(sqlite3_context *pCtx, u64 n){
|
||||
return SQLITE_OK;
|
||||
}
|
||||
void sqlite3_result_error_code(sqlite3_context *pCtx, int errCode){
|
||||
pCtx->isError = errCode;
|
||||
pCtx->fErrorOrAux = 1;
|
||||
pCtx->isError = errCode ? errCode : -1;
|
||||
#ifdef SQLITE_DEBUG
|
||||
if( pCtx->pVdbe ) pCtx->pVdbe->rcApp = errCode;
|
||||
#endif
|
||||
@@ -495,7 +497,6 @@ void sqlite3_result_error_code(sqlite3_context *pCtx, int errCode){
|
||||
void sqlite3_result_error_toobig(sqlite3_context *pCtx){
|
||||
assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) );
|
||||
pCtx->isError = SQLITE_TOOBIG;
|
||||
pCtx->fErrorOrAux = 1;
|
||||
sqlite3VdbeMemSetStr(pCtx->pOut, "string or blob too big", -1,
|
||||
SQLITE_UTF8, SQLITE_STATIC);
|
||||
}
|
||||
@@ -505,7 +506,6 @@ void sqlite3_result_error_nomem(sqlite3_context *pCtx){
|
||||
assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) );
|
||||
sqlite3VdbeMemSetNull(pCtx->pOut);
|
||||
pCtx->isError = SQLITE_NOMEM_BKPT;
|
||||
pCtx->fErrorOrAux = 1;
|
||||
sqlite3OomFault(pCtx->pOut->db);
|
||||
}
|
||||
|
||||
@@ -745,6 +745,25 @@ sqlite3 *sqlite3_context_db_handle(sqlite3_context *p){
|
||||
return p->pOut->db;
|
||||
}
|
||||
|
||||
/*
|
||||
** If this routine is invoked from within an xColumn method of a virtual
|
||||
** table, then it returns true if and only if the the call is during an
|
||||
** UPDATE operation and the value of the column will not be modified
|
||||
** by the UPDATE.
|
||||
**
|
||||
** If this routine is called from any context other than within the
|
||||
** xColumn method of a virtual table, then the return value is meaningless
|
||||
** and arbitrary.
|
||||
**
|
||||
** Virtual table implements might use this routine to optimize their
|
||||
** performance by substituting a NULL result, or some other light-weight
|
||||
** value, as a signal to the xUpdate routine that the column is unchanged.
|
||||
*/
|
||||
int sqlite3_vtab_nochange(sqlite3_context *p){
|
||||
assert( p );
|
||||
return sqlite3_value_nochange(p->pOut);
|
||||
}
|
||||
|
||||
/*
|
||||
** Return the current time for a statement. If the current time
|
||||
** is requested more than once within the same run of a single prepared
|
||||
@@ -893,10 +912,7 @@ void sqlite3_set_auxdata(
|
||||
pAuxData->iAuxArg = iArg;
|
||||
pAuxData->pNextAux = pVdbe->pAuxData;
|
||||
pVdbe->pAuxData = pAuxData;
|
||||
if( pCtx->fErrorOrAux==0 ){
|
||||
pCtx->isError = 0;
|
||||
pCtx->fErrorOrAux = 1;
|
||||
}
|
||||
if( pCtx->isError==0 ) pCtx->isError = -1;
|
||||
}else if( pAuxData->xDeleteAux ){
|
||||
pAuxData->xDeleteAux(pAuxData->pAux);
|
||||
}
|
||||
|
||||
+9
-1
@@ -866,6 +866,7 @@ static void freeP4(sqlite3 *db, int p4type, void *p4){
|
||||
case P4_REAL:
|
||||
case P4_INT64:
|
||||
case P4_DYNAMIC:
|
||||
case P4_DYNBLOB:
|
||||
case P4_INTARRAY: {
|
||||
sqlite3DbFree(db, p4);
|
||||
break;
|
||||
@@ -1407,6 +1408,7 @@ static char *displayP4(Op *pOp, char *zTemp, int nTemp){
|
||||
sqlite3XPrintf(&x, "program");
|
||||
break;
|
||||
}
|
||||
case P4_DYNBLOB:
|
||||
case P4_ADVANCE: {
|
||||
zTemp[0] = 0;
|
||||
break;
|
||||
@@ -3452,7 +3454,13 @@ u32 sqlite3VdbeSerialGet(
|
||||
Mem *pMem /* Memory cell to write value into */
|
||||
){
|
||||
switch( serial_type ){
|
||||
case 10: /* Reserved for future use */
|
||||
case 10: { /* Internal use only: NULL with virtual table
|
||||
** UPDATE no-change flag set */
|
||||
pMem->flags = MEM_Null|MEM_Zero;
|
||||
pMem->n = 0;
|
||||
pMem->u.nZero = 0;
|
||||
break;
|
||||
}
|
||||
case 11: /* Reserved for future use */
|
||||
case 0: { /* Null */
|
||||
/* EVIDENCE-OF: R-24078-09375 Value is a NULL. */
|
||||
|
||||
+61
-2
@@ -43,7 +43,7 @@ int sqlite3VdbeCheckMemInvariants(Mem *p){
|
||||
if( p->flags & MEM_Null ){
|
||||
/* Cannot be both MEM_Null and some other type */
|
||||
assert( (p->flags & (MEM_Int|MEM_Real|MEM_Str|MEM_Blob
|
||||
|MEM_RowSet|MEM_Frame|MEM_Agg|MEM_Zero))==0 );
|
||||
|MEM_RowSet|MEM_Frame|MEM_Agg))==0 );
|
||||
|
||||
/* If MEM_Null is set, then either the value is a pure NULL (the usual
|
||||
** case) or it is a pointer set using sqlite3_bind_pointer() or
|
||||
@@ -93,6 +93,51 @@ int sqlite3VdbeCheckMemInvariants(Mem *p){
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef SQLITE_DEBUG
|
||||
/*
|
||||
** Check that string value of pMem agrees with its integer or real value.
|
||||
**
|
||||
** A single int or real value always converts to the same strings. But
|
||||
** many different strings can be converted into the same int or real.
|
||||
** If a table contains a numeric value and an index is based on the
|
||||
** corresponding string value, then it is important that the string be
|
||||
** derived from the numeric value, not the other way around, to ensure
|
||||
** that the index and table are consistent. See ticket
|
||||
** https://www.sqlite.org/src/info/343634942dd54ab (2018-01-31) for
|
||||
** an example.
|
||||
**
|
||||
** This routine looks at pMem to verify that if it has both a numeric
|
||||
** representation and a string representation then the string rep has
|
||||
** been derived from the numeric and not the other way around. It returns
|
||||
** true if everything is ok and false if there is a problem.
|
||||
**
|
||||
** This routine is for use inside of assert() statements only.
|
||||
*/
|
||||
int sqlite3VdbeMemConsistentDualRep(Mem *p){
|
||||
char zBuf[100];
|
||||
char *z;
|
||||
int i, j, incr;
|
||||
if( (p->flags & MEM_Str)==0 ) return 1;
|
||||
if( (p->flags & (MEM_Int|MEM_Real))==0 ) return 1;
|
||||
if( p->flags & MEM_Int ){
|
||||
sqlite3_snprintf(sizeof(zBuf),zBuf,"%lld",p->u.i);
|
||||
}else{
|
||||
sqlite3_snprintf(sizeof(zBuf),zBuf,"%!.15g",p->u.r);
|
||||
}
|
||||
z = p->z;
|
||||
i = j = 0;
|
||||
incr = 1;
|
||||
if( p->enc!=SQLITE_UTF8 ){
|
||||
incr = 2;
|
||||
if( p->enc==SQLITE_UTF16BE ) z++;
|
||||
}
|
||||
while( zBuf[j] ){
|
||||
if( zBuf[j++]!=z[i] ) return 0;
|
||||
i += incr;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
#endif /* SQLITE_DEBUG */
|
||||
|
||||
/*
|
||||
** If pMem is an object with a valid string representation, this routine
|
||||
@@ -582,6 +627,18 @@ int sqlite3VdbeMemRealify(Mem *pMem){
|
||||
return SQLITE_OK;
|
||||
}
|
||||
|
||||
/* Compare a floating point value to an integer. Return true if the two
|
||||
** values are the same within the precision of the floating point value.
|
||||
**
|
||||
** For some versions of GCC on 32-bit machines, if you do the more obvious
|
||||
** comparison of "r1==(double)i" you sometimes get an answer of false even
|
||||
** though the r1 and (double)i values are bit-for-bit the same.
|
||||
*/
|
||||
static int sqlite3RealSameAsInt(double r1, sqlite3_int64 i){
|
||||
double r2 = (double)i;
|
||||
return memcmp(&r1, &r2, sizeof(r1))==0;
|
||||
}
|
||||
|
||||
/*
|
||||
** Convert pMem so that it has types MEM_Real or MEM_Int or both.
|
||||
** Invalidate any prior representations.
|
||||
@@ -601,7 +658,7 @@ int sqlite3VdbeMemNumerify(Mem *pMem){
|
||||
}else{
|
||||
i64 i = pMem->u.i;
|
||||
sqlite3AtoF(pMem->z, &pMem->u.r, pMem->n, pMem->enc);
|
||||
if( rc==1 && pMem->u.r==(double)i ){
|
||||
if( rc==1 && sqlite3RealSameAsInt(pMem->u.r, i) ){
|
||||
pMem->u.i = i;
|
||||
MemSetTypeFlag(pMem, MEM_Int);
|
||||
}else{
|
||||
@@ -1084,6 +1141,7 @@ static SQLITE_NOINLINE const void *valueToText(sqlite3_value* pVal, u8 enc){
|
||||
assert(pVal->enc==(enc & ~SQLITE_UTF16_ALIGNED) || pVal->db==0
|
||||
|| pVal->db->mallocFailed );
|
||||
if( pVal->enc==(enc & ~SQLITE_UTF16_ALIGNED) ){
|
||||
assert( sqlite3VdbeMemConsistentDualRep(pVal) );
|
||||
return pVal->z;
|
||||
}else{
|
||||
return 0;
|
||||
@@ -1106,6 +1164,7 @@ const void *sqlite3ValueText(sqlite3_value* pVal, u8 enc){
|
||||
assert( (enc&3)==(enc&~SQLITE_UTF16_ALIGNED) );
|
||||
assert( (pVal->flags & MEM_RowSet)==0 );
|
||||
if( (pVal->flags&(MEM_Str|MEM_Term))==(MEM_Str|MEM_Term) && pVal->enc==enc ){
|
||||
assert( sqlite3VdbeMemConsistentDualRep(pVal) );
|
||||
return pVal->z;
|
||||
}
|
||||
if( pVal->flags&MEM_Null ){
|
||||
|
||||
@@ -554,7 +554,11 @@ struct WalIterator {
|
||||
** page and SQLITE_OK is returned. If an error (an OOM or VFS error) occurs,
|
||||
** then an SQLite error code is returned and *ppPage is set to 0.
|
||||
*/
|
||||
static int walIndexPage(Wal *pWal, int iPage, volatile u32 **ppPage){
|
||||
static SQLITE_NOINLINE int walIndexPageRealloc(
|
||||
Wal *pWal, /* The WAL context */
|
||||
int iPage, /* The page we seek */
|
||||
volatile u32 **ppPage /* Write the page pointer here */
|
||||
){
|
||||
int rc = SQLITE_OK;
|
||||
|
||||
/* Enlarge the pWal->apWiData[] array if required */
|
||||
@@ -573,21 +577,20 @@ static int walIndexPage(Wal *pWal, int iPage, volatile u32 **ppPage){
|
||||
}
|
||||
|
||||
/* Request a pointer to the required page from the VFS */
|
||||
if( pWal->apWiData[iPage]==0 ){
|
||||
if( pWal->exclusiveMode==WAL_HEAPMEMORY_MODE ){
|
||||
pWal->apWiData[iPage] = (u32 volatile *)sqlite3MallocZero(WALINDEX_PGSZ);
|
||||
if( !pWal->apWiData[iPage] ) rc = SQLITE_NOMEM_BKPT;
|
||||
}else{
|
||||
rc = sqlite3OsShmMap(pWal->pDbFd, iPage, WALINDEX_PGSZ,
|
||||
pWal->writeLock, (void volatile **)&pWal->apWiData[iPage]
|
||||
);
|
||||
assert( pWal->apWiData[iPage]!=0 || rc!=SQLITE_OK || pWal->writeLock==0 );
|
||||
testcase( pWal->apWiData[iPage]==0 && rc==SQLITE_OK );
|
||||
if( (rc&0xff)==SQLITE_READONLY ){
|
||||
pWal->readOnly |= WAL_SHM_RDONLY;
|
||||
if( rc==SQLITE_READONLY ){
|
||||
rc = SQLITE_OK;
|
||||
}
|
||||
assert( pWal->apWiData[iPage]==0 );
|
||||
if( pWal->exclusiveMode==WAL_HEAPMEMORY_MODE ){
|
||||
pWal->apWiData[iPage] = (u32 volatile *)sqlite3MallocZero(WALINDEX_PGSZ);
|
||||
if( !pWal->apWiData[iPage] ) rc = SQLITE_NOMEM_BKPT;
|
||||
}else{
|
||||
rc = sqlite3OsShmMap(pWal->pDbFd, iPage, WALINDEX_PGSZ,
|
||||
pWal->writeLock, (void volatile **)&pWal->apWiData[iPage]
|
||||
);
|
||||
assert( pWal->apWiData[iPage]!=0 || rc!=SQLITE_OK || pWal->writeLock==0 );
|
||||
testcase( pWal->apWiData[iPage]==0 && rc==SQLITE_OK );
|
||||
if( (rc&0xff)==SQLITE_READONLY ){
|
||||
pWal->readOnly |= WAL_SHM_RDONLY;
|
||||
if( rc==SQLITE_READONLY ){
|
||||
rc = SQLITE_OK;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -596,6 +599,16 @@ static int walIndexPage(Wal *pWal, int iPage, volatile u32 **ppPage){
|
||||
assert( iPage==0 || *ppPage || rc!=SQLITE_OK );
|
||||
return rc;
|
||||
}
|
||||
static int walIndexPage(
|
||||
Wal *pWal, /* The WAL context */
|
||||
int iPage, /* The page we seek */
|
||||
volatile u32 **ppPage /* Write the page pointer here */
|
||||
){
|
||||
if( pWal->nWiData<=iPage || (*ppPage = pWal->apWiData[iPage])==0 ){
|
||||
return walIndexPageRealloc(pWal, iPage, ppPage);
|
||||
}
|
||||
return SQLITE_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
** Return a pointer to the WalCkptInfo structure in the wal-index.
|
||||
@@ -2868,7 +2881,7 @@ int sqlite3WalFindFrame(
|
||||
** table after the current read-transaction had started.
|
||||
*/
|
||||
iMinHash = walFramePage(pWal->minFrame);
|
||||
for(iHash=walFramePage(iLast); iHash>=iMinHash && iRead==0; iHash--){
|
||||
for(iHash=walFramePage(iLast); iHash>=iMinHash; iHash--){
|
||||
volatile ht_slot *aHash; /* Pointer to hash table */
|
||||
volatile u32 *aPgno; /* Pointer to array of page numbers */
|
||||
u32 iZero; /* Frame number corresponding to aPgno[0] */
|
||||
@@ -2891,6 +2904,7 @@ int sqlite3WalFindFrame(
|
||||
return SQLITE_CORRUPT_BKPT;
|
||||
}
|
||||
}
|
||||
if( iRead ) break;
|
||||
}
|
||||
|
||||
#ifdef SQLITE_ENABLE_EXPENSIVE_ASSERT
|
||||
|
||||
+27
-7
@@ -2481,10 +2481,12 @@ static int whereLoopAddBtreeIndex(
|
||||
if( iCol==XN_ROWID
|
||||
|| (iCol>=0 && nInMul==0 && saved_nEq==pProbe->nKeyCol-1)
|
||||
){
|
||||
if( iCol>=0 && pProbe->uniqNotNull==0 ){
|
||||
pNew->wsFlags |= WHERE_UNQ_WANTED;
|
||||
}else{
|
||||
if( iCol==XN_ROWID || pProbe->uniqNotNull
|
||||
|| (pProbe->nKeyCol==1 && pProbe->onError && eOp==WO_EQ)
|
||||
){
|
||||
pNew->wsFlags |= WHERE_ONEROW;
|
||||
}else{
|
||||
pNew->wsFlags |= WHERE_UNQ_WANTED;
|
||||
}
|
||||
}
|
||||
}else if( eOp & WO_ISNULL ){
|
||||
@@ -4631,6 +4633,7 @@ WhereInfo *sqlite3WhereBegin(
|
||||
*/
|
||||
for(ii=0; ii<sWLB.pWC->nTerm; ii++){
|
||||
WhereTerm *pT = &sWLB.pWC->a[ii];
|
||||
if( pT->wtFlags & TERM_VIRTUAL ) continue;
|
||||
if( pT->prereqAll==0 && (nTabList==0 || exprIsDeterministic(pT->pExpr)) ){
|
||||
sqlite3ExprIfFalse(pParse, pT->pExpr, pWInfo->iBreak, SQLITE_JUMPIFNULL);
|
||||
pT->wtFlags |= TERM_CODED;
|
||||
@@ -4801,15 +4804,32 @@ WhereInfo *sqlite3WhereBegin(
|
||||
|
||||
/* If the caller is an UPDATE or DELETE statement that is requesting
|
||||
** to use a one-pass algorithm, determine if this is appropriate.
|
||||
**
|
||||
** A one-pass approach can be used if the caller has requested one
|
||||
** and either (a) the scan visits at most one row or (b) each
|
||||
** of the following are true:
|
||||
**
|
||||
** * the caller has indicated that a one-pass approach can be used
|
||||
** with multiple rows (by setting WHERE_ONEPASS_MULTIROW), and
|
||||
** * the table is not a virtual table, and
|
||||
** * either the scan does not use the OR optimization or the caller
|
||||
** is a DELETE operation (WHERE_DUPLICATES_OK is only specified
|
||||
** for DELETE).
|
||||
**
|
||||
** The last qualification is because an UPDATE statement uses
|
||||
** WhereInfo.aiCurOnePass[1] to determine whether or not it really can
|
||||
** use a one-pass approach, and this is not set accurately for scans
|
||||
** that use the OR optimization.
|
||||
*/
|
||||
assert( (wctrlFlags & WHERE_ONEPASS_DESIRED)==0 || pWInfo->nLevel==1 );
|
||||
if( (wctrlFlags & WHERE_ONEPASS_DESIRED)!=0 ){
|
||||
int wsFlags = pWInfo->a[0].pWLoop->wsFlags;
|
||||
int bOnerow = (wsFlags & WHERE_ONEROW)!=0;
|
||||
if( bOnerow
|
||||
|| ((wctrlFlags & WHERE_ONEPASS_MULTIROW)!=0
|
||||
&& 0==(wsFlags & WHERE_VIRTUALTABLE))
|
||||
){
|
||||
if( bOnerow || (
|
||||
0!=(wctrlFlags & WHERE_ONEPASS_MULTIROW)
|
||||
&& 0==(wsFlags & WHERE_VIRTUALTABLE)
|
||||
&& (0==(wsFlags & WHERE_MULTI_OR) || (wctrlFlags & WHERE_DUPLICATES_OK))
|
||||
)){
|
||||
pWInfo->eOnePass = bOnerow ? ONEPASS_SINGLE : ONEPASS_MULTI;
|
||||
if( HasRowid(pTabList->a[0].pTab) && (wsFlags & WHERE_IDX_ONLY) ){
|
||||
if( wctrlFlags & WHERE_ONEPASS_MULTIROW ){
|
||||
|
||||
+15
-1
@@ -1395,7 +1395,15 @@ Bitmask sqlite3WhereCodeOneLoopStart(
|
||||
if( sqlite3ExprIsVector(pX->pRight) ){
|
||||
r1 = rTemp = sqlite3GetTempReg(pParse);
|
||||
codeExprOrVector(pParse, pX->pRight, r1, 1);
|
||||
op = aMoveOp[(pX->op - TK_GT) | 0x0001];
|
||||
testcase( pX->op==TK_GT );
|
||||
testcase( pX->op==TK_GE );
|
||||
testcase( pX->op==TK_LT );
|
||||
testcase( pX->op==TK_LE );
|
||||
op = aMoveOp[((pX->op - TK_GT - 1) & 0x3) | 0x1];
|
||||
assert( pX->op!=TK_GT || op==OP_SeekGE );
|
||||
assert( pX->op!=TK_GE || op==OP_SeekGE );
|
||||
assert( pX->op!=TK_LT || op==OP_SeekLE );
|
||||
assert( pX->op!=TK_LE || op==OP_SeekLE );
|
||||
}else{
|
||||
r1 = sqlite3ExprCodeTemp(pParse, pX->pRight, &rTemp);
|
||||
disableTerm(pLevel, pStart);
|
||||
@@ -2170,6 +2178,12 @@ Bitmask sqlite3WhereCodeOneLoopStart(
|
||||
WO_EQ|WO_IN|WO_IS, 0);
|
||||
if( pAlt==0 ) continue;
|
||||
if( pAlt->wtFlags & (TERM_CODED) ) continue;
|
||||
if( (pAlt->eOperator & WO_IN)
|
||||
&& (pAlt->pExpr->flags & EP_xIsSelect)
|
||||
&& (pAlt->pExpr->x.pSelect->pEList->nExpr>1)
|
||||
){
|
||||
continue;
|
||||
}
|
||||
testcase( pAlt->eOperator & WO_EQ );
|
||||
testcase( pAlt->eOperator & WO_IS );
|
||||
testcase( pAlt->eOperator & WO_IN );
|
||||
|
||||
+4
-1
@@ -876,6 +876,9 @@ static Bitmask exprSelectUsage(WhereMaskSet *pMaskSet, Select *pS){
|
||||
for(i=0; i<pSrc->nSrc; i++){
|
||||
mask |= exprSelectUsage(pMaskSet, pSrc->a[i].pSelect);
|
||||
mask |= sqlite3WhereExprUsage(pMaskSet, pSrc->a[i].pOn);
|
||||
if( pSrc->a[i].fg.isTabFunc ){
|
||||
mask |= sqlite3WhereExprListUsage(pMaskSet, pSrc->a[i].u1.pFuncArg);
|
||||
}
|
||||
}
|
||||
}
|
||||
pS = pS->pPrior;
|
||||
@@ -1288,7 +1291,7 @@ static void exprAnalyze(
|
||||
exprAnalyze(pSrc, pWC, idxNew);
|
||||
}
|
||||
pTerm = &pWC->a[idxTerm];
|
||||
pTerm->wtFlags = TERM_CODED|TERM_VIRTUAL; /* Disable the original */
|
||||
pTerm->wtFlags |= TERM_CODED|TERM_VIRTUAL; /* Disable the original */
|
||||
pTerm->eOperator = 0;
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -163,7 +163,7 @@ do_test capi2-3.2 {
|
||||
sqlite3_prepare $DB {select bogus from } -1 TAIL
|
||||
} msg]
|
||||
lappend rc $msg $TAIL
|
||||
} {1 {(1) near " ": syntax error} {}}
|
||||
} {1 {(1) incomplete input} {}}
|
||||
do_test capi2-3.3 {
|
||||
set rc [catch {
|
||||
sqlite3_prepare $DB {;;;;select bogus from sqlite_master} -1 TAIL
|
||||
|
||||
@@ -649,6 +649,18 @@ do_test capi3-5.33 {
|
||||
sqlite3_finalize $STMT
|
||||
} SQLITE_OK
|
||||
|
||||
# 2018-01-09: If a column is the last token if a string, the column name
|
||||
# was not being set correctly, due to changes in check-in
|
||||
# https://sqlite.org/src/info/0fdf97efe5df7455
|
||||
#
|
||||
# This problem was detected by the community during beta-testing.
|
||||
#
|
||||
do_test capi3-5.34 {
|
||||
set STMT [sqlite3_prepare $DB {SELECT :a, :b} -1 TAIL]
|
||||
sqlite3_column_count $STMT
|
||||
} 2
|
||||
check_header $STMT capi-5.35 {:a :b} {{} {}}
|
||||
sqlite3_finalize $STMT
|
||||
|
||||
set ::ENC [execsql {pragma encoding}]
|
||||
db close
|
||||
|
||||
@@ -343,4 +343,49 @@ do_test cast-4.4 {
|
||||
}
|
||||
} {0 abc 0.0 abc}
|
||||
|
||||
# Added 2018-01-26
|
||||
#
|
||||
# EVIDENCE-OF: R-48741-32454 If the prefix integer is greater than
|
||||
# +9223372036854775807 then the result of the cast is exactly
|
||||
# +9223372036854775807.
|
||||
do_execsql_test cast-5.1 {
|
||||
SELECT CAST('9223372036854775808' AS integer);
|
||||
SELECT CAST(' +000009223372036854775808' AS integer);
|
||||
SELECT CAST('12345678901234567890123' AS INTEGER);
|
||||
} {9223372036854775807 9223372036854775807 9223372036854775807}
|
||||
|
||||
# EVIDENCE-OF: R-06028-16857 Similarly, if the prefix integer is less
|
||||
# than -9223372036854775808 then the result of the cast is exactly
|
||||
# -9223372036854775808.
|
||||
do_execsql_test cast-5.2 {
|
||||
SELECT CAST('-9223372036854775808' AS integer);
|
||||
SELECT CAST('-9223372036854775809' AS integer);
|
||||
SELECT CAST('-12345678901234567890123' AS INTEGER);
|
||||
} {-9223372036854775808 -9223372036854775808 -9223372036854775808}
|
||||
|
||||
# EVIDENCE-OF: R-33990-33527 When casting to INTEGER, if the text looks
|
||||
# like a floating point value with an exponent, the exponent will be
|
||||
# ignored because it is no part of the integer prefix.
|
||||
# EVIDENCE-OF: R-24225-46995 For example, "(CAST '123e+5' AS INTEGER)"
|
||||
# results in 123, not in 12300000.
|
||||
do_execsql_test case-5.3 {
|
||||
SELECT CAST('123e+5' AS INTEGER);
|
||||
SELECT CAST('123e+5' AS NUMERIC);
|
||||
} {123 12300000.0}
|
||||
|
||||
|
||||
# The following does not have anything to do with the CAST operator,
|
||||
# but it does deal with affinity transformations.
|
||||
#
|
||||
do_execsql_test case-6.1 {
|
||||
DROP TABLE IF EXISTS t1;
|
||||
CREATE TABLE t1(a NUMERIC);
|
||||
INSERT INTO t1 VALUES
|
||||
('9000000000000000001'),
|
||||
('9000000000000000001 '),
|
||||
(' 9000000000000000001'),
|
||||
(' 9000000000000000001 ');
|
||||
SELECT * FROM t1;
|
||||
} {9000000000000000001 9000000000000000001 9000000000000000001 9000000000000000001}
|
||||
|
||||
finish_test
|
||||
|
||||
+6
-4
@@ -393,10 +393,12 @@ do_execsql_test colname-9.300 {
|
||||
do_test colname-9.310 {
|
||||
execsql2 {SELECT BBb FROM (SELECT aaa AS Bbb FROM t1)}
|
||||
} {Bbb 123}
|
||||
do_execsql_test colname-9.320 {
|
||||
CREATE TABLE t2 AS SELECT BBb FROM (SELECT aaa AS Bbb FROM t1);
|
||||
SELECT name FROM pragma_table_info('t2');
|
||||
} {Bbb}
|
||||
ifcapable vtab {
|
||||
do_execsql_test colname-9.320 {
|
||||
CREATE TABLE t2 AS SELECT BBb FROM (SELECT aaa AS Bbb FROM t1);
|
||||
SELECT name FROM pragma_table_info('t2');
|
||||
} {Bbb}
|
||||
}
|
||||
|
||||
# Issue detected by OSSFuzz on 2017-12-24 (Christmas Eve)
|
||||
# caused by check-in https://sqlite.org/src/info/6b2ff26c25
|
||||
|
||||
+8
-2
@@ -142,6 +142,7 @@ proc write_file {zFile zData} {
|
||||
# b) Less than 512, or
|
||||
# c) Greater than SQLITE_MAX_PAGE_SIZE
|
||||
#
|
||||
if {[atomic_batch_write test.db]==0} {
|
||||
do_test crash8-3.1 {
|
||||
list [file exists test.db-joural] [file exists test.db]
|
||||
} {0 1}
|
||||
@@ -228,6 +229,7 @@ do_test crash8-3.11 {
|
||||
PRAGMA integrity_check
|
||||
}
|
||||
} {6 ok}
|
||||
}
|
||||
|
||||
|
||||
# If a connection running in persistent-journal mode is part of a
|
||||
@@ -266,8 +268,12 @@ ifcapable pragma {
|
||||
UPDATE aux.ab SET b = randstr(1000,1000) WHERE a>=1;
|
||||
UPDATE ab SET b = randstr(1000,1000) WHERE a>=1;
|
||||
}
|
||||
list [file exists test.db-journal] [file exists test2.db-journal]
|
||||
} {1 1}
|
||||
} {persist persist}
|
||||
if {[atomic_batch_write test.db]==0} {
|
||||
do_test crash8.4.1.1 {
|
||||
list [file exists test.db-journal] [file exists test2.db-journal]
|
||||
} {1 1}
|
||||
}
|
||||
|
||||
do_test crash8-4.2 {
|
||||
execsql {
|
||||
|
||||
@@ -17,6 +17,11 @@ set testdir [file dirname $argv0]
|
||||
source $testdir/tester.tcl
|
||||
set testprefix delete_db
|
||||
|
||||
if {[atomic_batch_write test.db]} {
|
||||
finish_test
|
||||
return
|
||||
}
|
||||
|
||||
proc delete_all {} {
|
||||
foreach f [glob -nocomplain test2*] { file delete $f }
|
||||
foreach f [glob -nocomplain test3*] { file delete $f }
|
||||
|
||||
+6
-1
@@ -252,7 +252,9 @@ db2 close
|
||||
# opens the journal file for exclusive access, preventing its contents
|
||||
# from being inspected externally.
|
||||
#
|
||||
if {$tcl_platform(platform) != "windows"} {
|
||||
if {$tcl_platform(platform) != "windows"
|
||||
&& [atomic_batch_write test.db]==0
|
||||
} {
|
||||
|
||||
# Return a list of two booleans (either 0 or 1). The first is true
|
||||
# if the named file exists. The second is true only if the file
|
||||
@@ -391,6 +393,7 @@ do_test exclusive-4.5 {
|
||||
# Tests exclusive-5.X - test that statement journals are truncated
|
||||
# instead of deleted when in exclusive access mode.
|
||||
#
|
||||
if {[atomic_batch_write test.db]==0} {
|
||||
|
||||
# Close and reopen the database so that the temp database is no
|
||||
# longer active.
|
||||
@@ -508,4 +511,6 @@ do_execsql_test exclusive-6.5 {
|
||||
SELECT * FROM sqlite_master;
|
||||
} {exclusive}
|
||||
|
||||
} ;# atomic_batch_write==0
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -61,6 +61,7 @@ do_test fallocate-1.7 {
|
||||
execsql { BEGIN; INSERT INTO t1 VALUES(1, 2); }
|
||||
if {[permutation] != "inmemory_journal"
|
||||
&& [permutation] != "atomic-batch-write"
|
||||
&& [atomic_batch_write test.db]==0
|
||||
} {
|
||||
hexio_get_int [hexio_read test.db-journal 16 4]
|
||||
} else {
|
||||
|
||||
+11
-9
@@ -174,16 +174,18 @@ do_catchsql_test fkey1-5.2 {
|
||||
# Make sure sqlite3_trace() output works with triggers used to implement
|
||||
# FK constraints
|
||||
#
|
||||
proc sqltrace {txt} {
|
||||
global traceoutput
|
||||
lappend traceoutput $txt
|
||||
ifcapable trace {
|
||||
proc sqltrace {txt} {
|
||||
global traceoutput
|
||||
lappend traceoutput $txt
|
||||
}
|
||||
do_test fkey1-5.2.1 {
|
||||
unset -nocomplain traceoutput
|
||||
db trace sqltrace
|
||||
catch {db eval {INSERT OR REPLACE INTO t11 VALUES(2,3);}}
|
||||
set traceoutput
|
||||
} {{INSERT OR REPLACE INTO t11 VALUES(2,3);} {INSERT OR REPLACE INTO t11 VALUES(2,3);} {INSERT OR REPLACE INTO t11 VALUES(2,3);}}
|
||||
}
|
||||
do_test fkey1-5.2.1 {
|
||||
unset -nocomplain traceoutput
|
||||
db trace sqltrace
|
||||
catch {db eval {INSERT OR REPLACE INTO t11 VALUES(2,3);}}
|
||||
set traceoutput
|
||||
} {{INSERT OR REPLACE INTO t11 VALUES(2,3);} {INSERT OR REPLACE INTO t11 VALUES(2,3);} {INSERT OR REPLACE INTO t11 VALUES(2,3);}}
|
||||
|
||||
# A similar test to the above.
|
||||
do_execsql_test fkey1-5.3 {
|
||||
|
||||
@@ -250,4 +250,5 @@ do_execsql_test 9.2 {
|
||||
CREATE VIRTUAL TABLE t10 USING fts3(<, b, c);
|
||||
}
|
||||
|
||||
expand_all_sql db
|
||||
finish_test
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user