output of javap command

2.4k views Asked by At

I inspected my class file using javap command, I am unable to understand the below part

Classfile /D:/WaitNotifyExample.class

Last modified Dec 20, 2013; size 622 bytes
MD5 checksum 4781f8cf8062fa75efa30c76adc25cfb
 Compiled from "WaitNotifyExample.java"
 public class WaitNotifyExample
   SourceFile: "WaitNotifyExample.java"
minor version: 0
 major version: 51
flags: ACC_PUBLIC, ACC_SUPER

Constant pool:
#1 = Methodref          #12.#24        //  java/lang/Object."<init>":()V
 #2 = Class              #25            //  java/lang/String
 #3 = String             #26            //  I am hidden
 #4 = Methodref          #2.#27         //  java/lang/String."<init>":    
(Ljava/lang/String;)V
  #5 = Fieldref           #11.#28        //  WaitNotifyExample.s1:Ljava/lang/String;
 #6 = String             #29            //  I am diving into Pool
  #7 = Fieldref           #11.#30        //  WaitNotifyExample.s2:Ljava/lang/String;
  #8 = Fieldref           #31.#32        //  java/lang/System.out:Ljava/io/PrintStream;
  #9 = String             #33            //  hello World
 #10 = Methodref          #34.#35        //  java/io/PrintStream.println:  
(Ljava/lang/String;)V
 #11 = Class              #36            //  WaitNotifyExample
  #12 = Class              #37            //  java/lang/Object
#13 = Utf8               s1
#14 = Utf8               Ljava/lang/String;
#15 = Utf8               s2
#16 = Utf8               <init>
#17 = Utf8               ()V
 #18 = Utf8               Code
#19 = Utf8               LineNumberTable
#20 = Utf8               main
#21 = Utf8               ([Ljava/lang/String;)V
#22 = Utf8               SourceFile
#23 = Utf8               WaitNotifyExample.java
#24 = NameAndType        #16:#17        //  "<init>":()V
#25 = Utf8               java/lang/String
#26 = Utf8               I am hidden
#27 = NameAndType        #16:#38        //  "<init>":(Ljava/lang/String;)V
#28 = NameAndType        #13:#14        //  s1:Ljava/lang/String;
#29 = Utf8               I am diving into Pool
#30 = NameAndType        #15:#14        //  s2:Ljava/lang/String;
#31 = Class              #39            //  java/lang/System
#32 = NameAndType        #40:#41        //  out:Ljava/io/PrintStream;
#33 = Utf8               hello World
#34 = Class              #42            //  java/io/PrintStream
#35 = NameAndType        #43:#38        //  println:(Ljava/lang/String;)V
#36 = Utf8               WaitNotifyExample
#37 = Utf8               java/lang/Object
#38 = Utf8               (Ljava/lang/String;)V
#39 = Utf8               java/lang/System
#40 = Utf8               out
#41 = Utf8               Ljava/io/PrintStream;
#42 = Utf8               java/io/PrintStream
#43 = Utf8               println  

 {

 public java.lang.String s1;
flags: ACC_PUBLIC


 public java.lang.String s2;
flags: ACC_PUBLIC


  public WaitNotifyExample();
flags: ACC_PUBLIC

Code:
  stack=4, locals=1, args_size=1
     0: aload_0       
     1: invokespecial #1                  // Method java/lang/Object."<init>":()V
     4: aload_0       
     5: new           #2                  // class java/lang/String
     8: dup           
     9: ldc           #3                  // String I am hidden
    11: invokespecial #4                  // Method java/lang/String."<init>":(Ljava/lang/String;)V
    14: putfield      #5                  // Field s1:Ljava/lang/String;
    17: aload_0       
    18: new           #2                  // class java/lang/String
    21: dup           
    22: ldc           #6                  // String I am diving into Pool
    24: invokespecial #4                  // Method java/lang/String."<init>":(Ljava/lang/String;)V
    27: putfield      #7                  // Field s2:Ljava/lang/String;
    30: return        
  LineNumberTable:
    line 2: 0
    line 4: 4
    line 5: 17

  public static void main(java.lang.String[]);
flags: ACC_PUBLIC, ACC_STATIC

Code:
  stack=2, locals=2, args_size=1
     0: iconst_0      
     1: istore_1      
     2: getstatic     #8                  // Field java/lang/System.out:Ljava/io/PrintStream;
     5: ldc           #9                  // String hello World
     7: invokevirtual #10                 // Method java/io/PrintStream.println:(Ljava/lang/String;)V
    10: return        
  LineNumberTable:
    line 7: 0
    line 8: 2
    line 9: 10
}

Edit: below is the corresponding java code.

 public class WaitNotifyExample {

public String s1 = new String("I am hidden");
public String s2 = new String("I am diving into Pool");

public static void main(String[] args) {
    int mainLiteral = 0;
    System.out.println("hello World");
}

}

I do not understand the following things from the above class file:

  1. stack=4, locals=1, args_size=1
  2. LineNumberTable: section
3

There are 3 answers

0
aryann On

What is it that you are not getting? Its byte codes. If you understand byte codes then you would easily understand what the output is saying. javap 'de-assembles' the code and not decompiles it. So what this is saying is that you have a WaitNOtifyExample constructor, a main method and two public string references. Within those method and constructor definitions follows the byte codes of these and it describes what these two items are doing (in byte codes).

0
Sujith PS On
  Code:
      stack=2, locals=2, args_size=1
  • Stack Refers , how deep a stack is required for execution of the method,
  • arg_size Refers , how many parameters it takes in,
  • locals Refers , how many local variable slots need to be reserved in the local variables table.

And

 LineNumberTable: section

The LineNumberTable is one of the optional attributes that holds metadata for debugging purposes. It specifies which offsets in the bytecode correspond to each line in the original source code. This is useful for printing more informative stack traces and for providing features like single step in the debugger.

For more details about these two , Refer this.

You can refer Wikipedia for instruction set listing. And refer this for more details.

0
Antimony On

stack=4, locals=1, args_size=1

Values in bytecode are stored in local variable slots and on the operand stack. Each can have up to 2^16 - 1 slots, but for efficiency reasons, you are required to specify a limit on the stack and locals so that it won't waste all that space if you aren't actually using it.

In compiled code, the compiler will automatically calculate this as the minimum that's actually used in the function. In this case, it is using 4 slots in the operand stack and 1 slot in the local variable table. I am not sure what arg_size is, but I am guessing this is just the total size of parameters (i.e. the number of arguments). At any rate, this doesn't correspond to any feature of the classfile format, so whatever it is, javap is calculating and inserting it manually.

LineNumberTable: section

The LineNumberTable is one of the optional attributes that holds metadata for debugging purposes. In this case, it specifies which offsets in the bytecode correspond to each line in the original source code. This is useful for printing more informative stack traces and for providing features like single step in the debugger.