mirror of
https://github.com/sqlite/sqlite.git
synced 2025-11-11 01:42:22 +03:00
A new implementation of sqlite3VdbeMakeLabel() is faster and makes fewer
memory allocations by deferring memory allocation until sqlite3VdbeResolveLabel() is called, at which point the code generator has a better idea of how big the relocation table needs to be. The sqlite3VdbeMakeLabel() routine now takes a Parse* parameter instead of Vdbe*. FossilOrigin-Name: 4a0929ac76d8aa5dd65eac3b83d6bbf41e505e01d175ca0fb2b19ba02d439415
This commit is contained in:
40
src/select.c
40
src/select.c
@@ -631,7 +631,7 @@ static void pushOntoSorter(
|
||||
}
|
||||
assert( pSelect->iOffset==0 || pSelect->iLimit!=0 );
|
||||
iLimit = pSelect->iOffset ? pSelect->iOffset+1 : pSelect->iLimit;
|
||||
pSort->labelDone = sqlite3VdbeMakeLabel(v);
|
||||
pSort->labelDone = sqlite3VdbeMakeLabel(pParse);
|
||||
sqlite3ExprCodeExprList(pParse, pSort->pOrderBy, regBase, regOrigData,
|
||||
SQLITE_ECEL_DUP | (regOrigData? SQLITE_ECEL_REF : 0));
|
||||
if( bSeq ){
|
||||
@@ -670,7 +670,7 @@ static void pushOntoSorter(
|
||||
pKI->nAllField-pKI->nKeyField-1);
|
||||
addrJmp = sqlite3VdbeCurrentAddr(v);
|
||||
sqlite3VdbeAddOp3(v, OP_Jump, addrJmp+1, 0, addrJmp+1); VdbeCoverage(v);
|
||||
pSort->labelBkOut = sqlite3VdbeMakeLabel(v);
|
||||
pSort->labelBkOut = sqlite3VdbeMakeLabel(pParse);
|
||||
pSort->regReturn = ++pParse->nMem;
|
||||
sqlite3VdbeAddOp2(v, OP_Gosub, pSort->regReturn, pSort->labelBkOut);
|
||||
sqlite3VdbeAddOp1(v, OP_ResetSorter, pSort->iECursor);
|
||||
@@ -1417,7 +1417,7 @@ static void generateSortTail(
|
||||
){
|
||||
Vdbe *v = pParse->pVdbe; /* The prepared statement */
|
||||
int addrBreak = pSort->labelDone; /* Jump here to exit loop */
|
||||
int addrContinue = sqlite3VdbeMakeLabel(v); /* Jump here for next cycle */
|
||||
int addrContinue = sqlite3VdbeMakeLabel(pParse);/* Jump here for next cycle */
|
||||
int addr; /* Top of output loop. Jump for Next. */
|
||||
int addrOnce = 0;
|
||||
int iTab;
|
||||
@@ -2329,7 +2329,7 @@ static void generateWithRecursiveQuery(
|
||||
if( sqlite3AuthCheck(pParse, SQLITE_RECURSIVE, 0, 0, 0) ) return;
|
||||
|
||||
/* Process the LIMIT and OFFSET clauses, if they exist */
|
||||
addrBreak = sqlite3VdbeMakeLabel(v);
|
||||
addrBreak = sqlite3VdbeMakeLabel(pParse);
|
||||
p->nSelectRow = 320; /* 4 billion rows */
|
||||
computeLimitRegisters(pParse, p, addrBreak);
|
||||
pLimit = p->pLimit;
|
||||
@@ -2399,7 +2399,7 @@ static void generateWithRecursiveQuery(
|
||||
sqlite3VdbeAddOp1(v, OP_Delete, iQueue);
|
||||
|
||||
/* Output the single row in Current */
|
||||
addrCont = sqlite3VdbeMakeLabel(v);
|
||||
addrCont = sqlite3VdbeMakeLabel(pParse);
|
||||
codeOffset(v, regOffset, addrCont);
|
||||
selectInnerLoop(pParse, p, iCurrent,
|
||||
0, 0, pDest, addrCont, addrBreak);
|
||||
@@ -2707,8 +2707,8 @@ static int multiSelect(
|
||||
if( dest.eDest!=priorOp ){
|
||||
int iCont, iBreak, iStart;
|
||||
assert( p->pEList );
|
||||
iBreak = sqlite3VdbeMakeLabel(v);
|
||||
iCont = sqlite3VdbeMakeLabel(v);
|
||||
iBreak = sqlite3VdbeMakeLabel(pParse);
|
||||
iCont = sqlite3VdbeMakeLabel(pParse);
|
||||
computeLimitRegisters(pParse, p, iBreak);
|
||||
sqlite3VdbeAddOp2(v, OP_Rewind, unionTab, iBreak); VdbeCoverage(v);
|
||||
iStart = sqlite3VdbeCurrentAddr(v);
|
||||
@@ -2776,8 +2776,8 @@ static int multiSelect(
|
||||
** tables.
|
||||
*/
|
||||
assert( p->pEList );
|
||||
iBreak = sqlite3VdbeMakeLabel(v);
|
||||
iCont = sqlite3VdbeMakeLabel(v);
|
||||
iBreak = sqlite3VdbeMakeLabel(pParse);
|
||||
iCont = sqlite3VdbeMakeLabel(pParse);
|
||||
computeLimitRegisters(pParse, p, iBreak);
|
||||
sqlite3VdbeAddOp2(v, OP_Rewind, tab1, iBreak); VdbeCoverage(v);
|
||||
r1 = sqlite3GetTempReg(pParse);
|
||||
@@ -2907,7 +2907,7 @@ static int generateOutputSubroutine(
|
||||
int addr;
|
||||
|
||||
addr = sqlite3VdbeCurrentAddr(v);
|
||||
iContinue = sqlite3VdbeMakeLabel(v);
|
||||
iContinue = sqlite3VdbeMakeLabel(pParse);
|
||||
|
||||
/* Suppress duplicates for UNION, EXCEPT, and INTERSECT
|
||||
*/
|
||||
@@ -3144,8 +3144,8 @@ static int multiSelectOrderBy(
|
||||
db = pParse->db;
|
||||
v = pParse->pVdbe;
|
||||
assert( v!=0 ); /* Already thrown the error if VDBE alloc failed */
|
||||
labelEnd = sqlite3VdbeMakeLabel(v);
|
||||
labelCmpr = sqlite3VdbeMakeLabel(v);
|
||||
labelEnd = sqlite3VdbeMakeLabel(pParse);
|
||||
labelCmpr = sqlite3VdbeMakeLabel(pParse);
|
||||
|
||||
|
||||
/* Patch up the ORDER BY clause
|
||||
@@ -5330,7 +5330,7 @@ static void updateAccumulator(Parse *pParse, int regAcc, AggInfo *pAggInfo){
|
||||
regAgg = 0;
|
||||
}
|
||||
if( pF->iDistinct>=0 ){
|
||||
addrNext = sqlite3VdbeMakeLabel(v);
|
||||
addrNext = sqlite3VdbeMakeLabel(pParse);
|
||||
testcase( nArg==0 ); /* Error condition */
|
||||
testcase( nArg>1 ); /* Also an error */
|
||||
codeDistinct(pParse, pF->iDistinct, addrNext, 1, regAgg);
|
||||
@@ -6038,7 +6038,7 @@ int sqlite3Select(
|
||||
|
||||
/* Set the limiter.
|
||||
*/
|
||||
iEnd = sqlite3VdbeMakeLabel(v);
|
||||
iEnd = sqlite3VdbeMakeLabel(pParse);
|
||||
if( (p->selFlags & SF_FixedLimit)==0 ){
|
||||
p->nSelectRow = 320; /* 4 billion rows */
|
||||
}
|
||||
@@ -6105,9 +6105,9 @@ int sqlite3Select(
|
||||
assert( p->pEList==pEList );
|
||||
#ifndef SQLITE_OMIT_WINDOWFUNC
|
||||
if( pWin ){
|
||||
int addrGosub = sqlite3VdbeMakeLabel(v);
|
||||
int iCont = sqlite3VdbeMakeLabel(v);
|
||||
int iBreak = sqlite3VdbeMakeLabel(v);
|
||||
int addrGosub = sqlite3VdbeMakeLabel(pParse);
|
||||
int iCont = sqlite3VdbeMakeLabel(pParse);
|
||||
int iBreak = sqlite3VdbeMakeLabel(pParse);
|
||||
int regGosub = ++pParse->nMem;
|
||||
|
||||
sqlite3WindowCodeStep(pParse, p, pWInfo, regGosub, addrGosub);
|
||||
@@ -6182,7 +6182,7 @@ int sqlite3Select(
|
||||
}
|
||||
|
||||
/* Create a label to jump to when we want to abort the query */
|
||||
addrEnd = sqlite3VdbeMakeLabel(v);
|
||||
addrEnd = sqlite3VdbeMakeLabel(pParse);
|
||||
|
||||
/* Convert TK_COLUMN nodes into TK_AGG_COLUMN and make entries in
|
||||
** sAggInfo for all TK_AGG_FUNCTION nodes in expressions of the
|
||||
@@ -6271,9 +6271,9 @@ int sqlite3Select(
|
||||
iUseFlag = ++pParse->nMem;
|
||||
iAbortFlag = ++pParse->nMem;
|
||||
regOutputRow = ++pParse->nMem;
|
||||
addrOutputRow = sqlite3VdbeMakeLabel(v);
|
||||
addrOutputRow = sqlite3VdbeMakeLabel(pParse);
|
||||
regReset = ++pParse->nMem;
|
||||
addrReset = sqlite3VdbeMakeLabel(v);
|
||||
addrReset = sqlite3VdbeMakeLabel(pParse);
|
||||
iAMem = pParse->nMem + 1;
|
||||
pParse->nMem += pGroupBy->nExpr;
|
||||
iBMem = pParse->nMem + 1;
|
||||
|
||||
Reference in New Issue
Block a user