-C First\sattempt\sat\sadding\sa\sbuilt-in\sprepared\sstatement\scache.\s\sThis\sis\nmostly\sworking,\sbut\sstill\shas\sa\sfew\sobscure\sfaults.
-D 2022-08-24T17:55:27.625
+C Change\ssqlite3_prepare_v3()\sto\srequire\sSQLITE_PREPARE_CACHE\sin\sorder\sfor\sa\nstatement\sto\sbe\sa\scache\scandidate.\s\sBut\sany\sstatement\scan\spull\sfrom\sthe\scache.\nAlso\sadd\sstatement\scache\scontrol\sto\sthe\sCLI.
+D 2022-08-24T23:50:45.133
F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
F LICENSE.md df5091916dbb40e6e9686186587125e1b2ff51f022cc334e886c19a0e9982724
F src/json.c 7749b98c62f691697c7ee536b570c744c0583cab4a89200fdd0fc2aa8cc8cbd6
F src/legacy.c d7874bc885906868cd51e6c2156698f2754f02d9eee1bae2d687323c3ca8e5aa
F src/loadext.c 853385cc7a604157e137585097949252d5d0c731768e16b044608e5c95c3614b
-F src/main.c 5c82ba33d2032f099c90fbb2a7a05ed684164a0ddecb7aaeda4374d97f4055b5
+F src/main.c a9a6dbe70301a39a1d63b6460e329c4f9548a42b7a334d167fb077acdee9d275
F src/malloc.c b7a3430cbe91d3e8e04fc10c2041b3a19794e63556ad2441a13d8dadd9b2bafc
F src/mem0.c 6a55ebe57c46ca1a7d98da93aaa07f99f1059645
F src/mem1.c c12a42539b1ba105e3707d0e628ad70e611040d8f5e38cf942cee30c867083de
F src/pcache1.c 0b4245cd4964e635f2630908c2533cd8e9da7af3ca592e23ae8730aa25ae5eb9
F src/pragma.c b57a859a366472131194a9ad35cd76d5920577226b04c884b1b9085605faa280
F src/pragma.h e690a356c18e98414d2e870ea791c1be1545a714ba623719deb63f7f226d8bb7
-F src/prepare.c 54839876dd40924279004e98ba35e38a64aed728b9be5ba8641f10a9a5203496
+F src/prepare.c b0fb76a2c82587013410f0e27fcdb2ef5624f036d00179f7fd4f28a52acc0155
F src/printf.c e99ee9741e79ae3873458146f59644276657340385ade4e76a5f5d1c25793764
F src/random.c 546d6feb15ec69c1aafe9bb351a277cbb498fd5410e646add673acb805714960
F src/resolve.c efea4e5fbecfd6d0a9071b0be0d952620991673391b6ffaaf4c277b0bb674633
F src/rowset.c ba9515a922af32abe1f7d39406b9d35730ed65efab9443dc5702693b60854c92
F src/select.c ccce37e7fbe71089cf6aec91e7134c9c0c1d4840cff9f02587bbc71240d914a5
-F src/shell.c.in 269f682249c1bce2962883e5b99c8702b16a488a43b9ae186daa178713a93c5d
+F src/shell.c.in 6c18f7d3a42c590035f1c702265c73a8301fda79dda951a713bdae5ae185583b
F src/sqlite.h.in f34d1ca4091c969e1b4b4744839f415c7963618bb10b34bbe1ef6a356ace0840
F src/sqlite3.rc 5121c9e10c3964d5755191c80dd1180c122fc3a8
F src/sqlite3ext.h a988810c9b21c0dc36dc7a62735012339dc76fc7ab448fb0792721d30eacb69d
F src/vdbe.h c4c9defdf2ad9465f9c9c7f79c3b03555f47aa930ea2744f358d9b27269763c7
F src/vdbeInt.h e332f7d165b2cb984772c425c45f67f1d57e3c032d8dbf74a9ef8f1cebfa4bb2
F src/vdbeapi.c 8087dba84836f59d0d5340a6c554948cf4fef03ace62a8d7dd3c8f310107e3f4
-F src/vdbeaux.c fdbf1df03cfcf4d11c49178be30b23d2b750082edd4d7b6aa663479e7dc65f7c
+F src/vdbeaux.c 7e682b9cae69e3801d2c04fefe2c80b40e5fcca470a4e11aa53342e2218aa1ab
F src/vdbeblob.c 5e61ce31aca17db8fb60395407457a8c1c7fb471dde405e0cd675974611dcfcd
F src/vdbemem.c c3ce80af15e2ff5c2824a8db881681cbf511376f13613da020bac6d320c535b1
F src/vdbesort.c 43756031ca7430f7aec3ef904824a7883c4ede783e51f280d99b9b65c0796e35
F test/speed4.test abc0ad3399dcf9703abed2fff8705e4f8e416715
F test/speed4p.explain 6b5f104ebeb34a038b2f714150f51d01143e59aa
F test/speed4p.test 377a0c48e5a92e0b11c1c5ebb1bc9d83a7312c922bc0cb05970ef5d6a96d1f0c
-F test/speedtest1.c d37467faf7a43711b134f05e9cde7abfd1504bf8f16f6220f67d8db1bc0fc51f
+F test/speedtest1.c ace4f2f7053d01237d41ab3a9baaf785eab1f22457bdc0113a41d573a506d2c5
F test/spellfix.test 951a6405d49d1a23d6b78027d3877b4a33eeb8221dcab5704b499755bb4f552e
F test/spellfix2.test dfc8f519a3fc204cb2dfa8b4f29821ae90f6f8c3
F test/spellfix3.test 0f9efaaa502a0e0a09848028518a6fb096c8ad33
F tool/showwal.c 0253c187ae16fdae9cde89e63e1dfcd3bb35e5416d066415f99e2f8cac6ab03d
F tool/soak1.tcl 8d407956e1a45b485a8e072470a3e629a27037fe
F tool/spaceanal.tcl 1b5be34c6223cb1af06da2a10fb77863eb869b1962d055820b0a11cf2336ab45
-F tool/speed-check.sh fc224ee49062fedf3bbef87779197bb5103f6f796603e4255ea558633360e8ba
+F tool/speed-check.sh 13f8e07dbfe25f3aecda33fb6068894665af61ca1360a7b654be0ad0c3f3ae0b
F tool/speedtest.tcl 06c76698485ccf597b9e7dbb1ac70706eb873355
F tool/speedtest16.c ecb6542862151c3e6509bbc00509b234562ae81e
F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff
F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc
F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e
F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0
-P 34b8ea31877ae8b40729d37b3f51ae7e15f38be841881ea4a37c9c8f0a52896d
-R 08d11f60d527a9ebc32a98574ca5f0f9
-T *branch * stmt-cache
-T *sym-stmt-cache *
-T -sym-trunk *
+P c217b763b148e8bece9d1f72525fd5026d3f710b337c010ffd0306fde4f9add8
+R 46f3adc34868ee6f9be56f487a4c1aae
U drh
-Z c8d2ef694a3736c7eee4ba211f6abfcb
+Z 42a77517994ced9f374a6cd335be1880
# Remove this line to create a well-formed Fossil manifest.
int cnt; /* Number of records displayed so far */
int lineno; /* Line number of last line read from in */
int openFlags; /* Additional flags to open. (SQLITE_OPEN_NOFOLLOW) */
+ int prepFlags; /* Flags for sqlite3_prepare_v3() */
FILE *in; /* Read commands from this stream */
FILE *out; /* Write results here */
FILE *traceOut; /* Output for sqlite3_trace() */
int nResult;
int i;
const char *z;
- rc = sqlite3_prepare_v2(p->db, zSelect, -1, &pSelect, 0);
+ rc = sqlite3_prepare_v3(p->db, zSelect, -1, p->prepFlags, &pSelect, 0);
if( rc!=SQLITE_OK || !pSelect ){
char *zContext = shell_error_context(zSelect, p->db);
utf8_printf(p->out, "/**** ERROR: (%d) %s *****/\n%s", rc,
while( zSql[0] && (SQLITE_OK == rc) ){
static const char *zStmtSql;
- rc = sqlite3_prepare_v2(db, zSql, -1, &pStmt, &zLeftover);
+ rc = sqlite3_prepare_v3(db, zSql, -1, pArg->prepFlags, &pStmt, &zLeftover);
if( SQLITE_OK != rc ){
if( pzErrMsg ){
*pzErrMsg = save_err_msg(db, "in prepare", rc, zSql);
sqlite3_db_config(db, SQLITE_DBCONFIG_TRIGGER_EQP, 0, 0);
/* Reprepare pStmt before reactiving trace modes */
sqlite3_finalize(pStmt);
- sqlite3_prepare_v2(db, zSql, -1, &pStmt, 0);
+ sqlite3_prepare_v3(db, zSql, -1, pArg->prepFlags, &pStmt, 0);
if( pArg ) pArg->pStmt = pStmt;
}
restore_debug_trace_modes();
zSql = sqlite3_mprintf("PRAGMA table_info=%Q", zTab);
shell_check_oom(zSql);
- rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
+ rc = sqlite3_prepare_v3(p->db, zSql, -1, p->prepFlags, &pStmt, 0);
sqlite3_free(zSql);
if( rc ) return 0;
while( sqlite3_step(pStmt)==SQLITE_ROW ){
zSql = sqlite3_mprintf("SELECT 1 FROM pragma_index_list(%Q)"
" WHERE origin='pk'", zTab);
shell_check_oom(zSql);
- rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
+ rc = sqlite3_prepare_v3(p->db, zSql, -1, p->prepFlags, &pStmt, 0);
sqlite3_free(zSql);
if( rc ){
freeColumnList(azCol);
}
}else
- /* The undocumented ".breakpoint" command causes a call to the no-op
- ** routine named test_breakpoint().
+ /* UNDOCUMENTED COMMAND: .breakpoint
+ **
+ ** Causes a call to the no-op routine named test_breakpoint(). This provides
+ ** a convenient function on which to set a breakpoint.
*/
if( c=='b' && n>=3 && strncmp(azArg[0], "breakpoint", n)==0 ){
test_breakpoint();
{ "load_extension", SQLITE_DBCONFIG_ENABLE_LOAD_EXTENSION },
{ "no_ckpt_on_close", SQLITE_DBCONFIG_NO_CKPT_ON_CLOSE },
{ "reset_database", SQLITE_DBCONFIG_RESET_DATABASE },
+ { "stmtcache_size", SQLITE_DBCONFIG_STMTCACHE_SIZE },
{ "trigger_eqp", SQLITE_DBCONFIG_TRIGGER_EQP },
{ "trusted_schema", SQLITE_DBCONFIG_TRUSTED_SCHEMA },
{ "writable_schema", SQLITE_DBCONFIG_WRITABLE_SCHEMA },
int ii, v;
open_db(p, 0);
for(ii=0; ii<ArraySize(aDbConfig); ii++){
+ int op;
if( nArg>1 && strcmp(azArg[1], aDbConfig[ii].zName)!=0 ) continue;
+ op = aDbConfig[ii].op;
if( nArg>=3 ){
- sqlite3_db_config(p->db, aDbConfig[ii].op, booleanValue(azArg[2]), 0);
+ if( op==SQLITE_DBCONFIG_STMTCACHE_SIZE ){
+ sqlite3_db_config(p->db, op, (int)integerValue(azArg[2]), 0);
+ }else{
+ sqlite3_db_config(p->db, op, booleanValue(azArg[2]), 0);
+ }
+ }
+ sqlite3_db_config(p->db, op, -1, &v);
+ if( op==SQLITE_DBCONFIG_STMTCACHE_SIZE ){
+ utf8_printf(p->out, "%19s %d\n", aDbConfig[ii].zName, v);
+ }else{
+ utf8_printf(p->out, "%19s %s\n", aDbConfig[ii].zName, v ? "on" : "off");
}
- sqlite3_db_config(p->db, aDbConfig[ii].op, -1, &v);
- utf8_printf(p->out, "%19s %s\n", aDbConfig[ii].zName, v ? "on" : "off");
if( nArg>1 ) break;
}
if( nArg>1 && ii==ArraySize(aDbConfig) ){
showHelp(p->out, "parameter");
}else
+ /* UNDOCUMENTED COMMAND: .prepflags (+|-)FLAG ...
+ **
+ ** For SQLite core debugging use only.
+ **
+ ** Change the value of ShellState.prepFlags which becomes the flags
+ ** parameter to sqlite3_prepare_v3() in some calls in this application.
+ */
+ if( c=='p' && n>=3 && strncmp(azArg[0], "prepflags", n)==0 ){
+ int i;
+ for(i=1; i<nArg; i++){
+ int op = 0;
+ if( azArg[i][0]!='-' && azArg[i][0]!='+' ){
+ utf8_printf(p->out, "unknown option: \"%s\"\n", azArg[i]);
+ rc = 1;
+ goto meta_command_exit;
+ }
+ if( strcmp(azArg[i]+1, "persist")==0 ){
+ op = SQLITE_PREPARE_PERSISTENT;
+ }else if( strcmp(azArg[i]+1, "no-vtab")==0 ){
+ op = SQLITE_PREPARE_NO_VTAB;
+ }else if( strcmp(azArg[i]+1, "cache")==0 ){
+ op = SQLITE_PREPARE_CACHE;
+ }else{
+ utf8_printf(p->out, "option \"%s\" should be one of: \"%cpersist\""
+ "\"%cno-vtab\" \"%ccache\"\n",
+ azArg[i], azArg[i][0],azArg[i][0],azArg[i][0]);
+ rc = 1;
+ goto meta_command_exit;
+ }
+ if( azArg[i][0]=='+' ){
+ p->prepFlags |= op;
+ }else{
+ p->prepFlags &= ~op;
+ }
+ }
+ utf8_printf(p->out, " prepflags:");
+ utf8_printf(p->out, " %cpersist", (p->prepFlags & SQLITE_PREPARE_PERSISTENT)?'+':'-');
+ utf8_printf(p->out, " %cno-vtab", (p->prepFlags & SQLITE_PREPARE_NO_VTAB)?'+':'-');
+ utf8_printf(p->out, " %ccache\n", (p->prepFlags & SQLITE_PREPARE_CACHE)?'+':'-');
+ }else
+
if( c=='p' && n>=3 && strncmp(azArg[0], "print", n)==0 ){
int i;
for(i=1; i<nArg; i++){
}
}else
+ /* UNDOCUMENTED COMMAND: .treetrace N
+ **
+ ** For SQLite core debugging use only.
+ **
+ ** Set the treetrace mask to N. Also called ".selectrace" for historical
+ ** compatibility.
+ */
if( (c=='s' && n==11 && strncmp(azArg[0], "selecttrace", n)==0)
|| (c=='t' && n==9 && strncmp(azArg[0], "treetrace", n)==0)
){
rc = 1;
goto meta_command_exit;
}
+ utf8_printf(p->out,"%12.12s: ", "colseparator");
+ output_c_string(p->out, p->colSeparator);
+ raw_printf(p->out, "\n");
utf8_printf(p->out, "%12.12s: %s\n","echo",
azBool[ShellHasFlag(p, SHFLG_Echo)]);
utf8_printf(p->out, "%12.12s: %s\n","eqp", azBool[p->autoEQP&3]);
raw_printf(p->out, "\n");
utf8_printf(p->out,"%12.12s: %s\n","output",
strlen30(p->outfile) ? p->outfile : "stdout");
- utf8_printf(p->out,"%12.12s: ", "colseparator");
- output_c_string(p->out, p->colSeparator);
- raw_printf(p->out, "\n");
+ utf8_printf(p->out,"%12.12s:", "prepflags");
+ utf8_printf(p->out," %cpersist",(p->prepFlags&SQLITE_PREPARE_PERSISTENT)?'+':'-');
+ utf8_printf(p->out," %cno-vtab",(p->prepFlags&SQLITE_PREPARE_NO_VTAB)?'+':'-');
+ utf8_printf(p->out," %ccache\n",(p->prepFlags&SQLITE_PREPARE_CACHE)?'+':'-');
utf8_printf(p->out,"%12.12s: ", "rowseparator");
output_c_string(p->out, p->rowSeparator);
raw_printf(p->out, "\n");
}
}else
+ /* UNDOCUMENTED COMMMAND: .wheretrace NUMBER
+ **
+ ** For SQLite core debugging use only.
+ **
+ ** See the wheretrace mask to NUMBER.
+ */
if( c=='w' && strncmp(azArg[0], "wheretrace", n)==0 ){
unsigned int x = nArg>=2 ? (unsigned int)integerValue(azArg[1]) : 0xffffffff;
sqlite3_test_control(SQLITE_TESTCTRL_TRACEFLAGS, 3, &x);
" --size N Relative test size. Default=100\n"
" --strict Use STRICT table where appropriate\n"
" --stats Show statistics at the end\n"
+ " --stmtcache N Use a statement cache of size N\n"
" --temp N N from 0 to 9. 0: no temp table. 9: all temp tables\n"
" --testset T Run test-set T (main, cte, rtree, orm, fp, debug)\n"
" --trace Turn on SQL tracing\n"
int nRepeat; /* Repeat selects this many times */
int doCheckpoint; /* Run PRAGMA wal_checkpoint after each trans */
int nReserve; /* Reserve bytes */
+ int szStmtCache; /* Size of the statement cache */
const char *zWR; /* Might be WITHOUT ROWID */
const char *zNN; /* Might be NOT NULL */
const char *zPK; /* Might be UNIQUE or PRIMARY KEY */
#if SQLITE_VERSION_NUMBER>=3006001
if( g.bReprepare ){
sqlite3_stmt *pNew;
- if( g.mPrepFlags & SQLITE_PREPARE_PERSISTENT ){
+ if( g.mPrepFlags & SQLITE_PREPARE_CACHE ){
char zBuf[1000];
strncpy(zBuf, sqlite3_sql(g.pStmt), sizeof(zBuf));
zBuf[sizeof(zBuf)-1] = 0;
}else if( strcmp(z,"size")==0 ){
if( i>=argc-1 ) fatal_error("missing argument on %s\n", argv[i]);
g.szTest = integerValue(argv[++i]);
+ }else if( strcmp(z,"stmtcache")==0 ){
+ if( i>=argc-1 ) fatal_error("missing argument on %s\n", argv[i]);
+ g.szStmtCache = integerValue(argv[++i]);
+ g.mPrepFlags |= SQLITE_PREPARE_CACHE;
}else if( strcmp(z,"stats")==0 ){
showStats = 1;
}else if( strcmp(z,"temp")==0 ){
if( rc ) fatal_error("lookaside configuration failed: %d\n", rc);
}
#endif
+#ifdef SQLITE_DBCONFIG_STMTCACHE_SIZE
+ if( g.mPrepFlags & SQLITE_PREPARE_CACHE ){
+ int nCache = 0;
+ rc = sqlite3_db_config(g.db, SQLITE_DBCONFIG_STMTCACHE_SIZE,
+ g.szStmtCache, &nCache);
+ if( rc ) fatal_error("statement cache configuration failed: %d\n", rc);
+ }
+#endif /* SQLITE_DBCONFIG_STMTCACHE_SIZE */
if( g.nReserve>0 ){
sqlite3_file_control(g.db, 0, SQLITE_FCNTL_RESERVE_BYTES, &g.nReserve);
}