RFR: JDK-8222795: post inc operator inside compute function of HashMap results in Exception
Vicente Romero
vicente.romero at oracle.com
Mon May 13 22:07:55 UTC 2019
ping,
Thanks,
Vicente
On 5/8/19 6:25 PM, Vicente Romero wrote:
> Please review fix for regression [1] at [2]. The regression was
> introduced by [3] which introduced the support for switch expressions.
> The compiler is failing with an assertion error for code:
>
> import java.util.HashMap;
> import java.util.Map;
>
> public class LetExpressionAssertionTest {
> void m() {
> Map<String, Integer> m = new HashMap<>();
> m.put("a",2);
> m.compute("a", (k, v) -> (v > 5) ? v-- : v++);
> }
> }
>
> Where `v--` and `v++` are converted to let expressions. Recall that in
> this case `v` is of type integer so the let expressions are similar to:
>
> `(let /*synthetic*/ final Integer $373182087 = v in (let v =
> Integer.valueOf((int)(v.intValue() - 1)); in $373182087))`
>
> notice the cast, the ::intValue invocation etc.
>
> This patch, [3], also made some changes related to let expressions. In
> particular it changed a common idiom in Gen:
>
> `Assert.check(code.state.stacksize == 0);` by:
> Assert.check(code.isStatementStart());
>
> where Code::isStatementStart is:
> public boolean isStatementStart() {
> return !alive ||state.stacksize ==letExprStackPos;
> }
> which is basically the same check as before, modulo the `alive` check.
> The problem is that at Gen::visitVarDef we had a more relaxed
> assertion check before [3]:
>
> Assert.check(letExprDepth != 0 || code.state.stacksize == 0); which
> was also substituted by:
> Assert.check(code.isStatementStart());
>
> this implies a semantic change. In the old code `letExprDepth` was
> just a counter of "nestedness" of let expressions and the original
> condition in Gen::visitVarDef was mostly to check if the compiler was
> generating a let expression or not. Enforcing that
> code.state.stacksize has to be equal to the stack position of the let
> expression when we started generating the let expression, which is
> what the current assertion is checking is a too strong condition.
> Which can be false if, as in this case, the let expression has several
> method invocations inside, etc that will move the stack as get
> generated. This patch is proposing going back to a more relaxed
> assertion at Gen::visitVarDef,
>
> Thanks,
> Vicente
>
> [1] https://bugs.openjdk.java.net/browse/JDK-8222795
> [2] http://cr.openjdk.java.net/~vromero/8222795/webrev.00/
> [3] https://bugs.openjdk.java.net/browse/JDK-8206986
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://mail.openjdk.java.net/pipermail/compiler-dev/attachments/20190513/1846e413/attachment.html>
More information about the compiler-dev
mailing list