汇编语言中间代码生成_第1页
汇编语言中间代码生成_第2页
汇编语言中间代码生成_第3页
汇编语言中间代码生成_第4页
汇编语言中间代码生成_第5页
已阅读5页,还剩121页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

第七章中间代码生成本章内容介绍几种常用的中间表示:后缀表示、图形表示和三地址代码用语法制导定义和翻译方案的方法来说明程序设计语言的结构怎样被翻译成中间形式分析器静态检查器中间代码生成器中间代码记号流代码生成器7.1

中间语言7.1.1后缀表示表达式E的后缀表示可以如下归纳定义如果E是变量或常数,那么E的后缀表示就是E本身。7.1

中间语言7.1.1后缀表示表达式E的后缀表示可以如下归纳定义如果E是变量或常数,那么E的后缀表示就是E本身。如果E是形式为E1opE2的表达式,那么E的后缀表示是E1E2

op,其中E1和E2分别是E1和E2的后缀表示。7.1

中间语言7.1.1后缀表示表达式E的后缀表示可以如下归纳定义如果E是变量或常数,那么E的后缀表示就是E本身。如果E是形式为E1opE2的表达式,那么E的后缀表示是E1E2

op,其中E1和E2分别是E1和E2的后缀表示。如果E是形式为(E1)的表达式,那么E1的后缀表示也是E的后缀表示。

7.1

中间语言后缀表示不需要括号 (84)+2的后缀表示是842+

7.1

中间语言后缀表示不需要括号 (84)+2的后缀表示是842+

后缀表示的最大优点是便于计算机处理表达式7.1

中间语言后缀表示不需要括号 (84)+2的后缀表示是842+

后缀表示的最大优点是便于计算机处理表达式后缀表示很容易拓广到含一元算符的表达式7.1

中间语言后缀表示不需要括号 (84)+2的后缀表示是842+

后缀表示的最大优点是便于计算机处理表达式后缀表示很容易拓广到含一元算符的表达式后缀表示也可以拓广到表示赋值语句和控制语句,但很难用栈来描述它的计算7.1

中间语言7.1.2

图形表示语法树是一种图形化的中间表示

assigna++bcdcduminus(a)语法树

a=(b+cd)+cd的图形表示7.1

中间语言7.1.2

图形表示抽象语法树是一种图形化的中间表示有向无环图也是一种中间表示

assigna++bcdcduminusassigna++bcduminus(a)语法树(b)dag

a=(b+cd)+cd的图形表示7.1

中间语言构造赋值语句抽象语法树的语法制导定义 产

则Sid:=E

S.nptr=mknode(‘assign’,mkleaf(id,id.entry),E.nptr)E

E1+E2

E.nptr=mknode(‘+’,E1.nptr,E2.nptr)E

E1E2E.nptr=mknode(‘’,E1.nptr,E2.nptr)E

E1E.nptr=mkunode(‘uminus’,E1.nptr)E(E1)E.nptr=E1.nptr

FidE.nptr=mkleaf(id,id.entry)7.1

中间语言7.1.3三地址代码一般形式:x=yopz表达式x+y

z翻译成的三地址语句序列是t1=y

z

t2=x+t1

7.1

中间语言三地址代码是抽象语法树或dag的一种线性表示 a=(b+cd)+cd 抽象语法树的代码 t1=b

t2=c

d

t3=t1+t2

t4=c

d

t5=t3+t4

a=t5assigna++bcdcduminus7.1

中间语言三地址代码是语法树或dag的一种线性表示 a=(b+cd)+cd 语法树的代码 dag的代码 t1=b t1=b

t2=c

d t2=c

d

t3=t1+t2 t3=t1+t2

t4=c

d t4=t3+t2

t5=t3+t4 a=t4

a=t5assigna++bcduminus7.1

中间语言本书常用的三地址语句赋值语句x=yopz, x=opy, x=y无条件转移gotoL条件转移ifxrelop

ygotoL过程调用paramx

和callp,n过程返回

returny索引赋值x=y[i]和x[i]=y地址和指针赋值x=&y,x=y和x=y7.1

中间语言赋值语句生成三地址代码的属性文法产

则Sid:=E

S.code=E.code||gen(id.place‘=‘E.place)E

E1+E2

E

E1E27.1

中间语言赋值语句生成三地址代码的属性文法产

则Sid:=E

S.code=E.code||gen(id.place‘=‘E.place)E

E1+E2

E.Place=newtemp;E.Code=E1.code||E2.code||gen(E.place‘=‘E1.place‘+’E2.place)

E

E1E27.1

中间语言赋值语句生成三地址代码的属性文法产

则Sid:=E

S.code=E.code||gen(id.place‘=‘E.place)E

E1+E2

E.Place=newtemp;E.Code=E1.code||E2.code||gen(E.place‘=‘E1.place‘+’E2.place)

E

E1E2E.Place=newtemp;E.Code=E1.code||E2.code||gen(E.place‘=‘E1.place‘*’E2.place)7.1

中间语言赋值语句生成三地址代码的属性文法产

则E

E1E.Place=newtemp;E.Code=E1.code||gen(E.place‘=‘‘uminus’E1.place)E(E1)Eid7.1

中间语言赋值语句生成三地址代码的属性文法产

则E

E1E.Place=newtemp;E.Code=E1.code||gen(E.place‘=‘‘uminus’E1.place)E(E1)E.place=E1.place;E.Code=E1.code;Eid7.1

中间语言赋值语句生成三地址代码的属性文法产

则E

E1E.Place=newtemp;E.Code=E1.code||gen(E.place‘=‘‘uminus’E1.place)E(E1)E.place=E1.place;E.Code=E1.code;EidE.place=id.place;E.Code=‘’;7.1

中间语言三地址代码的具体表现形式:四元式三元式间接三元式7.1

中间语言四元式:a=b*-c+b*-coparg1arg2result(0)uminuscT1(1)*bT1T2(2)uminuscT3(3)*bT3T4(4)+T2T4T5(5)=T5a7.1

中间语言三元式:a=b*-c+b*-coparg1arg2(0)uminusc(1)*b(0)(2)uminusc(3)*b(2)(4)+(1)(3)(5)=a(4)7.1

中间语言间接三元式:a=b*-c+b*-coparg1arg2(0)uminusc(1)*b(0)(2)+(1)(1)(3)=a(2)间接代码表(0)(1)(0)(1)(2)(3)7.1

中间语言练习:将表达式:-(a+b)*((c+d)-(a+b+c))分别表示成:后缀式、抽象语法树、DAG、三元式、间接三元式、四元式7.2

声明语句为局部名字建立符号表条目为它分配存储单元符号表中包含名字的类型和分配给它的存储单元的相对地址等信息7.2

声明语句7.2.1

过程中的声明 例子: i:integer; j:real; k:array[10]ofreal; m:↑integer假设integer占4个字节,real占8个字节名称类型长度偏移符号表7.2

声明语句7.2.1

过程中的声明 例子: i:integer; j:real; k:array[10]ofreal; m:↑integer假设integer占4个字节,real占8个字节名称类型长度偏移iint40符号表7.2

声明语句7.2.1

过程中的声明 例子: i:integer; j:real; k:array[10]ofreal; m:↑integer假设integer占4个字节,real占8个字节名称类型长度偏移iint40jreal84符号表7.2

声明语句7.2.1

过程中的声明 例子: i:integer; j:real; k:array[10]ofreal; m:↑integer假设integer占4个字节,real占8个字节名称类型长度偏移iint40jreal84karray(10,real)8012符号表7.2

声明语句7.2.1

过程中的声明 例子: i:integer; j:real; k:array[10]ofreal; m:↑integer假设integer占4个字节,real占8个字节名称类型长度偏移iint40jreal84karray(10,real)8012mpointer(integer)492符号表7.2

声明语句计算被声明名字的类型和相对地址P {offset=0} DSD

D;D

Did:T {enter(,T.type,offset); offset=offset+T.width}Tinteger {T.type=integer;T.width=4}Treal{T.type=real;T.width=8}Tarray[num]ofT1 {T.type=array(num.val,T1.type);

T.width=num.val

T1.width}T

T1{T.type=pointer(T1.type);T.width=4}7.2

声明语句7.2.2作用域信息的保存所讨论语言的文法 P

DS DD;D|id:T|procid;D;S语义动作用到的函数mktable(previous)enter(table,name,type,offset)

addwidth(table,width)enterproc(table,name,newtable)7.2

声明语句Programsort(input,output) vara:array[0..10]ofinteger; x:integer; procedurereadarray; vari:integer; begin...a…end{readarray}; procedureexchange(i,j:integer); begin x:=a[i];a[i]:=a[j];a[j]:=x end{exchange};7.2

声明语句 procedurequicksort(m,n:integer); vark,v:integer; functionpartition(y,z:integer):integer; vari,j:integer; begin…a… …v… …exchange(i,j);… end{partition}; begin…end{quicksort};begin…end{sort}.7.2

声明语句嵌套关系sortreadarrayexchangepartition Sort当中定义了数组a,readarray中需要使用这一变量,应该如何去组织符号表呢?7.2

声明语句exchangereadarrayxa表头空sortquicksort指向readarraypartitionvk表头quicksortreadarrayi表头exchange表头指向exchangepartition7.2

声明语句P

MDS

{addwidth(top(tblptr),top(offset));

pop(tblptr);pop(offset)}M

{t=mktable(nil); push(t,tblprt);push(0,offset)}D

D1;D2Dprocid;ND1;S{t=top(tblptr);addwidth(t,top(offset));pop(tblptr);pop(offset); enterproc(top(tblptr),,t)}Did:T{enter(top(tblptr),,T.type,top(offset)); top(offset)=top(offset)+T.width}N

{t=mktable(top(tblptr)); push(t,tblptr);push(0,offset)}7.2

声明语句7.2.3

记录的域名TrecordDendTrecordL

Dend {T.type=record(top(tblptr)); T.width=top(offset); pop(tblptr);pop(offset)}L

{t=mktable(nil); push(t,tblptr);push(0,offset)}7.3

赋值语句a=(b+cd)+cd 三地址代码 t1=b

t2=c

d

t3=t1+t2

t4=c

d

t5=t3+t4

a=t5 四元式 0 (@,b,-,t1)1(*,c,d,t2)2(+,t1,t2,t3)3(*,c,d,t4)4(+,t3,t4,t5)5(=,t5,-,a)7.3

赋值语句7.3.1赋值语句的翻译模式Sid:=E {p=lookup(id.lexeme); ifp!=

nilthen emit(p,‘=’,E.place) elseerror}E

E1+E2

{E.place=newtemp;

emit(E.place,‘=’,E1.place,‘+’,E2.place)}7.3

赋值语句7.3.1赋值语句的翻译模式E

E1{E.place=newtemp; emit(E.place,‘=’,‘uminus’,E1.place)}E(E1){E.place=E1.place}Eid{p=lookup(id.lexeme); ifp!=

nilthenE.place=pelseerror}7.3

赋值语句7.3.2临时名字的重新使用大量临时变量的使用对优化有利大量临时变量会增加符号表管理的负担也会增加运行时临时数据占的空间7.3

赋值语句7.3.2临时名字的重新使用大量临时变量的使用对优化有利大量临时变量会增加符号表管理的负担也会增加运行时临时数据占的空间E

E1+E2的动作产生的代码的一般形式为

计算E1到t1

计算E2到t2

t3=t1

+t2 (())((()())())临时变量的生存期像配对括号那样嵌套或并列7.3

赋值语句基于临时变量生成期特征的三地址代码x=ab+cdef语

c的值

0$0=ab1$1=cd2$0=$0+$11

$1=ef2$0=$0$11x=$007.3

赋值语句数组的翻译:一维数组二维数组三维数组多维数组7.3

赋值语句7.3.3数组元素的地址计算一维数组A的第i个元素的地址计算

base+(i

low)

w7.3

赋值语句7.3.3数组元素的地址计算一维数组A的第i个元素的地址计算

base+(i

low)

w

重写成

(base

low

w)+i

w基址变址二维数组的翻译二维a[i1,i2]的维数d1*d2D=a+d2(i1–1)+i2–1=a–(d2+1)+i1d2+i2=Conspart+Varpart对D的四元式翻译 *,i1,d2,T1 +,T1,i2,T2 -,a,c,T3所以A[i1,i2]的地址D=T3[T2]三维A[i1,i2,i3]的维数d1*d2*d3i1i2i3d2d3d1D=a+d2d3(i1–1)+d3(i2-1)+i3–1=a–(d2d3+d3+1)+(i1d2d3+i2d3+i3)=Conspart+Varpart对D的四元式翻译 *,i1,d2,T1 +,T1,i2,T2 *,T2,d3,T3 +,T3,i3,T4 -,a,c,T5所以A[i1,i2,i3]的地址D=T5[T4]VarpartConspart7.3

赋值语句总结:对于所有的数组A[i1,i3,i3,…]来讲,数组的地址都可以概括成A-C+V的格式,其中A是数组的首地址,C是编译时可以预先确定的常数,V根据下标的变化而变化。一维:C=1×w,V=i1×w二维:C=(d2+1)×w,V=(i1d2+i2)×w三维:C=(d2d3+d3+1)×w =(((d2+1)×d3)+1)×w7.3

赋值语句三维:V=(i1d2d3+i2d3+i3)×w =(((i1d2+i2)×d3)

+i3))×w多维:C=((…(((d2+1)×d3)+1)…)dn+1)×w V=((…(((i1d2+i2)×d3)+i3)…)dn+in)×w7.3

赋值语句7.3.4数组元素地址计算的翻译方案下标变量访问的产生式

Lid[Elist]|id Elist

Elist,E|E改成

L

Elist]|id Elist

Elist,E|id[E7.3

赋值语句所有产生式S

L:=EE

E+EE(E)E

LL

Elist]LidElist

Elist,EElist

id[E7.3

赋值语句Lid{L.place=id.place;L.offset=null}7.3

赋值语句Lid{L.place=id.place;L.offset=null}Elist

id[E{Elist.place=E.place;Elist.ndim=1; Elist.array=id.place}7.3

赋值语句Lid{L.place=id.place;L.offset=null}Elist

id[E{Elist.place=E.place;Elist.ndim=1; Elist.array=id.place}Elist

Elist1,E{t=newtemp;m=Elist1.ndim+1;

emit(t,‘=’,Elist1.place,‘’,limit(Elist1.array,m));

emit(t,‘=’,t,‘+’,E.place);

Elist.array=Elist1.array;

Elist.place=t;Elist.ndim=m}7.3

赋值语句Lid{L.place=id.place;L.offset=null}Elist

id[E{Elist.place=E.place;Elist.ndim=1; Elist.array=id.place}Elist

Elist1,E{t=newtemp;m=Elist1.ndim+1;

emit(t,‘=’,Elist1.place,‘’,limit(Elist1.array,m));

emit(t,‘=’,t,‘+’,E.place);

Elist.array=Elist1.array;

Elist.place=t;Elist.ndim=m}L

Elist] {L.place=newtemp;emit(L.place,‘=’,base(Elist.array),‘’, invariant(Elist.array));L.offset=newtemp;emit(L.offset,‘=’,Elist.place,‘’,w)}7.3

赋值语句E

L{ifL.offset==nullthen/

L是简单变量

/

E.place=L.place

elsebeginE.place=newtemp;

emit(E.place,‘=’,L.place,‘[’,L.offset,‘]’)end}7.3

赋值语句E

L{ifL.offset==nullthen/

L是简单变量

/

E.place=L.place

elsebeginE.place=newtemp;

emit(E.place,‘=’,L.place,‘[’,L.offset,‘]’)end}E

E1+E2{E.place=newtemp; emit(E.place,‘=’,E1.place,‘+’,E2.place)}7.3

赋值语句E

L{ifL.offset==nullthen/

L是简单变量

/

E.place=L.place

elsebeginE.place=newtemp;

emit(E.place,‘=’,L.place,‘[’,L.offset,‘]’)end}E

E1+E2{E.place=newtemp; emit(E.place,‘=’,E1.place,‘+’,E2.place)}E(E1){E.place=E1.place}

7.3

赋值语句E

L{ifL.offset==nullthen/

L是简单变量

/

E.place=L.place

elsebeginE.place=newtemp;

emit(E.place,‘=’,L.place,‘[’,L.offset,‘]’)end}E

E1+E2{E.place=newtemp; emit(E.place,‘=’,E1.place,‘+’,E2.place)}E(E1){E.place=E1.place}S

L=E {ifL.offset==nullthen/

L是简单变量/

emit(L.place,‘=’,E.place) else

emit(L.place,‘[’,L.offset,‘]’,‘=’, E.place)}

7.3

赋值语句例题:设A为一个10×20的数组,即d1=10,d2=20,并设w=4,试对赋值语句x=A[y,z]进行翻译。假设数组的下标从1开始。7.3

赋值语句S:=L.place=xL.offset=nullxE.place=t4L.place=t2L.offset=t3Elist.place=t1Elist.ndim=2Elist.array=A,Elist.place=yElist.ndim=1Elist.array=AE.place=zL.place=zL.offset=nullE.place=yL.place=yL.offset=nullA[z]y

x:=A[y,z]的注释分析树7.3

赋值语句S:=L.place=xL.offset=nullxE.place=t4L.place=t2L.offset=t3Elist.place=t1Elist.ndim=2Elist.array=A,Elist.place=yElist.ndim=1Elist.array=AE.place=zL.place=zL.offset=nullE.place=yL.place=yL.offset=nullA[z]y

x:=A[y,z]的注释分析树t1=y20t1=t1+z

7.3

赋值语句S:=L.place=xL.offset=nullxE.place=t4L.place=t2L.offset=t3Elist.place=t1Elist.ndim=2Elist.array=A,Elist.place=yElist.ndim=1Elist.array=AE.place=zL.place=zL.offset=nullE.place=yL.place=yL.offset=nullA[z]y

x:=A[y,z]的注释分析树t1=y20t1=t1+z

t2=A84t3=4t1

7.3

赋值语句S:=L.place=xL.offset=nullxE.place=t4L.place=t2L.offset=t3Elist.place=t1Elist.ndim=2Elist.array=A,Elist.place=yElist.ndim=1Elist.array=AE.place=zL.place=zL.offset=nullE.place=yL.place=yL.offset=nullA[z]y

x:=A[y,z]的注释分析树t1=y20t1=t1+z

t2=A84t3=4t1

t4=t2[t3]7.3

赋值语句S:=L.place=xL.offset=nullxE.place=t4L.place=t2L.offset=t3Elist.place=t1Elist.ndim=2Elist.array=A,Elist.place=yElist.ndim=1Elist.array=AE.place=zL.place=zL.offset=nullE.place=yL.place=yL.offset=nullA[z]y

x:=A[y,z]的注释分析树t1=y20t1=t1+z

t2=A84t3=4t1

t4=t2[t3]x=t4

7.3

赋值语句T1=y×20T1=T1+zT2=A-84T3=4*T1T4=T2[T3]X=T4T1=y×20T2=T1+zT3=A-84T4=4*T1T5=T3[T4]X=T57.3

赋值语句7.3.5类型转换x=y+ij(x和y的类型是real,i和j的类型是integer)中间代码t1=iintjt2=inttorealt1

t3=yreal+t2

x=t37.3

赋值语句E

E1+E2E.place=newtempifE1.type==integer&&E2.type==integerthenbegin

emit(E.place,‘=’,E1.place,‘int+’,E2.place);

E.type=integerendelseifE1.type==integer&&E2.type==realthenbegin u=newtemp; emit(u,‘=’,‘inttoreal’,E1.place); emit(E.place,‘=’,u,

‘real+’,E2.place); E.type=realend...7.4

布尔表达式和控制流语句布尔表达式有两个基本目的计算逻辑值在控制流语句中用作条件表达式7.4

布尔表达式和控制流语句布尔表达式有两个基本目的计算逻辑值在控制流语句中用作条件表达式布尔表达式的完全计算布尔表达式的“短路”计算E1orE2定义成ifE1thentrueelseE2E1andE2定义成

ifE1thenE2elsefalse7.4

布尔表达式和控制流语句7.4.1布尔表达式的翻译E

E

orE|EandE|notE|(E) |idrelopid|true|falsea<b的翻译100:ifa<bgoto103101:t=0102:goto104103:t=1104:7.4

布尔表达式和控制流语句7.4.2控制流语句的翻译SifEthenS1 |ifEthenS1

elseS2 |whileEdoS1 |S1;S2

7.4

布尔表达式和控制流语句E.codeS1.codeE.true:...指向E.true指向E.false(a)if-thenE.codeS1.codeE.true:...指向E.true指向E.falseE.false:gotoS.nextS2.code(b)if-then-elseE.codeS1.codeE.true:...指向E.true指向E.falsegotoS.beginS.begin:(c)while-doS1.codeS2.codeS1.next:...(d)S1;S27.4

布尔表达式和控制流语句布尔表达式翻译用到的三种四元式结构(jnz,a,-,p) ifagotop(jrop,x,y,p) ifxropygotop(j,-,-,p) gotop7.4

布尔表达式和控制流语句布尔表达式的翻译规则先顺序翻译布尔变量和关系表达式,暂时不管布尔运算符号(not,and,or等)。其中,每一个布尔变量和关系表达式对应两条四元式,第一条是有条件跳转,第二条是无条件跳转。最后一个域即跳转到何处暂时不填,等到全部完成后再填。7.4

布尔表达式和控制流语句对于布尔变量A可以翻译成: (1) (jnz,A,-,-) (2)(j,-,-,-)对于关系表达式AropB (1) (jrop,

A,B,-) (2)(j,-,-,-)7.4

布尔表达式和控制流语句举例:IfAor(B<D)thens1elses27.4

布尔表达式和控制流语句举例:IfAor(B<D)thens1elses2(jnz,A,-,-)(j,-,-,-)(j<,B,D,-)(j,-,-,-)S1的四元式序列(j,-,-,-)(p+1)S2的四元式序列(q)7.4

布尔表达式和控制流语句举例:IfAor(B<D)thens1elses2(jnz,A,-,5)(j,-,-,3)(j<,B,D,5)(j,-,-,p+1)S1的四元式序列(j,-,-,q)(p+1)S2的四元式序列(q)选择结构的翻译模版IfEthenS1elseS2ES1S2100E.FalseE.Truep(j,_,_p)7.4

布尔表达式和控制流语句条件语句翻译举例Ifx>0theny=x+1elsey=x+27.4

布尔表达式和控制流语句Ifx>0theny=x+1elsey=x+2100 (j>,x,0,-)101 (j,-,-,-)102 (+,x,1,t1)103 (=,t1,-,y)104 (j,-,-,-)105 (+,x,2,t2)106 (=,t2,-,y)1077.4

布尔表达式和控制流语句Ifx>0theny=x+1elsey=x+2100 (j>,x,0,102)101 (j,-,-,105)102 (+,x,1,t1)103 (=,t1,-,y)104 (j,-,-,107)105 (+,x,2,t2)106 (=,t2,-,y)1077.4

布尔表达式和控制流语句练习:Ifnotaor(c<d)theny=x+1elsey=x+2循环结构的翻译模版DoEwhileSES

P(j,_,_,100)

P+1()100E.TCE.FC7.4

布尔表达式和控制流语句循环语句的翻译While(A<B)doIf(C>D)thenx=y+z;7.4

布尔表达式和控制流语句While(A<B)doIf(C>D)thenx=y+z;(j<,A,B,-)101(j,-,-,-)102(j>,C,D,-)103(j,-,-,-)104(+,y,z,t1)105(=,t1,-,x)106(j,-,-,100) 7.4

布尔表达式和控制流语句While(A<B)doIf(C>D)thenx=y+z;(j<,A,B,102)101(j,-,-,107)102(j>,C,D,104)103(j,-,-,100)104(+,y,z,t1)105(=,t1,-,x)106(j,-,-,100) 7.4

布尔表达式和控制流语句练习:While(iorj)and(j>5)do i=j7.4

布尔表达式和控制流语句布尔表达式的语法制导翻译(1)E->E1orME2{Backpatch(E1.falselist,M.quad);E.Truelist=merge(E1.truelist,E2.truelist);E.Falselist=E2.falselist;}7.4

布尔表达式和控制流语句(2)E->E1andME2{Backpatch(E1.truelist,M.quad);E.truelist=E2.truelist;E.falselist=merge(E1.falselist,E2.falselist);}7.4

布尔表达式和控制流语句(3)E->notE1{E.truelist=E1.falselist;E.falselist=E1.truelist;}(4)E->(E1){E.truelist=E1.truelist;E.Falselist=E1.falselist;}7.4

布尔表达式和控制流语句(5)E->id1relopid2{E.truelist=makelist(nextquad);E.falselist=makelist(nextquad+1);Emit(‘j’relop.op‘,’id1.place‘,’id2.place,‘,’‘0’);Emit(‘j,-,-,0’);}7.4

布尔表达式和控制流语句(6)E->id{E.truelist=makelist(nextquad);E.falselist=makelist(nextquad+1);Emit(‘jnz’‘,’id.place‘,’‘-’,‘,’‘0’);Emit(‘j,-,-,0’);}(7)M->ε{M.quad=nextquad;}7.4

布尔表达式和控制流语句布尔表达式的语法制导翻译举例a<borc<dande<forE.tc=100E.fc=101a<bE.tc=104E.fc={103,105}E.tc=102E.fc=103a<borc<dande<f的注释分析树M.q=102εc<dandM.q=104εE.tc=104E.fc=105e<fE.tc={100,104}E.fc={10.,105}7.4

布尔表达式和控制流语句布尔表达式的语法制导翻译举例a<borc<dande<f100(j<,a,b,0)101(j,-,-,102)102(j<,c,d,104)103(j,-,-,0)104(j<,e,f,0)105(j,-,-,0)7.4

布尔表达式和控制流语句控制语句的语法制导翻译(1)S->ifEthenM1S1NelseM2S2{Backpatch(E.truelist,M1.quad);Backpatch(E.falselist,M2.quad);S.Nextlist=merge(S1.nextlist,N.nextlist,S2.nextlist)}7.4

布尔表达式和控制流语句(2)N->ε{N.nextlist=makelist(nextquad);Emit(‘j,-,-,-’)}(3)M->ε{M.quad=nextquad;Backpatch(E.truelist,M.quad)}7.4

布尔表达式和控制流语句(4)S->ifEthenMS1{backpatch(E.truelist,M.quad);S.Nextlist=merge(E.falselist,S1.nextlist);}7.4

布尔表达式和控制流语句(5)S->whileM1EdoM2S2{backpatch(S1.nextlist,M1.quad);Backpatch(E.truelist,M2.quad);S.Nextlist=E.falselist;Emit(‘j,-,-,’M1.quad);}7.4

布尔表达式和控制流语句(6)S->beginLend{S.nextlist=L.nextlist}(7)S->A{S.nextlist=makelist()}(8)L->L1;MS{backpatch(L1.nextlist,M.quad);L.Nextlist=S.nextlist}(9)L->S{L.nextlist=S.nextlist}7.4

布尔表达式和控制流语句7.4.4开关语句的翻译switchE begin caseV1:S1 caseV2:S2 ... caseVn-1:Sn–1 default:Sn end7.4

布尔表达式和控制流语句分支数较少时 t=E的代码 |Ln-2:ift!=

Vn-1gotoLn-1

ift!=

V1gotoL1| Sn-1的代码

S1的代码 | gotonext gotonext |Ln-1:Sn的代码

L1: ift!=

V2gotoL2|next: S2的代码 gotonextL2: ... ...7.4

布尔表达式和控制流语句分支较多时,将分支测试的代码集中在一起,便于生成较好的分支测试代码。 t=E的代码 |Ln: Sn的代码 gototest

| gotonext

L1: S1的代码 |test:ift==V1gotoL1

gotonext | ift==V2gotoL2

L2: S2的代码

| ...

gotonext | ift==Vn-1gotoLn-1 ... | gotoLnLn-1: Sn-1的代码

|next:

gotonext7.4

布尔表达式和控制流语句中间代码增加一种case语句,便于代码生成器对它进行特别处理test: caseV1 L1 caseV2 L2 ... caseVn-1 Ln-1 caset Ln

next:7.4

布尔表达式和控制流语句7.4.5

过程调用的翻译Scallid(Elist)Elist

Elist,EElist

E7.4

布尔表达式和控制流语句过程调用id(E1,E2,…,En)的中间代码结构E1.place=E1的

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论