Thanks for the reviews, Attila and Marcus.
I've moved the providesScopeCreator method to Block which is much nicer
indeed. Link to new webrev below.
http://cr.openjdk.java.net/~hannesw/8151810/webrev.01/
I removed the es6 check since it's redundant. It was meant as a
shortcut, but checking for a synthetic block with a block-scoped for-in
seems good enough.
Hannes
Am 2016-03-21 um 15:47 schrieb Attila Szegedi:
Just a minor thing: consider if it’d make sense to move most of
CodeGenerator.providesScopeCreator it’d into a method on the Block (all parts
of the expression except for _es6 env check). Looking at
CodeGenerator.providesScopeCreator it’s doing an awful lot of “block.” this and
“block.” that.
Other than that, +1.
Attila.
On Mar 21, 2016, at 10:23 AM, Hannes Wallnoefer <hannes.wallnoe...@oracle.com>
wrote:
Please review JDK-8151810: for-in iteration does not provide per-iteration
scope.
http://cr.openjdk.java.net/~hannesw/8151810/webrev/
This issue popped up while I was implementing ES6 for-of statement. It turns
out that like for-of, the ES5 for-in statement needs a per-iteration scope when
used with a lexical declaration which I oversaw in my initial implementation of
ES6 block scope.
With normal for-statement this is pretty straightforward, because the spec says
that values from the previous iteration are reused in the next iteration, which
means that a const is actually a single const through all iterations of the
loop. This means that we can simply clone the existing per-iteration scope at
the end of the loop, which is what we do.
However, with for-in/of per iteration scopes are independent of each other. Therefore,
something like "for (const a of [1, 2, 3]) {...}" actually gets a new const for
each iteration. Now we could fake it and use a cloned scope and reset the const using
some magic, but doing that caused all kinds of problems (weird interaction with const
declaration logic and temporal dead zone detection, unstable scope maps etc).
So the solution I came up with is that the block that provides the scope for
for-in statements (which is a synthetic block/block statement) registers its
scope creator in case it has one. The for-node can then reuse the scope creator
to create an object with the exact same property map and uninitialized
consts/lets.
Hannes