Skip to content

Wrong debug line number in the body of a CaseDef #15535

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
adpi2 opened this issue Jun 27, 2022 · 0 comments · Fixed by #15783
Closed

Wrong debug line number in the body of a CaseDef #15535

adpi2 opened this issue Jun 27, 2022 · 0 comments · Fixed by #15783

Comments

@adpi2
Copy link
Member

adpi2 commented Jun 27, 2022

Compiler version

3.1.3 and also 2.13.8

Minimized code

package example

object Main {
  def m(x: Int): Unit = {
    x match {
      case y =>
        println(y) // breakpoint here, line 7
        println(y)
    }
  }
  
  def main(args: Array[String]): Unit = {
    m(1)
  }
}

Output

The program pauses on line 7 but the local variable y is not defined.

image

Expectation

The local variable y should be defined

Details

An incorrect line number table

The result of decompiling m from its class file is:

  public void m(int);
    Code:
       0: iload_1
       1: istore_2
       2: iload_2
       3: istore_3
       4: getstatic     #33                 // Field scala/Predef$.MODULE$:Lscala/Predef$;
       7: iload_3
       8: invokestatic  #39                 // Method scala/runtime/BoxesRunTime.boxToInteger:(I)Ljava/lang/Integer;
      11: invokevirtual #43                 // Method scala/Predef$.println:(Ljava/lang/Object;)V
      14: getstatic     #33                 // Field scala/Predef$.MODULE$:Lscala/Predef$;
      17: iload_3
      18: invokestatic  #39                 // Method scala/runtime/BoxesRunTime.boxToInteger:(I)Ljava/lang/Integer;
      21: invokevirtual #43                 // Method scala/Predef$.println:(Ljava/lang/Object;)V
      24: goto          27
      27: return
    LineNumberTable:
      line 4: 0
      line 5: 0
      line 7: 2
      line 8: 14
    LocalVariableTable:
      Start  Length  Slot  Name   Signature
          4      23     3     y   I
          0      28     0  this   Lexample/Main$;
          0      28     1     x   I

Here the line number 7 is associated with byte code 2 which is too early, the local variable y on slot 3 has not yet been initialized.

I believe the line number 7 should be associated with the byte code 4.

A correct line number table

If the body of the case contains only one instruction, then the debug line number table is correct:

def m(x: Int): Unit = {
  x match {
    case y =>
      println(y)
  }
}
  public void m(int);
    Code:
       0: iload_1
       1: istore_2
       2: iload_2
       3: istore_3
       4: getstatic     #33                 // Field scala/Predef$.MODULE$:Lscala/Predef$;
       7: iload_3
       8: invokestatic  #39                 // Method scala/runtime/BoxesRunTime.boxToInteger:(I)Ljava/lang/Integer;
      11: invokevirtual #43                 // Method scala/Predef$.println:(Ljava/lang/Object;)V
      14: goto          17
      17: return
    LineNumberTable:
      line 4: 0
      line 5: 0
      line 6: 2
      line 7: 4
    LocalVariableTable:
      Start  Length  Slot  Name   Signature
          4      13     3     y   I
          0      18     0  this   Lexample/Main$;
          0      18     1     x   I

@adpi2 adpi2 added itype:bug stat:needs triage Every issue needs to have an "area" and "itype" label labels Jun 27, 2022
@dwijnand dwijnand added area:pattern-matching and removed stat:needs triage Every issue needs to have an "area" and "itype" label labels Jun 27, 2022
@Florian3k Florian3k self-assigned this Jul 27, 2022
@Kordyjan Kordyjan added this to the 3.2.1 milestone Aug 1, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants