语法分析
编译器的第二个步骤成为语法分析或解析。语法分析器使用由词法分析器生成的各个词法单元的第一个分量来创建树形的中间表示。该中间表示给出了词法分析产生的词法单元流的语法结构。一个常用的表示方法是语法树,树种每个结点表示一个运算,该节点的子节点表示运算分量。编译器的后续步骤使用这个词法结构来帮助分析源程序,并生成目标程序。
语义分析
语义分析器使用语法树和符号表的信息检查源程序是否和语言定义的语义一致,同时收集类型信息以便随后使用。
语义分析的一个重要部分是类型检查。同时,程序设计语言可能允许某些类型转换,称为自动类型转换。
中间代码生成
把源程序翻译成目标代码的过程中,一个编译器可能构造出一个或多个中间表示。语法树是一种中间表示,通常在语法分析和语义分析中使用。
语法分析和语义分析完成后,很多编译器会生成一个明确的低级的或类机器语言的中间表示。该中间表示具有两个性质:易于生成,能被轻松的翻译为目标机器语言。
比如三地址代码的中间表示形式:
t1 = inttofloat(60);
t2 = id3*t1; ........
代码优化
机器无关的代码优化步骤试图改进中间代码,以便生成更好的目标代码。不同的编译器所做的代码优化量相差很大。那些优化工作做得更多的编译器,即所谓的“优化编译器”,会在优化阶段花相当多的时间。
代码生成
代码生成器以源程序的中间表现形式作为输入,并把它映射到目标语言。如果目标语言是机器代码,那么就必须为程序使用的每个变量选择寄存器或内存位置。然后,中间指令被翻译成能完成相同任务的机器指令序列。代码生成的一个至关重要的方面是合理分配寄存器以存放变量的值。
符号表管理
编译器的重要功能之一就是记录源程序中使用的变量的名字,并收集和每个名字的各种属性有关的信息。比如类型,作用域等。
符号表数据结构为每个变量名字创建了一个记录条目。记录的字段就是名字的各个属性。
编译器构造工具
常用的编译器构造工具:
- 语法分析器的生成器:根据一个程序设计语言的语法描述自动生成语法生成器
- 扫描器的生成器:可以根据一个语言的语法单元的正则表达式描述生成词法分析器
- 语法制导的翻译引擎:可以生成一组用于遍历分析树并生成中间代码的历程
- 代码生成器的生成器:依据一组关于如何把中间语言的每个运算翻译成目标语言的规则,生成一个代码生成器
- 数据流分析引擎:帮助收集数据量信息。数据流分析是代码优化的一个重要部分