[jboss-jira] [JBoss JIRA] (JASSIST-207) Inconsistent Stack Map when inserting throw Expression with Java 7

Scott Marlow (JIRA) jira-events at lists.jboss.org
Wed Jul 24 16:18:26 EDT 2013


    [ https://issues.jboss.org/browse/JASSIST-207?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=12792788#comment-12792788 ] 

Scott Marlow commented on JASSIST-207:
--------------------------------------

>From section "4.9 Constraints on Java Virtual Machine code"
{quote}
The index operand of each iload, fload, aload, istore, fstore, astore, iinc, and ret instruction must be a non-negative integer no greater than max_locals - 1. 
{quote}

When we insert the unconditional "throw Exception", we later build the StackMapTable with a max_locals that eliminates the now dead code, below the the "throw Exception".  However, the dead code is still validated to have correct "local variable" references.  

When the standard Javac compiler sees dead code, it throws an "unreachable code" (see [so|http://stackoverflow.com/questions/3795585/why-does-java-have-an-unreachable-statement-compiler-error] discussion for some complaints about that).

I'm not sure how yet (I'm still learning/stepping throw related internals), but I think the fix is to also include local variables from dead code blocks.
                
> Inconsistent Stack Map when inserting throw Expression with Java 7
> ------------------------------------------------------------------
>
>                 Key: JASSIST-207
>                 URL: https://issues.jboss.org/browse/JASSIST-207
>             Project: Javassist
>          Issue Type: Bug
>    Affects Versions: 3.18.0-GA
>            Reporter: Ben Romberg
>            Assignee: Scott Marlow
>            Priority: Critical
>         Attachments: afterInsertThrowExpression.txt, beforeInsertThrowExpression.txt, conditionalThrowExceptionInserted.txt
>
>
> I wrote a unit-test for javassist, reproducing the issue:
> {code}
> public class ThrowExpressionCorruptsStackMapTableTest extends JvstTestRoot {
> 	public ThrowExpressionCorruptsStackMapTableTest(String name) {
> 		super(name);
> 	}
> 	public void testInsertLocalVars() throws Exception {
> 		CtClass cc = sloader.get("test4.LocalVars");
> 		CtMethod m1 = cc.getDeclaredMethod("run");
> 		m1.insertBefore("throw new AssertionError((Object) \"assertion error\");");
> 		cc.writeFile();
> 		Object obj = make(cc.getName());
> 		assertEquals(10, invoke(obj, "run"));
> 	}
> }
> {code}
> Throws:
> java.lang.VerifyError: Expecting a stack map frame in method test4.LocalVars.run()I at offset 45
> My use-case is almost the same, inserting a "throw AssertionError(...)" expression with insertBefore. However, I get a slightly different error message:
> Stack map does not match the one at exception handler 37 in method timeofday.TimeOfDay.getSecond()I at offset 27

--
This message is automatically generated by JIRA.
If you think it was sent incorrectly, please contact your JIRA administrators
For more information on JIRA, see: http://www.atlassian.com/software/jira


More information about the jboss-jira mailing list