Java 12: javac crash with switch expression containing try-catch-finally

Jan Lahoda jan.lahoda at oracle.com
Thu Mar 21 17:24:32 UTC 2019


Hi Bernard,

I was peeking at this, and expected to start to work on this.

I do agree we will need to strip the extra values from the stack, but we 
may also need to set the letExprStackPos at some point.

Jan

On 21.3.2019 16:37, B. Blaser wrote:
> Hi,
>
> On Wed, 20 Mar 2019 at 05:11, Tagir Valeev <amaembo at gmail.com> wrote:
>>
>> Hello!
>>
>> I just wanted to draw your attention to the issue JDK-8220018. I
>> reported it several weeks ago, but saw no reaction. Probably I failed
>> to fill all the necessary fields. The problem is still actual in java
>> 12 GA:
>>
>> // SwTest.java
>> public class SwTest {
>>      public static void main(String[] args) {
>>          System.out.println(switch (0) {
>>             default -> {
>>                 try {
>>                     break 1;
>>                 }
>>                 catch (Exception ex) {
>>                     break 2;
>>                 }
>>                 finally {
>>                     break 3;
>>                 }
>>             }
>>          });
>>      }
>> }
>
> Is somebody already looking at this?
>
> This is an interesting issue because when generating the final 'break
> 3', an operand stack size mismatch occurs due to the other already
> emitted breaks.
> I tried the following tweak to pop the unnecessary operands before
> generating the last break, does this look reasonable (langtools:tier1
> being OK)?
>
> Thanks,
> Bernard
>
> diff --git a/src/jdk.compiler/share/classes/com/sun/tools/javac/jvm/Code.java
> b/src/jdk.compiler/share/classes/com/sun/tools/javac/jvm/Code.java
> --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/jvm/Code.java
> +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/jvm/Code.java
> @@ -1223,6 +1223,15 @@
>           return !alive || state.stacksize == letExprStackPos;
>       }
>
> +    public void makeStatementStart() {
> +        if (state.stacksize > letExprStackPos) {
> +            int toPop = state.stacksize - letExprStackPos;
> +            for (int i=0; i<toPop; i++) {
> +                emitop0(pop);
> +            }
> +        }
> +    }
> +
>   /**************************************************************************
>    * Stack map generation
>    *************************************************************************/
> diff --git a/src/jdk.compiler/share/classes/com/sun/tools/javac/jvm/Gen.java
> b/src/jdk.compiler/share/classes/com/sun/tools/javac/jvm/Gen.java
> --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/jvm/Gen.java
> +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/jvm/Gen.java
> @@ -1704,7 +1704,7 @@
>       }
>
>       public void visitBreak(JCBreak tree) {
> -        Assert.check(code.isStatementStart());
> +        code.makeStatementStart();
>           final Env<GenContext> targetEnv;
>           if (tree.isValueBreak()) {
>               //restore stack as it was before the switch expression:
>


More information about the compiler-dev mailing list