mirror of
https://github.com/sqlite/sqlite.git
synced 2025-11-12 13:01:09 +03:00
Avoid unnecessary moving of content between registers during an ORDER BY.
FossilOrigin-Name: 4f472accf072d9cb64f209923924b26f21b13d27
This commit is contained in:
14
manifest
14
manifest
@@ -1,5 +1,5 @@
|
|||||||
C Remove\san\sunnecessary\stemporary\sregister\sallocation.
|
C Avoid\sunnecessary\smoving\sof\scontent\sbetween\sregisters\sduring\san\sORDER\sBY.
|
||||||
D 2014-03-24T09:34:58.396
|
D 2014-03-24T18:08:15.960
|
||||||
F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f
|
F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f
|
||||||
F Makefile.in 2ef13430cd359f7b361bb863504e227b25cc7f81
|
F Makefile.in 2ef13430cd359f7b361bb863504e227b25cc7f81
|
||||||
F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23
|
F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23
|
||||||
@@ -217,7 +217,7 @@ F src/printf.c e5a0005f8b3de21f85da6a709d2fbee76775bf4b
|
|||||||
F src/random.c d10c1f85b6709ca97278428fd5db5bbb9c74eece
|
F src/random.c d10c1f85b6709ca97278428fd5db5bbb9c74eece
|
||||||
F src/resolve.c 273d5f47c4e2c05b2d3d2bffeda939551ab59e66
|
F src/resolve.c 273d5f47c4e2c05b2d3d2bffeda939551ab59e66
|
||||||
F src/rowset.c 64655f1a627c9c212d9ab497899e7424a34222e0
|
F src/rowset.c 64655f1a627c9c212d9ab497899e7424a34222e0
|
||||||
F src/select.c a088183774c4efae4105076355ac4010c62390a8
|
F src/select.c 7f4a1ef9c9e893ee6da160441cd773c951f3d44e
|
||||||
F src/shell.c cee9f46f2688a261601b1fd3d7f4b3cddf9b5cdf
|
F src/shell.c cee9f46f2688a261601b1fd3d7f4b3cddf9b5cdf
|
||||||
F src/sqlite.h.in a2ef671f92747a5a1c8a47bad5c585a8dd9eca80
|
F src/sqlite.h.in a2ef671f92747a5a1c8a47bad5c585a8dd9eca80
|
||||||
F src/sqlite3.rc 11094cc6a157a028b301a9f06b3d03089ea37c3e
|
F src/sqlite3.rc 11094cc6a157a028b301a9f06b3d03089ea37c3e
|
||||||
@@ -1157,7 +1157,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1
|
|||||||
F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4
|
F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4
|
||||||
F tool/warnings.sh d1a6de74685f360ab718efda6265994b99bbea01
|
F tool/warnings.sh d1a6de74685f360ab718efda6265994b99bbea01
|
||||||
F tool/win/sqlite.vsix 030f3eeaf2cb811a3692ab9c14d021a75ce41fff
|
F tool/win/sqlite.vsix 030f3eeaf2cb811a3692ab9c14d021a75ce41fff
|
||||||
P e6c59d23316c83b318b1a94d9b28a5d321737fa5
|
P 5d506743f541b022cde04a9606baa4680cdfd70b
|
||||||
R ab9aa4f9f7d5ea8c370ac77061403538
|
R edfc832bbac864fb9d0e2cb38ae7f098
|
||||||
U dan
|
U drh
|
||||||
Z 631d6a70f4aeb5d6a455a81761c8aefd
|
Z a04be0daeb9646c039a07b2f019c65a9
|
||||||
|
|||||||
@@ -1 +1 @@
|
|||||||
5d506743f541b022cde04a9606baa4680cdfd70b
|
4f472accf072d9cb64f209923924b26f21b13d27
|
||||||
34
src/select.c
34
src/select.c
@@ -463,19 +463,28 @@ static void pushOntoSorter(
|
|||||||
SortCtx *pSort, /* Information about the ORDER BY clause */
|
SortCtx *pSort, /* Information about the ORDER BY clause */
|
||||||
Select *pSelect, /* The whole SELECT statement */
|
Select *pSelect, /* The whole SELECT statement */
|
||||||
int regData, /* First register holding data to be sorted */
|
int regData, /* First register holding data to be sorted */
|
||||||
int nData /* Number of elements in the data array */
|
int nData, /* Number of elements in the data array */
|
||||||
|
int nPrefixReg /* No. of reg prior to regData available for use */
|
||||||
){
|
){
|
||||||
Vdbe *v = pParse->pVdbe; /* Stmt under construction */
|
Vdbe *v = pParse->pVdbe; /* Stmt under construction */
|
||||||
int nExpr = pSort->pOrderBy->nExpr; /* No. of ORDER BY terms */
|
int nExpr = pSort->pOrderBy->nExpr; /* No. of ORDER BY terms */
|
||||||
int nBase = nExpr + 1 + nData; /* Fields in sorter record */
|
int nBase = nExpr + 1 + nData; /* Fields in sorter record */
|
||||||
int regBase = sqlite3GetTempRange(pParse, nBase); /* Regs for sorter record */
|
int regBase; /* Regs for sorter record */
|
||||||
int regRecord = sqlite3GetTempReg(pParse); /* Assemblied sorter record */
|
int regRecord = sqlite3GetTempReg(pParse); /* Assemblied sorter record */
|
||||||
int nOBSat = pSort->nOBSat; /* No. ORDER BY terms to skip */
|
int nOBSat = pSort->nOBSat; /* No. ORDER BY terms to skip */
|
||||||
int op; /* Opcode to add sorter record to sorter */
|
int op; /* Opcode to add sorter record to sorter */
|
||||||
|
|
||||||
|
if( nPrefixReg ){
|
||||||
|
assert( nPrefixReg==nExpr+1 );
|
||||||
|
regBase = regData - nExpr - 1;
|
||||||
|
}else{
|
||||||
|
regBase = sqlite3GetTempRange(pParse, nBase);
|
||||||
|
}
|
||||||
sqlite3ExprCodeExprList(pParse, pSort->pOrderBy, regBase, SQLITE_ECEL_DUP);
|
sqlite3ExprCodeExprList(pParse, pSort->pOrderBy, regBase, SQLITE_ECEL_DUP);
|
||||||
sqlite3VdbeAddOp2(v, OP_Sequence, pSort->iECursor, regBase+nExpr);
|
sqlite3VdbeAddOp2(v, OP_Sequence, pSort->iECursor, regBase+nExpr);
|
||||||
|
if( nPrefixReg==0 ){
|
||||||
sqlite3VdbeAddOp3(v, OP_Move, regData, regBase+nExpr+1, nData);
|
sqlite3VdbeAddOp3(v, OP_Move, regData, regBase+nExpr+1, nData);
|
||||||
|
}
|
||||||
sqlite3VdbeAddOp3(v, OP_MakeRecord, regBase+nOBSat, nBase-nOBSat, regRecord);
|
sqlite3VdbeAddOp3(v, OP_MakeRecord, regBase+nOBSat, nBase-nOBSat, regRecord);
|
||||||
if( nOBSat>0 ){
|
if( nOBSat>0 ){
|
||||||
int regPrevKey; /* The first nOBSat columns of the previous row */
|
int regPrevKey; /* The first nOBSat columns of the previous row */
|
||||||
@@ -515,8 +524,10 @@ static void pushOntoSorter(
|
|||||||
sqlite3VdbeAddOp2(v, op, pSort->iECursor, regRecord);
|
sqlite3VdbeAddOp2(v, op, pSort->iECursor, regRecord);
|
||||||
if( nOBSat==0 ){
|
if( nOBSat==0 ){
|
||||||
sqlite3ReleaseTempReg(pParse, regRecord);
|
sqlite3ReleaseTempReg(pParse, regRecord);
|
||||||
|
if( nPrefixReg==0 ){
|
||||||
sqlite3ReleaseTempRange(pParse, regBase, nBase);
|
sqlite3ReleaseTempRange(pParse, regBase, nBase);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
if( pSelect->iLimit ){
|
if( pSelect->iLimit ){
|
||||||
int addr1, addr2;
|
int addr1, addr2;
|
||||||
int iLimit;
|
int iLimit;
|
||||||
@@ -631,6 +642,7 @@ static void selectInnerLoop(
|
|||||||
int eDest = pDest->eDest; /* How to dispose of results */
|
int eDest = pDest->eDest; /* How to dispose of results */
|
||||||
int iParm = pDest->iSDParm; /* First argument to disposal method */
|
int iParm = pDest->iSDParm; /* First argument to disposal method */
|
||||||
int nResultCol; /* Number of result columns */
|
int nResultCol; /* Number of result columns */
|
||||||
|
int nPrefixReg = 0; /* Number of extra registers before regResult */
|
||||||
|
|
||||||
assert( v );
|
assert( v );
|
||||||
assert( pEList!=0 );
|
assert( pEList!=0 );
|
||||||
@@ -646,6 +658,10 @@ static void selectInnerLoop(
|
|||||||
nResultCol = pEList->nExpr;
|
nResultCol = pEList->nExpr;
|
||||||
|
|
||||||
if( pDest->iSdst==0 ){
|
if( pDest->iSdst==0 ){
|
||||||
|
if( pSort ){
|
||||||
|
nPrefixReg = pSort->pOrderBy->nExpr + 1;
|
||||||
|
pParse->nMem += nPrefixReg;
|
||||||
|
}
|
||||||
pDest->iSdst = pParse->nMem+1;
|
pDest->iSdst = pParse->nMem+1;
|
||||||
pParse->nMem += nResultCol;
|
pParse->nMem += nResultCol;
|
||||||
}else if( pDest->iSdst+nResultCol > pParse->nMem ){
|
}else if( pDest->iSdst+nResultCol > pParse->nMem ){
|
||||||
@@ -762,10 +778,10 @@ static void selectInnerLoop(
|
|||||||
case SRT_DistFifo:
|
case SRT_DistFifo:
|
||||||
case SRT_Table:
|
case SRT_Table:
|
||||||
case SRT_EphemTab: {
|
case SRT_EphemTab: {
|
||||||
int r1 = sqlite3GetTempReg(pParse);
|
int r1 = sqlite3GetTempRange(pParse, nPrefixReg+1);
|
||||||
testcase( eDest==SRT_Table );
|
testcase( eDest==SRT_Table );
|
||||||
testcase( eDest==SRT_EphemTab );
|
testcase( eDest==SRT_EphemTab );
|
||||||
sqlite3VdbeAddOp3(v, OP_MakeRecord, regResult, nResultCol, r1);
|
sqlite3VdbeAddOp3(v, OP_MakeRecord, regResult, nResultCol, r1+nPrefixReg);
|
||||||
#ifndef SQLITE_OMIT_CTE
|
#ifndef SQLITE_OMIT_CTE
|
||||||
if( eDest==SRT_DistFifo ){
|
if( eDest==SRT_DistFifo ){
|
||||||
/* If the destination is DistFifo, then cursor (iParm+1) is open
|
/* If the destination is DistFifo, then cursor (iParm+1) is open
|
||||||
@@ -780,7 +796,7 @@ static void selectInnerLoop(
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
if( pSort ){
|
if( pSort ){
|
||||||
pushOntoSorter(pParse, pSort, p, r1, 1);
|
pushOntoSorter(pParse, pSort, p, r1+nPrefixReg, 1, nPrefixReg);
|
||||||
}else{
|
}else{
|
||||||
int r2 = sqlite3GetTempReg(pParse);
|
int r2 = sqlite3GetTempReg(pParse);
|
||||||
sqlite3VdbeAddOp2(v, OP_NewRowid, iParm, r2);
|
sqlite3VdbeAddOp2(v, OP_NewRowid, iParm, r2);
|
||||||
@@ -788,7 +804,7 @@ static void selectInnerLoop(
|
|||||||
sqlite3VdbeChangeP5(v, OPFLAG_APPEND);
|
sqlite3VdbeChangeP5(v, OPFLAG_APPEND);
|
||||||
sqlite3ReleaseTempReg(pParse, r2);
|
sqlite3ReleaseTempReg(pParse, r2);
|
||||||
}
|
}
|
||||||
sqlite3ReleaseTempReg(pParse, r1);
|
sqlite3ReleaseTempRange(pParse, r1, nPrefixReg+1);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -806,7 +822,7 @@ static void selectInnerLoop(
|
|||||||
** ORDER BY in this case since the order of entries in the set
|
** ORDER BY in this case since the order of entries in the set
|
||||||
** does not matter. But there might be a LIMIT clause, in which
|
** does not matter. But there might be a LIMIT clause, in which
|
||||||
** case the order does matter */
|
** case the order does matter */
|
||||||
pushOntoSorter(pParse, pSort, p, regResult, 1);
|
pushOntoSorter(pParse, pSort, p, regResult, 1, nPrefixReg);
|
||||||
}else{
|
}else{
|
||||||
int r1 = sqlite3GetTempReg(pParse);
|
int r1 = sqlite3GetTempReg(pParse);
|
||||||
sqlite3VdbeAddOp4(v, OP_MakeRecord, regResult,1,r1, &pDest->affSdst, 1);
|
sqlite3VdbeAddOp4(v, OP_MakeRecord, regResult,1,r1, &pDest->affSdst, 1);
|
||||||
@@ -832,7 +848,7 @@ static void selectInnerLoop(
|
|||||||
case SRT_Mem: {
|
case SRT_Mem: {
|
||||||
assert( nResultCol==1 );
|
assert( nResultCol==1 );
|
||||||
if( pSort ){
|
if( pSort ){
|
||||||
pushOntoSorter(pParse, pSort, p, regResult, 1);
|
pushOntoSorter(pParse, pSort, p, regResult, 1, nPrefixReg);
|
||||||
}else{
|
}else{
|
||||||
sqlite3ExprCodeMove(pParse, regResult, iParm, 1);
|
sqlite3ExprCodeMove(pParse, regResult, iParm, 1);
|
||||||
/* The LIMIT clause will jump out of the loop for us */
|
/* The LIMIT clause will jump out of the loop for us */
|
||||||
@@ -846,7 +862,7 @@ static void selectInnerLoop(
|
|||||||
testcase( eDest==SRT_Coroutine );
|
testcase( eDest==SRT_Coroutine );
|
||||||
testcase( eDest==SRT_Output );
|
testcase( eDest==SRT_Output );
|
||||||
if( pSort ){
|
if( pSort ){
|
||||||
pushOntoSorter(pParse, pSort, p, regResult, nResultCol);
|
pushOntoSorter(pParse, pSort, p, regResult, nResultCol, nPrefixReg);
|
||||||
}else if( eDest==SRT_Coroutine ){
|
}else if( eDest==SRT_Coroutine ){
|
||||||
sqlite3VdbeAddOp1(v, OP_Yield, pDest->iSDParm);
|
sqlite3VdbeAddOp1(v, OP_Yield, pDest->iSDParm);
|
||||||
}else{
|
}else{
|
||||||
|
|||||||
Reference in New Issue
Block a user