本文主要针对需要在Ubuntu下用clang
和libc++
标准库学习C++
的同学. 操作系统是Ubuntu 16.04的64位版.
安装必要的包:
sudo apt install subversion
sudo apt install cmake
建立目录(这里取名为
CL
):
cd ~
sudo mkdir CL cd CL
下载
llvm
:
svn co http://llvm.org/svn/llvm-project/llvm/trunk llvm
下载
clang
:
cd llvm/tools
svn co http://llvm.org/svn/llvm-project/cfe/trunk clang
cd ../..
下载
clang
工具(可选)
cd llvm/tools/clang/tools
svn co http://llvm.org/svn/llvm-project/clang-tools-extra/trunk extra
cd ../../../..
下载Compiler-RT(可选)
cd llvm/projects
svn co http://llvm.org/svn/llvm-project/compiler-rt/trunk compiler-rt
cd ../..
下载标准库
libcxx
(绝对要下载)还有
libcxxabi
(千万不要遗漏):
cd llvm/projects
svn co http://llvm.org/svn/llvm-project/libcxx/trunk libcxx
svn co http://llvm.org/svn/llvm-project/libcxxabi/trunk libcxxabi
cd ../..
编译安装
mkdir build
cd build
注意将默认的Debug模式换成Release模式.
cmake -G "Unix Makefiles" -DCMAKE_BUILD_TYPE=Release ../llvm
make
sudo make install
可以用了!
基于
c++11
使用
libc++
编译
x.cpp
并执行
a.out
clang++ -std=c++11 -stdlib=libc++ x.cpp
.\a.out
验证
x.cpp
的正确性
clang x.cpp -fsyntax-only
输出
x.cpp
未优化的LLVM代码
clang x.cpp -S -emit-llvm -o -
输出
x.cpp
经过
O3
优化的LLVM代码
clang x.cpp -S -emit-llvm -o - -O3
输出
x.cpp
的原生机器码
clang x.cpp -S -O3 -o -
折腾
安装完毕之后, 如果不嫌麻烦的话, 可以用
clang
再编译安装一次:
CC=clang CXX=clang++ cmake -G "Unix Makefiles" -DCMAKE_BUILD_TYPE=Release ../llvm
后续步骤同上:-)
Clang与GCC的区别
(1)Clang比GCC编译器的优势:
编译速度更快
编译产出更小
出错提示更友好,比如 clang 在编译过程可以直接指出相对简单的出错位置以及它 “ 认为 ” 正确的方式 。
内置有静态分析工具,可以对代码进行静态分析 (clang—analyze) 。这也是 gcc 做不到的 。
专注,因为 clang 只需要完成词法和语法分析,代码优化和机器代码的生成工作由 llvm 完成。所以和全部由自己包下的 gcc 比起来, clang 可以更专注地做好一件事。这种结构也使 clang 可以被单独拿出来用在其他的程序里,成为其它 app (主要是 IDE)的内嵌 C/C++ parser 。 对于 IDE 而言,代码补全、重构是重要的功能,然而如果没有底层的支持,只使用 tags 分析或是正则表达式匹配是很难达成的, clang正好充当了这一角色。 这样, editor 工具可以使用和 compiler 一样的 parser 来完成 edit-time 的语法检查 。 而 gcc 就没法很方便地做到这一点 。由于历史原因, GCC 是一个单一的可执行程序编译器,其内部完成了从预处理到最后代码生成的全部过程,中间诸多信息都无法被其他程序重用。
编译速度更快、编译产出更小、出错提示更友好
Clang采用的是BSD协议。这是苹果资助LLVM、FreeBSD淘汰GCC换用Clang的一个重要原因。
(2)GCC的优势:
一些软件用 clang 编译会出现莫名其妙的错误,但是用 gcc 编译可以通过 。
GCC 在 5.0 之前一直都在准备用 C++ 实现模块化,期待 GCC 的 5.0 会有所突破,补上无法模块化的短板。
gcc与g++的区别
GCC:GNU Compiler Collection(GUN 编译器集合),它可以编译C、C++、JAVA、Fortran、Pascal、Object-C、Ada等语言。
GCC 是GCC中的GUN C Compiler(C 编译器)
g++是GCC中的GUN C++ Compiler(C++编译器)
一个有趣的事实就是,就本质而言,gcc和g++并不是编译器,也不是编译器的集合,它们只是一种驱动器,根据参数中要编译的文件的类型,调用对应的GUN编译器而已。
gcc and g++分别是GNU 的c & c++编译器 gcc /g++在执行编译工作的时候,总共需要4步
1.预处理,编译处理宏定义等宏命令(eg:#define),生成.i的文件[预处理器cpp]
2.将预处理后的文件转换成汇编语言,生成文件.s[编译器ccl]
3.由汇编变为二进制目标代码(机器代码)生成.o的文件[汇编器as]
4.连接目标代码,生成可执行程序[链接器ld], Eg: 将print.o文件连接合并到hello.o文件中
gcc和g++的主要区别
1. 对于 *.c和*.cpp文件,gcc分别当做c和cpp文件编译(c和cpp的语法强度是不一样的)
2. 对于 *.c和*.cpp文件,g++则统一当做cpp文件编译
3. 使用g++编译文件时,g++会自动链接标准库STL,而gcc不会自动链接STL
4. gcc在编译C文件时,可使用的预定义宏是比较少的
5. gcc在编译cpp文件时/g++在编译c文件和cpp文件时(这时候gcc和g++调用的都是cpp文件的编译器),会加入一些额外的宏,这些宏如下:
#define __GXX_WEAK__ 1
#define __cplusplus 1
#define __DEPRECATED 1
#define __GNUG__ 4
#define __EXCEPTIONS 1
#define __private_extern__ extern
6.在用gcc编译c++文件时,为了能够使用STL,需要加参数 –lstdc++ ,但这并不代表 gcc –lstdc++ 和 g++等价,它们的区别不仅仅是这个
主要参数
-g - turn on debugging (so GDB gives morefriendly output)
-Wall - turns on most warnings
-O or -O2 - turn on optimizations
-o - name of the output file
-c - output an object file (.o)
-I - specify an includedirectory
-L - specify a libdirectory
-l - link with librarylib.a
使用示例:g++ -ohelloworld -I/homes/me/randomplace/include helloworld.C
Reference:
http://www.jianshu.com/p/cbb242026ff2
http://blog.csdn.net/csfreebird/article/details/17070739
https://www.ibm.com/developerworks/cn/opensource/os-cn-clang/
https://chaowyc.github.io/2017/02/21/install-LLVM-on-ubuntu/
http://blog.csdn.net/gatieme/article/details/45268549
http://www.cnblogs.com/zlcxbb/p/5759755.html
http://www.cnblogs.com/zlcxbb/p/5759738.html
http://blog.csdn.net/gmpy_tiger/article/details/47808081
http://www.cnblogs.com/wb118115/p/5969775.html