JVM虛擬機棧解析

虛擬機棧

Java虛擬機以方法作爲最基本的執行單元,“棧幀”(Stack Frame)則是用於支持虛擬機進行方法調用和方法執行背後的數據結構,它也是虛擬機運行時數據區中的虛擬機棧(VirtualMachine Stack)的棧元素

棧幀

棧幀的概念結構

局部變量表

  • 局部變量表(Local Variables Table)是一組變量值的存儲空間,用於存放方法參數和方法內部定義的局部變量
  • 局部變量表的容量以變量槽(Variable Slot)爲最小單位
  • Java中佔用不超過32位存儲空間的數據類型有boolean、byte、char、short、int、float、reference和returnAddress這8種類型,這8中類型佔用一個槽(Slot)
    long和double是64位的數據類型,java虛擬機會以高位對齊的方式爲其分配兩個連續的變量槽空間
  • 由於局部變量表是建立在線程堆棧中,屬於線程私有的數據,無論讀寫兩個連續的變量槽是否爲原子操作,都不會引起數據競爭和線程安全問題
  • Java虛擬機通過索引定位的方式使用局部變量表,索引值的範圍是從0開始至局部變量表最大的變量槽數量
    當一個方法被調用時,Java虛擬機會使用局部變量表來完成參數值到參數變量列表的傳遞過程,即實參到形參的傳遞
    如果執行的是實例方法(沒有被static修飾的方法),那局部變量表中第0位索引的變量槽默認是用於傳遞方法所屬對象實例的引用,在方法中可以通過關鍵字“this”來訪問到這個隱含的參數。其餘參數則按照參數表順序排列,佔用從1開始的局部變量槽,參數表分配完畢後,再根據方法體內部定義的變量順序和作用域分配其餘的變量槽

操作數棧

當一個方法剛剛開始執行的時候,這個方法的操作數棧是空的,在方法的執行過程中,會有各種字節碼指令往操作數棧中寫入和提取內容,也就是出棧和入棧操作
棧幀質檢的數據共享

動態連接

Class文件的常量池中存在大量的符號引用,字節碼中的方法調用指令就以常量池裏指向方法的符號引用作爲參數

  • 部分符號引用在類加載階段(解析)的時候就轉化爲直接引用,這種轉化爲靜態鏈接
  • 部分符號引用在運行期間轉化爲直接引用,這種轉化爲動態鏈接
方法解析:
  • invokestatic 用於調用靜態方法
  • invokespecial 用於調用實例構造器()方法、私有方法和父類中的方法
  • invokevirtual 用於調用所有的虛方法
  • invokeinterface 用於調用接口方法,會在運行時再確定一個實現該接口的對象
  1. 虛方法:
    在運行期間將符號引用轉化爲直接引用的方法被稱之爲虛方法,即動態鏈接
  2. 非虛方法:
    只要能被invokestatic和invokespecial指令調用的方法,都可以在解析階段中確定唯一的調用版本
    靜態方法、私有方法、實例構造器、父類方法、final修飾的方法(儘管它使用invokevirtual指令調用),這5中方法在類加載階段解析時解析爲直接引用,即靜態鏈接

方法返回地址

當一個方法開始執行後,只有兩種方式退出這個方法

  • 正常調用完成
  • 異常調用完成
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章