版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、2022-2-1512022-2-151编编 译译 原原 理理2022年2月15日S.PO.P语义分析、生成中间代码语义分析、生成中间代码生成目标程序生成目标程序代码优化代码优化语法分析程序语法分析程序词法分析程序词法分析程序错错误误处处理理符符号号表表管管理理2022-2-1522022-2-152编编 译译 原原 理理2022年2月15日第第5 5章章语法制导翻译技术和中间代码生成语法制导翻译技术和中间代码生成 要求明确语义分析的要求明确语义分析的任务任务 明确明确属性文法属性文法和和语法制导翻译语法制导翻译的含义的含义 明确明确自底向上和自顶向下自底向上和自顶向下语法制导翻译的语法制导翻
2、译的区别和特点区别和特点 明确明确生成中间代码的目的,中间代码的几生成中间代码的目的,中间代码的几种形式种形式教学目标教学目标2022-2-1532022-2-153编编 译译 原原 理理2022年2月15日 属性文法属性文法 语法制导翻译法的基本思想语法制导翻译法的基本思想 常见的中间代码常见的中间代码 各种不同语法结构的语法制导翻译技术各种不同语法结构的语法制导翻译技术教学内容教学内容2022-2-1542022-2-154编编 译译 原原 理理2022年2月15日词法分析,语法分析词法分析,语法分析:解决单词和语言成分的识别:解决单词和语言成分的识别及词法和语法结构的检查。语法结构可形式
3、化地用及词法和语法结构的检查。语法结构可形式化地用一组产生式来描述。给定一组产生式,我们能够很一组产生式来描述。给定一组产生式,我们能够很容易地将其分析器构造出来。容易地将其分析器构造出来。本章要介绍的是本章要介绍的是语义分析和中间代码生成技术语义分析和中间代码生成技术。程序语言中间代码目标代码程序语言中间代码目标代码翻译翻译翻译翻译2022-2-1552022-2-155编编 译译 原原 理理2022年2月15日根据语义规则对识别出的各种语法成分析其含义,根据语义规则对识别出的各种语法成分析其含义,进行初步翻译,生成相应的中间代码或直接生成目进行初步翻译,生成相应的中间代码或直接生成目标代码
4、。标代码。(1)确定数据类型)确定数据类型(2)语义检查)语义检查动态语义检查:在运行时刻进行动态语义检查:在运行时刻进行 静态语义检查:在编译时完成静态语义检查:在编译时完成(3)识别含义,进行真正的翻译)识别含义,进行真正的翻译5.15.1语义分析的任务语义分析的任务2022-2-1562022-2-156编编 译译 原原 理理2022年2月15日类型检查类型检查。控制流检查控制流检查,确保控制语句有合法的转向点。例,确保控制语句有合法的转向点。例如,如,C语言中的语言中的break语句使控制跳离包括该语句的语句使控制跳离包括该语句的最小的最小的switch,while或或for语句。如果
5、不存在包括它语句。如果不存在包括它的这样的语句,则应报错。的这样的语句,则应报错。静态语义检查静态语义检查2022-2-1572022-2-157编编 译译 原原 理理2022年2月15日静态语义检查静态语义检查一致性检查一致性检查。很多情况下要求对象只能被定义一。很多情况下要求对象只能被定义一次。例如,语言中规定一个标识符在同一作用域中次。例如,语言中规定一个标识符在同一作用域中只能被说明一次,同一只能被说明一次,同一case语句的标号不能相同,枚语句的标号不能相同,枚举类型的元素不能重复出现等。举类型的元素不能重复出现等。相关名字检查相关名字检查。有的语言中有时规定,同一名字。有的语言中有
6、时规定,同一名字必须出现两次或多次。例如,必须出现两次或多次。例如,Ada语言中,循环或程语言中,循环或程序块可以有一个名字,它出现在这些结构的开头和结序块可以有一个名字,它出现在这些结构的开头和结尾,如同语句括号一般,编译程序必须检查它们的配尾,如同语句括号一般,编译程序必须检查它们的配对情况。对情况。2022-2-1582022-2-158编编 译译 原原 理理2022年2月15日实际应用中比较流行的语义分析方法:实际应用中比较流行的语义分析方法:基于基于属性文法属性文法的的语法制导翻译方法语法制导翻译方法 5.25.2语法制导翻译语法制导翻译2022-2-1592022-2-159编编
7、译译 原原 理理2022年2月15日附加了一组附加了一组属性属性和和运算(语义)规则运算(语义)规则的的文法文法 5.2.1 属性文法属性文法文法符号文法符号X的属性的属性t常用常用X.t来表示来表示 语义规则是根据产生式所语义规则是根据产生式所蕴涵的语义蕴涵的语义操作建立起来的,操作建立起来的,并与并与语义分析的目标语义分析的目标有关有关不同的不同的产生式产生式对应不同的语义规则对应不同的语义规则不同的不同的分析目标分析目标也对应不同的语义规则也对应不同的语义规则 1. 属性的表示属性的表示2.语义规则语义规则的表示的表示语义信息语义信息语义之间的关系语义之间的关系静态语义检查、符号静态语义
8、检查、符号表操作、代码生成及表操作、代码生成及打印各种错误信息打印各种错误信息 2022-2-15102022-2-1510编编 译译 原原 理理2022年2月15日 非终结符非终结符E E、T T及及F F都有一个综合属性都有一个综合属性val,val,符号符号i i有一个综合属性,它的值由词法分析器提供。有一个综合属性,它的值由词法分析器提供。 某些非终结符加下标是为了区分一个产生式某些非终结符加下标是为了区分一个产生式中同一非终结符多次出现中同一非终结符多次出现语语 义义 规规 则则E E1+TE T T T1 * FT FF (E)F i E.val=E1.val+T.valE.val
9、=T.val T.val=T1.val F.valT.val=F.valF.val=E.val F.val=i.lexval产生式产生式例例5.15.12022-2-15112022-2-1511编编 译译 原原 理理2022年2月15日5.2.2 语法制导翻译的过程语法制导翻译的过程语法制导翻译:语法制导翻译:将将语义规则语义规则与与语法规则语法规则相结合,在相结合,在语法分析语法分析的过程中通过执行的过程中通过执行语义动作语义动作,计算语义属,计算语义属性值,从而完成预定的翻译工作。性值,从而完成预定的翻译工作。 YaccYacc利用的就是语法制导翻译方法,它使用符号利用的就是语法制导翻译
10、方法,它使用符号$表示表示产生式左端的属性,产生式左端的属性,$n$n表示存取产生式右端第表示存取产生式右端第n n个文法符个文法符号相联的属性号相联的属性expr : expr + expr $ = $1 + $3; 2022-2-15122022-2-1512编编 译译 原原 理理2022年2月15日自底向上语自底向上语法制导翻译法制导翻译自顶向下语自顶向下语法制导翻译法制导翻译语法制导翻译的实现语法制导翻译的实现2022-2-15132022-2-1513编编 译译 原原 理理2022年2月15日语法制导翻译分为两种语法制导翻译分为两种处理方法处理方法:(1)语法制导定义(自底向上):)
11、语法制导定义(自底向上):对每个产生式编制一个语义子程序,在进行语法分析的过对每个产生式编制一个语义子程序,在进行语法分析的过程中,程中,当一个产生式获得匹配时当一个产生式获得匹配时,就调用相应的语义子程,就调用相应的语义子程序实现语义检查与翻译。这种实现方案隐藏了其中语义规序实现语义检查与翻译。这种实现方案隐藏了其中语义规则的计算次序等实现细节,不必规定翻译顺序。则的计算次序等实现细节,不必规定翻译顺序。(2)翻译方案(自顶向下):)翻译方案(自顶向下):在产生式右部的适当位置,插入相应的语义动作,按照分在产生式右部的适当位置,插入相应的语义动作,按照分析的进程,执行遇到的语义动作。这是一种
12、析的进程,执行遇到的语义动作。这是一种动作与分析交动作与分析交错错的实现方案。的实现方案。2022-2-15142022-2-1514编编 译译 原原 理理2022年2月15日输入符号串输入符号串 分析树分析树执行执行语义规则语义规则 翻译结果翻译结果翻译步骤翻译步骤()从分析树得到描述结点属性间依赖关系的()从分析树得到描述结点属性间依赖关系的依赖图依赖图,由,由依赖图得到语义规则的依赖图得到语义规则的计算次序计算次序 (1)分析输入符号串,建立)分析输入符号串,建立分析语法树分析语法树()进行语义规则的计算,得到翻译结果()进行语义规则的计算,得到翻译结果 2022-2-15152022-
13、2-1515编编 译译 原原 理理2022年2月15日5.2.3 语法制导定义语法制导定义对每个产生式编制一个对每个产生式编制一个语义子程序语义子程序在进行语法分析的过程中,在进行语法分析的过程中,当一个产生式获得匹配时当一个产生式获得匹配时,就调,就调用相应的语义子程序实现语义检查与翻译用相应的语义子程序实现语义检查与翻译综合属性综合属性继承属性继承属性自底向上自底向上传递信息传递信息自顶向下(自左自顶向下(自左向右)向右)传递信息传递信息2022-2-15162022-2-1516编编 译译 原原 理理2022年2月15日 print(E.val)print(E.val)打印由打印由E E
14、产生的算术表达式的值,产生的算术表达式的值,可认为这条规则定义了可认为这条规则定义了L L的一个的一个虚属性虚属性。 L EE E1+TE T T T1 * FT FF (E)F iprint(E.val) E.val=E1.val+T.valE.val=T.val T.val=T1.val F.val T.val=F.valF.val=E.valF.val=i.lexval例例5.5.综合属性综合属性语语 义义 规规 则则产生式产生式2022-2-15172022-2-1517编编 译译 原原 理理2022年2月15日 一个结点的综合属性一个结点的综合属性值是其值是其子结点子结点的某些的某些
15、属性来决定的属性来决定的+3+3* *4 4的注释分析树的注释分析树通常使用通常使用自底向上自底向上的分析方法的分析方法在在每个结点每个结点处使用语义规则处使用语义规则来计算综合属性值来计算综合属性值当一个当一个产生式获得匹配产生式获得匹配时,时,就调用相应的语义子程序就调用相应的语义子程序从从叶结点到根结点叶结点到根结点进行计算进行计算 只含有只含有综合属性综合属性的语法制的语法制导定义称为导定义称为S S属性定义属性定义2022-2-15182022-2-1518编编 译译 原原 理理2022年2月15日5.2.5 S属性定义与自底向上翻译属性定义与自底向上翻译 LRLR分析器可以改造为一
16、个翻译器,在对输入串分析器可以改造为一个翻译器,在对输入串进行语法分析的同时对属性进行计算进行语法分析的同时对属性进行计算 LRLR分析器增加分析器增加属性值(语义)栈属性值(语义)栈 2022-2-15192022-2-1519编编 译译 原原 理理2022年2月15日步步 骤骤状状 态态 栈栈符符 号号 栈栈属属 性性 值值 栈栈剩余符号串剩余符号串分分 析析 动动 作作10#2+3*4#移进移进205#2+3*4#用用Fi归约归约303#F2+3*4#用用TF归约归约402#T2+3*4#用用ET归约归约501#E23*4#移进移进6016#E+2*4#移进移进70165#E+32*4#
17、用用Fi归约归约80163#E+F23*4#用用TF归约归约90169#E+T23*4#移进移进1001697#E+T*234#移进移进11016975#E+T*423#用用Fi归约归约1201697 10#E+T*F234#用用TT*F归约归约130169#E+T2 (12)#用用EE+T归归约约1401#E (14)#acc2022-2-15202022-2-1520编编 译译 原原 理理2022年2月15日产生式产生式语语 义义 规规 则则D TL T int T float L L1,idL idL.in=T.typeT.type=intT.type=floatL1.in=L.in e
18、nter(id.entry,L.in) enter(id.entry,L.in)例例5.35.3继承属性继承属性L.inint id1,id2,id3DL.in= intL.in= intL.in= intT.type=intintid2id1id3., 一个结点的继承属性值一个结点的继承属性值是由其是由其父结点或兄弟结父结点或兄弟结点点的某些属性决定的的某些属性决定的2022-2-15212022-2-1521编编 译译 原原 理理2022年2月15日1、文法非终结符既有综合属性,也可有继承属性;、文法非终结符既有综合属性,也可有继承属性;2、开始符号没有继承属性;、开始符号没有继承属性;3
19、、终结符只有综合属性,由词法分析器提供。、终结符只有综合属性,由词法分析器提供。几点说明:几点说明:2022-2-15222022-2-1522编编 译译 原原 理理2022年2月15日生成中间代码的生成中间代码的目的目的(1)便于优化便于优化(2)便于移植便于移植常见的中间代码常见的中间代码形式形式:后缀式后缀式三地址代码三地址代码(四元式、三元式和间接三元式(四元式、三元式和间接三元式 )图形图形(抽象语法树、有向无环图)(抽象语法树、有向无环图) 中间代码:一种介于中间代码:一种介于源语言和目标语言之间源语言和目标语言之间的中间语言形式的中间语言形式5.5.中间代码中间代码2022-2-
20、15232022-2-1523编编 译译 原原 理理2022年2月15日.java java源程序文件.class 二进制字节码文件Java虚拟机(JVM)本地计算机系统编译JavaJava语言语言2022-2-15242022-2-1524编编 译译 原原 理理2022年2月15日.NET.NET框架框架 2022-2-15252022-2-1525编编 译译 原原 理理2022年2月15日GCCGCC 2022-2-15262022-2-1526编编 译译 原原 理理2022年2月15日中缀表示中缀表示后缀表示后缀表示a+b ab+a+b*c abc*+(a+b)*c ab+c*a:=b*
21、c+b*d abc*bd*+:=特点特点1、运算对象出现的顺序和原有顺序(从左到右)相同、运算对象出现的顺序和原有顺序(从左到右)相同2、运算符按实际计算顺序(从左到右)出现、运算符按实际计算顺序(从左到右)出现3、运算符紧跟在运算对象的后面出现,且没有括号、运算符紧跟在运算对象的后面出现,且没有括号优点:简明、便于计值优点:简明、便于计值5.3.1 后缀式后缀式2022-2-15272022-2-1527编编 译译 原原 理理2022年2月15日分别给出下列表达式的后缀表示分别给出下列表达式的后缀表示1. -a+b*(-c+d)2. X:=-(a+b)/(c-d)-(a+b*c)3. a=c
22、 b=d4. ab+c ada+bea-bc-d+*+Xab+-cd-/abc*+-:=ac= bd=abc+ ad ab+e 2022-2-15282022-2-1528编编 译译 原原 理理2022年2月15日5.3.2 三地址代码三地址代码种类种类(1)x = y op z形式的赋值语句,其中形式的赋值语句,其中op是二元运算符。是二元运算符。(2)x = op y形式的赋值语句,其中形式的赋值语句,其中op是一元运算符。是一元运算符。(3)x = y形式的赋值语句。形式的赋值语句。(4)无条件转移语句)无条件转移语句goto L,表示下一个要执行的语句是,表示下一个要执行的语句是标号为
23、标号为L的语句。的语句。(5)条件转移语句)条件转移语句if x rop y goto L中,中,rop为关系运算符,为关系运算符,如果如果x和和y满足关系满足关系rop,就转而执行标号为,就转而执行标号为L的语句,否则的语句,否则顺序执行下一个语句。顺序执行下一个语句。2022-2-15292022-2-1529编编 译译 原原 理理2022年2月15日(6)过程调用语句)过程调用语句param x 和和call p , n。源程序中的过程。源程序中的过程调用语句调用语句p(x1,x2,xn)可以产生如下的三地址代码:可以产生如下的三地址代码:param x1param x2 param x
24、ncall p, n其中其中n为实参个数。过程返回语句形如为实参个数。过程返回语句形如return y,其中,其中y为为过程返回的一个值。过程返回的一个值。 2022-2-15302022-2-1530编编 译译 原原 理理2022年2月15日(7)变址赋值:)变址赋值:x= yi,把从,把从y开始的第开始的第i个存储单元的值赋给个存储单元的值赋给x。xi= y,把,把y的值赋给的值赋给x开始的第开始的第i个存储单元。个存储单元。其中,其中,x,y和和i都代表数据对象。都代表数据对象。(8)地址和指针赋值:)地址和指针赋值:x=&y,把,把y的地址赋给的地址赋给x。x= y,把,把y指
25、示的地址单元中的内容赋给指示的地址单元中的内容赋给x。 x = y,把,把x指向的存储单元的值置为指向的存储单元的值置为y。2022-2-15312022-2-1531编编 译译 原原 理理2022年2月15日2具体实现具体实现四元式四元式操作符操作符 操作数操作数1 操作数操作数2 结果结果结果:通常是由编译引进的临时变量结果:通常是由编译引进的临时变量例例: X=(A+B)*(C+D)-E+, A, B, T1+, C, D, T2*, T1, T2, T3-, T3, E, T4=, T4, 一一, XT1,T2,T3,T4为临时变量,为临时变量,由四元式优化比较方便由四元式优化比较方便
26、T1=A+BT2=C+DT3=T1+T2T4=T3-EX=T42022-2-15322022-2-1532编编 译译 原原 理理2022年2月15日操作符操作符 左操作符数左操作符数 右操作数右操作数 表达式的三元式:表达式的三元式:w*x+(y+z)(1) *, w, x(2) +, y, z(3) +, (1), (2) 第三个三元第三个三元式中的操作数式中的操作数(1)(2)表示第表示第(1)和第和第(2)条三元式的计条三元式的计算结果。算结果。三三元式元式2022-2-15332022-2-1533编编 译译 原原 理理2022年2月15日例:例: A=B+C*D/E F=C*D三元式
27、三元式(1) *, C, D(2) / , (1), E(3) +, B, (2) (4) =, A, (3)(5) *, C, D(6) =, F, (1)不便于代码优化:删不便于代码优化:删除某些三元式后可能除某些三元式后可能需作一系列的修改需作一系列的修改 三元式三元式(1) *, C, D(2) / , (1), E(3) +, B, (2) (4) =, A, (3)(5) =, F, (1)间接三元式间接三元式执行顺序执行顺序(1)(2)(3)(4)(1)(5)三元式的执行次序用另一张三元式的执行次序用另一张表表示表表示, 优化时三元式可以不优化时三元式可以不变,仅仅改变其执行顺序
28、表变,仅仅改变其执行顺序表2022-2-15342022-2-1534编编 译译 原原 理理2022年2月15日例:例:x = y +y z + y z 抽象语法树抽象语法树5.3.3 图形表示图形表示有向无环图有向无环图2022-2-15352022-2-1535编编 译译 原原 理理2022年2月15日5.95.9PL/0PL/0编译程序的语义分析编译程序的语义分析特点:将语义子程序嵌入到每个递归过程中特点:将语义子程序嵌入到每个递归过程中,通过递归子,通过递归子程序内部的局部量和参数传递语义信息。程序内部的局部量和参数传递语义信息。对于某个产生式,不必产生式右部所有符号扫描后再处理,对于
29、某个产生式,不必产生式右部所有符号扫描后再处理,可在处理一个符号后,随时加进有关该符号的语义子程序。可在处理一个符号后,随时加进有关该符号的语义子程序。自顶向下语法制导翻译自顶向下语法制导翻译回忆回忆“4.7 PL/04.7 PL/0编译程序的语法分析编译程序的语法分析”(见第(见第4 4章讲义)章讲义)2022-2-15362022-2-1536编编 译译 原原 理理2022年2月15日 为 dx,tx 置初值,暂时将代码 code的下标指针 cx 值保存在 table 表中 N Y N N Y N Y 常量说明处理 sym=procsym? 在 table 表中登记过程名 变量说明处理 递
30、归调用 block, 参数 lev+1 测试 sym 是否为语句开始符? 出错 处理 在 table 表中返回过程体入口口 Y sym=constsym? sym=varsym? block 说明部说明部分分2022-2-15372022-2-1537编编 译译 原原 理理2022年2月15日Y Y N N N sym=procsym? 在 table 表中登记过程名 变量说明处理 递归调用 block, 参数 lev+1 取单词 getsym 测试 sym 是否为语句后跟符? 出错 处理 调用列目标程序函数 返回 测试 sym 是否为语句开始符? 出错 处理 在 table 表中返回过程体入
31、口口 生成开辟数据段指令:ini 0 a 调用语句处理函数 生成退出数据段指令: opr 0 0 Y 2022-2-15382022-2-1538编编 译译 原原 理理2022年2月15日5.9.1 说明部分的分析说明部分的分析 对每个过程的对每个过程的说明对象说明对象填写符号表填写符号表 具体要填写标识符的具体要填写标识符的名字、属性、所在层次和分名字、属性、所在层次和分配的相对位置配的相对位置等等 标识符的标识符的属性属性不同时,所需要填写的信息也有所不同时,所需要填写的信息也有所不同不同 符号表的填写是由符号表的填写是由enterenter函数来完成的函数来完成的2022-2-15392
32、022-2-1539编编 译译 原原 理理2022年2月15日enum objectconstant,variable,procedure; /枚举定义常量、变量和过程枚举定义常量、变量和过程enum object kind;struct table1/符号表为结构体型数据符号表为结构体型数据 char name AL; /标识符名字,最长为标识符名字,最长为AL,已定义为,已定义为10 enum object kind; /标识符名字的属性,为常量、变量或过程标识符名字的属性,为常量、变量或过程 int val,level,adr, size; struct table1 tableTXMA
33、X+1; /符号表用一维数组符号表用一维数组table来表示,最多有来表示,最多有TXMAX项,项,TXMAX已定义为已定义为1002022-2-15402022-2-1540编编 译译 原原 理理2022年2月15日const a=35const a=35,b=49b=49;var cvar c,d d,e e;procedure pprocedure p;var gvar g namename kind level/val adr size表格管理表格管理a a b b c c d d e e p p c co on ns st ta an nt t c co on ns st ta an
34、 nt t v va ar ri ia ab bl le e v va ar ri ia ab bl le e v va ar ri ia ab bl le e p pr ro oc ce ed du ur re e 3 35 5 4 49 9 l le ev v l le ev v l le ev v l le ev v d dx x d dx x+ +1 1 d dx x+ +2 2 4 4 g g v va ar ri ia ab bl le e l le ev v+ +1 1 d dx x 2022-2-15412022-2-1541编编 译译 原原 理理2022年2月15日变量定义语
35、句的处理变量定义语句的处理if(strcmp(sym,varsym)=0) getsym(); do vardeclaration( );/处理一个变量处理一个变量 while (strcmp(sym,comma)=0) getsym(); vardeclaration( ); if (strcmp(sym,semicolon)=0) getsym(); else error(5); while (strcmp(sym,ident)=0);2022-2-15422022-2-1542编编 译译 原原 理理2022年2月15日if(strcmp(sym,varsym)=0) /* 遇到变量说明符
36、号,处理变量说明遇到变量说明符号,处理变量说明 */ getsym(); do vardeclaration(); /* 处理一个变量处理一个变量 */ while (strcmp(sym,comma)=0) getsym(); vardeclaration(); if(strcmp(sym,semicolon)=0) getsym(); else error(5); /* 漏掉了漏掉了,或或; */ while (strcmp(sym,ident)=0); 变量定义语句的处理变量定义语句的处理变量说明部分变量说明部分-var-var标识符标识符 ,标识符,标识符 ; 2022-2-15432
37、022-2-1543编编 译译 原原 理理2022年2月15日变量定义语句的处理变量定义语句的处理void vardeclaration() if(strcmp(sym,ident)=0) enter(variable); /* 填写符号表填写符号表 */ getsym(); else error(4); /* var后应为标识符后应为标识符 */2022-2-15442022-2-1544编编 译译 原原 理理2022年2月15日void enter(enum object k)void enter(enum object k) tx=tx+1; / tx=tx+1; /* * 表的登记项目
38、增加表的登记项目增加 * */ / strcpy(,id); / strcpy(,id); /* * 记录标识符的名字记录标识符的名字 * */ / tabletx.kind=k; / tabletx.kind=k; /* * 标识符的种类(常量、变量或过程)标识符的种类(常量、变量或过程)* */ / switch(k) / switch(k) /* * 分类别登记符号表分类别登记符号表 * */ / case constant: / case constant: /* * 常量常量 * */ / if(numAMAX) if(numAMAX)
39、 error(31); / error(31); /* * 常数大于常数大于AMAX 2047 AMAX 2047 * */ / num=0; num=0; tabletx.val=num; / tabletx.val=num; /* * 登记常数的值登记常数的值 * */ / break; break; case variable: / case variable: /* * 变量变量 * */ / tabletx.level=lev; / tabletx.level=lev; /* * 登记变量的层次登记变量的层次 * */ / tabletx.adr=dx; / tabletx.adr=
40、dx; /* * 登记变量的地址登记变量的地址 * */ / dx+; dx+; break; break; case procedure: / case procedure: /* * 过程过程 * */ / tabletx.level=lev; / tabletx.level=lev; /* * 登记过程的层次登记过程的层次 * */ / break; break; 函数函数enterenter的实现的实现2022-2-15452022-2-1545编编 译译 原原 理理2022年2月15日5.9.2 过程体部分的分析过程体部分的分析 根据根据当前读入的符号当前读入的符号就可以立即断定它应
41、属于哪就可以立即断定它应属于哪一种语句,当语法正确时就生成相应语句功能的一种语句,当语法正确时就生成相应语句功能的目标代码。目标代码。 凡遇到凡遇到标识符标识符,都要调用,都要调用position函数查找符号表函数查找符号表 若该标识符已定义,则若该标识符已定义,则返回它在符号表中的位置返回它在符号表中的位置,并据,并据此取得有关属性信息,然后翻译生成相应的目标代码此取得有关属性信息,然后翻译生成相应的目标代码 若符号表中没有该标识符,则若符号表中没有该标识符,则返回返回0,表示出错,表示出错 注意查找符号表时是注意查找符号表时是从后向前查从后向前查 2022-2-15462022-2-154
42、6编编 译译 原原 理理2022年2月15日 if (strcmp(sym,beginsym)=0)if (strcmp(sym,beginsym)=0) getsym( ); getsym( ); statement(add(temp3,fsys),plev); statement(add(temp3,fsys),plev); while(in(sym,add(temp4,statbegsys)=1) while(in(sym,add(temp4,statbegsys)=1) if (strcmp(sym,semicolon)=0) getsym(); if (strcmp(sym,semi
43、colon)=0) getsym(); else error(10); else error(10); / /* *语句之间漏了语句之间漏了;* */ / statement(add(temp3,fsys),plev); statement(add(temp3,fsys),plev); if (strcmp(sym,endsym)=0) if (strcmp(sym,endsym)=0) getsym(); getsym(); else error(17); else error(17); / /* *丢了丢了endend或或;* */ / := begin := begin;endend20
44、22-2-15472022-2-1547编编 译译 原原 理理2022年2月15日 if (strcmp(sym,ident)=0)if (strcmp(sym,ident)=0) i=position(id); i=position(id); if(i=0)error(ll); if(i=0)error(ll); / /* *标识符未说明标识符未说明* */ / else if(tablei.kind!=variable) else if(tablei.kind!=variable) error(12); error(12); / /* *赋值语句中赋值语句中, , 赋值号左部标识符属性应是
45、变量赋值号左部标识符属性应是变量* */ / i=0; i=0; getsym(); getsym(); if (strcmp(sym,becomes)=0) getsym(); if (strcmp(sym,becomes)=0) getsym(); else error(13); else error(13); / /* *赋值语句左部标识符后应是赋值号赋值语句左部标识符后应是赋值号:=:=* */ / expression(fsys); expression(fsys); if (i!=0) if (i!=0) gen(sto,plev-tablei.level,tablei.adr);
46、gen(sto,plev-tablei.level,tablei.adr); / /* *将栈顶内容送入某变量单元中将栈顶内容送入某变量单元中* */ / := := :=:= 2022-2-15482022-2-1548编编 译译 原原 理理2022年2月15日 if(strcmp(sym,readsym)=0)if(strcmp(sym,readsym)=0) getsym(); getsym(); if (strcmp(sym,lparen)!=0) error(24); if (strcmp(sym,lparen)!=0) error(24); else else do do gets
47、ym(); getsym(); if (strcmp(sym,ident)=0) i=position(id); if (strcmp(sym,ident)=0) i=position(id); else i=0; else i=0; if (i=0) error( if (i=0) error(3232);); else else gen(opr,0,16);gen(opr,0,16);/ /* *从命令行读入一个输入置于栈顶从命令行读入一个输入置于栈顶* */ / gen(sto,plev-tablei.level,tablei.adr);gen(sto,plev-tablei.level
48、,tablei.adr); / /* *将栈顶内容送入某变量单元中将栈顶内容送入某变量单元中* */ / getsym(); getsym(); while(strcmp(sym,comma)=0); while(strcmp(sym,comma)=0); if (strcmp(sym,rparen)!=0) if (strcmp(sym,rparen)!=0) error(22); error(22);while(in (sym,fsys)=0) getsym(); while(in (sym,fsys)=0) getsym(); else getsym(); else getsym();
49、=read(=read(, )2022-2-15492022-2-1549编编 译译 原原 理理2022年2月15日5.9.3 PL/0编译程序目标代码的结构编译程序目标代码的结构 目标代码目标代码pcodepcode是一种假想栈式计算机的是一种假想栈式计算机的汇编语言。汇编语言。 指令格式:指令格式:f l af l af f功能码功能码l l层次差层次差a a根据不同的指令有所区别根据不同的指令有所区别2022-2-15502022-2-1550编编 译译 原原 理理2022年2月15日struct instruction /* 目标代码的结构目标代码的结构 */ enum fct f;
50、int l; int a; struct instruction codeCXMAX+1; /* 记录所生成的目标代码记录所生成的目标代码 */2022-2-15512022-2-1551编编 译译 原原 理理2022年2月15日f flainiini0 0常常 量量litlit0 常常 量量 lodlod层次差层次差 数据地址数据地址 stosto层次差层次差 数据地址数据地址 calcal层次差层次差 程序地址程序地址 jmpjmp0 0程序地址程序地址 jpcjpc0 0程序地址程序地址 opropr0 0运算类别运算类别 8 8条目标指令条目标指令层次差层次差为变量名或过程名引用和声明
51、之间的静态层次差为变量名或过程名引用和声明之间的静态层次差程序地址程序地址为目标数组为目标数组codecode的下标的下标数据地址数据地址为变量在局部存贮中的相对地址为变量在局部存贮中的相对地址2022-2-15522022-2-1552编编 译译 原原 理理2022年2月15日23条指令详解条指令详解根据上面的解释去理解函数根据上面的解释去理解函数interpret( )2022-2-15532022-2-1553编编 译译 原原 理理2022年2月15日5.9.4 PL/0编译程序目标代码的生成编译程序目标代码的生成 PL/0PL/0语言的代码生成是由函数语言的代码生成是由函数gengen
52、完成。完成。 gengen有三个参数,分别代表目标代码的功有三个参数,分别代表目标代码的功能码,层差和位移量。能码,层差和位移量。gen(opr,0,16); gen(sto,lev-level,adr)gen(opr,0,16); gen(sto,lev-level,adr) 生成的代码顺序放在数组生成的代码顺序放在数组codecode中中codecode为一维数组,数组元素为结构体型数为一维数组,数组元素为结构体型数据。每个元素就是一条目标指令。据。每个元素就是一条目标指令。cxcx为指令为指令的指针,由的指针,由0 0开始顺序增加开始顺序增加目标代码的顺序是内层过程的在前边,主目标代码的
53、顺序是内层过程的在前边,主程序的目标代码在最后程序的目标代码在最后2022-2-15542022-2-1554编编 译译 原原 理理2022年2月15日void gen(x,y,z)void gen(x,y,z)enum fct x;enum fct x;int y,z;int y,z; if (cxCXMAX)if (cxCXMAX) printf(program too long); printf(program too long); codecx.f=x;codecx.f=x;codecx.l=y;codecx.l=y;codecx.a=z;codecx.a=z;cx+;cx+; 代码生
54、成的实现代码生成的实现2022-2-15552022-2-1555编编 译译 原原 理理2022年2月15日代码生成的规则代码生成的规则(1)每个过程开始前,生成)每个过程开始前,生成1条条jmp 0 0指令,若连续嵌套说明几个过程,指令,若连续嵌套说明几个过程,则连续生成几条则连续生成几条jmp 0 0指令。这条指令的含义是可以跳转到相应的过程,指令。这条指令的含义是可以跳转到相应的过程,其中跳转地址是在此过程的目标代码生成后,再进行回填。其中跳转地址是在此过程的目标代码生成后,再进行回填。(2)进入每个过程后,首先生成一条)进入每个过程后,首先生成一条ini 0 a指令(指令(a=局部变量
55、数局部变量数+3),其),其含义是在数据栈中为被调用的过程开辟含义是在数据栈中为被调用的过程开辟a个单元的数据区。个单元的数据区。(3)一个过程结束后,生成一条)一个过程结束后,生成一条opr 0 0指令,表明返回调用点。指令,表明返回调用点。(4)在语句中遇到常量(不论是常数还是常量标识符)时,生成一条)在语句中遇到常量(不论是常数还是常量标识符)时,生成一条lit 0 a指令(指令(a=常量值),其含义是将常量值置于数据栈的栈顶。这条指令是在常量值),其含义是将常量值置于数据栈的栈顶。这条指令是在factor函数中生成的。函数中生成的。(5)在语句中遇到变量时,生成一条)在语句中遇到变量时
56、,生成一条lod lev-level adr指令,其中,指令,其中,lev是该是该语句所在过程段的层次,语句所在过程段的层次, level是变量说明的层次,是变量说明的层次, adr是变量的相对地址。是变量的相对地址。这条指令也是在这条指令也是在factor函数中生成的。函数中生成的。(6)有关表达式及各种语句的翻译规则见下面的详细解释。)有关表达式及各种语句的翻译规则见下面的详细解释。 2022-2-15562022-2-1556编编 译译 原原 理理2022年2月15日表达式的翻译表达式的翻译 算术表达式算术表达式条件表达式条件表达式后缀式后缀式Y op ZY Z opNo.No.f fl
57、a100100lodlodY Y层次差层次差Y Y相对地址相对地址101101lodlodZ Z层次差层次差Z Z相对地址相对地址102102opropr-OP OP 2022-2-15572022-2-1557编编 译译 原原 理理2022年2月15日opr 0 1栈顶元素取反栈顶元素取反opr 0 2次栈顶与栈顶相加,退两个栈元素,相加次栈顶与栈顶相加,退两个栈元素,相加值进栈值进栈opr 0 3次栈顶减去栈顶次栈顶减去栈顶opr 0 4次栈顶乘以栈顶次栈顶乘以栈顶opr 0 5次栈顶除以栈顶次栈顶除以栈顶opr 0 6栈顶元素的奇偶判断栈顶元素的奇偶判断opr 0 8次栈顶与栈顶是否相等
58、次栈顶与栈顶是否相等opr 0 9次栈顶与栈顶是否不等次栈顶与栈顶是否不等opr 0 10次栈顶是否小于栈顶次栈顶是否小于栈顶opr 0 11次栈顶是否大于等于栈顶次栈顶是否大于等于栈顶opr 0 12次栈顶是否大于栈顶次栈顶是否大于栈顶opr 0 13次栈顶是否小于等于栈顶次栈顶是否小于等于栈顶2022-2-15582022-2-1558编编 译译 原原 理理2022年2月15日将将T(ident“=” expression)依次翻译成:依次翻译成:T(expression)sto l a (将栈顶元素值赋给层差为将栈顶元素值赋给层差为l、相对位置为、相对位置为a的变量的变量即即ident)
59、No.No.f fla100100lodlodY Y层次差层次差Y Y相对地址相对地址101101lodlodZ Z层次差层次差Z Z相对地址相对地址102102opropr-OP OP 103103stostoX X层次差层次差 X X相对地址相对地址赋值语句的翻译赋值语句的翻译 X := Y op Z2022-2-15592022-2-1559编编 译译 原原 理理2022年2月15日将将T(“read” “(” ident ”)” )翻译成:翻译成:opr 0 16(先读入一个数据置于栈顶)(先读入一个数据置于栈顶)sto l a(将栈顶元素即刚读入的数据出栈,值赋给层(将栈顶元素即刚读
60、入的数据出栈,值赋给层差为差为l、相对位置为、相对位置为a的变量)的变量)read、write语句的翻译语句的翻译 将将T(“write” “(” ident ”)” )翻译成:翻译成:opr 0 14(输出栈顶的数据)(输出栈顶的数据)opr 0 15 (输出一个换行符)(输出一个换行符)2022-2-15602022-2-1560编编 译译 原原 理理2022年2月15日将将T(“call” ident )翻译成:翻译成:call l al是过程调用层和过程定义层的差值,用来计算出被是过程调用层和过程定义层的差值,用来计算出被调用过程在数据栈对应的过程段的静态链接地址调用过程在数据栈对应的过程段的
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 赣州职业技术学院《民用航空法》2023-2024学年第一学期期末试卷
- 赣西科技职业学院《医学检验进展(二)》2023-2024学年第一学期期末试卷
- 赣南科技学院《心理咨询与身心健康》2023-2024学年第一学期期末试卷
- 赣东学院《传染科护理学》2023-2024学年第一学期期末试卷
- 法警安全检查课件
- 中心对称图片课件
- 七年级语文上册第五单元18狼课后习题新人教版
- 三年级品德与社会下册第一单元在爱的阳光下第二课读懂爸爸妈妈的心教案新人教版
- 三年级科学上册第四单元人与水教材说明首师大版
- 2021一建考试《建设工程项目管理》题库试卷考点题库及参考答案解析五
- 商业定价表(含各商铺价格测算销售回款)
- 【化学】重庆市2021-2022学年高一上学期期末联合检测试题
- 单位工程质量控制程序流程图
- 化学工业有毒有害作业工种范围表
- 统编版小学四年级语文上册五六单元测试卷(附答案)
- 商票保贴协议
- 高支模技术交底(新版)
- TOP-DOWN培训
- 电动力学答案完整
- 弱电工程保修书(共4页)
- 项目合伙人管理制度
评论
0/150
提交评论