1
0
mirror of https://github.com/sqlite/sqlite.git synced 2025-08-07 02:42:48 +03:00

Optimizations to the OP_Found opcode save about 600K cycles in speedtest1.

FossilOrigin-Name: 5c3357ad62843fe982b9c2d31dbf02018f2948ceab2c85dac917cd9ce1e97dd6
This commit is contained in:
drh
2022-04-04 19:43:57 +00:00
parent 36d2d09023
commit b834e0de59
3 changed files with 36 additions and 31 deletions

View File

@@ -4966,11 +4966,9 @@ case OP_NoConflict: /* jump, in3 */
case OP_NotFound: /* jump, in3 */
case OP_Found: { /* jump, in3 */
int alreadyExists;
int takeJump;
int ii;
VdbeCursor *pC;
int res;
UnpackedRecord *pFree;
UnpackedRecord *pIdxKey;
UnpackedRecord r;
@@ -4990,9 +4988,11 @@ case OP_Found: { /* jump, in3 */
assert( pC->uc.pCursor!=0 );
assert( pC->isTable==0 );
if( pOp->p4.i>0 ){
r.pKeyInfo = pC->pKeyInfo;
/* Key values in an array of registers */
r.nField = (u16)pOp->p4.i;
r.pKeyInfo = pC->pKeyInfo;
r.aMem = pIn3;
r.default_rc = 0;
#ifdef SQLITE_DEBUG
for(ii=0; ii<r.nField; ii++){
assert( memIsValid(&r.aMem[ii]) );
@@ -5000,32 +5000,21 @@ case OP_Found: { /* jump, in3 */
if( ii ) REGISTER_TRACE(pOp->p3+ii, &r.aMem[ii]);
}
#endif
pIdxKey = &r;
pFree = 0;
rc = sqlite3BtreeIndexMoveto(pC->uc.pCursor, &r, &res);
}else{
/* Composite key generated by OP_MakeRecord */
assert( pIn3->flags & MEM_Blob );
assert( pOp->opcode!=OP_NoConflict );
rc = ExpandBlob(pIn3);
assert( rc==SQLITE_OK || rc==SQLITE_NOMEM );
if( rc ) goto no_mem;
pFree = pIdxKey = sqlite3VdbeAllocUnpackedRecord(pC->pKeyInfo);
pIdxKey = sqlite3VdbeAllocUnpackedRecord(pC->pKeyInfo);
if( pIdxKey==0 ) goto no_mem;
sqlite3VdbeRecordUnpack(pC->pKeyInfo, pIn3->n, pIn3->z, pIdxKey);
pIdxKey->default_rc = 0;
rc = sqlite3BtreeIndexMoveto(pC->uc.pCursor, pIdxKey, &res);
sqlite3DbFreeNN(db, pIdxKey);
}
pIdxKey->default_rc = 0;
takeJump = 0;
if( pOp->opcode==OP_NoConflict ){
/* For the OP_NoConflict opcode, take the jump if any of the
** input fields are NULL, since any key with a NULL will not
** conflict */
for(ii=0; ii<pIdxKey->nField; ii++){
if( pIdxKey->aMem[ii].flags & MEM_Null ){
takeJump = 1;
break;
}
}
}
rc = sqlite3BtreeIndexMoveto(pC->uc.pCursor, pIdxKey, &res);
if( pFree ) sqlite3DbFreeNN(db, pFree);
if( rc!=SQLITE_OK ){
goto abort_due_to_error;
}
@@ -5038,9 +5027,25 @@ case OP_Found: { /* jump, in3 */
VdbeBranchTaken(alreadyExists!=0,2);
if( alreadyExists ) goto jump_to_p2;
}else{
VdbeBranchTaken(takeJump||alreadyExists==0,2);
if( takeJump || !alreadyExists ) goto jump_to_p2;
if( pOp->opcode==OP_IfNoHope ) pC->seekHit = pOp->p4.i;
if( !alreadyExists ){
VdbeBranchTaken(1,2);
goto jump_to_p2;
}
if( pOp->opcode==OP_NoConflict ){
/* For the OP_NoConflict opcode, take the jump if any of the
** input fields are NULL, since any key with a NULL will not
** conflict */
for(ii=0; ii<r.nField; ii++){
if( r.aMem[ii].flags & MEM_Null ){
VdbeBranchTaken(1,2);
goto jump_to_p2;
}
}
}
VdbeBranchTaken(0,2);
if( pOp->opcode==OP_IfNoHope ){
pC->seekHit = pOp->p4.i;
}
}
break;
}