一、LLVM编译器组成
LLVM项目是模块化、可重用的编译器以及工具链技术的集合,由前端(Fronttend),优化器(Optimizer),后端(Backend);
作用:
- 前端(Fronttend): 词法分析,语法分析,语义分析,生成中间代码;
- 优化器(Optimizer):中间代码优化;
-
后端(Backend):生成机器码(比如生成Mach-o);
二、clang
- llvm项目的一个子项目;
- 基于llvm架构的c/c++/objective-c编码器前端;
三、lang 与 llvm的关系
clang 作为llvm编译器的前端,负责对源代码词法分析,语法分析,语义分析,生成中间代码等功能,只是编译器的一部分。
四、oc源文件的编译过程
编写一个oc文件,取出.m文件,使用命令行 clang -ccc-print-phases xxx.m , 就可以看到文件的编译过程;
0:导入源文件main.m的oc文件;
1:preprocessor 预编译过程,生成对于cpp输出文件;
2:compiler 编译。通过使用ir (中间代码LLVM Intermediate Representation (LLVM IR)) 编译;
3:后端部分,生成对应的汇编代码;
4:汇编代码生成目标文件;
5:linker;
6:生成对于的二进制文件;
详细步骤:
-
查看preprocessor(预处理)的结果:$ clang -E main.m
-
词法分析,生成Token: $ clang -fmodules -E -Xclang -dump-tokens main.m
- 语法分析,生成语法树(AST,Abstract Syntax Tree): $ clang -fmodules -fsyntax-only -Xclang -ast-dump main.m
main.m 内容:
void test(int a, int b) {
int c = a + b - 3;
}
- LLVM IR中间代码
LLVM IR有3种表示形式 :
text:便于阅读的文本格式,类似于汇编语言,拓展名.ll, $ clang -S -emit-llvm main.m
memory:内存格式
-
bitcode:二进制格式,拓展名.bc, $ clang -c -emit-llvm main.m
全局标识符以@开头,局部标识符以%开头
alloca,在当前函数栈帧中分配内存
i32,32bit,4个字节的意思
align,内存对齐
store,写入数据
load,读取数据