为什么64位JVM比32位JVM更快?

最近我一直在对我公司的数据库产品的写入性能进行一些基准测试,我发现只需切换到64位JVM就可以实现20-30%的一致性能提升。

我不允许详细介绍我们的产品,但基本上它是一个面向列的数据库,针对存储日志进行了优化。 该基准测试涉及为其提供几千兆字节的原始日志,并计算分析它们并将其作为结构化数据存储在数据库中所需的时间。 CPU和I / O的处理非常繁重,但很难说它的比例是多少。

关于设置的一些注意事项:

Processor: Xeon E5640 2.66GHz (4 core) x 2 RAM: 24GB Disk: 7200rpm, no RAID OS: RHEL 6 64bit Filesystem: Ext4 JVMs: 1.6.0_21 (32bit), 1.6.0_23 (64bit) Max heap size (-Xmx): 512 MB (for both 32bit and 64bit JVMs) 

两个JVM的常量:

  • 相同的操作系统(64位RHEL)
  • 相同的硬件(64位CPU)
  • 最大堆大小固定为512 MB(因此速度增加不是由于64位JVM使用更大的堆)

为简单起见,我已经关闭了产品中的所有multithreading选项,因此几乎所有处理都以单线程方式进行。 (当我打开multithreading时,当然系统变得更快,但32位和64位性能之间的比率保持不变。)

所以,我的问题是……为什么我在使用64位JVM时会看到20-30%的速度提升? 以前有人见过类似的结果吗?

直到现在我的直觉如下:

  • 64位指针更大,因此L1和L2缓存更容易溢出,因此64位JVM上的性能更差。

  • JVM使用一些花哨的指针压缩技巧来尽可能地缓解上述问题。 Sun网站上的详细信息。

  • 在64位模式下运行时,允许JVM使用更多寄存器,这会略微提高速度。

鉴于以上三点,我预计64位性能会稍微慢一点,或大约等于32位JVM。

有任何想法吗? 提前致谢。

编辑:澄清了有关基准环境的一些观点。

不知道你的硬件,我只是采取一些疯狂的刺

  • 您的特定CPU可能正在使用微代码来“模拟”某些x86指令 – 最值得注意的是x87 ISA
  • x64使用sse数学而不是x87数学,我注意到在这种情况下,一些数学繁重的C ++应用程序加速了10%~20%。 如果你使用strictfp数学差异可能是真正的杀手。
  • 记忆。 64位为您提供更多的地址空间。 也许GC在64位模式下不那么激进,因为你有额外的RAM。
  • 您的操作系统是否处于64b模式并通过某个包装实用程序运行32b jvm?

来自: http : //www.oracle.com/technetwork/java/hotspotfaq-138619.html#64bit_performance

“通常,能够处理大量内存的好处是64位虚拟机的性能损失小,而在32位虚拟机上运行相同的应用程序。这是因为系统中的每个本机指针都是如此。这个额外数据的加载会对内存使用产生影响,这会导致执行速度稍慢,这取决于在执行Java程序期间加载了多少指针。好消息是使用AMD64和EM64T在64位模式下运行的平台上,Java VM可以使用一些额外的寄存器来生成更高效的本机指令序列。这些额外的寄存器可以将性能提高到在比较32到64时通常没有性能损失的程度。位执行速度。
当您迁移到64位VM时,将64位平台上运行的应用程序与SPARC上的32位平台相比,性能差异大约为10-20%。 在AMD64和EM64T平台上,这种差异范围为0-15%,具体取决于访问应用程序的指针数量。“

64位指令集还有8个寄存器,这样可以使代码整体更快。

但是,由于现在的处理器大多等待内存或磁盘,我认为内存子系统或磁盘i / o在64位模式下可能更有效。

基于快速谷歌的32位与64位性能图表,我的最佳猜测是64位I / O效率更高。 我想你做了很多I / O ……

如果在移动数据时涉及memcpy,则复制long而不是整数可能更有效。

意识到64位JVM不是神奇的小精灵,它使Java应用程序变得更快。 64位JVM允许堆>> 4 GB,因此,仅对可以利用具有它的系统上的大量内存的应用程序有意义。

通常,存在轻微改进(由于某些平台上的某些硬件优化)或轻微降级(由于指针大小增加)。 一般来说,需要更少的GC – 但是当它们确实发生时,它们可能会更长。

在内存数据库或搜索引擎中,可以使用增加的内存来缓存对象,从而避免IPC或磁盘访问,这将看到最大的应用程序级别改进。 此外,64位JVM还允许您运行比32位更多的线程,因为线程堆栈等内容的地址空间更多。一般32位JVM的最大线程数是~100但是~100000个线程与64位JVM。

但有一些缺点:
64位JVM的其他问题是不支持某些面向客户端的function,如Java Plug-in和Java Web Start。 此外,任何本机代码也需要兼容(例如,类型II JDBC驱动程序的JNI)。 这对于纯Java开发人员来说是一个额外的好处,因为纯粹的应用程序应该是开箱即用的。

更多关于Java.net上的这个主题