1、编译原理实验报告 Foshan University编译原理课程设计实验报告学 院: 专 业: 计算机科学与技术 班 级: 姓 名: 学 号: 日 期: 2014 年 6 月 5 日目录一、实验简介 1二、语言定义 2三、词法分析 21.实现方法 32.PL/0语言的词汇表 33.具体实现流程图 44.错误处理 4四、语法分析 41.实现方法 52.程序流程图 53.错误处理 7五、目标代码生成 81.实现方法 82.汇编指令集 83.具体实现 8六、程序运行测试 81.测试样例 92.词法分析结果 93.语法分析结果 94.汇编代码生成 9七、程序所存在的缺点与不足 10八、实验总结 10一
2、、实验简介本次实验旨在设计一个类PL语言子集的编译器,可以对自己设计的语言进行编译,最终生成可执行的汇编代码。实验分为词法分析、语法分析和中间代码生成、汇编代码生成四个阶段。通过实验,掌握词法分析的实现技术,深入了解语法分析的四种实现技术及具体实现方法,了解代码优化和代码生成的实现技术及具体实现方法。明确编译各阶段之间的关系。熟悉符号表的建立及在编译过程中的作用。二、PL/0语言文法的EBNF:=. := :=CONST,; := := :=VAR , ; :=| :=; ; :=PROCEDURE ; :=| | :=:= :=BEGIN ; END := |ODD := +|- := :=
3、 | () := +|- := *|/ := =|#|= := IF THEN := CALL 标识符 := WHILE DO := READ(,) := WRITE(,) := a|b|X|Y|Z := 0|1|8|9:=VAR 数字3、词法分析1. 实现方法通过逐词读入样例程序中的内容,对每个单词进行判断分析,输出该单词的内容以及种别码。PL的词法分析器将要完成以下工作:(1) 跳过分隔符(如空格,回车,制表符);(2) 识别诸如begin,end,if,while等保留字;(3) 识别非保留字的一般标识符,此标识符值(字符序列)赋给全局量id,而全局量sym赋值为SYM_IDENTIFI
4、ER。(4) 识别数字序列,当前值赋给全局量NUM,sym则置为SYM_NUMBER;(5) 识别:=,=之类的特殊符号,全局量sym则分别被赋值为SYM_BECOMES,SYM_LEQ,SYM_GEQ等。相关过程(函数)有getsym(),getch(),其中getch()为获取单个字符的过程,除此之外,它还完成:(1) 识别且跳过行结束符;(2) 将输入源文件进行词法分析后写到输出文件;产生一份程序列表,输出相应行号或指令计数器的值2. PL/0语言的词汇表序号类别单词编码1基本字begin, call, const, do, endif, odd, procedure, readthen
5、, var, while, writebeginsym, callsym, constsymdosym, endsym, ifsym, oddsymproceduresym, readsym, thensymvarsym, whilesym, writesym2标识符ident3常数number4运算符+, -, *, /, odd=, , , , =, :=plus, minus, times, slash, oddsymeql, neq, lss, leq, gtr, geq, becomes5界符( ) , ;.Lparen, rparen, comma, semicolonperiod
6、3.具体实现流程图4.错误处理当遇到非法字符、标示符与关键字重复时会显示相应的错误信息。四、语法分析1.实现方法使用LR(1)算法,首先求出语言定义文法的LR(1)分析表,然后LR分析算法的总控程序根据分析表对源语言进行语法分析。采用递归下降的方法来设计PL/0编译器,证明PL/0语言属于LL(1)文法。然后结合语法图编写(递归下降)语法分析程序的一般方法,具体方面有:(1)用合适的替换将语法约化成尽可能少的单个图;(2)将每一个图按下面的规则(3)-(7)翻译成一个过程说明;(3)顺序图对应复合语句:SnS1S2对应:begin T(S1); T(S2); .; T(Sn) end(4)选择
7、:S1S2S3 对应:case语句或者条件语句: case ch of if ch in L1 then T(S1) else L1: T(S1); if ch in L2 then T(S2) else L2: T(S2); 或 . . if ch in Ln then T(Sn) else Ln: T(Sn); error 其中LiFIRST(Si),ch为当前输入符号。(下同)(5)循环:S 对应:while ch in L do T(S)(6)表示另一个图A的图:A对应:过程调用A。(7)表示终结符的单元图:对应:if ch = x then read(ch) else error相关
8、过程有:block(), constdeclaration(), vardeclaration(), statement(), condition(), expression(), term(), factor()等。并画出它们之间依赖关系图,并在此基础上实现程序的编制。 并适当进行语义分析的相关检查:(1)是否存在标识符先引用未声明的情况;(2)是否存在己声明的标识符的错误引用;(3)是否存在一般标识符的多重声明。2. 程序流程图语法分析流程图:3.错误处理A对于缺少括号和;等分割符的错误:对栈中的元素进行判断如果为非终结符还不匹配则出栈。说明缺少;)等但是由于一般这种错误都在上一行缺少所以
9、:错误行数为当前token所在行前一行B.对于程序未完全解析完的处理不配陪:可能由于括号冗余使得在文件未完全解析完时栈已经为空。所以在控制程序中添加对栈底的判断,如果遇到文件还没有解析完将语句块非终结符压入栈中继续匹配。一般为上一行冗余。错误行数:为当前token所在行前一行。E代码不完整对于程序解析完栈中还有符号,说明缺少部分信息,代码不完全需要将栈清空,并说明程序不完整。错误行数:代码的末尾。五、目标代码生成1.实现方法通过查看语义分析所产生的结果,分析四元式,输出相应的汇编语句。2.汇编指令集本次目标代码的翻译采用了AT&T汇编指令集。3.具体实现详见源代码。六、程序运行测试1.测试样例
10、测试程序1const a=10;var b,c;beginread(b);c:=a+b;write(c)end. 所有测试程序见附录编译原理测试程序。2.词法分析结果3.语法分析结果5.汇编代码生成七、程序所存在的缺点与不足1.由于时间原因,在语义分析阶段,没有实现对数组、函数部分的分析。2.语法分析和语义分析的错误处理方面只能报出错误类型,无法确定是错误出现的具体位置。3.词法分析和其他部分没有合并。4.在布尔表达式方面,并未实现多个表达式之间的与、或、非功能。5.文法设计的不够合理,有很多不需要的地方使得源语言很繁琐(if、while语句在结束时要在后加上一个;等等)。八、实验总结通过从词
11、法分析-语法分析-目标代码生成的过程,我也真是的体会着编码的开心与痛苦,但是收获解决一个个问题的幸福感,在不断学习中也教会我如何自己去学习,一点点建立着属于自己的信心,增强着自己不算强的问题解决能力。词法分析虽然比较简单,但是构造识别单词的自动机的时候让我复习和巩固了关于自动机方面的知识。语法分析过程中我掌握了自底向上和自顶向下两张思想,最后采用LR(1)分析法。通过编写程序,我对LR(1)分析法有了深刻的理解。汇编代码生成阶段让我对AT&T汇编语言有了一定的了解。 总之,通过实验我掌握了编译原理的一些基础,对于Java的堆栈的使用和list的使用有了进一步的了解,同时在每天思考如何实现程序时,也增强了的我解决问题的能力。
copyright@ 2008-2022 冰豆网网站版权所有
经营许可证编号:鄂ICP备2022015515号-1