Registerification of the VDBE is complete. The operand stack has been
removed from the code. All instructions operate out of registers only. (CVS 4718) FossilOrigin-Name: 706b41b70bd1e2030e6fa44358c38a26c5cf0985
This commit is contained in:
parent
07a518ebf6
commit
9cbf3425fb
46
manifest
46
manifest
@ -1,5 +1,5 @@
|
||||
C Registerification\sof\sthe\sWHERE\sclause\slogic.\s(CVS\s4717)
|
||||
D 2008-01-17T02:36:28
|
||||
C Registerification\sof\sthe\sVDBE\sis\scomplete.\s\sThe\soperand\sstack\shas\sbeen\nremoved\sfrom\sthe\scode.\s\sAll\sinstructions\soperate\sout\sof\sregisters\sonly.\s(CVS\s4718)
|
||||
D 2008-01-17T16:22:14
|
||||
F Makefile.arm-wince-mingw32ce-gcc ac5f7b2cef0cd850d6f755ba6ee4ab961b1fadf7
|
||||
F Makefile.in 30789bf70614bad659351660d76b8e533f3340e9
|
||||
F Makefile.linux-gcc d53183f4aa6a9192d249731c90dbdffbd2c68654
|
||||
@ -69,7 +69,7 @@ F mkdll.sh 5f8438dcac98e795d7df6529159a1ec566de0183
|
||||
F mkextu.sh 416f9b7089d80e5590a29692c9d9280a10dbad9f
|
||||
F mkextw.sh 1a866b53637dab137191341cc875575a5ca110fb
|
||||
F mkopcodec.awk 3fb9bf077053c968451f4dd03d11661ac373f9d1
|
||||
F mkopcodeh.awk 754a156fc83d47933c985186fba7fc800f88d2e1
|
||||
F mkopcodeh.awk 926deb36f57c3b573cfa79db675fdcff2ea6c5db
|
||||
F mkso.sh 24bde4c09e6fe80f718db3c31c068f45e13a2f2c
|
||||
F publish.sh 1c0658c63d70f182a8f5e17cc28422f1b237f51d
|
||||
F publish_osx.sh eca87df1e3d43d128d97d3261fd48b3d6877996e
|
||||
@ -78,25 +78,25 @@ F sqlite.pc.in 30552343140c53304c2a658c080fbe810cd09ca2
|
||||
F sqlite3.1 6be1ad09113570e1fc8dcaff84c9b0b337db5ffc
|
||||
F sqlite3.def a96c1d0d39362b763d2ddba220a32da41a15c4b4
|
||||
F sqlite3.pc.in abed4664817e1cd500f2276142c71958087c16bc
|
||||
F src/alter.c 5a54f58d9481ac14c4e58b702f3f8758dee84d04
|
||||
F src/alter.c 2a101cb062b82fa29db9b105a1078690aa0a3c11
|
||||
F src/analyze.c ac17da1f9c804aabf709a1afff12ed35fc215104
|
||||
F src/attach.c 71f5c886004a9740fc6e6033d4e1ce0517ab6574
|
||||
F src/attach.c f7a34eb0f0e01db5fbfd8acb12109f87aed8159d
|
||||
F src/auth.c c8b2ab5c8bad4bd90ed7c294694f48269162c627
|
||||
F src/btmutex.c 5d39da37c9d1282f3c6f9967afae6a34ee36b7ff
|
||||
F src/btree.c 5164b32950cfd41f2c5c31e8ff82c4a499918aef
|
||||
F src/btree.h 19dcf5ad23c17b98855da548e9a8e3eb4429d5eb
|
||||
F src/btreeInt.h 1c5a9da165718ef7de81e35ce9ab5d9ba9283f76
|
||||
F src/build.c ea291f091434aa9cd9700ea1611f2601c3c6a118
|
||||
F src/build.c 27a3be10a7186515915ac73c40667dc55beacbac
|
||||
F src/callback.c 77b302b0d41468dcda78c70e706e5b84577f0fa0
|
||||
F src/complete.c 4cf68fd75d60257524cbe74f87351b9848399131
|
||||
F src/date.c 49c5a6d2de6c12000905b4d36868b07d3011bbf6
|
||||
F src/delete.c ca07deed95f6f79c64338147147f698811628dc9
|
||||
F src/delete.c 739ccbab8fa7478762bded5c9cc67f16a4d09dbe
|
||||
F src/experimental.c 1b2d1a6cd62ecc39610e97670332ca073c50792b
|
||||
F src/expr.c 00ee6555e323cd772f85e48b353109865d1eb539
|
||||
F src/expr.c 217ba4f47ffc17b10c79b091d896535e28aaa033
|
||||
F src/func.c 996071cf0af9d967e58b69fce1909555059ebc7d
|
||||
F src/hash.c 45a7005aac044b6c86bd7e49c44bc15d30006d6c
|
||||
F src/hash.h 031cd9f915aff27e12262cb9eb570ac1b8326b53
|
||||
F src/insert.c 8a90ba2d934bef98562cee12b778a17446730594
|
||||
F src/insert.c ed16eaf9391929e29fdbfa589db09b7224b31905
|
||||
F src/journal.c 807bed7a158979ac8d63953e1774e8d85bff65e2
|
||||
F src/legacy.c 4ac53191fad2e3c4d59bde1228879b2dc5a96d66
|
||||
F src/limits.h 71ab25f17e35e0a9f3f6f234b8ed49cc56731d35
|
||||
@ -127,16 +127,16 @@ F src/os_win.h 41a946bea10f61c158ce8645e7646b29d44f122b
|
||||
F src/pager.c 0cb6ccea4b9615627d61d7c4417cedc45776d429
|
||||
F src/pager.h f504f7ae84060fee0416a853e368d3d113c3d6fa
|
||||
F src/parse.y 2ae06e8d3190faace49c5b82e7cea1fc60d084a1
|
||||
F src/pragma.c 0768de04ea4e97c8c79748110147c5bc6986c440
|
||||
F src/pragma.c 155315ee3e6a861a0060ba4d184dfffd08ebbc03
|
||||
F src/prepare.c c31a879d6795f4765fd0b113675c6debbc96b7fd
|
||||
F src/printf.c eb27822ba2eec669161409ca31279a24c26ac910
|
||||
F src/random.c 02ef38b469237482f1ea14a78b2087cfbaec48bd
|
||||
F src/select.c 841eba5f83fb81f267bb2633bbf1b0cb7cfda96f
|
||||
F src/select.c fb2d6653954478c0a7f4ca64b5c4a6f024212296
|
||||
F src/server.c 087b92a39d883e3fa113cae259d64e4c7438bc96
|
||||
F src/shell.c 0691a3d52dc37cf6ac2f74838e5ff8ae1055ac9b
|
||||
F src/sqlite.h.in 2a7e3776534bbe6ff2cdc058f3abebe91e7e429f
|
||||
F src/sqlite3ext.h a93f59cdee3638dc0c9c086f80df743a4e68c3cb
|
||||
F src/sqliteInt.h 89dc8eb7784948ef80966addc645721e20f9b772
|
||||
F src/sqliteInt.h 8389662011bc23851199750ea1e6dc1a72d26109
|
||||
F src/sqliteLimit.h ee4430f88f69bf63527967bb35ca52af7b0ccb1e
|
||||
F src/table.c 1aeb9eab57b4235db86fe15a35dec76fb445a9c4
|
||||
F src/tclsqlite.c 9923abeffc9b3d7dad58e92b319661521f60debf
|
||||
@ -163,21 +163,21 @@ F src/test_server.c a6ece6c835e7eae835054124e09e947e422b1ac5
|
||||
F src/test_tclvar.c b2d1115e4d489179d3f029e765211b2ad527ba59
|
||||
F src/test_thread.c e297dd41db0b249646e69f97d36ec13e56e8b730
|
||||
F src/tokenize.c a4e04438c11fed2c67ec47fe3edbef9cca2d1b48
|
||||
F src/trigger.c 5e869352a2f35890dc4711161bfe958fcec8f4d7
|
||||
F src/update.c a4da9976e06bf1cc676dc270e0e0dba8ae39729c
|
||||
F src/trigger.c 9bd3b6fa0beff4a02d262c96466f752ec15a7fc3
|
||||
F src/update.c 2513c6120f9510ae782446a2b839931e994b75dd
|
||||
F src/utf.c ef4b7d83bae533b76c3e1bf635b113fdad86a736
|
||||
F src/util.c 05f31144bbd3f1a24f4139ae029c42545cb72624
|
||||
F src/vacuum.c 3f34f278809bf3eb0b62ec46ff779e9c385b28f0
|
||||
F src/vdbe.c 9de1ce4ddf2906a63cef6bd11156d299edf31cd0
|
||||
F src/vdbe.c 94d3da762729118e8062abf7866b22b6e41e7a3b
|
||||
F src/vdbe.h a9166e1601f5b74c20516a74182773a20baee43e
|
||||
F src/vdbeInt.h 31bd686595356284d5484592e2dc6e58025aa346
|
||||
F src/vdbeInt.h 835e6f0337ce89d705ef9a162338788808adc4b7
|
||||
F src/vdbeapi.c cb8c427a3ab646490c83204a98e94eff03ee2e89
|
||||
F src/vdbeaux.c e5b401253f66f099c5d790dcbee43d614681eae5
|
||||
F src/vdbeaux.c 0d2a9730195d40f7d1156731bc69f240927255c5
|
||||
F src/vdbeblob.c e386d49d8354aa5a58f0a7f2794303442c149120
|
||||
F src/vdbefifo.c 334c838c8f42d61a94813d136019ee566b5dc2f6
|
||||
F src/vdbemem.c a86119b5ccc41ab8653e4746f83d591ff0ae892e
|
||||
F src/vtab.c 7f206d148f6e76f427f008f589610c72a4b9336c
|
||||
F src/where.c 75908cb6dbcc7f2f21e42d65b68b1a24e6b5f679
|
||||
F src/vtab.c 9924e37cf7f5c527aeabb5da025874af505fb91d
|
||||
F src/where.c 0cc6052f73aef0d2ce59505d7ae06d6fbf696025
|
||||
F tclinstaller.tcl 4356d9d94d2b5ed5e68f9f0c80c4df3048dd7617
|
||||
F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2
|
||||
F test/all.test ee350b9ab15b175fc0a8fb51bf2141ed3a3b9cba
|
||||
@ -323,7 +323,7 @@ F test/hook.test 3870abead2ee75d2c03585c916256ca8b5584679
|
||||
F test/icu.test e6bfae7f625c88fd14df6f540fe835bdfc1e4329
|
||||
F test/in.test 763a29007a4850d611ac4441bfa488fb9969ad30
|
||||
F test/in2.test b1f447f4f0f67e9f83ff931e7e2e30873f9ea055
|
||||
F test/in3.test e335959db24d71d6cfdff9553c90ce2b56fb978c
|
||||
F test/in3.test 2f829007cc8d25d17b859f7fe882ef2bd2e2eb49
|
||||
F test/incrblob.test 854c23b7ff8dd3822f675936b22c094655b3c739
|
||||
F test/incrblob_err.test 5273097dc7c97f9b7008423a6ffd5c80d21923cb
|
||||
F test/incrvacuum.test 1ed44535e89a0fa10c48c1aa0a3d48ee72bcc733
|
||||
@ -606,7 +606,7 @@ F www/tclsqlite.tcl 8be95ee6dba05eabcd27a9d91331c803f2ce2130
|
||||
F www/vdbe.tcl 87a31ace769f20d3627a64fa1fade7fed47b90d0
|
||||
F www/version3.tcl 890248cf7b70e60c383b0e84d77d5132b3ead42b
|
||||
F www/whentouse.tcl fc46eae081251c3c181bd79c5faef8195d7991a5
|
||||
P b3a141b2b0c09bf3c7704deeade290d71b7c9b77
|
||||
R 9b81ffae960f644182cd49ff81018f5f
|
||||
P 5581160f43c60825d03de58e67aa66904d9d8964
|
||||
R 9b66d11764748ee0bf0a1a49c0663779
|
||||
U drh
|
||||
Z e206730fa35a583eeb4dac70ee5ed4f0
|
||||
Z a08c417a1e9cffb9cc564c4f53d0978f
|
||||
|
@ -1 +1 @@
|
||||
5581160f43c60825d03de58e67aa66904d9d8964
|
||||
706b41b70bd1e2030e6fa44358c38a26c5cf0985
|
@ -51,7 +51,6 @@
|
||||
sub("\r","",name)
|
||||
op[name] = -1
|
||||
jump[name] = 0
|
||||
nopush[name] = 0
|
||||
out2_prerelease[name] = 0
|
||||
in1[name] = 0
|
||||
in2[name] = 0
|
||||
@ -68,9 +67,7 @@
|
||||
}
|
||||
x = $i
|
||||
sub(",","",x)
|
||||
if(x=="no-push"){
|
||||
nopush[name] = 1
|
||||
}else if(x=="jump"){
|
||||
if(x=="jump"){
|
||||
jump[name] = 1
|
||||
}else if(x=="out2-prerelease"){
|
||||
out2_prerelease[name] = 1
|
||||
@ -130,16 +127,16 @@ END {
|
||||
for(name in op){
|
||||
x = op[name]
|
||||
a0 = a1 = a2 = a3 = a4 = a5 = a6 = a7 = 0
|
||||
a8 = a9 = a10 = a11 = a12 = a13 = a14 = a15 = 0
|
||||
# a8 = a9 = a10 = a11 = a12 = a13 = a14 = a15 = 0
|
||||
if( jump[name] ) a0 = 1;
|
||||
if( nopush[name]==0 ) a1 = 2;
|
||||
if( out2_prerelease[name] ) a2 = 4;
|
||||
if( in1[name] ) a3 = 8;
|
||||
if( in2[name] ) a4 = 16;
|
||||
if( in3[name] ) a5 = 32;
|
||||
if( out2[name] ) a6 = 64;
|
||||
if( out3[name] ) a7 = 128;
|
||||
bv[x] = a0+a1+a2+a3+a4+a5+a6+a7+a8+a9+a10+a11+a12+a13+a14+a15;
|
||||
if( out2_prerelease[name] ) a1 = 2;
|
||||
if( in1[name] ) a2 = 4;
|
||||
if( in2[name] ) a3 = 8;
|
||||
if( in3[name] ) a4 = 16;
|
||||
if( out2[name] ) a5 = 32;
|
||||
if( out3[name] ) a6 = 64;
|
||||
# bv[x] = a0+a1+a2+a3+a4+a5+a6+a7+a8+a9+a10+a11+a12+a13+a14+a15;
|
||||
bv[x] = a0+a1+a2+a3+a4+a5+a6;
|
||||
}
|
||||
print "\n"
|
||||
print "/* Properties such as \"out2\" or \"jump\" that are specified in"
|
||||
@ -147,17 +144,16 @@ END {
|
||||
print "** are encoded into bitvectors as follows:"
|
||||
print "*/"
|
||||
print "#define OPFLG_JUMP 0x0001 /* jump: P2 holds jmp target */"
|
||||
print "#define OPFLG_PUSH 0x0002 /* ~no-push: Does not push */"
|
||||
print "#define OPFLG_OUT2_PRERELEASE 0x0004 /* out2-prerelease: */"
|
||||
print "#define OPFLG_IN1 0x0008 /* in1: P1 is an input */"
|
||||
print "#define OPFLG_IN2 0x0010 /* in2: P2 is an input */"
|
||||
print "#define OPFLG_IN3 0x0020 /* in3: P3 is an input */"
|
||||
print "#define OPFLG_OUT2 0x0040 /* out2: P2 is an output */"
|
||||
print "#define OPFLG_OUT3 0x0080 /* out3: P3 is an output */"
|
||||
print "#define OPFLG_OUT2_PRERELEASE 0x0002 /* out2-prerelease: */"
|
||||
print "#define OPFLG_IN1 0x0004 /* in1: P1 is an input */"
|
||||
print "#define OPFLG_IN2 0x0008 /* in2: P2 is an input */"
|
||||
print "#define OPFLG_IN3 0x0010 /* in3: P3 is an input */"
|
||||
print "#define OPFLG_OUT2 0x0020 /* out2: P2 is an output */"
|
||||
print "#define OPFLG_OUT3 0x0040 /* out3: P3 is an output */"
|
||||
print "#define OPFLG_INITIALIZER {\\"
|
||||
for(i=0; i<=max; i++){
|
||||
if( i%8==0 ) printf("/* %3d */",i)
|
||||
printf " 0x%04x,", bv[i]
|
||||
printf " 0x%02x,", bv[i]
|
||||
if( i%8==7 ) printf("\\\n");
|
||||
}
|
||||
print "}"
|
||||
|
@ -12,7 +12,7 @@
|
||||
** This file contains C code routines that used to generate VDBE code
|
||||
** that implements the ALTER TABLE command.
|
||||
**
|
||||
** $Id: alter.c,v 1.39 2008/01/04 22:01:03 drh Exp $
|
||||
** $Id: alter.c,v 1.40 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#include "sqliteInt.h"
|
||||
#include <ctype.h>
|
||||
@ -353,7 +353,7 @@ void sqlite3AlterRenameTable(
|
||||
goto exit_rename_table;
|
||||
}
|
||||
sqlite3BeginWriteOperation(pParse, isVirtualRename, iDb);
|
||||
sqlite3ChangeCookie(db, v, iDb);
|
||||
sqlite3ChangeCookie(pParse, iDb);
|
||||
|
||||
/* If this is a virtual table, invoke the xRename() function if
|
||||
** one is defined. The xRename() callback will modify the names
|
||||
@ -621,7 +621,7 @@ void sqlite3AlterBeginAddColumn(Parse *pParse, SrcList *pSrc){
|
||||
sqlite3BeginWriteOperation(pParse, 0, iDb);
|
||||
v = sqlite3GetVdbe(pParse);
|
||||
if( !v ) goto exit_begin_add_column;
|
||||
sqlite3ChangeCookie(db, v, iDb);
|
||||
sqlite3ChangeCookie(pParse, iDb);
|
||||
|
||||
exit_begin_add_column:
|
||||
sqlite3SrcListDelete(pSrc);
|
||||
|
@ -11,7 +11,7 @@
|
||||
*************************************************************************
|
||||
** This file contains code used to implement the ATTACH and DETACH commands.
|
||||
**
|
||||
** $Id: attach.c,v 1.68 2008/01/12 19:03:49 drh Exp $
|
||||
** $Id: attach.c,v 1.69 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#include "sqliteInt.h"
|
||||
|
||||
@ -327,7 +327,7 @@ static void codeAttach(
|
||||
}
|
||||
|
||||
v = sqlite3GetVdbe(pParse);
|
||||
regArgs = sqlite3GetTempRange(pParse, nFunc);
|
||||
regArgs = sqlite3GetTempRange(pParse, 3);
|
||||
sqlite3ExprCode(pParse, pFilename, regArgs);
|
||||
sqlite3ExprCode(pParse, pDbname, regArgs+1);
|
||||
sqlite3ExprCode(pParse, pKey, regArgs+2);
|
||||
|
20
src/build.c
20
src/build.c
@ -22,7 +22,7 @@
|
||||
** COMMIT
|
||||
** ROLLBACK
|
||||
**
|
||||
** $Id: build.c,v 1.466 2008/01/17 02:36:28 drh Exp $
|
||||
** $Id: build.c,v 1.467 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#include "sqliteInt.h"
|
||||
#include <ctype.h>
|
||||
@ -1277,9 +1277,13 @@ CollSeq *sqlite3LocateCollSeq(Parse *pParse, const char *zName, int nName){
|
||||
** and the probability of hitting the same cookie value is only
|
||||
** 1 chance in 2^32. So we're safe enough.
|
||||
*/
|
||||
void sqlite3ChangeCookie(sqlite3 *db, Vdbe *v, int iDb){
|
||||
sqlite3VdbeAddOp2(v, OP_Integer, db->aDb[iDb].pSchema->schema_cookie+1, 0);
|
||||
sqlite3VdbeAddOp2(v, OP_SetCookie, iDb, 0);
|
||||
void sqlite3ChangeCookie(Parse *pParse, int iDb){
|
||||
int r1 = sqlite3GetTempReg(pParse);
|
||||
sqlite3 *db = pParse->db;
|
||||
Vdbe *v = pParse->pVdbe;
|
||||
sqlite3VdbeAddOp2(v, OP_Integer, db->aDb[iDb].pSchema->schema_cookie+1, r1);
|
||||
sqlite3VdbeAddOp3(v, OP_SetCookie, iDb, 0, r1);
|
||||
sqlite3ReleaseTempReg(pParse, r1);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1544,7 +1548,7 @@ void sqlite3EndTable(
|
||||
pParse->regRowid
|
||||
);
|
||||
sqlite3_free(zStmt);
|
||||
sqlite3ChangeCookie(db, v, iDb);
|
||||
sqlite3ChangeCookie(pParse, iDb);
|
||||
|
||||
#ifndef SQLITE_OMIT_AUTOINCREMENT
|
||||
/* Check to see if we need to create an sqlite_sequence table for
|
||||
@ -2066,7 +2070,7 @@ void sqlite3DropTable(Parse *pParse, SrcList *pName, int isView, int noErr){
|
||||
sqlite3VdbeAddOp4(v, OP_VDestroy, iDb, 0, 0, pTab->zName, 0);
|
||||
}
|
||||
sqlite3VdbeAddOp4(v, OP_DropTable, iDb, 0, 0, pTab->zName, 0);
|
||||
sqlite3ChangeCookie(db, v, iDb);
|
||||
sqlite3ChangeCookie(pParse, iDb);
|
||||
}
|
||||
sqliteViewResetAll(db, iDb);
|
||||
|
||||
@ -2688,7 +2692,7 @@ void sqlite3CreateIndex(
|
||||
*/
|
||||
if( pTblName ){
|
||||
sqlite3RefillIndex(pParse, pIndex, iMem);
|
||||
sqlite3ChangeCookie(db, v, iDb);
|
||||
sqlite3ChangeCookie(pParse, iDb);
|
||||
sqlite3VdbeAddOp4(v, OP_ParseSchema, iDb, 0, 0,
|
||||
sqlite3MPrintf(db, "name='%q'", pIndex->zName), P4_DYNAMIC);
|
||||
sqlite3VdbeAddOp1(v, OP_Expire, 0);
|
||||
@ -2840,7 +2844,7 @@ void sqlite3DropIndex(Parse *pParse, SrcList *pName, int ifExists){
|
||||
db->aDb[iDb].zName, SCHEMA_TABLE(iDb),
|
||||
pIndex->zName
|
||||
);
|
||||
sqlite3ChangeCookie(db, v, iDb);
|
||||
sqlite3ChangeCookie(pParse, iDb);
|
||||
destroyRootPage(pParse, pIndex->tnum, iDb);
|
||||
sqlite3VdbeAddOp4(v, OP_DropIndex, iDb, 0, 0, pIndex->zName, 0);
|
||||
}
|
||||
|
10
src/delete.c
10
src/delete.c
@ -12,7 +12,7 @@
|
||||
** This file contains C code routines that are called by the parser
|
||||
** in order to generate code for DELETE FROM statements.
|
||||
**
|
||||
** $Id: delete.c,v 1.158 2008/01/17 02:36:28 drh Exp $
|
||||
** $Id: delete.c,v 1.159 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#include "sqliteInt.h"
|
||||
|
||||
@ -317,7 +317,6 @@ void sqlite3DeleteFrom(
|
||||
sqlite3VdbeResolveLabel(v, addr);
|
||||
}
|
||||
addr = sqlite3VdbeAddOp2(v, OP_FifoRead, iRowid, end);
|
||||
sqlite3VdbeAddOp1(v, OP_StackDepth, -1);
|
||||
|
||||
if( triggers_exist ){
|
||||
int iData = ++pParse->nMem; /* For storing row data of OLD table */
|
||||
@ -458,12 +457,15 @@ void sqlite3GenerateRowIndexDelete(
|
||||
){
|
||||
int i;
|
||||
Index *pIdx;
|
||||
int r1;
|
||||
|
||||
r1 = sqlite3GetTempReg(pParse);
|
||||
for(i=1, pIdx=pTab->pIndex; pIdx; i++, pIdx=pIdx->pNext){
|
||||
if( aRegIdx!=0 && aRegIdx[i-1]==0 ) continue;
|
||||
sqlite3GenerateIndexKey(pParse, pIdx, iCur, 0);
|
||||
sqlite3VdbeAddOp2(pParse->pVdbe, OP_IdxDelete, iCur+i, 0);
|
||||
sqlite3GenerateIndexKey(pParse, pIdx, iCur, r1);
|
||||
sqlite3VdbeAddOp2(pParse->pVdbe, OP_IdxDelete, iCur+i, r1);
|
||||
}
|
||||
sqlite3ReleaseTempReg(pParse, r1);
|
||||
}
|
||||
|
||||
/*
|
||||
|
32
src/expr.c
32
src/expr.c
@ -12,7 +12,7 @@
|
||||
** This file contains routines used for analyzing expressions and
|
||||
** for generating VDBE code that evaluates expressions in SQLite.
|
||||
**
|
||||
** $Id: expr.c,v 1.346 2008/01/17 02:36:28 drh Exp $
|
||||
** $Id: expr.c,v 1.347 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#include "sqliteInt.h"
|
||||
#include <ctype.h>
|
||||
@ -1848,7 +1848,7 @@ static char *dup8bytes(Vdbe *v, const char *in){
|
||||
|
||||
/*
|
||||
** Generate an instruction that will put the floating point
|
||||
** value described by z[0..n-1] on the stack.
|
||||
** value described by z[0..n-1] into register iMem.
|
||||
**
|
||||
** The z[] string will probably not be zero-terminated. But the
|
||||
** z[n] character is guaranteed to be something that does not look
|
||||
@ -1870,7 +1870,7 @@ static void codeReal(Vdbe *v, const char *z, int n, int negateFlag, int iMem){
|
||||
|
||||
/*
|
||||
** Generate an instruction that will put the integer describe by
|
||||
** text z[0..n-1] on the stack.
|
||||
** text z[0..n-1] into register iMem.
|
||||
**
|
||||
** The z[] string will probably not be zero-terminated. But the
|
||||
** z[n] character is guaranteed to be something that does not look
|
||||
@ -1900,8 +1900,8 @@ static void codeInteger(Vdbe *v, const char *z, int n, int negFlag, int iMem){
|
||||
|
||||
/*
|
||||
** Generate code that will extract the iColumn-th column from
|
||||
** table pTab and store the column value in register iMem, or on
|
||||
** the stack if iMem==0. There is an open cursor to pTab in
|
||||
** table pTab and store the column value in register iReg.
|
||||
** There is an open cursor to pTab in
|
||||
** iTable. If iColumn<0 then code is generated that extracts the rowid.
|
||||
*/
|
||||
void sqlite3ExprCodeGetColumn(
|
||||
@ -1948,7 +1948,7 @@ static int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target){
|
||||
int r1, r2, r3; /* Various register numbers */
|
||||
|
||||
assert( v!=0 || pParse->db->mallocFailed );
|
||||
assert( target>=0 );
|
||||
assert( target>0 && target<=pParse->nMem );
|
||||
if( v==0 ) return 0;
|
||||
|
||||
if( pExpr==0 ){
|
||||
@ -2417,11 +2417,13 @@ int sqlite3ExprCodeTemp(Parse *pParse, Expr *pExpr, int *pReg){
|
||||
** in register target.
|
||||
*/
|
||||
int sqlite3ExprCode(Parse *pParse, Expr *pExpr, int target){
|
||||
int inReg = sqlite3ExprCodeTarget(pParse, pExpr, target);
|
||||
int inReg;
|
||||
|
||||
assert( target>0 && target<=pParse->nMem );
|
||||
inReg = sqlite3ExprCodeTarget(pParse, pExpr, target);
|
||||
assert( pParse->pVdbe || pParse->db->mallocFailed );
|
||||
if( inReg!=target && pParse->pVdbe ){
|
||||
sqlite3VdbeAddOp2(pParse->pVdbe, (inReg>0 ? OP_SCopy : OP_Move),
|
||||
inReg, target);
|
||||
sqlite3VdbeAddOp2(pParse->pVdbe, OP_SCopy, inReg, target);
|
||||
}
|
||||
return target;
|
||||
}
|
||||
@ -2461,8 +2463,7 @@ int sqlite3ExprCodeAndCache(Parse *pParse, Expr *pExpr, int target){
|
||||
|
||||
/*
|
||||
** Generate code that pushes the value of every element of the given
|
||||
** expression list onto the stack if target==0 or into a sequence of
|
||||
** registers beginning at target.
|
||||
** expression list into a sequence of registers beginning at target.
|
||||
**
|
||||
** Return the number of elements evaluated.
|
||||
*/
|
||||
@ -2472,19 +2473,16 @@ int sqlite3ExprCodeExprList(
|
||||
int target /* Where to write results */
|
||||
){
|
||||
struct ExprList_item *pItem;
|
||||
int i, n, incr = 1;
|
||||
int i, n;
|
||||
assert( pList!=0 || pParse->db->mallocFailed );
|
||||
if( pList==0 ){
|
||||
return 0;
|
||||
}
|
||||
assert( target>=0 );
|
||||
assert( target>0 );
|
||||
n = pList->nExpr;
|
||||
if( target==0 ){
|
||||
incr = 0;
|
||||
}
|
||||
for(pItem=pList->a, i=n; i>0; i--, pItem++){
|
||||
sqlite3ExprCode(pParse, pItem->pExpr, target);
|
||||
target += incr;
|
||||
target++;
|
||||
}
|
||||
return n;
|
||||
}
|
||||
|
@ -12,7 +12,7 @@
|
||||
** This file contains C code routines that are called by the parser
|
||||
** to handle INSERT statements in SQLite.
|
||||
**
|
||||
** $Id: insert.c,v 1.224 2008/01/17 02:36:28 drh Exp $
|
||||
** $Id: insert.c,v 1.225 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#include "sqliteInt.h"
|
||||
|
||||
@ -667,7 +667,6 @@ void sqlite3Insert(
|
||||
}else if( pSelect ){
|
||||
sqlite3VdbeAddOp2(v, OP_Goto, 0, iSelectLoop);
|
||||
sqlite3VdbeResolveLabel(v, iInsertBlock);
|
||||
sqlite3VdbeAddOp2(v, OP_StackDepth, -1, 0);
|
||||
}
|
||||
|
||||
/* Allocate registers for holding the rowid of the new row,
|
||||
|
18
src/pragma.c
18
src/pragma.c
@ -11,7 +11,7 @@
|
||||
*************************************************************************
|
||||
** This file contains code used to implement the PRAGMA command.
|
||||
**
|
||||
** $Id: pragma.c,v 1.167 2008/01/17 02:36:28 drh Exp $
|
||||
** $Id: pragma.c,v 1.168 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#include "sqliteInt.h"
|
||||
#include <ctype.h>
|
||||
@ -252,7 +252,7 @@ void sqlite3Pragma(
|
||||
Db *pDb;
|
||||
Vdbe *v = pParse->pVdbe = sqlite3VdbeCreate(db);
|
||||
if( v==0 ) return;
|
||||
pParse->nMem = 1;
|
||||
pParse->nMem = 2;
|
||||
|
||||
/* Interpret the [database.] part of the pragma statement. iDb is the
|
||||
** index of the database this pragma is being applied to in db.aDb[]. */
|
||||
@ -321,12 +321,12 @@ void sqlite3Pragma(
|
||||
int size = atoi(zRight);
|
||||
if( size<0 ) size = -size;
|
||||
sqlite3BeginWriteOperation(pParse, 0, iDb);
|
||||
sqlite3VdbeAddOp1(v, OP_Integer, size);
|
||||
sqlite3VdbeAddOp3(v, OP_ReadCookie, iDb, 0, 2);
|
||||
addr = sqlite3VdbeAddOp2(v, OP_IfPos, 0, 0);
|
||||
sqlite3VdbeAddOp1(v, OP_Integer, -size);
|
||||
sqlite3VdbeAddOp2(v, OP_Integer, size, 1);
|
||||
sqlite3VdbeAddOp3(v, OP_ReadCookie, iDb, 2, 2);
|
||||
addr = sqlite3VdbeAddOp2(v, OP_IfPos, 2, 0);
|
||||
sqlite3VdbeAddOp2(v, OP_Integer, -size, 1);
|
||||
sqlite3VdbeJumpHere(v, addr);
|
||||
sqlite3VdbeAddOp2(v, OP_SetCookie, iDb, 2);
|
||||
sqlite3VdbeAddOp3(v, OP_SetCookie, iDb, 2, 1);
|
||||
pDb->pSchema->cache_size = size;
|
||||
sqlite3BtreeSetCacheSize(pDb->pBt, pDb->pSchema->cache_size);
|
||||
}
|
||||
@ -1109,8 +1109,8 @@ void sqlite3Pragma(
|
||||
/* Write the specified cookie value */
|
||||
static const VdbeOpList setCookie[] = {
|
||||
{ OP_Transaction, 0, 1, 0}, /* 0 */
|
||||
{ OP_Integer, 0, 0, 0}, /* 1 */
|
||||
{ OP_SetCookie, 0, 0, 0}, /* 2 */
|
||||
{ OP_Integer, 0, 1, 0}, /* 1 */
|
||||
{ OP_SetCookie, 0, 0, 1}, /* 2 */
|
||||
};
|
||||
int addr = sqlite3VdbeAddOpList(v, ArraySize(setCookie), setCookie);
|
||||
sqlite3VdbeChangeP1(v, addr, iDb);
|
||||
|
26
src/select.c
26
src/select.c
@ -12,7 +12,7 @@
|
||||
** This file contains C code routines that are called by the parser
|
||||
** to handle SELECT statements in SQLite.
|
||||
**
|
||||
** $Id: select.c,v 1.403 2008/01/17 02:36:28 drh Exp $
|
||||
** $Id: select.c,v 1.404 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#include "sqliteInt.h"
|
||||
|
||||
@ -583,11 +583,14 @@ static int selectInnerLoop(
|
||||
*/
|
||||
#ifndef SQLITE_OMIT_COMPOUND_SELECT
|
||||
case SRT_Union: {
|
||||
sqlite3VdbeAddOp2(v, OP_MakeRecord, iMem, nColumn);
|
||||
int r1;
|
||||
r1 = sqlite3GetTempReg(pParse);
|
||||
sqlite3VdbeAddOp3(v, OP_MakeRecord, iMem, nColumn, r1);
|
||||
if( aff ){
|
||||
sqlite3VdbeChangeP4(v, -1, aff, P4_STATIC);
|
||||
}
|
||||
sqlite3VdbeAddOp2(v, OP_IdxInsert, iParm, 0);
|
||||
sqlite3VdbeAddOp2(v, OP_IdxInsert, iParm, r1);
|
||||
sqlite3ReleaseTempReg(pParse, r1);
|
||||
break;
|
||||
}
|
||||
|
||||
@ -596,11 +599,13 @@ static int selectInnerLoop(
|
||||
** the temporary table iParm.
|
||||
*/
|
||||
case SRT_Except: {
|
||||
int addr;
|
||||
addr = sqlite3VdbeAddOp2(v, OP_MakeRecord, iMem, nColumn);
|
||||
int addr, r1;
|
||||
r1 = sqlite3GetTempReg(pParse);
|
||||
addr = sqlite3VdbeAddOp3(v, OP_MakeRecord, iMem, nColumn, r1);
|
||||
sqlite3VdbeChangeP4(v, -1, aff, P4_STATIC);
|
||||
sqlite3VdbeAddOp2(v, OP_NotFound, iParm, addr+3);
|
||||
sqlite3VdbeAddOp2(v, OP_Delete, iParm, 0);
|
||||
sqlite3VdbeAddOp3(v, OP_NotFound, iParm, addr+3, r1);
|
||||
sqlite3VdbeAddOp1(v, OP_Delete, iParm);
|
||||
sqlite3ReleaseTempReg(pParse, r1);
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
@ -2067,6 +2072,7 @@ static int multiSelect(
|
||||
Expr *pLimit, *pOffset;
|
||||
int addr;
|
||||
SelectDest intersectdest;
|
||||
int r1;
|
||||
|
||||
/* INTERSECT is different from the others since it requires
|
||||
** two temporary tables. Hence it has its own case. Begin
|
||||
@ -2127,8 +2133,10 @@ static int multiSelect(
|
||||
iCont = sqlite3VdbeMakeLabel(v);
|
||||
computeLimitRegisters(pParse, p, iBreak);
|
||||
sqlite3VdbeAddOp2(v, OP_Rewind, tab1, iBreak);
|
||||
iStart = sqlite3VdbeAddOp1(v, OP_RowKey, tab1);
|
||||
sqlite3VdbeAddOp2(v, OP_NotFound, tab2, iCont);
|
||||
r1 = sqlite3GetTempReg(pParse);
|
||||
iStart = sqlite3VdbeAddOp2(v, OP_RowKey, tab1, r1);
|
||||
sqlite3VdbeAddOp3(v, OP_NotFound, tab2, iCont, r1);
|
||||
sqlite3ReleaseTempReg(pParse, r1);
|
||||
rc = selectInnerLoop(pParse, p, p->pEList, tab1, p->pEList->nExpr,
|
||||
pOrderBy, -1, &dest, iCont, iBreak, 0);
|
||||
if( rc ){
|
||||
|
@ -11,7 +11,7 @@
|
||||
*************************************************************************
|
||||
** Internal interface definitions for SQLite.
|
||||
**
|
||||
** @(#) $Id: sqliteInt.h,v 1.650 2008/01/17 02:36:28 drh Exp $
|
||||
** @(#) $Id: sqliteInt.h,v 1.651 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#ifndef _SQLITEINT_H_
|
||||
#define _SQLITEINT_H_
|
||||
@ -1819,7 +1819,7 @@ void sqlite3RegisterDateTimeFunctions(sqlite3*);
|
||||
int sqlite3SafetyOn(sqlite3*);
|
||||
int sqlite3SafetyOff(sqlite3*);
|
||||
int sqlite3SafetyCheck(sqlite3*);
|
||||
void sqlite3ChangeCookie(sqlite3*, Vdbe*, int);
|
||||
void sqlite3ChangeCookie(Parse*, int);
|
||||
|
||||
#ifndef SQLITE_OMIT_TRIGGER
|
||||
void sqlite3BeginTrigger(Parse*, Token*,Token*,int,int,IdList*,SrcList*,
|
||||
|
@ -240,7 +240,7 @@ void sqlite3FinishTrigger(
|
||||
db->aDb[iDb].zName, SCHEMA_TABLE(iDb), pTrig->name,
|
||||
pTrig->table, z);
|
||||
sqlite3_free(z);
|
||||
sqlite3ChangeCookie(db, v, iDb);
|
||||
sqlite3ChangeCookie(pParse, iDb);
|
||||
sqlite3VdbeAddOp4(v, OP_ParseSchema, iDb, 0, 0, sqlite3MPrintf(
|
||||
db, "type='trigger' AND name='%q'", pTrig->name), P4_DYNAMIC
|
||||
);
|
||||
@ -538,7 +538,7 @@ void sqlite3DropTriggerPtr(Parse *pParse, Trigger *pTrigger){
|
||||
base = sqlite3VdbeAddOpList(v, ArraySize(dropTrigger), dropTrigger);
|
||||
sqlite3VdbeChangeP4(v, base+1, pTrigger->name, 0);
|
||||
sqlite3VdbeChangeP4(v, base+4, "trigger", P4_STATIC);
|
||||
sqlite3ChangeCookie(db, v, iDb);
|
||||
sqlite3ChangeCookie(pParse, iDb);
|
||||
sqlite3VdbeAddOp2(v, OP_Close, 0, 0);
|
||||
sqlite3VdbeAddOp4(v, OP_DropTrigger, iDb, 0, 0, pTrigger->name, 0);
|
||||
}
|
||||
|
@ -12,7 +12,7 @@
|
||||
** This file contains C code routines that are called by the parser
|
||||
** to handle UPDATE statements.
|
||||
**
|
||||
** $Id: update.c,v 1.168 2008/01/17 02:36:28 drh Exp $
|
||||
** $Id: update.c,v 1.169 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#include "sqliteInt.h"
|
||||
|
||||
@ -401,7 +401,6 @@ void sqlite3Update(
|
||||
|
||||
/* Top of the update loop */
|
||||
addr = sqlite3VdbeAddOp2(v, OP_FifoRead, regOldRowid, 0);
|
||||
sqlite3VdbeAddOp2(v, OP_StackDepth, -1, 0);
|
||||
|
||||
if( triggers_exist ){
|
||||
int regRowid;
|
||||
|
755
src/vdbe.c
755
src/vdbe.c
File diff suppressed because it is too large
Load Diff
@ -291,8 +291,6 @@ struct Vdbe {
|
||||
int nLabel; /* Number of labels used */
|
||||
int nLabelAlloc; /* Number of slots allocated in aLabel[] */
|
||||
int *aLabel; /* Space to hold the labels */
|
||||
Mem *aStack; /* The operand stack, except string values */
|
||||
Mem *pTos; /* Top entry in the operand stack */
|
||||
Mem **apArg; /* Arguments to currently executing user function */
|
||||
Mem *aColName; /* Column names to return */
|
||||
int nCursor; /* Number of slots in apCsr[] */
|
||||
@ -319,7 +317,6 @@ struct Vdbe {
|
||||
int returnDepth; /* Next unused element in returnStack[] */
|
||||
int nResColumn; /* Number of columns in one row of the result set */
|
||||
char **azResColumn; /* Values for one row of result */
|
||||
int popStack; /* Pop the stack this much on entry to VdbeExec() */
|
||||
char *zErrMsg; /* Error message written here */
|
||||
Mem *pResultSet; /* Pointer to an array of results */
|
||||
u8 explain; /* True if EXPLAIN present on SQL command */
|
||||
|
@ -233,9 +233,9 @@ void sqlite3VdbeResolveLabel(Vdbe *p, int x){
|
||||
}
|
||||
|
||||
/*
|
||||
** Loop through the program looking for P2 values that are negative.
|
||||
** Each such value is a label. Resolve the label by setting the P2
|
||||
** value to its correct non-zero value.
|
||||
** Loop through the program looking for P2 values that are negative
|
||||
** on jump instructions. Each such value is a label. Resolve the
|
||||
** label by setting the P2 value to its correct non-zero value.
|
||||
**
|
||||
** This routine is called once after all opcodes have been inserted.
|
||||
**
|
||||
@ -243,9 +243,6 @@ void sqlite3VdbeResolveLabel(Vdbe *p, int x){
|
||||
** to an OP_Function, OP_AggStep or OP_VFilter opcode. This is used by
|
||||
** sqlite3VdbeMakeReady() to size the Vdbe.apArg[] array.
|
||||
**
|
||||
** The integer *pMaxStack is set to the maximum number of vdbe stack
|
||||
** entries that static analysis reveals this program might need.
|
||||
**
|
||||
** This routine also does the following optimization: It scans for
|
||||
** instructions that might cause a statement rollback. Such instructions
|
||||
** are:
|
||||
@ -259,10 +256,9 @@ void sqlite3VdbeResolveLabel(Vdbe *p, int x){
|
||||
** is changed to a Noop. In this way, we avoid creating the statement
|
||||
** journal file unnecessarily.
|
||||
*/
|
||||
static void resolveP2Values(Vdbe *p, int *pMaxFuncArgs, int *pMaxStack){
|
||||
static void resolveP2Values(Vdbe *p, int *pMaxFuncArgs){
|
||||
int i;
|
||||
int nMaxArgs = 0;
|
||||
int nMaxStack = p->nOp;
|
||||
Op *pOp;
|
||||
int *aLabel = p->aLabel;
|
||||
int doesStatementRollback = 0;
|
||||
@ -298,9 +294,6 @@ static void resolveP2Values(Vdbe *p, int *pMaxFuncArgs, int *pMaxStack){
|
||||
if( n>nMaxArgs ) nMaxArgs = n;
|
||||
#endif
|
||||
}
|
||||
if( !sqlite3VdbeOpcodeHasProperty(opcode, OPFLG_PUSH) ){
|
||||
nMaxStack--;
|
||||
}
|
||||
|
||||
if( sqlite3VdbeOpcodeHasProperty(opcode, OPFLG_JUMP) && pOp->p2<0 ){
|
||||
assert( -1-pOp->p2<p->nLabel );
|
||||
@ -311,7 +304,6 @@ static void resolveP2Values(Vdbe *p, int *pMaxFuncArgs, int *pMaxStack){
|
||||
p->aLabel = 0;
|
||||
|
||||
*pMaxFuncArgs = nMaxArgs;
|
||||
*pMaxStack = nMaxStack;
|
||||
|
||||
/* If we never rollback a statement transaction, then statement
|
||||
** transactions are not needed. So change every OP_Statement
|
||||
@ -739,7 +731,7 @@ static void releaseMemArray(Mem *p, int N){
|
||||
if( p ){
|
||||
while( N-->0 ){
|
||||
assert( N<2 || p[0].db==p[1].db );
|
||||
sqlite3VdbeMemRelease(p++);
|
||||
sqlite3VdbeMemSetNull(p++);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -751,6 +743,11 @@ static void releaseMemArray(Mem *p, int N){
|
||||
** The interface is the same as sqlite3VdbeExec(). But instead of
|
||||
** running the code, it invokes the callback once for each instruction.
|
||||
** This feature is used to implement "EXPLAIN".
|
||||
**
|
||||
** When p->explain==1, each instruction is listed. When
|
||||
** p->explain==2, only OP_Explain instructions are listed and these
|
||||
** are shown in a different format. p->explain==2 is used to implement
|
||||
** EXPLAIN QUERY PLAN.
|
||||
*/
|
||||
int sqlite3VdbeList(
|
||||
Vdbe *p /* The VDBE */
|
||||
@ -758,20 +755,18 @@ int sqlite3VdbeList(
|
||||
sqlite3 *db = p->db;
|
||||
int i;
|
||||
int rc = SQLITE_OK;
|
||||
Mem *pMem = p->pResultSet = &p->aMem[1];
|
||||
|
||||
assert( p->explain );
|
||||
if( p->magic!=VDBE_MAGIC_RUN ) return SQLITE_MISUSE;
|
||||
assert( db->magic==SQLITE_MAGIC_BUSY );
|
||||
assert( p->rc==SQLITE_OK || p->rc==SQLITE_BUSY );
|
||||
|
||||
/* Even though this opcode does not put dynamic strings onto the
|
||||
** the stack, they may become dynamic if the user calls
|
||||
/* Even though this opcode does not use dynamic strings for
|
||||
** the result, result columns may become dynamic if the user calls
|
||||
** sqlite3_column_text16(), causing a translation to UTF-16 encoding.
|
||||
*/
|
||||
if( p->pResultSet ){
|
||||
releaseMemArray(p->pResultSet, 5);
|
||||
p->pResultSet = 0;
|
||||
}
|
||||
releaseMemArray(pMem, p->nMem);
|
||||
|
||||
do{
|
||||
i = p->pc++;
|
||||
@ -785,7 +780,6 @@ int sqlite3VdbeList(
|
||||
sqlite3SetString(&p->zErrMsg, sqlite3ErrStr(p->rc), (char*)0);
|
||||
}else{
|
||||
Op *pOp = &p->aOp[i];
|
||||
Mem *pMem = p->pResultSet = p->aStack;
|
||||
if( p->explain==1 ){
|
||||
pMem->flags = MEM_Int;
|
||||
pMem->type = SQLITE_INTEGER;
|
||||
@ -846,7 +840,6 @@ int sqlite3VdbeList(
|
||||
}
|
||||
|
||||
p->nResColumn = 8 - 5*(p->explain-1);
|
||||
p->pTos = pMem;
|
||||
p->rc = SQLITE_OK;
|
||||
rc = SQLITE_ROW;
|
||||
}
|
||||
@ -935,36 +928,27 @@ void sqlite3VdbeMakeReady(
|
||||
*/
|
||||
p->magic = VDBE_MAGIC_RUN;
|
||||
|
||||
/* No instruction ever pushes more than a single element onto the
|
||||
** stack. And the stack never grows on successive executions of the
|
||||
** same loop. So the total number of instructions is an upper bound
|
||||
** on the maximum stack depth required. (Added later:) The
|
||||
** resolveP2Values() call computes a tighter upper bound on the
|
||||
** stack size.
|
||||
**
|
||||
** Allocation all the stack space we will ever need.
|
||||
/*
|
||||
** Allocation space for registers.
|
||||
*/
|
||||
if( p->aStack==0 ){
|
||||
if( p->aMem==0 ){
|
||||
int nArg; /* Maximum number of args passed to a user function. */
|
||||
int nStack; /* Maximum number of stack entries required */
|
||||
resolveP2Values(p, &nArg, &nStack);
|
||||
resolveP2Values(p, &nArg);
|
||||
resizeOpArray(p, p->nOp);
|
||||
assert( nVar>=0 );
|
||||
assert( nStack<p->nOp );
|
||||
if( isExplain ){
|
||||
nStack = 16;
|
||||
if( isExplain && nMem<10 ){
|
||||
p->nMem = nMem = 10;
|
||||
}
|
||||
p->aStack = sqlite3DbMallocZero(db,
|
||||
nStack*sizeof(p->aStack[0]) /* aStack */
|
||||
+ nArg*sizeof(Mem*) /* apArg */
|
||||
p->aMem = sqlite3DbMallocZero(db,
|
||||
nMem*sizeof(Mem) /* aMem */
|
||||
+ nVar*sizeof(Mem) /* aVar */
|
||||
+ nArg*sizeof(Mem*) /* apArg */
|
||||
+ nVar*sizeof(char*) /* azVar */
|
||||
+ nMem*sizeof(Mem) /* aMem */
|
||||
+ nCursor*sizeof(Cursor*) + 1 /* apCsr */
|
||||
);
|
||||
if( !db->mallocFailed ){
|
||||
p->aMem = &p->aStack[nStack-1]; /* aMem[] goes from 1..nMem */
|
||||
p->nMem = nMem; /* not from 0..nMem-1 */
|
||||
p->aMem--; /* aMem[] goes from 1..nMem */
|
||||
p->nMem = nMem; /* not from 0..nMem-1 */
|
||||
p->aVar = &p->aMem[nMem+1];
|
||||
p->nVar = nVar;
|
||||
p->okVar = 0;
|
||||
@ -976,23 +960,24 @@ void sqlite3VdbeMakeReady(
|
||||
p->aVar[n].flags = MEM_Null;
|
||||
p->aVar[n].db = db;
|
||||
}
|
||||
for(n=0; n<nStack; n++){
|
||||
p->aStack[n].db = db;
|
||||
for(n=1; n<=nMem; n++){
|
||||
p->aMem[n].flags = MEM_Null;
|
||||
p->aMem[n].db = db;
|
||||
}
|
||||
}
|
||||
}
|
||||
for(n=1; n<=p->nMem; n++){
|
||||
p->aMem[n].flags = MEM_Null;
|
||||
p->aMem[n].db = db;
|
||||
#ifdef SQLITE_DEBUG
|
||||
for(n=1; n<p->nMem; n++){
|
||||
assert( p->aMem[n].db==db );
|
||||
assert( p->aMem[n].flags==MEM_Null );
|
||||
}
|
||||
#endif
|
||||
|
||||
p->pTos = &p->aStack[-1];
|
||||
p->pc = -1;
|
||||
p->rc = SQLITE_OK;
|
||||
p->uniqueCnt = 0;
|
||||
p->returnDepth = 0;
|
||||
p->errorAction = OE_Abort;
|
||||
p->popStack = 0;
|
||||
p->explain |= isExplain;
|
||||
p->magic = VDBE_MAGIC_RUN;
|
||||
p->nChange = 0;
|
||||
@ -1065,10 +1050,6 @@ static void closeAllCursorsExceptActiveVtabs(Vdbe *p){
|
||||
*/
|
||||
static void Cleanup(Vdbe *p){
|
||||
int i;
|
||||
if( p->aStack ){
|
||||
releaseMemArray(p->aStack, 1 + (p->pTos - p->aStack));
|
||||
p->pTos = &p->aStack[-1];
|
||||
}
|
||||
closeAllCursorsExceptActiveVtabs(p);
|
||||
releaseMemArray(&p->aMem[1], p->nMem);
|
||||
sqlite3VdbeFifoClear(&p->sFifo);
|
||||
@ -1664,7 +1645,6 @@ int sqlite3VdbeReset(Vdbe *p){
|
||||
|
||||
/* Save profiling information from this VDBE run.
|
||||
*/
|
||||
assert( p->pTos<&p->aStack[p->pc<0?0:p->pc] || !p->aStack );
|
||||
#ifdef VDBE_PROFILE
|
||||
{
|
||||
FILE *out = fopen("vdbe_profile.out", "a");
|
||||
@ -1755,7 +1735,9 @@ void sqlite3VdbeDelete(Vdbe *p){
|
||||
}
|
||||
releaseMemArray(p->aVar, p->nVar);
|
||||
sqlite3_free(p->aLabel);
|
||||
sqlite3_free(p->aStack);
|
||||
if( p->aMem ){
|
||||
sqlite3_free(&p->aMem[1]);
|
||||
}
|
||||
releaseMemArray(p->aColName, p->nResColumn*COLNAME_N);
|
||||
sqlite3_free(p->aColName);
|
||||
sqlite3_free(p->zSql);
|
||||
|
@ -11,7 +11,7 @@
|
||||
*************************************************************************
|
||||
** This file contains code used to help implement virtual tables.
|
||||
**
|
||||
** $Id: vtab.c,v 1.61 2008/01/12 12:48:08 drh Exp $
|
||||
** $Id: vtab.c,v 1.62 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#ifndef SQLITE_OMIT_VIRTUALTABLE
|
||||
#include "sqliteInt.h"
|
||||
@ -276,7 +276,7 @@ void sqlite3VtabFinishParse(Parse *pParse, Token *pEnd){
|
||||
);
|
||||
sqlite3_free(zStmt);
|
||||
v = sqlite3GetVdbe(pParse);
|
||||
sqlite3ChangeCookie(db, v, iDb);
|
||||
sqlite3ChangeCookie(pParse, iDb);
|
||||
|
||||
sqlite3VdbeAddOp2(v, OP_Expire, 0, 0);
|
||||
zWhere = sqlite3MPrintf(db, "name='%q'", pTab->zName);
|
||||
|
@ -16,7 +16,7 @@
|
||||
** so is applicable. Because this module is responsible for selecting
|
||||
** indices, you might also think of this module as the "query optimizer".
|
||||
**
|
||||
** $Id: where.c,v 1.282 2008/01/17 02:36:28 drh Exp $
|
||||
** $Id: where.c,v 1.283 2008/01/17 16:22:15 drh Exp $
|
||||
*/
|
||||
#include "sqliteInt.h"
|
||||
|
||||
@ -2647,7 +2647,6 @@ WhereInfo *sqlite3WhereBegin(
|
||||
pLevel->p2 = 1 + sqlite3VdbeAddOp2(v, OP_Rewind, iCur, brk);
|
||||
}
|
||||
notReady &= ~getMask(&maskSet, iCur);
|
||||
sqlite3VdbeAddOp2(v, OP_StackDepth, -1, 0);
|
||||
|
||||
/* Insert code to test every subexpression that can be completely
|
||||
** computed using the current set of tables.
|
||||
|
@ -13,7 +13,7 @@
|
||||
#
|
||||
# <value> IN (SELECT <column> FROM <table>)
|
||||
#
|
||||
# $Id: in3.test,v 1.2 2007/12/10 05:03:48 danielk1977 Exp $
|
||||
# $Id: in3.test,v 1.3 2008/01/17 16:22:16 drh Exp $
|
||||
|
||||
set testdir [file dirname $argv0]
|
||||
source $testdir/tester.tcl
|
||||
@ -266,4 +266,3 @@ do_test in3-4.6 {
|
||||
} {}
|
||||
|
||||
finish_test
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user