Re: Nested CASE-WHEN scoping

From: Heikki Linnakangas <heikki(dot)linnakangas(at)enterprisedb(dot)com>
To: Tom Lane <tgl(at)sss(dot)pgh(dot)pa(dot)us>
Cc: PostgreSQL-development <pgsql-hackers(at)postgresql(dot)org>
Subject: Re: Nested CASE-WHEN scoping
Date: 2011-06-03 19:46:16
Message-ID: 4DE93A08.90309@enterprisedb.com
Views: Raw Message | Whole Thread | Download mbox | Resend email
Thread:
Lists: pgsql-hackers

On 31.05.2011 19:10, Heikki Linnakangas wrote:
> For index expressions, we could use a function similar to
> ChangeVarNodes(), that shifts all the paramids in the already-planned
> expression, preparing it for inclusion within the enclosing plan. I'm a
> bit worried that that might screw up the logic used to compare if an
> expression matches the index expression, though; the param ids in the
> two expressions won't match.

Yeah, the expression comparison logic gets all confused by this :-(. I
couldn't figure out a way to make it work without making the comparison
a whole lot more complicated than it is today. I'm going back to my
original thoughts of a new kind of node to replace CaseTestExpr, which
allows referencing values from upper levels in the expression tree.

So, here's a WIP patch using that approach. I've replaced CaseTestExpr
with ExpressionParam. ExpressionParam has a levelsup field, which is
similar to varlevelsup in Var. With levelsup == 0, ExpressionParam works
just like CaseTestExpr did. With levelsup == 1, it refers to the value
from above the enclosing CaseExpr (or any other node that uses these
ExpressionParams/CaseTestExprs).

The complicated part is to ensure that levelsup is always set correctly.
At parse time, levelsup is always set to 0, as the syntax doesn't allow
referencing upper levels directly. When an SQL function is inlined, any
ExpressionParams in the expressions that are substituted for Params need
to have their levelsup adjusted, so that it still refers to the right
value if there's CASE expressions in the inlined function. Also, when an
ExpressionParam is replaced with a Const, the levelsup fields of any
other ExpressionParams within the CaseExpr referring to higher levels
need to have their levelsup decremented to account for the fact that the
CaseExpr doesn't push the expression parameter anymore.

At execution time, the expression parameters form a stack. We've always
done the save-restore logic, but the stack is now represented explicitly
as a List in ExprContext. When an ExpressionParam is evaluated, the nth
element is fetched from the stack, corresponding to levelsup.

--
Heikki Linnakangas
EnterpriseDB http://www.enterprisedb.com

Attachment Content-Type Size
replace-casetestexpr-with-expressionparams-2.patch text/x-diff 54.2 KB

In response to

Responses

Browse pgsql-hackers by date

  From Date Subject
Next Message Kevin Grittner 2011-06-03 19:57:51 Re: Domains versus polymorphic functions, redux
Previous Message Tom Lane 2011-06-03 19:46:15 Re: SIREAD lock versus ACCESS EXCLUSIVE lock