mirror of
https://github.com/sqlite/sqlite.git
synced 2025-11-16 23:02:26 +03:00
Simplifications to the way UnpackedRecord objects are allocated. Smaller
and faster code that also fixes a subtle (currently unreachable) bug. FossilOrigin-Name: f7ab01f254cd9d7006b8dec29adb234a671b8e6f
This commit is contained in:
15
src/btree.c
15
src/btree.c
@@ -763,26 +763,23 @@ static int btreeMoveto(
|
||||
){
|
||||
int rc; /* Status code */
|
||||
UnpackedRecord *pIdxKey; /* Unpacked index key */
|
||||
char aSpace[384]; /* Temp space for pIdxKey - to avoid a malloc */
|
||||
char *pFree = 0;
|
||||
|
||||
if( pKey ){
|
||||
assert( nKey==(i64)(int)nKey );
|
||||
pIdxKey = sqlite3VdbeAllocUnpackedRecord(
|
||||
pCur->pKeyInfo, aSpace, sizeof(aSpace), &pFree
|
||||
);
|
||||
pIdxKey = sqlite3VdbeAllocUnpackedRecord(pCur->pKeyInfo);
|
||||
if( pIdxKey==0 ) return SQLITE_NOMEM_BKPT;
|
||||
sqlite3VdbeRecordUnpack(pCur->pKeyInfo, (int)nKey, pKey, pIdxKey);
|
||||
if( pIdxKey->nField==0 ){
|
||||
sqlite3DbFree(pCur->pKeyInfo->db, pFree);
|
||||
return SQLITE_CORRUPT_BKPT;
|
||||
rc = SQLITE_CORRUPT_BKPT;
|
||||
goto moveto_done;
|
||||
}
|
||||
}else{
|
||||
pIdxKey = 0;
|
||||
}
|
||||
rc = sqlite3BtreeMovetoUnpacked(pCur, pIdxKey, nKey, bias, pRes);
|
||||
if( pFree ){
|
||||
sqlite3DbFree(pCur->pKeyInfo->db, pFree);
|
||||
moveto_done:
|
||||
if( pIdxKey ){
|
||||
sqlite3DbFree(pCur->pKeyInfo->db, pIdxKey);
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
11
src/vdbe.c
11
src/vdbe.c
@@ -3985,10 +3985,9 @@ case OP_Found: { /* jump, in3 */
|
||||
int ii;
|
||||
VdbeCursor *pC;
|
||||
int res;
|
||||
char *pFree;
|
||||
UnpackedRecord *pFree;
|
||||
UnpackedRecord *pIdxKey;
|
||||
UnpackedRecord r;
|
||||
char aTempRec[ROUND8(sizeof(UnpackedRecord)) + sizeof(Mem)*4 + 7];
|
||||
|
||||
#ifdef SQLITE_TEST
|
||||
if( pOp->opcode!=OP_NoConflict ) sqlite3_found_count++;
|
||||
@@ -4005,7 +4004,6 @@ case OP_Found: { /* jump, in3 */
|
||||
assert( pC->eCurType==CURTYPE_BTREE );
|
||||
assert( pC->uc.pCursor!=0 );
|
||||
assert( pC->isTable==0 );
|
||||
pFree = 0;
|
||||
if( pOp->p4.i>0 ){
|
||||
r.pKeyInfo = pC->pKeyInfo;
|
||||
r.nField = (u16)pOp->p4.i;
|
||||
@@ -4018,10 +4016,9 @@ case OP_Found: { /* jump, in3 */
|
||||
}
|
||||
#endif
|
||||
pIdxKey = &r;
|
||||
pFree = 0;
|
||||
}else{
|
||||
pIdxKey = sqlite3VdbeAllocUnpackedRecord(
|
||||
pC->pKeyInfo, aTempRec, sizeof(aTempRec), &pFree
|
||||
);
|
||||
pFree = pIdxKey = sqlite3VdbeAllocUnpackedRecord(pC->pKeyInfo);
|
||||
if( pIdxKey==0 ) goto no_mem;
|
||||
assert( pIn3->flags & MEM_Blob );
|
||||
(void)ExpandBlob(pIn3);
|
||||
@@ -4041,7 +4038,7 @@ case OP_Found: { /* jump, in3 */
|
||||
}
|
||||
}
|
||||
rc = sqlite3BtreeMovetoUnpacked(pC->uc.pCursor, pIdxKey, 0, 0, &res);
|
||||
sqlite3DbFree(db, pFree);
|
||||
if( pFree ) sqlite3DbFree(db, pFree);
|
||||
if( rc!=SQLITE_OK ){
|
||||
goto abort_due_to_error;
|
||||
}
|
||||
|
||||
@@ -233,7 +233,7 @@ int sqlite3MemCompare(const Mem*, const Mem*, const CollSeq*);
|
||||
void sqlite3VdbeRecordUnpack(KeyInfo*,int,const void*,UnpackedRecord*);
|
||||
int sqlite3VdbeRecordCompare(int,const void*,UnpackedRecord*);
|
||||
int sqlite3VdbeRecordCompareWithSkip(int, const void *, UnpackedRecord *, int);
|
||||
UnpackedRecord *sqlite3VdbeAllocUnpackedRecord(KeyInfo *, char *, int, char **);
|
||||
UnpackedRecord *sqlite3VdbeAllocUnpackedRecord(KeyInfo*);
|
||||
|
||||
typedef int (*RecordCompare)(int,const void*,UnpackedRecord*);
|
||||
RecordCompare sqlite3VdbeFindCompare(UnpackedRecord*);
|
||||
|
||||
@@ -1657,10 +1657,9 @@ static UnpackedRecord *vdbeUnpackRecord(
|
||||
int nKey,
|
||||
const void *pKey
|
||||
){
|
||||
char *dummy; /* Dummy argument for AllocUnpackedRecord() */
|
||||
UnpackedRecord *pRet; /* Return value */
|
||||
|
||||
pRet = sqlite3VdbeAllocUnpackedRecord(pKeyInfo, 0, 0, &dummy);
|
||||
pRet = sqlite3VdbeAllocUnpackedRecord(pKeyInfo);
|
||||
if( pRet ){
|
||||
memset(pRet->aMem, 0, sizeof(Mem)*(pKeyInfo->nField+1));
|
||||
sqlite3VdbeRecordUnpack(pKeyInfo, nKey, pKey, pRet);
|
||||
|
||||
@@ -3494,30 +3494,13 @@ u32 sqlite3VdbeSerialGet(
|
||||
** If an OOM error occurs, NULL is returned.
|
||||
*/
|
||||
UnpackedRecord *sqlite3VdbeAllocUnpackedRecord(
|
||||
KeyInfo *pKeyInfo, /* Description of the record */
|
||||
char *pSpace, /* Unaligned space available */
|
||||
int szSpace, /* Size of pSpace[] in bytes */
|
||||
char **ppFree /* OUT: Caller should free this pointer */
|
||||
KeyInfo *pKeyInfo /* Description of the record */
|
||||
){
|
||||
UnpackedRecord *p; /* Unpacked record to return */
|
||||
int nOff; /* Increment pSpace by nOff to align it */
|
||||
int nByte; /* Number of bytes required for *p */
|
||||
|
||||
/* We want to shift the pointer pSpace up such that it is 8-byte aligned.
|
||||
** Thus, we need to calculate a value, nOff, between 0 and 7, to shift
|
||||
** it by. If pSpace is already 8-byte aligned, nOff should be zero.
|
||||
*/
|
||||
nOff = (8 - (SQLITE_PTR_TO_INT(pSpace) & 7)) & 7;
|
||||
nByte = ROUND8(sizeof(UnpackedRecord)) + sizeof(Mem)*(pKeyInfo->nField+1);
|
||||
if( nByte>szSpace+nOff ){
|
||||
p = (UnpackedRecord *)sqlite3DbMallocRaw(pKeyInfo->db, nByte);
|
||||
*ppFree = (char *)p;
|
||||
if( !p ) return 0;
|
||||
}else{
|
||||
p = (UnpackedRecord*)&pSpace[nOff];
|
||||
*ppFree = 0;
|
||||
}
|
||||
|
||||
p = (UnpackedRecord *)sqlite3DbMallocRaw(pKeyInfo->db, nByte);
|
||||
if( !p ) return 0;
|
||||
p->aMem = (Mem*)&((char*)p)[ROUND8(sizeof(UnpackedRecord))];
|
||||
assert( pKeyInfo->aSortOrder!=0 );
|
||||
p->pKeyInfo = pKeyInfo;
|
||||
|
||||
@@ -1327,12 +1327,8 @@ static int vdbeSorterOpenTempFile(
|
||||
*/
|
||||
static int vdbeSortAllocUnpacked(SortSubtask *pTask){
|
||||
if( pTask->pUnpacked==0 ){
|
||||
char *pFree;
|
||||
pTask->pUnpacked = sqlite3VdbeAllocUnpackedRecord(
|
||||
pTask->pSorter->pKeyInfo, 0, 0, &pFree
|
||||
);
|
||||
assert( pTask->pUnpacked==(UnpackedRecord*)pFree );
|
||||
if( pFree==0 ) return SQLITE_NOMEM_BKPT;
|
||||
pTask->pUnpacked = sqlite3VdbeAllocUnpackedRecord(pTask->pSorter->pKeyInfo);
|
||||
if( pTask->pUnpacked==0 ) return SQLITE_NOMEM_BKPT;
|
||||
pTask->pUnpacked->nField = pTask->pSorter->pKeyInfo->nField;
|
||||
pTask->pUnpacked->errCode = 0;
|
||||
}
|
||||
@@ -2733,9 +2729,7 @@ int sqlite3VdbeSorterCompare(
|
||||
r2 = pSorter->pUnpacked;
|
||||
pKeyInfo = pCsr->pKeyInfo;
|
||||
if( r2==0 ){
|
||||
char *p;
|
||||
r2 = pSorter->pUnpacked = sqlite3VdbeAllocUnpackedRecord(pKeyInfo,0,0,&p);
|
||||
assert( pSorter->pUnpacked==(UnpackedRecord*)p );
|
||||
r2 = pSorter->pUnpacked = sqlite3VdbeAllocUnpackedRecord(pKeyInfo);
|
||||
if( r2==0 ) return SQLITE_NOMEM_BKPT;
|
||||
r2->nField = nKeyCol;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user