文章目录

  • 简介
  • JDK8和JDK14中的PrintAssembly
  • JDK8中使用Assembly
  • JDK14中的Assembly
  • 在JMH中使用Assembly
  • 总结

简介

上篇文章和小师妹一起介绍了PrintAssembly和PrintAssembly在命令行的使用,今天本文将会更进一步讲解如何在JDK8和JDK14中分别使用PrintAssembly,并在实际的例子中对其进行进一步的深入理解。

JDK8和JDK14中的PrintAssembly

小师妹:F师兄,上次你介绍的PrintAssembly的自测命令,怎么在JDK14中不好用呢?

java -XX:+UnlockDiagnosticVMOptions -XX:+PrintAssembly -version

有什么不好用的,命令不是正常打出来了吗?

小师妹:F师兄,你看下我运行的结果,机器码下面展示的怎么是448b 5608这样的数字呀,不应该是assembly language吗?

嗯…小师妹的话让我陷入了深深的思考,究竟是什么导致了这样的反常的结果呢?是道德的沦丧还是人性的扭曲?

于是我翻遍了baidu,哦,不对是google,还是没有找到结果。

难点是JDK14有bug?还是JDK14已经使用了另外的Assembly的实现?

有问题就解决问题,我们先从JDK8开始,来探索一下最原始的PrintAssembly的使用。

更多精彩内容且看:

  • 区块链从入门到放弃系列教程-涵盖密码学,超级账本,以太坊,Libra,比特币等持续更新
  • Spring Boot 2.X系列教程:七天从无到有掌握Spring Boot-持续更新
  • Spring 5.X系列教程:满足你对Spring5的一切想象-持续更新
  • java程序员从小工到专家成神之路(2020版)-持续更新中,附详细文章教程

JDK8中使用Assembly

在JDK8中如果我们运行Assembly的测试命令,可以得到下面的结果:

java -XX:+UnlockDiagnosticVMOptions -XX:+PrintAssembly -versionJava HotSpot(TM) 64-Bit Server VM warning: PrintAssembly is enabled; turning on DebugNonSafepoints to gain additional output
Could not load hsdis-amd64.dylib; library not loadable; PrintAssembly is disabled
java version "1.8.0_171"
Java(TM) SE Runtime Environment (build 1.8.0_171-b11)
Java HotSpot(TM) 64-Bit Server VM (build 25.171-b11, mixed mode)

这个故事告诉我们,虽然PrintAssembly开关打开了,但是系统不支持,缺少了hsdis-amd64.dylib文件。

这个hsdis是一个反汇编的工具,我们需要hsdis的支持才能在JDK8中使用Assembly。

我是mac系统,下面是在mac系统怎么安装hsdis:

hg clone http://hg.openjdk.java.net/jdk8u/jdk8ucd jdk8u/hotspot/src/share/tools/hsdis/wget http://ftp.heanet.ie/mirrors/ftp.gnu.org/gnu/binutils/binutils-2.30.tar.gztar -xzf binutils-2.30.tar.gzmake BINUTILS=binutils-2.30 ARCH=amd64#java8
sudo cp build/macosx-amd64/hsdis-amd64.dylib /Library/Java/JavaVirtualMachines/jdk1.8.0_181.jdk/Contents/Home/jre/lib/server/#java9 onwards
sudo cp build/macosx-amd64/hsdis-amd64.dylib /Library/Java/JavaVirtualMachines/jdk-9.0.4.jdk/Contents/Home/lib/server/

如果你是linux或者windows系统,请自行探索hsdis的安装方法。

按照步骤先把java8的hsdis-amd64.dylib安装好。

然后再次运行测试命令:

完美,汇编语言出现了。

JDK14中的Assembly

然后我想到,如果把这个dylib文件拷贝到JDK14相应的目录下面,运行一次会怎么样呢?

大家注意,JDK9之后,使用了模块化,所以之前的目录结构发生了比较大的变化,大家参考上面我列出的地址。

再次运行测试代码:

大家看到,Assembly又出现了,真的是让我热内盈亏。

其实最开始的时候,我发现JDK14中Assembly没能正常显示的时候,我也有想过拷贝一个hsdis-amd64.dylib过来试试,但是一看还需要下载JDK的代码,重新编译,就打起了退堂鼓。

吃一堑,长一智,下次遇到问题千万不能走捷径。抄近路害死人呀!

在JMH中使用Assembly

Assembly主要是为了进行代码调优或者理解JVM的运行原理来使用的。

这里我们举一个在JMH中使用Assembly的例子:

@Warmup(iterations = 2, time = 1, timeUnit = TimeUnit.SECONDS)
@Measurement(iterations = 2, time = 1, timeUnit = TimeUnit.SECONDS)
@Fork(value = 1,jvmArgsPrepend = {"-XX:+UnlockDiagnosticVMOptions","-XX:CompileCommand=print,com.flydean.PrintAssemblyUsage::testPrintAssembly"
}
)
@State(Scope.Benchmark)
@BenchmarkMode(Mode.AverageTime)
@OutputTimeUnit(TimeUnit.NANOSECONDS)
public class PrintAssemblyUsage {int x;@Benchmark@CompilerControl(CompilerControl.Mode.DONT_INLINE)public void testPrintAssembly() {for (int c = 0; c < 1000; c++) {synchronized (this) {x += 0xFF;}}}public static void main(String[] args) throws RunnerException {Options opt = new OptionsBuilder().include(PrintAssemblyUsage.class.getSimpleName()).build();new Runner(opt).run();}
}

上面的例子中,我们使用了-XX:CompileCommand指定要打印的方法,而不是输出所有的Assembly,方便我们查看和分析结果。

总结

本文介绍了JDK8和JDK14中,怎么开启PrintAssembly。并举了一个在JMH中使用的例子。

那么有人会问了,在JMH中使用Assembly到底有什么意义呢?别急,我们在后面深入JVM的本质中,马上就要讲到,敬请期待。

本文作者:flydean程序那些事

本文链接:http://www.flydean.com/jvm-jit-printassembly-2/

本文来源:flydean的博客

欢迎关注我的公众号:程序那些事,更多精彩等着您!

小师妹学JVM之:JIT中的PrintAssembly续集相关推荐

  1. 小师妹学JVM之:JIT中的PrintAssembly

    文章目录 简介 使用PrintAssembly 输出过滤 总结 简介 想不想了解JVM最最底层的运行机制?想不想从本质上理解java代码的执行过程?想不想对你的代码进行进一步的优化和性能提升? 如果你 ...

  2. 小师妹学JVM之:JIT中的PrintCompilation

    文章目录 简介 PrintCompilation 分析PrintCompilation的结果 总结 简介 上篇文章我们讲到了JIT中的LogCompilation,将编译的日志都收集起来,存到日志文件 ...

  3. 小师妹学JVM之:JIT中的LogCompilation

    文章目录 简介 LogCompilation简介 LogCompilation的使用 解析LogCompilation文件 总结 简介 我们知道在JVM中为了加快编译速度,引入了JIT即时编译的功能. ...

  4. 小师妹学JVM之:JDK14中JVM的性能优化

    文章目录 简介 String压缩 分层编译(Tiered Compilation) Code Cache分层 新的JIT编译器Graal 前置编译 压缩对象指针 Zero-Based 压缩指针 Esc ...

  5. 小师妹学JVM之:JVM中的Safepoints

    文章目录 简介 GC的垃圾回收器 分代回收器中的问题 safepoints safepoint一般用在什么地方 总结 简介 java程序员都听说过GC,大家也都知道GC的目的是扫描堆空间,然后将那些标 ...

  6. 小师妹学JVM之:深入理解JIT和编译优化-你看不懂系列

    文章目录 简介 JIT编译器 Tiered Compilation分层编译 OSR(On-Stack Replacement) Deoptimization 常见的编译优化举例 Inlining内联 ...

  7. 小师妹学JVM之:cache line对代码性能的影响

    文章目录 简介 一个奇怪的现象 两个问题的答案 CPU cache line inc 和 add 总结 简介 读万卷书不如行万里路,讲了这么多assembly和JVM的原理与优化,今天我们来点不一样的 ...

  8. 小师妹学JVM之:JVM的架构和执行过程

    文章目录 简介 JVM是一种标准 java程序的执行顺序 JVM的架构 类加载系统 运行时数据区域 执行引擎 总结 简介 JVM也叫Java Virtual Machine,它是java程序运行的基础 ...

  9. 小师妹学JVM之:Dirty cards和PLAB

    文章目录 简介 分代收集器中的空间划分 Write barrier和Dirty cards PLAB old space分配对象 总结 简介 分代垃圾回收器在进行minor GC的时候会发生什么操作呢 ...

最新文章

  1. YARN-2.7.3-源码分析系列2:启动脚本原理的分析
  2. HDU4635(强连通分量+Kosaraju算法)
  3. Linux下的inode记录
  4. mysql删除默认密码_修改mysql默认密码方法
  5. 电脑运行adb闪退_adb命令调试工具
  6. 理解 Glance - 每天5分钟玩转 OpenStack(20)
  7. 北妈每日一题:到底谁养了我的鱼!
  8. vue 原型设计 拖拽_设计即开发,如何打通软件研发的“任督二脉”?
  9. dllimport 找不到指定的模块_Python语法基础(15)模块与包
  10. 中国节能电梯市场趋势报告、技术动态创新及市场预测
  11. python pos函数_从0入门Python — 4. 函数
  12. 黑马程序员java整套视频地址 javaweb+ssh+ssm视频+源码+软件
  13. 单片微型计算机原理及应用pdf,《单片微型计算机原理、应用及接口技术》.pdf...
  14. mybatis的缓存,看这一篇就够了!
  15. [C#学习教程-委托]001.大道至简之委托(代理),匿名函数,Lambda表达式
  16. android bitmap转nv21(YUV420SP)
  17. 【JokerのZYNQ7020】SDK程序从QSPI启动。
  18. 用Bootstrap框架制作下拉列表
  19. 马斯克:特斯拉刚成为一家真正的汽车公司
  20. 浏览器HTTP缓存策略

热门文章

  1. 剑指Offer-LeetCode刷题
  2. python实战-pdf文件转txt
  3. pg 定时删除_PostgreSQL的时间函数使用整理
  4. 求n!,C(n,m)和A(n,m)最后的非零位。
  5. C++ 智能指针 :内存泄漏、 RAII、智能指针、auto_ptr、unique_ptr、shared_ptr、weak_ptr、定制删除器deleter
  6. Python 移动文件夹所有的文件到另外一个文件夹,重复的跳过
  7. Idea单测执行报错“Command line is too long“ 解决办法
  8. 冷静对待你遇到的所有Java内存异常
  9. Auto packing the repository in background for optimum performance.
  10. 大厂「offer 收割机」修炼记