1. 程式人生 > >小師妹學JVM之:JIT中的LogCompilation

小師妹學JVM之:JIT中的LogCompilation

[toc] # 簡介 我們知道在JVM中為了加快編譯速度,引入了JIT即時編譯的功能。那麼JIT什麼時候開始編譯的,又是怎麼編譯的,作為一個高傲的程式設計師,有沒有辦法去探究JIT編譯的祕密呢?答案是有的,今天和小師妹一起帶大家來看一看這個編譯背後的祕密。 更多精彩內容且看: * [區塊鏈從入門到放棄系列教程-涵蓋密碼學,超級賬本,以太坊,Libra,比特幣等持續更新](http://www.flydean.com/blockchain/) * [Spring Boot 2.X系列教程:七天從無到有掌握Spring Boot-持續更新](http://www.flydean.com/learn-spring-boot/) * [Spring 5.X系列教程:滿足你對Spring5的一切想象-持續更新](http://www.flydean.com/spring5/) * [java程式設計師從小工到專家成神之路(2020版)-持續更新中,附詳細文章教程](http://www.flydean.com/java-roadmap-2020/) # LogCompilation簡介 小師妹:F師兄,JIT這麼神器,但是好像就是一個黑盒子,有沒有辦法可以探尋到其內部的本質呢? 追求真理和探索精神是我們作為程式設計師的最大優點,想想如果沒有玻爾關於原子結構的新理論,怎麼會有原子體系的突破,如果沒有海森堡的矩陣力學,怎麼會有量子力學的建立? JIT的編譯日誌輸出很簡單,使用 -XX:+LogCompilation就夠了。 如果要把日誌重定向到一個日誌檔案中,則可以使用-XX:LogFile= 。 但是要開啟這些分析的功能,又需要使用-XX:+UnlockDiagnosticVMOptions。 所以總結一下,我們需要這樣使用: ~~~java -XX:+UnlockDiagnosticVMOptions -XX:+LogCompilation -XX:LogFile=www.flydean.com.log ~~~ # LogCompilation的使用 根據上面的介紹,我們現場來生成一個JIT的編譯日誌,為了體現出專業性,這裡我們需要使用到JMH來做效能測試。 JMH的全稱是Java Microbenchmark Harness,是一個open JDK中用來做效能測試的套件。該套件已經被包含在了JDK 12中。 如果你使用的不是JDK 12,那麼需要新增如下依賴: ~~~xml ~~~ 更多詳情可以參考我之前寫的: 在java中使用JMH(Java Microbenchmark Harness)做效能測試一文。 之前有的朋友說,程式碼也用圖片,看起來好看,從本文之後,我們會盡量把程式碼也轉成圖片來展示: ![](https://img-blog.csdnimg.cn/20200529101342389.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_0,text_aHR0cDovL3d3dy5mbHlkZWFuLmNvbQ==,size_35,color_8F8F8F,t_70) 看完我的JMH的介紹,上面的例子應該很清楚了,主要就是做一個累加操作,然後warmup 5輪,測試5輪。 在@Fork註解裡面,我們可以配置jvm的引數,為什麼我註釋掉了呢?因為我發現在jvmArgsPrepend中的-XX:LogFile是不生效的。 沒辦法,我只好在執行配置中新增: ![](https://img-blog.csdnimg.cn/20200529101742580.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_0,text_aHR0cDovL3d3dy5mbHlkZWFuLmNvbQ==,size_35,color_8F8F8F,t_70) 執行之後,你就可以得到輸出的編譯日誌檔案。 # 解析LogCompilation檔案 小師妹:F師兄,我看了一下生成的檔案好複雜啊,用肉眼能看得明白嗎? 別怕,只是內容的多一點,如果我們細細再細細的分析一下,你會發現其實它真的非常非常......複雜! 其實寫點簡單的小白文不好嗎?為什麼要來分析這麼複雜,又沒人看,看了也沒人懂的JVM底層..... 大概,這就是專業吧! LogCompilation檔案其實是xml格式的,我們現在來大概分析一下,它的結構,讓大家下次看到這個檔案也能夠大概瞭解它的重點。 ![](https://img-blog.csdnimg.cn/20200529222302406.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_0,text_aHR0cDovL3d3dy5mbHlkZWFuLmNvbQ==,size_35,color_8F8F8F,t_70) 首先最基本的資訊就是JVM的資訊,包括JVM的版本,JVM執行的引數,還有一些properties屬性。 我們收集到的日誌其實是分兩類的,第一類是應用程式本身的的編譯日誌,第二類就是編譯執行緒自己內部產生的日誌。 第二類的日誌會以hs_c*.log的格式儲存,然後在JVM退出的時候,再將這些檔案跟最終的日誌輸出檔案合併,生成一個整體的日誌檔案。 比如下面的兩個就是編譯執行緒內部的日誌: ~~~java