1. 下载源码包
mkdir -p $HOME/dist/clang-3.9.1
cd $HOME/dist/clang-3.9.1
wget -c http://releases.llvm.org/3.9.1/llvm-3.9.1.src.tar.xz
wget -c http://releases.llvm.org/3.9.1/cfe-3.9.1.src.tar.xz
wget -c http://releases.llvm.org/3.9.1/compiler-rt-3.9.1.src.tar.xz
wget -c http://releases.llvm.org/3.9.1/libcxx-3.9.1.src.tar.xz
wget -c http://releases.llvm.org/3.9.1/libcxxabi-3.9.1.src.tar.xz
wget -c http://releases.llvm.org/3.9.1/libunwind-3.9.1.src.tar.xz
wget -c http://releases.llvm.org/3.9.1/lld-3.9.1.src.tar.xz
wget -c http://releases.llvm.org/3.9.1/clang-tools-extra-3.9.1.src.tar.xz
2. 解压源码
version="3.9.1"
dist=$HOME/dist/clang-${version}
opts="--strip-components=1"
mkdir -p $HOME/src/clang-${version}
cd $HOME/src/clang-${version}
mkdir -p llvm
tar -C llvm $opts -xf $dist/llvm-${version}.src.tar.?z
mkdir -p llvm/tools/clang
tar -C llvm/tools/clang $opts -xf $dist/cfe-${version}.src.tar.?z
mkdir -p llvm/tools/lld
tar -C llvm/tools/lld $opts -xf $dist/lld-${version}.src.tar.?z
mkdir llvm/tools/clang/tools/extra
tar -C llvm/tools/clang/tools/extra $opts -xf $dist/clang-tools-extra-${version}.src.tar.?z
mkdir -p llvm/projects/libcxx
tar -C llvm/projects/libcxx $opts -xf $dist/libcxx-${version}.src.tar.?z
mkdir -p llvm/projects/libcxxabi
tar -C llvm/projects/libcxxabi $opts -xf $dist/libcxxabi-${version}.src.tar.?z
mkdir -p llvm/projects/libunwind
tar -C llvm/projects/libunwind $opts -xf $dist/libunwind-${version}.src.tar.?z
mkdir -p llvm/projects/compiler-rt
tar -C llvm/projects/compiler-rt $opts -xf $dist/compiler-rt-${version}.src.tar.?z
3. 编译和安装
#
# build tree
#
# src
# \---clang-3.9.1
# +---llvm
# | +---projects
# | | +---CMakeLists.txt
# | | +---LLVMBuild.txt
# | | +---compiler-rt
# | | +---libcxx
# | | +---libcxxabi
# | | \---libunwind
# | +---tools
# | +---CMakeLists.txt
# | +---LLVMBuild.txt
# | +---...
# | +---clang
# | \---...
# \---build
# +----b1
# +----b2
# +----b3
# +----b4
# \----stage1
#
mkdir -p $HOME/src/build
cd $HOME/src/build
if [ "x$INSTALL_PREFIX" = "x" ]
then
INSTALL_PREFIX=/usr/local
fi
if [ "x$MAKE_JOBS" = "x" ]
then
MAKE_JOBS=4
fi
build_dir=`pwd`
llvm_toolchain=${build_dir}/stage1
gcc_toolchain=${GCC_TOOLCHAIN}
#
# libstdc++ -- libgcc_s
#
install_prefix=${llvm_toolchain}
printf "b1: "
date "+%Y-%m-%dT%H:%M:%S%z"
mkdir -p ${install_prefix}
mkdir b1 && cd b1
if [ "x$gcc_toolchain" = "x" ]
then
cmake -G "Unix Makefiles" \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_INSTALL_PREFIX=${install_prefix} \
../../llvm
else
cmake -G "Unix Makefiles" \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_C_COMPILER="${gcc_toolchain}/bin/gcc" \
-DCMAKE_CXX_COMPILER="${gcc_toolchain}/bin/g++" \
-DCMAKE_CXX_LINK_FLAGS="-Wl,-rpath,${gcc_toolchain}/lib64 -L/${gcc_toolchain}/lib64" \
-DCMAKE_INSTALL_PREFIX=${install_prefix} \
../../llvm
fi
make -j${MAKE_JOBS} && make install
cd ..
printf "b1: "
date "+%Y-%m-%dT%H:%M:%S%z"
#
# libc++abi libunwind
#
install_prefix=${INSTALL_PREFIX}
printf "b2: "
date "+%Y-%m-%dT%H:%M:%S%z"
mkdir b2 && cd b2
if [ "x$gcc_toolchain" = "x" ]
then
cmake -G "Unix Makefiles" \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_C_COMPILER="${llvm_toolchain}/bin/clang" \
-DCMAKE_CXX_COMPILER="${llvm_toolchain}/bin/clang++" \
-DCMAKE_SHARED_LINKER_FLAGS="-Wl,-rpath,${install_prefix}/lib -L${install_prefix}/lib" \
-DLIBCXXABI_USE_COMPILER_RT=YES \
-DLIBCXXABI_USE_LLVM_UNWINDER=YES \
-DCMAKE_INSTALL_PREFIX=${install_prefix} \
../../llvm
else
cmake -G "Unix Makefiles" \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_C_COMPILER="${llvm_toolchain}/bin/clang" \
-DCMAKE_CXX_COMPILER="${llvm_toolchain}/bin/clang++" \
-DCMAKE_C_FLAGS="--gcc-toolchain=${gcc_toolchain}" \
-DCMAKE_CXX_FLAGS="--gcc-toolchain=${gcc_toolchain}" \
-DCMAKE_SHARED_LINKER_FLAGS="-Wl,-rpath,${install_prefix}/lib -L${install_prefix}/lib" \
-DLIBCXXABI_USE_COMPILER_RT=YES \
-DLIBCXXABI_USE_LLVM_UNWINDER=YES \
-DCMAKE_INSTALL_PREFIX=${install_prefix} \
../../llvm
fi
(cd projects/libunwind && make install)
(cd projects/libcxxabi && make install)
cd ..
printf "b2: "
date "+%Y-%m-%dT%H:%M:%S%z"
#
# libc++
#
install_prefix=${INSTALL_PREFIX}
printf "b3: "
date "+%Y-%m-%dT%H:%M:%S%z"
mkdir b3 && cd b3
if [ "x$gcc_toolchain" = "x" ]
then
cmake -G "Unix Makefiles" \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_C_COMPILER="${llvm_toolchain}/bin/clang" \
-DCMAKE_CXX_COMPILER="${llvm_toolchain}/bin/clang++" \
-DCMAKE_SHARED_LINKER_FLAGS="-Wl,-rpath,${install_prefix}/lib -L${install_prefix}/lib" \
-DLIBCXX_HAS_GCC_S_LIB=NO \
-DLIBCXX_CXX_ABI=libcxxabi \
-DLIBCXX_CXX_ABI_INCLUDE_PATHS="../../llvm/projects/libcxxabi/include" \
-DLIBCXX_CXX_ABI_LIBRARY_PATH="${install_prefix}/lib" \
-DLLVM_PATH=../../llvm \
-DCMAKE_INSTALL_PREFIX=${install_prefix} \
../../llvm/projects/libcxx
else
cmake -G "Unix Makefiles" \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_C_COMPILER="${llvm_toolchain}/bin/clang" \
-DCMAKE_CXX_COMPILER="${llvm_toolchain}/bin/clang++" \
-DCMAKE_C_FLAGS="--gcc-toolchain=${gcc_toolchain}" \
-DCMAKE_CXX_FLAGS="--gcc-toolchain=${gcc_toolchain}" \
-DCMAKE_SHARED_LINKER_FLAGS="-Wl,-rpath,${install_prefix}/lib -L${install_prefix}/lib" \
-DLIBCXX_HAS_GCC_S_LIB=NO \
-DLIBCXX_CXX_ABI=libcxxabi \
-DLIBCXX_CXX_ABI_INCLUDE_PATHS="../../llvm/projects/libcxxabi/include" \
-DLIBCXX_CXX_ABI_LIBRARY_PATH="${install_prefix}/lib" \
-DLLVM_PATH=../../llvm \
-DCMAKE_INSTALL_PREFIX=${install_prefix} \
../../llvm/projects/libcxx
fi
make -j${MAKE_JOBS} && make install
cd ..
printf "b3: "
date "+%Y-%m-%dT%H:%M:%S%z"
#
# clang++ libc++ libc++abi libunwind
#
install_prefix=${INSTALL_PREFIX}
printf "b4: "
date "+%Y-%m-%dT%H:%M:%S%z"
mkdir -p projects && mv ../llvm/projects/libcxx ../llvm/projects/libcxxabi ../llvm/projects/libunwind projects
mkdir b4 && cd b4
if [ "x$gcc_toolchain" = "x" ]
then
cmake -G "Unix Makefiles" \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_C_COMPILER="${llvm_toolchain}/bin/clang" \
-DCMAKE_CXX_COMPILER="${llvm_toolchain}/bin/clang++" \
-DCMAKE_CXX_LINK_FLAGS="-Wl,-rpath,${install_prefix}/lib -L${install_prefix}/lib -rtlib=compiler-rt" \
-DCMAKE_SHARED_LINKER_FLAGS="-Wl,-rpath,${install_prefix}/lib -L${install_prefix}/lib -rtlib=compiler-rt -lunwind" \
-DCMAKE_MODULE_LINKER_FLAGS="-Wl,-rpath,${install_prefix}/lib -L${install_prefix}/lib -rtlib=compiler-rt" \
-DCMAKE_INSTALL_PREFIX=${install_prefix} \
../../llvm
else
cmake -G "Unix Makefiles" \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_C_COMPILER="${llvm_toolchain}/bin/clang" \
-DCMAKE_CXX_COMPILER="${llvm_toolchain}/bin/clang++" \
-DCMAKE_C_FLAGS="--gcc-toolchain=${gcc_toolchain}" \
-DCMAKE_CXX_FLAGS="--gcc-toolchain=${gcc_toolchain} -stdlib=libc++" \
-DCMAKE_CXX_LINK_FLAGS="-Wl,-rpath,${install_prefix}/lib -L${install_prefix}/lib -rtlib=compiler-rt" \
-DCMAKE_SHARED_LINKER_FLAGS="-Wl,-rpath,${install_prefix}/lib -L${install_prefix}/lib -rtlib=compiler-rt -lunwind" \
-DCMAKE_MODULE_LINKER_FLAGS="-Wl,-rpath,${install_prefix}/lib -L${install_prefix}/lib -rtlib=compiler-rt" \
-DCMAKE_INSTALL_PREFIX=${install_prefix} \
../../llvm
fi
make -j${MAKE_JOBS} && make install
cd ..
mv projects/libcxx projects/libcxxabi projects/libunwind ../llvm/projects
printf "b4: "
date "+%Y-%m-%dT%H:%M:%S%z"
4. 测试 clang++
写一个简单的C++程序,然后用clang++编译后查看依赖的动态库
$ clang++ -stdlib=libc++ -rtlib=compiler-rt demo.cpp -o demo
$ ldd demo
linux-vdso.so.1 => (0x00007fff821ca000)
libc++.so.1 => /usr/local/clang/lib/libc++.so.1 (0x00007f4b3de41000)
libc++abi.so.1 => /usr/local/clang/lib/libc++abi.so.1 (0x00007f4b3dc07000)
libunwind.so.1 => /usr/local/clang/lib/libunwind.so.1 (0x00007f4b3d9fa000)
libm.so.6 => /lib64/libm.so.6 (0x0000003d52e00000)
libc.so.6 => /lib64/libc.so.6 (0x0000003d52600000)
libpthread.so.0 => /lib64/libpthread.so.0 (0x0000003d52a00000)
librt.so.1 => /lib64/librt.so.1 (0x0000003d53600000)
libdl.so.2 => /lib64/libdl.so.2 (0x0000003d52200000)
/lib64/ld-linux-x86-64.so.2 (0x0000003d51e00000)
5. 参考链接
http://releases.llvm.org/8.0.1/docs/GettingStarted.html#getting-a-modern-host-c-toolchain
https://blogs.gentoo.org/gsoc2016-native-clang/2016/05/05/build-a-freestanding-libcxx/
https://blog.csdn.net/qq_23599965/article/details/90768265