diff options
Diffstat (limited to 'src/select.c')
-rw-r--r-- | src/select.c | 117 |
1 files changed, 48 insertions, 69 deletions
diff --git a/src/select.c b/src/select.c index 353ef06c9..56a75c97f 100644 --- a/src/select.c +++ b/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.459 2008/07/24 15:50:41 drh Exp $ +** $Id: select.c,v 1.460 2008/07/28 19:34:53 drh Exp $ */ #include "sqliteInt.h" @@ -21,16 +21,16 @@ ** Delete all the content of a Select structure but do not deallocate ** the select structure itself. */ -static void clearSelect(Select *p){ - sqlite3ExprListDelete(p->pEList); - sqlite3SrcListDelete(p->pSrc); - sqlite3ExprDelete(p->pWhere); - sqlite3ExprListDelete(p->pGroupBy); - sqlite3ExprDelete(p->pHaving); - sqlite3ExprListDelete(p->pOrderBy); - sqlite3SelectDelete(p->pPrior); - sqlite3ExprDelete(p->pLimit); - sqlite3ExprDelete(p->pOffset); +static void clearSelect(sqlite3 *db, Select *p){ + sqlite3ExprListDelete(db, p->pEList); + sqlite3SrcListDelete(db, p->pSrc); + sqlite3ExprDelete(db, p->pWhere); + sqlite3ExprListDelete(db, p->pGroupBy); + sqlite3ExprDelete(db, p->pHaving); + sqlite3ExprListDelete(db, p->pOrderBy); + sqlite3SelectDelete(db, p->pPrior); + sqlite3ExprDelete(db, p->pLimit); + sqlite3ExprDelete(db, p->pOffset); } /* @@ -88,7 +88,7 @@ Select *sqlite3SelectNew( pNew->addrOpenEphm[1] = -1; pNew->addrOpenEphm[2] = -1; if( pNew==&standin) { - clearSelect(pNew); + clearSelect(db, pNew); pNew = 0; } return pNew; @@ -97,10 +97,10 @@ Select *sqlite3SelectNew( /* ** Delete the given Select structure and all of its substructures. */ -void sqlite3SelectDelete(Select *p){ +void sqlite3SelectDelete(sqlite3 *db, Select *p){ if( p ){ - clearSelect(p); - sqlite3_free(p); + clearSelect(db, p); + sqlite3DbFree(db, p); } } @@ -1163,6 +1163,7 @@ Table *sqlite3ResultSetOfSelect(Parse *pParse, char *zTabName, Select *pSelect){ if( pTab==0 ){ return 0; } + pTab->db = db; pTab->nRef = 1; pTab->zName = zTabName ? sqlite3DbStrDup(db, zTabName) : 0; pEList = pSelect->pEList; @@ -1196,7 +1197,7 @@ Table *sqlite3ResultSetOfSelect(Parse *pParse, char *zTabName, Select *pSelect){ zName = sqlite3MPrintf(db, "%T", &p->span); } if( db->mallocFailed ){ - sqlite3_free(zName); + sqlite3DbFree(db, zName); break; } sqlite3Dequote(zName); @@ -1207,8 +1208,11 @@ Table *sqlite3ResultSetOfSelect(Parse *pParse, char *zTabName, Select *pSelect){ nName = strlen(zName); for(j=cnt=0; j<i; j++){ if( sqlite3StrICmp(aCol[j].zName, zName)==0 ){ + char *zNewName; zName[nName] = 0; - zName = sqlite3MPrintf(db, "%z:%d", zName, ++cnt); + zNewName = sqlite3MPrintf(db, "%s:%d", zName, ++cnt); + sqlite3DbFree(db, zName); + zName = zNewName; j = -1; if( zName==0 ) break; } @@ -1474,10 +1478,10 @@ static int prepSelectStmt(Parse *pParse, Select *p){ } rc = 1; } - sqlite3_free(zTName); + sqlite3DbFree(db, zTName); } } - sqlite3ExprListDelete(pEList); + sqlite3ExprListDelete(db, pEList); p->pEList = pNew; } #if SQLITE_MAX_COLUMN @@ -1538,11 +1542,11 @@ static int matchOrderByTermToExprList( for(i=0; i<pEList->nExpr; i++){ char *zAs = pEList->a[i].zName; if( zAs!=0 && sqlite3StrICmp(zAs, zCol)==0 ){ - sqlite3_free(zCol); + sqlite3DbFree(db, zCol); return i+1; } } - sqlite3_free(zCol); + sqlite3DbFree(db, zCol); } /* Resolve all names in the ORDER BY term expression @@ -1631,7 +1635,7 @@ static int processOrderGroupBy( if( iCol>0 ){ CollSeq *pColl = pE->pColl; int flags = pE->flags & EP_ExpCollate; - sqlite3ExprDelete(pE); + sqlite3ExprDelete(db, pE); pE = sqlite3ExprDup(db, pEList->a[iCol-1].pExpr); pOrderBy->a[i].pExpr = pE; if( pE && pColl && flags ){ @@ -1702,7 +1706,7 @@ static int processCompoundOrderBy( assert(pDup); iCol = matchOrderByTermToExprList(pParse, pSelect, pDup, i+1, 1, 0); } - sqlite3ExprDelete(pDup); + sqlite3ExprDelete(db, pDup); if( iCol<0 ){ return 1; } @@ -1882,6 +1886,7 @@ static int multiSelect( Vdbe *v; /* Generate code to this VDBE */ SelectDest dest; /* Alternative data destination */ Select *pDelete = 0; /* Chain of simple selects to delete */ + sqlite3 *db; /* Database connection */ /* Make sure there is no ORDER BY or LIMIT clause on prior SELECTs. Only ** the last (right-most) SELECT in the series may have an ORDER BY or LIMIT. @@ -1890,6 +1895,7 @@ static int multiSelect( rc = 1; goto multi_select_end; } + db = pParse->db; pPrior = p->pPrior; assert( pPrior->pRightmost!=pPrior ); assert( pPrior->pRightmost==p->pRightmost ); @@ -2026,11 +2032,11 @@ static int multiSelect( rc = sqlite3Select(pParse, p, &uniondest, 0, 0, 0); /* Query flattening in sqlite3Select() might refill p->pOrderBy. ** Be sure to delete p->pOrderBy, therefore, to avoid a memory leak. */ - sqlite3ExprListDelete(p->pOrderBy); + sqlite3ExprListDelete(db, p->pOrderBy); pDelete = p->pPrior; p->pPrior = pPrior; p->pOrderBy = 0; - sqlite3ExprDelete(p->pLimit); + sqlite3ExprDelete(db, p->pLimit); p->pLimit = pLimit; p->pOffset = pOffset; p->iLimit = 0; @@ -2109,7 +2115,7 @@ static int multiSelect( rc = sqlite3Select(pParse, p, &intersectdest, 0, 0, 0); pDelete = p->pPrior; p->pPrior = pPrior; - sqlite3ExprDelete(p->pLimit); + sqlite3ExprDelete(db, p->pLimit); p->pLimit = pLimit; p->pOffset = pOffset; if( rc ){ @@ -2162,20 +2168,20 @@ static int multiSelect( assert( p->pRightmost==p ); nCol = p->pEList->nExpr; - pKeyInfo = sqlite3DbMallocZero(pParse->db, + pKeyInfo = sqlite3DbMallocZero(db, sizeof(*pKeyInfo)+nCol*(sizeof(CollSeq*) + 1)); if( !pKeyInfo ){ rc = SQLITE_NOMEM; goto multi_select_end; } - pKeyInfo->enc = ENC(pParse->db); + pKeyInfo->enc = ENC(db); pKeyInfo->nField = nCol; for(i=0, apColl=pKeyInfo->aColl; i<nCol; i++, apColl++){ *apColl = multiSelectCollSeq(pParse, p, i); if( 0==*apColl ){ - *apColl = pParse->db->pDfltColl; + *apColl = db->pDfltColl; } } @@ -2193,13 +2199,13 @@ static int multiSelect( pLoop->addrOpenEphm[i] = -1; } } - sqlite3_free(pKeyInfo); + sqlite3DbFree(db, pKeyInfo); } multi_select_end: pDest->iMem = dest.iMem; pDest->nMem = dest.nMem; - sqlite3SelectDelete(pDelete); + sqlite3SelectDelete(db, pDelete); return rc; } #endif /* SQLITE_OMIT_COMPOUND_SELECT */ @@ -2622,9 +2628,9 @@ static int multiSelectOrderBy( }else{ regLimitA = regLimitB = 0; } - sqlite3ExprDelete(p->pLimit); + sqlite3ExprDelete(db, p->pLimit); p->pLimit = 0; - sqlite3ExprDelete(p->pOffset); + sqlite3ExprDelete(db, p->pOffset); p->pOffset = 0; regAddrA = ++pParse->nMem; @@ -2786,7 +2792,7 @@ static int multiSelectOrderBy( /* Reassembly the compound query so that it will be freed correctly ** by the calling function */ if( p->pPrior ){ - sqlite3SelectDelete(p->pPrior); + sqlite3SelectDelete(db, p->pPrior); } p->pPrior = pPrior; @@ -3155,9 +3161,9 @@ static int flattenSubquery( nSubSrc = pSubSrc->nSrc; jointype = pSubitem->jointype; sqlite3DeleteTable(pSubitem->pTab); - sqlite3_free(pSubitem->zDatabase); - sqlite3_free(pSubitem->zName); - sqlite3_free(pSubitem->zAlias); + sqlite3DbFree(db, pSubitem->zDatabase); + sqlite3DbFree(db, pSubitem->zName); + sqlite3DbFree(db, pSubitem->zAlias); pSubitem->pTab = 0; pSubitem->zDatabase = 0; pSubitem->zName = 0; @@ -3254,7 +3260,7 @@ static int flattenSubquery( /* Finially, delete what is left of the subquery and return ** success. */ - sqlite3SelectDelete(pSub1); + sqlite3SelectDelete(db, pSub1); return 1; } @@ -3525,33 +3531,6 @@ static void updateAccumulator(Parse *pParse, AggInfo *pAggInfo){ pAggInfo->directMode = 0; } -#if 0 -/* -** This function is used when a SELECT statement is used to create a -** temporary table for iterating through when running an INSTEAD OF -** UPDATE or INSTEAD OF DELETE trigger. -** -** If possible, the SELECT statement is modified so that NULL values -** are stored in the temporary table for all columns for which the -** corresponding bit in argument mask is not set. If mask takes the -** special value 0xffffffff, then all columns are populated. -*/ -void sqlite3SelectMask(Parse *pParse, Select *p, u32 mask){ - if( p && !p->pPrior && !p->isDistinct && mask!=0xffffffff ){ - ExprList *pEList; - int i; - sqlite3SelectResolve(pParse, p, 0); - pEList = p->pEList; - for(i=0; pEList && i<pEList->nExpr && i<32; i++){ - if( !(mask&((u32)1<<i)) ){ - sqlite3ExprDelete(pEList->a[i].pExpr); - pEList->a[i].pExpr = sqlite3Expr(pParse->db, TK_NULL, 0, 0, 0); - } - } - } -} -#endif - /* ** Generate code for the given SELECT statement. ** @@ -4144,7 +4123,7 @@ int sqlite3Select( resetAccumulator(pParse, &sAggInfo); pWInfo = sqlite3WhereBegin(pParse, pTabList, pWhere, &pMinMax, flag); if( pWInfo==0 ){ - sqlite3ExprListDelete(pDel); + sqlite3ExprListDelete(db, pDel); goto select_end; } updateAccumulator(pParse, &sAggInfo); @@ -4161,7 +4140,7 @@ int sqlite3Select( selectInnerLoop(pParse, p, p->pEList, 0, 0, 0, -1, pDest, addrEnd, addrEnd); - sqlite3ExprListDelete(pDel); + sqlite3ExprListDelete(db, pDel); } sqlite3VdbeResolveLabel(v, addrEnd); @@ -4208,8 +4187,8 @@ select_end: generateColumnNames(pParse, pTabList, pEList); } - sqlite3_free(sAggInfo.aCol); - sqlite3_free(sAggInfo.aFunc); + sqlite3DbFree(db, sAggInfo.aCol); + sqlite3DbFree(db, sAggInfo.aFunc); return rc; } |