收藏 分享(赏)

编译第一章32585.ppt

上传人:tkhy51908 文档编号:9598608 上传时间:2019-08-17 格式:PPT 页数:52 大小:464.50KB
下载 相关 举报
编译第一章32585.ppt_第1页
第1页 / 共52页
编译第一章32585.ppt_第2页
第2页 / 共52页
编译第一章32585.ppt_第3页
第3页 / 共52页
编译第一章32585.ppt_第4页
第4页 / 共52页
编译第一章32585.ppt_第5页
第5页 / 共52页
点击查看更多>>
资源描述

1、编译原理,黄金城 ,课程的性质:,通过本课程我们主要学习编译程序构造的一般原理,基本设计方法,主要实现技术。编译程序构造的基本原理和技术广泛用于一般软件的设计和实现,本课程也可作为从事系统软件和软件工具研究与开发的参考。,课程架构:,1 理论和实践并重的课程 2 理论部分的题目出现于书面练习和期末考试 3 实验 4个 4 各部分权重 平时出勤和作业10% 实验出勤、实验表现及实验报告20% 期末考试 70% 闭卷,教材及主要参考书,教材:编译原理(第2版),张素琴、吕映芝、蒋维杜、戴桂兰,清华大学出版社 2004 参考书:程序设计语言 编译原理(第3版),陈火旺、刘春林等,国防工业出版社 20

2、00,教学内容,1 编译程序概述 编译程序是现代计算机系统的基本组成部分之一.编译程序一般由词法分析程序,语法分析程序,语义分析程序,中间代码生成程序,目标代码生成程序,代码优化程序,符号表管理程序和错误处理程序等成分构成。本章概要介绍编译成分的主要功能以及编译阶段的逻辑关系。 2 PL/0 编译程序剖析给出一个简单的类Pascal语言,其编译程序用高级语言(C和Pascal)实现。通过剖析该高级语言程序以理解各编译成分的功能及手工实现方法。,教学内容,3 高级语言的认识 要学习和构造编译程序,理解和定义程序设计语言是必不可少的。每个程序设计语言都有一定的规则用以规定合适程序的语法结构,也需要

3、有对一个程序的含义的描述。上下文无关文法给出程序设计语言的精确的,易于理解的语法说明。尚没有公认的形式系统描述程序含义,但也有流行的描述语义规则的方法属性文法。 4 词法分析程序的自动构造词法分析程序是编译程序的一个构成部分,它的主要任务是扫描源程序,按构词规则识别单词,并报告发现的词法错误。正则表达式和有穷状态自动机分别作为单词的描述工具和识别机制,成为词法分析程序的自动构造原理。,教学内容,5 语法分析程序的构造 自顶向下的语法分析。可以看作是为一个输入串寻找一个最左推导的过程,也等价于从根开始,按前序生成结点,为输入串构造分析树的过程。讨论一种有效的无回溯的自顶向下分析程序,这种分析程序

4、称为预测分析程序。介绍对于一个文法类:LL(1)文法, 如何自动地构造预测分析程序。 自底向上(自下而上)语法分析方法,也称移进-归约分析法。它的实现思想是对输入符号串自左向右进行扫描,并将输入符逐个移入一个后进先出栈中,边移进边分析,一旦栈顶符号串形成可归约串,就用相应非终结符代替可归约串,这称为一步归约,重复这一过程,直到归约到栈中只剩文法的开始符号时,则为分析成功,并确认输入串是文法的句子。本章介绍LR分析法,分析过程中归约的是当前句型的句柄,称为规范归约。重点讲解LR类(LR(0)、SLR(1)、LALR(1)、LR(1)文法的分析表的构造原理。,教学内容,6 语义分析和中间代码生成在

5、词法分析和语法分析之后,编译程序下一个逻辑阶段的任务是语义分析和生成中间代码。引入属性文法和语法制导的翻译的概念,介绍中间代码的形式,针对一些语法成分讨论相应语义处理工作的描述。 7 符号表介绍符号表的一般组织和使用方法,讨论分程序结构语言的名字作用域分析及符号表设计方案。,教学内容,8 运行时的存储组织和管理编译的最终目标是生成目标程序。在目标代码生成前,编译程序必须对目标程序运行时的数据空间进行组织和安排. 介绍目标程序运行时的数据空间的存储分配策略,说明程序设计语言本身关于名称的作用域和生存期的规则与存储分配策略的关系,重点讨论栈式动态存储方案.,教学内容,9 代码优化和目标代码生成代码

6、优化是对代码作一些等价变换,以使得最后生成的目标代码更为高效。介绍优化技术,优化分类以及优化工作的基础控制流和数据流分析问题。编译的最后一个逻辑阶段是目标代码生成。目标代码生成程序的设计细节要考虑目标语言和操作系统的特点。讨论目标代码生成程序设计的一般问题,包括指令选择,寄存器分配和计算顺序选择。,教学要求 掌握:编译的概念,编译 的过程 理解:编译的各个阶段 了解:编译的结构和组合,第一章 编译程序概述,1.1 什么是编译程序,机器语言(Machine Language)与汇编语言(Assemble Language) 0、1代码与助记符:更接近于计算机硬件指令系统的工作 高级语言(High

7、 Level Language) 其表示方法更接近于待解问题的表示方法 定义数据、描述运算、控制流程、传输数据 如:C、FORTRAN、PASCAL、C+、JAVA、SQL(数据定义、数据操作) 命令语言(Command Language) 控制系统的工作以功能封装为特征 如UNIX上的shell,1011 1000 0010 1011 0001 0101 (B82B15) 1000 1110 1101 1000 (8ED8) 1010 0001 0000 0000 0000 0000 (A10000) 1000 1011 0001 1110 0000 0010 0000 0000 (8B1E

8、0200) 1011 1001 0000 0000 0000 0000 (B90000) 0000 0011 1100 1000 (03C8) 0000 0011 1100 1011 (03CB) 1000 1011 0000 1110 0000 0100 0000 0000 (8B0E0400) 1011 1000 0000 0000 0100 1100 (B8004C) 1100 1101 0010 0001 (CD21),int main int a,b,c;a=1234h;b=5678h;c=a+b;return 0; ,assume cs:code, ds:data data seg

9、mentdw 1234h,5678h data ends code segment start: mov ax, datamov ds, axmov ax, ds:0mov bx, ds:2mov cx, 0add cx, axadd cx, bxmov cx, ds:4mov ax, 4c00hint 21h code ends end start,1.1、什么是编译程序,编译程序是现代计算机系统的基本组成部分之一,而且多数计算机系统都含有不止一个高级语言的编译程序,对有些高级语言甚至配置了几个不同性能的编译程序。,1.1 什么是编译程序,从功能上看,一个编译程序就是一个语言翻译程序。它把一

10、种语言(称作源语言)书写的程序翻译成另一种语言(称作目标语言)的等价的程序。如果把编译程序看成一个“黑盒子”,它所执行的转换工作可以用图1.1来说明。,图1.1 编译程序的功能,编译程序,高级语言程序(源程序),低级语言程序 (目标程序),C ,Pascal,等,机器语言,汇编语言,一个源程序有时可能分成几个模块放在不同的文件里,将这些源程序汇集在一起的任务,由一个叫做预处理程序的程序来完成,有些预处理程序也负责宏展开。图1.2中的编译程序生成的目标程序是汇编代码形式,需要经过汇编程序翻译成可再装配的机器代码,再经过装配/连接编辑程序与某些库程序连接成真正能在机器上运行的代码。也就是说,一个编

11、译程序的输入可能要由一个或多个预处理程序来产生。,1.1 什么是编译程序,1.1 什么是编译程序,需预处理的源程序,预处理程序,源程序,编译程序,目标汇编程序,汇编程序,可再装配的机器代码,装配/连接 编辑程序,绝对机器代码,图1.2 高级语言程序的处理过程,可再装配目标文件,编译程序的发展,第一个编译程序的出现:20世纪50年代早期,主要将算术公式翻译成机器代码 20世纪50年代中期,一批编译系统程序开发成功 20世纪50年代末,开始研究编译程序的自动生成工具 20世纪60年代,研究使用自展技术,1971年自展技术成功后,影响越来越大。,编译程序的重要性:使得计算机用户不必考虑与机器有关的繁

12、琐细节,使程序员和程序设计专家独立于机器。,1.2.1 编译过程概述,一个编译程序的整个工作过程是划分成阶段进行的,每个阶段将源程序从一种表示形式转换成另一种表示形式。 典型的划分方法:,源程序,词法分析,语法分析,语义分析,中间代码生成,代码优化,目标代码生成,目标程序,语义分析,图1.3 编译的各个阶段,词法分析阶段:编译过程的第一个阶段,任务:从左到右一个字符一个字符地读入源程序,对构成源程序的字符流进行扫描和分解,从而识别出一个个单词。单词:标识符(sum,count),保留字(begin,end,if,else),算符(+,-.*,/),界符(.)等,逻辑上紧密相连的一组字符,这些字

13、 符具有集体含义。,begin var sum , first , count:real;sum:=first+count*10end.用id1,id2和id3分别表示sum, first和count三个表示符的内部形式,经过词法分析,上述赋值语句变为:id1:=id2+id3*10,保留字,标识符,运算符,界符,语法分析:编译过程的第二个阶段,任务:在词法分析的基础上将单词系列分解成各类语法短语,如“程序”,“语句”,“表达式”等 语法分析的依据是语言的语法规则,即描述程序结构的规则,通过语法分析确定整个输入串是否构成一个语法上正确的程序。程序的结构通常是由递归规则表示的。,例:sum:=f

14、irst+count*10 ; 用id1,id2,id3表示sum,first,count的内部形式,经过词法分析后,赋值语句表示为: id1:=id2+id3*10 规则:=“:=”:=“+”:=“*”:=“(”“)”:=:=:=,赋值语句,标识符 := 表达式,表达式 + 表达式,表达式 * 表达式,标识符,id2(first),标识符,id3(count),整数(10),id1(sum),图1.4 语句id1:=id2+id3*10的语法树,词法分析和语法分析本质上都是对源程序的结构进行分析。 词法分析是线性扫描完成。比如识别标识符,因为标识符的结构是字母打头的字母和数字串,这只要顺序扫

15、描输入流,遇到既不是字母又不是数字字符时,将前面所发现的所有字母和数字组合在一起而构成单词标识符。但是这种线性扫描则不能用于识别递归定义的语法充分,比如不能用此方法去匹配表达式中的括号 语法分析识别递归定义的语法成分。,语义分析阶段(第三阶段),审查源程序有无语义错误,为代码生成阶段收集类型信息。 语义分析进行类型审查,审查每个算符是否具有语言规范允许的运算对象,当不符合规范时,编译程序应报告错误。如有的编译程序对实数用作数组下标的情况报告错误,二目运算施于一整型和一实型时,强制转换,并不认为是源程序的错误。,:=,id1,id2,id3,+,*,inttoreal,10,图1.6 插入语义处

16、理节点的树(P4),中间代码生成(第四阶段),在进行了语法分析和语义分析阶段的工作后,有的编译程序将源程序生成一种内部表示形式,这种内部表示形式叫中间代码。 中间代码是一种结构简单、含义明确的记号系统。 设计中间代码的原则:一是容易生成,二是容易翻译成目标代码。,许多编译系统采用了近似“三地址指令”的“四元式”中间代码,其形式为: (运算符,运算对象1,运算对象2,结果) 例如: sum:=first+count*10可以生成四元式序列,如图1.7所示,其中ti是编译程序生成的临时名字,用于存放运算的中间结果。,中间代码的形式: (intoreal 10 - t1 ) (* id3 t1 t2

17、 ) (+ id2 t2 t3 ) (:= t3 - id1) 图1.7 中间代码,代码优化(第五阶段),此阶段的任务是对前阶段产生的中间代码进行变换和改造,目的是使生成的目标代码更为高效,即省时间省空间。例如图1.7的代码可以变换为图1.8的代码,仅剩了两个四元式而执行了同样的计算。(* id3 10.0 t1 )(+ id2 t1 id1) 图1.8 优化后的中间代码,目标代码生成:编译的最后阶段,把中间代码变换成特定机器上的绝对指令代码或可重定位的指令代码或汇编指令代码,它的工作与硬件系统和指令含义有关,这个阶段的工作很复杂,涉及到硬件系统功能部件的运用、机器指令的选择、各种数据类型变量

18、的存储空间分配以及寄存器和后续缓存器的调度等。,例如使用两个寄存器R1和R2,可将图1.8所示的中间代码生成如图1.9的某种汇编代码 MOV id3 , R2 MUL #10.0 , R2 MOV id2 , R1 ADD R1 , R2MOV R1 , id1 图1.9 目标代码 第1条指令将id3的内容送至寄存器R2; 第2条指令将其与实常数10.0相乘,#表明把10.0处理为常数; 第3条指令将id2移至寄存器R1; 第4条指令将R1和R2中的值相加; 第5条指令将寄存器R1的值移到id1的地址中。 这些代码实现了本节开头给的源程序片段的赋值。,1.2.2 编译程序的结构,上述编译过程的

19、六个阶段的任务,再加上表格管理和出错处理的工作可分别由几个模块或程序完成,它们分别称作词法分析程序、语法分析程序、语义分析程序、中间代码生成程序、代码优化程序、目标代码生成程序、表格管理程序和出错处理程序。从而可以给出一个典型的编译程序结构框图,如图1.10所示。,源程序,词法分析程序,语法分析程序,语义分析,中间代码生成程序,代码优化程序,目标代码生成程序,目标程序,表格管理程序,出错处理程序,语义分析程序,图1.10 编译程序结构框图,符号表管理,记录源程序中使用的名字 收集每个名字的各种属性信息,出错处理,检查错误、报告出错信息、排错、恢复编译工作,1.2.3 编译阶段的组合,在前面讨论

20、的编译过程中阶段的划分是编译程序的逻辑组织。有时,常常把编译的过程分为前端(front end)和后端(back end)。,前端:由主要依赖于源语言而与目标机无关的阶段组成。通常这些阶段包括词法分析,语法分析,语义分析,中间代码生成,某些优化工作也可以在前端做,也包括与前端每个阶段相关的出错和表格管理程序 后端:指那些依赖于目标机而一般不依赖源语言,只与中间代码有关的那些阶段,即目标代码生成,以及相关出错处理和表格管理程序。 遍:对源程序或源程序的中间表示形式从头到尾扫描一次,生成新的中间结果或目标程序。每一遍扫描可以完成上述一个阶段或多个阶段的工作。,相同的前端,不同的后端,可为不同的机器

21、生成构造同一个语言的编译程序。 不同的前端,相同的后端,可为同一机器生成几个语言的编译程序。 一个编译过程可由一趟或多趟完成。 多趟完成占内存少,逻辑结构清晰但消耗时间多,速度慢。,编译程序和解释程序,编译程序是一个语言处理程序,它把一个高级语言程序翻译成某个机器的汇编或二进制代码程序,这个二进制代码程序在机器上运行以生成结果。因此通过编译程序使得我们可以先准备好一个在该机器上运行的程序,然后这个程序便会以机器的速度运行。但是在不把整个程序全部都翻译结束之后,这个程序是不能开始运行,也不能产生任何结果的。编译和运行是两个独立分开的阶段。但在一个交互环境中,不需要将这两个阶段分隔开,编译就不如解

22、释的方法更方便。另一种语言处理程序,解释程序,它不需要在运行前先把源程序翻译成目标代码,也可以让我们实现在某台机器上运行程序并生成结果。,解释程序,是这样一个程序,它接受某个语言的程序并立即运行这个源程序。它的工作模式是一个个地获取,分析并执行源程序语句,一旦第一个语句分析结束,源程序便开始运行并且生成结果。 它特别适合程序员交互方式的工作情况,即希望在获取下一个语句之前了解每个语句的执行结果,允许执行时修改程序。 著名的解释程序有Basic语言解释程序 ,Lisp语言解释程序,UNIX命令语言解释程序(shell),数据库查询语言SQL 解释程序以及Java语言环境中的bytecode解释程

23、序。,高级语言解释系统(interpreter),图1.11示意了解释程序的功能,图1.12示意了编译程序和解释程序的不同工作模式。 功能 让计算机执行高级语言(basic,lisp,prolog) 与编译程序的不同 1)不生成目标代码2)能支持交互环境(同增量式编译系统) 源 程 序 初始数据,解释程序,计算结果,图1.11 解释程序的功能,解释系统,直接对源程序中的语句进行分析,执行其隐含的操作。 如: b := 2 ;a := b+2 ; 编译程序write a ; 解释程序直接将4的值输出(显示),Int 2 St b Ld b add 2 St a,生成代码,图1.12 编译程序和解

24、释程序的不同工作模式,编译程序和解释程序的存储组织也有很大不同,编译程序处理时,在源语言程序被编译阶段,存储区中要为源程序(中间形式)和目标代码开辟空间,要存放编译用的各种各样表格,比如符号表。在目标代码运行阶段,存储区中主要是目标代码和数据,编译所用的任何信息都不再需要。 解释程序一般是把源程序一个语句一个语句的进行语法分析,转换为一种内部表示形式,存放在源程序区,比如BASIC解释程序,将LET和GOTO这样的关键字表示为一个字节的操作码,标识符用其在符号表的入口位置表示。因为解释程序允许在执行用户程序时修改用户程序,这就要求源程序,符号表等内容始终存放在存储区中,并且存放格式要设计的易于

25、使用和修改。,编译阶段和运行阶段存储结构,编译时 运行时,名字表,目标代码缓冲区,编译用源程序中 间表示各种表格,目标代码区,数据区,源程序缓冲区,解释系统存储结构,编译技术和软件工具,编译程序本身也是一种软件开发工具,软件工作人员研制了不少对源程序处理的工具,不同程度地利用到编译程序各个部分的技术和方法:语言结构化编辑器语言程序的调试工具高级语言之间的转换工具并行编译技术,处理源程序的软件工具,1.语言的结构化编辑器 2.语言程序的调试工具 3.程序格式化工具 4.语言程序测试工具 5.程序理解工具 6.高级语言之间的转换工具,1.语言的结构化编辑器用户可使用该编辑器在语言的语法制导下编制出

26、所需的源程序。结构化编辑器不仅具有通常的正文编辑器的正文编辑和修改功能,而且还能像编译程序那样对源程序正文进行分析。因此,结构化编辑器能够执行一些对编制程序有用的附加的任务。例如,它能够检查用户的输入是否正确,能够自动地提供关键字,当用户敲入if后,编辑器立即显示then并将这两个关键字之间必须出现的条件留给用户输入,并能检查begin或左括号与end或右括号是否相匹配等等。由于结构化编辑器具有上述功能,既可保证编出的源程序无语法错误,并有统一的可读性好的程序格式,这无疑将会提高程序的开发效率和质量。商用产品很多如Turbo-Edit,Editplus和Ultraedit等等.很多集成开发环境

27、中里也都包含这种类似的工具,如Jbuild中就有JAVA程序的结构化编辑器.,2.语言程序的调试工具 调试是软件开发过程中一个重要环节,结构化编辑器只能解决语法错误的问题,而对一个已通过编译的程序来说,需进一步了解的是程序执行的结果与编程人员的意图是否一致,程序的执行是否实现预计的算法和功能。这种对算法的错误或程序没能反映算法的功能等错误就需用调试器来协助解决。有一种调试器允许用户使用源程序正文和它的符号来调试,即一行一行的跟踪程序,查看变量和数据结构的变化以进行调试工作.当然,这些符号的信息必须由编译程序提供.调试器的实现可以有很多途径.其中一种是写一个解释器,以交互的方式翻译和执行每一行,

28、它必须维护其所有的运行时的资源以保证在程序执行期间很容易的查询不同变量的当前值.如果不想通过解释程序允许编译了的代码调试,编译程序必须在目标代码(汇编)生成时同时生成特定的调试信息,比如,关联标识符和它表示的地址的信息,用于无歧义的引用一个声明了多次的标识符的信息等等.调试功能愈强,实现愈复杂,它涉及源程序的语法分析和语义处理技术。,3.程序格式化工具 程序格式化工具分析源程序并以使程序结构变得清晰可读的形式打印出来。例如,注释可以以一种专门的字形出现,且语句的嵌套层次结构可以用缩排方式(齿形结构)表示出来。4.语言程序测试工具 语言程序的测试工具有两种:静态分析器和动态测试器。静态分析器是在

29、不运行程序的情况下对源程序进行静态地分析,以发现程序中潜在的错误或异常.它对源程序进行语法分析并制定相应表格,检查变量定值与引用的关系。如某变量未被赋值就被引用,或定值后未被引用,或多余的源代码等一些编译程序的语法分析发现不了的错误。动态测试工具也是首先对源程序进行分析,在分析基础上将用于记录和显示程序执行轨迹的语句或函数插入到源程序的适当位置,并用测试用例记录和显示程序运行时的实际路径,将运行结果与期望的结果进行比较分析,帮助编程人员查找问题。,5.程序理解工具 对程序进行分析,确定模块间的调用关系,记录程序数据的静态属性和结构属性,并画出控制流程图,帮助用户理解程序。6. 高级语言之间的转换工具 由于计算机硬件的不断更新换代,更新更好的程序设计语言的推出为提高计算机的使用效率提供了良好条件,然而一些已有的非常成熟的软件如何在新机器新语言情况下使用呢?为了减少重新编制程序所耗费的人力和时间,就要解决如何把一种高级语言转换成另一种高级语言,乃至汇编语言转换成高级语言的问题。这种转换工作要对被转换的语言进行词法和语法分析,只不过生成的目标语言是另一种高级语言而已。这与实现一个完整的编译程序相比工作量要少些。比如:C,PASCAL,FORTRAN到Ada的翻译器IBM 4700汇编到C的转换器COBOL 到Java 的编译器,作业,书后习题1,2,3,

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 企业管理 > 管理学资料

本站链接:文库   一言   我酷   合作


客服QQ:2549714901微博号:道客多多官方知乎号:道客多多

经营许可证编号: 粤ICP备2021046453号世界地图

道客多多©版权所有2020-2025营业执照举报