From 843e4cdea9418748de18aa76879d69de0e861027 Mon Sep 17 00:00:00 2001 From: mistachkin Date: Fri, 26 Sep 2014 18:30:11 +0000 Subject: [PATCH 01/54] Add an assert() to verify the last-row-id for the database just prior to calling a SQL function. FossilOrigin-Name: d026f0c944ce812732d3595eaa3c5d432a86c7dd --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/vdbe.c | 1 + 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 131d77b3a9..63e97cbf9f 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sthe\s"PRAGMA\sintegrity_check"\scommand\sso\sthat\sit\savoids\sformatting\serror\nmessage\scontext\smessages\suntil\sit\sactually\sneeds\sto\sgenerate\san\serror\smessage.\nThis\savoids\smuch\sformatting,\sand\shence\sgreatly\simproves\sthe\sperformance\sof\n"PRAGMA\sintegrity_check"\sin\sthe\scommon\scase\swhen\sthere\sare\sno\serrors.\s\sIt\salso\nmakes\sthe\scode\sa\slittle\ssmaller. -D 2014-09-26T02:41:05.726 +C Add\san\sassert()\sto\sverify\sthe\slast-row-id\sfor\sthe\sdatabase\sjust\sprior\sto\scalling\sa\sSQL\sfunction. +D 2014-09-26T18:30:11.093 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -289,7 +289,7 @@ F src/update.c 729f6f18fc27740591d085e1172cebe311144bf0 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 4006c01772bd8d8ac4306d523bbcee41d3e392d8 F src/vacuum.c 59f03f92bcff57faa6a8ca256eb29ccddfb0614a -F src/vdbe.c 91b7e12bca7b6056574ce28935e3e3f4769ce3c4 +F src/vdbe.c 93eeb6f9c3a3084133225a196f220454d71cca10 F src/vdbe.h 09f5b4e3719fa454f252322b1cdab5cf1f361327 F src/vdbeInt.h bb7f7ecfdead1a2ae0251b59f86f5724838d975c F src/vdbeapi.c e9e33b59834e3edc8790209765e069874c269d9d @@ -1200,7 +1200,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P e93aecc090c2a1d3c231bb2bde044886eff0bdf7 -R 32be19747fff5e8f2465eed0f224b45d -U drh -Z f56b9000203c19d0f3a8172e8374b279 +P 83913515830aa850f9e38406f9422d7e88dcab66 +R dc4da31df9102dea4f18af6519657b79 +U mistachkin +Z 6fd91dd1e10822b3b57f7222d98e1fa9 diff --git a/manifest.uuid b/manifest.uuid index b182c8c316..482b361956 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -83913515830aa850f9e38406f9422d7e88dcab66 \ No newline at end of file +d026f0c944ce812732d3595eaa3c5d432a86c7dd \ No newline at end of file diff --git a/src/vdbe.c b/src/vdbe.c index 1a1e441cd4..34eb1d42c5 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -1558,6 +1558,7 @@ case OP_Function: { ctx.pVdbe = p; MemSetTypeFlag(ctx.pOut, MEM_Null); ctx.fErrorOrAux = 0; + assert( db->lastRowid==lastRowid ); (*ctx.pFunc->xFunc)(&ctx, n, apVal); /* IMP: R-24505-23230 */ lastRowid = db->lastRowid; /* Remember rowid changes made by xFunc */ From 7682a476f6da4808691d6387d330a3f5d7378e7b Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 29 Sep 2014 15:00:28 +0000 Subject: [PATCH 02/54] Ensure that the OP_Prev opcode verifies that content has not been deleted out from under the cursor. Fix for ticket [209d31e3161b9e9ff]. FossilOrigin-Name: 414f0d6a647a4d040b5463c73c5e15e699d85b4c --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/btree.c | 3 +-- test/eval.test | 12 ++++++++++++ 4 files changed, 22 insertions(+), 11 deletions(-) diff --git a/manifest b/manifest index 63e97cbf9f..68c67e07c1 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\san\sassert()\sto\sverify\sthe\slast-row-id\sfor\sthe\sdatabase\sjust\sprior\sto\scalling\sa\sSQL\sfunction. -D 2014-09-26T18:30:11.093 +C Ensure\sthat\sthe\sOP_Prev\sopcode\sverifies\sthat\scontent\shas\snot\sbeen\sdeleted\nout\sfrom\sunder\sthe\scursor.\s\sFix\sfor\sticket\s[209d31e3161b9e9ff]. +D 2014-09-29T15:00:28.761 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -172,7 +172,7 @@ F src/auth.c d8abcde53426275dab6243b441256fcd8ccbebb2 F src/backup.c a31809c65623cc41849b94d368917f8bb66e6a7e F src/bitvec.c 19a4ba637bd85f8f63fc8c9bae5ade9fb05ec1cb F src/btmutex.c 49ca66250c7dfa844a4d4cb8272b87420d27d3a5 -F src/btree.c 59f03e421dad3cb6e27cc7d2393d3a7459be4b5e +F src/btree.c ede8348a7d623257ee6c06ca4796ceaee13b8657 F src/btree.h a79aa6a71e7f1055f01052b7f821bd1c2dce95c8 F src/btreeInt.h 1bd7957161a1346a914f1f09231610e777a8e58d F src/build.c bde83dd5cf812e310a7e5ad2846790a14745bef4 @@ -469,7 +469,7 @@ F test/enc3.test 90683ad0e6ea587b9d5542ca93568af9a9858c40 F test/enc4.test c8f1ce3618508fd0909945beb8b8831feef2c020 F test/eqp.test 85873fa5816c48915c82c4e74cb5c35a5b48160f F test/errmsg.test f31592a594b44ee121371d25ddd5d63497bb3401 -F test/eval.test bc269c365ba877554948441e91ad5373f9f91be3 +F test/eval.test a64c9105d6ff163df7cf09d6ac29cdad5922078c F test/exclusive.test c7ebbc756eacf544c108b15eed64d7d4e5f86b75 F test/exclusive2.test 32798111aae78a5deec980eee383213f189df308 F test/exec.test e949714dc127eaa5ecc7d723efec1ec27118fdd7 @@ -1200,7 +1200,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 83913515830aa850f9e38406f9422d7e88dcab66 -R dc4da31df9102dea4f18af6519657b79 -U mistachkin -Z 6fd91dd1e10822b3b57f7222d98e1fa9 +P d026f0c944ce812732d3595eaa3c5d432a86c7dd +R 4bbd3babbb639de348c82ac1e98901ef +U drh +Z e609ec38acb2ceba655fca4c2f22f4af diff --git a/manifest.uuid b/manifest.uuid index 482b361956..909bc1e4db 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -d026f0c944ce812732d3595eaa3c5d432a86c7dd \ No newline at end of file +414f0d6a647a4d040b5463c73c5e15e699d85b4c \ No newline at end of file diff --git a/src/btree.c b/src/btree.c index 135b40139f..503a2fb5d0 100644 --- a/src/btree.c +++ b/src/btree.c @@ -4985,8 +4985,7 @@ static SQLITE_NOINLINE int btreePrevious(BtCursor *pCur, int *pRes){ assert( (pCur->curFlags & (BTCF_AtLast|BTCF_ValidOvfl|BTCF_ValidNKey))==0 ); assert( pCur->info.nSize==0 ); if( pCur->eState!=CURSOR_VALID ){ - assert( pCur->eState>=CURSOR_REQUIRESEEK ); - rc = btreeRestoreCursorPosition(pCur); + rc = restoreCursorPosition(pCur); if( rc!=SQLITE_OK ){ return rc; } diff --git a/test/eval.test b/test/eval.test index 912dc8215b..360d158f3c 100644 --- a/test/eval.test +++ b/test/eval.test @@ -58,6 +58,18 @@ do_test eval-2.2 { SELECT * FROM t2 } } {} +do_test eval-2.3 { + execsql { + INSERT INTO t2 SELECT x, x+1 FROM t1 WHERE x<5; + SELECT x, test_eval('DELETE FROM t2 WHERE x='||x), y FROM t2 + ORDER BY rowid DESC; + } +} {4 {} {} 3 {} {} 2 {} {} 1 {} {}} +do_test eval-2.4 { + execsql { + SELECT * FROM t2 + } +} {} # Modify a row while it is being read. # From 39c4b82b5a82977db329f688ebf4bf0a2d901ec1 Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 29 Sep 2014 15:42:01 +0000 Subject: [PATCH 03/54] Fix the header comment in sqlite3VdbeDeletePriorOpcode(). No changes to code. FossilOrigin-Name: 7fb1626866c2f8dad84c7e6184824be3efd71ca2 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/vdbeaux.c | 3 ++- 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 68c67e07c1..c39ace7ac0 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Ensure\sthat\sthe\sOP_Prev\sopcode\sverifies\sthat\scontent\shas\snot\sbeen\sdeleted\nout\sfrom\sunder\sthe\scursor.\s\sFix\sfor\sticket\s[209d31e3161b9e9ff]. -D 2014-09-29T15:00:28.761 +C Fix\sthe\sheader\scomment\sin\ssqlite3VdbeDeletePriorOpcode().\s\sNo\schanges\sto\ncode. +D 2014-09-29T15:42:01.115 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -293,7 +293,7 @@ F src/vdbe.c 93eeb6f9c3a3084133225a196f220454d71cca10 F src/vdbe.h 09f5b4e3719fa454f252322b1cdab5cf1f361327 F src/vdbeInt.h bb7f7ecfdead1a2ae0251b59f86f5724838d975c F src/vdbeapi.c e9e33b59834e3edc8790209765e069874c269d9d -F src/vdbeaux.c a05adc3c96abdaf3db14768ddd63132fc9678060 +F src/vdbeaux.c 8e016c6051c013a394f8e8679be1ca60723707bd F src/vdbeblob.c 848238dc73e93e48432991bb5651bf87d865eca4 F src/vdbemem.c 1e105dacf5190fc85a8ec2107c0dcc1884e75099 F src/vdbesort.c 5c1bacf90578d22b630fbf6ed98ccf60d83435ef @@ -1200,7 +1200,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P d026f0c944ce812732d3595eaa3c5d432a86c7dd -R 4bbd3babbb639de348c82ac1e98901ef +P 414f0d6a647a4d040b5463c73c5e15e699d85b4c +R f6298f1a1c0cd9e9dc9c3dc07f24407e U drh -Z e609ec38acb2ceba655fca4c2f22f4af +Z 0f82639c06e932d5523a9215bf58cd9c diff --git a/manifest.uuid b/manifest.uuid index 909bc1e4db..b5ea57e647 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -414f0d6a647a4d040b5463c73c5e15e699d85b4c \ No newline at end of file +7fb1626866c2f8dad84c7e6184824be3efd71ca2 \ No newline at end of file diff --git a/src/vdbeaux.c b/src/vdbeaux.c index 87b14a6d87..2562c63b62 100644 --- a/src/vdbeaux.c +++ b/src/vdbeaux.c @@ -752,7 +752,8 @@ void sqlite3VdbeChangeToNoop(Vdbe *p, int addr){ } /* -** Remove the last opcode inserted +** If the last opcode is "op" and it is not a jump destination, +** then remove it. Return true if and only if an opcode was removed. */ int sqlite3VdbeDeletePriorOpcode(Vdbe *p, u8 op){ if( (p->nOp-1)>(p->pParse->iFixedOp) && p->aOp[p->nOp-1].opcode==op ){ From 4fa4a54f7eb58c465186cac6fe9ab4f5cbddbc12 Mon Sep 17 00:00:00 2001 From: drh Date: Tue, 30 Sep 2014 12:33:33 +0000 Subject: [PATCH 04/54] Remove the SQLITE_ENABLE_TREE_EXPLAIN compile-time option. Add alternative debugging display routines: sqlite3TreeViewExpr(), sqlite3TreeViewExprList(), and sqlite3TreeViewSelect(). FossilOrigin-Name: 4ff51325d6b41d0c59e303b573700ec80c51d216 --- manifest | 34 +++++----- manifest.uuid | 2 +- src/expr.c | 167 ++++++++++++++++++++++-------------------------- src/main.c | 16 ----- src/parse.y | 3 - src/printf.c | 64 +++++++++++++++++++ src/select.c | 124 +++++++++++++++++------------------ src/shell.c | 9 --- src/sqlite.h.in | 2 +- src/sqliteInt.h | 45 +++++++------ src/vdbeInt.h | 4 -- src/vdbeaux.c | 4 -- src/vdbetrace.c | 115 --------------------------------- src/where.c | 59 ----------------- 14 files changed, 245 insertions(+), 403 deletions(-) diff --git a/manifest b/manifest index c39ace7ac0..642f78d5ff 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sthe\sheader\scomment\sin\ssqlite3VdbeDeletePriorOpcode().\s\sNo\schanges\sto\ncode. -D 2014-09-29T15:42:01.115 +C Remove\sthe\sSQLITE_ENABLE_TREE_EXPLAIN\scompile-time\soption.\s\sAdd\salternative\ndebugging\sdisplay\sroutines:\ssqlite3TreeViewExpr(),\ssqlite3TreeViewExprList(),\nand\ssqlite3TreeViewSelect(). +D 2014-09-30T12:33:33.546 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -181,7 +181,7 @@ F src/complete.c 535183afb3c75628b78ce82612931ac7cdf26f14 F src/ctime.c bb434068b5308a857b181c2d204a320ff0d6c638 F src/date.c 57a7f9ba9f6b4d5268f5e411739066a611f99036 F src/delete.c fae81cc2eb14b75267d4f47d3cfc9ae02aae726f -F src/expr.c f32119248996680aa73c5c37bfdd42820804dc17 +F src/expr.c 46a8ca93361d09f2ec6d9b7d524751510569d737 F src/fault.c 160a0c015b6c2629d3899ed2daf63d75754a32bb F src/fkey.c da985ae673efef2c712caef825a5d2edb087ead7 F src/func.c ba47c1671ab3cfdafa6e9d6ee490939ea578adee @@ -194,7 +194,7 @@ F src/journal.c b4124532212b6952f42eb2c12fa3c25701d8ba8d F src/legacy.c ba1863ea58c4c840335a84ec276fc2b25e22bc4e F src/lempar.c 7274c97d24bb46631e504332ccd3bd1b37841770 F src/loadext.c de741e66e5ddc1598d904d7289239696e40ed994 -F src/main.c d15621461fb0c52675eba2b650492ed1beef69ab +F src/main.c 4a507a467cc20979579e4320ca6466b8ed0be268 F src/malloc.c 5bb99ee1e08ad58e457063cf79ce521db0e24195 F src/mem0.c 6a55ebe57c46ca1a7d98da93aaa07f99f1059645 F src/mem1.c faf615aafd8be74a71494dfa027c113ea5c6615f @@ -217,22 +217,22 @@ F src/os_win.c 0a4042ef35f322e86fa01f6c8884c5e645b911e7 F src/os_win.h 09e751b20bbc107ffbd46e13555dc73576d88e21 F src/pager.c caab007743821d96752597c9cfd7351654697b06 F src/pager.h ffd5607f7b3e4590b415b007a4382f693334d428 -F src/parse.y b98772da2bb5415970085b707203f92569400aa8 +F src/parse.y ce1494308578d2f10a68cd8debc9fc156dda1094 F src/pcache.c 4121a0571c18581ee9f82f086d5e2030051ebd6a F src/pcache.h 9b559127b83f84ff76d735c8262f04853be0c59a F src/pcache1.c dab8ab930d4a73b99768d881185994f34b80ecaa F src/pragma.c 3f3e959390a10c0131676f0e307acce372777e0f F src/prepare.c 6ef0cf2f9274982988ed6b7cab1be23147e94196 -F src/printf.c 3a47f526b173813d9a7f4e7044007771ba68cde1 +F src/printf.c 0db94d24f97b4e562e9da9d2ce85e8a69531daf6 F src/random.c d10c1f85b6709ca97278428fd5db5bbb9c74eece F src/resolve.c a3466128b52a86c466e47ac1a19e2174f7b5cf89 F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e -F src/select.c a83ed8bc2a31c131e3addb6f0488b68334085e7b -F src/shell.c dad23987c34faddb061a339da3e92e05ccc6935e -F src/sqlite.h.in 8b018219ce988913e5977d5de9ab4beb33be23b6 +F src/select.c 373da54c2bd7e38993bc926a284bc05a53b01b8b +F src/shell.c 38f627b0885191357f55902a3ac199de90d79715 +F src/sqlite.h.in 159f2cb9eef74b6c99aeeb4c071e7745835f04f6 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d -F src/sqliteInt.h 5e09fe04f999223680801ddf8fbae6b60751d613 +F src/sqliteInt.h 8242d04760ec2a943a152eba2a006ea121a3eafd F src/sqliteLimit.h 164b0e6749d31e0daa1a4589a169d31c0dec7b3d F src/status.c 7ac05a5c7017d0b9f0b4bcd701228b784f987158 F src/table.c 2e99ef7ef16187e17033d9398dc962ce22dab5cb @@ -291,18 +291,18 @@ F src/util.c 4006c01772bd8d8ac4306d523bbcee41d3e392d8 F src/vacuum.c 59f03f92bcff57faa6a8ca256eb29ccddfb0614a F src/vdbe.c 93eeb6f9c3a3084133225a196f220454d71cca10 F src/vdbe.h 09f5b4e3719fa454f252322b1cdab5cf1f361327 -F src/vdbeInt.h bb7f7ecfdead1a2ae0251b59f86f5724838d975c +F src/vdbeInt.h 0b97a3190f8fbf460655985a9183019f5a702754 F src/vdbeapi.c e9e33b59834e3edc8790209765e069874c269d9d -F src/vdbeaux.c 8e016c6051c013a394f8e8679be1ca60723707bd +F src/vdbeaux.c 5b687d7b5beaaa5b97189edf25cf08c311834933 F src/vdbeblob.c 848238dc73e93e48432991bb5651bf87d865eca4 F src/vdbemem.c 1e105dacf5190fc85a8ec2107c0dcc1884e75099 F src/vdbesort.c 5c1bacf90578d22b630fbf6ed98ccf60d83435ef -F src/vdbetrace.c 4f29b04edb0cec3d5fcd9b566d9f0e75c8984362 +F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c a14d3d8042adeb51f81731c1b47b3e481d1cc23a +F src/where.c 5a2c700f6f29da91ac633015d1378b91dcf237b6 F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1200,7 +1200,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 414f0d6a647a4d040b5463c73c5e15e699d85b4c -R f6298f1a1c0cd9e9dc9c3dc07f24407e +P 7fb1626866c2f8dad84c7e6184824be3efd71ca2 +R f57511c6ad57aee6db1d51feabde515b U drh -Z 0f82639c06e932d5523a9215bf58cd9c +Z d2ed6dec33496c4977b9e22861714f01 diff --git a/manifest.uuid b/manifest.uuid index b5ea57e647..246f7552d4 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -7fb1626866c2f8dad84c7e6184824be3efd71ca2 \ No newline at end of file +4ff51325d6b41d0c59e303b573700ec80c51d216 \ No newline at end of file diff --git a/src/expr.c b/src/expr.c index 57e462ea6e..31ff98ea4f 100644 --- a/src/expr.c +++ b/src/expr.c @@ -3236,90 +3236,86 @@ void sqlite3ExprCodeAndCache(Parse *pParse, Expr *pExpr, int target){ exprToRegister(pExpr, iMem); } -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) +#ifdef SQLITE_DEBUG /* ** Generate a human-readable explanation of an expression tree. */ -void sqlite3ExplainExpr(Vdbe *pOut, Expr *pExpr){ - int op; /* The opcode being coded */ +void sqlite3TreeViewExpr(TreeView *pView, const Expr *pExpr, u8 moreToFollow){ const char *zBinOp = 0; /* Binary operator */ const char *zUniOp = 0; /* Unary operator */ + pView = sqlite3TreeViewPush(pView, moreToFollow); if( pExpr==0 ){ - op = TK_NULL; - }else{ - op = pExpr->op; + sqlite3TreeViewLine(pView, "nil"); + sqlite3TreeViewPop(pView); + return; } - switch( op ){ + switch( pExpr->op ){ case TK_AGG_COLUMN: { - sqlite3ExplainPrintf(pOut, "AGG{%d:%d}", + sqlite3TreeViewLine(pView, "AGG{%d:%d}", pExpr->iTable, pExpr->iColumn); break; } case TK_COLUMN: { if( pExpr->iTable<0 ){ /* This only happens when coding check constraints */ - sqlite3ExplainPrintf(pOut, "COLUMN(%d)", pExpr->iColumn); + sqlite3TreeViewLine(pView, "COLUMN(%d)", pExpr->iColumn); }else{ - sqlite3ExplainPrintf(pOut, "{%d:%d}", + sqlite3TreeViewLine(pView, "{%d:%d}", pExpr->iTable, pExpr->iColumn); } break; } case TK_INTEGER: { if( pExpr->flags & EP_IntValue ){ - sqlite3ExplainPrintf(pOut, "%d", pExpr->u.iValue); + sqlite3TreeViewLine(pView, "%d", pExpr->u.iValue); }else{ - sqlite3ExplainPrintf(pOut, "%s", pExpr->u.zToken); + sqlite3TreeViewLine(pView, "%s", pExpr->u.zToken); } break; } #ifndef SQLITE_OMIT_FLOATING_POINT case TK_FLOAT: { - sqlite3ExplainPrintf(pOut,"%s", pExpr->u.zToken); + sqlite3TreeViewLine(pView,"%s", pExpr->u.zToken); break; } #endif case TK_STRING: { - sqlite3ExplainPrintf(pOut,"%Q", pExpr->u.zToken); + sqlite3TreeViewLine(pView,"%Q", pExpr->u.zToken); break; } case TK_NULL: { - sqlite3ExplainPrintf(pOut,"NULL"); + sqlite3TreeViewLine(pView,"NULL"); break; } #ifndef SQLITE_OMIT_BLOB_LITERAL case TK_BLOB: { - sqlite3ExplainPrintf(pOut,"%s", pExpr->u.zToken); + sqlite3TreeViewLine(pView,"%s", pExpr->u.zToken); break; } #endif case TK_VARIABLE: { - sqlite3ExplainPrintf(pOut,"VARIABLE(%s,%d)", - pExpr->u.zToken, pExpr->iColumn); + sqlite3TreeViewLine(pView,"VARIABLE(%s,%d)", + pExpr->u.zToken, pExpr->iColumn); break; } case TK_REGISTER: { - sqlite3ExplainPrintf(pOut,"REGISTER(%d)", pExpr->iTable); + sqlite3TreeViewLine(pView,"REGISTER(%d)", pExpr->iTable); break; } case TK_AS: { - sqlite3ExplainExpr(pOut, pExpr->pLeft); + sqlite3TreeViewLine(pView,"AS %Q", pExpr->u.zToken); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 0); + break; + } + case TK_ID: { + sqlite3TreeViewLine(pView,"ID %Q", pExpr->u.zToken); break; } #ifndef SQLITE_OMIT_CAST case TK_CAST: { /* Expressions of the form: CAST(pLeft AS token) */ - const char *zAff = "unk"; - switch( sqlite3AffinityType(pExpr->u.zToken, 0) ){ - case SQLITE_AFF_TEXT: zAff = "TEXT"; break; - case SQLITE_AFF_NONE: zAff = "NONE"; break; - case SQLITE_AFF_NUMERIC: zAff = "NUMERIC"; break; - case SQLITE_AFF_INTEGER: zAff = "INTEGER"; break; - case SQLITE_AFF_REAL: zAff = "REAL"; break; - } - sqlite3ExplainPrintf(pOut, "CAST-%s(", zAff); - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut, ")"); + sqlite3TreeViewLine(pView,"CAST %Q", pExpr->u.zToken); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 0); break; } #endif /* SQLITE_OMIT_CAST */ @@ -3352,8 +3348,8 @@ void sqlite3ExplainExpr(Vdbe *pOut, Expr *pExpr){ case TK_NOTNULL: zUniOp = "NOTNULL"; break; case TK_COLLATE: { - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut,".COLLATE(%s)",pExpr->u.zToken); + sqlite3TreeViewLine(pView, "COLLATE %Q", pExpr->u.zToken); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 0); break; } @@ -3365,41 +3361,36 @@ void sqlite3ExplainExpr(Vdbe *pOut, Expr *pExpr){ }else{ pFarg = pExpr->x.pList; } - if( op==TK_AGG_FUNCTION ){ - sqlite3ExplainPrintf(pOut, "AGG_FUNCTION%d:%s(", + if( pExpr->op==TK_AGG_FUNCTION ){ + sqlite3TreeViewLine(pView, "AGG_FUNCTION%d %Q", pExpr->op2, pExpr->u.zToken); }else{ - sqlite3ExplainPrintf(pOut, "FUNCTION:%s(", pExpr->u.zToken); + sqlite3TreeViewLine(pView, "FUNCTION %Q", pExpr->u.zToken); } if( pFarg ){ - sqlite3ExplainExprList(pOut, pFarg); + sqlite3TreeViewExprList(pView, pFarg, 0, 0); } - sqlite3ExplainPrintf(pOut, ")"); break; } #ifndef SQLITE_OMIT_SUBQUERY case TK_EXISTS: { - sqlite3ExplainPrintf(pOut, "EXISTS("); - sqlite3ExplainSelect(pOut, pExpr->x.pSelect); - sqlite3ExplainPrintf(pOut,")"); + sqlite3TreeViewLine(pView, "EXISTS-expr"); + sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0); break; } case TK_SELECT: { - sqlite3ExplainPrintf(pOut, "("); - sqlite3ExplainSelect(pOut, pExpr->x.pSelect); - sqlite3ExplainPrintf(pOut, ")"); + sqlite3TreeViewLine(pView, "SELECT-expr"); + sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0); break; } case TK_IN: { - sqlite3ExplainPrintf(pOut, "IN("); - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut, ","); + sqlite3TreeViewLine(pView, "IN"); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 1); if( ExprHasProperty(pExpr, EP_xIsSelect) ){ - sqlite3ExplainSelect(pOut, pExpr->x.pSelect); + sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0); }else{ - sqlite3ExplainExprList(pOut, pExpr->x.pList); + sqlite3TreeViewExprList(pView, pExpr->x.pList, 0, 0); } - sqlite3ExplainPrintf(pOut, ")"); break; } #endif /* SQLITE_OMIT_SUBQUERY */ @@ -3419,13 +3410,10 @@ void sqlite3ExplainExpr(Vdbe *pOut, Expr *pExpr){ Expr *pX = pExpr->pLeft; Expr *pY = pExpr->x.pList->a[0].pExpr; Expr *pZ = pExpr->x.pList->a[1].pExpr; - sqlite3ExplainPrintf(pOut, "BETWEEN("); - sqlite3ExplainExpr(pOut, pX); - sqlite3ExplainPrintf(pOut, ","); - sqlite3ExplainExpr(pOut, pY); - sqlite3ExplainPrintf(pOut, ","); - sqlite3ExplainExpr(pOut, pZ); - sqlite3ExplainPrintf(pOut, ")"); + sqlite3TreeViewLine(pView, "BETWEEN"); + sqlite3TreeViewExpr(pView, pX, 1); + sqlite3TreeViewExpr(pView, pY, 1); + sqlite3TreeViewExpr(pView, pZ, 0); break; } case TK_TRIGGER: { @@ -3436,15 +3424,14 @@ void sqlite3ExplainExpr(Vdbe *pOut, Expr *pExpr){ ** is set to the column of the pseudo-table to read, or to -1 to ** read the rowid field. */ - sqlite3ExplainPrintf(pOut, "%s(%d)", + sqlite3TreeViewLine(pView, "%s(%d)", pExpr->iTable ? "NEW" : "OLD", pExpr->iColumn); break; } case TK_CASE: { - sqlite3ExplainPrintf(pOut, "CASE("); - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut, ","); - sqlite3ExplainExprList(pOut, pExpr->x.pList); + sqlite3TreeViewLine(pView, "CASE"); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 1); + sqlite3TreeViewExprList(pView, pExpr->x.pList, 0, 0); break; } #ifndef SQLITE_OMIT_TRIGGER @@ -3456,55 +3443,57 @@ void sqlite3ExplainExpr(Vdbe *pOut, Expr *pExpr){ case OE_Fail: zType = "fail"; break; case OE_Ignore: zType = "ignore"; break; } - sqlite3ExplainPrintf(pOut, "RAISE-%s(%s)", zType, pExpr->u.zToken); + sqlite3TreeViewLine(pView, "RAISE %s(%Q)", zType, pExpr->u.zToken); break; } #endif + default: { + sqlite3TreeViewLine(pView, "op=%d", pExpr->op); + break; + } } if( zBinOp ){ - sqlite3ExplainPrintf(pOut,"%s(", zBinOp); - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut,","); - sqlite3ExplainExpr(pOut, pExpr->pRight); - sqlite3ExplainPrintf(pOut,")"); + sqlite3TreeViewLine(pView, "%s", zBinOp); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 1); + sqlite3TreeViewExpr(pView, pExpr->pRight, 0); }else if( zUniOp ){ - sqlite3ExplainPrintf(pOut,"%s(", zUniOp); - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut,")"); + sqlite3TreeViewLine(pView, "%s", zUniOp); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 0); } + sqlite3TreeViewPop(pView); } -#endif /* defined(SQLITE_ENABLE_TREE_EXPLAIN) */ +#endif /* SQLITE_DEBUG */ -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) +#ifdef SQLITE_DEBUG /* ** Generate a human-readable explanation of an expression list. */ -void sqlite3ExplainExprList(Vdbe *pOut, ExprList *pList){ +void sqlite3TreeViewExprList( + TreeView *pView, + const ExprList *pList, + u8 moreToFollow, + const char *zLabel +){ int i; - if( pList==0 || pList->nExpr==0 ){ - sqlite3ExplainPrintf(pOut, "(empty-list)"); - return; - }else if( pList->nExpr==1 ){ - sqlite3ExplainExpr(pOut, pList->a[0].pExpr); + pView = sqlite3TreeViewPush(pView, moreToFollow); + if( zLabel==0 || zLabel[0]==0 ) zLabel = "LIST"; + if( pList==0 ){ + sqlite3TreeViewLine(pView, "%s (empty)", zLabel); }else{ - sqlite3ExplainPush(pOut); + sqlite3TreeViewLine(pView, "%s", zLabel); for(i=0; inExpr; i++){ - sqlite3ExplainPrintf(pOut, "item[%d] = ", i); - sqlite3ExplainPush(pOut); - sqlite3ExplainExpr(pOut, pList->a[i].pExpr); - sqlite3ExplainPop(pOut); - if( pList->a[i].zName ){ + sqlite3TreeViewExpr(pView, pList->a[i].pExpr, inExpr-1); +#if 0 + if( pList->a[i].zName ){ sqlite3ExplainPrintf(pOut, " AS %s", pList->a[i].zName); } if( pList->a[i].bSpanIsTab ){ sqlite3ExplainPrintf(pOut, " (%s)", pList->a[i].zSpan); } - if( inExpr-1 ){ - sqlite3ExplainNL(pOut); - } +#endif } - sqlite3ExplainPop(pOut); } + sqlite3TreeViewPop(pView); } #endif /* SQLITE_DEBUG */ diff --git a/src/main.c b/src/main.c index 231890de4b..dc17917796 100644 --- a/src/main.c +++ b/src/main.c @@ -3327,22 +3327,6 @@ int sqlite3_test_control(int op, ...){ break; } -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) - /* sqlite3_test_control(SQLITE_TESTCTRL_EXPLAIN_STMT, - ** sqlite3_stmt*,const char**); - ** - ** If compiled with SQLITE_ENABLE_TREE_EXPLAIN, each sqlite3_stmt holds - ** a string that describes the optimized parse tree. This test-control - ** returns a pointer to that string. - */ - case SQLITE_TESTCTRL_EXPLAIN_STMT: { - sqlite3_stmt *pStmt = va_arg(ap, sqlite3_stmt*); - const char **pzRet = va_arg(ap, const char**); - *pzRet = sqlite3VdbeExplanation((Vdbe*)pStmt); - break; - } -#endif - /* sqlite3_test_control(SQLITE_TESTCTRL_NEVER_CORRUPT, int); ** ** Set or clear a flag that indicates that the database file is always well- diff --git a/src/parse.y b/src/parse.y index 30a6dc5ff4..b47f531ee3 100644 --- a/src/parse.y +++ b/src/parse.y @@ -399,9 +399,6 @@ cmd ::= DROP VIEW ifexists(E) fullname(X). { cmd ::= select(X). { SelectDest dest = {SRT_Output, 0, 0, 0, 0, 0}; sqlite3Select(pParse, X, &dest); - sqlite3ExplainBegin(pParse->pVdbe); - sqlite3ExplainSelect(pParse->pVdbe, X); - sqlite3ExplainFinish(pParse->pVdbe); sqlite3SelectDelete(pParse->db, X); } diff --git a/src/printf.c b/src/printf.c index 6d4b1b4ac7..92e8e100de 100644 --- a/src/printf.c +++ b/src/printf.c @@ -1056,6 +1056,70 @@ void sqlite3DebugPrintf(const char *zFormat, ...){ } #endif +#ifdef SQLITE_DEBUG +/************************************************************************* +** Routines for implementing the "TreeView" display of hierarchical +** data structures for debugging. +** +** The main entry points (coded elsewhere) are: +** sqlite3TreeViewExpr(0, pExpr, 0); +** sqlite3TreeViewExprList(0, pList, 0, 0); +** sqlite3TreeViewSelect(0, pSelect, 0); +** Insert calls to those routines while debugging in order to display +** a diagram of Expr, ExprList, and Select objects. +** +*/ +/* Add a new subitem to the tree. The moreToFollow flag indicates that this +** is not the last item in the tree. */ +TreeView *sqlite3TreeViewPush(TreeView *p, u8 moreToFollow){ + if( p==0 ){ + p = sqlite3_malloc( sizeof(*p) ); + if( p==0 ) return 0; + memset(p, 0, sizeof(*p)); + }else{ + p->iLevel++; + } + assert( moreToFollow==0 || moreToFollow==1 ); + p->mLine &= ~(1<iLevel); + p->mLine |= moreToFollow << p->iLevel; + return p; +} +/* Finished with one layer of the tree */ +void sqlite3TreeViewPop(TreeView *p){ + if( p==0 ) return; + p->iLevel--; + if( p->iLevel<0 ) sqlite3_free(p); +} +/* Generate a single line of output for the tree, with a prefix that contains +** all the appropriate tree lines */ +void sqlite3TreeViewLine(TreeView *p, const char *zFormat, ...){ + va_list ap; + int i; + StrAccum acc; + char zBuf[500]; + sqlite3StrAccumInit(&acc, zBuf, sizeof(zBuf), 0); + acc.useMalloc = 0; + if( p ){ + for(i=0; iiLevel; i++){ + sqlite3StrAccumAppend(&acc, (p->mLine & (1<mLine & (1<selFlags & (SF_Distinct|SF_Aggregate) ){ - if( p->selFlags & SF_Distinct ){ - sqlite3ExplainPrintf(pVdbe, "DISTINCT "); - } - if( p->selFlags & SF_Aggregate ){ - sqlite3ExplainPrintf(pVdbe, "agg_flag "); - } - sqlite3ExplainNL(pVdbe); - sqlite3ExplainPrintf(pVdbe, " "); - } - sqlite3ExplainExprList(pVdbe, p->pEList); - sqlite3ExplainNL(pVdbe); +void sqlite3TreeViewSelect(TreeView *pView, const Select *p, u8 moreToFollow){ + pView = sqlite3TreeViewPush(pView, moreToFollow); + sqlite3TreeViewLine(pView, "SELECT%s%s", + ((p->selFlags & SF_Distinct) ? " DISTINCT" : ""), + ((p->selFlags & SF_Aggregate) ? " agg_flag" : "") + ); + sqlite3TreeViewExprList(pView, p->pEList, 1, "result-set"); if( p->pSrc && p->pSrc->nSrc ){ int i; - sqlite3ExplainPrintf(pVdbe, "FROM "); - sqlite3ExplainPush(pVdbe); + pView = sqlite3TreeViewPush(pView, 1); + sqlite3TreeViewLine(pView, "FROM"); for(i=0; ipSrc->nSrc; i++){ struct SrcList_item *pItem = &p->pSrc->a[i]; - sqlite3ExplainPrintf(pVdbe, "{%d,*} = ", pItem->iCursor); - if( pItem->pSelect ){ - sqlite3ExplainSelect(pVdbe, pItem->pSelect); - if( pItem->pTab ){ - sqlite3ExplainPrintf(pVdbe, " (tabname=%s)", pItem->pTab->zName); - } + StrAccum x; + char zLine[100]; + sqlite3StrAccumInit(&x, zLine, sizeof(zLine), 0); + sqlite3XPrintf(&x, 0, "{%d,*}", pItem->iCursor); + if( pItem->zDatabase ){ + sqlite3XPrintf(&x, 0, " %s.%s", pItem->zDatabase, pItem->zName); }else if( pItem->zName ){ - sqlite3ExplainPrintf(pVdbe, "%s", pItem->zName); + sqlite3XPrintf(&x, 0, " %s", pItem->zName); + } + if( pItem->pTab ){ + sqlite3XPrintf(&x, 0, " tabname=%Q", pItem->pTab->zName); } if( pItem->zAlias ){ - sqlite3ExplainPrintf(pVdbe, " (AS %s)", pItem->zAlias); + sqlite3XPrintf(&x, 0, " (AS %s)", pItem->zAlias); } if( pItem->jointype & JT_LEFT ){ - sqlite3ExplainPrintf(pVdbe, " LEFT-JOIN"); + sqlite3XPrintf(&x, 0, " LEFT-JOIN"); } - sqlite3ExplainNL(pVdbe); + sqlite3StrAccumFinish(&x); + sqlite3TreeViewItem(pView, zLine, ipSrc->nSrc-1); + if( pItem->pSelect ){ + sqlite3TreeViewSelect(pView, pItem->pSelect, 0); + } + sqlite3TreeViewPop(pView); } - sqlite3ExplainPop(pVdbe); + sqlite3TreeViewPop(pView); } if( p->pWhere ){ - sqlite3ExplainPrintf(pVdbe, "WHERE "); - sqlite3ExplainExpr(pVdbe, p->pWhere); - sqlite3ExplainNL(pVdbe); + sqlite3TreeViewItem(pView, "WHERE", 1); + sqlite3TreeViewExpr(pView, p->pWhere, 0); + sqlite3TreeViewPop(pView); } if( p->pGroupBy ){ - sqlite3ExplainPrintf(pVdbe, "GROUPBY "); - sqlite3ExplainExprList(pVdbe, p->pGroupBy); - sqlite3ExplainNL(pVdbe); + sqlite3TreeViewExprList(pView, p->pGroupBy, 1, "GROUPBY"); } if( p->pHaving ){ - sqlite3ExplainPrintf(pVdbe, "HAVING "); - sqlite3ExplainExpr(pVdbe, p->pHaving); - sqlite3ExplainNL(pVdbe); + sqlite3TreeViewItem(pView, "HAVING", 1); + sqlite3TreeViewExpr(pView, p->pHaving, 0); + sqlite3TreeViewPop(pView); } if( p->pOrderBy ){ - sqlite3ExplainPrintf(pVdbe, "ORDERBY "); - sqlite3ExplainExprList(pVdbe, p->pOrderBy); - sqlite3ExplainNL(pVdbe); + sqlite3TreeViewExprList(pView, p->pOrderBy, 1, "ORDERBY"); } if( p->pLimit ){ - sqlite3ExplainPrintf(pVdbe, "LIMIT "); - sqlite3ExplainExpr(pVdbe, p->pLimit); - sqlite3ExplainNL(pVdbe); + sqlite3TreeViewItem(pView, "LIMIT", 1); + sqlite3TreeViewExpr(pView, p->pLimit, 0); + sqlite3TreeViewPop(pView); } if( p->pOffset ){ - sqlite3ExplainPrintf(pVdbe, "OFFSET "); - sqlite3ExplainExpr(pVdbe, p->pOffset); - sqlite3ExplainNL(pVdbe); + sqlite3TreeViewItem(pView, "OFFSET", 1); + sqlite3TreeViewExpr(pView, p->pOffset, 0); + sqlite3TreeViewPop(pView); } + if( p->pPrior ){ + const char *zOp = "UNION"; + switch( p->op ){ + case TK_ALL: zOp = "UNION ALL"; break; + case TK_INTERSECT: zOp = "INTERSECT"; break; + case TK_EXCEPT: zOp = "EXCEPT"; break; + } + sqlite3TreeViewItem(pView, zOp, 1); + sqlite3TreeViewSelect(pView, p->pPrior, 1); + sqlite3TreeViewPop(pView); + } + sqlite3TreeViewItem(pView, "END-SELECT", 0); + sqlite3TreeViewPop(pView); + sqlite3TreeViewPop(pView); } -void sqlite3ExplainSelect(Vdbe *pVdbe, Select *p){ - if( p==0 ){ - sqlite3ExplainPrintf(pVdbe, "(null-select)"); - return; - } - sqlite3ExplainPush(pVdbe); - while( p ){ - explainOneSelect(pVdbe, p); - p = p->pNext; - if( p==0 ) break; - sqlite3ExplainNL(pVdbe); - sqlite3ExplainPrintf(pVdbe, "%s\n", selectOpName(p->op)); - } - sqlite3ExplainPrintf(pVdbe, "END"); - sqlite3ExplainPop(pVdbe); -} - -/* End of the structure debug printing code -*****************************************************************************/ -#endif /* defined(SQLITE_ENABLE_TREE_EXPLAIN) */ +#endif /* SQLITE_DEBUG */ diff --git a/src/shell.c b/src/shell.c index 9745e0ff25..cd4dadb08c 100644 --- a/src/shell.c +++ b/src/shell.c @@ -1353,15 +1353,6 @@ static int shell_exec( sqlite3_free(zEQP); } - /* Output TESTCTRL_EXPLAIN text of requested */ - if( pArg && pArg->mode==MODE_Explain ){ - const char *zExplain = 0; - sqlite3_test_control(SQLITE_TESTCTRL_EXPLAIN_STMT, pStmt, &zExplain); - if( zExplain && zExplain[0] ){ - fprintf(pArg->out, "%s", zExplain); - } - } - /* If the shell is currently in ".explain" mode, gather the extra ** data required to add indents to the output.*/ if( pArg && pArg->mode==MODE_Explain ){ diff --git a/src/sqlite.h.in b/src/sqlite.h.in index 8d7ac79ee7..ffb020058f 100644 --- a/src/sqlite.h.in +++ b/src/sqlite.h.in @@ -6205,7 +6205,7 @@ int sqlite3_test_control(int op, ...); #define SQLITE_TESTCTRL_ISKEYWORD 16 #define SQLITE_TESTCTRL_SCRATCHMALLOC 17 #define SQLITE_TESTCTRL_LOCALTIME_FAULT 18 -#define SQLITE_TESTCTRL_EXPLAIN_STMT 19 +#define SQLITE_TESTCTRL_EXPLAIN_STMT 19 /* NOT USED */ #define SQLITE_TESTCTRL_NEVER_CORRUPT 20 #define SQLITE_TESTCTRL_VDBE_COVERAGE 21 #define SQLITE_TESTCTRL_BYTEORDER 22 diff --git a/src/sqliteInt.h b/src/sqliteInt.h index b7e4d071ac..d637df782a 100644 --- a/src/sqliteInt.h +++ b/src/sqliteInt.h @@ -469,6 +469,11 @@ #define MIN(A,B) ((A)<(B)?(A):(B)) #define MAX(A,B) ((A)>(B)?(A):(B)) +/* +** Swap two objects of type TYPE. +*/ +#define SWAP(TYPE,A,B) {TYPE t=A; A=B; B=t;} + /* ** Check to see if this machine uses EBCDIC. (Yes, believe it or ** not, there are still machines out there that use EBCDIC.) @@ -855,6 +860,7 @@ typedef struct StrAccum StrAccum; typedef struct Table Table; typedef struct TableLock TableLock; typedef struct Token Token; +typedef struct TreeView TreeView; typedef struct Trigger Trigger; typedef struct TriggerPrg TriggerPrg; typedef struct TriggerStep TriggerStep; @@ -2923,6 +2929,17 @@ struct With { } a[1]; }; +#ifdef SQLITE_DEBUG +/* +** An instance of the TreeView object is used for printing the content of +** data structures on sqlite3DebugPrintf() using a tree-like view. +*/ +struct TreeView { + int iLevel; /* Which level of the tree we are on */ + u64 mLine; /* Mask of continuation lines to be drawn */ +}; +#endif /* SQLITE_DEBUG */ + /* ** Assuming zIn points to the first byte of a UTF-8 character, ** advance zIn to point to the first byte of the next UTF-8 character. @@ -3087,25 +3104,14 @@ char *sqlite3MAppendf(sqlite3*,char*,const char*,...); void *sqlite3TestTextToPtr(const char*); #endif -/* Output formatting for SQLITE_TESTCTRL_EXPLAIN */ -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) - void sqlite3ExplainBegin(Vdbe*); - void sqlite3ExplainPrintf(Vdbe*, const char*, ...); - void sqlite3ExplainNL(Vdbe*); - void sqlite3ExplainPush(Vdbe*); - void sqlite3ExplainPop(Vdbe*); - void sqlite3ExplainFinish(Vdbe*); - void sqlite3ExplainSelect(Vdbe*, Select*); - void sqlite3ExplainExpr(Vdbe*, Expr*); - void sqlite3ExplainExprList(Vdbe*, ExprList*); - const char *sqlite3VdbeExplanation(Vdbe*); -#else -# define sqlite3ExplainBegin(X) -# define sqlite3ExplainSelect(A,B) -# define sqlite3ExplainExpr(A,B) -# define sqlite3ExplainExprList(A,B) -# define sqlite3ExplainFinish(X) -# define sqlite3VdbeExplanation(X) 0 +#if defined(SQLITE_DEBUG) + TreeView *sqlite3TreeViewPush(TreeView*,u8); + void sqlite3TreeViewPop(TreeView*); + void sqlite3TreeViewLine(TreeView*, const char*, ...); + void sqlite3TreeViewItem(TreeView*, const char*, u8); + void sqlite3TreeViewExpr(TreeView*, const Expr*, u8); + void sqlite3TreeViewExprList(TreeView*, const ExprList*, u8, const char*); + void sqlite3TreeViewSelect(TreeView*, const Select*, u8); #endif @@ -3128,6 +3134,7 @@ Expr *sqlite3ExprAnd(sqlite3*,Expr*, Expr*); Expr *sqlite3ExprFunction(Parse*,ExprList*, Token*); void sqlite3ExprAssignVarNumber(Parse*, Expr*); void sqlite3ExprDelete(sqlite3*, Expr*); +void sqlite3ExprFactor(sqlite3*, Expr*, u8); ExprList *sqlite3ExprListAppend(Parse*,ExprList*,Expr*); void sqlite3ExprListSetName(Parse*,ExprList*,Token*,int); void sqlite3ExprListSetSpan(Parse*,ExprList*,ExprSpan*); diff --git a/src/vdbeInt.h b/src/vdbeInt.h index f54c9c6d3b..aa1132e31c 100644 --- a/src/vdbeInt.h +++ b/src/vdbeInt.h @@ -360,10 +360,6 @@ struct Vdbe { i64 nStmtDefImmCons; /* Number of def. imm constraints when stmt started */ char *zSql; /* Text of the SQL statement that generated this */ void *pFree; /* Free this when deleting the vdbe */ -#ifdef SQLITE_ENABLE_TREE_EXPLAIN - Explain *pExplain; /* The explainer */ - char *zExplain; /* Explanation of data structures */ -#endif VdbeFrame *pFrame; /* Parent frame */ VdbeFrame *pDelFrame; /* List of frame objects to free on VM reset */ int nFrame; /* Number of frames in pFrame list */ diff --git a/src/vdbeaux.c b/src/vdbeaux.c index 2562c63b62..33fa055369 100644 --- a/src/vdbeaux.c +++ b/src/vdbeaux.c @@ -2678,10 +2678,6 @@ void sqlite3VdbeClearObject(sqlite3 *db, Vdbe *p){ sqlite3DbFree(db, p->aColName); sqlite3DbFree(db, p->zSql); sqlite3DbFree(db, p->pFree); -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) - sqlite3DbFree(db, p->zExplain); - sqlite3DbFree(db, p->pExplain); -#endif } /* diff --git a/src/vdbetrace.c b/src/vdbetrace.c index d27693450e..507c2f12fc 100644 --- a/src/vdbetrace.c +++ b/src/vdbetrace.c @@ -183,118 +183,3 @@ char *sqlite3VdbeExpandSql( } #endif /* #ifndef SQLITE_OMIT_TRACE */ - -/***************************************************************************** -** The following code implements the data-structure explaining logic -** for the Vdbe. -*/ - -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) - -/* -** Allocate a new Explain object -*/ -void sqlite3ExplainBegin(Vdbe *pVdbe){ - if( pVdbe ){ - Explain *p; - sqlite3BeginBenignMalloc(); - p = (Explain *)sqlite3MallocZero( sizeof(Explain) ); - if( p ){ - p->pVdbe = pVdbe; - sqlite3_free(pVdbe->pExplain); - pVdbe->pExplain = p; - sqlite3StrAccumInit(&p->str, p->zBase, sizeof(p->zBase), - SQLITE_MAX_LENGTH); - p->str.useMalloc = 2; - }else{ - sqlite3EndBenignMalloc(); - } - } -} - -/* -** Return true if the Explain ends with a new-line. -*/ -static int endsWithNL(Explain *p){ - return p && p->str.zText && p->str.nChar - && p->str.zText[p->str.nChar-1]=='\n'; -} - -/* -** Append text to the indentation -*/ -void sqlite3ExplainPrintf(Vdbe *pVdbe, const char *zFormat, ...){ - Explain *p; - if( pVdbe && (p = pVdbe->pExplain)!=0 ){ - va_list ap; - if( p->nIndent && endsWithNL(p) ){ - int n = p->nIndent; - if( n>ArraySize(p->aIndent) ) n = ArraySize(p->aIndent); - sqlite3AppendSpace(&p->str, p->aIndent[n-1]); - } - va_start(ap, zFormat); - sqlite3VXPrintf(&p->str, SQLITE_PRINTF_INTERNAL, zFormat, ap); - va_end(ap); - } -} - -/* -** Append a '\n' if there is not already one. -*/ -void sqlite3ExplainNL(Vdbe *pVdbe){ - Explain *p; - if( pVdbe && (p = pVdbe->pExplain)!=0 && !endsWithNL(p) ){ - sqlite3StrAccumAppend(&p->str, "\n", 1); - } -} - -/* -** Push a new indentation level. Subsequent lines will be indented -** so that they begin at the current cursor position. -*/ -void sqlite3ExplainPush(Vdbe *pVdbe){ - Explain *p; - if( pVdbe && (p = pVdbe->pExplain)!=0 ){ - if( p->str.zText && p->nIndentaIndent) ){ - const char *z = p->str.zText; - int i = p->str.nChar-1; - int x; - while( i>=0 && z[i]!='\n' ){ i--; } - x = (p->str.nChar - 1) - i; - if( p->nIndent && xaIndent[p->nIndent-1] ){ - x = p->aIndent[p->nIndent-1]; - } - p->aIndent[p->nIndent] = x; - } - p->nIndent++; - } -} - -/* -** Pop the indentation stack by one level. -*/ -void sqlite3ExplainPop(Vdbe *p){ - if( p && p->pExplain ) p->pExplain->nIndent--; -} - -/* -** Free the indentation structure -*/ -void sqlite3ExplainFinish(Vdbe *pVdbe){ - if( pVdbe && pVdbe->pExplain ){ - sqlite3_free(pVdbe->zExplain); - sqlite3ExplainNL(pVdbe); - pVdbe->zExplain = sqlite3StrAccumFinish(&pVdbe->pExplain->str); - sqlite3_free(pVdbe->pExplain); - pVdbe->pExplain = 0; - sqlite3EndBenignMalloc(); - } -} - -/* -** Return the explanation of a virtual machine. -*/ -const char *sqlite3VdbeExplanation(Vdbe *pVdbe){ - return (pVdbe && pVdbe->zExplain) ? pVdbe->zExplain : 0; -} -#endif /* defined(SQLITE_DEBUG) */ diff --git a/src/where.c b/src/where.c index 40f95acc49..9ece59f939 100644 --- a/src/where.c +++ b/src/where.c @@ -364,11 +364,6 @@ static int allowedOp(int op){ return op==TK_IN || (op>=TK_EQ && op<=TK_GE) || op==TK_ISNULL; } -/* -** Swap two objects of type TYPE. -*/ -#define SWAP(TYPE,A,B) {TYPE t=A; A=B; B=t;} - /* ** Commute a comparison operator. Expressions of the form "X op Y" ** are converted into "Y op X". @@ -3761,22 +3756,6 @@ static Bitmask codeOneLoopStart( return pLevel->notReady; } -#if defined(WHERETRACE_ENABLED) && defined(SQLITE_ENABLE_TREE_EXPLAIN) -/* -** Generate "Explanation" text for a WhereTerm. -*/ -static void whereExplainTerm(Vdbe *v, WhereTerm *pTerm){ - char zType[4]; - memcpy(zType, "...", 4); - if( pTerm->wtFlags & TERM_VIRTUAL ) zType[0] = 'V'; - if( pTerm->eOperator & WO_EQUIV ) zType[1] = 'E'; - if( ExprHasProperty(pTerm->pExpr, EP_FromJoin) ) zType[2] = 'L'; - sqlite3ExplainPrintf(v, "%s ", zType); - sqlite3ExplainExpr(v, pTerm->pExpr); -} -#endif /* WHERETRACE_ENABLED && SQLITE_ENABLE_TREE_EXPLAIN */ - - #ifdef WHERETRACE_ENABLED /* ** Print a WhereLoop object for debugging purposes @@ -3819,27 +3798,6 @@ static void whereLoopPrint(WhereLoop *p, WhereClause *pWC){ sqlite3DebugPrintf(" f %05x N %d", p->wsFlags, p->nLTerm); } sqlite3DebugPrintf(" cost %d,%d,%d\n", p->rSetup, p->rRun, p->nOut); -#ifdef SQLITE_ENABLE_TREE_EXPLAIN - /* If the 0x100 bit of wheretracing is set, then show all of the constraint - ** expressions in the WhereLoop.aLTerm[] array. - */ - if( p->nLTerm && (sqlite3WhereTrace & 0x100)!=0 ){ /* WHERETRACE 0x100 */ - int i; - Vdbe *v = pWInfo->pParse->pVdbe; - sqlite3ExplainBegin(v); - for(i=0; inLTerm; i++){ - WhereTerm *pTerm = p->aLTerm[i]; - if( pTerm==0 ) continue; - sqlite3ExplainPrintf(v, " (%d) #%-2d ", i+1, (int)(pTerm-pWC->a)); - sqlite3ExplainPush(v); - whereExplainTerm(v, pTerm); - sqlite3ExplainPop(v); - sqlite3ExplainNL(v); - } - sqlite3ExplainFinish(v); - sqlite3DebugPrintf("%s", sqlite3VdbeExplanation(v)); - } -#endif } #endif @@ -6172,23 +6130,6 @@ WhereInfo *sqlite3WhereBegin( /* Construct the WhereLoop objects */ WHERETRACE(0xffff,("*** Optimizer Start ***\n")); - /* Display all terms of the WHERE clause */ -#if defined(WHERETRACE_ENABLED) && defined(SQLITE_ENABLE_TREE_EXPLAIN) - if( sqlite3WhereTrace & 0x100 ){ - int i; - Vdbe *v = pParse->pVdbe; - sqlite3ExplainBegin(v); - for(i=0; inTerm; i++){ - sqlite3ExplainPrintf(v, "#%-2d ", i); - sqlite3ExplainPush(v); - whereExplainTerm(v, &sWLB.pWC->a[i]); - sqlite3ExplainPop(v); - sqlite3ExplainNL(v); - } - sqlite3ExplainFinish(v); - sqlite3DebugPrintf("%s", sqlite3VdbeExplanation(v)); - } -#endif if( nTabList!=1 || whereShortCut(&sWLB)==0 ){ rc = whereLoopAddAll(&sWLB); if( rc ) goto whereBeginError; From c90713d3d2feb19ca1d4f78e679a0dcc0b0e8948 Mon Sep 17 00:00:00 2001 From: drh Date: Tue, 30 Sep 2014 13:46:49 +0000 Subject: [PATCH 05/54] Show tree diagrams of data structures in the debugging output when the 0x100 bit is set on sqlite3WhereTrace or sqlite3SelectTrace. FossilOrigin-Name: 92e0b4bd4d75e8b000586e51a07b3e181d9af20b --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/select.c | 12 +++++++++++- src/where.c | 35 +++++++++++++++++++++++++++++++++++ 4 files changed, 54 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 642f78d5ff..4ef89a6d0a 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\sthe\sSQLITE_ENABLE_TREE_EXPLAIN\scompile-time\soption.\s\sAdd\salternative\ndebugging\sdisplay\sroutines:\ssqlite3TreeViewExpr(),\ssqlite3TreeViewExprList(),\nand\ssqlite3TreeViewSelect(). -D 2014-09-30T12:33:33.546 +C Show\stree\sdiagrams\sof\sdata\sstructures\sin\sthe\sdebugging\soutput\swhen\sthe\s0x100\nbit\sis\sset\son\ssqlite3WhereTrace\sor\ssqlite3SelectTrace. +D 2014-09-30T13:46:49.195 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -227,7 +227,7 @@ F src/printf.c 0db94d24f97b4e562e9da9d2ce85e8a69531daf6 F src/random.c d10c1f85b6709ca97278428fd5db5bbb9c74eece F src/resolve.c a3466128b52a86c466e47ac1a19e2174f7b5cf89 F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e -F src/select.c 373da54c2bd7e38993bc926a284bc05a53b01b8b +F src/select.c b5304314d9456850e755a106d64b378d60c62644 F src/shell.c 38f627b0885191357f55902a3ac199de90d79715 F src/sqlite.h.in 159f2cb9eef74b6c99aeeb4c071e7745835f04f6 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 5a2c700f6f29da91ac633015d1378b91dcf237b6 +F src/where.c 5924c54986ec694e0b9e90eca506a930cfc71f6f F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1200,7 +1200,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 7fb1626866c2f8dad84c7e6184824be3efd71ca2 -R f57511c6ad57aee6db1d51feabde515b +P 4ff51325d6b41d0c59e303b573700ec80c51d216 +R 1c3af6544b324d9bf4b577de17e6b173 U drh -Z d2ed6dec33496c4977b9e22861714f01 +Z e2f1f26ff32680c40b90d9645bff7468 diff --git a/manifest.uuid b/manifest.uuid index 246f7552d4..1357a3ed6c 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -4ff51325d6b41d0c59e303b573700ec80c51d216 \ No newline at end of file +92e0b4bd4d75e8b000586e51a07b3e181d9af20b \ No newline at end of file diff --git a/src/select.c b/src/select.c index 595926fa1a..4fb3860fb3 100644 --- a/src/select.c +++ b/src/select.c @@ -3642,6 +3642,13 @@ static int flattenSubquery( */ sqlite3SelectDelete(db, pSub1); +#if SELECTTRACE_ENABLED + if( sqlite3SelectTrace & 0x100 ){ + sqlite3DebugPrintf("After flattening:\n"); + sqlite3TreeViewSelect(0, p, 0); + } +#endif + return 1; } #endif /* !defined(SQLITE_OMIT_SUBQUERY) || !defined(SQLITE_OMIT_VIEW) */ @@ -4649,7 +4656,10 @@ int sqlite3Select( memset(&sAggInfo, 0, sizeof(sAggInfo)); #if SELECTTRACE_ENABLED pParse->nSelectIndent++; - SELECTTRACE(1,pParse,p, ("begin processing\n")); + SELECTTRACE(1,pParse,p, ("begin processing:\n")); + if( sqlite3SelectTrace & 0x100 ){ + sqlite3TreeViewSelect(0, p, 0); + } #endif assert( p->pOrderBy==0 || pDest->eDest!=SRT_DistFifo ); diff --git a/src/where.c b/src/where.c index 9ece59f939..e2020ca06e 100644 --- a/src/where.c +++ b/src/where.c @@ -3756,6 +3756,23 @@ static Bitmask codeOneLoopStart( return pLevel->notReady; } +#ifdef WHERETRACE_ENABLED +/* +** Print the content of a WhereTerm object +*/ +static void whereTermPrint(WhereTerm *pTerm, int iTerm){ + char zType[4]; + memcpy(zType, "...", 4); + if( pTerm->wtFlags & TERM_VIRTUAL ) zType[0] = 'V'; + if( pTerm->eOperator & WO_EQUIV ) zType[1] = 'E'; + if( ExprHasProperty(pTerm->pExpr, EP_FromJoin) ) zType[2] = 'L'; + sqlite3DebugPrintf("TERM-%-3d %p %s cursor=%-3d prob=%-3d op=0x%03x\n", iTerm, + pTerm, zType, pTerm->leftCursor, pTerm->truthProb, + pTerm->eOperator); + sqlite3TreeViewExpr(0, pTerm->pExpr, 0); +} +#endif + #ifdef WHERETRACE_ENABLED /* ** Print a WhereLoop object for debugging purposes @@ -3798,6 +3815,14 @@ static void whereLoopPrint(WhereLoop *p, WhereClause *pWC){ sqlite3DebugPrintf(" f %05x N %d", p->wsFlags, p->nLTerm); } sqlite3DebugPrintf(" cost %d,%d,%d\n", p->rSetup, p->rRun, p->nOut); + if( p->nLTerm && (sqlite3WhereTrace & 0x100)!=0 ){ + int i; + for(i=0; inLTerm; i++){ + WhereTerm *pTerm = p->aLTerm[i]; + if( pTerm==0 ) continue; + whereTermPrint(pTerm, i); + } + } } #endif @@ -6130,6 +6155,16 @@ WhereInfo *sqlite3WhereBegin( /* Construct the WhereLoop objects */ WHERETRACE(0xffff,("*** Optimizer Start ***\n")); +#if defined(WHERETRACE_ENABLED) + /* Display all terms of the WHERE clause */ + if( sqlite3WhereTrace & 0x100 ){ + int i; + for(i=0; inTerm; i++){ + whereTermPrint(&sWLB.pWC->a[i], i); + } + } +#endif + if( nTabList!=1 || whereShortCut(&sWLB)==0 ){ rc = whereLoopAddAll(&sWLB); if( rc ) goto whereBeginError; From 5265149c0d5eed40f7a4858aeaf73776da69f78b Mon Sep 17 00:00:00 2001 From: drh Date: Tue, 30 Sep 2014 14:14:19 +0000 Subject: [PATCH 06/54] Enhanced debug output for OR-logic in the query loop optimizer. FossilOrigin-Name: 2e375eae473e4a9f2e7870d59e22ba39051ecbce --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/where.c | 6 ++++++ 3 files changed, 13 insertions(+), 7 deletions(-) diff --git a/manifest b/manifest index 4ef89a6d0a..1c128cf92e 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Show\stree\sdiagrams\sof\sdata\sstructures\sin\sthe\sdebugging\soutput\swhen\sthe\s0x100\nbit\sis\sset\son\ssqlite3WhereTrace\sor\ssqlite3SelectTrace. -D 2014-09-30T13:46:49.195 +C Enhanced\sdebug\soutput\sfor\sOR-logic\sin\sthe\squery\sloop\soptimizer. +D 2014-09-30T14:14:19.732 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 5924c54986ec694e0b9e90eca506a930cfc71f6f +F src/where.c 1d22623f4cc01ad34f4660daae77826550033c58 F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1200,7 +1200,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 4ff51325d6b41d0c59e303b573700ec80c51d216 -R 1c3af6544b324d9bf4b577de17e6b173 +P 92e0b4bd4d75e8b000586e51a07b3e181d9af20b +R ad11511f8b3c0903ec6511fb5cd0e86b U drh -Z e2f1f26ff32680c40b90d9645bff7468 +Z 55bafa322513796a5af056ecffd49293 diff --git a/manifest.uuid b/manifest.uuid index 1357a3ed6c..e80a6f2549 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -92e0b4bd4d75e8b000586e51a07b3e181d9af20b \ No newline at end of file +2e375eae473e4a9f2e7870d59e22ba39051ecbce \ No newline at end of file diff --git a/src/where.c b/src/where.c index e2020ca06e..3cde23be49 100644 --- a/src/where.c +++ b/src/where.c @@ -5037,6 +5037,12 @@ static int whereLoopAddOr(WhereLoopBuilder *pBuilder, Bitmask mExtra){ continue; } sCur.n = 0; +#ifdef WHERETRACE_ENABLED + if( sqlite3WhereTrace & 0x200 ){ + sqlite3DebugPrintf("OR-term %d:\n",(int)(pOrTerm-pOrWC->a)); + sqlite3TreeViewExpr(0, pOrTerm->pExpr, 0); + } +#endif #ifndef SQLITE_OMIT_VIRTUALTABLE if( IsVirtual(pItem->pTab) ){ rc = whereLoopAddVirtual(&sSubBuild, mExtra); From 0a99ba3bc86ceecde75b8b3b8ed8a689183d24b8 Mon Sep 17 00:00:00 2001 From: drh Date: Tue, 30 Sep 2014 17:03:35 +0000 Subject: [PATCH 07/54] Further enhancements to the "wheretrace" debugging output. FossilOrigin-Name: 670993eb8113f386cb2cb8b1507917f6da3b4d98 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/where.c | 38 +++++++++++++++++++++++--------------- 3 files changed, 30 insertions(+), 22 deletions(-) diff --git a/manifest b/manifest index 1c128cf92e..2a2a4b68cc 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Enhanced\sdebug\soutput\sfor\sOR-logic\sin\sthe\squery\sloop\soptimizer. -D 2014-09-30T14:14:19.732 +C Further\senhancements\sto\sthe\s"wheretrace"\sdebugging\soutput. +D 2014-09-30T17:03:35.868 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 1d22623f4cc01ad34f4660daae77826550033c58 +F src/where.c a459332dc671138a6997904850ead36d83bfb8e0 F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1200,7 +1200,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 92e0b4bd4d75e8b000586e51a07b3e181d9af20b -R ad11511f8b3c0903ec6511fb5cd0e86b +P 2e375eae473e4a9f2e7870d59e22ba39051ecbce +R c96a5d9652d91d70c0e54df21653ce3e U drh -Z 55bafa322513796a5af056ecffd49293 +Z 7116ce524f0c5c15e04b43bf011b61b4 diff --git a/manifest.uuid b/manifest.uuid index e80a6f2549..42170fe6be 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -2e375eae473e4a9f2e7870d59e22ba39051ecbce \ No newline at end of file +670993eb8113f386cb2cb8b1507917f6da3b4d98 \ No newline at end of file diff --git a/src/where.c b/src/where.c index 3cde23be49..bc7e58a7fe 100644 --- a/src/where.c +++ b/src/where.c @@ -3537,6 +3537,7 @@ static Bitmask codeOneLoopStart( pOrExpr = pAndExpr; } /* Loop through table entries that match term pOrTerm. */ + WHERETRACE(0xffff, ("Subplan for OR-clause:\n")); pSubWInfo = sqlite3WhereBegin(pParse, pOrTab, pOrExpr, 0, 0, wctrlFlags, iCovCur); assert( pSubWInfo || pParse->nErr || db->mallocFailed ); @@ -3761,15 +3762,19 @@ static Bitmask codeOneLoopStart( ** Print the content of a WhereTerm object */ static void whereTermPrint(WhereTerm *pTerm, int iTerm){ - char zType[4]; - memcpy(zType, "...", 4); - if( pTerm->wtFlags & TERM_VIRTUAL ) zType[0] = 'V'; - if( pTerm->eOperator & WO_EQUIV ) zType[1] = 'E'; - if( ExprHasProperty(pTerm->pExpr, EP_FromJoin) ) zType[2] = 'L'; - sqlite3DebugPrintf("TERM-%-3d %p %s cursor=%-3d prob=%-3d op=0x%03x\n", iTerm, - pTerm, zType, pTerm->leftCursor, pTerm->truthProb, - pTerm->eOperator); - sqlite3TreeViewExpr(0, pTerm->pExpr, 0); + if( pTerm==0 ){ + sqlite3DebugPrintf("TERM-%-3d NULL\n", iTerm); + }else{ + char zType[4]; + memcpy(zType, "...", 4); + if( pTerm->wtFlags & TERM_VIRTUAL ) zType[0] = 'V'; + if( pTerm->eOperator & WO_EQUIV ) zType[1] = 'E'; + if( ExprHasProperty(pTerm->pExpr, EP_FromJoin) ) zType[2] = 'L'; + sqlite3DebugPrintf("TERM-%-3d %p %s cursor=%-3d prob=%-3d op=0x%03x\n", + iTerm, pTerm, zType, pTerm->leftCursor, pTerm->truthProb, + pTerm->eOperator); + sqlite3TreeViewExpr(0, pTerm->pExpr, 0); + } } #endif @@ -3818,9 +3823,7 @@ static void whereLoopPrint(WhereLoop *p, WhereClause *pWC){ if( p->nLTerm && (sqlite3WhereTrace & 0x100)!=0 ){ int i; for(i=0; inLTerm; i++){ - WhereTerm *pTerm = p->aLTerm[i]; - if( pTerm==0 ) continue; - whereTermPrint(pTerm, i); + whereTermPrint(p->aLTerm[i], i); } } } @@ -5023,6 +5026,7 @@ static int whereLoopAddOr(WhereLoopBuilder *pBuilder, Bitmask mExtra){ sSubBuild.pOrderBy = 0; sSubBuild.pOrSet = &sCur; + WHERETRACE(0x200, ("Begin processing OR-clause %p\n", pTerm)); for(pOrTerm=pOrWC->a; pOrTermeOperator & WO_AND)!=0 ){ sSubBuild.pWC = &pOrTerm->u.pAndInfo->wc; @@ -5038,9 +5042,12 @@ static int whereLoopAddOr(WhereLoopBuilder *pBuilder, Bitmask mExtra){ } sCur.n = 0; #ifdef WHERETRACE_ENABLED - if( sqlite3WhereTrace & 0x200 ){ - sqlite3DebugPrintf("OR-term %d:\n",(int)(pOrTerm-pOrWC->a)); - sqlite3TreeViewExpr(0, pOrTerm->pExpr, 0); + WHERETRACE(0x200, ("OR-term %d of %p has %d subterms:\n", + (int)(pOrTerm-pOrWC->a), pTerm, sSubBuild.pWC->nTerm)); + if( sqlite3WhereTrace & 0x400 ){ + for(i=0; inTerm; i++){ + whereTermPrint(&sSubBuild.pWC->a[i], i); + } } #endif #ifndef SQLITE_OMIT_VIRTUALTABLE @@ -5095,6 +5102,7 @@ static int whereLoopAddOr(WhereLoopBuilder *pBuilder, Bitmask mExtra){ pNew->prereq = sSum.a[i].prereq; rc = whereLoopInsert(pBuilder, pNew); } + WHERETRACE(0x200, ("End processing OR-clause %p\n", pTerm)); } } return rc; From 36be4c49e42951cc38894244dd8b591803c6bd3f Mon Sep 17 00:00:00 2001 From: drh Date: Tue, 30 Sep 2014 17:31:23 +0000 Subject: [PATCH 08/54] Enable the query planner to deal with WHERE clauses that have OR terms nested within AND terms that are nested within OR terms. Also remove an unused function declaration. FossilOrigin-Name: b6b289182f6590288ebc7b9efbcb29b6b4480538 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/sqliteInt.h | 3 +-- src/where.c | 9 ++++++--- 4 files changed, 15 insertions(+), 13 deletions(-) diff --git a/manifest b/manifest index 2a2a4b68cc..84f200ceb8 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Further\senhancements\sto\sthe\s"wheretrace"\sdebugging\soutput. -D 2014-09-30T17:03:35.868 +C Enable\sthe\squery\splanner\sto\sdeal\swith\sWHERE\sclauses\sthat\shave\sOR\sterms\nnested\swithin\sAND\sterms\sthat\sare\snested\swithin\sOR\sterms.\s\sAlso\sremove\san\nunused\sfunction\sdeclaration. +D 2014-09-30T17:31:23.408 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -232,7 +232,7 @@ F src/shell.c 38f627b0885191357f55902a3ac199de90d79715 F src/sqlite.h.in 159f2cb9eef74b6c99aeeb4c071e7745835f04f6 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d -F src/sqliteInt.h 8242d04760ec2a943a152eba2a006ea121a3eafd +F src/sqliteInt.h 254797e62264c53184172d98a491aa2b8cd4ad88 F src/sqliteLimit.h 164b0e6749d31e0daa1a4589a169d31c0dec7b3d F src/status.c 7ac05a5c7017d0b9f0b4bcd701228b784f987158 F src/table.c 2e99ef7ef16187e17033d9398dc962ce22dab5cb @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c a459332dc671138a6997904850ead36d83bfb8e0 +F src/where.c 2f42fe0d19303e0f5ce29aff3afbd3e43cbd6efb F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1200,7 +1200,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 2e375eae473e4a9f2e7870d59e22ba39051ecbce -R c96a5d9652d91d70c0e54df21653ce3e +P 670993eb8113f386cb2cb8b1507917f6da3b4d98 +R 1a06ccbab92129ac2bab7054741ffba8 U drh -Z 7116ce524f0c5c15e04b43bf011b61b4 +Z 36668dfa98188ac65878a88086fca9b9 diff --git a/manifest.uuid b/manifest.uuid index 42170fe6be..9e6ff3561c 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -670993eb8113f386cb2cb8b1507917f6da3b4d98 \ No newline at end of file +b6b289182f6590288ebc7b9efbcb29b6b4480538 \ No newline at end of file diff --git a/src/sqliteInt.h b/src/sqliteInt.h index d637df782a..35cadcdbc0 100644 --- a/src/sqliteInt.h +++ b/src/sqliteInt.h @@ -2231,7 +2231,7 @@ struct SrcList { #define WHERE_OMIT_OPEN_CLOSE 0x0010 /* Table cursors are already open */ #define WHERE_FORCE_TABLE 0x0020 /* Do not use an index-only search */ #define WHERE_ONETABLE_ONLY 0x0040 /* Only code the 1st table in pTabList */ -#define WHERE_AND_ONLY 0x0080 /* Don't use indices for OR terms */ + /* 0x0080 // not currently used */ #define WHERE_GROUPBY 0x0100 /* pOrderBy is really a GROUP BY */ #define WHERE_DISTINCTBY 0x0200 /* pOrderby is really a DISTINCT clause */ #define WHERE_WANT_DISTINCT 0x0400 /* All output needs to be distinct */ @@ -3134,7 +3134,6 @@ Expr *sqlite3ExprAnd(sqlite3*,Expr*, Expr*); Expr *sqlite3ExprFunction(Parse*,ExprList*, Token*); void sqlite3ExprAssignVarNumber(Parse*, Expr*); void sqlite3ExprDelete(sqlite3*, Expr*); -void sqlite3ExprFactor(sqlite3*, Expr*, u8); ExprList *sqlite3ExprListAppend(Parse*,ExprList*,Expr*); void sqlite3ExprListSetName(Parse*,ExprList*,Token*,int); void sqlite3ExprListSetSpan(Parse*,ExprList*,ExprSpan*); diff --git a/src/where.c b/src/where.c index bc7e58a7fe..8974895c45 100644 --- a/src/where.c +++ b/src/where.c @@ -3524,8 +3524,9 @@ static Bitmask codeOneLoopStart( ** eliminating duplicates from other WHERE clauses, the action for each ** sub-WHERE clause is to to invoke the main loop body as a subroutine. */ - wctrlFlags = WHERE_OMIT_OPEN_CLOSE | WHERE_AND_ONLY | - WHERE_FORCE_TABLE | WHERE_ONETABLE_ONLY; + wctrlFlags = WHERE_OMIT_OPEN_CLOSE + | WHERE_FORCE_TABLE + | WHERE_ONETABLE_ONLY; for(ii=0; iinTerm; ii++){ WhereTerm *pOrTerm = &pOrWc->a[ii]; if( pOrTerm->leftCursor==iCur || (pOrTerm->eOperator & WO_AND)!=0 ){ @@ -5005,7 +5006,6 @@ static int whereLoopAddOr(WhereLoopBuilder *pBuilder, Bitmask mExtra){ struct SrcList_item *pItem; pWC = pBuilder->pWC; - if( pWInfo->wctrlFlags & WHERE_AND_ONLY ) return SQLITE_OK; pWCEnd = pWC->a + pWC->nTerm; pNew = pBuilder->pNew; memset(&sSum, 0, sizeof(sSum)); @@ -5058,6 +5058,9 @@ static int whereLoopAddOr(WhereLoopBuilder *pBuilder, Bitmask mExtra){ { rc = whereLoopAddBtree(&sSubBuild, mExtra); } + if( rc==SQLITE_OK ){ + rc = whereLoopAddOr(&sSubBuild, mExtra); + } assert( rc==SQLITE_OK || sCur.n==0 ); if( sCur.n==0 ){ sSum.n = 0; From b08cd3f34517bbb7a7cd8c745b2c51fe5bd09082 Mon Sep 17 00:00:00 2001 From: drh Date: Tue, 30 Sep 2014 19:04:41 +0000 Subject: [PATCH 09/54] Improvements to the new syntax-tree output routines: Omit the "END SELECT" mark and instead terminate the graph at the last item. Increase the maximum tree depth to 100. FossilOrigin-Name: 5ce05757aac80b99c3b2141cd301809f8e28e661 --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/printf.c | 9 ++++----- src/select.c | 31 +++++++++++++++++++------------ src/sqliteInt.h | 2 +- 5 files changed, 33 insertions(+), 27 deletions(-) diff --git a/manifest b/manifest index 84f200ceb8..4f1b85c92d 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Enable\sthe\squery\splanner\sto\sdeal\swith\sWHERE\sclauses\sthat\shave\sOR\sterms\nnested\swithin\sAND\sterms\sthat\sare\snested\swithin\sOR\sterms.\s\sAlso\sremove\san\nunused\sfunction\sdeclaration. -D 2014-09-30T17:31:23.408 +C Improvements\sto\sthe\snew\ssyntax-tree\soutput\sroutines:\s\sOmit\sthe\s"END\sSELECT"\nmark\sand\sinstead\sterminate\sthe\sgraph\sat\sthe\slast\sitem.\s\sIncrease\sthe\smaximum\ntree\sdepth\sto\s100. +D 2014-09-30T19:04:41.396 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -223,16 +223,16 @@ F src/pcache.h 9b559127b83f84ff76d735c8262f04853be0c59a F src/pcache1.c dab8ab930d4a73b99768d881185994f34b80ecaa F src/pragma.c 3f3e959390a10c0131676f0e307acce372777e0f F src/prepare.c 6ef0cf2f9274982988ed6b7cab1be23147e94196 -F src/printf.c 0db94d24f97b4e562e9da9d2ce85e8a69531daf6 +F src/printf.c 6b79bbd063dcbadca4cf617a4cde255bcc13ea64 F src/random.c d10c1f85b6709ca97278428fd5db5bbb9c74eece F src/resolve.c a3466128b52a86c466e47ac1a19e2174f7b5cf89 F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e -F src/select.c b5304314d9456850e755a106d64b378d60c62644 +F src/select.c f11533162b57ed5ed37f549add34cbcdf51f6712 F src/shell.c 38f627b0885191357f55902a3ac199de90d79715 F src/sqlite.h.in 159f2cb9eef74b6c99aeeb4c071e7745835f04f6 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d -F src/sqliteInt.h 254797e62264c53184172d98a491aa2b8cd4ad88 +F src/sqliteInt.h 5a430c5443717d7c5e2c224f9dcc2534348dc3f6 F src/sqliteLimit.h 164b0e6749d31e0daa1a4589a169d31c0dec7b3d F src/status.c 7ac05a5c7017d0b9f0b4bcd701228b784f987158 F src/table.c 2e99ef7ef16187e17033d9398dc962ce22dab5cb @@ -1200,7 +1200,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 670993eb8113f386cb2cb8b1507917f6da3b4d98 -R 1a06ccbab92129ac2bab7054741ffba8 +P b6b289182f6590288ebc7b9efbcb29b6b4480538 +R cfd4c6e5c7836f29218c39baf2122e42 U drh -Z 36668dfa98188ac65878a88086fca9b9 +Z 3bfcd52f8fd5ecba827fd0c1ccf2615c diff --git a/manifest.uuid b/manifest.uuid index 9e6ff3561c..f78de65f58 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -b6b289182f6590288ebc7b9efbcb29b6b4480538 \ No newline at end of file +5ce05757aac80b99c3b2141cd301809f8e28e661 \ No newline at end of file diff --git a/src/printf.c b/src/printf.c index 92e8e100de..c0b3c70f6b 100644 --- a/src/printf.c +++ b/src/printf.c @@ -1080,8 +1080,7 @@ TreeView *sqlite3TreeViewPush(TreeView *p, u8 moreToFollow){ p->iLevel++; } assert( moreToFollow==0 || moreToFollow==1 ); - p->mLine &= ~(1<iLevel); - p->mLine |= moreToFollow << p->iLevel; + if( p->iLevelbLine) ) p->bLine[p->iLevel] = moreToFollow; return p; } /* Finished with one layer of the tree */ @@ -1100,10 +1099,10 @@ void sqlite3TreeViewLine(TreeView *p, const char *zFormat, ...){ sqlite3StrAccumInit(&acc, zBuf, sizeof(zBuf), 0); acc.useMalloc = 0; if( p ){ - for(i=0; iiLevel; i++){ - sqlite3StrAccumAppend(&acc, (p->mLine & (1<iLevel && ibLine)-1; i++){ + sqlite3StrAccumAppend(&acc, p->bLine[i] ? "| " : " ", 4); } - sqlite3StrAccumAppend(&acc, (p->mLine & (1<bLine[i] ? "|-- " : "'-- ", 4); } va_start(ap, zFormat); sqlite3VXPrintf(&acc, 0, zFormat, ap); diff --git a/src/select.c b/src/select.c index 4fb3860fb3..411bca0df4 100644 --- a/src/select.c +++ b/src/select.c @@ -5432,15 +5432,24 @@ select_end: ** Generate a human-readable description of a the Select object. */ void sqlite3TreeViewSelect(TreeView *pView, const Select *p, u8 moreToFollow){ + int n = 0; pView = sqlite3TreeViewPush(pView, moreToFollow); sqlite3TreeViewLine(pView, "SELECT%s%s", ((p->selFlags & SF_Distinct) ? " DISTINCT" : ""), ((p->selFlags & SF_Aggregate) ? " agg_flag" : "") ); - sqlite3TreeViewExprList(pView, p->pEList, 1, "result-set"); + if( p->pSrc && p->pSrc->nSrc ) n++; + if( p->pWhere ) n++; + if( p->pGroupBy ) n++; + if( p->pHaving ) n++; + if( p->pOrderBy ) n++; + if( p->pLimit ) n++; + if( p->pOffset ) n++; + if( p->pPrior ) n++; + sqlite3TreeViewExprList(pView, p->pEList, (n--)>0, "result-set"); if( p->pSrc && p->pSrc->nSrc ){ int i; - pView = sqlite3TreeViewPush(pView, 1); + pView = sqlite3TreeViewPush(pView, (n--)>0); sqlite3TreeViewLine(pView, "FROM"); for(i=0; ipSrc->nSrc; i++){ struct SrcList_item *pItem = &p->pSrc->a[i]; @@ -5472,28 +5481,28 @@ void sqlite3TreeViewSelect(TreeView *pView, const Select *p, u8 moreToFollow){ sqlite3TreeViewPop(pView); } if( p->pWhere ){ - sqlite3TreeViewItem(pView, "WHERE", 1); + sqlite3TreeViewItem(pView, "WHERE", (n--)>0); sqlite3TreeViewExpr(pView, p->pWhere, 0); sqlite3TreeViewPop(pView); } if( p->pGroupBy ){ - sqlite3TreeViewExprList(pView, p->pGroupBy, 1, "GROUPBY"); + sqlite3TreeViewExprList(pView, p->pGroupBy, (n--)>0, "GROUPBY"); } if( p->pHaving ){ - sqlite3TreeViewItem(pView, "HAVING", 1); + sqlite3TreeViewItem(pView, "HAVING", (n--)>0); sqlite3TreeViewExpr(pView, p->pHaving, 0); sqlite3TreeViewPop(pView); } if( p->pOrderBy ){ - sqlite3TreeViewExprList(pView, p->pOrderBy, 1, "ORDERBY"); + sqlite3TreeViewExprList(pView, p->pOrderBy, (n--)>0, "ORDERBY"); } if( p->pLimit ){ - sqlite3TreeViewItem(pView, "LIMIT", 1); + sqlite3TreeViewItem(pView, "LIMIT", (n--)>0); sqlite3TreeViewExpr(pView, p->pLimit, 0); sqlite3TreeViewPop(pView); } if( p->pOffset ){ - sqlite3TreeViewItem(pView, "OFFSET", 1); + sqlite3TreeViewItem(pView, "OFFSET", (n--)>0); sqlite3TreeViewExpr(pView, p->pOffset, 0); sqlite3TreeViewPop(pView); } @@ -5504,12 +5513,10 @@ void sqlite3TreeViewSelect(TreeView *pView, const Select *p, u8 moreToFollow){ case TK_INTERSECT: zOp = "INTERSECT"; break; case TK_EXCEPT: zOp = "EXCEPT"; break; } - sqlite3TreeViewItem(pView, zOp, 1); - sqlite3TreeViewSelect(pView, p->pPrior, 1); + sqlite3TreeViewItem(pView, zOp, (n--)>0); + sqlite3TreeViewSelect(pView, p->pPrior, 0); sqlite3TreeViewPop(pView); } - sqlite3TreeViewItem(pView, "END-SELECT", 0); - sqlite3TreeViewPop(pView); sqlite3TreeViewPop(pView); } #endif /* SQLITE_DEBUG */ diff --git a/src/sqliteInt.h b/src/sqliteInt.h index 35cadcdbc0..695b63d753 100644 --- a/src/sqliteInt.h +++ b/src/sqliteInt.h @@ -2936,7 +2936,7 @@ struct With { */ struct TreeView { int iLevel; /* Which level of the tree we are on */ - u64 mLine; /* Mask of continuation lines to be drawn */ + u8 bLine[100]; /* Draw vertical in column i if bLine[i] is true */ }; #endif /* SQLITE_DEBUG */ From 9501a6451650d7dd19b616ce71a4b1fec45fdf64 Mon Sep 17 00:00:00 2001 From: dan Date: Wed, 1 Oct 2014 12:01:10 +0000 Subject: [PATCH 10/54] Avoid ever writing before the start of an allocated buffer in the DIRECT_OVERFLOW_READ code. Fix for [e3a290961a6]. FossilOrigin-Name: c3c15d20c6913811956a5041c959a56ca4eeb5eb --- manifest | 15 ++++++++------- manifest.uuid | 2 +- src/btree.c | 4 ++++ test/ovfl.test | 49 +++++++++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 62 insertions(+), 8 deletions(-) create mode 100644 test/ovfl.test diff --git a/manifest b/manifest index 4f1b85c92d..22b9dc1ea8 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Improvements\sto\sthe\snew\ssyntax-tree\soutput\sroutines:\s\sOmit\sthe\s"END\sSELECT"\nmark\sand\sinstead\sterminate\sthe\sgraph\sat\sthe\slast\sitem.\s\sIncrease\sthe\smaximum\ntree\sdepth\sto\s100. -D 2014-09-30T19:04:41.396 +C Avoid\sever\swriting\sbefore\sthe\sstart\sof\san\sallocated\sbuffer\sin\sthe\sDIRECT_OVERFLOW_READ\scode.\sFix\sfor\s[e3a290961a6]. +D 2014-10-01T12:01:10.959 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -172,7 +172,7 @@ F src/auth.c d8abcde53426275dab6243b441256fcd8ccbebb2 F src/backup.c a31809c65623cc41849b94d368917f8bb66e6a7e F src/bitvec.c 19a4ba637bd85f8f63fc8c9bae5ade9fb05ec1cb F src/btmutex.c 49ca66250c7dfa844a4d4cb8272b87420d27d3a5 -F src/btree.c ede8348a7d623257ee6c06ca4796ceaee13b8657 +F src/btree.c fa00618117fb6bb46c243452c56997c0d22d4fc9 F src/btree.h a79aa6a71e7f1055f01052b7f821bd1c2dce95c8 F src/btreeInt.h 1bd7957161a1346a914f1f09231610e777a8e58d F src/build.c bde83dd5cf812e310a7e5ad2846790a14745bef4 @@ -749,6 +749,7 @@ F test/orderby5.test 8f08a54836d21fb7c70245360751aedd1c2286fb F test/orderby6.test 8b38138ab0972588240b3fca0985d2e400432859 F test/orderby7.test 3d1383d52ade5b9eb3a173b3147fdd296f0202da F test/oserror.test 50417780d0e0d7cd23cf12a8277bb44024765df3 +F test/ovfl.test 4f7ca651cba5c059a12d8c67dddd49bec5747799 F test/pager1.test 1acbdb14c5952a72dd43129cabdbf69aaa3ed1fa F test/pager2.test 67b8f40ae98112bcdba1f2b2d03ea83266418c71 F test/pager3.test 3856d9c80839be0668efee1b74811b1b7f7fc95f @@ -1200,7 +1201,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P b6b289182f6590288ebc7b9efbcb29b6b4480538 -R cfd4c6e5c7836f29218c39baf2122e42 -U drh -Z 3bfcd52f8fd5ecba827fd0c1ccf2615c +P 5ce05757aac80b99c3b2141cd301809f8e28e661 +R 8b86b2d12e4b9100e4b861428290f6cc +U dan +Z 9b09f2a5bed05af5296fa69f0721cad2 diff --git a/manifest.uuid b/manifest.uuid index f78de65f58..8b1c98cc6b 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -5ce05757aac80b99c3b2141cd301809f8e28e661 \ No newline at end of file +c3c15d20c6913811956a5041c959a56ca4eeb5eb \ No newline at end of file diff --git a/src/btree.c b/src/btree.c index 503a2fb5d0..12dcb44cba 100644 --- a/src/btree.c +++ b/src/btree.c @@ -4022,6 +4022,7 @@ static int accessPayload( MemPage *pPage = pCur->apPage[pCur->iPage]; /* Btree page of current entry */ BtShared *pBt = pCur->pBt; /* Btree this cursor belongs to */ #ifdef SQLITE_DIRECT_OVERFLOW_READ + unsigned char * const pBufStart = pBuf; int bEnd; /* True if reading to end of data */ #endif @@ -4149,6 +4150,7 @@ static int accessPayload( ** 4) there is no open write-transaction, and ** 5) the database is not a WAL database, ** 6) all data from the page is being read. + ** 7) at least 4 bytes have already been read into the output buffer ** ** then data can be read directly from the database file into the ** output buffer, bypassing the page-cache altogether. This speeds @@ -4160,9 +4162,11 @@ static int accessPayload( && pBt->inTransaction==TRANS_READ /* (4) */ && (fd = sqlite3PagerFile(pBt->pPager))->pMethods /* (3) */ && pBt->pPage1->aData[19]==0x01 /* (5) */ + && &pBuf[-4]>=pBufStart /* (7) */ ){ u8 aSave[4]; u8 *aWrite = &pBuf[-4]; + assert( aWrite>=pBufStart ); /* hence (7) */ memcpy(aSave, aWrite, 4); rc = sqlite3OsRead(fd, aWrite, a+4, (i64)pBt->pageSize*(nextPage-1)); nextPage = get4byte(aWrite); diff --git a/test/ovfl.test b/test/ovfl.test new file mode 100644 index 0000000000..075b1e43dd --- /dev/null +++ b/test/ovfl.test @@ -0,0 +1,49 @@ +# 2014 October 01 +# +# 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 implements regression tests for SQLite library. The +# focus of this file is testing the SQLITE_DIRECT_OVERFLOW_READ logic. +# + +set testdir [file dirname $argv0] +source $testdir/tester.tcl +set testprefix ovfl + +# Populate table t2: +# +# CREATE TABLE t1(c1 TEXT, c2 TEXT); +# +# with 2000 rows. In each row, c2 spans multiple overflow pages. The text +# value of c1 ranges in size from 1 to 2000 bytes. The idea is to create +# at least one row where the first byte of c2 is also the first byte of +# an overflow page. This was at one point exposing an obscure bug in the +# SQLITE_DIRECT_OVERFLOW_READ logic. +# +do_test 1.1 { + set c2 [string repeat abcdefghij 200] + execsql { + PRAGMA cache_size = 10; + CREATE TABLE t1(c1 TEXT, c2 TEXT); + BEGIN; + } + for {set i 1} {$i <= 2000} {incr i} { + set c1 [string repeat . $i] + execsql { INSERT INTO t1 VALUES($c1, $c2) } + } + execsql COMMIT +} {} + +do_execsql_test 1.2 { + SELECT sum(length(c2)) FROM t1; +} [expr 2000 * 2000] + +finish_test + + From ccaba81e26a04e0b36c29cf6e9b3dcf44b50953e Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 1 Oct 2014 13:17:34 +0000 Subject: [PATCH 11/54] Show the TK_DOT operator in the TreeView debugging output. No changes to production code. FossilOrigin-Name: 07c89940c49a5dca3205a4b6fa8290f23bcb6e10 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/expr.c | 1 + 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 22b9dc1ea8..06559afc44 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Avoid\sever\swriting\sbefore\sthe\sstart\sof\san\sallocated\sbuffer\sin\sthe\sDIRECT_OVERFLOW_READ\scode.\sFix\sfor\s[e3a290961a6]. -D 2014-10-01T12:01:10.959 +C Show\sthe\sTK_DOT\soperator\sin\sthe\sTreeView\sdebugging\soutput.\nNo\schanges\sto\sproduction\scode. +D 2014-10-01T13:17:34.666 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -181,7 +181,7 @@ F src/complete.c 535183afb3c75628b78ce82612931ac7cdf26f14 F src/ctime.c bb434068b5308a857b181c2d204a320ff0d6c638 F src/date.c 57a7f9ba9f6b4d5268f5e411739066a611f99036 F src/delete.c fae81cc2eb14b75267d4f47d3cfc9ae02aae726f -F src/expr.c 46a8ca93361d09f2ec6d9b7d524751510569d737 +F src/expr.c fc204d08af06437ddaffe5a1b1f1f6f9e1a55d6d F src/fault.c 160a0c015b6c2629d3899ed2daf63d75754a32bb F src/fkey.c da985ae673efef2c712caef825a5d2edb087ead7 F src/func.c ba47c1671ab3cfdafa6e9d6ee490939ea578adee @@ -1201,7 +1201,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 5ce05757aac80b99c3b2141cd301809f8e28e661 -R 8b86b2d12e4b9100e4b861428290f6cc -U dan -Z 9b09f2a5bed05af5296fa69f0721cad2 +P c3c15d20c6913811956a5041c959a56ca4eeb5eb +R edd47e8e1fee70147349c2e68dee2e83 +U drh +Z 9e63ea12305cf84dbf6e1aed1e91c8fa diff --git a/manifest.uuid b/manifest.uuid index 8b1c98cc6b..b9538ddd77 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -c3c15d20c6913811956a5041c959a56ca4eeb5eb \ No newline at end of file +07c89940c49a5dca3205a4b6fa8290f23bcb6e10 \ No newline at end of file diff --git a/src/expr.c b/src/expr.c index 31ff98ea4f..1ad9a879a3 100644 --- a/src/expr.c +++ b/src/expr.c @@ -3339,6 +3339,7 @@ void sqlite3TreeViewExpr(TreeView *pView, const Expr *pExpr, u8 moreToFollow){ case TK_LSHIFT: zBinOp = "LSHIFT"; break; case TK_RSHIFT: zBinOp = "RSHIFT"; break; case TK_CONCAT: zBinOp = "CONCAT"; break; + case TK_DOT: zBinOp = "DOT"; break; case TK_UMINUS: zUniOp = "UMINUS"; break; case TK_UPLUS: zUniOp = "UPLUS"; break; From 2a3d1d17fd6007bb2ed86ed86fe38df4f9cb4804 Mon Sep 17 00:00:00 2001 From: drh Date: Thu, 2 Oct 2014 21:52:35 +0000 Subject: [PATCH 12/54] Avoid a NULL pointer deference when processing the IS operator if the right-hand side is an illegal "#ID" style variable. Fix for ticket [8c32a33a53092c85a15b] FossilOrigin-Name: ffe7573636c8057614b02f0a85559e1857fd04e4 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/parse.y | 2 +- test/expr.test | 4 ++++ 4 files changed, 13 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 06559afc44..fe8f3f84fe 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Show\sthe\sTK_DOT\soperator\sin\sthe\sTreeView\sdebugging\soutput.\nNo\schanges\sto\sproduction\scode. -D 2014-10-01T13:17:34.666 +C Avoid\sa\sNULL\spointer\sdeference\swhen\sprocessing\sthe\sIS\soperator\sif\sthe\nright-hand\sside\sis\san\sillegal\s"#ID"\sstyle\svariable.\nFix\sfor\sticket\s[8c32a33a53092c85a15b] +D 2014-10-02T21:52:35.759 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -217,7 +217,7 @@ F src/os_win.c 0a4042ef35f322e86fa01f6c8884c5e645b911e7 F src/os_win.h 09e751b20bbc107ffbd46e13555dc73576d88e21 F src/pager.c caab007743821d96752597c9cfd7351654697b06 F src/pager.h ffd5607f7b3e4590b415b007a4382f693334d428 -F src/parse.y ce1494308578d2f10a68cd8debc9fc156dda1094 +F src/parse.y 5dfead8aed90cb0c7c1115898ee2266804daff45 F src/pcache.c 4121a0571c18581ee9f82f086d5e2030051ebd6a F src/pcache.h 9b559127b83f84ff76d735c8262f04853be0c59a F src/pcache1.c dab8ab930d4a73b99768d881185994f34b80ecaa @@ -474,7 +474,7 @@ F test/exclusive.test c7ebbc756eacf544c108b15eed64d7d4e5f86b75 F test/exclusive2.test 32798111aae78a5deec980eee383213f189df308 F test/exec.test e949714dc127eaa5ecc7d723efec1ec27118fdd7 F test/exists.test 8f7b27b61c2fbe5822f0a1f899c715d14e416e30 -F test/expr.test 67c9fd6f8f829e239dc8b0f4a08a73c08b09196d +F test/expr.test c4b9bf0cc60b26862475e19999fbd2609ca8259c F test/extension01.test 00d13cec817f331a687a243e0e5a2d87b0e358c9 F test/fallocate.test 3e979af17dfa7e5e9dda5eba1a696c04fa9d47f7 F test/filectrl.test 14fa712e42c4cb791e09dfd58a6a03efb47ef13a @@ -1201,7 +1201,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P c3c15d20c6913811956a5041c959a56ca4eeb5eb -R edd47e8e1fee70147349c2e68dee2e83 +P 07c89940c49a5dca3205a4b6fa8290f23bcb6e10 +R 3ff78086c12aaca80a7d944710785692 U drh -Z 9e63ea12305cf84dbf6e1aed1e91c8fa +Z 3bce8c89e00f85ac67bad3c4bc80b65e diff --git a/manifest.uuid b/manifest.uuid index b9538ddd77..839ebd889d 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -07c89940c49a5dca3205a4b6fa8290f23bcb6e10 \ No newline at end of file +ffe7573636c8057614b02f0a85559e1857fd04e4 \ No newline at end of file diff --git a/src/parse.y b/src/parse.y index b47f531ee3..877827e68d 100644 --- a/src/parse.y +++ b/src/parse.y @@ -961,7 +961,7 @@ expr(A) ::= expr(X) NOT NULL(E). {spanUnaryPostfix(&A,pParse,TK_NOTNULL,&X,&E);} ** unary TK_ISNULL or TK_NOTNULL expression. */ static void binaryToUnaryIfNull(Parse *pParse, Expr *pY, Expr *pA, int op){ sqlite3 *db = pParse->db; - if( db->mallocFailed==0 && pY->op==TK_NULL ){ + if( pY && pA && pY->op==TK_NULL ){ pA->op = (u8)op; sqlite3ExprDelete(db, pA->pRight); pA->pRight = 0; diff --git a/test/expr.test b/test/expr.test index cc4c9c67f1..8d913d2a1a 100644 --- a/test/expr.test +++ b/test/expr.test @@ -205,6 +205,10 @@ test_expr expr-1.125 {i1=6, i2=NULL} \ test_expr expr-1.126 {i1=8, i2=8} \ {CASE WHEN i1 IS NOT i2 THEN 'yes' ELSE 'no' END} no +do_catchsql_test expr-1.127 { + SELECT 1 IS #1; +} {1 {near "#1": syntax error}} + ifcapable floatingpoint {if {[working_64bit_int]} { test_expr expr-1.200\ {i1=9223372036854775806, i2=1} {i1+i2} 9223372036854775807 From 8da47419ddf4b06ac31ad7e72e4c236d82a47765 Mon Sep 17 00:00:00 2001 From: drh Date: Fri, 3 Oct 2014 14:54:47 +0000 Subject: [PATCH 13/54] Update to requirements marks related to changes in the memory allocation interface and enhancement of the documentation regarding DEFAULT clauses in CREATE TABLE. FossilOrigin-Name: 440705b98a3429b830ea85e71cc1e414bc6d8058 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/malloc.c | 10 +++++----- test/e_createtable.test | 15 ++++++++------- 4 files changed, 21 insertions(+), 20 deletions(-) diff --git a/manifest b/manifest index fe8f3f84fe..3abf1e8c7b 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Avoid\sa\sNULL\spointer\sdeference\swhen\sprocessing\sthe\sIS\soperator\sif\sthe\nright-hand\sside\sis\san\sillegal\s"#ID"\sstyle\svariable.\nFix\sfor\sticket\s[8c32a33a53092c85a15b] -D 2014-10-02T21:52:35.759 +C Update\sto\srequirements\smarks\srelated\sto\schanges\sin\sthe\smemory\sallocation\ninterface\sand\senhancement\sof\sthe\sdocumentation\sregarding\sDEFAULT\sclauses\nin\sCREATE\sTABLE. +D 2014-10-03T14:54:47.347 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -195,7 +195,7 @@ F src/legacy.c ba1863ea58c4c840335a84ec276fc2b25e22bc4e F src/lempar.c 7274c97d24bb46631e504332ccd3bd1b37841770 F src/loadext.c de741e66e5ddc1598d904d7289239696e40ed994 F src/main.c 4a507a467cc20979579e4320ca6466b8ed0be268 -F src/malloc.c 5bb99ee1e08ad58e457063cf79ce521db0e24195 +F src/malloc.c 7cf86b4f2310898675d8a962342e5650779dfb3f F src/mem0.c 6a55ebe57c46ca1a7d98da93aaa07f99f1059645 F src/mem1.c faf615aafd8be74a71494dfa027c113ea5c6615f F src/mem2.c dce31758da87ec2cfa52ba4c5df1aed6e07d8e8f @@ -448,7 +448,7 @@ F test/descidx3.test 09ddbe3f5295f482d2f8b687cf6db8bad7acd9a2 F test/diskfull.test 106391384780753ea6896b7b4f005d10e9866b6e F test/distinct.test 086e70c765f172e8974e9f83b9ac5ca03c154e77 F test/distinctagg.test 1a6ef9c87a58669438fc771450d7a72577417376 -F test/e_createtable.test 181653f6f45e3adde73f8686600ce5ad7515466b +F test/e_createtable.test c7e67b49e6cf92473c8fb30ab26143e9e2128cf7 F test/e_delete.test d5186e2f5478b659f16a2c8b66c09892823e542a F test/e_droptrigger.test 3cd080807622c13e5bbb61fc9a57bd7754da2412 F test/e_dropview.test 0c9f7f60989164a70a67a9d9c26d1083bc808306 @@ -1201,7 +1201,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 07c89940c49a5dca3205a4b6fa8290f23bcb6e10 -R 3ff78086c12aaca80a7d944710785692 +P ffe7573636c8057614b02f0a85559e1857fd04e4 +R aa87a5e90d62a634fb6995b4f5b80a7f U drh -Z 3bce8c89e00f85ac67bad3c4bc80b65e +Z fba6f65828fcf9ec8fdba2a5c0c0fdb8 diff --git a/manifest.uuid b/manifest.uuid index 839ebd889d..4fde6cabd2 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -ffe7573636c8057614b02f0a85559e1857fd04e4 \ No newline at end of file +440705b98a3429b830ea85e71cc1e414bc6d8058 \ No newline at end of file diff --git a/src/malloc.c b/src/malloc.c index 8ba5fa0a84..7562ce2c41 100644 --- a/src/malloc.c +++ b/src/malloc.c @@ -310,7 +310,7 @@ void *sqlite3Malloc(u64 n){ }else{ p = sqlite3GlobalConfig.m.xMalloc((int)n); } - assert( EIGHT_BYTE_ALIGNMENT(p) ); /* IMP: R-04675-44850 */ + assert( EIGHT_BYTE_ALIGNMENT(p) ); /* IMP: R-11148-40995 */ return p; } @@ -533,10 +533,10 @@ void *sqlite3Realloc(void *pOld, u64 nBytes){ int nOld, nNew, nDiff; void *pNew; if( pOld==0 ){ - return sqlite3Malloc(nBytes); /* IMP: R-28354-25769 */ + return sqlite3Malloc(nBytes); /* IMP: R-04300-56712 */ } if( nBytes==0 ){ - sqlite3_free(pOld); /* IMP: R-31593-10574 */ + sqlite3_free(pOld); /* IMP: R-26507-47431 */ return 0; } if( nBytes>=0x7fffff00 ){ @@ -573,7 +573,7 @@ void *sqlite3Realloc(void *pOld, u64 nBytes){ }else{ pNew = sqlite3GlobalConfig.m.xRealloc(pOld, nNew); } - assert( EIGHT_BYTE_ALIGNMENT(pNew) ); /* IMP: R-04675-44850 */ + assert( EIGHT_BYTE_ALIGNMENT(pNew) ); /* IMP: R-11148-40995 */ return pNew; } @@ -585,7 +585,7 @@ void *sqlite3_realloc(void *pOld, int n){ #ifndef SQLITE_OMIT_AUTOINIT if( sqlite3_initialize() ) return 0; #endif - if( n<0 ) n = 0; + if( n<0 ) n = 0; /* IMP: R-26507-47431 */ return sqlite3Realloc(pOld, n); } void *sqlite3_realloc64(void *pOld, sqlite3_uint64 n){ diff --git a/test/e_createtable.test b/test/e_createtable.test index 08f606f65b..2921d86c6f 100644 --- a/test/e_createtable.test +++ b/test/e_createtable.test @@ -862,11 +862,11 @@ do_createtable_tests 3.2.3 -query { 3 "INSERT INTO t1 DEFAULT VALUES" {NULL NULL NULL} } -# EVIDENCE-OF: R-62940-43005 An explicit DEFAULT clause may specify that +# EVIDENCE-OF: R-07343-35026 An explicit DEFAULT clause may specify that # the default value is NULL, a string constant, a blob constant, a -# signed-number, or any constant expression enclosed in parentheses. An -# explicit default value may also be one of the special case-independent -# keywords CURRENT_TIME, CURRENT_DATE or CURRENT_TIMESTAMP. +# signed-number, or any constant expression enclosed in parentheses. A +# default value may also be one of the special case-independent keywords +# CURRENT_TIME, CURRENT_DATE or CURRENT_TIMESTAMP. # do_execsql_test e_createtable-3.3.1 { CREATE TABLE t4( @@ -884,9 +884,9 @@ do_execsql_test e_createtable-3.3.1 { ); } {} -# EVIDENCE-OF: R-36381-62919 For the purposes of the DEFAULT clause, an -# expression is considered constant provided that it does not contain -# any sub-queries, column or table references, or string literals +# EVIDENCE-OF: R-18415-27776 For the purposes of the DEFAULT clause, an +# expression is considered constant if it does contains no sub-queries, +# column or table references, bound parameters, or string literals # enclosed in double-quotes instead of single-quotes. # do_createtable_tests 3.4.1 -error { @@ -896,6 +896,7 @@ do_createtable_tests 3.4.1 -error { 2 {CREATE TABLE t5(x DEFAULT ( "abc" ))} {} 3 {CREATE TABLE t5(x DEFAULT ( 1 IN (SELECT 1) ))} {} 4 {CREATE TABLE t5(x DEFAULT ( EXISTS (SELECT 1) ))} {} + 5 {CREATE TABLE t5(x DEFAULT ( x!=?1 ))} {} } do_createtable_tests 3.4.2 -repair { catchsql { DROP TABLE t5 } From 79f7af9a9e16c65c5ab3947bb0358b28a7240519 Mon Sep 17 00:00:00 2001 From: drh Date: Fri, 3 Oct 2014 16:00:51 +0000 Subject: [PATCH 14/54] Add requirements marks on the sqlite3_db_status() interface implementation. Fix a typo in the documentation. Fix the new sqlite3_result_text64() routine so that it works correctly with an encoding parameter of SQLITE_UTF16. FossilOrigin-Name: d2fc322728331ae2d147c8496129df5e3c655eb5 --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/sqlite.h.in | 2 +- src/status.c | 8 +++++--- src/vdbeapi.c | 1 + 5 files changed, 16 insertions(+), 13 deletions(-) diff --git a/manifest b/manifest index 3abf1e8c7b..1c0365b036 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Update\sto\srequirements\smarks\srelated\sto\schanges\sin\sthe\smemory\sallocation\ninterface\sand\senhancement\sof\sthe\sdocumentation\sregarding\sDEFAULT\sclauses\nin\sCREATE\sTABLE. -D 2014-10-03T14:54:47.347 +C Add\srequirements\smarks\son\sthe\ssqlite3_db_status()\sinterface\simplementation.\nFix\sa\stypo\sin\sthe\sdocumentation.\s\sFix\sthe\snew\ssqlite3_result_text64()\sroutine\nso\sthat\sit\sworks\scorrectly\swith\san\sencoding\sparameter\sof\sSQLITE_UTF16. +D 2014-10-03T16:00:51.115 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -229,12 +229,12 @@ F src/resolve.c a3466128b52a86c466e47ac1a19e2174f7b5cf89 F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e F src/select.c f11533162b57ed5ed37f549add34cbcdf51f6712 F src/shell.c 38f627b0885191357f55902a3ac199de90d79715 -F src/sqlite.h.in 159f2cb9eef74b6c99aeeb4c071e7745835f04f6 +F src/sqlite.h.in a0b09ea5f73f3629c20b9788e0cde2a70f1703f5 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d F src/sqliteInt.h 5a430c5443717d7c5e2c224f9dcc2534348dc3f6 F src/sqliteLimit.h 164b0e6749d31e0daa1a4589a169d31c0dec7b3d -F src/status.c 7ac05a5c7017d0b9f0b4bcd701228b784f987158 +F src/status.c 961d5926e5a8fda611d385ec22c226b8635cd1cb F src/table.c 2e99ef7ef16187e17033d9398dc962ce22dab5cb F src/tclsqlite.c c67d310c833046cccc192125d64ad422ab882684 F src/test1.c 523cd70ded28db71af9a30ec184cbe0957de9575 @@ -292,7 +292,7 @@ F src/vacuum.c 59f03f92bcff57faa6a8ca256eb29ccddfb0614a F src/vdbe.c 93eeb6f9c3a3084133225a196f220454d71cca10 F src/vdbe.h 09f5b4e3719fa454f252322b1cdab5cf1f361327 F src/vdbeInt.h 0b97a3190f8fbf460655985a9183019f5a702754 -F src/vdbeapi.c e9e33b59834e3edc8790209765e069874c269d9d +F src/vdbeapi.c 37a6c6ae284a97bcace365f2f0a225680c0499d9 F src/vdbeaux.c 5b687d7b5beaaa5b97189edf25cf08c311834933 F src/vdbeblob.c 848238dc73e93e48432991bb5651bf87d865eca4 F src/vdbemem.c 1e105dacf5190fc85a8ec2107c0dcc1884e75099 @@ -1201,7 +1201,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P ffe7573636c8057614b02f0a85559e1857fd04e4 -R aa87a5e90d62a634fb6995b4f5b80a7f +P 440705b98a3429b830ea85e71cc1e414bc6d8058 +R 8a35df4f3d17b4f437ae0dc791626bd3 U drh -Z fba6f65828fcf9ec8fdba2a5c0c0fdb8 +Z 3c9270c816943439d7ab9b669a742153 diff --git a/manifest.uuid b/manifest.uuid index 4fde6cabd2..4d17ba50dd 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -440705b98a3429b830ea85e71cc1e414bc6d8058 \ No newline at end of file +d2fc322728331ae2d147c8496129df5e3c655eb5 \ No newline at end of file diff --git a/src/sqlite.h.in b/src/sqlite.h.in index ffb020058f..cc7bcd620e 100644 --- a/src/sqlite.h.in +++ b/src/sqlite.h.in @@ -4445,7 +4445,7 @@ typedef void (*sqlite3_destructor_type)(void*); ** of the application-defined function to be NULL. ** ** ^The sqlite3_result_text(), sqlite3_result_text16(), -** sqlite3_result_text16le(), and sqlite3_result_text16be() +** sqlite3_result_text16le(), and sqlite3_result_text16be() interfaces ** set the return value of the application-defined function to be ** a text string which is represented as UTF-8, UTF-16 native byte order, ** UTF-16 little endian, or UTF-16 big endian, respectively. diff --git a/src/status.c b/src/status.c index 5fcb68ddc3..79a8001b8a 100644 --- a/src/status.c +++ b/src/status.c @@ -213,7 +213,7 @@ int sqlite3_db_status( } db->pnBytesFreed = 0; - *pHighwater = 0; + *pHighwater = 0; /* IMP: R-64479-57858 */ *pCurrent = nByte; break; @@ -238,7 +238,9 @@ int sqlite3_db_status( sqlite3PagerCacheStat(pPager, op, resetFlag, &nRet); } } - *pHighwater = 0; + *pHighwater = 0; /* IMP: R-42420-56072 */ + /* IMP: R-54100-20147 */ + /* IMP: R-29431-39229 */ *pCurrent = nRet; break; } @@ -248,7 +250,7 @@ int sqlite3_db_status( ** have been satisfied. The *pHighwater is always set to zero. */ case SQLITE_DBSTATUS_DEFERRED_FKS: { - *pHighwater = 0; + *pHighwater = 0; /* IMP: R-11967-56545 */ *pCurrent = db->nDeferredImmCons>0 || db->nDeferredCons>0; break; } diff --git a/src/vdbeapi.c b/src/vdbeapi.c index dc38132382..0ab76e0784 100644 --- a/src/vdbeapi.c +++ b/src/vdbeapi.c @@ -318,6 +318,7 @@ void sqlite3_result_text64( ){ assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); assert( xDel!=SQLITE_DYNAMIC ); + if( enc==SQLITE_UTF16 ) enc = SQLITE_UTF16NATIVE; if( n>0x7fffffff ){ (void)invokeValueDestructor(z, xDel, pCtx); }else{ From 43085d742548e19d3a61c26c547d4dc3cf42bf36 Mon Sep 17 00:00:00 2001 From: dan Date: Fri, 3 Oct 2014 19:16:53 +0000 Subject: [PATCH 15/54] Improve the accuracy of the estimates used when searching an index for values not present in any stat4 samples under some circumstances. FossilOrigin-Name: e6f7f97dbc677c9f01b23142928c3fa7307c2fba --- manifest | 19 +++++++++-------- manifest.uuid | 2 +- src/analyze.c | 54 ++++++++++++++++++++++++++++++++++++------------- src/sqliteInt.h | 1 + 4 files changed, 53 insertions(+), 23 deletions(-) diff --git a/manifest b/manifest index 1c0365b036..f180b21817 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\srequirements\smarks\son\sthe\ssqlite3_db_status()\sinterface\simplementation.\nFix\sa\stypo\sin\sthe\sdocumentation.\s\sFix\sthe\snew\ssqlite3_result_text64()\sroutine\nso\sthat\sit\sworks\scorrectly\swith\san\sencoding\sparameter\sof\sSQLITE_UTF16. -D 2014-10-03T16:00:51.115 +C Improve\sthe\saccuracy\sof\sthe\sestimates\sused\swhen\ssearching\san\sindex\sfor\svalues\snot\spresent\sin\sany\sstat4\ssamples\sunder\ssome\scircumstances. +D 2014-10-03T19:16:53.018 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -166,7 +166,7 @@ F sqlite.pc.in 42b7bf0d02e08b9e77734a47798d1a55a9e0716b F sqlite3.1 3d8b83c91651f53472ca17599dae3457b8b89494 F sqlite3.pc.in 48fed132e7cb71ab676105d2a4dc77127d8c1f3a F src/alter.c ba266a779bc7ce10e52e59e7d3dc79fa342e8fdb -F src/analyze.c 6290a109be876daaa242cd7216f97240f5401776 +F src/analyze.c 418c2fc20cd36f1acc82456b5bd9baae77dbda78 F src/attach.c f4e94df2d1826feda65eb0939f7f6f5f923a0ad9 F src/auth.c d8abcde53426275dab6243b441256fcd8ccbebb2 F src/backup.c a31809c65623cc41849b94d368917f8bb66e6a7e @@ -232,7 +232,7 @@ F src/shell.c 38f627b0885191357f55902a3ac199de90d79715 F src/sqlite.h.in a0b09ea5f73f3629c20b9788e0cde2a70f1703f5 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d -F src/sqliteInt.h 5a430c5443717d7c5e2c224f9dcc2534348dc3f6 +F src/sqliteInt.h 3e4bd1b2288528b6a7f2d52709618572b422ab7e F src/sqliteLimit.h 164b0e6749d31e0daa1a4589a169d31c0dec7b3d F src/status.c 961d5926e5a8fda611d385ec22c226b8635cd1cb F src/table.c 2e99ef7ef16187e17033d9398dc962ce22dab5cb @@ -1201,7 +1201,10 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 440705b98a3429b830ea85e71cc1e414bc6d8058 -R 8a35df4f3d17b4f437ae0dc791626bd3 -U drh -Z 3c9270c816943439d7ab9b669a742153 +P d2fc322728331ae2d147c8496129df5e3c655eb5 +R 57c99795ca217ceed92eda9a33e89730 +T *branch * stat4-avgeq +T *sym-stat4-avgeq * +T -sym-trunk * +U dan +Z 343ac493fd77cb5d6f7bcecf2a2a97e2 diff --git a/manifest.uuid b/manifest.uuid index 4d17ba50dd..ea230c321e 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -d2fc322728331ae2d147c8496129df5e3c655eb5 \ No newline at end of file +e6f7f97dbc677c9f01b23142928c3fa7307c2fba \ No newline at end of file diff --git a/src/analyze.c b/src/analyze.c index aec1f021ea..154033d067 100644 --- a/src/analyze.c +++ b/src/analyze.c @@ -1448,12 +1448,12 @@ static void decodeIntArray( #ifdef SQLITE_ENABLE_STAT3_OR_STAT4 if( aOut ){ aOut[i] = v; - }else + } #else assert( aOut==0 ); UNUSED_PARAMETER(aOut); #endif - { + if( aLog ){ aLog[i] = sqlite3LogEst(v); } if( *z==' ' ) z++; @@ -1516,8 +1516,16 @@ static int analysisLoader(void *pData, int argc, char **argv, char **NotUsed){ z = argv[2]; if( pIndex ){ + int nCol = pIndex->nKeyCol+1; +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 + tRowcnt * const aiRowEst = pIndex->aiRowEst = (tRowcnt*)sqlite3DbMallocZero( + pInfo->db, sizeof(tRowcnt) * nCol + ); +#else + tRowcnt * const aiRowEst = 0; +#endif pIndex->bUnordered = 0; - decodeIntArray((char*)z, pIndex->nKeyCol+1, 0, pIndex->aiRowLogEst, pIndex); + decodeIntArray((char*)z, nCol, aiRowEst, pIndex->aiRowLogEst, pIndex); if( pIndex->pPartIdxWhere==0 ) pTable->nRowLogEst = pIndex->aiRowLogEst[0]; }else{ Index fakeIdx; @@ -1576,25 +1584,38 @@ static void initAvgEq(Index *pIdx){ pIdx->aAvgEq[nCol] = 1; } for(iCol=0; iColnSample; int i; /* Used to iterate through samples */ tRowcnt sumEq = 0; /* Sum of the nEq values */ - tRowcnt nSum = 0; /* Number of terms contributing to sumEq */ tRowcnt avgEq = 0; - tRowcnt nDLt = pFinal->anDLt[iCol]; + tRowcnt nRow; /* Number of rows in index */ + i64 nSum100 = 0; /* Number of terms contributing to sumEq */ + i64 nDist100; /* Number of distinct values in index */ + + if( pIdx->aiRowEst==0 ){ + nRow = pFinal->anLt[iCol]; + nDist100 = (i64)100 * pFinal->anDLt[iCol]; + nSample--; + }else{ + nRow = pIdx->aiRowEst[0]; + nDist100 = ((i64)100 * pIdx->aiRowEst[0]) / pIdx->aiRowEst[iCol+1]; + } /* Set nSum to the number of distinct (iCol+1) field prefixes that - ** occur in the stat4 table for this index before pFinal. Set - ** sumEq to the sum of the nEq values for column iCol for the same - ** set (adding the value only once where there exist duplicate - ** prefixes). */ - for(i=0; i<(pIdx->nSample-1); i++){ - if( aSample[i].anDLt[iCol]!=aSample[i+1].anDLt[iCol] ){ + ** occur in the stat4 table for this index. Set sumEq to the sum of + ** the nEq values for column iCol for the same set (adding the value + ** only once where there exist duplicate prefixes). */ + for(i=0; inSample-1) + || aSample[i].anDLt[iCol]!=aSample[i+1].anDLt[iCol] + ){ sumEq += aSample[i].anEq[iCol]; - nSum++; + nSum100 += 100; } } - if( nDLt>nSum ){ - avgEq = (pFinal->anLt[iCol] - sumEq)/(nDLt - nSum); + + if( nDist100>nSum100 ){ + avgEq = ((i64)100 * (nRow - sumEq))/(nDist100 - nSum100); } if( avgEq==0 ) avgEq = 1; pIdx->aAvgEq[iCol] = avgEq; @@ -1846,6 +1867,11 @@ int sqlite3AnalysisLoad(sqlite3 *db, int iDb){ rc = loadStat4(db, sInfo.zDatabase); db->lookaside.bEnabled = lookasideEnabled; } + for(i=sqliteHashFirst(&db->aDb[iDb].pSchema->idxHash);i;i=sqliteHashNext(i)){ + Index *pIdx = sqliteHashData(i); + sqlite3DbFree(db, pIdx->aiRowEst); + pIdx->aiRowEst = 0; + } #endif if( rc==SQLITE_NOMEM ){ diff --git a/src/sqliteInt.h b/src/sqliteInt.h index 695b63d753..74c36c8db5 100644 --- a/src/sqliteInt.h +++ b/src/sqliteInt.h @@ -1801,6 +1801,7 @@ struct Index { int nSampleCol; /* Size of IndexSample.anEq[] and so on */ tRowcnt *aAvgEq; /* Average nEq values for keys not in aSample */ IndexSample *aSample; /* Samples of the left-most key */ + tRowcnt *aiRowEst; /* Non-logarithmic stat1 data for this table */ #endif }; From 0c1a18b2944ef0a3dedfb192a90927dc69b32068 Mon Sep 17 00:00:00 2001 From: dan Date: Fri, 3 Oct 2014 19:29:39 +0000 Subject: [PATCH 16/54] Fix a division-by-zero error that might occur if the sqlite_stat1 table is corrupt. FossilOrigin-Name: f9c053b23ece877a7fdbe82204a10592f2d24a2d --- manifest | 15 ++++++--------- manifest.uuid | 2 +- src/analyze.c | 2 +- 3 files changed, 8 insertions(+), 11 deletions(-) diff --git a/manifest b/manifest index f180b21817..db1dca9628 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Improve\sthe\saccuracy\sof\sthe\sestimates\sused\swhen\ssearching\san\sindex\sfor\svalues\snot\spresent\sin\sany\sstat4\ssamples\sunder\ssome\scircumstances. -D 2014-10-03T19:16:53.018 +C Fix\sa\sdivision-by-zero\serror\sthat\smight\soccur\sif\sthe\ssqlite_stat1\stable\sis\scorrupt. +D 2014-10-03T19:29:39.807 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -166,7 +166,7 @@ F sqlite.pc.in 42b7bf0d02e08b9e77734a47798d1a55a9e0716b F sqlite3.1 3d8b83c91651f53472ca17599dae3457b8b89494 F sqlite3.pc.in 48fed132e7cb71ab676105d2a4dc77127d8c1f3a F src/alter.c ba266a779bc7ce10e52e59e7d3dc79fa342e8fdb -F src/analyze.c 418c2fc20cd36f1acc82456b5bd9baae77dbda78 +F src/analyze.c 8d5a138936dab3436e67ca3a0f6466ad2f18d86b F src/attach.c f4e94df2d1826feda65eb0939f7f6f5f923a0ad9 F src/auth.c d8abcde53426275dab6243b441256fcd8ccbebb2 F src/backup.c a31809c65623cc41849b94d368917f8bb66e6a7e @@ -1201,10 +1201,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P d2fc322728331ae2d147c8496129df5e3c655eb5 -R 57c99795ca217ceed92eda9a33e89730 -T *branch * stat4-avgeq -T *sym-stat4-avgeq * -T -sym-trunk * +P e6f7f97dbc677c9f01b23142928c3fa7307c2fba +R d767aa2120b870307998a73a73f29d86 U dan -Z 343ac493fd77cb5d6f7bcecf2a2a97e2 +Z 9bc979da9e7cfcf210fc63943ac10f56 diff --git a/manifest.uuid b/manifest.uuid index ea230c321e..662bc404af 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -e6f7f97dbc677c9f01b23142928c3fa7307c2fba \ No newline at end of file +f9c053b23ece877a7fdbe82204a10592f2d24a2d \ No newline at end of file diff --git a/src/analyze.c b/src/analyze.c index 154033d067..2f65fe3d3e 100644 --- a/src/analyze.c +++ b/src/analyze.c @@ -1592,7 +1592,7 @@ static void initAvgEq(Index *pIdx){ i64 nSum100 = 0; /* Number of terms contributing to sumEq */ i64 nDist100; /* Number of distinct values in index */ - if( pIdx->aiRowEst==0 ){ + if( pIdx->aiRowEst==0 || pIdx->aiRowEst[iCol+1]==0 ){ nRow = pFinal->anLt[iCol]; nDist100 = (i64)100 * pFinal->anDLt[iCol]; nSample--; From 75b170b16431b1b38aaf1bf64e29b8de5aec6325 Mon Sep 17 00:00:00 2001 From: drh Date: Sat, 4 Oct 2014 00:07:44 +0000 Subject: [PATCH 17/54] Avoid leaking Index.aiRowEst memory if an OOM causes a rollback which deletes the index before the aiRowEst deletion code in sqlite3AnalysisLoad() routine has a chance to run. Since the aiRowEst now might be deleted from freeIndex() which does not always have a db pointer, make sure the aiRowEst memory is not held in lookaside. FossilOrigin-Name: efd87ba142723ba131fcc985db6eb45c5a3c637b --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/analyze.c | 7 ++++--- src/build.c | 3 +++ 4 files changed, 16 insertions(+), 12 deletions(-) diff --git a/manifest b/manifest index db1dca9628..2b01d7bbcc 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sa\sdivision-by-zero\serror\sthat\smight\soccur\sif\sthe\ssqlite_stat1\stable\sis\scorrupt. -D 2014-10-03T19:29:39.807 +C Avoid\sleaking\sIndex.aiRowEst\smemory\sif\san\sOOM\scauses\sa\srollback\swhich\sdeletes\nthe\sindex\sbefore\sthe\saiRowEst\sdeletion\scode\sin\ssqlite3AnalysisLoad()\sroutine\nhas\sa\schance\sto\srun.\s\sSince\sthe\saiRowEst\snow\smight\sbe\sdeleted\sfrom\sfreeIndex()\nwhich\sdoes\snot\salways\shave\sa\sdb\spointer,\smake\ssure\sthe\saiRowEst\smemory\sis\nnot\sheld\sin\slookaside. +D 2014-10-04T00:07:44.206 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -166,7 +166,7 @@ F sqlite.pc.in 42b7bf0d02e08b9e77734a47798d1a55a9e0716b F sqlite3.1 3d8b83c91651f53472ca17599dae3457b8b89494 F sqlite3.pc.in 48fed132e7cb71ab676105d2a4dc77127d8c1f3a F src/alter.c ba266a779bc7ce10e52e59e7d3dc79fa342e8fdb -F src/analyze.c 8d5a138936dab3436e67ca3a0f6466ad2f18d86b +F src/analyze.c ee85c504829aea05489ed0c67cbcd68d6a1ea7dd F src/attach.c f4e94df2d1826feda65eb0939f7f6f5f923a0ad9 F src/auth.c d8abcde53426275dab6243b441256fcd8ccbebb2 F src/backup.c a31809c65623cc41849b94d368917f8bb66e6a7e @@ -175,7 +175,7 @@ F src/btmutex.c 49ca66250c7dfa844a4d4cb8272b87420d27d3a5 F src/btree.c fa00618117fb6bb46c243452c56997c0d22d4fc9 F src/btree.h a79aa6a71e7f1055f01052b7f821bd1c2dce95c8 F src/btreeInt.h 1bd7957161a1346a914f1f09231610e777a8e58d -F src/build.c bde83dd5cf812e310a7e5ad2846790a14745bef4 +F src/build.c 9e5205db9a0c8a1a4ce7379d60a2a34cb0b7339c F src/callback.c 7b44ce59674338ad48b0e84e7b72f935ea4f68b0 F src/complete.c 535183afb3c75628b78ce82612931ac7cdf26f14 F src/ctime.c bb434068b5308a857b181c2d204a320ff0d6c638 @@ -1201,7 +1201,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P e6f7f97dbc677c9f01b23142928c3fa7307c2fba -R d767aa2120b870307998a73a73f29d86 -U dan -Z 9bc979da9e7cfcf210fc63943ac10f56 +P f9c053b23ece877a7fdbe82204a10592f2d24a2d +R f53222c51c5cd542b15f6fc746109d5c +U drh +Z 12ba20164b8e53ca4d39b40be557570a diff --git a/manifest.uuid b/manifest.uuid index 662bc404af..e923963045 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -f9c053b23ece877a7fdbe82204a10592f2d24a2d \ No newline at end of file +efd87ba142723ba131fcc985db6eb45c5a3c637b \ No newline at end of file diff --git a/src/analyze.c b/src/analyze.c index 2f65fe3d3e..6b244dd9a7 100644 --- a/src/analyze.c +++ b/src/analyze.c @@ -1518,9 +1518,10 @@ static int analysisLoader(void *pData, int argc, char **argv, char **NotUsed){ if( pIndex ){ int nCol = pIndex->nKeyCol+1; #ifdef SQLITE_ENABLE_STAT3_OR_STAT4 - tRowcnt * const aiRowEst = pIndex->aiRowEst = (tRowcnt*)sqlite3DbMallocZero( - pInfo->db, sizeof(tRowcnt) * nCol + tRowcnt * const aiRowEst = pIndex->aiRowEst = (tRowcnt*)sqlite3MallocZero( + sizeof(tRowcnt) * nCol ); + if( aiRowEst==0 ) pInfo->db->mallocFailed = 1; #else tRowcnt * const aiRowEst = 0; #endif @@ -1869,7 +1870,7 @@ int sqlite3AnalysisLoad(sqlite3 *db, int iDb){ } for(i=sqliteHashFirst(&db->aDb[iDb].pSchema->idxHash);i;i=sqliteHashNext(i)){ Index *pIdx = sqliteHashData(i); - sqlite3DbFree(db, pIdx->aiRowEst); + sqlite3_free(pIdx->aiRowEst); pIdx->aiRowEst = 0; } #endif diff --git a/src/build.c b/src/build.c index 777831aab5..14d8aab587 100644 --- a/src/build.c +++ b/src/build.c @@ -435,6 +435,9 @@ static void freeIndex(sqlite3 *db, Index *p){ sqlite3ExprDelete(db, p->pPartIdxWhere); sqlite3DbFree(db, p->zColAff); if( p->isResized ) sqlite3DbFree(db, p->azColl); +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 + sqlite3_free(p->aiRowEst); +#endif sqlite3DbFree(db, p); } From 4ee3eb0ad482c160527260af9210f410581e6436 Mon Sep 17 00:00:00 2001 From: dan Date: Sat, 4 Oct 2014 10:22:01 +0000 Subject: [PATCH 18/54] Add a test to show that the change on this branch is effective. FossilOrigin-Name: fc619be057975b8be6d0958024c5d436edbdf084 --- manifest | 13 ++--- manifest.uuid | 2 +- test/analyzeD.test | 117 +++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 125 insertions(+), 7 deletions(-) create mode 100644 test/analyzeD.test diff --git a/manifest b/manifest index 2b01d7bbcc..7ac24e1526 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Avoid\sleaking\sIndex.aiRowEst\smemory\sif\san\sOOM\scauses\sa\srollback\swhich\sdeletes\nthe\sindex\sbefore\sthe\saiRowEst\sdeletion\scode\sin\ssqlite3AnalysisLoad()\sroutine\nhas\sa\schance\sto\srun.\s\sSince\sthe\saiRowEst\snow\smight\sbe\sdeleted\sfrom\sfreeIndex()\nwhich\sdoes\snot\salways\shave\sa\sdb\spointer,\smake\ssure\sthe\saiRowEst\smemory\sis\nnot\sheld\sin\slookaside. -D 2014-10-04T00:07:44.206 +C Add\sa\stest\sto\sshow\sthat\sthe\schange\son\sthis\sbranch\sis\seffective. +D 2014-10-04T10:22:01.856 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -326,6 +326,7 @@ F test/analyze9.test 72795c8113604b5dcd47a1498a61d6d7fb5d041a F test/analyzeA.test 3335697f6700c7052295cfd0067fc5b2aacddf9a F test/analyzeB.test 8bf35ee0a548aea831bf56762cb8e7fdb1db083d F test/analyzeC.test 555a6cc388b9818b6eda6df816f01ce0a75d3a93 +F test/analyzeD.test 08f9d0bee4e118a66fff3a32d02dbe0ee0a2b594 F test/async.test 1d0e056ba1bb9729283a0f22718d3a25e82c277b F test/async2.test c0a9bd20816d7d6a2ceca7b8c03d3d69c28ffb8b F test/async3.test d73a062002376d7edc1fe3edff493edbec1fc2f7 @@ -1201,7 +1202,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P f9c053b23ece877a7fdbe82204a10592f2d24a2d -R f53222c51c5cd542b15f6fc746109d5c -U drh -Z 12ba20164b8e53ca4d39b40be557570a +P efd87ba142723ba131fcc985db6eb45c5a3c637b +R 4172251d18757975548e0803ec5466b1 +U dan +Z d36e743f41577a93de7b943cc5387e20 diff --git a/manifest.uuid b/manifest.uuid index e923963045..cfe8277192 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -efd87ba142723ba131fcc985db6eb45c5a3c637b \ No newline at end of file +fc619be057975b8be6d0958024c5d436edbdf084 \ No newline at end of file diff --git a/test/analyzeD.test b/test/analyzeD.test new file mode 100644 index 0000000000..4d46be6c64 --- /dev/null +++ b/test/analyzeD.test @@ -0,0 +1,117 @@ +# 2005 July 22 +# +# 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 implements regression tests for SQLite library. +# This file implements tests for the ANALYZE command. +# +# $Id: analyze.test,v 1.9 2008/08/11 18:44:58 drh Exp $ + +set testdir [file dirname $argv0] +source $testdir/tester.tcl +set ::testprefix analyzeD + +ifcapable {!stat4} { + finish_test + return +} + + +# Set up a table with the following properties: +# +# * Contains 1000 rows. +# * Column a contains even integers between 0 and 18, inclusive (so that +# a=? for any such integer matches 100 rows). +# * Column b contains integers between 0 and 9, inclusive. +# * Column c contains integers between 0 and 199, inclusive (so that +# for any such integer, c=? matches 5 rows). +# * Then add 7 rows with a new value for "a" - 3001. The stat4 table will +# not contain any samples with a=3001. +# +do_execsql_test 1.0 { + CREATE TABLE t1(a, b, c); +} +do_test 1.1 { + for {set i 1} {$i < 1000} {incr i} { + set c [expr $i % 200] + execsql { INSERT INTO t1(a, b, c) VALUES( 2*($i/100), $i%10, $c ) } + } + + execsql { + INSERT INTO t1 VALUES(3001, 3001, 3001); + INSERT INTO t1 VALUES(3001, 3001, 3002); + INSERT INTO t1 VALUES(3001, 3001, 3003); + INSERT INTO t1 VALUES(3001, 3001, 3004); + INSERT INTO t1 VALUES(3001, 3001, 3005); + INSERT INTO t1 VALUES(3001, 3001, 3006); + INSERT INTO t1 VALUES(3001, 3001, 3007); + + CREATE INDEX t1_ab ON t1(a, b); + CREATE INDEX t1_c ON t1(c); + + ANALYZE; + } +} {} + +# With full ANALYZE data, SQLite sees that c=150 (5 rows) is better than +# a=3001 (7 rows). +# +do_eqp_test 1.2 { + SELECT * FROM t1 WHERE a=3001 AND c=150; +} { + 0 0 0 {SEARCH TABLE t1 USING INDEX t1_c (c=?)} +} + +do_test 1.3 { + execsql { DELETE FROM sqlite_stat1 } + db close + sqlite3 db test.db +} {} + +# Without stat1, because 3001 is larger than all samples in the stat4 +# table, SQLite things that a=3001 matches just 1 row. So it (incorrectly) +# chooses it over the c=150 index (5 rows). Even with stat1 data, things +# worked this way before commit [e6f7f97dbc]. +# +do_eqp_test 1.4 { + SELECT * FROM t1 WHERE a=3001 AND c=150; +} { + 0 0 0 {SEARCH TABLE t1 USING INDEX t1_ab (a=?)} +} + +do_test 1.5 { + execsql { + UPDATE t1 SET a=13 WHERE a = 3001; + ANALYZE; + } +} {} + +do_eqp_test 1.6 { + SELECT * FROM t1 WHERE a=13 AND c=150; +} { + 0 0 0 {SEARCH TABLE t1 USING INDEX t1_c (c=?)} +} + +do_test 1.7 { + execsql { DELETE FROM sqlite_stat1 } + db close + sqlite3 db test.db +} {} + +# Same test as 1.4, except this time the 7 rows that match the a=? condition +# do not feature larger values than all rows in the stat4 table. So SQLite +# gets this right, even without stat1 data. +do_eqp_test 1.8 { + SELECT * FROM t1 WHERE a=13 AND c=150; +} { + 0 0 0 {SEARCH TABLE t1 USING INDEX t1_c (c=?)} +} + +finish_test + From 00729cba46c0b51d5001027f139b596ab81497da Mon Sep 17 00:00:00 2001 From: drh Date: Sat, 4 Oct 2014 11:59:33 +0000 Subject: [PATCH 19/54] Updates to documentation and requirements marks. No code changes. FossilOrigin-Name: 0f8102d71a0ee828629f037775ad86fe2a544120 --- manifest | 18 +++++++++--------- manifest.uuid | 2 +- src/global.c | 7 +++++++ src/main.c | 11 +++++++++-- src/sqlite.h.in | 13 ++++++------- test/e_uri.test | 3 +++ 6 files changed, 35 insertions(+), 19 deletions(-) diff --git a/manifest b/manifest index 1c0365b036..ec8a762863 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\srequirements\smarks\son\sthe\ssqlite3_db_status()\sinterface\simplementation.\nFix\sa\stypo\sin\sthe\sdocumentation.\s\sFix\sthe\snew\ssqlite3_result_text64()\sroutine\nso\sthat\sit\sworks\scorrectly\swith\san\sencoding\sparameter\sof\sSQLITE_UTF16. -D 2014-10-03T16:00:51.115 +C Updates\sto\sdocumentation\sand\srequirements\smarks.\s\sNo\scode\schanges. +D 2014-10-04T11:59:33.912 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -185,7 +185,7 @@ F src/expr.c fc204d08af06437ddaffe5a1b1f1f6f9e1a55d6d F src/fault.c 160a0c015b6c2629d3899ed2daf63d75754a32bb F src/fkey.c da985ae673efef2c712caef825a5d2edb087ead7 F src/func.c ba47c1671ab3cfdafa6e9d6ee490939ea578adee -F src/global.c 5110fa12e09729b84eee0191c984ec4008e21937 +F src/global.c 01c1f36ecfcf10770db648422a8852c222308bb9 F src/hash.c 4263fbc955f26c2e8cdc0cf214bc42435aa4e4f5 F src/hash.h c8f3c31722cf3277d03713909761e152a5b81094 F src/hwtime.h d32741c8f4df852c7d959236615444e2b1063b08 @@ -194,7 +194,7 @@ F src/journal.c b4124532212b6952f42eb2c12fa3c25701d8ba8d F src/legacy.c ba1863ea58c4c840335a84ec276fc2b25e22bc4e F src/lempar.c 7274c97d24bb46631e504332ccd3bd1b37841770 F src/loadext.c de741e66e5ddc1598d904d7289239696e40ed994 -F src/main.c 4a507a467cc20979579e4320ca6466b8ed0be268 +F src/main.c bbe872b0ac0007bed0ebe1936fc493b039ad4f51 F src/malloc.c 7cf86b4f2310898675d8a962342e5650779dfb3f F src/mem0.c 6a55ebe57c46ca1a7d98da93aaa07f99f1059645 F src/mem1.c faf615aafd8be74a71494dfa027c113ea5c6615f @@ -229,7 +229,7 @@ F src/resolve.c a3466128b52a86c466e47ac1a19e2174f7b5cf89 F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e F src/select.c f11533162b57ed5ed37f549add34cbcdf51f6712 F src/shell.c 38f627b0885191357f55902a3ac199de90d79715 -F src/sqlite.h.in a0b09ea5f73f3629c20b9788e0cde2a70f1703f5 +F src/sqlite.h.in 7e5a6b5cce31f0b4844376566b9374fabc4985f9 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d F src/sqliteInt.h 5a430c5443717d7c5e2c224f9dcc2534348dc3f6 @@ -461,7 +461,7 @@ F test/e_resolve.test dcce9308fb13b934ce29591105d031d3e14fbba6 F test/e_select.test 52692ff3849541e828ad4661fe3773a9b8711763 F test/e_select2.test aceb80ab927d46fba5ce7586ebabf23e2bb0604f F test/e_update.test 312cb8f5ccfe41515a6bb092f8ea562a9bd54d52 -F test/e_uri.test a2c92d80093a7efdcfbb11093651cbea87097b6b +F test/e_uri.test 5ae33760fb2039c61aa2d90886f1664664173585 F test/e_vacuum.test 5bfbdc21b65c0abf24398d0ba31dc88d93ca77a9 F test/enc.test e54531cd6bf941ee6760be041dff19a104c7acea F test/enc2.test 83437a79ba1545a55fb549309175c683fb334473 @@ -1201,7 +1201,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 440705b98a3429b830ea85e71cc1e414bc6d8058 -R 8a35df4f3d17b4f437ae0dc791626bd3 +P d2fc322728331ae2d147c8496129df5e3c655eb5 +R 48a7506351fd9c89c269926766fa27eb U drh -Z 3c9270c816943439d7ab9b669a742153 +Z 0614c4bed4c215b7b30b213ff48ceb06 diff --git a/manifest.uuid b/manifest.uuid index 4d17ba50dd..de0530ba8a 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -d2fc322728331ae2d147c8496129df5e3c655eb5 \ No newline at end of file +0f8102d71a0ee828629f037775ad86fe2a544120 \ No newline at end of file diff --git a/src/global.c b/src/global.c index 22b990699b..e769eb425f 100644 --- a/src/global.c +++ b/src/global.c @@ -129,6 +129,13 @@ const unsigned char sqlite3CtypeMap[256] = { }; #endif +/* EVIDENCE-OF: R-02982-34736 In order to maintain full backwards +** compatibility for legacy applications, the URI filename capability is +** disabled by default. +** +** EVIDENCE-OF: R-38799-08373 URI filenames can be enabled or disabled +** using the SQLITE_USE_URI=1 or SQLITE_USE_URI=0 compile-time options. +*/ #ifndef SQLITE_USE_URI # define SQLITE_USE_URI 0 #endif diff --git a/src/main.c b/src/main.c index dc17917796..ea03f2639f 100644 --- a/src/main.c +++ b/src/main.c @@ -476,6 +476,11 @@ int sqlite3_config(int op, ...){ break; } + /* EVIDENCE-OF: R-55548-33817 The compile-time setting for URI filenames + ** can be changed at start-time using the + ** sqlite3_config(SQLITE_CONFIG_URI,1) or + ** sqlite3_config(SQLITE_CONFIG_URI,0) configuration calls. + */ case SQLITE_CONFIG_URI: { sqlite3GlobalConfig.bOpenUri = va_arg(ap, int); break; @@ -2213,7 +2218,7 @@ int sqlite3ParseUri( assert( *pzErrMsg==0 ); if( ((flags & SQLITE_OPEN_URI) || sqlite3GlobalConfig.bOpenUri) - && nUri>=5 && memcmp(zUri, "file:", 5)==0 + && nUri>=5 && memcmp(zUri, "file:", 5)==0 /* IMP: R-57884-37496 */ ){ char *zOpt; int eState; /* Parser state when parsing URI */ @@ -2443,7 +2448,9 @@ static int openDatabase( testcase( (1<<(flags&7))==0x02 ); /* READONLY */ testcase( (1<<(flags&7))==0x04 ); /* READWRITE */ testcase( (1<<(flags&7))==0x40 ); /* READWRITE | CREATE */ - if( ((1<<(flags&7)) & 0x46)==0 ) return SQLITE_MISUSE_BKPT; + if( ((1<<(flags&7)) & 0x46)==0 ){ + return SQLITE_MISUSE_BKPT; /* IMP: R-65497-44594 */ + } if( sqlite3GlobalConfig.bCoreMutex==0 ){ isThreadsafe = 0; diff --git a/src/sqlite.h.in b/src/sqlite.h.in index cc7bcd620e..d8e99c13e1 100644 --- a/src/sqlite.h.in +++ b/src/sqlite.h.in @@ -2754,13 +2754,14 @@ void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*); ** then it is interpreted as an absolute path. ^If the path does not begin ** with a '/' (meaning that the authority section is omitted from the URI) ** then the path is interpreted as a relative path. -** ^On windows, the first component of an absolute path -** is a drive specification (e.g. "C:"). +** ^(On windows, the first component of an absolute path +** is a drive specification (e.g. "C:").)^ ** ** [[core URI query parameters]] ** The query component of a URI may contain parameters that are interpreted ** either by SQLite itself, or by a [VFS | custom VFS implementation]. -** SQLite interprets the following three query parameters: +** SQLite and its built-in [VFSes] interpret the +** following query parameters: ** **
    **
  • vfs: ^The "vfs" parameter may be used to specify the name of @@ -2795,11 +2796,9 @@ void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*); ** a URI filename, its value overrides any behavior requested by setting ** SQLITE_OPEN_PRIVATECACHE or SQLITE_OPEN_SHAREDCACHE flag. ** -**
  • psow: ^The psow parameter may be "true" (or "on" or "yes" or -** "1") or "false" (or "off" or "no" or "0") to indicate that the +**
  • psow: ^The psow parameter indicates whether or not the ** [powersafe overwrite] property does or does not apply to the -** storage media on which the database file resides. ^The psow query -** parameter only works for the built-in unix and Windows VFSes. +** storage media on which the database file resides. ** **
  • nolock: ^The nolock parameter is a boolean query parameter ** which if set disables file locking in rollback journal modes. This diff --git a/test/e_uri.test b/test/e_uri.test index a8865cad28..d1590e4108 100644 --- a/test/e_uri.test +++ b/test/e_uri.test @@ -125,6 +125,9 @@ if {$tcl_platform(platform) == "unix"} { sqlite3_shutdown sqlite3_config_uri 1 +# EVIDENCE-OF: R-06842-00595 If the URI contains an authority, then it +# must be either an empty string or the string "localhost". +# # EVIDENCE-OF: R-17482-00398 If the authority is not an empty string or # "localhost", an error is returned to the caller. # From df868a4fbf0a0055ff3416c121c4c1ad5e675a15 Mon Sep 17 00:00:00 2001 From: drh Date: Sat, 4 Oct 2014 19:31:53 +0000 Subject: [PATCH 20/54] Tweaks to documentation on sqlite3_open() and sqlite3_bind(). No code changes. FossilOrigin-Name: b8f7f19dc06c59de2e194d83e6c052fb7d28c71d --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/sqlite.h.in | 15 +++++++-------- 3 files changed, 14 insertions(+), 15 deletions(-) diff --git a/manifest b/manifest index ec8a762863..5ed0c93fb2 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Updates\sto\sdocumentation\sand\srequirements\smarks.\s\sNo\scode\schanges. -D 2014-10-04T11:59:33.912 +C Tweaks\sto\sdocumentation\son\ssqlite3_open()\sand\ssqlite3_bind().\s\sNo\scode\schanges. +D 2014-10-04T19:31:53.403 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -229,7 +229,7 @@ F src/resolve.c a3466128b52a86c466e47ac1a19e2174f7b5cf89 F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e F src/select.c f11533162b57ed5ed37f549add34cbcdf51f6712 F src/shell.c 38f627b0885191357f55902a3ac199de90d79715 -F src/sqlite.h.in 7e5a6b5cce31f0b4844376566b9374fabc4985f9 +F src/sqlite.h.in 4a5e5158c189d2bcd45c7c4607c2c0eb6d25c153 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d F src/sqliteInt.h 5a430c5443717d7c5e2c224f9dcc2534348dc3f6 @@ -1201,7 +1201,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P d2fc322728331ae2d147c8496129df5e3c655eb5 -R 48a7506351fd9c89c269926766fa27eb +P 0f8102d71a0ee828629f037775ad86fe2a544120 +R 9fc77b39bf813ff4a1732fefd3521b90 U drh -Z 0614c4bed4c215b7b30b213ff48ceb06 +Z 7cb27b268889a7c66aa5ab31d2f83fa7 diff --git a/manifest.uuid b/manifest.uuid index de0530ba8a..4a5b1c0284 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -0f8102d71a0ee828629f037775ad86fe2a544120 \ No newline at end of file +b8f7f19dc06c59de2e194d83e6c052fb7d28c71d \ No newline at end of file diff --git a/src/sqlite.h.in b/src/sqlite.h.in index d8e99c13e1..f1d4e406e8 100644 --- a/src/sqlite.h.in +++ b/src/sqlite.h.in @@ -2664,9 +2664,9 @@ void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*); ** an English language description of the error following a failure of any ** of the sqlite3_open() routines. ** -** ^The default encoding for the database will be UTF-8 if -** sqlite3_open() or sqlite3_open_v2() is called and -** UTF-16 in the native byte order if sqlite3_open16() is used. +** ^The default encoding will be UTF-8 for databases created using +** sqlite3_open() or sqlite3_open_v2(). ^The default encoding for databases +** created using sqlite3_open16() will be UTF-16 in the native byte order. ** ** Whether or not an error occurs when it is opened, resources ** associated with the [database connection] handle should be released by @@ -3393,11 +3393,10 @@ typedef struct sqlite3_context sqlite3_context; ** contain embedded NULs. The result of expressions involving strings ** with embedded NULs is undefined. ** -** ^The fifth argument to sqlite3_bind_blob(), sqlite3_bind_text(), and -** sqlite3_bind_text16() is a destructor used to dispose of the BLOB or +** ^The fifth argument to the BLOB and string binding interfaces +** is a destructor used to dispose of the BLOB or ** string after SQLite has finished with it. ^The destructor is called -** to dispose of the BLOB or string even if the call to sqlite3_bind_blob(), -** sqlite3_bind_text(), or sqlite3_bind_text16() fails. +** to dispose of the BLOB or string even if the call to bind API fails. ** ^If the fifth argument is ** the special value [SQLITE_STATIC], then SQLite assumes that the ** information is in static, unmanaged space and does not need to be freed. @@ -3408,7 +3407,7 @@ typedef struct sqlite3_context sqlite3_context; ** ^The sixth argument to sqlite3_bind_text64() must be one of ** [SQLITE_UTF8], [SQLITE_UTF16], [SQLITE_UTF16BE], or [SQLITE_UTF16LE] ** to specify the encoding of the text in the third parameter. If -** the sixth argument to sqlite3_bind_text64() is not how of the +** the sixth argument to sqlite3_bind_text64() is not one of the ** allowed values shown above, or if the text encoding is different ** from the encoding specified by the sixth parameter, then the behavior ** is undefined. From b8e8d5055a19500a5e38e9b95fe967cb06605206 Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 6 Oct 2014 12:41:57 +0000 Subject: [PATCH 21/54] Fix a harmless compiler warning inside an assert() in FTS4. FossilOrigin-Name: 418f3c9ad28672e5fe38d772d34e7cf8d26bc0e1 --- ext/fts3/fts3.c | 2 +- manifest | 12 ++++++------ manifest.uuid | 2 +- 3 files changed, 8 insertions(+), 8 deletions(-) diff --git a/ext/fts3/fts3.c b/ext/fts3/fts3.c index 4f4b667430..582b7e27a1 100644 --- a/ext/fts3/fts3.c +++ b/ext/fts3/fts3.c @@ -4426,7 +4426,7 @@ static int fts3EvalIncrPhraseNext( bMaxSet = 1; } } - assert( rc!=SQLITE_OK || a[p->nToken-1].bIgnore==0 ); + assert( rc!=SQLITE_OK || (p->nToken>=1 && a[p->nToken-1].bIgnore==0) ); assert( rc!=SQLITE_OK || bMaxSet ); /* Keep advancing iterators until they all point to the same document */ diff --git a/manifest b/manifest index 5ed0c93fb2..e86e7242aa 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Tweaks\sto\sdocumentation\son\ssqlite3_open()\sand\ssqlite3_bind().\s\sNo\scode\schanges. -D 2014-10-04T19:31:53.403 +C Fix\sa\sharmless\scompiler\swarning\sinside\san\sassert()\sin\sFTS4. +D 2014-10-06T12:41:57.462 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -78,7 +78,7 @@ F ext/fts3/README.content fdc666a70d5257a64fee209f97cf89e0e6e32b51 F ext/fts3/README.syntax a19711dc5458c20734b8e485e75fb1981ec2427a F ext/fts3/README.tokenizers e0a8b81383ea60d0334d274fadf305ea14a8c314 F ext/fts3/README.txt 8c18f41574404623b76917b9da66fcb0ab38328d -F ext/fts3/fts3.c 2f5e925bdb9d6d3e488c5a981af60cad4f9cdfe7 +F ext/fts3/fts3.c 66f39c425fa834b939d06caeeb14f49e038d443b F ext/fts3/fts3.h 3a10a0af180d502cecc50df77b1b22df142817fe F ext/fts3/fts3Int.h 53d4eca1fb23eab00681fb028fb82eb5705c1e21 F ext/fts3/fts3_aux.c 5c211e17a64885faeb16b9ba7772f9d5445c2365 @@ -1201,7 +1201,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 0f8102d71a0ee828629f037775ad86fe2a544120 -R 9fc77b39bf813ff4a1732fefd3521b90 +P b8f7f19dc06c59de2e194d83e6c052fb7d28c71d +R 4c5bc018ecacdd56e0a0b436c7d98214 U drh -Z 7cb27b268889a7c66aa5ab31d2f83fa7 +Z bf48e2ee6f6966054d7eb786534348de diff --git a/manifest.uuid b/manifest.uuid index 4a5b1c0284..3d35e96c0c 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -b8f7f19dc06c59de2e194d83e6c052fb7d28c71d \ No newline at end of file +418f3c9ad28672e5fe38d772d34e7cf8d26bc0e1 \ No newline at end of file From 85d117bc56a04688971a4e550717cea554939492 Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 6 Oct 2014 18:33:49 +0000 Subject: [PATCH 22/54] Remove unreachable branches in decodeIntArray() when compiling without STAT3 or STAT4. FossilOrigin-Name: 80e1baa5c225c78902e08dbea9d577ff5757847f --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/analyze.c | 12 +++++------- 3 files changed, 13 insertions(+), 15 deletions(-) diff --git a/manifest b/manifest index 8a54593787..8f581e16e1 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Improve\sthe\saccuracy\sof\sthe\sestimates\sused\swhen\ssearching\san\sindex\sfor\svalues\snot\spresent\sin\sany\sstat4\ssamples. -D 2014-10-06T14:37:48.824 +C Remove\sunreachable\sbranches\sin\sdecodeIntArray()\swhen\scompiling\swithout\nSTAT3\sor\sSTAT4. +D 2014-10-06T18:33:49.122 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -166,7 +166,7 @@ F sqlite.pc.in 42b7bf0d02e08b9e77734a47798d1a55a9e0716b F sqlite3.1 3d8b83c91651f53472ca17599dae3457b8b89494 F sqlite3.pc.in 48fed132e7cb71ab676105d2a4dc77127d8c1f3a F src/alter.c ba266a779bc7ce10e52e59e7d3dc79fa342e8fdb -F src/analyze.c ee85c504829aea05489ed0c67cbcd68d6a1ea7dd +F src/analyze.c 8c322e1ecc08909526dbd5ab4421889d05f2263d F src/attach.c f4e94df2d1826feda65eb0939f7f6f5f923a0ad9 F src/auth.c d8abcde53426275dab6243b441256fcd8ccbebb2 F src/backup.c a31809c65623cc41849b94d368917f8bb66e6a7e @@ -1202,7 +1202,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 418f3c9ad28672e5fe38d772d34e7cf8d26bc0e1 fc619be057975b8be6d0958024c5d436edbdf084 -R 08d6dd1c11aa3044fd1c3c851cac54a0 -U dan -Z 0fcae61ad3d53701c4c43039d043043c +P 3aff9a9cac7aa994dfdaa0ab5c23ae73a1e820f0 +R 2a9f3a3ac6efdd67ef1666d9c29f8a31 +U drh +Z 0a50a0d9b770dc9e76964bc37ef2d3c3 diff --git a/manifest.uuid b/manifest.uuid index 3fb60d9ba8..3d0480e133 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -3aff9a9cac7aa994dfdaa0ab5c23ae73a1e820f0 \ No newline at end of file +80e1baa5c225c78902e08dbea9d577ff5757847f \ No newline at end of file diff --git a/src/analyze.c b/src/analyze.c index 6b244dd9a7..7d36f01318 100644 --- a/src/analyze.c +++ b/src/analyze.c @@ -1437,7 +1437,7 @@ static void decodeIntArray( #ifdef SQLITE_ENABLE_STAT3_OR_STAT4 if( z==0 ) z = ""; #else - if( NEVER(z==0) ) z = ""; + assert( z!=0 ); #endif for(i=0; *z && i Date: Tue, 7 Oct 2014 15:46:54 +0000 Subject: [PATCH 23/54] Enhance (and fix) the MEMTYPE tags associated with heap memory allocations when SQLITE_MEMDEBUG is used. FossilOrigin-Name: ca5b789e33c4e5ce366d8f5372d086442f84e230 --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/malloc.c | 31 ++++++++++++++++--------------- src/mem2.c | 4 ++-- src/sqliteInt.h | 3 +-- 5 files changed, 28 insertions(+), 28 deletions(-) diff --git a/manifest b/manifest index 8f581e16e1..6b9f0fa8b5 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\sunreachable\sbranches\sin\sdecodeIntArray()\swhen\scompiling\swithout\nSTAT3\sor\sSTAT4. -D 2014-10-06T18:33:49.122 +C Enhance\s(and\sfix)\sthe\sMEMTYPE\stags\sassociated\swith\sheap\smemory\sallocations\nwhen\sSQLITE_MEMDEBUG\sis\sused. +D 2014-10-07T15:46:54.844 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -195,10 +195,10 @@ F src/legacy.c ba1863ea58c4c840335a84ec276fc2b25e22bc4e F src/lempar.c 7274c97d24bb46631e504332ccd3bd1b37841770 F src/loadext.c de741e66e5ddc1598d904d7289239696e40ed994 F src/main.c bbe872b0ac0007bed0ebe1936fc493b039ad4f51 -F src/malloc.c 7cf86b4f2310898675d8a962342e5650779dfb3f +F src/malloc.c 3c3ac67969612493d435e14b6832793209afd2ec F src/mem0.c 6a55ebe57c46ca1a7d98da93aaa07f99f1059645 F src/mem1.c faf615aafd8be74a71494dfa027c113ea5c6615f -F src/mem2.c dce31758da87ec2cfa52ba4c5df1aed6e07d8e8f +F src/mem2.c f1940d9e91948dd6a908fbb9ce3835c36b5d83c3 F src/mem3.c 61c9d47b792908c532ca3a62b999cf21795c6534 F src/mem5.c 61eeb90134f9a5be6c2e68d8daae7628b25953fb F src/memjournal.c 3eb2c0b51adbd869cb6a44780323f05fa904dc85 @@ -232,7 +232,7 @@ F src/shell.c 38f627b0885191357f55902a3ac199de90d79715 F src/sqlite.h.in 4a5e5158c189d2bcd45c7c4607c2c0eb6d25c153 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d -F src/sqliteInt.h 3e4bd1b2288528b6a7f2d52709618572b422ab7e +F src/sqliteInt.h 6ac5e34a590ad7ea22af91d190bdb212b12107be F src/sqliteLimit.h 164b0e6749d31e0daa1a4589a169d31c0dec7b3d F src/status.c 961d5926e5a8fda611d385ec22c226b8635cd1cb F src/table.c 2e99ef7ef16187e17033d9398dc962ce22dab5cb @@ -1202,7 +1202,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 3aff9a9cac7aa994dfdaa0ab5c23ae73a1e820f0 -R 2a9f3a3ac6efdd67ef1666d9c29f8a31 +P 80e1baa5c225c78902e08dbea9d577ff5757847f +R feb5d8a0d69f5af350e2ea3e74be0e6b U drh -Z 0a50a0d9b770dc9e76964bc37ef2d3c3 +Z 1e9604671a765b8eca12ebcbe81357fc diff --git a/manifest.uuid b/manifest.uuid index 3d0480e133..579a427501 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -80e1baa5c225c78902e08dbea9d577ff5757847f \ No newline at end of file +ca5b789e33c4e5ce366d8f5372d086442f84e230 \ No newline at end of file diff --git a/src/malloc.c b/src/malloc.c index 7562ce2c41..6fb9d53d1b 100644 --- a/src/malloc.c +++ b/src/malloc.c @@ -447,25 +447,27 @@ static int isLookaside(sqlite3 *db, void *p){ */ int sqlite3MallocSize(void *p){ assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) ); - assert( sqlite3MemdebugNoType(p, MEMTYPE_DB) ); return sqlite3GlobalConfig.m.xSize(p); } int sqlite3DbMallocSize(sqlite3 *db, void *p){ if( db==0 ){ + assert( sqlite3MemdebugNoType(p, ~MEMTYPE_HEAP) ); + assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) ); return sqlite3MallocSize(p); }else{ assert( sqlite3_mutex_held(db->mutex) ); if( isLookaside(db, p) ){ return db->lookaside.sz; }else{ - assert( sqlite3MemdebugHasType(p, MEMTYPE_DB) ); - assert( sqlite3MemdebugHasType(p, MEMTYPE_LOOKASIDE|MEMTYPE_HEAP) ); - assert( db!=0 || sqlite3MemdebugNoType(p, MEMTYPE_LOOKASIDE) ); + assert( sqlite3MemdebugHasType(p, (MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); + assert( sqlite3MemdebugNoType(p, ~(MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); return sqlite3GlobalConfig.m.xSize(p); } } } sqlite3_uint64 sqlite3_msize(void *p){ + assert( sqlite3MemdebugNoType(p, ~MEMTYPE_HEAP) ); + assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) ); return (sqlite3_uint64)sqlite3GlobalConfig.m.xSize(p); } @@ -474,8 +476,8 @@ sqlite3_uint64 sqlite3_msize(void *p){ */ void sqlite3_free(void *p){ if( p==0 ) return; /* IMP: R-49053-54554 */ - assert( sqlite3MemdebugNoType(p, MEMTYPE_DB) ); assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) ); + assert( sqlite3MemdebugNoType(p, ~MEMTYPE_HEAP) ); if( sqlite3GlobalConfig.bMemstat ){ sqlite3_mutex_enter(mem0.mutex); sqlite3StatusAdd(SQLITE_STATUS_MEMORY_USED, -sqlite3MallocSize(p)); @@ -519,8 +521,8 @@ void sqlite3DbFree(sqlite3 *db, void *p){ return; } } - assert( sqlite3MemdebugHasType(p, MEMTYPE_DB) ); - assert( sqlite3MemdebugHasType(p, MEMTYPE_LOOKASIDE|MEMTYPE_HEAP) ); + assert( sqlite3MemdebugHasType(p, (MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); + assert( sqlite3MemdebugNoType(p, ~(MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); assert( db!=0 || sqlite3MemdebugNoType(p, MEMTYPE_LOOKASIDE) ); sqlite3MemdebugSetType(p, MEMTYPE_HEAP); sqlite3_free(p); @@ -532,6 +534,8 @@ void sqlite3DbFree(sqlite3 *db, void *p){ void *sqlite3Realloc(void *pOld, u64 nBytes){ int nOld, nNew, nDiff; void *pNew; + assert( sqlite3MemdebugHasType(pOld, MEMTYPE_HEAP) ); + assert( sqlite3MemdebugNoType(pOld, ~MEMTYPE_HEAP) ); if( pOld==0 ){ return sqlite3Malloc(nBytes); /* IMP: R-04300-56712 */ } @@ -558,8 +562,6 @@ void *sqlite3Realloc(void *pOld, u64 nBytes){ mem0.alarmThreshold-nDiff ){ sqlite3MallocAlarm(nDiff); } - assert( sqlite3MemdebugHasType(pOld, MEMTYPE_HEAP) ); - assert( sqlite3MemdebugNoType(pOld, ~MEMTYPE_HEAP) ); pNew = sqlite3GlobalConfig.m.xRealloc(pOld, nNew); if( pNew==0 && mem0.alarmCallback ){ sqlite3MallocAlarm((int)nBytes); @@ -672,8 +674,8 @@ void *sqlite3DbMallocRaw(sqlite3 *db, u64 n){ if( !p && db ){ db->mallocFailed = 1; } - sqlite3MemdebugSetType(p, MEMTYPE_DB | - ((db && db->lookaside.bEnabled) ? MEMTYPE_LOOKASIDE : MEMTYPE_HEAP)); + sqlite3MemdebugSetType(p, + (db && db->lookaside.bEnabled) ? MEMTYPE_LOOKASIDE : MEMTYPE_HEAP); return p; } @@ -699,15 +701,14 @@ void *sqlite3DbRealloc(sqlite3 *db, void *p, u64 n){ sqlite3DbFree(db, p); } }else{ - assert( sqlite3MemdebugHasType(p, MEMTYPE_DB) ); - assert( sqlite3MemdebugHasType(p, MEMTYPE_LOOKASIDE|MEMTYPE_HEAP) ); + assert( sqlite3MemdebugHasType(p, (MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); + assert( sqlite3MemdebugNoType(p, ~(MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); sqlite3MemdebugSetType(p, MEMTYPE_HEAP); pNew = sqlite3_realloc64(p, n); if( !pNew ){ - sqlite3MemdebugSetType(p, MEMTYPE_DB|MEMTYPE_HEAP); db->mallocFailed = 1; } - sqlite3MemdebugSetType(pNew, MEMTYPE_DB | + sqlite3MemdebugSetType(pNew, (db->lookaside.bEnabled ? MEMTYPE_LOOKASIDE : MEMTYPE_HEAP)); } } diff --git a/src/mem2.c b/src/mem2.c index 99ea42517e..51ea297c6a 100644 --- a/src/mem2.c +++ b/src/mem2.c @@ -394,7 +394,7 @@ void sqlite3MemdebugSetType(void *p, u8 eType){ ** This routine is designed for use within an assert() statement, to ** verify the type of an allocation. For example: ** -** assert( sqlite3MemdebugHasType(p, MEMTYPE_DB) ); +** assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) ); */ int sqlite3MemdebugHasType(void *p, u8 eType){ int rc = 1; @@ -416,7 +416,7 @@ int sqlite3MemdebugHasType(void *p, u8 eType){ ** This routine is designed for use within an assert() statement, to ** verify the type of an allocation. For example: ** -** assert( sqlite3MemdebugNoType(p, MEMTYPE_DB) ); +** assert( sqlite3MemdebugNoType(p, MEMTYPE_LOOKASIDE) ); */ int sqlite3MemdebugNoType(void *p, u8 eType){ int rc = 1; diff --git a/src/sqliteInt.h b/src/sqliteInt.h index 74c36c8db5..7998638c7f 100644 --- a/src/sqliteInt.h +++ b/src/sqliteInt.h @@ -3800,10 +3800,9 @@ SQLITE_EXTERN void (*sqlite3IoTrace)(const char*,...); # define sqlite3MemdebugNoType(X,Y) 1 #endif #define MEMTYPE_HEAP 0x01 /* General heap allocations */ -#define MEMTYPE_LOOKASIDE 0x02 /* Might have been lookaside memory */ +#define MEMTYPE_LOOKASIDE 0x02 /* Heap that might have been lookaside */ #define MEMTYPE_SCRATCH 0x04 /* Scratch allocations */ #define MEMTYPE_PCACHE 0x08 /* Page cache allocations */ -#define MEMTYPE_DB 0x10 /* Uses sqlite3DbMalloc, not sqlite_malloc */ /* ** Threading interface From 3b335fce5cf01719274718986b785fa60500b667 Mon Sep 17 00:00:00 2001 From: drh Date: Tue, 7 Oct 2014 16:59:22 +0000 Subject: [PATCH 24/54] Restrict the scope of the valueToText() routine. FossilOrigin-Name: 13c962b33df411a0d9ead0bb1969596faa286f79 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/vdbemem.c | 2 +- 3 files changed, 8 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 6b9f0fa8b5..907be1a736 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Enhance\s(and\sfix)\sthe\sMEMTYPE\stags\sassociated\swith\sheap\smemory\sallocations\nwhen\sSQLITE_MEMDEBUG\sis\sused. -D 2014-10-07T15:46:54.844 +C Restrict\sthe\sscope\sof\sthe\svalueToText()\sroutine. +D 2014-10-07T16:59:22.085 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -295,7 +295,7 @@ F src/vdbeInt.h 0b97a3190f8fbf460655985a9183019f5a702754 F src/vdbeapi.c 37a6c6ae284a97bcace365f2f0a225680c0499d9 F src/vdbeaux.c 5b687d7b5beaaa5b97189edf25cf08c311834933 F src/vdbeblob.c 848238dc73e93e48432991bb5651bf87d865eca4 -F src/vdbemem.c 1e105dacf5190fc85a8ec2107c0dcc1884e75099 +F src/vdbemem.c ee0c60af8c0f5535c6a06c49a624d87cf70b0573 F src/vdbesort.c 5c1bacf90578d22b630fbf6ed98ccf60d83435ef F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f @@ -1202,7 +1202,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 80e1baa5c225c78902e08dbea9d577ff5757847f -R feb5d8a0d69f5af350e2ea3e74be0e6b +P ca5b789e33c4e5ce366d8f5372d086442f84e230 +R 0b0659acf5a7c9ad242fd7056973fd11 U drh -Z 1e9604671a765b8eca12ebcbe81357fc +Z 23204866f7082d1eef3090df8e45b47e diff --git a/manifest.uuid b/manifest.uuid index 579a427501..43aa93cb2a 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -ca5b789e33c4e5ce366d8f5372d086442f84e230 \ No newline at end of file +13c962b33df411a0d9ead0bb1969596faa286f79 \ No newline at end of file diff --git a/src/vdbemem.c b/src/vdbemem.c index 36db80fa18..a4caf51759 100644 --- a/src/vdbemem.c +++ b/src/vdbemem.c @@ -994,7 +994,7 @@ int sqlite3VdbeMemFromBtree( ** Convert it into a string with encoding enc and return a pointer ** to a zero-terminated version of that string. */ -SQLITE_NOINLINE const void *valueToText(sqlite3_value* pVal, u8 enc){ +static SQLITE_NOINLINE const void *valueToText(sqlite3_value* pVal, u8 enc){ assert( pVal!=0 ); assert( pVal->db==0 || sqlite3_mutex_held(pVal->db->mutex) ); assert( (enc&3)==(enc&~SQLITE_UTF16_ALIGNED) ); From 89a5833cb9a6c9be11b244d4ed6d3fe89b6f47d0 Mon Sep 17 00:00:00 2001 From: drh Date: Tue, 7 Oct 2014 20:09:27 +0000 Subject: [PATCH 25/54] Fix the corruptI.test script so that it works with SQLITE_ENABLE_OVERSIZE_CELL_CHECK and with SQLITE_DEFAULT_AUTOVACUUM=1. FossilOrigin-Name: e405b9e4a9ef322d84b20e902234b4f6aa196b1b --- manifest | 12 +++++----- manifest.uuid | 2 +- test/corruptI.test | 57 ++++++++++++++++++++++++---------------------- 3 files changed, 37 insertions(+), 34 deletions(-) diff --git a/manifest b/manifest index 907be1a736..433a723055 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Restrict\sthe\sscope\sof\sthe\svalueToText()\sroutine. -D 2014-10-07T16:59:22.085 +C Fix\sthe\scorruptI.test\sscript\sso\sthat\sit\sworks\swith\nSQLITE_ENABLE_OVERSIZE_CELL_CHECK\sand\swith\sSQLITE_DEFAULT_AUTOVACUUM=1. +D 2014-10-07T20:09:27.561 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -420,7 +420,7 @@ F test/corruptE.test 193b4ca4e927e77c1d5f4f56203ddc998432a7ee F test/corruptF.test be9fde98e4c93648f1ba52b74e5318edc8f59fe4 F test/corruptG.test 1ab3bf97ee7bdba70e0ff3ba2320657df55d1804 F test/corruptH.test 88ed71a086e13591c917aac6de32750e7c7281cb -F test/corruptI.test 0afbba50bfae006094cc548b4605f521c1179502 +F test/corruptI.test 221ad8b7f0a9ac6b80fc577e73b5ad8cdea31243 F test/cost.test 19d314526616ce4473eb4e4e450fcb94499ce318 F test/count.test 42a251178e32f617eda33f76236a7f79825a50b5 F test/coveridxscan.test cdb47d01acc4a634a34fd25abe85189e0d0f1e62 @@ -1202,7 +1202,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P ca5b789e33c4e5ce366d8f5372d086442f84e230 -R 0b0659acf5a7c9ad242fd7056973fd11 +P 13c962b33df411a0d9ead0bb1969596faa286f79 +R bc98a778a72f51d6ea08f3f2bdc76392 U drh -Z 23204866f7082d1eef3090df8e45b47e +Z 156ceab5010f208eb433cfa9f4253059 diff --git a/manifest.uuid b/manifest.uuid index 43aa93cb2a..d79d2fd138 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -13c962b33df411a0d9ead0bb1969596faa286f79 \ No newline at end of file +e405b9e4a9ef322d84b20e902234b4f6aa196b1b \ No newline at end of file diff --git a/test/corruptI.test b/test/corruptI.test index 41200c5409..c8d0176236 100644 --- a/test/corruptI.test +++ b/test/corruptI.test @@ -75,31 +75,34 @@ do_test 2.2 { catchsql { SELECT * FROM r WHERE x >= 10 } } {1 {database disk image is malformed}} -reset_db - -do_execsql_test 3.1 { - PRAGMA page_size = 512; - CREATE TABLE t1(a INTEGER PRIMARY KEY, b); - WITH s(a, b) AS ( - SELECT 2, 'abcdefghij' - UNION ALL - SELECT a+2, b FROM s WHERe a < 40 - ) - INSERT INTO t1 SELECT * FROM s; -} {} - -do_test 3.2 { - hexio_write test.db [expr 512+3] 0054 - db close - sqlite3 db test.db - execsql { INSERT INTO t1 VALUES(5, 'klmnopqrst') } - execsql { INSERT INTO t1 VALUES(7, 'klmnopqrst') } -} {} - -db close -sqlite3 db test.db -do_catchsql_test 3.2 { - INSERT INTO t1 VALUES(9, 'klmnopqrst'); -} {1 {database disk image is malformed}} - +if {[db one {SELECT sqlite_compileoption_used('ENABLE_OVERSIZE_CELL_CHECK')}]} { + # The following tests only work if OVERSIZE_CELL_CHECK is disabled +} else { + reset_db + do_execsql_test 3.1 { + PRAGMA auto_vacuum=0; + PRAGMA page_size = 512; + CREATE TABLE t1(a INTEGER PRIMARY KEY, b); + WITH s(a, b) AS ( + SELECT 2, 'abcdefghij' + UNION ALL + SELECT a+2, b FROM s WHERe a < 40 + ) + INSERT INTO t1 SELECT * FROM s; + } {} + + do_test 3.2 { + hexio_write test.db [expr 512+3] 0054 + db close + sqlite3 db test.db + execsql { INSERT INTO t1 VALUES(5, 'klmnopqrst') } + execsql { INSERT INTO t1 VALUES(7, 'klmnopqrst') } + } {} + + db close + sqlite3 db test.db + do_catchsql_test 3.3 { + INSERT INTO t1 VALUES(9, 'klmnopqrst'); + } {1 {database disk image is malformed}} +} ;# end-if !defined(ENABLE_OVERSIZE_CELL_CHECK) finish_test From 722246e801299ea9042db1278ab6365384d72e22 Mon Sep 17 00:00:00 2001 From: drh Date: Tue, 7 Oct 2014 23:02:24 +0000 Subject: [PATCH 26/54] Make sure the sqlite3VdbeMemClearAndResize() routine is never called with a zero size parameter, since a size of zero could lead to either a memory leak or an assertion fault. FossilOrigin-Name: f672a380e2e52bede95ff11a533fd9f7d412d494 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/vdbe.c | 3 ++- src/vdbemem.c | 13 ++++++++++--- 4 files changed, 20 insertions(+), 12 deletions(-) diff --git a/manifest b/manifest index 433a723055..8b6acbd4de 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sthe\scorruptI.test\sscript\sso\sthat\sit\sworks\swith\nSQLITE_ENABLE_OVERSIZE_CELL_CHECK\sand\swith\sSQLITE_DEFAULT_AUTOVACUUM=1. -D 2014-10-07T20:09:27.561 +C Make\ssure\sthe\ssqlite3VdbeMemClearAndResize()\sroutine\sis\snever\scalled\swith\sa\nzero\ssize\sparameter,\ssince\sa\ssize\sof\szero\scould\slead\sto\seither\sa\smemory\sleak\nor\san\sassertion\sfault. +D 2014-10-07T23:02:24.724 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -289,13 +289,13 @@ F src/update.c 729f6f18fc27740591d085e1172cebe311144bf0 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 4006c01772bd8d8ac4306d523bbcee41d3e392d8 F src/vacuum.c 59f03f92bcff57faa6a8ca256eb29ccddfb0614a -F src/vdbe.c 93eeb6f9c3a3084133225a196f220454d71cca10 +F src/vdbe.c e6c964101382d6fb144853b1d5b288158a9aba0e F src/vdbe.h 09f5b4e3719fa454f252322b1cdab5cf1f361327 F src/vdbeInt.h 0b97a3190f8fbf460655985a9183019f5a702754 F src/vdbeapi.c 37a6c6ae284a97bcace365f2f0a225680c0499d9 F src/vdbeaux.c 5b687d7b5beaaa5b97189edf25cf08c311834933 F src/vdbeblob.c 848238dc73e93e48432991bb5651bf87d865eca4 -F src/vdbemem.c ee0c60af8c0f5535c6a06c49a624d87cf70b0573 +F src/vdbemem.c 481327f50d9da330053aa7456702ce46d0a4e70f F src/vdbesort.c 5c1bacf90578d22b630fbf6ed98ccf60d83435ef F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f @@ -1202,7 +1202,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 13c962b33df411a0d9ead0bb1969596faa286f79 -R bc98a778a72f51d6ea08f3f2bdc76392 +P e405b9e4a9ef322d84b20e902234b4f6aa196b1b +R 59a3e15d0b7c925a5c413304ec5e314b U drh -Z 156ceab5010f208eb433cfa9f4253059 +Z 1de6834c7b78df261ad24af6ce5dedbe diff --git a/manifest.uuid b/manifest.uuid index d79d2fd138..169d9b9887 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -e405b9e4a9ef322d84b20e902234b4f6aa196b1b \ No newline at end of file +f672a380e2e52bede95ff11a533fd9f7d412d494 \ No newline at end of file diff --git a/src/vdbe.c b/src/vdbe.c index 34eb1d42c5..18e1cd83a9 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -4333,7 +4333,8 @@ case OP_RowData: { goto too_big; } } - if( sqlite3VdbeMemClearAndResize(pOut, n) ){ + testcase( n==0 ); + if( sqlite3VdbeMemClearAndResize(pOut, MAX(n,32)) ){ goto no_mem; } pOut->n = n; diff --git a/src/vdbemem.c b/src/vdbemem.c index a4caf51759..0c62db0720 100644 --- a/src/vdbemem.c +++ b/src/vdbemem.c @@ -31,7 +31,10 @@ int sqlite3VdbeCheckMemInvariants(Mem *p){ */ assert( (p->flags & MEM_Dyn)==0 || p->xDel!=0 ); - /* MEM_Dyn may only be set if Mem.szMalloc==0 */ + /* MEM_Dyn may only be set if Mem.szMalloc==0. In this way we + ** ensure that if Mem.szMalloc>0 then it is safe to do + ** Mem.z = Mem.zMalloc without having to check Mem.flags&MEM_Dyn. + ** That saves a few cycles in inner loops. */ assert( (p->flags & MEM_Dyn)==0 || p->szMalloc==0 ); /* Cannot be both MEM_Int and MEM_Real at the same time */ @@ -167,7 +170,8 @@ SQLITE_NOINLINE int sqlite3VdbeMemGrow(Mem *pMem, int n, int bPreserve){ ** if unable to complete the resizing. */ int sqlite3VdbeMemClearAndResize(Mem *pMem, int szNew){ - assert( szNew>=0 ); + assert( szNew>0 ); + assert( (pMem->flags & MEM_Dyn)==0 || pMem->szMalloc==0 ); if( pMem->szMallociLimit ){ return SQLITE_TOOBIG; } - if( sqlite3VdbeMemClearAndResize(pMem, nAlloc) ){ + testcase( nAlloc==0 ); + testcase( nAlloc==31 ); + testcase( nAlloc==32 ); + if( sqlite3VdbeMemClearAndResize(pMem, MAX(nAlloc,32)) ){ return SQLITE_NOMEM; } memcpy(pMem->z, z, nAlloc); From 9a7b41d74a384431c53bc986e78852cf5d6e9575 Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 8 Oct 2014 00:08:08 +0000 Subject: [PATCH 27/54] More intuitive labels on ".wheretrace" output. FossilOrigin-Name: adcb3fed489b580221c7bf2692a60e24248b23a0 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/where.c | 8 ++++---- 3 files changed, 11 insertions(+), 11 deletions(-) diff --git a/manifest b/manifest index 8b6acbd4de..7b23da26a8 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Make\ssure\sthe\ssqlite3VdbeMemClearAndResize()\sroutine\sis\snever\scalled\swith\sa\nzero\ssize\sparameter,\ssince\sa\ssize\sof\szero\scould\slead\sto\seither\sa\smemory\sleak\nor\san\sassertion\sfault. -D 2014-10-07T23:02:24.724 +C More\sintuitive\slabels\son\s".wheretrace"\soutput. +D 2014-10-08T00:08:08.905 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 2f42fe0d19303e0f5ce29aff3afbd3e43cbd6efb +F src/where.c 74e1f7e136bfb52c9c65a55909f8a24873b1edb5 F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1202,7 +1202,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P e405b9e4a9ef322d84b20e902234b4f6aa196b1b -R 59a3e15d0b7c925a5c413304ec5e314b +P f672a380e2e52bede95ff11a533fd9f7d412d494 +R b98bb7ee2a60e85b3c67deaa06ee1000 U drh -Z 1de6834c7b78df261ad24af6ce5dedbe +Z 71a8e8f52b1016a5adbdd28eb6eb38bb diff --git a/manifest.uuid b/manifest.uuid index 169d9b9887..bfe9547db3 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -f672a380e2e52bede95ff11a533fd9f7d412d494 \ No newline at end of file +adcb3fed489b580221c7bf2692a60e24248b23a0 \ No newline at end of file diff --git a/src/where.c b/src/where.c index 8974895c45..23481bb05e 100644 --- a/src/where.c +++ b/src/where.c @@ -4139,7 +4139,7 @@ static int whereLoopInsert(WhereLoopBuilder *pBuilder, WhereLoop *pTemplate){ ** than pTemplate, so just ignore pTemplate */ #if WHERETRACE_ENABLED /* 0x8 */ if( sqlite3WhereTrace & 0x8 ){ - sqlite3DebugPrintf("ins-noop: "); + sqlite3DebugPrintf(" skip: "); whereLoopPrint(pTemplate, pBuilder->pWC); } #endif @@ -4155,10 +4155,10 @@ static int whereLoopInsert(WhereLoopBuilder *pBuilder, WhereLoop *pTemplate){ #if WHERETRACE_ENABLED /* 0x8 */ if( sqlite3WhereTrace & 0x8 ){ if( p!=0 ){ - sqlite3DebugPrintf("ins-del: "); + sqlite3DebugPrintf("replace: "); whereLoopPrint(p, pBuilder->pWC); } - sqlite3DebugPrintf("ins-new: "); + sqlite3DebugPrintf(" add: "); whereLoopPrint(pTemplate, pBuilder->pWC); } #endif @@ -4182,7 +4182,7 @@ static int whereLoopInsert(WhereLoopBuilder *pBuilder, WhereLoop *pTemplate){ *ppTail = pToDel->pNextLoop; #if WHERETRACE_ENABLED /* 0x8 */ if( sqlite3WhereTrace & 0x8 ){ - sqlite3DebugPrintf("ins-del: "); + sqlite3DebugPrintf(" delete: "); whereLoopPrint(pToDel, pBuilder->pWC); } #endif From 69afd9980efa75371340a16bee238721f8b27cb2 Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 8 Oct 2014 02:53:25 +0000 Subject: [PATCH 28/54] Fix the STAT4 range scan estimates for DESC indexes. FossilOrigin-Name: e3fe84005259ef9a6027d25793514cebb2d4e7e0 --- manifest | 13 +-- manifest.uuid | 2 +- src/where.c | 13 ++- test/analyzeE.test | 242 +++++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 259 insertions(+), 11 deletions(-) create mode 100644 test/analyzeE.test diff --git a/manifest b/manifest index 7b23da26a8..36cf57e18d 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C More\sintuitive\slabels\son\s".wheretrace"\soutput. -D 2014-10-08T00:08:08.905 +C Fix\sthe\sSTAT4\srange\sscan\sestimates\sfor\sDESC\sindexes. +D 2014-10-08T02:53:25.568 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 74e1f7e136bfb52c9c65a55909f8a24873b1edb5 +F src/where.c 982f1ce21355452f2e5cd284359ab141c1eff547 F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -327,6 +327,7 @@ F test/analyzeA.test 3335697f6700c7052295cfd0067fc5b2aacddf9a F test/analyzeB.test 8bf35ee0a548aea831bf56762cb8e7fdb1db083d F test/analyzeC.test 555a6cc388b9818b6eda6df816f01ce0a75d3a93 F test/analyzeD.test 08f9d0bee4e118a66fff3a32d02dbe0ee0a2b594 +F test/analyzeE.test 8684e8ac5722fb97c251887ad97e5d496a98af1d F test/async.test 1d0e056ba1bb9729283a0f22718d3a25e82c277b F test/async2.test c0a9bd20816d7d6a2ceca7b8c03d3d69c28ffb8b F test/async3.test d73a062002376d7edc1fe3edff493edbec1fc2f7 @@ -1202,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P f672a380e2e52bede95ff11a533fd9f7d412d494 -R b98bb7ee2a60e85b3c67deaa06ee1000 +P adcb3fed489b580221c7bf2692a60e24248b23a0 +R 50f3751b824cfe9cc6f7ad401beb29e1 U drh -Z 71a8e8f52b1016a5adbdd28eb6eb38bb +Z 07946a58b794ebe5e4cb12afd1dbd645 diff --git a/manifest.uuid b/manifest.uuid index bfe9547db3..ee71c7f98a 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -adcb3fed489b580221c7bf2692a60e24248b23a0 \ No newline at end of file +e3fe84005259ef9a6027d25793514cebb2d4e7e0 \ No newline at end of file diff --git a/src/where.c b/src/where.c index 23481bb05e..236337a405 100644 --- a/src/where.c +++ b/src/where.c @@ -2207,16 +2207,22 @@ static int whereRangeScanEst( iUpper = a[0] + a[1]; } + assert( pLower==0 || (pLower->eOperator & (WO_GT|WO_GE))!=0 ); + assert( pUpper==0 || (pUpper->eOperator & (WO_LT|WO_LE))!=0 ); + if( p->pKeyInfo && p->pKeyInfo->aSortOrder[nEq] ){ + /* The roles of pLower and pUpper are swapped for a DESC index */ + SWAP(WhereTerm*, pLower, pUpper); + } + /* If possible, improve on the iLower estimate using ($P:$L). */ if( pLower ){ int bOk; /* True if value is extracted from pExpr */ Expr *pExpr = pLower->pExpr->pRight; - assert( (pLower->eOperator & (WO_GT|WO_GE))!=0 ); rc = sqlite3Stat4ProbeSetValue(pParse, p, &pRec, pExpr, aff, nEq, &bOk); if( rc==SQLITE_OK && bOk ){ tRowcnt iNew; whereKeyStats(pParse, p, pRec, 0, a); - iNew = a[0] + ((pLower->eOperator & WO_GT) ? a[1] : 0); + iNew = a[0] + ((pLower->eOperator & (WO_GT|WO_LE)) ? a[1] : 0); if( iNew>iLower ) iLower = iNew; nOut--; pLower = 0; @@ -2227,12 +2233,11 @@ static int whereRangeScanEst( if( pUpper ){ int bOk; /* True if value is extracted from pExpr */ Expr *pExpr = pUpper->pExpr->pRight; - assert( (pUpper->eOperator & (WO_LT|WO_LE))!=0 ); rc = sqlite3Stat4ProbeSetValue(pParse, p, &pRec, pExpr, aff, nEq, &bOk); if( rc==SQLITE_OK && bOk ){ tRowcnt iNew; whereKeyStats(pParse, p, pRec, 1, a); - iNew = a[0] + ((pUpper->eOperator & WO_LE) ? a[1] : 0); + iNew = a[0] + ((pUpper->eOperator & (WO_GT|WO_LE)) ? a[1] : 0); if( iNew2500 +} {/SEARCH TABLE t1 USING INDEX t1a/} +do_execsql_test analyzeE-1.8 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a>1900 +} {/SEARCH TABLE t1 USING INDEX t1a/} +do_execsql_test analyzeE-1.9 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a>1100 +} {/SCAN TABLE t1/} +do_execsql_test analyzeE-1.10 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a<1100 +} {/SEARCH TABLE t1 USING INDEX t1a/} +do_execsql_test analyzeE-1.11 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a<1900 +} {/SCAN TABLE t1/} + +# Verify that everything works the same on a DESCENDING index. +# +do_execsql_test analyzeE-2.0 { + DROP INDEX t1a; + CREATE INDEX t1a ON t1(a DESC); + ANALYZE; +} {} +do_execsql_test analyzeE-2.1 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 500 AND 2500; +} {/SCAN TABLE t1/} +do_execsql_test analyzeE-2.2 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 2900 AND 3000; +} {/SEARCH TABLE t1 USING INDEX t1a/} +do_execsql_test analyzeE-2.3 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 1700 AND 1750; +} {/SEARCH TABLE t1 USING INDEX t1a/} +do_execsql_test analyzeE-2.4 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 1 AND 500 +} {/SEARCH TABLE t1 USING INDEX t1a/} +do_execsql_test analyzeE-2.5 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 3000 AND 3000000 +} {/SEARCH TABLE t1 USING INDEX t1a/} +do_execsql_test analyzeE-2.6 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a<500 +} {/SEARCH TABLE t1 USING INDEX t1a/} +do_execsql_test analyzeE-2.7 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a>2500 +} {/SEARCH TABLE t1 USING INDEX t1a/} +do_execsql_test analyzeE-2.8 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a>1900 +} {/SEARCH TABLE t1 USING INDEX t1a/} +do_execsql_test analyzeE-2.9 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a>1100 +} {/SCAN TABLE t1/} +do_execsql_test analyzeE-2.10 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a<1100 +} {/SEARCH TABLE t1 USING INDEX t1a/} +do_execsql_test analyzeE-2.11 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a<1900 +} {/SCAN TABLE t1/} + +# Now do a range query on the second term of an ASCENDING index +# where the first term is constrained by equality. +# +do_execsql_test analyzeE-3.0 { + DROP TABLE t1; + CREATE TABLE t1(a,b,c); + WITH RECURSIVE + cnt(x) AS (VALUES(1000) UNION ALL SELECT x+1 FROM cnt WHERE x<2000) + INSERT INTO t1(a,b,c) SELECT x, x, 123 FROM cnt; + CREATE INDEX t1ca ON t1(c,a); + ANALYZE; +} {} +do_execsql_test analyzeE-3.1 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 500 AND 2500 AND c=123; +} {/SCAN TABLE t1/} +do_execsql_test analyzeE-3.2 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 2900 AND 3000 AND c=123; +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-3.3 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 1700 AND 1750 AND c=123; +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-3.4 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 1 AND 500 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-3.5 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 3000 AND 3000000 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-3.6 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a<500 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-3.7 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a>2500 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-3.8 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a>1900 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-3.9 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a>1100 AND c=123 +} {/SCAN TABLE t1/} +do_execsql_test analyzeE-3.10 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a<1100 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-3.11 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a<1900 AND c=123 +} {/SCAN TABLE t1/} + +# Repeat the 3.x tests using a DESCENDING index +# +do_execsql_test analyzeE-4.0 { + DROP INDEX t1ca; + CREATE INDEX t1ca ON t1(c ASC,a DESC); + ANALYZE; +} {} +do_execsql_test analyzeE-4.1 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 500 AND 2500 AND c=123; +} {/SCAN TABLE t1/} +do_execsql_test analyzeE-4.2 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 2900 AND 3000 AND c=123; +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-4.3 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 1700 AND 1750 AND c=123; +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-4.4 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 1 AND 500 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-4.5 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a BETWEEN 3000 AND 3000000 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-4.6 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a<500 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-4.7 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a>2500 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-4.8 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a>1900 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-4.9 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a>1100 AND c=123 +} {/SCAN TABLE t1/} +do_execsql_test analyzeE-4.10 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a<1100 AND c=123 +} {/SEARCH TABLE t1 USING INDEX t1ca/} +do_execsql_test analyzeE-4.11 { + EXPLAIN QUERY PLAN + SELECT * FROM t1 WHERE a<1900 AND c=123 +} {/SCAN TABLE t1/} + +finish_test From 923c0b53beffb478a8f279170fdb980d93c7d951 Mon Sep 17 00:00:00 2001 From: dan Date: Wed, 8 Oct 2014 11:11:24 +0000 Subject: [PATCH 29/54] Remove some temporary code in mallocA.test that was accidentally checked in. FossilOrigin-Name: dedd15f7cd13868f3be37646dd30ab7ceac5dea7 --- manifest | 14 +++++++------- manifest.uuid | 2 +- test/mallocA.test | 2 -- 3 files changed, 8 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index 36cf57e18d..61a2a23950 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sthe\sSTAT4\srange\sscan\sestimates\sfor\sDESC\sindexes. -D 2014-10-08T02:53:25.568 +C Remove\ssome\stemporary\scode\sin\smallocA.test\sthat\swas\saccidentally\schecked\sin. +D 2014-10-08T11:11:24.999 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -692,7 +692,7 @@ F test/malloc6.test 2f039d9821927eacae43e1831f815e157659a151 F test/malloc7.test 7c68a32942858bc715284856c5507446bba88c3a F test/malloc8.test 9b7a3f8cb9cf0b12fff566e80a980b1767bd961d F test/malloc9.test 2307c6ee3703b0a21391f3ea92388b4b73f9105e -F test/mallocA.test c049224adeb0244b8f6eb770c1fa6ac40f9b3518 +F test/mallocA.test 672cd7dedb63771bade3a6f557f851a4ad161d4a F test/mallocAll.test 98f1be74bc9f49a858bc4f361fc58e26486798be F test/mallocB.test bc475ab850cda896142ab935bbfbc74c24e51ed6 F test/mallocC.test 3dffe16532f109293ce1ccecd0c31dca55ef08c4 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P adcb3fed489b580221c7bf2692a60e24248b23a0 -R 50f3751b824cfe9cc6f7ad401beb29e1 -U drh -Z 07946a58b794ebe5e4cb12afd1dbd645 +P e3fe84005259ef9a6027d25793514cebb2d4e7e0 +R 041f735fd7729856664b7e587c89b3dc +U dan +Z 7e47868b81dfec753c3dcd2a3c6c6ccd diff --git a/manifest.uuid b/manifest.uuid index ee71c7f98a..0fb51d4d96 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -e3fe84005259ef9a6027d25793514cebb2d4e7e0 \ No newline at end of file +dedd15f7cd13868f3be37646dd30ab7ceac5dea7 \ No newline at end of file diff --git a/test/mallocA.test b/test/mallocA.test index d6d6de8222..a78073d833 100644 --- a/test/mallocA.test +++ b/test/mallocA.test @@ -119,8 +119,6 @@ do_execsql_test 7.0 { PRAGMA cache_size = 5; } do_faultsim_test 7 -faults oom-trans* -prep { - if {$iFail < 500} { set iFail 2000 } - if {$iFail > 1215} { set iFail 2000 } } -body { execsql { WITH r(x,y) AS ( From 6a15440378465848343def4f398861d04a6c5e5f Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 8 Oct 2014 13:34:21 +0000 Subject: [PATCH 30/54] Ensure that the Pager.pTmpSpace allocation is correct even if an OOM error occurs while reducing the page size. FossilOrigin-Name: e4b43967fd9a0b4944be9ab5575bff3678be8ed5 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/pager.c | 6 ++++-- 3 files changed, 12 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index 61a2a23950..2d5dcf21ef 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\ssome\stemporary\scode\sin\smallocA.test\sthat\swas\saccidentally\schecked\sin. -D 2014-10-08T11:11:24.999 +C Ensure\sthat\sthe\sPager.pTmpSpace\sallocation\sis\scorrect\seven\sif\san\sOOM\serror\noccurs\swhile\sreducing\sthe\spage\ssize. +D 2014-10-08T13:34:21.522 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -215,7 +215,7 @@ F src/os_setup.h c9d4553b5aaa6f73391448b265b89bed0b890faa F src/os_unix.c fb587121840f690101336879adfa6d0b2cd0e8c7 F src/os_win.c 0a4042ef35f322e86fa01f6c8884c5e645b911e7 F src/os_win.h 09e751b20bbc107ffbd46e13555dc73576d88e21 -F src/pager.c caab007743821d96752597c9cfd7351654697b06 +F src/pager.c a171cf9dd09c6cb162b262c328d4dfd198e04f80 F src/pager.h ffd5607f7b3e4590b415b007a4382f693334d428 F src/parse.y 5dfead8aed90cb0c7c1115898ee2266804daff45 F src/pcache.c 4121a0571c18581ee9f82f086d5e2030051ebd6a @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P e3fe84005259ef9a6027d25793514cebb2d4e7e0 -R 041f735fd7729856664b7e587c89b3dc -U dan -Z 7e47868b81dfec753c3dcd2a3c6c6ccd +P dedd15f7cd13868f3be37646dd30ab7ceac5dea7 +R 4cf08d774ef596973588c752956e991d +U drh +Z e3bcbea265a57269fe808fe62b242441 diff --git a/manifest.uuid b/manifest.uuid index 0fb51d4d96..b199078c31 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -dedd15f7cd13868f3be37646dd30ab7ceac5dea7 \ No newline at end of file +e4b43967fd9a0b4944be9ab5575bff3678be8ed5 \ No newline at end of file diff --git a/src/pager.c b/src/pager.c index 79bfe15f10..d3a36ef484 100644 --- a/src/pager.c +++ b/src/pager.c @@ -3618,13 +3618,15 @@ int sqlite3PagerSetPagesize(Pager *pPager, u32 *pPageSize, int nReserve){ if( rc==SQLITE_OK ){ pager_reset(pPager); - sqlite3PageFree(pPager->pTmpSpace); - pPager->pTmpSpace = pNew; rc = sqlite3PcacheSetPageSize(pPager->pPCache, pageSize); } if( rc==SQLITE_OK ){ + sqlite3PageFree(pPager->pTmpSpace); + pPager->pTmpSpace = pNew; pPager->dbSize = (Pgno)((nByte+pageSize-1)/pageSize); pPager->pageSize = pageSize; + }else{ + sqlite3PageFree(pNew); } } From f6aff8052551c6818d8077cf18ae50482c3c729e Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 8 Oct 2014 14:28:31 +0000 Subject: [PATCH 31/54] Set the connection-specific lastRowid value before calling any SQL function. FossilOrigin-Name: dff0f6422e60a7e2e4efb658aab202a119cfa702 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/vdbe.c | 2 +- 3 files changed, 8 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 2d5dcf21ef..4860d29d3d 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Ensure\sthat\sthe\sPager.pTmpSpace\sallocation\sis\scorrect\seven\sif\san\sOOM\serror\noccurs\swhile\sreducing\sthe\spage\ssize. -D 2014-10-08T13:34:21.522 +C Set\sthe\sconnection-specific\slastRowid\svalue\sbefore\scalling\sany\sSQL\sfunction. +D 2014-10-08T14:28:31.133 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -289,7 +289,7 @@ F src/update.c 729f6f18fc27740591d085e1172cebe311144bf0 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 4006c01772bd8d8ac4306d523bbcee41d3e392d8 F src/vacuum.c 59f03f92bcff57faa6a8ca256eb29ccddfb0614a -F src/vdbe.c e6c964101382d6fb144853b1d5b288158a9aba0e +F src/vdbe.c fee8286ff026bb9cf96ce87971b60aba53863b78 F src/vdbe.h 09f5b4e3719fa454f252322b1cdab5cf1f361327 F src/vdbeInt.h 0b97a3190f8fbf460655985a9183019f5a702754 F src/vdbeapi.c 37a6c6ae284a97bcace365f2f0a225680c0499d9 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P dedd15f7cd13868f3be37646dd30ab7ceac5dea7 -R 4cf08d774ef596973588c752956e991d +P e4b43967fd9a0b4944be9ab5575bff3678be8ed5 +R 4b3fd8ad675c779547c8afe5951393e2 U drh -Z e3bcbea265a57269fe808fe62b242441 +Z c9285a151f73aa9d039cef676eec6a31 diff --git a/manifest.uuid b/manifest.uuid index b199078c31..27c74f4c9b 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -e4b43967fd9a0b4944be9ab5575bff3678be8ed5 \ No newline at end of file +dff0f6422e60a7e2e4efb658aab202a119cfa702 \ No newline at end of file diff --git a/src/vdbe.c b/src/vdbe.c index 18e1cd83a9..c039dcc862 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -1558,7 +1558,7 @@ case OP_Function: { ctx.pVdbe = p; MemSetTypeFlag(ctx.pOut, MEM_Null); ctx.fErrorOrAux = 0; - assert( db->lastRowid==lastRowid ); + db->lastRowid = lastRowid; (*ctx.pFunc->xFunc)(&ctx, n, apVal); /* IMP: R-24505-23230 */ lastRowid = db->lastRowid; /* Remember rowid changes made by xFunc */ From 3705ef6a736d656e96d6de2ba5d069d5b0a6e7ae Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 8 Oct 2014 15:53:21 +0000 Subject: [PATCH 32/54] Fix up test cases to account for the new SQLITE_LIMIT_WORKER_THREADS limit. FossilOrigin-Name: 6483d426c4c5c772cd49412ea37e0fa7a0378904 --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/test1.c | 3 ++- src/test_config.c | 1 + test/sqllimits1.test | 7 +++++++ 5 files changed, 19 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index 4860d29d3d..91746f0685 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Set\sthe\sconnection-specific\slastRowid\svalue\sbefore\scalling\sany\sSQL\sfunction. -D 2014-10-08T14:28:31.133 +C Fix\sup\stest\scases\sto\saccount\sfor\sthe\snew\sSQLITE_LIMIT_WORKER_THREADS\slimit. +D 2014-10-08T15:53:21.620 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -237,7 +237,7 @@ F src/sqliteLimit.h 164b0e6749d31e0daa1a4589a169d31c0dec7b3d F src/status.c 961d5926e5a8fda611d385ec22c226b8635cd1cb F src/table.c 2e99ef7ef16187e17033d9398dc962ce22dab5cb F src/tclsqlite.c c67d310c833046cccc192125d64ad422ab882684 -F src/test1.c 523cd70ded28db71af9a30ec184cbe0957de9575 +F src/test1.c 518db4305d76b29dd9da3f022ca899c8fcdf9fc7 F src/test2.c 98049e51a17dc62606a99a9eb95ee477f9996712 F src/test3.c 1c0e5d6f080b8e33c1ce8b3078e7013fdbcd560c F src/test4.c 9b32d22f5f150abe23c1830e2057c4037c45b3df @@ -250,7 +250,7 @@ F src/test_async.c 21e11293a2f72080eda70e1124e9102044531cd8 F src/test_autoext.c dea8a01a7153b9adc97bd26161e4226329546e12 F src/test_backup.c 3875e899222b651e18b662f86e0e50daa946344e F src/test_btree.c 2e9978eca99a9a4bfa8cae949efb00886860a64f -F src/test_config.c 6f721f0337b96d58e81ff69bba101113c8168c2b +F src/test_config.c a4cdebe093474c02eecc5e4008b1a22198edf975 F src/test_demovfs.c 69b2085076654ebc18014cbc6386f04409c959a9 F src/test_devsym.c e7498904e72ba7491d142d5c83b476c4e76993bc F src/test_fs.c ced436e3d4b8e4681328409b8081051ce614e28f @@ -862,7 +862,7 @@ F test/speed4p.explain 6b5f104ebeb34a038b2f714150f51d01143e59aa F test/speed4p.test 0e51908951677de5a969b723e03a27a1c45db38b F test/speedtest1.c 83f6b3318f7ee60e52b978b5a5e5dd7e83dfb7ee F test/spellfix.test 24f676831acddd2f4056a598fd731a72c6311f49 -F test/sqllimits1.test b1aae27cc98eceb845e7f7adf918561256e31298 +F test/sqllimits1.test 9014524e7ab16e2a4976b13397db4c29cc29c6d9 F test/stat.test 76fd746b85459e812a0193410fb599f0531f22de F test/stmt.test 25d64e3dbf9a3ce89558667d7f39d966fe2a71b9 F test/subquery.test 666fdecceac258f5fd84bed09a64e49d9f37edd9 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P e4b43967fd9a0b4944be9ab5575bff3678be8ed5 -R 4b3fd8ad675c779547c8afe5951393e2 +P dff0f6422e60a7e2e4efb658aab202a119cfa702 +R 7321f912fc295ac13d3e667e8ae8fde4 U drh -Z c9285a151f73aa9d039cef676eec6a31 +Z a0d7563bd184d766bb67ad4df881d191 diff --git a/manifest.uuid b/manifest.uuid index 27c74f4c9b..44dfb50593 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -dff0f6422e60a7e2e4efb658aab202a119cfa702 \ No newline at end of file +6483d426c4c5c772cd49412ea37e0fa7a0378904 \ No newline at end of file diff --git a/src/test1.c b/src/test1.c index 62b575989d..85a16488ba 100644 --- a/src/test1.c +++ b/src/test1.c @@ -5513,10 +5513,11 @@ static int test_limit( { "SQLITE_LIMIT_LIKE_PATTERN_LENGTH", SQLITE_LIMIT_LIKE_PATTERN_LENGTH }, { "SQLITE_LIMIT_VARIABLE_NUMBER", SQLITE_LIMIT_VARIABLE_NUMBER }, { "SQLITE_LIMIT_TRIGGER_DEPTH", SQLITE_LIMIT_TRIGGER_DEPTH }, + { "SQLITE_LIMIT_WORKER_THREADS", SQLITE_LIMIT_WORKER_THREADS }, /* Out of range test cases */ { "SQLITE_LIMIT_TOOSMALL", -1, }, - { "SQLITE_LIMIT_TOOBIG", SQLITE_LIMIT_TRIGGER_DEPTH+1 }, + { "SQLITE_LIMIT_TOOBIG", SQLITE_LIMIT_WORKER_THREADS+1 }, }; int i, id; int val; diff --git a/src/test_config.c b/src/test_config.c index 074faf2116..2c11f713fb 100644 --- a/src/test_config.c +++ b/src/test_config.c @@ -644,6 +644,7 @@ Tcl_SetVar2(interp, "sqlite_options", "mergesort", "1", TCL_GLOBAL_ONLY); LINKVAR( DEFAULT_FILE_FORMAT ); LINKVAR( MAX_ATTACHED ); LINKVAR( MAX_DEFAULT_PAGE_SIZE ); + LINKVAR( MAX_WORKER_THREADS ); { static const int cv_TEMP_STORE = SQLITE_TEMP_STORE; diff --git a/test/sqllimits1.test b/test/sqllimits1.test index 2cbad3ffb8..57fc931f7c 100644 --- a/test/sqllimits1.test +++ b/test/sqllimits1.test @@ -51,6 +51,13 @@ do_test sqllimits1-1.9 { do_test sqllimits1-1.10 { sqlite3_limit db SQLITE_LIMIT_VARIABLE_NUMBER -1 } $SQLITE_MAX_VARIABLE_NUMBER +do_test sqllimits1-1.11 { + sqlite3_limit db SQLITE_LIMIT_TRIGGER_DEPTH -1 +} $SQLITE_MAX_TRIGGER_DEPTH +do_test sqllimits1-1.12 { + sqlite3_limit db SQLITE_LIMIT_WORKER_THREADS 99999 + sqlite3_limit db SQLITE_LIMIT_WORKER_THREADS -1 +} $SQLITE_MAX_WORKER_THREADS # Limit parameters out of range. # From 8e0a8f681ab3a7f5be1d0f7d080c8064f5b27127 Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 8 Oct 2014 19:33:54 +0000 Subject: [PATCH 33/54] Remove an always-true branch in whereRangeScanEst(). Replace it with an assert(). FossilOrigin-Name: 42e48fd3a6a6219d9bd6135d821b38c5157922ba --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/where.c | 3 ++- 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 91746f0685..d52803d558 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sup\stest\scases\sto\saccount\sfor\sthe\snew\sSQLITE_LIMIT_WORKER_THREADS\slimit. -D 2014-10-08T15:53:21.620 +C Remove\san\salways-true\sbranch\sin\swhereRangeScanEst().\s\sReplace\sit\swith\san\nassert(). +D 2014-10-08T19:33:54.518 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 982f1ce21355452f2e5cd284359ab141c1eff547 +F src/where.c 6fe21e0f60a449af5d75d00e6d480370464a9a48 F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P dff0f6422e60a7e2e4efb658aab202a119cfa702 -R 7321f912fc295ac13d3e667e8ae8fde4 +P 6483d426c4c5c772cd49412ea37e0fa7a0378904 +R df1d18db7990f8a7d78a79273193f180 U drh -Z a0d7563bd184d766bb67ad4df881d191 +Z 70427f180e63fb554c9a4909a2862788 diff --git a/manifest.uuid b/manifest.uuid index 44dfb50593..ba92b776aa 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -6483d426c4c5c772cd49412ea37e0fa7a0378904 \ No newline at end of file +42e48fd3a6a6219d9bd6135d821b38c5157922ba \ No newline at end of file diff --git a/src/where.c b/src/where.c index 236337a405..011ad66c00 100644 --- a/src/where.c +++ b/src/where.c @@ -2209,7 +2209,8 @@ static int whereRangeScanEst( assert( pLower==0 || (pLower->eOperator & (WO_GT|WO_GE))!=0 ); assert( pUpper==0 || (pUpper->eOperator & (WO_LT|WO_LE))!=0 ); - if( p->pKeyInfo && p->pKeyInfo->aSortOrder[nEq] ){ + assert( p->pKeyInfo!=0 && p->pKeyInfo->aSortOrder!=0 ); + if( p->pKeyInfo->aSortOrder[nEq] ){ /* The roles of pLower and pUpper are swapped for a DESC index */ SWAP(WhereTerm*, pLower, pUpper); } From a8950d5038d443a0014eb7ca6c14544b4d48ab9e Mon Sep 17 00:00:00 2001 From: drh Date: Thu, 9 Oct 2014 14:00:49 +0000 Subject: [PATCH 34/54] Fix a memory leak associated with the FTS4 matchinfo() function. FossilOrigin-Name: fb8da82411b80a234c6a5481622027815450996a --- ext/fts3/fts3.c | 1 + manifest | 12 ++++++------ manifest.uuid | 2 +- 3 files changed, 8 insertions(+), 7 deletions(-) diff --git a/ext/fts3/fts3.c b/ext/fts3/fts3.c index 582b7e27a1..2b93c62715 100644 --- a/ext/fts3/fts3.c +++ b/ext/fts3/fts3.c @@ -3116,6 +3116,7 @@ static int fts3FilterMethod( /* In case the cursor has been used before, clear it now. */ sqlite3_finalize(pCsr->pStmt); sqlite3_free(pCsr->aDoclist); + sqlite3_free(pCsr->aMatchinfo); sqlite3Fts3ExprFree(pCsr->pExpr); memset(&pCursor[1], 0, sizeof(Fts3Cursor)-sizeof(sqlite3_vtab_cursor)); diff --git a/manifest b/manifest index d52803d558..213759fab2 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\san\salways-true\sbranch\sin\swhereRangeScanEst().\s\sReplace\sit\swith\san\nassert(). -D 2014-10-08T19:33:54.518 +C Fix\sa\smemory\sleak\sassociated\swith\sthe\sFTS4\smatchinfo()\sfunction. +D 2014-10-09T14:00:49.227 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -78,7 +78,7 @@ F ext/fts3/README.content fdc666a70d5257a64fee209f97cf89e0e6e32b51 F ext/fts3/README.syntax a19711dc5458c20734b8e485e75fb1981ec2427a F ext/fts3/README.tokenizers e0a8b81383ea60d0334d274fadf305ea14a8c314 F ext/fts3/README.txt 8c18f41574404623b76917b9da66fcb0ab38328d -F ext/fts3/fts3.c 66f39c425fa834b939d06caeeb14f49e038d443b +F ext/fts3/fts3.c 8b6cceb3e0be22da26d83a3cec0e0e337e6b8ec6 F ext/fts3/fts3.h 3a10a0af180d502cecc50df77b1b22df142817fe F ext/fts3/fts3Int.h 53d4eca1fb23eab00681fb028fb82eb5705c1e21 F ext/fts3/fts3_aux.c 5c211e17a64885faeb16b9ba7772f9d5445c2365 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 6483d426c4c5c772cd49412ea37e0fa7a0378904 -R df1d18db7990f8a7d78a79273193f180 +P 42e48fd3a6a6219d9bd6135d821b38c5157922ba +R b5e5fdd1e3ce299c36e7187cabf29d23 U drh -Z 70427f180e63fb554c9a4909a2862788 +Z 0cd30ecf2cac304fdb077fd52d8a3789 diff --git a/manifest.uuid b/manifest.uuid index ba92b776aa..261ccbda05 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -42e48fd3a6a6219d9bd6135d821b38c5157922ba \ No newline at end of file +fb8da82411b80a234c6a5481622027815450996a \ No newline at end of file From 622d4f8bb1f3c530cf5886242a19fbc931585801 Mon Sep 17 00:00:00 2001 From: drh Date: Thu, 9 Oct 2014 14:10:38 +0000 Subject: [PATCH 35/54] Add a test case for the memory leak fixed by the previous check-in. FossilOrigin-Name: bae36d544676c90e337381a83f4513b4d925ab05 --- manifest | 12 ++++++------ manifest.uuid | 2 +- test/fts3matchinfo.test | 17 +++++++++++++++++ 3 files changed, 24 insertions(+), 7 deletions(-) diff --git a/manifest b/manifest index 213759fab2..96904c6bca 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sa\smemory\sleak\sassociated\swith\sthe\sFTS4\smatchinfo()\sfunction. -D 2014-10-09T14:00:49.227 +C Add\sa\stest\scase\sfor\sthe\smemory\sleak\sfixed\sby\sthe\sprevious\scheck-in. +D 2014-10-09T14:10:38.803 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -568,7 +568,7 @@ F test/fts3fault2.test 3198eef2804deea7cac8403e771d9cbcb752d887 F test/fts3first.test dbdedd20914c8d539aa3206c9b34a23775644641 F test/fts3join.test 53e66a0c21eb568580674a43b21c059acb26f499 F test/fts3malloc.test b0e4c133b8d61d4f6d112d8110f8320e9e453ef6 -F test/fts3matchinfo.test ff423e73faab8fc6d7adeefedf74dd8e2b0b14e0 +F test/fts3matchinfo.test 58544fa4d254000fa4e7f494b0a832f7ba61d45e F test/fts3near.test 7e3354d46f155a822b59c0e957fd2a70c1d7e905 F test/fts3prefix.test b36d4f00b128a51e7b386cc013a874246d9d7dc1 F test/fts3prefix2.test e1f0a822ca661dced7f12ce392e14eaf65609dce @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 42e48fd3a6a6219d9bd6135d821b38c5157922ba -R b5e5fdd1e3ce299c36e7187cabf29d23 +P fb8da82411b80a234c6a5481622027815450996a +R 3f68f640c5da00a278a8bfe99729cf27 U drh -Z 0cd30ecf2cac304fdb077fd52d8a3789 +Z d27fedea65c2ff594a69f62bdfd5cd22 diff --git a/manifest.uuid b/manifest.uuid index 261ccbda05..66a5fa9d03 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -fb8da82411b80a234c6a5481622027815450996a \ No newline at end of file +bae36d544676c90e337381a83f4513b4d925ab05 \ No newline at end of file diff --git a/test/fts3matchinfo.test b/test/fts3matchinfo.test index fd475af2e4..36c9121118 100644 --- a/test/fts3matchinfo.test +++ b/test/fts3matchinfo.test @@ -433,4 +433,21 @@ do_execsql_test 9.1 { SELECT snippet(ft2, '[', ']', '', -1, 1) FROM ft2 WHERE ft2 MATCH 'c'; } {{[c]} {[c]}} +#--------------------------------------------------------------------------- +# Test for a memory leak +# +do_execsql_test 10.1 { + DROP TABLE t10; + CREATE VIRTUAL TABLE t10 USING fts4(idx, value); + INSERT INTO t10 values (1, 'one'),(2, 'two'),(3, 'three'); + SELECT docId, t10.* + FROM t10 + JOIN (SELECT 1 AS idx UNION SELECT 2 UNION SELECT 3) AS x + WHERE t10 MATCH x.idx + AND matchinfo(t10) not null + GROUP BY docId + ORDER BY 1; +} {1 1 one 2 2 two 3 3 three} + + finish_test From 6e1a03735790e1ccf2f243d26197090e7954b9fc Mon Sep 17 00:00:00 2001 From: dan Date: Thu, 9 Oct 2014 15:08:17 +0000 Subject: [PATCH 36/54] Allow FTS tokenizers to choose whether or not to consider the "*" character part of tokens or not. This restores the pre-[e21bf7a2ad] behaviour. Also fix a problem causing FTS to interpret tokens beginning with "*" characters as EOF. FossilOrigin-Name: 49dfee7cd1c9ab2901b8a871a6cd00b2ead76801 --- ext/fts3/fts3_expr.c | 2 +- manifest | 16 ++++++++-------- manifest.uuid | 2 +- test/fts3expr4.test | 31 ++++++++++++++++++++++++++++--- 4 files changed, 38 insertions(+), 13 deletions(-) diff --git a/ext/fts3/fts3_expr.c b/ext/fts3/fts3_expr.c index f5d28cbfcc..2ba786ce80 100644 --- a/ext/fts3/fts3_expr.c +++ b/ext/fts3/fts3_expr.c @@ -190,7 +190,7 @@ static int getNextToken( /* Set variable i to the maximum number of bytes of input to tokenize. */ for(i=0; i Date: Fri, 10 Oct 2014 13:08:33 +0000 Subject: [PATCH 37/54] Cause the command-line shell to return non-zero if the final SQL statement is incomplete. FossilOrigin-Name: 177fff3b98b101b98f1e7d334b6a80530b645565 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/shell.c | 1 + 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 993d89e658..1d67001ce9 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Allow\sFTS\stokenizers\sto\schoose\swhether\sor\snot\sto\sconsider\sthe\s"*"\scharacter\spart\sof\stokens\sor\snot.\sThis\srestores\sthe\spre-[e21bf7a2ad]\sbehaviour.\sAlso\sfix\sa\sproblem\scausing\sFTS\sto\sinterpret\stokens\sbeginning\swith\s"*"\scharacters\sas\sEOF. -D 2014-10-09T15:08:17.615 +C Cause\sthe\scommand-line\sshell\sto\sreturn\snon-zero\sif\sthe\sfinal\sSQL\sstatement\nis\sincomplete. +D 2014-10-10T13:08:33.966 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -228,7 +228,7 @@ F src/random.c d10c1f85b6709ca97278428fd5db5bbb9c74eece F src/resolve.c a3466128b52a86c466e47ac1a19e2174f7b5cf89 F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e F src/select.c f11533162b57ed5ed37f549add34cbcdf51f6712 -F src/shell.c 38f627b0885191357f55902a3ac199de90d79715 +F src/shell.c 18ee8bbe9502d8848072dc2eddd1ea09254ba494 F src/sqlite.h.in 4a5e5158c189d2bcd45c7c4607c2c0eb6d25c153 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P bae36d544676c90e337381a83f4513b4d925ab05 -R f3cda043ab8d3408ba2f57353f2b5a88 -U dan -Z 374021995a45280d12595d646a4004c7 +P 49dfee7cd1c9ab2901b8a871a6cd00b2ead76801 +R cb2ddf412f0df2d20c53503ae15115d8 +U drh +Z 473a503ca2f65e4944005f1668696768 diff --git a/manifest.uuid b/manifest.uuid index f52ad1a7ce..20fdb6bf5a 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -49dfee7cd1c9ab2901b8a871a6cd00b2ead76801 \ No newline at end of file +177fff3b98b101b98f1e7d334b6a80530b645565 \ No newline at end of file diff --git a/src/shell.c b/src/shell.c index cd4dadb08c..3ca4b094bc 100644 --- a/src/shell.c +++ b/src/shell.c @@ -3725,6 +3725,7 @@ static int process_input(ShellState *p, FILE *in){ if( nSql ){ if( !_all_whitespace(zSql) ){ fprintf(stderr, "Error: incomplete SQL: %s\n", zSql); + errCnt++; } free(zSql); } From 681fca0018cd931953350475bfe63e46d6ef9374 Mon Sep 17 00:00:00 2001 From: drh Date: Fri, 10 Oct 2014 15:01:46 +0000 Subject: [PATCH 38/54] Fix a potential problem in the whereRangeScanEst() routine when STAT4 is active. The problem was introduced by recent enhancements. FossilOrigin-Name: 68e1b4de700b5291f79249a03e1a750c6b2c9ae4 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/where.c | 4 ++-- 3 files changed, 9 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 1d67001ce9..a49120ba19 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Cause\sthe\scommand-line\sshell\sto\sreturn\snon-zero\sif\sthe\sfinal\sSQL\sstatement\nis\sincomplete. -D 2014-10-10T13:08:33.966 +C Fix\sa\spotential\sproblem\sin\sthe\swhereRangeScanEst()\sroutine\swhen\sSTAT4\sis\nactive.\s\sThe\sproblem\swas\sintroduced\sby\srecent\senhancements. +D 2014-10-10T15:01:46.922 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 6fe21e0f60a449af5d75d00e6d480370464a9a48 +F src/where.c d1e315e338f51e4e7ff83ac6231a81d1c0cd30f9 F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 49dfee7cd1c9ab2901b8a871a6cd00b2ead76801 -R cb2ddf412f0df2d20c53503ae15115d8 +P 177fff3b98b101b98f1e7d334b6a80530b645565 +R 07357edada657f8492081fa01ca31a82 U drh -Z 473a503ca2f65e4944005f1668696768 +Z a44558a0f7d62314eeda3bb13a5723b9 diff --git a/manifest.uuid b/manifest.uuid index 20fdb6bf5a..dc8efe9532 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -177fff3b98b101b98f1e7d334b6a80530b645565 \ No newline at end of file +68e1b4de700b5291f79249a03e1a750c6b2c9ae4 \ No newline at end of file diff --git a/src/where.c b/src/where.c index 011ad66c00..e3ab542525 100644 --- a/src/where.c +++ b/src/where.c @@ -2209,8 +2209,8 @@ static int whereRangeScanEst( assert( pLower==0 || (pLower->eOperator & (WO_GT|WO_GE))!=0 ); assert( pUpper==0 || (pUpper->eOperator & (WO_LT|WO_LE))!=0 ); - assert( p->pKeyInfo!=0 && p->pKeyInfo->aSortOrder!=0 ); - if( p->pKeyInfo->aSortOrder[nEq] ){ + assert( p->aSortOrder!=0 ); + if( p->aSortOrder[nEq] ){ /* The roles of pLower and pUpper are swapped for a DESC index */ SWAP(WhereTerm*, pLower, pUpper); } From 6c97789d2eb2df436506132cc3a4f211a68c6aa5 Mon Sep 17 00:00:00 2001 From: drh Date: Fri, 10 Oct 2014 15:47:46 +0000 Subject: [PATCH 39/54] Simplify the code used to generate the text for EXPLAIN QUERY PLAN. FossilOrigin-Name: beea1efc3a49cad08087fcbb18dbce71c873fe57 --- manifest | 12 +++--- manifest.uuid | 2 +- src/where.c | 100 +++++++++++++++++++++++++------------------------- 3 files changed, 57 insertions(+), 57 deletions(-) diff --git a/manifest b/manifest index a49120ba19..d11aa809a0 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sa\spotential\sproblem\sin\sthe\swhereRangeScanEst()\sroutine\swhen\sSTAT4\sis\nactive.\s\sThe\sproblem\swas\sintroduced\sby\srecent\senhancements. -D 2014-10-10T15:01:46.922 +C Simplify\sthe\scode\sused\sto\sgenerate\sthe\stext\sfor\sEXPLAIN\sQUERY\sPLAN. +D 2014-10-10T15:47:46.266 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c d1e315e338f51e4e7ff83ac6231a81d1c0cd30f9 +F src/where.c 23b9e5dd96a51657fb7d81091c28cd84f54dc8a0 F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 177fff3b98b101b98f1e7d334b6a80530b645565 -R 07357edada657f8492081fa01ca31a82 +P 68e1b4de700b5291f79249a03e1a750c6b2c9ae4 +R 1d64962e74f9e7c1f94f06e344d62c75 U drh -Z a44558a0f7d62314eeda3bb13a5723b9 +Z 5a7fbeb924ed3728c1bc69e5188e226a diff --git a/manifest.uuid b/manifest.uuid index dc8efe9532..948793a5c8 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -68e1b4de700b5291f79249a03e1a750c6b2c9ae4 \ No newline at end of file +beea1efc3a49cad08087fcbb18dbce71c873fe57 \ No newline at end of file diff --git a/src/where.c b/src/where.c index e3ab542525..d1f379b6c3 100644 --- a/src/where.c +++ b/src/where.c @@ -2737,9 +2737,8 @@ static void explainAppendTerm( /* ** Argument pLevel describes a strategy for scanning table pTab. This -** function returns a pointer to a string buffer containing a description -** of the subset of table rows scanned by the strategy in the form of an -** SQL expression. Or, if all rows are scanned, NULL is returned. +** function appends text to pStr that describes the subset of table +** rows scanned by the strategy in the form of an SQL expression. ** ** For example, if the query: ** @@ -2749,49 +2748,37 @@ static void explainAppendTerm( ** string similar to: ** ** "a=? AND b>?" -** -** The returned pointer points to memory obtained from sqlite3DbMalloc(). -** It is the responsibility of the caller to free the buffer when it is -** no longer required. */ -static char *explainIndexRange(sqlite3 *db, WhereLoop *pLoop, Table *pTab){ +void explainIndexRange(StrAccum *pStr, WhereLoop *pLoop, Table *pTab){ Index *pIndex = pLoop->u.btree.pIndex; u16 nEq = pLoop->u.btree.nEq; u16 nSkip = pLoop->u.btree.nSkip; int i, j; Column *aCol = pTab->aCol; i16 *aiColumn = pIndex->aiColumn; - StrAccum txt; - if( nEq==0 && (pLoop->wsFlags & (WHERE_BTM_LIMIT|WHERE_TOP_LIMIT))==0 ){ - return 0; - } - sqlite3StrAccumInit(&txt, 0, 0, SQLITE_MAX_LENGTH); - txt.db = db; - sqlite3StrAccumAppend(&txt, " (", 2); + if( nEq==0 && (pLoop->wsFlags&(WHERE_BTM_LIMIT|WHERE_TOP_LIMIT))==0 ) return; + sqlite3StrAccumAppend(pStr, " (", 2); for(i=0; i=nSkip ){ - explainAppendTerm(&txt, i, z, "="); + explainAppendTerm(pStr, i, z, "="); }else{ - if( i ) sqlite3StrAccumAppend(&txt, " AND ", 5); - sqlite3StrAccumAppend(&txt, "ANY(", 4); - sqlite3StrAccumAppendAll(&txt, z); - sqlite3StrAccumAppend(&txt, ")", 1); + if( i ) sqlite3StrAccumAppend(pStr, " AND ", 5); + sqlite3XPrintf(pStr, 0, "ANY(%s)", z); } } j = i; if( pLoop->wsFlags&WHERE_BTM_LIMIT ){ char *z = aiColumn[j] < 0 ? "rowid" : aCol[aiColumn[j]].zName; - explainAppendTerm(&txt, i++, z, ">"); + explainAppendTerm(pStr, i++, z, ">"); } if( pLoop->wsFlags&WHERE_TOP_LIMIT ){ char *z = aiColumn[j] < 0 ? "rowid" : aCol[aiColumn[j]].zName; - explainAppendTerm(&txt, i, z, "<"); + explainAppendTerm(pStr, i, z, "<"); } - sqlite3StrAccumAppend(&txt, ")", 1); - return sqlite3StrAccumFinish(&txt); + sqlite3StrAccumAppend(pStr, ")", 1); } /* @@ -2815,11 +2802,13 @@ static void explainOneScan( struct SrcList_item *pItem = &pTabList->a[pLevel->iFrom]; Vdbe *v = pParse->pVdbe; /* VM being constructed */ sqlite3 *db = pParse->db; /* Database handle */ - char *zMsg; /* Text to add to EQP output */ int iId = pParse->iSelectId; /* Select id (left-most output column) */ int isSearch; /* True for a SEARCH. False for SCAN. */ WhereLoop *pLoop; /* The controlling WhereLoop object */ u32 flags; /* Flags that describe this loop */ + char *zMsg; /* Text to add to EQP output */ + StrAccum str; /* EQP output string */ + char zBuf[100]; /* Initial space for EQP output string */ pLoop = pLevel->pWLoop; flags = pLoop->wsFlags; @@ -2829,54 +2818,65 @@ static void explainOneScan( || ((flags&WHERE_VIRTUALTABLE)==0 && (pLoop->u.btree.nEq>0)) || (wctrlFlags&(WHERE_ORDERBY_MIN|WHERE_ORDERBY_MAX)); - zMsg = sqlite3MPrintf(db, "%s", isSearch?"SEARCH":"SCAN"); + sqlite3StrAccumInit(&str, zBuf, sizeof(zBuf), SQLITE_MAX_LENGTH); + str.db = db; + sqlite3StrAccumAppendAll(&str, isSearch ? "SEARCH" : "SCAN"); if( pItem->pSelect ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s SUBQUERY %d", zMsg,pItem->iSelectId); + sqlite3XPrintf(&str, 0, " SUBQUERY %d", pItem->iSelectId); }else{ - zMsg = sqlite3MAppendf(db, zMsg, "%s TABLE %s", zMsg, pItem->zName); + sqlite3XPrintf(&str, 0, " TABLE %s", pItem->zName); } if( pItem->zAlias ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s AS %s", zMsg, pItem->zAlias); + sqlite3XPrintf(&str, 0, " AS %s", pItem->zAlias); } - if( (flags & (WHERE_IPK|WHERE_VIRTUALTABLE))==0 - && ALWAYS(pLoop->u.btree.pIndex!=0) - ){ - const char *zFmt; - Index *pIdx = pLoop->u.btree.pIndex; - char *zWhere = explainIndexRange(db, pLoop, pItem->pTab); + if( (flags & (WHERE_IPK|WHERE_VIRTUALTABLE))==0 ){ + const char *zFmt = 0; + Index *pIdx; + + assert( pLoop->u.btree.pIndex!=0 ); + pIdx = pLoop->u.btree.pIndex; assert( !(flags&WHERE_AUTO_INDEX) || (flags&WHERE_IDX_ONLY) ); if( !HasRowid(pItem->pTab) && IsPrimaryKeyIndex(pIdx) ){ - zFmt = zWhere ? "%s USING PRIMARY KEY%.0s%s" : "%s%.0s%s"; + if( pLoop->u.btree.nEq>0 + || (pLoop->wsFlags & (WHERE_BTM_LIMIT|WHERE_TOP_LIMIT))!=0 + ){ + zFmt = "PRIMARY KEY"; + } }else if( flags & WHERE_AUTO_INDEX ){ - zFmt = "%s USING AUTOMATIC COVERING INDEX%.0s%s"; + zFmt = "AUTOMATIC COVERING INDEX"; }else if( flags & WHERE_IDX_ONLY ){ - zFmt = "%s USING COVERING INDEX %s%s"; + zFmt = "COVERING INDEX %s"; }else{ - zFmt = "%s USING INDEX %s%s"; + zFmt = "INDEX %s"; + } + if( zFmt ){ + sqlite3StrAccumAppend(&str, " USING ", 7); + sqlite3XPrintf(&str, 0, zFmt, pIdx->zName); + explainIndexRange(&str, pLoop, pItem->pTab); } - zMsg = sqlite3MAppendf(db, zMsg, zFmt, zMsg, pIdx->zName, zWhere); - sqlite3DbFree(db, zWhere); }else if( (flags & WHERE_IPK)!=0 && (flags & WHERE_CONSTRAINT)!=0 ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s USING INTEGER PRIMARY KEY", zMsg); - + const char *zRange; if( flags&(WHERE_COLUMN_EQ|WHERE_COLUMN_IN) ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s (rowid=?)", zMsg); + zRange = "(rowid=?)"; }else if( (flags&WHERE_BOTH_LIMIT)==WHERE_BOTH_LIMIT ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s (rowid>? AND rowid? AND rowid?)", zMsg); - }else if( ALWAYS(flags&WHERE_TOP_LIMIT) ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s (rowid?)"; + }else{ + assert( flags&WHERE_TOP_LIMIT); + zRange = "(rowidu.vtab.idxNum, pLoop->u.vtab.idxStr); } #endif - zMsg = sqlite3MAppendf(db, zMsg, "%s", zMsg); + zMsg = sqlite3StrAccumFinish(&str); sqlite3VdbeAddOp4(v, OP_Explain, iId, iLevel, iFrom, zMsg, P4_DYNAMIC); } } From 98545bb2edf182c7b29a14710fd1e80979b78151 Mon Sep 17 00:00:00 2001 From: drh Date: Fri, 10 Oct 2014 17:20:39 +0000 Subject: [PATCH 40/54] Add the estimated number of output rows to the EXPLAIN QUERY PLAN output if compiled with SQLITE_EXPLAIN_ESTIMATED_ROWS. This feature is off by default for the time being. FossilOrigin-Name: daa8314fba9dc3c4f5e7fbda42c97604fbfc4392 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/where.c | 7 +++++++ 3 files changed, 14 insertions(+), 7 deletions(-) diff --git a/manifest b/manifest index d11aa809a0..52085777df 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Simplify\sthe\scode\sused\sto\sgenerate\sthe\stext\sfor\sEXPLAIN\sQUERY\sPLAN. -D 2014-10-10T15:47:46.266 +C Add\sthe\sestimated\snumber\sof\soutput\srows\sto\sthe\sEXPLAIN\sQUERY\sPLAN\soutput\nif\scompiled\swith\sSQLITE_EXPLAIN_ESTIMATED_ROWS.\s\sThis\sfeature\sis\soff\sby\ndefault\sfor\sthe\stime\sbeing. +D 2014-10-10T17:20:39.349 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 23b9e5dd96a51657fb7d81091c28cd84f54dc8a0 +F src/where.c b511252533ca9f70e6adfc0ffd5c82594df137a2 F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 68e1b4de700b5291f79249a03e1a750c6b2c9ae4 -R 1d64962e74f9e7c1f94f06e344d62c75 +P beea1efc3a49cad08087fcbb18dbce71c873fe57 +R a0896f7681cce645a858136a6e4bda47 U drh -Z 5a7fbeb924ed3728c1bc69e5188e226a +Z 8fddc2c9d3b88cabdf0b2692b84338ef diff --git a/manifest.uuid b/manifest.uuid index 948793a5c8..10d95ef678 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -beea1efc3a49cad08087fcbb18dbce71c873fe57 \ No newline at end of file +daa8314fba9dc3c4f5e7fbda42c97604fbfc4392 \ No newline at end of file diff --git a/src/where.c b/src/where.c index d1f379b6c3..5b639946cf 100644 --- a/src/where.c +++ b/src/where.c @@ -2875,6 +2875,13 @@ static void explainOneScan( sqlite3XPrintf(&str, 0, " VIRTUAL TABLE INDEX %d:%s", pLoop->u.vtab.idxNum, pLoop->u.vtab.idxStr); } +#endif +#ifdef SQLITE_EXPLAIN_ESTIMATED_ROWS + if( pLoop->nOut>=10 ){ + sqlite3XPrintf(&str, 0, " (~%llu rows)", sqlite3LogEstToInt(pLoop->nOut)); + }else{ + sqlite3StrAccumAppend(&str, " (~1 row)", 9); + } #endif zMsg = sqlite3StrAccumFinish(&str); sqlite3VdbeAddOp4(v, OP_Explain, iId, iLevel, iFrom, zMsg, P4_DYNAMIC); From 2eeb7ae437b080ae73789bf7957effc77cc0bc90 Mon Sep 17 00:00:00 2001 From: drh Date: Fri, 10 Oct 2014 17:44:03 +0000 Subject: [PATCH 41/54] Provide the new "-config CONFIG" option to the test/releasetest.tcl script, which allows one to run a single test configuration selected by name. FossilOrigin-Name: d479e32be205f6cd0474f002282eae6eec613f36 --- manifest | 12 ++++++------ manifest.uuid | 2 +- test/releasetest.tcl | 13 ++++++++++++- 3 files changed, 19 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 52085777df..0af18811ed 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\sthe\sestimated\snumber\sof\soutput\srows\sto\sthe\sEXPLAIN\sQUERY\sPLAN\soutput\nif\scompiled\swith\sSQLITE_EXPLAIN_ESTIMATED_ROWS.\s\sThis\sfeature\sis\soff\sby\ndefault\sfor\sthe\stime\sbeing. -D 2014-10-10T17:20:39.349 +C Provide\sthe\snew\s"-config\sCONFIG"\soption\sto\sthe\stest/releasetest.tcl\sscript,\nwhich\sallows\sone\sto\srun\sa\ssingle\stest\sconfiguration\sselected\sby\sname. +D 2014-10-10T17:44:03.334 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -783,7 +783,7 @@ F test/rdonly.test dd30a4858d8e0fbad2304c2bd74a33d4df36412a F test/regexp1.test 497ea812f264d12b6198d6e50a76be4a1973a9d8 F test/reindex.test 44edd3966b474468b823d481eafef0c305022254 F test/releasetest.mk 2eced2f9ae701fd0a29e714a241760503ccba25a -F test/releasetest.tcl a0df0dfc5e3ee83ade87b9cc96db41b52d590b9e +F test/releasetest.tcl aa7aea9bacd0d76b3d9d5754bb1846d10103af57 F test/resolver01.test 33abf37ff8335e6bf98f2b45a0af3e06996ccd9a F test/rollback.test e9504a009a202c3ed711da2e6879ff60c5a4669c F test/rowhash.test 0bc1d31415e4575d10cacf31e1a66b5cc0f8be81 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P beea1efc3a49cad08087fcbb18dbce71c873fe57 -R a0896f7681cce645a858136a6e4bda47 +P daa8314fba9dc3c4f5e7fbda42c97604fbfc4392 +R d16c504828c83cfa33bdf3d0eaba9ed0 U drh -Z 8fddc2c9d3b88cabdf0b2692b84338ef +Z b39929cd4032458ed60510f729a1a0e8 diff --git a/manifest.uuid b/manifest.uuid index 10d95ef678..fd80ff2ddf 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -daa8314fba9dc3c4f5e7fbda42c97604fbfc4392 \ No newline at end of file +d479e32be205f6cd0474f002282eae6eec613f36 \ No newline at end of file diff --git a/test/releasetest.tcl b/test/releasetest.tcl index eb2e440013..99790d3248 100644 --- a/test/releasetest.tcl +++ b/test/releasetest.tcl @@ -13,6 +13,7 @@ optional) are: -makefile PATH-TO-MAKEFILE (default "releasetest.mk") -platform PLATFORM (see below) -quick BOOLEAN (default "0") + -config CONFIGNAME (Run only CONFIGNAME) The default value for -makefile is "./releasetest.mk". @@ -292,6 +293,7 @@ proc run_test_suite {name testtarget config} { proc process_options {argv} { set ::MAKEFILE releasetest.mk ;# Default value set ::QUICK 0 ;# Default value + set config {} set platform $::tcl_platform(os)-$::tcl_platform(machine) for {set i 0} {$i < [llength $argv]} {incr i} { @@ -310,6 +312,11 @@ proc process_options {argv} { incr i set ::QUICK [lindex $argv $i] } + + -config { + incr i + set config [lindex $argv $i] + } default { puts stderr "" @@ -333,7 +340,11 @@ proc process_options {argv} { exit } - set ::CONFIGLIST $::Platforms($platform) + if {$config!=""} { + set ::CONFIGLIST $config + } else { + set ::CONFIGLIST $::Platforms($platform) + } puts "Running the following configurations for $platform:" puts " [string trim $::CONFIGLIST]" } From e35626fabdb0183eafd481930e2a487a973cee3d Mon Sep 17 00:00:00 2001 From: drh Date: Fri, 10 Oct 2014 17:47:00 +0000 Subject: [PATCH 42/54] When using the -config option to releasetest.tcl, default the testing type to "fulltest" if it is not specified on the command line. FossilOrigin-Name: cf291cbe9f49396f03cfca39c2e892f27f750107 --- manifest | 12 ++++++------ manifest.uuid | 2 +- test/releasetest.tcl | 1 + 3 files changed, 8 insertions(+), 7 deletions(-) diff --git a/manifest b/manifest index 0af18811ed..258e0ade2b 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Provide\sthe\snew\s"-config\sCONFIG"\soption\sto\sthe\stest/releasetest.tcl\sscript,\nwhich\sallows\sone\sto\srun\sa\ssingle\stest\sconfiguration\sselected\sby\sname. -D 2014-10-10T17:44:03.334 +C When\susing\sthe\s-config\soption\sto\sreleasetest.tcl,\sdefault\sthe\stesting\stype\nto\s"fulltest"\sif\sit\sis\snot\sspecified\son\sthe\scommand\sline. +D 2014-10-10T17:47:00.230 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -783,7 +783,7 @@ F test/rdonly.test dd30a4858d8e0fbad2304c2bd74a33d4df36412a F test/regexp1.test 497ea812f264d12b6198d6e50a76be4a1973a9d8 F test/reindex.test 44edd3966b474468b823d481eafef0c305022254 F test/releasetest.mk 2eced2f9ae701fd0a29e714a241760503ccba25a -F test/releasetest.tcl aa7aea9bacd0d76b3d9d5754bb1846d10103af57 +F test/releasetest.tcl 4296b9adbc5992bcd0b0b2876b7651f57c1494f2 F test/resolver01.test 33abf37ff8335e6bf98f2b45a0af3e06996ccd9a F test/rollback.test e9504a009a202c3ed711da2e6879ff60c5a4669c F test/rowhash.test 0bc1d31415e4575d10cacf31e1a66b5cc0f8be81 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P daa8314fba9dc3c4f5e7fbda42c97604fbfc4392 -R d16c504828c83cfa33bdf3d0eaba9ed0 +P d479e32be205f6cd0474f002282eae6eec613f36 +R 931ed67b9f38d30c31761dd7af84265b U drh -Z b39929cd4032458ed60510f729a1a0e8 +Z 3cea3f1ee45c98cf88d87a6691b7a96c diff --git a/manifest.uuid b/manifest.uuid index fd80ff2ddf..29909b01ca 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -d479e32be205f6cd0474f002282eae6eec613f36 \ No newline at end of file +cf291cbe9f49396f03cfca39c2e892f27f750107 \ No newline at end of file diff --git a/test/releasetest.tcl b/test/releasetest.tcl index 99790d3248..589319d680 100644 --- a/test/releasetest.tcl +++ b/test/releasetest.tcl @@ -341,6 +341,7 @@ proc process_options {argv} { } if {$config!=""} { + if {[llength $config]==1} {lappend config fulltest} set ::CONFIGLIST $config } else { set ::CONFIGLIST $::Platforms($platform) From ab993380a27226883381d21d5401d76df7fccaee Mon Sep 17 00:00:00 2001 From: drh Date: Fri, 10 Oct 2014 18:09:52 +0000 Subject: [PATCH 43/54] Changes to enable compiling using VC6. FossilOrigin-Name: 9ee5686ab3b0bca8cabdf455c75bd9410cdc5378 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/sqliteInt.h | 2 +- src/threads.c | 4 ++-- 4 files changed, 11 insertions(+), 11 deletions(-) diff --git a/manifest b/manifest index 258e0ade2b..fd3281f6c5 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C When\susing\sthe\s-config\soption\sto\sreleasetest.tcl,\sdefault\sthe\stesting\stype\nto\s"fulltest"\sif\sit\sis\snot\sspecified\son\sthe\scommand\sline. -D 2014-10-10T17:47:00.230 +C Changes\sto\senable\scompiling\susing\sVC6. +D 2014-10-10T18:09:52.113 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -232,7 +232,7 @@ F src/shell.c 18ee8bbe9502d8848072dc2eddd1ea09254ba494 F src/sqlite.h.in 4a5e5158c189d2bcd45c7c4607c2c0eb6d25c153 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d -F src/sqliteInt.h 6ac5e34a590ad7ea22af91d190bdb212b12107be +F src/sqliteInt.h c417a25e2369f705b651897a2f1cc8da0e6aa1c4 F src/sqliteLimit.h 164b0e6749d31e0daa1a4589a169d31c0dec7b3d F src/status.c 961d5926e5a8fda611d385ec22c226b8635cd1cb F src/table.c 2e99ef7ef16187e17033d9398dc962ce22dab5cb @@ -282,7 +282,7 @@ F src/test_thread.c 1e133a40b50e9c035b00174035b846e7eef481cb F src/test_vfs.c f84075a388527892ff184988f43b69ce69b8083c F src/test_vfstrace.c bab9594adc976cbe696ff3970728830b4c5ed698 F src/test_wsd.c 41cadfd9d97fe8e3e4e44f61a4a8ccd6f7ca8fe9 -F src/threads.c 22dded4283dc4b25422f6444cdcb8d6b1ea0b5ff +F src/threads.c 60c9d400abf17ccdc8767cdc6af90b9c5acf58bd F src/tokenize.c cc9016e5007fc5e76789079616d2f26741bcc689 F src/trigger.c 25571661fdeae8c7f975ff40ffec205520a3f92f F src/update.c 729f6f18fc27740591d085e1172cebe311144bf0 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P d479e32be205f6cd0474f002282eae6eec613f36 -R 931ed67b9f38d30c31761dd7af84265b +P cf291cbe9f49396f03cfca39c2e892f27f750107 +R 9d22f3b27c328e6d3cb49e4853606989 U drh -Z 3cea3f1ee45c98cf88d87a6691b7a96c +Z 2221fbb0fe2956ed5002647d0de83cc0 diff --git a/manifest.uuid b/manifest.uuid index 29909b01ca..8d12ba50f3 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -cf291cbe9f49396f03cfca39c2e892f27f750107 \ No newline at end of file +9ee5686ab3b0bca8cabdf455c75bd9410cdc5378 \ No newline at end of file diff --git a/src/sqliteInt.h b/src/sqliteInt.h index 7998638c7f..e648430353 100644 --- a/src/sqliteInt.h +++ b/src/sqliteInt.h @@ -159,7 +159,7 @@ */ #if defined(__GNUC__) # define SQLITE_NOINLINE __attribute__((noinline)) -#elif defined(_MSC_VER) +#elif defined(_MSC_VER) && _MSC_VER>=1310 # define SQLITE_NOINLINE __declspec(noinline) #else # define SQLITE_NOINLINE diff --git a/src/threads.c b/src/threads.c index 213a129c99..6d39042fd9 100644 --- a/src/threads.c +++ b/src/threads.c @@ -105,7 +105,7 @@ int sqlite3ThreadJoin(SQLiteThread *p, void **ppOut){ /* A running thread */ struct SQLiteThread { - uintptr_t tid; /* The thread handle */ + void *tid; /* The thread handle */ unsigned id; /* The thread identifier */ void *(*xTask)(void*); /* The routine to run as a thread */ void *pIn; /* Argument to xTask */ @@ -153,7 +153,7 @@ int sqlite3ThreadCreate( }else{ p->xTask = xTask; p->pIn = pIn; - p->tid = _beginthreadex(0, 0, sqlite3ThreadProc, p, 0, &p->id); + p->tid = (void*)_beginthreadex(0, 0, sqlite3ThreadProc, p, 0, &p->id); if( p->tid==0 ){ memset(p, 0, sizeof(*p)); } From 5bd8af7c6b9b0b3947d1da11311af25dee1875b4 Mon Sep 17 00:00:00 2001 From: dan Date: Fri, 10 Oct 2014 19:10:59 +0000 Subject: [PATCH 44/54] Fix a failing test case in index5.test. Also tweak the way cache memory is divided between read-only and dirty pages when using SQLITE_CONFIG_PAGECACHE to reduce IO in some cases. FossilOrigin-Name: 8541dfb3bbdf63dc9ab304d8a0ab8b290cdc9d96 --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/pcache1.c | 2 +- test/index5.test | 5 ++++- 4 files changed, 14 insertions(+), 11 deletions(-) diff --git a/manifest b/manifest index fd3281f6c5..1b392cbba7 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Changes\sto\senable\scompiling\susing\sVC6. -D 2014-10-10T18:09:52.113 +C Fix\sa\sfailing\stest\scase\sin\sindex5.test.\sAlso\stweak\sthe\sway\scache\smemory\sis\sdivided\sbetween\sread-only\sand\sdirty\spages\swhen\susing\sSQLITE_CONFIG_PAGECACHE\sto\sreduce\sIO\sin\ssome\scases. +D 2014-10-10T19:10:59.145 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -220,7 +220,7 @@ F src/pager.h ffd5607f7b3e4590b415b007a4382f693334d428 F src/parse.y 5dfead8aed90cb0c7c1115898ee2266804daff45 F src/pcache.c 4121a0571c18581ee9f82f086d5e2030051ebd6a F src/pcache.h 9b559127b83f84ff76d735c8262f04853be0c59a -F src/pcache1.c dab8ab930d4a73b99768d881185994f34b80ecaa +F src/pcache1.c e412cb585f777c840ddce0500eddc5c6043c2bb5 F src/pragma.c 3f3e959390a10c0131676f0e307acce372777e0f F src/prepare.c 6ef0cf2f9274982988ed6b7cab1be23147e94196 F src/printf.c 6b79bbd063dcbadca4cf617a4cde255bcc13ea64 @@ -631,7 +631,7 @@ F test/index.test 4d990005a67a36984e4f1a5f1bdccea8d08da4ee F test/index2.test ee83c6b5e3173a3d7137140d945d9a5d4fdfb9d6 F test/index3.test 55a90cff99834305e8141df7afaef39674b57062 F test/index4.test ab92e736d5946840236cd61ac3191f91a7856bf6 -F test/index5.test fc07c14193c0430814e7a08b5da46888ee795c33 +F test/index5.test 25b0b451aceed4ac5f7d49f856f6de7257470b3e F test/index6.test fb370966ac3cd0989053dd5385757b5c3e24ab6a F test/index7.test 917cf1e1c7439bb155abbeabec511b28945e157b F test/indexedby.test b2f22f3e693a53813aa3f50b812eb609ba6df1ec @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P cf291cbe9f49396f03cfca39c2e892f27f750107 -R 9d22f3b27c328e6d3cb49e4853606989 -U drh -Z 2221fbb0fe2956ed5002647d0de83cc0 +P 9ee5686ab3b0bca8cabdf455c75bd9410cdc5378 +R a867243fa8e0f0e41c6d9028f2d48296 +U dan +Z 113af8b0b8de7f680d672bce9ecfd1d0 diff --git a/manifest.uuid b/manifest.uuid index 8d12ba50f3..14bf033b25 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -9ee5686ab3b0bca8cabdf455c75bd9410cdc5378 \ No newline at end of file +8541dfb3bbdf63dc9ab304d8a0ab8b290cdc9d96 \ No newline at end of file diff --git a/src/pcache1.c b/src/pcache1.c index 9d15e8514c..a8c3217382 100644 --- a/src/pcache1.c +++ b/src/pcache1.c @@ -688,7 +688,7 @@ static SQLITE_NOINLINE PgHdr1 *pcache1FetchStage2( if( createFlag==1 && ( nPinned>=pGroup->mxPinned || nPinned>=pCache->n90pct - || pcache1UnderMemoryPressure(pCache) + || (pcache1UnderMemoryPressure(pCache) && pCache->nRecyclable Date: Fri, 10 Oct 2014 19:15:35 +0000 Subject: [PATCH 45/54] Restrict the scope of the explainIndexRange() function in where.c. FossilOrigin-Name: c30124520027f0f860223bf842e2f09db3dafb5f --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/where.c | 2 +- 3 files changed, 9 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 1b392cbba7..d84631e220 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sa\sfailing\stest\scase\sin\sindex5.test.\sAlso\stweak\sthe\sway\scache\smemory\sis\sdivided\sbetween\sread-only\sand\sdirty\spages\swhen\susing\sSQLITE_CONFIG_PAGECACHE\sto\sreduce\sIO\sin\ssome\scases. -D 2014-10-10T19:10:59.145 +C Restrict\sthe\sscope\sof\sthe\sexplainIndexRange()\sfunction\sin\swhere.c. +D 2014-10-10T19:15:35.023 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c b511252533ca9f70e6adfc0ffd5c82594df137a2 +F src/where.c 75af78b4a4125e891f62d997d6d93b006a8c7d68 F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 9ee5686ab3b0bca8cabdf455c75bd9410cdc5378 -R a867243fa8e0f0e41c6d9028f2d48296 -U dan -Z 113af8b0b8de7f680d672bce9ecfd1d0 +P 8541dfb3bbdf63dc9ab304d8a0ab8b290cdc9d96 +R 56927b83c6bc9f8ed8f382263f0b3a19 +U drh +Z 9069bb5e423e6471fadcdc96cb083909 diff --git a/manifest.uuid b/manifest.uuid index 14bf033b25..ced410d581 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -8541dfb3bbdf63dc9ab304d8a0ab8b290cdc9d96 \ No newline at end of file +c30124520027f0f860223bf842e2f09db3dafb5f \ No newline at end of file diff --git a/src/where.c b/src/where.c index 5b639946cf..bd59055b4a 100644 --- a/src/where.c +++ b/src/where.c @@ -2749,7 +2749,7 @@ static void explainAppendTerm( ** ** "a=? AND b>?" */ -void explainIndexRange(StrAccum *pStr, WhereLoop *pLoop, Table *pTab){ +static void explainIndexRange(StrAccum *pStr, WhereLoop *pLoop, Table *pTab){ Index *pIndex = pLoop->u.btree.pIndex; u16 nEq = pLoop->u.btree.nEq; u16 nSkip = pLoop->u.btree.nSkip; From b6453201d2ec13d7c71da62e2d11cae427d3bf04 Mon Sep 17 00:00:00 2001 From: dan Date: Fri, 10 Oct 2014 20:52:53 +0000 Subject: [PATCH 46/54] Account for the ASC/DESC properties of ORDER BY expressions when using the same index for GROUP BY and ORDER BY. Candidate fix for [ba7cbfaedc]. FossilOrigin-Name: 2a9573962b837973c4959465d8a5f2641d109a5a --- manifest | 18 ++++++----- manifest.uuid | 2 +- src/where.c | 17 +++++++---- test/tkt-ba7cbfaedc.test | 65 ++++++++++++++++++++++++++++++++++++++++ 4 files changed, 89 insertions(+), 13 deletions(-) create mode 100644 test/tkt-ba7cbfaedc.test diff --git a/manifest b/manifest index d84631e220..ced935d9a0 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Restrict\sthe\sscope\sof\sthe\sexplainIndexRange()\sfunction\sin\swhere.c. -D 2014-10-10T19:15:35.023 +C Account\sfor\sthe\sASC/DESC\sproperties\sof\sORDER\sBY\sexpressions\swhen\susing\sthe\ssame\sindex\sfor\sGROUP\sBY\sand\sORDER\sBY.\sCandidate\sfix\sfor\s[ba7cbfaedc]. +D 2014-10-10T20:52:53.529 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 75af78b4a4125e891f62d997d6d93b006a8c7d68 +F src/where.c 7137da023fa550b44f98251ab6fcf132ce4e371e F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -933,6 +933,7 @@ F test/tkt-b1d3a2e531.test 8f7576e41ca179289ee1a8fee28386fd8e4b0550 F test/tkt-b351d95f9.test d14a503c414c5c58fdde3e80f9a3cfef986498c0 F test/tkt-b72787b1.test a95e8cdad0b98af1853ac7f0afd4ab27b77bf5f3 F test/tkt-b75a9ca6b0.test 97cc2d5eeaf82799eb42138c0a1ff64370238ce4 +F test/tkt-ba7cbfaedc.test e76d88e572e489ee0d64fe4caf4af18b3d1dc688 F test/tkt-bd484a090c.test 60460bf946f79a79712b71f202eda501ca99b898 F test/tkt-bdc6bbbb38.test fc38bb09bdd440e3513a1f5f98fc60a075182d7d F test/tkt-c48d99d690.test ba61977d62ab612fc515b3c488a6fbd6464a2447 @@ -1203,7 +1204,10 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 8541dfb3bbdf63dc9ab304d8a0ab8b290cdc9d96 -R 56927b83c6bc9f8ed8f382263f0b3a19 -U drh -Z 9069bb5e423e6471fadcdc96cb083909 +P c30124520027f0f860223bf842e2f09db3dafb5f +R 8de40b978c4dd5c8456f5f796f63e003 +T *branch * experimental +T *sym-experimental * +T -sym-trunk * +U dan +Z 060424e4e85bb8595890bea0de65ac0e diff --git a/manifest.uuid b/manifest.uuid index ced410d581..604705047d 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -c30124520027f0f860223bf842e2f09db3dafb5f \ No newline at end of file +2a9573962b837973c4959465d8a5f2641d109a5a \ No newline at end of file diff --git a/src/where.c b/src/where.c index bd59055b4a..6a5e918669 100644 --- a/src/where.c +++ b/src/where.c @@ -5827,12 +5827,19 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ if( (pWInfo->wctrlFlags & WHERE_SORTBYGROUP) && pWInfo->nOBSat==pWInfo->pOrderBy->nExpr ){ - Bitmask notUsed = 0; - int nOrder = wherePathSatisfiesOrderBy(pWInfo, pWInfo->pOrderBy, - pFrom, 0, nLoop-1, pFrom->aLoop[nLoop-1], ¬Used - ); + Bitmask revMask = 0; + int nOrder; + assert( pWInfo->wctrlFlags & WHERE_GROUPBY ); assert( pWInfo->sorted==0 ); - pWInfo->sorted = (nOrder==pWInfo->pOrderBy->nExpr); + pWInfo->wctrlFlags &= ~WHERE_GROUPBY; + nOrder = wherePathSatisfiesOrderBy(pWInfo, pWInfo->pOrderBy, + pFrom, 0, nLoop-1, pFrom->aLoop[nLoop-1], &revMask + ); + pWInfo->wctrlFlags |= WHERE_GROUPBY; + if( nOrder==pWInfo->pOrderBy->nExpr ){ + pWInfo->sorted = 1; + pWInfo->revMask = revMask; + } } } diff --git a/test/tkt-ba7cbfaedc.test b/test/tkt-ba7cbfaedc.test new file mode 100644 index 0000000000..a558d4cec3 --- /dev/null +++ b/test/tkt-ba7cbfaedc.test @@ -0,0 +1,65 @@ +# 2014-10-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. +# +#************************************************************************* +# +# Test that ticket [ba7cbfaedc] has been fixed. +# + +set testdir [file dirname $argv0] +source $testdir/tester.tcl +set testprefix tkt-ba7cbfaedc + +do_execsql_test 1 { + CREATE TABLE t1 (x, y); + INSERT INTO t1 VALUES (3, 'a'); + INSERT INTO t1 VALUES (1, 'a'); + INSERT INTO t1 VALUES (2, 'b'); + INSERT INTO t1 VALUES (2, 'a'); + INSERT INTO t1 VALUES (3, 'b'); + INSERT INTO t1 VALUES (1, 'b'); +} + +do_execsql_test 1.1 { + CREATE INDEX i1 ON t1(x, y); +} + +foreach {n idx} { + 1 { CREATE INDEX i1 ON t1(x, y) } + 2 { CREATE INDEX i1 ON t1(x DESC, y) } + 3 { CREATE INDEX i1 ON t1(x, y DESC) } + 4 { CREATE INDEX i1 ON t1(x DESC, y DESC) } +} { + catchsql { DROP INDEX i1 } + execsql $idx + foreach {tn q res} { + 1 "GROUP BY x, y ORDER BY x, y" {1 a 1 b 2 a 2 b 3 a 3 b} + 2 "GROUP BY x, y ORDER BY x DESC, y" {3 a 3 b 2 a 2 b 1 a 1 b} + 3 "GROUP BY x, y ORDER BY x, y DESC" {1 b 1 a 2 b 2 a 3 b 3 a} + 4 "GROUP BY x, y ORDER BY x DESC, y DESC" {3 b 3 a 2 b 2 a 1 b 1 a} + } { + do_execsql_test 1.$n.$tn "SELECT * FROM t1 $q" $res + } +} + +do_execsql_test 2.0 { + drop table if exists t1; + create table t1(id int); + insert into t1(id) values(1),(2),(3),(4),(5); + create index t1_idx_id on t1(id asc); + select * from t1 group by id order by id; + select * from t1 group by id order by id asc; + select * from t1 group by id order by id desc; +} { + 1 2 3 4 5 1 2 3 4 5 5 4 3 2 1 +} + +finish_test + + From c631faa922b129adac37c2e26dd38e77897fcb7a Mon Sep 17 00:00:00 2001 From: drh Date: Sat, 11 Oct 2014 01:22:16 +0000 Subject: [PATCH 47/54] Remove an unnecessary conditional from the EXPLAIN QUERY PLAN logic. FossilOrigin-Name: c5dc83ebded914f07286b7f98d0a50c28c16f609 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/where.c | 4 +--- 3 files changed, 8 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index d84631e220..b8991f9317 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Restrict\sthe\sscope\sof\sthe\sexplainIndexRange()\sfunction\sin\swhere.c. -D 2014-10-10T19:15:35.023 +C Remove\san\sunnecessary\sconditional\sfrom\sthe\sEXPLAIN\sQUERY\sPLAN\slogic. +D 2014-10-11T01:22:16.169 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f F src/wal.c 10e7de7ce90865a68153f001a61f1d985cd17983 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 75af78b4a4125e891f62d997d6d93b006a8c7d68 +F src/where.c 45202a9a2848848a17b64316fe87bdb5a75f5910 F src/whereInt.h 124d970450955a6982e174b07c320ae6d62a595c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -1203,7 +1203,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 8541dfb3bbdf63dc9ab304d8a0ab8b290cdc9d96 -R 56927b83c6bc9f8ed8f382263f0b3a19 +P c30124520027f0f860223bf842e2f09db3dafb5f +R 76a395c9de317da89295170f9596fa71 U drh -Z 9069bb5e423e6471fadcdc96cb083909 +Z efd3e7a68804083aa9d3740b204464db diff --git a/manifest.uuid b/manifest.uuid index ced410d581..e90d20a635 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -c30124520027f0f860223bf842e2f09db3dafb5f \ No newline at end of file +c5dc83ebded914f07286b7f98d0a50c28c16f609 \ No newline at end of file diff --git a/src/where.c b/src/where.c index bd59055b4a..4aa208d2ee 100644 --- a/src/where.c +++ b/src/where.c @@ -2838,9 +2838,7 @@ static void explainOneScan( pIdx = pLoop->u.btree.pIndex; assert( !(flags&WHERE_AUTO_INDEX) || (flags&WHERE_IDX_ONLY) ); if( !HasRowid(pItem->pTab) && IsPrimaryKeyIndex(pIdx) ){ - if( pLoop->u.btree.nEq>0 - || (pLoop->wsFlags & (WHERE_BTM_LIMIT|WHERE_TOP_LIMIT))!=0 - ){ + if( isSearch ){ zFmt = "PRIMARY KEY"; } }else if( flags & WHERE_AUTO_INDEX ){ From 8683e08676d96538bc2cb05d04cbff4db110f890 Mon Sep 17 00:00:00 2001 From: drh Date: Sat, 11 Oct 2014 10:52:54 +0000 Subject: [PATCH 48/54] Require the SQLITE_ENABLE_RTREE compile-time option in speedtest1.c in order to enable the R-Tree tests. FossilOrigin-Name: 5d29a033b0f17b0fd74656b28a8367a9a9067f81 --- manifest | 13 ++++++------- manifest.uuid | 2 +- test/speedtest1.c | 11 +++++++++++ 3 files changed, 18 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 0395f4e8a7..f11096d9d2 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Make\ssure\sthat\sa\sGROUP\sBY\sthat\salso\simplements\san\sORDER\sBY\sscans\sthe\stable\nin\sthe\scorrect\sorder.\s\sFix\sfor\sticket\s[ba7cbfaedc7e6]. -D 2014-10-11T02:12:58.777 +C Require\sthe\sSQLITE_ENABLE_RTREE\scompile-time\soption\sin\sspeedtest1.c\sin\sorder\nto\senable\sthe\sR-Tree\stests. +D 2014-10-11T10:52:54.590 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -860,7 +860,7 @@ F test/speed3.test d32043614c08c53eafdc80f33191d5bd9b920523 F test/speed4.test abc0ad3399dcf9703abed2fff8705e4f8e416715 F test/speed4p.explain 6b5f104ebeb34a038b2f714150f51d01143e59aa F test/speed4p.test 0e51908951677de5a969b723e03a27a1c45db38b -F test/speedtest1.c 83f6b3318f7ee60e52b978b5a5e5dd7e83dfb7ee +F test/speedtest1.c e4e2aa37ff66bad9f414a50a8cb9edfaac65c9e5 F test/spellfix.test 24f676831acddd2f4056a598fd731a72c6311f49 F test/sqllimits1.test 9014524e7ab16e2a4976b13397db4c29cc29c6d9 F test/stat.test 76fd746b85459e812a0193410fb599f0531f22de @@ -1204,8 +1204,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P c5dc83ebded914f07286b7f98d0a50c28c16f609 2a9573962b837973c4959465d8a5f2641d109a5a -R 6f36f8a6a865ae8ec418dbbf6437f4b9 -T +closed 2a9573962b837973c4959465d8a5f2641d109a5a +P 7a32fdfd4be2138c0ab00f3dc6f54a70e4e07be4 +R 4281e286fbeeaa18c9716d9bb0cdd63c U drh -Z b85f219ca12b10b385d8fb433d0ee994 +Z 50870d5e316ccf74380338fbaf696334 diff --git a/manifest.uuid b/manifest.uuid index c394cc6a6e..44905c9e54 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -7a32fdfd4be2138c0ab00f3dc6f54a70e4e07be4 \ No newline at end of file +5d29a033b0f17b0fd74656b28a8367a9a9067f81 \ No newline at end of file diff --git a/test/speedtest1.c b/test/speedtest1.c index 8589b16333..8e5b74c56e 100644 --- a/test/speedtest1.c +++ b/test/speedtest1.c @@ -934,6 +934,7 @@ void testset_cte(void){ } +#ifdef SQLITE_ENABLE_RTREE /* Generate two numbers between 1 and mx. The first number is less than ** the second. Usually the numbers are near each other but can sometimes ** be far apart. @@ -954,7 +955,9 @@ static void twoCoords( *pX0 = x0; *pX1 = x1; } +#endif +#ifdef SQLITE_ENABLE_RTREE /* The following routine is an R-Tree geometry callback. It returns ** true if the object overlaps a slice on the Y coordinate between the ** two values given as arguments. In other words @@ -974,7 +977,9 @@ static int xsliceGeometryCallback( *pRes = aCoord[3]>=p->aParam[0] && aCoord[2]<=p->aParam[1]; return SQLITE_OK; } +#endif /* SQLITE_ENABLE_RTREE */ +#ifdef SQLITE_ENABLE_RTREE /* ** A testset for the R-Tree virtual table */ @@ -1110,6 +1115,7 @@ void testset_rtree(int p1, int p2){ } speedtest1_end_test(); } +#endif /* SQLITE_ENABLE_RTREE */ /* ** A testset used for debugging speedtest1 itself. @@ -1329,7 +1335,12 @@ int main(int argc, char **argv){ }else if( strcmp(zTSet,"cte")==0 ){ testset_cte(); }else if( strcmp(zTSet,"rtree")==0 ){ +#ifdef SQLITE_ENABLE_RTREE testset_rtree(6, 147); +#else + fatal_error("compile with -DSQLITE_ENABLE_RTREE to enable " + "the R-Tree tests\n"); +#endif }else{ fatal_error("unknown testset: \"%s\"\nChoices: main debug1 cte rtree\n", zTSet); From d6176c413164d7ea4240af9be56889a0461715be Mon Sep 17 00:00:00 2001 From: drh Date: Sat, 11 Oct 2014 17:22:55 +0000 Subject: [PATCH 49/54] Simplification to the insertCell() routine in btree.c, resulting in a performance boost and a very small size decrease. It turns out that the extra work involved in sometimes avoiding an memcpy() of the first four bytes of a record takes more time than just unconditionally copying those four bytes. FossilOrigin-Name: 66de15580d3c289601e67debfe1edee286f4db5f --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/btree.c | 10 ++-------- 3 files changed, 9 insertions(+), 15 deletions(-) diff --git a/manifest b/manifest index f11096d9d2..517771d6a6 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Require\sthe\sSQLITE_ENABLE_RTREE\scompile-time\soption\sin\sspeedtest1.c\sin\sorder\nto\senable\sthe\sR-Tree\stests. -D 2014-10-11T10:52:54.590 +C Simplification\sto\sthe\sinsertCell()\sroutine\sin\sbtree.c,\sresulting\sin\sa\nperformance\sboost\sand\sa\svery\ssmall\ssize\sdecrease.\s\sIt\sturns\sout\sthat\sthe\nextra\swork\sinvolved\sin\ssometimes\savoiding\san\smemcpy()\sof\sthe\sfirst\sfour\sbytes\nof\sa\srecord\stakes\smore\stime\sthan\sjust\sunconditionally\scopying\sthose\nfour\sbytes. +D 2014-10-11T17:22:55.486 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -172,7 +172,7 @@ F src/auth.c d8abcde53426275dab6243b441256fcd8ccbebb2 F src/backup.c a31809c65623cc41849b94d368917f8bb66e6a7e F src/bitvec.c 19a4ba637bd85f8f63fc8c9bae5ade9fb05ec1cb F src/btmutex.c 49ca66250c7dfa844a4d4cb8272b87420d27d3a5 -F src/btree.c fa00618117fb6bb46c243452c56997c0d22d4fc9 +F src/btree.c 5c0b78c49d00da49a0e8e3d2738900a431df7fca F src/btree.h a79aa6a71e7f1055f01052b7f821bd1c2dce95c8 F src/btreeInt.h 1bd7957161a1346a914f1f09231610e777a8e58d F src/build.c 9e5205db9a0c8a1a4ce7379d60a2a34cb0b7339c @@ -1204,7 +1204,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 7a32fdfd4be2138c0ab00f3dc6f54a70e4e07be4 -R 4281e286fbeeaa18c9716d9bb0cdd63c +P 5d29a033b0f17b0fd74656b28a8367a9a9067f81 +R 8d2ebada6cfcd93628f86065b0703bad U drh -Z 50870d5e316ccf74380338fbaf696334 +Z b915e33ee9cbdc5e832f0d58216a79da diff --git a/manifest.uuid b/manifest.uuid index 44905c9e54..e1067663de 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -5d29a033b0f17b0fd74656b28a8367a9a9067f81 \ No newline at end of file +66de15580d3c289601e67debfe1edee286f4db5f \ No newline at end of file diff --git a/src/btree.c b/src/btree.c index 12dcb44cba..cfe623342a 100644 --- a/src/btree.c +++ b/src/btree.c @@ -5845,11 +5845,6 @@ static void dropCell(MemPage *pPage, int idx, int sz, int *pRC){ ** in pTemp or the original pCell) and also record its index. ** Allocating a new entry in pPage->aCell[] implies that ** pPage->nOverflow is incremented. -** -** If nSkip is non-zero, then do not copy the first nSkip bytes of the -** cell. The caller will overwrite them after this function returns. If -** nSkip is non-zero, then pCell may not point to an invalid memory location -** (but pCell+nSkip is always valid). */ static void insertCell( MemPage *pPage, /* Page into which we are copying */ @@ -5866,7 +5861,6 @@ static void insertCell( int ins; /* Index in data[] where new cell pointer is inserted */ int cellOffset; /* Address of first cell pointer in data[] */ u8 *data; /* The content of the whole page */ - int nSkip = (iChild ? 4 : 0); if( *pRC ) return; @@ -5884,7 +5878,7 @@ static void insertCell( assert( sz==cellSizePtr(pPage, pCell) || (sz==8 && iChild>0) ); if( pPage->nOverflow || sz+2>pPage->nFree ){ if( pTemp ){ - memcpy(pTemp+nSkip, pCell+nSkip, sz-nSkip); + memcpy(pTemp, pCell, sz); pCell = pTemp; } if( iChild ){ @@ -5913,7 +5907,7 @@ static void insertCell( assert( idx+sz <= (int)pPage->pBt->usableSize ); pPage->nCell++; pPage->nFree -= (u16)(2 + sz); - memcpy(&data[idx+nSkip], pCell+nSkip, sz-nSkip); + memcpy(&data[idx], pCell, sz); if( iChild ){ put4byte(&data[idx], iChild); } From c81aa2e1203c4e3aa389f69e715c019f50fe1420 Mon Sep 17 00:00:00 2001 From: drh Date: Sat, 11 Oct 2014 23:31:52 +0000 Subject: [PATCH 50/54] Performance optimization and very slight size reduction for OP_Column. FossilOrigin-Name: 869c30e45cc87063be423c650f16b99e8adb3df0 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/vdbe.c | 25 +++++++++++++++++-------- 3 files changed, 24 insertions(+), 15 deletions(-) diff --git a/manifest b/manifest index 517771d6a6..62b5d0c870 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Simplification\sto\sthe\sinsertCell()\sroutine\sin\sbtree.c,\sresulting\sin\sa\nperformance\sboost\sand\sa\svery\ssmall\ssize\sdecrease.\s\sIt\sturns\sout\sthat\sthe\nextra\swork\sinvolved\sin\ssometimes\savoiding\san\smemcpy()\sof\sthe\sfirst\sfour\sbytes\nof\sa\srecord\stakes\smore\stime\sthan\sjust\sunconditionally\scopying\sthose\nfour\sbytes. -D 2014-10-11T17:22:55.486 +C Performance\soptimization\sand\svery\sslight\ssize\sreduction\sfor\sOP_Column. +D 2014-10-11T23:31:52.159 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -289,7 +289,7 @@ F src/update.c 729f6f18fc27740591d085e1172cebe311144bf0 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 4006c01772bd8d8ac4306d523bbcee41d3e392d8 F src/vacuum.c 59f03f92bcff57faa6a8ca256eb29ccddfb0614a -F src/vdbe.c fee8286ff026bb9cf96ce87971b60aba53863b78 +F src/vdbe.c 58c19340f009d29b63d3701bd1871aad03e4c134 F src/vdbe.h 09f5b4e3719fa454f252322b1cdab5cf1f361327 F src/vdbeInt.h 0b97a3190f8fbf460655985a9183019f5a702754 F src/vdbeapi.c 37a6c6ae284a97bcace365f2f0a225680c0499d9 @@ -1204,7 +1204,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 5d29a033b0f17b0fd74656b28a8367a9a9067f81 -R 8d2ebada6cfcd93628f86065b0703bad +P 66de15580d3c289601e67debfe1edee286f4db5f +R 512122d0d240ac7f0b4d899edd214ecb U drh -Z b915e33ee9cbdc5e832f0d58216a79da +Z 7a9b66d8d53ebbf7b4743296d025a097 diff --git a/manifest.uuid b/manifest.uuid index e1067663de..2c31982904 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -66de15580d3c289601e67debfe1edee286f4db5f \ No newline at end of file +869c30e45cc87063be423c650f16b99e8adb3df0 \ No newline at end of file diff --git a/src/vdbe.c b/src/vdbe.c index c039dcc862..8223d21611 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -2332,14 +2332,6 @@ case OP_Column: { pC->iHdrOffset = getVarint32(pC->aRow, offset); pC->nHdrParsed = 0; aOffset[0] = offset; - if( availaRow does not have to hold the entire row, but it does at least - ** need to cover the header of the record. If pC->aRow does not contain - ** the complete header, then set it to zero, forcing the header to be - ** dynamically allocated. */ - pC->aRow = 0; - pC->szRow = 0; - } /* Make sure a corrupt database has not given us an oversize header. ** Do this now to avoid an oversize memory allocation. @@ -2354,6 +2346,22 @@ case OP_Column: { rc = SQLITE_CORRUPT_BKPT; goto op_column_error; } + + if( availaRow does not have to hold the entire row, but it does at least + ** need to cover the header of the record. If pC->aRow does not contain + ** the complete header, then set it to zero, forcing the header to be + ** dynamically allocated. */ + pC->aRow = 0; + pC->szRow = 0; + } + + /* The following goto is an optimization. It can be omitted and + ** everything will still work. But OP_Column is measurably faster + ** by skipping the subsequent conditional, which is always true. + */ + assert( pC->nHdrParsed<=p2 ); /* Conditional skipped */ + goto op_column_read_header; } /* Make sure at least the first p2+1 entries of the header have been @@ -2363,6 +2371,7 @@ case OP_Column: { /* If there is more header available for parsing in the record, try ** to extract additional fields up through the p2+1-th field */ + op_column_read_header: if( pC->iHdrOffsetaRow==0 ){ From b53a5a9e50d376a6cda897ce629f4af55b96c193 Mon Sep 17 00:00:00 2001 From: drh Date: Sun, 12 Oct 2014 22:37:22 +0000 Subject: [PATCH 51/54] Remove the VdbeCursor.lastRowid cache of the current rowid, since maintaining the correct cache value uses more CPU cycles than just recomputing the rowid on the occasions when it is actually needed. Replace it with the VdbeCursor.aOffset field which used to be computed from VdbeCursor.aType when needed. Saves 100 bytes of code space and runs 0.2% faster. FossilOrigin-Name: 91384a7d727ef0f285cd430e829ba9f3852db50e --- manifest | 16 +++++++-------- manifest.uuid | 2 +- src/vdbe.c | 56 +++++++++++++++++---------------------------------- src/vdbeInt.h | 3 +-- src/vdbeaux.c | 2 -- 5 files changed, 28 insertions(+), 51 deletions(-) diff --git a/manifest b/manifest index 62b5d0c870..0d0dc6d249 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Performance\soptimization\sand\svery\sslight\ssize\sreduction\sfor\sOP_Column. -D 2014-10-11T23:31:52.159 +C Remove\sthe\sVdbeCursor.lastRowid\scache\sof\sthe\scurrent\srowid,\ssince\smaintaining\nthe\scorrect\scache\svalue\suses\smore\sCPU\scycles\sthan\sjust\srecomputing\sthe\srowid\non\sthe\soccasions\swhen\sit\sis\sactually\sneeded.\s\sReplace\sit\swith\sthe\nVdbeCursor.aOffset\sfield\swhich\sused\sto\sbe\scomputed\sfrom\sVdbeCursor.aType\nwhen\sneeded.\sSaves\s100\sbytes\sof\scode\sspace\sand\sruns\s0.2%\sfaster. +D 2014-10-12T22:37:22.384 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -289,11 +289,11 @@ F src/update.c 729f6f18fc27740591d085e1172cebe311144bf0 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 4006c01772bd8d8ac4306d523bbcee41d3e392d8 F src/vacuum.c 59f03f92bcff57faa6a8ca256eb29ccddfb0614a -F src/vdbe.c 58c19340f009d29b63d3701bd1871aad03e4c134 +F src/vdbe.c 97c6c50e272ed531bc3af308d5f156cfca0ce4f4 F src/vdbe.h 09f5b4e3719fa454f252322b1cdab5cf1f361327 -F src/vdbeInt.h 0b97a3190f8fbf460655985a9183019f5a702754 +F src/vdbeInt.h e1173bd72b282633c2ec8f3a2f78b5117229f268 F src/vdbeapi.c 37a6c6ae284a97bcace365f2f0a225680c0499d9 -F src/vdbeaux.c 5b687d7b5beaaa5b97189edf25cf08c311834933 +F src/vdbeaux.c e223d15ab39c844c04ad19931e8c71966c20c68d F src/vdbeblob.c 848238dc73e93e48432991bb5651bf87d865eca4 F src/vdbemem.c 481327f50d9da330053aa7456702ce46d0a4e70f F src/vdbesort.c 5c1bacf90578d22b630fbf6ed98ccf60d83435ef @@ -1204,7 +1204,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 66de15580d3c289601e67debfe1edee286f4db5f -R 512122d0d240ac7f0b4d899edd214ecb +P 869c30e45cc87063be423c650f16b99e8adb3df0 +R d569318d3e6a6b025c49ffecae9bf7d4 U drh -Z 7a9b66d8d53ebbf7b4743296d025a097 +Z e6cf351e034f82bffef92232dfc65ffe diff --git a/manifest.uuid b/manifest.uuid index 2c31982904..a04b930976 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -869c30e45cc87063be423c650f16b99e8adb3df0 \ No newline at end of file +91384a7d727ef0f285cd430e829ba9f3852db50e \ No newline at end of file diff --git a/src/vdbe.c b/src/vdbe.c index 8223d21611..347b604bf4 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -214,6 +214,7 @@ static VdbeCursor *allocateCursor( memset(pCx, 0, sizeof(VdbeCursor)); pCx->iDb = iDb; pCx->nField = nField; + pCx->aOffset = &pCx->aType[nField]; if( isBtreeCursor ){ pCx->pCursor = (BtCursor*) &pMem->z[ROUND8(sizeof(VdbeCursor))+2*sizeof(u32)*nField]; @@ -2276,7 +2277,7 @@ case OP_Column: { pC = p->apCsr[pOp->p1]; assert( pC!=0 ); assert( p2nField ); - aOffset = pC->aType + pC->nField; + aOffset = pC->aOffset; #ifndef SQLITE_OMIT_VIRTUALTABLE assert( pC->pVtabCursor==0 ); /* OP_Column never called on virtual table */ #endif @@ -3563,7 +3564,6 @@ case OP_SeekGT: { /* jump, in3 */ applyNumericAffinity(pIn3, 0); } iKey = sqlite3VdbeIntValue(pIn3); - pC->rowidIsValid = 0; /* If the P3 value could not be converted into an integer without ** loss of information, then special processing is required... */ @@ -3599,13 +3599,10 @@ case OP_SeekGT: { /* jump, in3 */ } } rc = sqlite3BtreeMovetoUnpacked(pC->pCursor, 0, (u64)iKey, 0, &res); + pC->movetoTarget = iKey; /* Used by OP_Delete */ if( rc!=SQLITE_OK ){ goto abort_due_to_error; } - if( res==0 ){ - pC->rowidIsValid = 1; - pC->lastRowid = iKey; - } }else{ nField = pOp->p4.i; assert( pOp->p4type==P4_INT32 ); @@ -3635,7 +3632,6 @@ case OP_SeekGT: { /* jump, in3 */ if( rc!=SQLITE_OK ){ goto abort_due_to_error; } - pC->rowidIsValid = 0; } pC->deferredMoveto = 0; pC->cacheStatus = CACHE_STALE; @@ -3647,7 +3643,6 @@ case OP_SeekGT: { /* jump, in3 */ res = 0; rc = sqlite3BtreeNext(pC->pCursor, &res); if( rc!=SQLITE_OK ) goto abort_due_to_error; - pC->rowidIsValid = 0; }else{ res = 0; } @@ -3657,7 +3652,6 @@ case OP_SeekGT: { /* jump, in3 */ res = 0; rc = sqlite3BtreePrevious(pC->pCursor, &res); if( rc!=SQLITE_OK ) goto abort_due_to_error; - pC->rowidIsValid = 0; }else{ /* res might be negative because the table is empty. Check to ** see if this is the case. @@ -3694,7 +3688,6 @@ case OP_Seek: { /* in2 */ pC->nullRow = 0; pIn2 = &aMem[pOp->p2]; pC->movetoTarget = sqlite3VdbeIntValue(pIn2); - pC->rowidIsValid = 0; pC->deferredMoveto = 1; break; } @@ -3880,15 +3873,13 @@ case OP_NotExists: { /* jump, in3 */ res = 0; iKey = pIn3->u.i; rc = sqlite3BtreeMovetoUnpacked(pCrsr, 0, iKey, 0, &res); - pC->lastRowid = pIn3->u.i; - pC->rowidIsValid = res==0 ?1:0; + pC->movetoTarget = iKey; /* Used by OP_Delete */ pC->nullRow = 0; pC->cacheStatus = CACHE_STALE; pC->deferredMoveto = 0; VdbeBranchTaken(res!=0,2); if( res!=0 ){ pc = pOp->p2 - 1; - assert( pC->rowidIsValid==0 ); } pC->seekResult = res; break; @@ -4036,7 +4027,6 @@ case OP_NewRowid: { /* out2-prerelease */ } assert( v>0 ); /* EV: R-40812-03570 */ } - pC->rowidIsValid = 0; pC->deferredMoveto = 0; pC->cacheStatus = CACHE_STALE; } @@ -4141,7 +4131,6 @@ case OP_InsertInt: { pData->z, pData->n, nZero, (pOp->p5 & OPFLAG_APPEND)!=0, seekResult ); - pC->rowidIsValid = 0; pC->deferredMoveto = 0; pC->cacheStatus = CACHE_STALE; @@ -4178,33 +4167,32 @@ case OP_InsertInt: { ** using OP_NotFound prior to invoking this opcode. */ case OP_Delete: { - i64 iKey; VdbeCursor *pC; assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); assert( pC->pCursor!=0 ); /* Only valid for real tables, no pseudotables */ - iKey = pC->lastRowid; /* Only used for the update hook */ - - /* The OP_Delete opcode always follows an OP_NotExists or OP_Last or - ** OP_Column on the same table without any intervening operations that - ** might move or invalidate the cursor. Hence cursor pC is always pointing - ** to the row to be deleted and the sqlite3VdbeCursorMoveto() operation - ** below is always a no-op and cannot fail. We will run it anyhow, though, - ** to guard against future changes to the code generator. - **/ assert( pC->deferredMoveto==0 ); - rc = sqlite3VdbeCursorMoveto(pC); - if( NEVER(rc!=SQLITE_OK) ) goto abort_due_to_error; +#ifdef SQLITE_DEBUG + /* The seek operation that positioned the cursor prior to OP_Delete will + ** have also set the pC->movetoTarget field to the rowid of the row that + ** is being deleted */ + if( pOp->p4.z && pC->isTable ){ + i64 iKey = 0; + sqlite3BtreeKeySize(pC->pCursor, &iKey); + assert( pC->movetoTarget==iKey ); + } +#endif + rc = sqlite3BtreeDelete(pC->pCursor); pC->cacheStatus = CACHE_STALE; /* Invoke the update-hook if required. */ if( rc==SQLITE_OK && db->xUpdateCallback && pOp->p4.z && pC->isTable ){ db->xUpdateCallback(db->pUpdateArg, SQLITE_DELETE, - db->aDb[pC->iDb].zName, pOp->p4.z, iKey); + db->aDb[pC->iDb].zName, pOp->p4.z, pC->movetoTarget); assert( pC->iDb>=0 ); } if( pOp->p2 & OPFLAG_NCHANGE ) p->nChange++; @@ -4396,12 +4384,8 @@ case OP_Rowid: { /* out2-prerelease */ assert( pC->pCursor!=0 ); rc = sqlite3VdbeCursorMoveto(pC); if( rc ) goto abort_due_to_error; - if( pC->rowidIsValid ){ - v = pC->lastRowid; - }else{ - rc = sqlite3BtreeKeySize(pC->pCursor, &v); - assert( rc==SQLITE_OK ); /* Always so because of CursorMoveto() above */ - } + rc = sqlite3BtreeKeySize(pC->pCursor, &v); + assert( rc==SQLITE_OK ); /* Always so because of CursorMoveto() above */ } pOut->u.i = v; break; @@ -4420,7 +4404,6 @@ case OP_NullRow: { pC = p->apCsr[pOp->p1]; assert( pC!=0 ); pC->nullRow = 1; - pC->rowidIsValid = 0; pC->cacheStatus = CACHE_STALE; if( pC->pCursor ){ sqlite3BtreeClearCursor(pC->pCursor); @@ -4454,7 +4437,6 @@ case OP_Last: { /* jump */ rc = sqlite3BtreeLast(pCrsr, &res); pC->nullRow = (u8)res; pC->deferredMoveto = 0; - pC->rowidIsValid = 0; pC->cacheStatus = CACHE_STALE; #ifdef SQLITE_DEBUG pC->seekOp = OP_Last; @@ -4521,7 +4503,6 @@ case OP_Rewind: { /* jump */ rc = sqlite3BtreeFirst(pCrsr, &res); pC->deferredMoveto = 0; pC->cacheStatus = CACHE_STALE; - pC->rowidIsValid = 0; } pC->nullRow = (u8)res; assert( pOp->p2>0 && pOp->p2nOp ); @@ -4647,7 +4628,6 @@ next_tail: }else{ pC->nullRow = 1; } - pC->rowidIsValid = 0; goto check_for_interrupt; } diff --git a/src/vdbeInt.h b/src/vdbeInt.h index aa1132e31c..1c7bebc9f6 100644 --- a/src/vdbeInt.h +++ b/src/vdbeInt.h @@ -73,7 +73,6 @@ struct VdbeCursor { #endif i8 iDb; /* Index of cursor database in db->aDb[] (or -1) */ u8 nullRow; /* True if pointing to a row with no data */ - u8 rowidIsValid; /* True if lastRowid is valid */ u8 deferredMoveto; /* A call to sqlite3BtreeMoveto() is needed */ Bool isEphemeral:1; /* True for an ephemeral table */ Bool useRandomRowid:1;/* Generate new record numbers semi-randomly */ @@ -83,7 +82,6 @@ struct VdbeCursor { sqlite3_vtab_cursor *pVtabCursor; /* The cursor for a virtual table */ i64 seqCount; /* Sequence counter */ i64 movetoTarget; /* Argument to the deferred sqlite3BtreeMoveto() */ - i64 lastRowid; /* Rowid being deleted by OP_Delete */ VdbeSorter *pSorter; /* Sorter object for OP_SorterOpen cursors */ /* Cached information about the header for the data record that the @@ -100,6 +98,7 @@ struct VdbeCursor { u32 szRow; /* Byte available in aRow */ u32 iHdrOffset; /* Offset to next unparsed byte of the header */ const u8 *aRow; /* Data for the current row, if all on one page */ + u32 *aOffset; /* Pointer to aType[nField] */ u32 aType[1]; /* Type values for all entries in the record */ /* 2*nField extra array elements allocated for aType[], beyond the one ** static element declared in the structure. nField total array slots for diff --git a/src/vdbeaux.c b/src/vdbeaux.c index 33fa055369..fefa0ef337 100644 --- a/src/vdbeaux.c +++ b/src/vdbeaux.c @@ -2718,9 +2718,7 @@ static int SQLITE_NOINLINE handleDeferredMoveto(VdbeCursor *p){ assert( p->isTable ); rc = sqlite3BtreeMovetoUnpacked(p->pCursor, 0, p->movetoTarget, 0, &res); if( rc ) return rc; - p->lastRowid = p->movetoTarget; if( res!=0 ) return SQLITE_CORRUPT_BKPT; - p->rowidIsValid = 1; #ifdef SQLITE_TEST sqlite3_search_count++; #endif From 6cf4a7dfa65fb5c4d16aca12d1065bd04257c831 Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 13 Oct 2014 13:00:58 +0000 Subject: [PATCH 52/54] Remove the OPFLAG_CLEARCACHE flag from OP_Column. In its place, change the P3 parameter of OP_SorterData to be the index of the pseudo-table cursor whose record header cache is to be cleared. This gives a small size reduction and performance increase. FossilOrigin-Name: 20062f49428a2349a2dd705af570c60b499a3eef --- manifest | 18 +++++++++--------- manifest.uuid | 2 +- src/build.c | 2 +- src/select.c | 9 ++------- src/sqliteInt.h | 1 - src/vdbe.c | 13 +++++++++++-- 6 files changed, 24 insertions(+), 21 deletions(-) diff --git a/manifest b/manifest index 0d0dc6d249..ea3a0d9c70 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\sthe\sVdbeCursor.lastRowid\scache\sof\sthe\scurrent\srowid,\ssince\smaintaining\nthe\scorrect\scache\svalue\suses\smore\sCPU\scycles\sthan\sjust\srecomputing\sthe\srowid\non\sthe\soccasions\swhen\sit\sis\sactually\sneeded.\s\sReplace\sit\swith\sthe\nVdbeCursor.aOffset\sfield\swhich\sused\sto\sbe\scomputed\sfrom\sVdbeCursor.aType\nwhen\sneeded.\sSaves\s100\sbytes\sof\scode\sspace\sand\sruns\s0.2%\sfaster. -D 2014-10-12T22:37:22.384 +C Remove\sthe\sOPFLAG_CLEARCACHE\sflag\sfrom\sOP_Column.\s\sIn\sits\splace,\schange\sthe\nP3\sparameter\sof\sOP_SorterData\sto\sbe\sthe\sindex\sof\sthe\spseudo-table\scursor\swhose\nrecord\sheader\scache\sis\sto\sbe\scleared.\s\sThis\sgives\sa\ssmall\ssize\sreduction\nand\sperformance\sincrease. +D 2014-10-13T13:00:58.198 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -175,7 +175,7 @@ F src/btmutex.c 49ca66250c7dfa844a4d4cb8272b87420d27d3a5 F src/btree.c 5c0b78c49d00da49a0e8e3d2738900a431df7fca F src/btree.h a79aa6a71e7f1055f01052b7f821bd1c2dce95c8 F src/btreeInt.h 1bd7957161a1346a914f1f09231610e777a8e58d -F src/build.c 9e5205db9a0c8a1a4ce7379d60a2a34cb0b7339c +F src/build.c 9dc2bd94347b878c89627000c92b0c8d97ec2919 F src/callback.c 7b44ce59674338ad48b0e84e7b72f935ea4f68b0 F src/complete.c 535183afb3c75628b78ce82612931ac7cdf26f14 F src/ctime.c bb434068b5308a857b181c2d204a320ff0d6c638 @@ -227,12 +227,12 @@ F src/printf.c 6b79bbd063dcbadca4cf617a4cde255bcc13ea64 F src/random.c d10c1f85b6709ca97278428fd5db5bbb9c74eece F src/resolve.c a3466128b52a86c466e47ac1a19e2174f7b5cf89 F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e -F src/select.c f11533162b57ed5ed37f549add34cbcdf51f6712 +F src/select.c 428165951748151e87a15295b7357221433e311b F src/shell.c 18ee8bbe9502d8848072dc2eddd1ea09254ba494 F src/sqlite.h.in 4a5e5158c189d2bcd45c7c4607c2c0eb6d25c153 F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d -F src/sqliteInt.h c417a25e2369f705b651897a2f1cc8da0e6aa1c4 +F src/sqliteInt.h f7812f74f2d0c6041ef6b91a99c5a45f775dd408 F src/sqliteLimit.h 164b0e6749d31e0daa1a4589a169d31c0dec7b3d F src/status.c 961d5926e5a8fda611d385ec22c226b8635cd1cb F src/table.c 2e99ef7ef16187e17033d9398dc962ce22dab5cb @@ -289,7 +289,7 @@ F src/update.c 729f6f18fc27740591d085e1172cebe311144bf0 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 4006c01772bd8d8ac4306d523bbcee41d3e392d8 F src/vacuum.c 59f03f92bcff57faa6a8ca256eb29ccddfb0614a -F src/vdbe.c 97c6c50e272ed531bc3af308d5f156cfca0ce4f4 +F src/vdbe.c 6e07ea132d94b464fa9d28dd7ea85a977524de31 F src/vdbe.h 09f5b4e3719fa454f252322b1cdab5cf1f361327 F src/vdbeInt.h e1173bd72b282633c2ec8f3a2f78b5117229f268 F src/vdbeapi.c 37a6c6ae284a97bcace365f2f0a225680c0499d9 @@ -1204,7 +1204,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 869c30e45cc87063be423c650f16b99e8adb3df0 -R d569318d3e6a6b025c49ffecae9bf7d4 +P 91384a7d727ef0f285cd430e829ba9f3852db50e +R 398856b8d4cf81a7bc85ff63a35b9f22 U drh -Z e6cf351e034f82bffef92232dfc65ffe +Z cd7cdfd82fa519c77c73eb77000032e4 diff --git a/manifest.uuid b/manifest.uuid index a04b930976..9e8c25c8d6 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -91384a7d727ef0f285cd430e829ba9f3852db50e \ No newline at end of file +20062f49428a2349a2dd705af570c60b499a3eef \ No newline at end of file diff --git a/src/build.c b/src/build.c index 14d8aab587..b897494db3 100644 --- a/src/build.c +++ b/src/build.c @@ -2747,7 +2747,7 @@ static void sqlite3RefillIndex(Parse *pParse, Index *pIndex, int memRootPage){ }else{ addr2 = sqlite3VdbeCurrentAddr(v); } - sqlite3VdbeAddOp2(v, OP_SorterData, iSorter, regRecord); + sqlite3VdbeAddOp3(v, OP_SorterData, iSorter, regRecord, iIdx); sqlite3VdbeAddOp3(v, OP_IdxInsert, iIdx, regRecord, 1); sqlite3VdbeChangeP5(v, OPFLAG_USESEEKRESULT); sqlite3ReleaseTempReg(pParse, regRecord); diff --git a/src/select.c b/src/select.c index 411bca0df4..3b422f1100 100644 --- a/src/select.c +++ b/src/select.c @@ -1181,7 +1181,6 @@ static void generateSortTail( int nKey; int iSortTab; /* Sorter cursor to read from */ int nSortData; /* Trailing values to read from sorter */ - u8 p5; /* p5 parameter for 1st OP_Column */ int i; int bSeq; /* True if sorter record includes seq. no. */ #ifdef SQLITE_ENABLE_EXPLAIN_COMMENTS @@ -1215,19 +1214,16 @@ static void generateSortTail( addr = 1 + sqlite3VdbeAddOp2(v, OP_SorterSort, iTab, addrBreak); VdbeCoverage(v); codeOffset(v, p->iOffset, addrContinue); - sqlite3VdbeAddOp2(v, OP_SorterData, iTab, regSortOut); - p5 = OPFLAG_CLEARCACHE; + sqlite3VdbeAddOp3(v, OP_SorterData, iTab, regSortOut, iSortTab); bSeq = 0; }else{ addr = 1 + sqlite3VdbeAddOp2(v, OP_Sort, iTab, addrBreak); VdbeCoverage(v); codeOffset(v, p->iOffset, addrContinue); iSortTab = iTab; - p5 = 0; bSeq = 1; } for(i=0; inExpr; j++){ if( groupBySort ){ sqlite3VdbeAddOp3(v, OP_Column, sortPTab, j, iBMem+j); - if( j==0 ) sqlite3VdbeChangeP5(v, OPFLAG_CLEARCACHE); }else{ sAggInfo.directMode = 1; sqlite3ExprCode(pParse, pGroupBy->a[j].pExpr, iBMem+j); diff --git a/src/sqliteInt.h b/src/sqliteInt.h index e648430353..cba89b03e7 100644 --- a/src/sqliteInt.h +++ b/src/sqliteInt.h @@ -2666,7 +2666,6 @@ struct AuthContext { #define OPFLAG_ISUPDATE 0x04 /* This OP_Insert is an sql UPDATE */ #define OPFLAG_APPEND 0x08 /* This is likely to be an append */ #define OPFLAG_USESEEKRESULT 0x10 /* Try to avoid a seek in BtreeInsert() */ -#define OPFLAG_CLEARCACHE 0x20 /* Clear pseudo-table cache in OP_Column */ #define OPFLAG_LENGTHARG 0x40 /* OP_Column only used for length() */ #define OPFLAG_TYPEOFARG 0x80 /* OP_Column only used for typeof() */ #define OPFLAG_BULKCSR 0x01 /* OP_Open** used to open bulk cursor */ diff --git a/src/vdbe.c b/src/vdbe.c index 347b604bf4..19cf117ce5 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -2288,7 +2288,7 @@ case OP_Column: { /* If the cursor cache is stale, bring it up-to-date */ rc = sqlite3VdbeCursorMoveto(pC); if( rc ) goto abort_due_to_error; - if( pC->cacheStatus!=p->cacheCtr || (pOp->p5&OPFLAG_CLEARCACHE)!=0 ){ + if( pC->cacheStatus!=p->cacheCtr ){ if( pC->nullRow ){ if( pCrsr==0 ){ assert( pC->pseudoTableReg>0 ); @@ -4245,10 +4245,17 @@ case OP_SorterCompare: { break; }; -/* Opcode: SorterData P1 P2 * * * +/* Opcode: SorterData P1 P2 P3 * * ** Synopsis: r[P2]=data ** ** Write into register P2 the current sorter data for sorter cursor P1. +** Then clear the column header cache on cursor P3. +** +** This opcode is normally use to move a record out of the sorter and into +** a register that is the source for a pseudo-table cursor created using +** OpenPseudo. That pseudo-table cursor is the one that is identified by +** parameter P3. Clearing the P3 column cache as part of this opcode saves +** us from having to issue a separate NullRow instruction to clear that cache. */ case OP_SorterData: { VdbeCursor *pC; @@ -4258,6 +4265,8 @@ case OP_SorterData: { assert( isSorter(pC) ); rc = sqlite3VdbeSorterRowkey(pC, pOut); assert( rc!=SQLITE_OK || (pOut->flags & MEM_Blob) ); + assert( pOp->p1>=0 && pOp->p1nCursor ); + p->apCsr[pOp->p3]->cacheStatus = CACHE_STALE; break; } From c22284f4b3939c1a09c0df2759bd5cca2dc34bad Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 13 Oct 2014 16:02:20 +0000 Subject: [PATCH 53/54] Reduce the CPU load imposed by sqlit3VdbeCursorMoveto() by factoring out some of its functions and by avoiding unnecessary calls. FossilOrigin-Name: c2799aece17d347c64217a0e407bb10e50c184a3 --- manifest | 18 +++++++++--------- manifest.uuid | 2 +- src/btree.c | 2 +- src/vdbe.c | 28 +++++++++++++++++++--------- src/vdbeInt.h | 1 + src/vdbeaux.c | 13 ++++++++++++- 6 files changed, 43 insertions(+), 21 deletions(-) diff --git a/manifest b/manifest index ea3a0d9c70..72398a68f7 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\sthe\sOPFLAG_CLEARCACHE\sflag\sfrom\sOP_Column.\s\sIn\sits\splace,\schange\sthe\nP3\sparameter\sof\sOP_SorterData\sto\sbe\sthe\sindex\sof\sthe\spseudo-table\scursor\swhose\nrecord\sheader\scache\sis\sto\sbe\scleared.\s\sThis\sgives\sa\ssmall\ssize\sreduction\nand\sperformance\sincrease. -D 2014-10-13T13:00:58.198 +C Reduce\sthe\sCPU\sload\simposed\sby\ssqlit3VdbeCursorMoveto()\sby\sfactoring\sout\nsome\sof\sits\sfunctions\sand\sby\savoiding\sunnecessary\scalls. +D 2014-10-13T16:02:20.134 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -172,7 +172,7 @@ F src/auth.c d8abcde53426275dab6243b441256fcd8ccbebb2 F src/backup.c a31809c65623cc41849b94d368917f8bb66e6a7e F src/bitvec.c 19a4ba637bd85f8f63fc8c9bae5ade9fb05ec1cb F src/btmutex.c 49ca66250c7dfa844a4d4cb8272b87420d27d3a5 -F src/btree.c 5c0b78c49d00da49a0e8e3d2738900a431df7fca +F src/btree.c c9fcae8145436f728c61272cba72b1469c07f30d F src/btree.h a79aa6a71e7f1055f01052b7f821bd1c2dce95c8 F src/btreeInt.h 1bd7957161a1346a914f1f09231610e777a8e58d F src/build.c 9dc2bd94347b878c89627000c92b0c8d97ec2919 @@ -289,11 +289,11 @@ F src/update.c 729f6f18fc27740591d085e1172cebe311144bf0 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 4006c01772bd8d8ac4306d523bbcee41d3e392d8 F src/vacuum.c 59f03f92bcff57faa6a8ca256eb29ccddfb0614a -F src/vdbe.c 6e07ea132d94b464fa9d28dd7ea85a977524de31 +F src/vdbe.c cf7c24e531aad047689e4235a66b22526e765e46 F src/vdbe.h 09f5b4e3719fa454f252322b1cdab5cf1f361327 -F src/vdbeInt.h e1173bd72b282633c2ec8f3a2f78b5117229f268 +F src/vdbeInt.h 90c0ae53382d16a4f77ad5a9c4b3e35278e9e061 F src/vdbeapi.c 37a6c6ae284a97bcace365f2f0a225680c0499d9 -F src/vdbeaux.c e223d15ab39c844c04ad19931e8c71966c20c68d +F src/vdbeaux.c 8d101333912e33ed36201898d839cd560d8e87f4 F src/vdbeblob.c 848238dc73e93e48432991bb5651bf87d865eca4 F src/vdbemem.c 481327f50d9da330053aa7456702ce46d0a4e70f F src/vdbesort.c 5c1bacf90578d22b630fbf6ed98ccf60d83435ef @@ -1204,7 +1204,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 91384a7d727ef0f285cd430e829ba9f3852db50e -R 398856b8d4cf81a7bc85ff63a35b9f22 +P 20062f49428a2349a2dd705af570c60b499a3eef +R a5158d9f69a4de7fce20f1a1e7deba5e U drh -Z cd7cdfd82fa519c77c73eb77000032e4 +Z 9da431167b91f4974349edc450eddb7a diff --git a/manifest.uuid b/manifest.uuid index 9e8c25c8d6..5724d7dce8 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -20062f49428a2349a2dd705af570c60b499a3eef \ No newline at end of file +c2799aece17d347c64217a0e407bb10e50c184a3 \ No newline at end of file diff --git a/src/btree.c b/src/btree.c index cfe623342a..3553924c0f 100644 --- a/src/btree.c +++ b/src/btree.c @@ -776,7 +776,7 @@ static int btreeRestoreCursorPosition(BtCursor *pCur){ ** back to where it ought to be if this routine returns true. */ int sqlite3BtreeCursorHasMoved(BtCursor *pCur){ - return pCur && pCur->eState!=CURSOR_VALID; + return pCur->eState!=CURSOR_VALID; } /* diff --git a/src/vdbe.c b/src/vdbe.c index 19cf117ce5..7e0e35fb0e 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -4313,16 +4313,20 @@ case OP_RowData: { assert( pC->pseudoTableReg==0 ); assert( pC->pCursor!=0 ); pCrsr = pC->pCursor; - assert( sqlite3BtreeCursorIsValid(pCrsr) ); /* The OP_RowKey and OP_RowData opcodes always follow OP_NotExists or ** OP_Rewind/Op_Next with no intervening instructions that might invalidate - ** the cursor. Hence the following sqlite3VdbeCursorMoveto() call is always - ** a no-op and can never fail. But we leave it in place as a safety. + ** the cursor. If this where not the case, on of the following assert()s + ** would fail. Should this ever change (because of changes in the code + ** generator) then the fix would be to insert a call to + ** sqlite3VdbeCursorMoveto(). */ assert( pC->deferredMoveto==0 ); + assert( sqlite3BtreeCursorIsValid(pCrsr) ); +#if 0 /* Not required due to the previous to assert() statements */ rc = sqlite3VdbeCursorMoveto(pC); - if( NEVER(rc!=SQLITE_OK) ) goto abort_due_to_error; + if( rc!=SQLITE_OK ) goto abort_due_to_error; +#endif if( pC->isTable==0 ){ assert( !pC->isTable ); @@ -4391,10 +4395,10 @@ case OP_Rowid: { /* out2-prerelease */ #endif /* SQLITE_OMIT_VIRTUALTABLE */ }else{ assert( pC->pCursor!=0 ); - rc = sqlite3VdbeCursorMoveto(pC); + rc = sqlite3VdbeCursorRestore(pC); if( rc ) goto abort_due_to_error; rc = sqlite3BtreeKeySize(pC->pCursor, &v); - assert( rc==SQLITE_OK ); /* Always so because of CursorMoveto() above */ + assert( rc==SQLITE_OK ); /* Always so because of CursorRestore() above */ } pOut->u.i = v; break; @@ -4752,10 +4756,16 @@ case OP_IdxRowid: { /* out2-prerelease */ pCrsr = pC->pCursor; assert( pCrsr!=0 ); pOut->flags = MEM_Null; - rc = sqlite3VdbeCursorMoveto(pC); - if( NEVER(rc) ) goto abort_due_to_error; - assert( pC->deferredMoveto==0 ); assert( pC->isTable==0 ); + assert( pC->deferredMoveto==0 ); + + /* sqlite3VbeCursorRestore() can only fail if the record has been deleted + ** out from under the cursor. That will never happend for an IdxRowid + ** opcode, hence the NEVER() arround the check of the return value. + */ + rc = sqlite3VdbeCursorRestore(pC); + if( NEVER(rc!=SQLITE_OK) ) goto abort_due_to_error; + if( !pC->nullRow ){ rowid = 0; /* Not needed. Only used to silence a warning. */ rc = sqlite3VdbeIdxRowid(db, pCrsr, &rowid); diff --git a/src/vdbeInt.h b/src/vdbeInt.h index 1c7bebc9f6..1b27e88e72 100644 --- a/src/vdbeInt.h +++ b/src/vdbeInt.h @@ -383,6 +383,7 @@ struct Vdbe { void sqlite3VdbeFreeCursor(Vdbe *, VdbeCursor*); void sqliteVdbePopStack(Vdbe*,int); int sqlite3VdbeCursorMoveto(VdbeCursor*); +int sqlite3VdbeCursorRestore(VdbeCursor*); #if defined(SQLITE_DEBUG) || defined(VDBE_PROFILE) void sqlite3VdbePrintOp(FILE*, int, Op*); #endif diff --git a/src/vdbeaux.c b/src/vdbeaux.c index fefa0ef337..88bf2c3dd8 100644 --- a/src/vdbeaux.c +++ b/src/vdbeaux.c @@ -2744,6 +2744,17 @@ static int SQLITE_NOINLINE handleMovedCursor(VdbeCursor *p){ return rc; } +/* +** Check to ensure that the cursor is valid. Restore the cursor +** if need be. Return any I/O error from the restore operation. +*/ +int sqlite3VdbeCursorRestore(VdbeCursor *p){ + if( sqlite3BtreeCursorHasMoved(p->pCursor) ){ + return handleMovedCursor(p); + } + return SQLITE_OK; +} + /* ** Make sure the cursor p is ready to read or write the row to which it ** was last positioned. Return an error code if an OOM fault or I/O error @@ -2761,7 +2772,7 @@ int sqlite3VdbeCursorMoveto(VdbeCursor *p){ if( p->deferredMoveto ){ return handleDeferredMoveto(p); } - if( sqlite3BtreeCursorHasMoved(p->pCursor) ){ + if( p->pCursor && sqlite3BtreeCursorHasMoved(p->pCursor) ){ return handleMovedCursor(p); } return SQLITE_OK; From f526dcad299bbb3d00817a84c9268ef9191bf07e Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 13 Oct 2014 17:42:05 +0000 Subject: [PATCH 54/54] Three small optimizations to vdbeaux.c. FossilOrigin-Name: 04892f8ba6c55cec4fe37bfe59b6349fd2a40698 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/vdbeaux.c | 9 +++++---- 3 files changed, 12 insertions(+), 11 deletions(-) diff --git a/manifest b/manifest index 72398a68f7..f76c05d5cd 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Reduce\sthe\sCPU\sload\simposed\sby\ssqlit3VdbeCursorMoveto()\sby\sfactoring\sout\nsome\sof\sits\sfunctions\sand\sby\savoiding\sunnecessary\scalls. -D 2014-10-13T16:02:20.134 +C Three\ssmall\soptimizations\sto\svdbeaux.c. +D 2014-10-13T17:42:05.891 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in cf57f673d77606ab0f2d9627ca52a9ba1464146a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -293,7 +293,7 @@ F src/vdbe.c cf7c24e531aad047689e4235a66b22526e765e46 F src/vdbe.h 09f5b4e3719fa454f252322b1cdab5cf1f361327 F src/vdbeInt.h 90c0ae53382d16a4f77ad5a9c4b3e35278e9e061 F src/vdbeapi.c 37a6c6ae284a97bcace365f2f0a225680c0499d9 -F src/vdbeaux.c 8d101333912e33ed36201898d839cd560d8e87f4 +F src/vdbeaux.c edbb7a9c8b2a8f7a68ac75c2475edd4040266b76 F src/vdbeblob.c 848238dc73e93e48432991bb5651bf87d865eca4 F src/vdbemem.c 481327f50d9da330053aa7456702ce46d0a4e70f F src/vdbesort.c 5c1bacf90578d22b630fbf6ed98ccf60d83435ef @@ -1204,7 +1204,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 20062f49428a2349a2dd705af570c60b499a3eef -R a5158d9f69a4de7fce20f1a1e7deba5e +P c2799aece17d347c64217a0e407bb10e50c184a3 +R f9a2ff50dcb19a8595444c5c4cad6f5f U drh -Z 9da431167b91f4974349edc450eddb7a +Z bf4e3c223808aa3476302aafe1aa8090 diff --git a/manifest.uuid b/manifest.uuid index 5724d7dce8..02b54f919a 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -c2799aece17d347c64217a0e407bb10e50c184a3 \ No newline at end of file +04892f8ba6c55cec4fe37bfe59b6349fd2a40698 \ No newline at end of file diff --git a/src/vdbeaux.c b/src/vdbeaux.c index 88bf2c3dd8..c0018bb71c 100644 --- a/src/vdbeaux.c +++ b/src/vdbeaux.c @@ -1745,7 +1745,7 @@ void sqlite3VdbeFreeCursor(Vdbe *p, VdbeCursor *pCx){ sqlite3BtreeCloseCursor(pCx->pCursor); } #ifndef SQLITE_OMIT_VIRTUALTABLE - if( pCx->pVtabCursor ){ + else if( pCx->pVtabCursor ){ sqlite3_vtab_cursor *pVtabCursor = pCx->pVtabCursor; const sqlite3_module *pModule = pVtabCursor->pVtab->pModule; p->inVtabMethod = 1; @@ -1788,9 +1788,10 @@ static void closeAllCursors(Vdbe *p){ VdbeFrame *pFrame; for(pFrame=p->pFrame; pFrame->pParent; pFrame=pFrame->pParent); sqlite3VdbeFrameRestore(pFrame); + p->pFrame = 0; + p->nFrame = 0; } - p->pFrame = 0; - p->nFrame = 0; + assert( p->nFrame==0 ); if( p->apCsr ){ int i; @@ -1812,7 +1813,7 @@ static void closeAllCursors(Vdbe *p){ } /* Delete any auxdata allocations made by the VM */ - sqlite3VdbeDeleteAuxData(p, -1, 0); + if( p->pAuxData ) sqlite3VdbeDeleteAuxData(p, -1, 0); assert( p->pAuxData==0 ); }