棧幀(Stack Frame)是用于支援虛拟機進行方法調用和方法執行的資料結構,它是虛拟機運作時資料區中的虛拟機棧的棧元素。每一個棧幀都包括了局部變量表、操作數棧、動态連接配接、方法傳回位址和一些額外的附加資訊。在編譯程式代碼的時候,棧幀中需要多大的局部變量表、多深的操作數棧都已經完全确定了,并且寫入到方法表的 Code 屬性之中。
局部變量表
局部變量表是一組變量值存儲空間,用于存放方法參數和方法内部定義的局部變量。方法 Code 屬性的 max_locals 資料項确定了該方法所需要配置設定的最大局部變量表的容量。
局部變量不存在“準備”階段,如果一個局部變量定義了但沒有賦初始值是沒法使用的。
賦 null 值的操作在經過虛拟機 JIT 編譯器優化之後會被消除掉。
操作數棧
操作數棧是一個後入先出(LIFO)棧,當一個方法剛剛開始執行的時候,這個方法的操作數棧是空的,在方法的執行過程中,會有各種位元組碼指令向操作數棧中寫入和提取内容,也就是入棧和出棧操作。方法 Code 屬性的 max_stacks 資料項設定了操作數棧的最大深度。
動态連接配接
Class 檔案常量池中指向方法的符号引用中會有一部分在運作期間轉化為直接引用,這部分稱為動态連接配接。
與動态連接配接相對應的是靜态連接配接。靜态方法、私有方法、執行個體構造器、父類方法和 final 方法統稱為虛方法,虛方法的調用沒有其他版本,無須對方法接收者進行多态選擇,是以它們在類加載的解析階段就會把涉及到的符号引用全部轉變為可确定的直接引用,不會延遲到運作期才去完成。而有些方法,比如重載和重寫方法,具有多個版本,無法直接确定調用的是什麼版本,這部分符号引用的轉換就必須等到運作期來完成。
方法傳回位址
方法傳回位址指的是方法退出後的傳回位址。一般來說,方法正常退出時,調用者的 PC 計數器的值就可以作為傳回位址,棧幀中很可能會儲存這個計數器值。而方法異常退出時,傳回位址是要通過異常處理器來确定的,棧幀中一般不會儲存這部分資訊。
附加資訊
附加資訊指的是在虛拟機實作中加入了一些規範裡沒有描述的資訊到棧幀之中,例如與調試相關的資訊。