南开大学硕士学位论文基于LLVM的编译器移植中关键技术研究姓名:刘俊波申请学位级别:硕士专业:计算机应用指导教师:张红光2012-05
摘要摘要现在嵌入式系统已经广泛应用在社会生产和生活的各个方面。由于功能、成本、功耗等综合性的要求,嵌入式系统必须要有交叉编译的开发环境和编译工具链,包括编译器、汇编器、链接器和调试器。论文以开源的编译框架LLvM(LowLevelVirtualMachine)为基础,针对实验室自主研发的嵌入式处理器SRP32,设计实现了一款交叉编译器。论文首先介绍了LLVM系统结构,深入分析了框架中与后端移植相关的接口和技术。在理解目标机处理器体系结构和LLⅧ后端移植的基础上,详细讨论了针对SRP32处理器编译器设计和实现中的关键技术。在移植过程中,分析了后端代码的生成过程,完成了目标机体系各项属性的描述。在测试与验证中,移植的交叉编译器能够通过由大量LLVM系统提供的测试程序。实现的编译器完善了SRP32处理器的编译工具链,还充分利用LLVM提供的优化方法在编译层次上提高目标机的性能。关键词:LLVM,编译器,SRP,后端
AbstractAbstractTodayembeddedsystemshavebeenwidelyusedinmanyareasoflifeandindustries.Duetothecomprehensiverequirementsforfunctionality,costandpowerconsumption,embeddedsystemshouldhaveacross-compilerdevelopmentenvironmentandcompilertoolchain,includingcompiler,assembler,linkeranddebugger.ThisthesisdescribesthedesignandimplementofacrosscompilerbyusedtheLLVM(LowLevelVirtualMachine)compilerframeworkfortheSRP32processorwhichwasdevelopedbyourlaboratory.Inthecourseofthethesis,initiallythetechnicaloverviewofLLVMcompilerframeworkandtheanalysisoftheinterfaceprovidedbysystemtoportanewbackendaregiven.Subsequently,thedesignandimplementationofthecompilerbackendarediscussedindetailandthekeytechnologiesalsoaredescribed,throughunderstandingthetargetprocessorarchitectureandinterfaceofportingnewbackend.Intheprocessofportingnewbackend,weanalyzethecodegenerationofbackendanddescribethepropertyofthetargetsystem.Lastly,thecrosscompilercouldcompilethetestprogramswhichareprovidedbyLLVMsystem.Thenewcompilercanimprovethequalityofthecompilertoolchain,andalsomakefulluseoftheLLVMoptimizationmethodstoenhancetheperformanceofthetargetmachineinthecompilerlevel.Keywords:LLVM,compiler,SRP,backendII
第一章绪论第一章绪论第一节研究背景嵌入式系统被定义为以应用为中心、软件硬件可裁剪、适应应用系统对功能、可靠性、成本、体积、功耗等严格综合性要求的专用计算机系统。它一般由嵌入式微处理器、外围硬件设备、嵌入式操作系统以及应用程序等四个部分组成。嵌入式系统与通用的计算机系统相比有着如下不同的特性:首先嵌入式系统通常面向特定的应用,嵌入式处理器一般具有低功耗、体积小、集成度高的特点;其次为了提高执行的速度和系统的可靠性,嵌入式系统中的软件一般固化在存储器的芯片中;嵌入式系统本身通常不具备开发能力,用户通常不能直接对嵌入式系统中运行的程序功能进行修改,必须有一套开发工具和环境才能进行开发。由于上述特点,嵌入式系统中的软件开发一般采用主从模式。嵌入式系统所在的机器称为目标机,开发程序时使用的机器称为宿主机。一般目标机的运行能力和存储空间都十分有限,其主要任务是运行嵌入式系统程序而不包括针对本系统的开发工具。宿主机一般使用通用的桌面计算机,可以完成代码的编辑、编译、汇编、链接等开发工作。由于嵌入式系统自身的特点使得它必然种类繁多,而针对一款专用的系统都需要在宿主机提供良好的开发工具链,其包括交叉编译器、汇编器、链接器和调试器等。所以针对专用嵌入式系统的工具链的开发工作变的非常急迫而且重要。本文的研究重点是针对一款自行研发的32位嵌入式微处理器SRP32设计实现相应的交叉C编译器。在嵌入式系统的软件开发环境中,交叉编译器是工具链中的一个重要的部分。嵌入式系统的编程语言通常包括汇编语言,但是汇编语言编写困难、不易阅读、也难于调试、依赖于特定的目标体系结构,束缚了嵌入式系统的应用和开发。有了交叉编译器的支持,程序员可以大大提高开发的效率同时降低代码的维护成本。嵌入式系统的发展日新月异,快速开发针对目标机的交叉编译器对于嵌入式系统至关重要。重新设计开发一款新编译器需要花费高昂的代价和很长的开
第一章绪论发时间,因此移植现有的优秀开源编译器是一个快速有效的途径。传统编译器一般要求在合理的编译时间生成高效正确的目标代码,而对编译器本身的可重用性和可扩展性考虑不多。非常有名的GGC编译器有着良好的稳定性和可靠性,但其代码层次结构复杂,不易扩展和重用,后端移植时相对复杂。LLVM是一个高效的,模块化的编译框架,提供了用于实现编译器的前端、中间优化和后端的各种库…。为了便于对程序在编译时、链接时和运行时进行优化和分析,LLVM有着清晰的代码结构和接口。由于LLVM这些特性,我们需要研究其实现技术和移植方法,进而完成专用处理器SRP32的编译器移植。第二节研究现状随着计算机体系结构的发展,编译技术研究也在不断进步,其中嵌入式编译技术更是如此。嵌入式处理器系统结构本身丰富多样,有用于数字信号实时处理的DSP,有应用于控制领域的微控制器,还有指令格式相对固定简单的RISC处理器。由于嵌入式处理器的多样性,针对不同嵌入式系统的编译技术也非常丰富。例如,针对采用超长指令字(VLlw)体系系统的DSP,怎样利用其特性生成高效优化的代码这是编译技术需要考虑的问题[2圳。随着互联网的快速发展,面向网络处理器(Networkprocessor)的编译技术逐渐得到重视[5-91。功耗对很多嵌入式系统非常重要,通过编译技术来降低系统功耗也得到了广泛的研究[10-121。上述新技术和新方法,只有当它们被结合到可以实际使用的编译器中后,才能得到有意义的评价。而重新开发一个完整编译器需要大量工作,由单独的研究组完成通常需要花费很长的时间和较高的代价。现在已有的一些开源并且具有工业质量的编译器为研究者采用新的优化方法、新的代码生成策略或移植后端提供了很好平台。下面介绍一些优秀的编译框架。GCC是在开源社区广泛使用的编译系统,其表示GNUCompilerCollection,包含一系列针对不同语言和不同目标平台的编译器。GCC本身采用C语言实现,有着很高的优化程度和可靠性,是类Unix系统的标准编译器。已经有很多嵌入式处理器的编译器通过移植GCC来生成,如OpenRISC、Nios和ARC等[13,141。Open64是具有工业质量的开源编译器。它最初源于SGI的MIPSpro编译器,随后增加对Itanium后端的支持,Delaware大学负责维护其代码后将其改名Open64。后来又有很多组织参与了Open64的研究和移植,其前端支持C、C++2
第一章绪论和Fortran,后端支持MIPS、X86、IA.64、ARM和PowerPC等处理器[15】。Nvidia公司使用Open64来开发CUDA的工具链。SUIF是斯坦福大学开发的用于研究的编译系统,其模块化的代码结构,利于代码重用。研究者可以通过插入新的优化模块,对生成代码进行优化。SUIF本身并不是完整的编译系统而更类似于编译前端,可以把C、Fortran转变成中间代码。随后开发的MachineSUIF系统是一个编译后端,可以将SUIF生成的中间代码翻译成X86或Alpha的汇编语言。利用MachineSUIF可以方便的复位向新的目标机后端【l6|。LCC是一个可重定向的ANSIC编译器,最初由Princeton大学两位老师开发。其定位于针对C语言的一个子集的编译器,作为编译原理的教学、学习使用,之后逐步发展成了适用于实用的ANSIC编译器,由于其不凡的性能,开始推广,成为一个比较流行的C编译器。LCC比大多数其它ANSIC编译器代码量更小、编译速度更快。LCC以产生好的本地代码为设计目标,能够生成相当高效的目标代码,但其它编译器所具有的全局优化并不在LCC的设计目标中【311。实验室之前通过移植LCC为SRP32进行过交叉编译器的开发,但LCC本身就缺少有效的优化和调试功能。LLVM(LowLevelVirtualMachine)是源于UIUC大学开源编译框架。它以库的形式为编译器的编写提供了相关支持,或者可以使用它提供的API进行编译时(compile.time)、链接时(1ink.time)和运行时的优化[1,17]。它定义了一种中间语言LLVMIR,前端语言先编译生成LLVMIR,然后再由LLVMIR生成目标机器代码【l81。苹果公司随后开始支持LLVM项目并以LLVM为基础开发了针对iPone、iPad以及多核Mac的编译工具链。LLVM也被用于程序分析优化【19’201、静态检查【21】,为脚本语言的编译执行生成新的后端[22】。嵌入式处理器一般为特定的应用需要而设计的,其系统结构和指令集通常也是专有的,存在着各种各样不同处理器类型。为不同处理器实现编译器一直是重要而且急需的工作,其中有部分就是移植已有的编译框架来生成编译器。中科院计算所基于Open64研发了龙芯交叉编译器系统,编译器现已经在为龙芯1号、2号、3号处理器服务。龙芯编译器继承了Open64的多种特性,如健壮性好、性能好、代码风格较好、有固定社区支持等优点[231。国防科技大学通过移植GCC的后端,实现了一个支持C6x处理器的开源编译器[24】。浙江大学通过分析GCC,为车控电子系统中的MPC555嵌入式处理器移植了交叉编译器,该处3
第一章绪论理器集成了PowerPC的内核和一些必要的外部设备、通信功能模块【25】。德国纽伦堡大学的以LLVM为基础,为TriCore处理器生成了新的交叉编译器[26】。上述编译器的后端多是通过手工编写代码来实现的,现在也有研究利用体系结构描述语言(ADL)来自动生成编译器的技术。ADL通过对目标体系结构详细的描述信息自动生成处理器所需要的软件工具链,包括高级语言编译器、汇编器、链接器、指令仿真器及一些其它的二进制工具等【27]。其中影响较大的一种是nML语言,它最初是为了自动生成指令仿真器设计,后来逐步扩展成可支持编译器自动生成的描述语言【281。MADL是普林斯顿大学提出的一种以OSM(OperationStateMachine)为基础的语言,支持时钟周期精确的指令仿真和编译器后端自动生成。它很容易支持流水线结构,可以解决流水线冲突,实现复位向,支持其它ADL不支持的多处理器建模。与针对描述处理器硬件结构的ADL语言不同,xADL为编译器的后端自动生成提出。维也纳技术大学以LLVM编译框架为基础,通过xADL描述自动生成MIPS后端代码的质量可以和手工编写的编译器代码质量相媲美【291。第三节本文内容及组织结构本文以LLVM编译框架为基础,设计实现了一款针对32位嵌入式处理器的交叉编译器。文中介绍了LLVM系统结构,深入分析了框架中与后端移植相关的接口和技术。在理解目标机处理器体系结构和LLVM后端移植的基础上,详细讨论了针对SRP32处理器编译器设计和实现中的关键技术。最后给出了基于LLVM的交叉编译器的测试结果和经验总结。本文的首先介绍了目标机交叉编译器移植的背景和现有的编译器移植方法,然后介绍了编译程序的基本概念,分析了LLVM后端的移植技术,最后在LLVM编译框架的基础上实现了针对SRP32处理的交叉编译器,并给出了系统的测试结果。本文的组织结构如下:第一章为全文的导论,首先阐述了交叉编译移植提出的背景,介绍了已有的一些开源编译器与编译器移植的研究现状,并且简单介绍了本文的工作。第二章首先介绍了编译器的一般概念与基本结构,然后简单叙述了本文所使用的LLVM编译框架,重点分析其基本结构和中间语言。第三章阐述了了基于LLVM的交叉C编译移植策略设计,详细介绍了后端4
第一章绪论移植接口和用于自动代码生成的工具,描述了中间语言到目标机汇编语言转换的代码生成过程。第四章具体描述了交叉编译器的移植工作。结合目标机的体系结构,讨论了针对目标机C编译器的设计,然后给出了后端移植实现的过程,阐述了针对SI冲32处理器的DAG转换规则。第五章介绍了对移植的编译系统的测试,首先使用系统提供的11c工具测试LLVM中间语言到目标机汇编代码的变换,然后使用系统提供C测试程序测试交叉编译器。第六章总结本文所做的工作,并对下一步的研究工作做出展望。5