diff options
author | dan <dan@noemail.net> | 2019-03-28 16:15:05 +0000 |
---|---|---|
committer | dan <dan@noemail.net> | 2019-03-28 16:15:05 +0000 |
commit | 4ded26a53c4df312e9fd06facbbf70377e969983 (patch) | |
tree | 7588d33692e04f5f0c7dcb72199b0cc9b98a2422 /src/resolve.c | |
parent | 6f1644c0f963c8d1d7388d6e52f60a6604aae2c1 (diff) | |
download | sqlite-4ded26a53c4df312e9fd06facbbf70377e969983.tar.gz sqlite-4ded26a53c4df312e9fd06facbbf70377e969983.zip |
Prevent aliases of window functions expressions from being used as arguments to aggregate or other window functions.
FossilOrigin-Name: 1e16d3e8fc60d39ca3899759ff15d355fdd7d3e23b325d8d2b0f954e11ce8dce
Diffstat (limited to 'src/resolve.c')
-rw-r--r-- | src/resolve.c | 21 |
1 files changed, 16 insertions, 5 deletions
diff --git a/src/resolve.c b/src/resolve.c index 2644e069f..eb9e137fd 100644 --- a/src/resolve.c +++ b/src/resolve.c @@ -435,6 +435,10 @@ static int lookupName( sqlite3ErrorMsg(pParse, "misuse of aliased aggregate %s", zAs); return WRC_Abort; } + if( (pNC->ncFlags&NC_AllowWin)==0 && ExprHasProperty(pOrig, EP_Win) ){ + sqlite3ErrorMsg(pParse, "misuse of aliased window function %s",zAs); + return WRC_Abort; + } if( sqlite3ExprVectorSize(pOrig)!=1 ){ sqlite3ErrorMsg(pParse, "row value misused"); return WRC_Abort; @@ -725,6 +729,7 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ const char *zId; /* The function name. */ FuncDef *pDef; /* Information about the function */ u8 enc = ENC(pParse->db); /* The database encoding */ + int savedAllowFlags = (pNC->ncFlags & (NC_AllowAgg | NC_AllowWin)); assert( !ExprHasProperty(pExpr, EP_xIsSelect) ); zId = pExpr->u.zToken; @@ -846,8 +851,11 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ pNC->nErr++; } if( is_agg ){ + /* Window functions may not be arguments of aggregate functions. + ** Or arguments of other window functions. But aggregate functions + ** may be arguments for window functions. */ #ifndef SQLITE_OMIT_WINDOWFUNC - pNC->ncFlags &= ~(pExpr->y.pWin ? NC_AllowWin : NC_AllowAgg); + pNC->ncFlags &= ~(NC_AllowWin | (!pExpr->y.pWin ? NC_AllowAgg : 0)); #else pNC->ncFlags &= ~NC_AllowAgg; #endif @@ -868,7 +876,7 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ pExpr->y.pWin->pNextWin = pSel->pWin; pSel->pWin = pExpr->y.pWin; } - pNC->ncFlags |= NC_AllowWin; + pNC->ncFlags |= NC_HasWin; }else #endif /* SQLITE_OMIT_WINDOWFUNC */ { @@ -886,8 +894,8 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ pNC2->ncFlags |= NC_HasAgg | (pDef->funcFlags & SQLITE_FUNC_MINMAX); } - pNC->ncFlags |= NC_AllowAgg; } + pNC->ncFlags |= savedAllowFlags; } /* FIX ME: Compute pExpr->affinity based on the expected return ** type of the function @@ -1648,8 +1656,8 @@ int sqlite3ResolveExprNames( Walker w; if( pExpr==0 ) return SQLITE_OK; - savedHasAgg = pNC->ncFlags & (NC_HasAgg|NC_MinMaxAgg); - pNC->ncFlags &= ~(NC_HasAgg|NC_MinMaxAgg); + savedHasAgg = pNC->ncFlags & (NC_HasAgg|NC_MinMaxAgg|NC_HasWin); + pNC->ncFlags &= ~(NC_HasAgg|NC_MinMaxAgg|NC_HasWin); w.pParse = pNC->pParse; w.xExprCallback = resolveExprStep; w.xSelectCallback = resolveSelectStep; @@ -1668,6 +1676,9 @@ int sqlite3ResolveExprNames( if( pNC->ncFlags & NC_HasAgg ){ ExprSetProperty(pExpr, EP_Agg); } + if( pNC->ncFlags & NC_HasWin ){ + ExprSetProperty(pExpr, EP_Win); + } pNC->ncFlags |= savedHasAgg; return pNC->nErr>0 || w.pParse->nErr>0; } |