当一个java文件被javac编译之后,就可以成为一个通用的class文件格式。我们之前说JVM里面的运行期常量池,主要也就是说的从classFile中读取的常量信息。作为JVM来说,它并没有对类,接口,实例等有一个内部的数据结构,所有的指令的引用信息均来自于常量池中。
Java Virtual Machine instructions do not rely on the run-time layout of classes, interfaces, class instances, or arrays. Instead, instructions refer to symbolic information in the constant_pool table.
本文自:http://docs.oracle.com/javase/specs/jvms/se7/html/jvms-4.html 4.4节
这里,我们有一个很简单的HelloWorld例子,如下所示:
public class T { public static void main(String args[]) { String s = "abcdefghijk"; System.out.println(s); } }
采用指令:javac -g:none T.java进行编译。编译之后产生的class如下所示:
Offset 0 1 2 3 4 5 6 7 8 9 A B C D E F 00000000 CA FE BA BE 00 00 00 33 00 1A 0A 00 06 00 0C 08 3 00000010 00 0D 09 00 0E 00 0F 0A 00 10 00 11 07 00 12 07 00000020 00 13 01 00 06 3C 69 6E 69 74 3E 01 00 03 28 29 <init> () 00000030 56 01 00 04 43 6F 64 65 01 00 04 6D 61 69 6E 01 V Code main 00000040 00 16 28 5B 4C 6A 61 76 61 2F 6C 61 6E 67 2F 53 ([Ljava/lang/S 00000050 74 72 69 6E 67 3B 29 56 0C 00 07 00 08 01 00 0B tring;)V 00000060 61 62 63 64 65 66 67 68 69 6A 6B 07 00 14 0C 00 abcdefghijk 00000070 15 00 16 07 00 17 0C 00 18 00 19 01 00 01 54 01 T 00000080 00 10 6A 61 76 61 2F 6C 61 6E 67 2F 4F 62 6A 65 java/lang/Obje 00000090 63 74 01 00 10 6A 61 76 61 2F 6C 61 6E 67 2F 53 ct java/lang/S 000000A0 79 73 74 65 6D 01 00 03 6F 75 74 01 00 15 4C 6A ystem out Lj 000000B0 61 76 61 2F 69 6F 2F 50 72 69 6E 74 53 74 72 65 ava/io/PrintStre 000000C0 61 6D 3B 01 00 13 6A 61 76 61 2F 69 6F 2F 50 72 am; java/io/Pr 000000D0 69 6E 74 53 74 72 65 61 6D 01 00 07 70 72 69 6E intStream prin 000000E0 74 6C 6E 01 00 15 28 4C 6A 61 76 61 2F 6C 61 6E tln (Ljava/lan 000000F0 67 2F 53 74 72 69 6E 67 3B 29 56 00 21 00 05 00 g/String;)V ! 00000100 06 00 00 00 00 00 02 00 01 00 07 00 08 00 01 00 00000110 09 00 00 00 11 00 01 00 01 00 00 00 05 2A B7 00 *? 00000120 01 B1 00 00 00 00 00 09 00 0A 00 0B 00 01 00 09 ? 00000130 00 00 00 17 00 02 00 02 00 00 00 0B 12 02 4C B2 L? 00000140 00 03 2B B6 00 04 B1 00 00 00 00 00 00 +? ?
本文是描述如何从这个classFile中详细的找出相应的常量池信息,从文件本身描述的信息中手动地找出相应的内部结构,以方便进一步掌握class的结构形式,以方便了解JVM规范及组织。