diff options
author | drh <drh@noemail.net> | 2012-12-07 21:02:47 +0000 |
---|---|---|
committer | drh <drh@noemail.net> | 2012-12-07 21:02:47 +0000 |
commit | bd13d34b08ddc66a079f671bcbe96127b41da957 (patch) | |
tree | 771997d58c4d8ad8cdf79c82be16987e0f20fe7e /src/resolve.c | |
parent | 7a66da1395eefb5368b7f72439cccf25c4531537 (diff) | |
download | sqlite-bd13d34b08ddc66a079f671bcbe96127b41da957.tar.gz sqlite-bd13d34b08ddc66a079f671bcbe96127b41da957.zip |
Fix the processing of ORDER BY clauses with COLLATE terms on compound
queries. 52 veryquick test failures remain.
FossilOrigin-Name: 49654453ad157693414c1f86fa3afa0918acffd4
Diffstat (limited to 'src/resolve.c')
-rw-r--r-- | src/resolve.c | 22 |
1 files changed, 17 insertions, 5 deletions
diff --git a/src/resolve.c b/src/resolve.c index 6e5e2e7a9..4b9d8fa14 100644 --- a/src/resolve.c +++ b/src/resolve.c @@ -129,6 +129,9 @@ static void resolveAlias( /* Before calling sqlite3ExprDelete(), set the EP_Static flag. This ** prevents ExprDelete() from deleting the Expr structure itself, ** allowing it to be repopulated by the memcpy() on the following line. + ** The pExpr->u.zToken might point into memory that will be freed by the + ** sqlite3DbFree(db, pDup) on the last line of this block, so be sure to + ** make a copy of the token before doing the sqlite3DbFree(). */ ExprSetProperty(pExpr, EP_Static); sqlite3ExprDelete(db, pExpr); @@ -824,7 +827,7 @@ static int resolveCompoundOrderBy( int iCol = -1; Expr *pE, *pDup; if( pItem->done ) continue; - pE = pItem->pExpr; + pE = sqlite3ExprSkipCollate(pItem->pExpr); if( sqlite3ExprIsInteger(pE, &iCol) ){ if( iCol<=0 || iCol>pEList->nExpr ){ resolveOutOfRangeError(pParse, "ORDER", i+1, pEList->nExpr); @@ -842,11 +845,20 @@ static int resolveCompoundOrderBy( } } if( iCol>0 ){ + /* Convert the ORDER BY term into an integer column number iCol, + ** taking care to preserve the COLLATE clause if it exists */ + Expr *pNew = sqlite3Expr(db, TK_INTEGER, 0); + if( pNew==0 ) return 1; + pNew->flags |= EP_IntValue; + pNew->u.iValue = iCol; + if( pItem->pExpr==pE ){ + pItem->pExpr = pNew; + }else{ + assert( pItem->pExpr->op==TK_COLLATE ); + assert( pItem->pExpr->pLeft==pE ); + pItem->pExpr->pLeft = pNew; + } sqlite3ExprDelete(db, pE); - pItem->pExpr = pE = sqlite3Expr(db, TK_INTEGER, 0); - if( pE==0 ) return 1; - pE->flags |= EP_IntValue; - pE->u.iValue = iCol; pItem->iOrderByCol = (u16)iCol; pItem->done = 1; }else{ |