HotSpot虛擬機之字節碼執行引擎

目錄

一、棧幀

1. 棧幀結構

2.?基于棧的解釋執行過程

二、方法調用

1. 方法調用指令

2. 分派

三、動態類型語言

四、參考資料


一、棧幀

1. 棧幀結構

????????棧幀是Java虛擬機棧進行方法調用和執行的數據結構,是方法最基本的執行單元,是棧的元素。一個棧幀分配多大內存,則不受運行期影響,由程序源碼和占內存布局決定(內存大小編譯期可知)。每一個方法的調用開始和結束,都對應JVM棧的元素(棧幀)的入棧和出棧。

????????處于Java虛擬機棧頂的棧幀,稱為“當前棧幀”;當前棧幀所關聯的方法,稱為“當前方法”。從Java程序層面看,同一時刻、同一線程里,棧的所有方法都處于執行狀態;從執行引擎層面看,只有處于棧頂的方法才是執行狀態。

? ? ? ? 棧幀的結構包含:局部變量表、操作數棧、動態連接、返回地址、附加信息,如下表所示。注意:方法調用時,用局部變量表完成參數值到參數變量列表的傳遞過程,即:實參到形參的傳遞

棧幀結構

作用

特點

局部變量表

(Local?Variables?Table)

變量值的存儲空間

1.存儲:方法參數及方法定義的局部變量

2.局部變量表容量以變量槽(slot)為最小單位;

3.方法Code屬性max_locals決定最大容量(slot數量)

4.每個slot都能存儲boolean、byte、char、short、int、float、returnAddress類型的數據;

5.64位JVM時,只有long、double會以高位對齊的方式分配兩個連續的slot空間

6.實例方法時,第0位slot是this參數;其他:方法參數、方法局部變量的順序

7.slot被回收重用的根本原因:slot中是否還存有對象的引用或值

操作數棧

(Operand?Stack)

操作數據的棧

1.JVM解釋執行引擎稱為“基于棧的操作引擎”;

2.棧的最大深度由編譯器Code屬性的max_stacks決定

3.字節碼指令往棧中寫入和讀取操作數,即:操作數的入棧和出棧;

4.棧中元素數據類型與字節碼指令的類型必須嚴格匹配

5.模型中JVM棧的元素(棧幀)是相互獨立的,但是JVM實際優化時,可能會有重疊區域。

動態連接

(Dynamic?Linking)

棧幀所屬方法的引用

1.每個棧幀都包含一個指向常量池該棧幀所屬方法的引用(反過來,字節碼的方法調用以常量池的符號引用作為參數)

2.靜態解析:編譯器符號引用轉直接引用;

??動態連接:每次運行時符號引用轉直接引用。

返回地址

(Return?Address)

返回給方法調用者

1.兩種方式退出當前方法:

??“正常調用完成”:執行引擎遇到方法的返回指令;

??“異常調用完成”:當前方法的異常表中沒有搜索到匹配的異常,則異常退出(不會有任何返回值)

2.方法正常退出時,一般主調方法的PC計數值可作為返回地址,若有返回值則壓入主調方法的棧幀中

附加信息

其他信息

如調試、性能收集相關的信息

????????其中,reference數據類型的作用: ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?

  • 根據直接引用或間接引用查找到堆中實例對象的起始地址或索引; ??
  • 根據直接引用或間接引用查找到元空間(方法區)的類型信息(反射機制獲取Class信息);?

2.?基于棧的解釋執行過程

????????指令集架構分類如下,Java是基于棧的指令集架構

  • 基于棧的指令集架構:字節碼指令流大部分都是零地址指令,依賴操作數棧工作,其優點:可移植; ??
  • 基于寄存器的指令集架構:依賴于寄存器來訪問和存儲數據,如:主流PC機(x86二地址指令集)

????????執行字節碼有兩種選擇(或兩著兼備):解釋執行(解釋器)、編譯執行(即時編譯產生本地機器代碼),下面是基于棧的解釋執行過程實例、源碼和class文件如下。指令含義參考《HotSpot虛擬機之Class文件及字節碼指令》。

public int calc() {int a = 100;int b = 100;int c = 100;return (a + b) * c;
}
  public int calc();descriptor: ()Iflags: ACC_PUBLICCode:stack=2, locals=4, args_size=10: bipush        1002: istore_13: bipush        1005: istore_26: bipush        1008: istore_39: iload_110: iload_211: iadd12: iload_313: imul14: ireturnLineNumberTable:line 29: 0line 30: 3line 31: 6line 32: 9LocalVariableTable:Start  Length  Slot  Name   Signature0      15     0  this   Lcom/cmmon/instance/classLoad/NotInitialization;3      12     1     a   I6       9     2     b   I9       6     3     c   I

二、方法調用

1. 方法調用指令

????????方法調用階段唯一目的是確定被調用方法的版本,即:調用哪個方法,其指令有5種:invokestatic、invokespecial、invokevirtual、invokeinterface、invokedynamic,如下表所示。

方法調用指令

特點

invokestatic

作用:調用靜態方法;

invokespecial

作用:調用實例構造器<init>()方法、私有方法、父類中的方法

invokevirtual

1.作用:調用所有的虛方法;

2.該指令:動態分派實現方法復寫

invokeinterface

作用:調用接口方法,運行時確定一個實現該接口的方法

invokedynamic

1.作用:動態調用方法;

2.運行時動態解析動態解析調用點限定符所引用的方法,再去執行;

注意:

???a.invokestatic、invokespecial、invokevirtual、invokeinterface其分派邏輯固化在JVM內部;而invokedynamic分派邏輯由用戶設定的引導方法來決定

???b.只要能被invokestatic、invokespecial調用的方法,在編譯器可以確定方法版本,如:靜態、實例構造器<init>()、私有、父類、final修飾的方法;

???c.final修飾的方法雖然用invokevirtual調用,但它是非虛方法。

????????invokevirtual指令不僅把常量池的方法符號引用解析為直接引用,同時根據方法接收者的實際類型來選擇方法版本。invokevirtual指令解析過程,如下步驟:

  • step1:找到操作數棧頂元素指向的對象的實際類型C;
  • step2:類型C中查找與當前常量池匹配的方法時,且訪問權限校驗,通過則返回該方法,查找結束;否則拋出異常:java.lang.IllegalAccessError;
  • step3:否則,從下往上的繼承關系對C的父類,進行搜索和驗證;
  • step4:否則,沒有查找到匹配的方法,拋出異常:java.lang.AbstractMethodError。

2. 分派

????????分派揭示Java多態性的實現,即:如重載、重寫是如何實現。其分類:靜態分派、動態分派或是單分派、多分派,如下表所示。

分派分類

概念

應用

特點

靜態分派

所有依賴靜態類型來決定方法版本的分派動作

方法重載

1.靜態分派發生在編譯期

2.重載版本多個時,選擇最合適的順序:自動類型轉換、自動裝箱、裝箱實現接口、父類(從下往上)、可變參數方法

動態分派

運行期根據實際類型來決定方法版本的分派動作

方法重寫

1.動態分派發生在運行期

2.由invokevirtual指令實現。

注意:

???a.只有方法有多態,而字段永遠不參與多態;

???b.變量的“靜態類型”和“實際類型”:(都可能變化,但是變化時期不同)

? ? ? 靜態類型:變化在使用時發生,且變量本身的類型不會改變,且最終在編譯期可知;

? ? ? 實際類型:變化結果在運行期確定,編譯期不知道一個對象的實際類型是什么

???c.類型“寬化轉換”:chart?>?int?>?long?>?float?>?double(不會匹配byte、short類型);

???d.“方法的宗量”:方法接收者、方法的參數

? ? ? ?分派:根據一個宗量對目標方法進行選擇;

? ? ? ?分派:根據多于一個宗量對目標方法進行選擇。

? ? ? ? 注意:方法重寫的本質是不僅把常量池的方法符號引用解析為直接引用,同時根據方法接收者的實際類型來選擇方法版本;字段不參與多態,但子類聲明與父類的相同的字段時,子類內存中兩個字段都會存在,但子類會遮蔽父類的同名字段

? ? ? ? 方法重寫實現多態,在運行時頻繁從元數據進行查找,解決該問題的方法:invokevirtual的虛方法表;invokeinterface的接口方法表。虛方法表目的是存儲該類各個方法的實際入口地址,如下所示其特點。

三、動態類型語言

????????JDK7增加了動態類型指令invokedynamic,其類型檢查的主過程在運行期,而不是編譯期

四、參考資料

HotSpot虛擬機之Class文件及字節碼指令_愛我所愛0505的博客-CSDN博客

HotSpot虛擬機之類加載過程及類加載器_愛我所愛0505的博客-CSDN博客

百度安全驗證

【Java 虛擬機原理】棧幀 | 動態鏈接 | 方法區 | 字節碼文件二進制分析-騰訊云開發者社區-騰訊云

Java虛擬機運行時棧幀結構_java棧幀_愛躺平的咸魚的博客-CSDN博客

【Java -- 虛擬器】方法分派模型 -- 靜態分派、動態分派_51CTO博客_java虛擬器

Java中的靜態分派和動態分派原理_51CTO博客_靜態分派

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/38686.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/38686.shtml
英文地址,請注明出處:http://en.pswp.cn/news/38686.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

【環境配置】Windows10終端和VSCode下能夠直接打開Anaconda-Prompt

很多小伙伴在 Windows 下做深度學習開發的時候&#xff0c;遇到終端沒有在 Linux 那么方便&#xff0c;那么我們現在就可以來設置一下&#xff1b;這樣我們也可以在文件夾內部右鍵打開終端&#xff0c;也可以在 VS Code 里面新建一個虛擬環境的控制臺&#xff1b;這里主要是針對…

佛祖保佑,永不宕機,永無bug

當我們的程序編譯通過&#xff0c;能預防的bug也都預防了&#xff0c;其它的就只能交給天意了。當然請求佛祖的保佑也是必不可少的。 下面是一些常用的保佑圖&#xff1a; 佛祖保佑圖 ——————————————————————————————————————————…

【c語言】動態內存管理(超詳細)

他治愈了身邊所有人&#xff0c;唯獨沒有治愈他自己—超脫 csdn上的朋友你們好呀&#xff01;&#xff01;今天給大家分享的是動態內存管理 &#x1f440;為什么存在動態內存分配 我們定義的局部變量在棧區創建 int n 4;//在棧上開辟4個字節大小int arr[10] { 0 };//在棧上開…

Android Socket使用TCP協議實現手機投屏

本節主要通過實戰來了解Socket在TCP/IP協議中充當的是一個什么角色&#xff0c;有什么作用。通過Socket使用TCP協議實現局域網內手機A充當服務端&#xff0c;手機B充當客戶端&#xff0c;手機B連接手機A&#xff0c;手機A獲取屏幕數據轉化為Bitmap&#xff0c;通過Socket傳遞個…

Excel設置某列或者某行不某行不可以編輯,只讀屬性

設置單元格只讀的三種方式: 1、通過單元格只讀按鈕&#xff0c;設置為只為 設置行或者列的只讀屬性&#xff0c;可以設置整行或者整列只讀 2、設置單元格編輯控件為標簽控件(標簽控件不可編輯) 3、通過鎖定行&#xff0c;鎖定行的修改。鎖定的行與只讀行的區別在于鎖定的行不…

電子商務環境下旅游價值鏈

邁克爾 ? 波特(Michael E. Porter)在其《競爭優勢》一書中提出了“價值鏈” 的概念&#xff0c;并認為一家企業最核心的競爭優勢在于對價值鏈的設計。雖然邁克爾 ? 波 特提出的價值鏈主要是針對企業內部的價值鏈&#xff0c;但他視價值鏈為一系列連續完成的 活動&#xff…

openGauss學習筆記-40 openGauss 高級數據管理-鎖

文章目錄 openGauss學習筆記-40 openGauss 高級數據管理-鎖40.1 語法格式40.2 參數說明40.3 示例 openGauss學習筆記-40 openGauss 高級數據管理-鎖 如果需要保持數據庫數據的一致性&#xff0c;可以使用LOCK TABLE來阻止其他用戶修改表。 例如&#xff0c;一個應用需要保證表…

GPT垂直領域相關模型 現有的開源領域大模型

對于ToC端來說&#xff0c;廣大群眾的口味已經被ChatGPT給養叼了&#xff0c;市場基本上被ChatGPT吃的干干凈凈。雖然國內大廠在緊追不舍&#xff0c;但目前絕大多數都還在實行內測機制&#xff0c;大概率是不會廣泛開放的&#xff08;畢竟&#xff0c;各大廠還是主盯ToB、ToG市…

C/C++ 注意點補充

C/C 注意點補充 函數缺省 函數缺省 https://blog.csdn.net/xinger_28/article/details/83898804 // 是的&#xff0c;C語言中的函數不支持直接定義缺省參數。在你提供的代碼中&#xff0c;函數DelayXms沒有定義缺省參數。缺省參數只在一些高級編程語言中&#xff08;如C&…

flutter

1.dart語言學習 dart在線編輯器 //第一段dart代碼 void main() {ceshi c new ceshi(1,2);print(c.right);c.right 2;print(c.right);print(c.bottom);c.bottom 4;print(c.bottom); }class ceshi {num left, top;ceshi(this.left, this.top);num get right > left top;…

視頻集中存儲安防監控平臺EasyCVR優化AI硬件接入時的通道顯示異常問題

安防視頻監控平臺視頻集中存儲EasyCVR可拓展性強、視頻能力靈活、部署輕快&#xff0c;可支持的主流標準協議有國標GB28181、RTSP/Onvif、RTMP等&#xff0c;以及支持廠家私有協議與SDK接入&#xff0c;包括海康Ehome、海大宇等設備的SDK等。 安防監控視頻云存儲平臺EasyCVR既具…

【Python國內源】pip換源終極方法【Windows】

1、為什么要pip換源下載 安裝第三方庫時&#xff0c;很多庫來自于國外&#xff0c;下載速度慢得感人&#xff01; 2、常見的國內源 https://pypi.tuna.tsinghua.edu.cn/simple #清華 http://mirrors.aliyun.com/pypi/simple/ #阿里云 https://pypi.mirrors.ustc.e…

go_細節注意

go細節 一、使用指針接受者和不使用指針接受者1&#xff0c;不使用指針接受者&#xff1a;2&#xff0c;使用指針接受者3&#xff0c;區別與優劣勢 一、使用指針接受者和不使用指針接受者 1&#xff0c;不使用指針接受者&#xff1a; func (d dog) move() {fmt.Println("…

使用Logstash將數據從MySQL同步至Elasticsearch(有坑)

文章目錄 一、準備工作1、安裝elasticSearchkibana2、安裝MySQL3、安裝Logstash 二、全量同步1、準備MySQL數據與表2、上傳mysql-connector-java.jar3、啟動Logstash4、修改logstash.conf文件5、修改full_jdbc.sql文件6、打開Kibana創建索引和映射7、重啟logstash進行全量同步8…

TCP/IP協議追層分析物理層(第三十九課)

TCP/IP協議追層分析物理層(第三十九課) 1 物理層:建立、維護、斷開物理連接,定義了接口及介質,實現了比特流的傳輸。 1、傳輸介質分類 有線介質:網線(雙絞線)、光纖 無線介質:無線電 微波 激光 紅外線 2、雙絞線分類: 五類cat5: 適用于100Mbps 超五類cat5e:適用于…

Qt掃盲- Graphics View框架理論綜述

Graphics View框架理論綜述 一、概述二、Graphics View 體系結構1. The Scene2. The View3. 圖元 Item 三、圖形視圖坐標系統1. 圖元Item的坐標2. Scene Scene坐標3. View 視圖坐標4. 坐標映射 四、關鍵特性1. 縮放和旋轉2. 打印3. 拖放4. 鼠標指針和 提示5. 動畫6. OpenGL渲染…

【100天精通python】Day35:一文掌握GUI界面編程基本操作

目錄 專欄導讀 1 GUI 編程概述 1.1 為什么需要GUI&#xff1f; 1.2 常見的GUI編程工具和庫 1.3 GUI應用程序的組成和架構 2 使用Tkinter 庫 進行GUI編程 2.1 使用Tkinter庫進行GUI編程的基本流程 2.2 使用Tkinter庫進行GUI編程 2.2.1 導入Tkinter庫 2.2.2 添加標簽和…

繪制世界地圖or中國地圖

寫在前面 在8月初,自己需要使用中國地圖的圖形,自己就此也查詢相關的教程,自己也做一下小小總結,希望對自己和同學們有所幫助。 最終圖形 這個系列從2022年開始,一直更新使用R語言分析數據及繪制精美圖形。小杜的生信筆記主要分享小杜學習日常!如果,你對此感興趣可以加…

Flutter Engine編譯環境安裝

前言 根據設置引擎開發環境的描述&#xff0c;確保有以下可用依賴項&#xff1a; Linux、macOS 或 Windows。 Linux 支持 Android 和 Fuchsia 的交叉編譯工件&#xff0c;但不支持 iOS。macOS 支持 Android 和 iOS 的交叉編譯工件。Windows 不支持任何 Android、Fuchsia 或 i…

MySQL存儲結構及索引

文章目錄 MySQL結構1.2存儲引擎介紹1.3存儲引擎特點InnoDB邏輯存儲結構 MyISAMMemory區別及特點存儲引擎選擇 索引索引概述索引結構BTreeHash索引分類聚集索引&二級索引索引語法SQL性能分析索引優化最左前綴法則范圍查詢字符串不加引號模糊查詢or連接條件數據分布影響覆蓋索…