引:好像是在大四的时候,自己按照《深入理解Java虚拟机》去编译JDK没有成功!但是在最近经历一些面试之后,感到JVM绝对是面试的一块重点,而看源码绝对是你深入理解JVM的一个很重要的点!在看源码,就需要调试,那么编译自己JDK越是必然的。这次我们在Mac下去编译OpenJDK9!!!
4.24看完复联4,脑子太多的点化为爱你三千遍!
进入今天的正题!!!
准备
关于编译JDK,其实在官方的源码包下有个帮助文件(openjdk/common/building.html/md)。这个文件会告诉我们在编译JDK之前需要做的准备以及编译的步骤。具体的大家可以仔细阅读看看。下次只讲述自己这次所编译的过程!
我们需要准备一些东西,首先你需要准备 homebrew,homwbrew是mac下的包管理器,如果你的mac上没有安装,可以按照下面的方式来安装:1
/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"
homwbrew下载完成之后,接下来准备编译环境:
- 安装openjdk的版本管理工具mercurial(hg)
- 安装ccache和freetype,ccache用来加速编译,freetype在编译过程也会依赖到
安装脚本为:1
2
3brew install mercurial
brew install ccache
brew install freetype
准备好之后就可以开始具体的操作了!
下载源码
官方推荐hg
hg:Mercurial source code management system
我为源码专门创建了一个目录 ~/jvm
,然后运行下面的命令:1
2cd ~/jvm
hg clone http://hg.openjdk.java.net/jdk9/jdk9 jdk9
这条命令运行之后,openjdk的源码并没有下载下来,我们随后进入到~/jvm/jdk9
目录,会发现有一个 get_source.sh
的文件,调用这个脚本下载完整的源码之前,需要做一下简单的修改,不然可能你在下载源码的过程中会数次中断。1
2
3
4
5# Get clones of all absent nested repositories (harmless if already exist)
sh ./common/bin/hgforest.sh clone "$@" || exit $?
# Update all existing repositories to the latest sources
sh ./common/bin/hgforest.sh pull -u
我们把上面几行的脚本删掉,替换成下面的脚本:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15# Get clones of all absent nested repositories (harmless if already exist)
sh ./common/bin/hgforest.sh clone "$@"
while [ $? -ne 0 ]
do
sh ./common/bin/hgforest.sh clone "$@"
done
# Update all existing repositories to the latest sources
sh ./common/bin/hgforest.sh pull -u
while [ $? -ne 0 ]
do
sh ./common/bin/hgforest.sh pull -u
done
然后,愉快地调用:1
bash ./get_source.sh
本人表示这个这个方法我没有成功,hhh。我在执行hg clone
的时候就一直报网络错误,可能是由于the great wall吧,还好有下面的方法。
github
1 | 1. https://github.com/unofficial-openjdk/openjdk/ |
我选择了第二个,切换到了jdk/jdk9分支,因为我们这次要编译jdk9。操作如下:1
2
3
4cd ~/jvm
git clone https://github.com/dmlloyd/openjdk.git
cd openjdk
git checkout -b jdk9 origin/jdk9/jdk9
这个还是挺顺利的,哈哈!
configure
我们先进行编译前的配置(检查):1
./configure --with-target-bits=64 --with-freetype=/usr/local/Cellar/freetype/2.8.1 --enable-ccache --with-jvm-variants=server,client --with-boot-jdk-jvmargs="-Xlint:deprecation -Xlint:unchecked" --disable-zip-debug-info --disable-warnings-as-errors --with-debug-level=slowdebug 2>&1 | tee configure_mac_x64.log
有日志,出问题查问题也很方便!
注意,上面的freetype,需要替换成本机实际安装的版本
如果出现如下的提示,那么恭喜你,接下来就可以执行编译了:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30====================================================
The existing configuration has been successfully updated in
/Users/rex/jvm/openjdk/build/macosx-x86_64-normal-serverANDclient-slowdebug
using configure arguments '--with-target-bits=64 --with-freetype=/usr/local/Cellar/freetype/2.10.0 --enable-ccache --with-jvm-variants=server,client --with-boot-jdk-jvmargs='-Xlint:deprecation -Xlint:unchecked' --disable-warnings-as-errors --with-debug-level=slowdebug'.
Configuration summary:
* Debug level: slowdebug
* HS debug level: debug
* JDK variant: normal
* JVM variants: server client
* OpenJDK target: OS: macosx, CPU architecture: x86, address length: 64
* Version string: 9-internal+0-adhoc.rex.openjdk (9-internal)
Tools summary:
* Boot JDK: java version "9" Java(TM) SE Runtime Environment (build 9+181) Java HotSpot(TM) 64-Bit Server VM (build 9+181, mixed mode) (at /Library/Java/JavaVirtualMachines/jdk-9.jdk/Contents/Home)
* Toolchain: clang (clang/LLVM from Xcode 9.4.1)
* C Compiler: Version 9.1.0 (at /usr/bin/clang)
* C++ Compiler: Version 9.1.0 (at /usr/bin/clang++)
Build performance summary:
* Cores to use: 4
* Memory limit: 8192 MB
* ccache status: Active (3.6)
NOTE: You have requested to build more than one version of the JVM, which
will result in longer build times.
WARNING: The result of this configuration has overridden an older
configuration. You *should* run 'make clean' to make sure you get a
proper build. Failure to do so might result in strange build problems.
make
我们执行下面的操作:1
2export LANG=C
make all LOG=debug 2>&1 | tee make_mac_x64.log
如果出现如下的提示,那么恭喜你,你的运气太好了!!!1
2
3
4
5
6
7
8
9
10
11----- Build times -------
Start 2019-04-25 18:55:19
End 2019-04-25 19:00:57
00:05:38 TOTAL
-------------------------
if test -f /Users/rex/jvm/openjdk/build/macosx-x86_64-normal-serverANDclient-slowdebug/make-support/exit-with-error ; then \
exit 1 ; \
fi
/usr/bin/printf "Finished building target 'all' in configuration 'macosx-x86_64-normal-serverANDclient-slowdebug'\n" > >(/usr/bin/tee -a /Users/rex/jvm/openjdk/build/macosx-x86_64-normal-serverANDclient-slowdebug/build.log) 2> >(/usr/bin/tee -a /Users/rex/jvm/openjdk/build/macosx-x86_64-normal-serverANDclient-slowdebug/build.log >&2) && wait
Finished building target 'all' in configuration 'macosx-x86_64-normal-serverANDclient-slowdebug'
最后,验证一下1
2cd build/macosx-x86_64-normal-serverANDclient-slowdebug/jdk/bin
./java -version
出现下面的提示就完美了:1
2
3openjdk version "9-internal"
OpenJDK Runtime Environment (slowdebug build 9-internal+0-adhoc.rex.openjdk)
OpenJDK 64-Bit Server VM (slowdebug build 9-internal+0-adhoc.rex.openjdk, mixed mode)
编译过程中的问题
根据墨菲定律:1
2
3
4一、任何事都没有表面看起来那么简单;
二、所有的事都会比你预计的时间长;
三、会出错的事总会出错;
四、如果你担心某种情况发生,那么它就更有可能发生。
这个时间会比较长,出错是大概率事件,而我就碰到网上该有的所有错!!!!
Xcode版本问题
我的Xcode版本原来为10+,XCode升级到10之后, 删除了底层目录下的libstdc++文件。导致在JDK的Make时会报错, 无法识别
三个空指针转换
日志被覆盖了,忘记存了,但是可能会出现这样的问题,下面的更改的答案:1
2
3
4
5
6
7
8
9
10
11#1\. src/hotspot/share/memory/virtualspace.cpp # l585
if (base() != NULL) {
#2\. src/hotspot/share/opto/lcm.cpp # l42
if (Universe::narrow_oop_base() != NULL) { // Implies UseCompressedOops.
#3\. src/hotspot/share/opto/loopPredicate.cpp # l915
assert(rng->Opcode() == Op_LoadRange || iff->is_RangeCheck() || _igvn.type(rng)->is_int()->_lo >= 0, "must be");
JVM crash
自己也忘记截图,所以也盗图了:
解决方法:Building OpenJDK 9 on Mac os
上面三个问题全被自己遇到了,运气真好,不过走到这里,终于是把JDK编译好了!
总结
但行好事,莫问前程