资源描述
单击此处编辑母版标题样式,单击此处编辑母版文本样式,第二级,第三级,第四级,第五级,*,g+,编译选项与,makefile,文件的编写,-cosmozhang,课程大纲,g+,编译选项,1,g+,常见问题及处理,2,Makefile文件的编写,3,Makefile实例,4,g+编译选项 概述,gcc,认为预处理后的文件(.i)是C文件,并且设定C形式的连接.,g+认为预处理后的文件(.i)是C+文件,并且设定C+形式的连接.,选项必须分立给出,如:-dr与-d-r完全不是一回事,选项区分大小写,大多数-f和-W选项有两个相反的格式:-fname和-fno-name(或-Wname和-Wno-name),g+编译选项 选项分类及常用选项,1、总体选项 -c-s-E-o-v,2、语言选项 -ansi,3、警告选项 -Wall-pedantic-errors -werror,4、调试选项 -g(默认为g2),5、优化选项 -O 一般宁可优化代码也不用这个选项,6、预处理选项-Dmacro-Dmacro=defn-Umacro,7、汇编选项,8、连接器选项-l-static-shared-symbolic,9、目录选项-I-I-L-B(.),10、目标机选项-V,11、配置相关选项-G,12、代码生成选项 -fpic-fPIC,g+,编译选项 总体选项,一、,gcc/g+,在执行编译,,总共需要,4,步,1、预处理,生成,.i,的文件,预处理器,cpp,2、将预处理后的文件不转换成汇编语言,生成文件,.s,编译器,egcs,3,、有汇编变为目标代码,(,机器代码,),生成,.o,的文件,汇编器,as,4,、连接目标代码,生成可执行程序,链接器,ld,注:除非使用了-c,-S,或-E选项(或者编译错误阻止了完整的过程),否则连接总是 最后的步骤。,要生成以上4种文件,编译选项是什么?,g+,编译选项 总体选项,对应的编译选项是:,-E,激活,预处理,这个不生成文件,你需要把它重定向到一个输出文件里面,.,g,+,-E hello.cpp,precompile,.txt,-S,激活,预处理,、,编译,,就是指把文件编译成为汇编代码。,g+-S hello.cpp,-c,激活,预处理,、,编译,、,汇编,g+-c hello.cpp,生成目标代码,根据要生成文件类型有所差异(执行文件、.a、.so文件)。g+默认生成的是可执行文件。,g+,编译选项 目录选项,二、编译、链接目录及文件选项,-,IDIRNAME 指定头文件路径,-i,相当于#include,-L,DIRNAME,指定库文件路径,-l,FOO 链接库名 lib*.a,编译及链接器会根据-I,-L指定的目录依次进行匹配,相当于连字符,编译及链接查询目录顺序是怎样的?,g+编译选项 目录选项,匹配顺序是:,1、当前路径,2,、用户指定的路径,写在,specs,内的,后来用,-D-I-L,指定的,3、环境变量(,PATH,及,LD_LIBRARY_PATH,.)指定的路径,4、系统内定的默认路径,5、,ld.so,的环境变量(这是,run time,的时候),当初在编译时指定的(在,gcc/gcc/collect2.c:locatelib,()?,更具体的匹配顺序见附件:,编译、链接、执行查询路径,g+编译选项 调试选项,三、调试选项,-g 以操作系统的本地格式.产生调试信息.GDB能够使用这些调试信息.,-ggdb 以本地格式(如果支持)输出调试信息,尽可能包括GDB扩展,-glevel 请求生成调试信息,同时用level指出需要多少信息.默认的level值是2.,g+编译选项 链接选项,四、链接方式选项:,-static 此选项将禁止使用动态库。,优点:程序运行不依赖于其他库,缺点:文件比较大,-shared(-G)此选项将尽量使用动态库,为默认选项,优点:生成文件比较小,缺点:运行时需要系统提供动态库,-symbolic 建立共享目标文件的时候,把引用绑定到全局符号上.对所有无法解析的引用作出警告(除非用连接编辑选项-Xlinker-z-Xlinker defs取代)。,注:只有部分系统支持该选项.,g+编译选项 警告选项,五、错误与告警选项,-Wall 一般使用该选项,允许发出GCC能够提供的所有有用的警告。也可以用-Wwarning来标记指定的警告。,-pedantic 允许发出ANSI/ISO C标准所列出的所有警告,-pedantic-errors 允许发出ANSI/ISO C标准所列出的错误,-werror,把所有警告转换为错误,以在警告发生时中止编译过程,-w,关闭所有警告,建议不要使用此项,g+编译选项 预处理选项,六、预处理选项,-Dmacro,相当于C语言中的#define macro,-Dmacro=defn,相当于C语言中的#define macro=defn,-Umacro,相当于C语言中的#undef macro,-undef,取消对任何非标准宏的定义,g+编译选项 其他选项,-O 优化选项,一般不建议使用。代码优化比使用该选项要更好。,-fpic 编译器就生成位置无关目标码.适用于共享库(shared library).,-fPIC 编译器就输出位置无关目标码.适用于动态连接(dynamic linking),即使分支需要大范围转移.,第二章 g+常见问题及处理,g+,编译选项,1,g+,常见问题及处理,2,Makefile文件的编写,3,Makefile实例,4,g+常见问题,一、如何减小,发布,的可执行文件的大小:,1、使用动态链接方式,2、不使用-g编译选项(正式发布前将-g选项却除,但为了跟踪问题,会结合记录可配置级别的log),3、发布前使用strip命令对可执行文件进行处理。,二、-D选项的妙用,1、发布debug,release版本时定义不同的宏,2、作为不同操作系统、软件环境的开关。,三、显示详细的编译、汇编、连接命令,1、在g+中带上选项-v,g+,常见问题,四、,undefined reference,问题,引起此类问题的原因主要有:,1.缺少某个源文件,或源文件中缺少某个函数,2.源文件中的宏,未正确开启,3.链接时,多个库的顺序未根据依赖关系安排,4.编译时的先后顺序未按依赖关系安排,1-2处理:,一般把未添加的函数,源文件或者库添加到编译环境中,。Linux下使用grep命令也可以快速的找到,如可以在项目(库)目录下,使用 grep-n something*,3-4处理:主要是解决链接顺序。如果liba依赖于libb,在Makefile的LD选项中,libb应出现在liba的左侧。如下图:,g+,常见问题,原因:libSamebarRecommendPublic.a依赖于libqqact.a,但-lqqact选项在-l,SamebarRecommendPublic前面,所以发生连接错误。,解决方法:将-lSamebarRecommendPublic选项移至-lqqact前,五、如何查看libnetbar_public.a(或执行文件、动态库)中的符号,1、readelf-s libnetbar_public.a,g+常见问题,g+常见问题,2、objdump -t libnetbar_public.a,g+常见问题,3、ldd libnetbar_public.a (只能对.so及可执行文件),只显示会调用到的动态链接库,g+常见问题,五、日志使用_FILE_,_LINE_,_FUNCTION_宏,以方便问题的定位。,六、编译提示:,/usr/lib/gcc/i586-suse-linux/4.1.0/././././i586-suse-linux/bin/ld:cannot find-lidn,方法:使用-v选项,并查看连接的各个路径下是否存在libidn.a的文件,第三章 Makefile文件的编写,g+,编译选项,1,g+,常见问题及处理,2,Makefile文件的编写,3,Makefile实例,4,Makefile文件的编写 总述,一、简介,make,是Linux下的一款程序自动维护工具,配合,makefile,的使用,就能够根据程序中模块的修改情况,自动判断应该对那些模块重新编译,从而保证软件是由最新的模块构成。,二、make的作用(或者说为什么要用make),1、避免重复输入烦琐的编译命令。,2、加快编译速度,3、建立手册页,4、将应用程序安装至指定目录,makefile文件编写,三、make命令调用格式:,make-f makefile文件名选项宏定义目标,常用选项有:,-Idirname 指定被包含的makefile所在目录,-w 如果make在执行时改变目录,打印当前目录名,-d 打印调试信息,-k 用该选项,即使make程序遇到错误也会继续向下运行,makefile文件编写 总述,四、makefile文件主要包含了5部分内容,1、显示规则,2、隐式规则:,又称预定义规则。隐式规则简化了makefile的编写和维护。(make命令带-p选项),比如:,后缀规则,可以指定:.SUFFIXES:.cpp,3、,模式规则,提供的一种扩展make隐式规则的方法,规则与普通规则一样,主要是目标必定含有%号,比如:,%.o:%.c,$(CC)-c$(CFLAGS)$(CPPFLAGS),$,-o,$,4、变量定义(自动变量/预定义变量/自定义变量),5、文件指示(include,make-I,#if include),6、特殊字符:注释#转义 通配符*宿主目录,makefile编写 总述,五、makefile文件是被make命令调用的,用于描述系统中模块之间的相互,依赖关系,以及产生目标文件所要执行的命令(,规则,)。,编写规则通用形式:,target:dependency depenency.,command,command,.,注:command前是tab键,而非空格,makefile文件编写 关系依赖,六、makefile关系依赖:规定了最终得到的应用程序跟生成它的各个源文件之间的关系,如下图:,main:main.o f1.o f2.o,main.o:main.c def1.h,f1.o:f1.c def1.h def2.h,f2.o:f2.c def2.h def3.h,makefile文件编写 规则,七、规则:描述如何生成目标,或者说使用哪些命令来根据依赖模块产生目标。这就是command,这里的command即可以是gcc/g+编译命令,也可以是shell命令或是其他可执行文件。,main:main.o f1.o f2.o,gcc-o main main.o f1.o f2.o,main.o:main.c def1.h,gcc-c main.c,f1.o:f1.c def1.h def2.h,gcc-c f1.c,f2.o:f2.c def2.h def3.h,gcc-c f2.c,makefile文件编写 变量,八、变量(或者说宏),1、定义方法:VARNAME,=,some_text.,如:OBJS,:=,howdy.o helper.o,2、变量引用:$(VARNAME)或$VARNAME),3、变量扩展:VARNAME+=$(VARNAME)some_textn.,注:在使用变量时要注意库的连接左右问题,建议使用:VARNAME:=some_textn$(VARNAME),4、作用:用,代表某些多处使用而又可能发生变化的内容,节省重复修改的工作,避免遗漏,。一般用来代表一些文件名或选项。,makefile编写 变量,5、自动变量,$规则的目标所对应的文件名,$规则中的第一个相关文件名,$规则中所有相关文件的列表,以空格为分隔符,$?规则中日期新于目标的所有相关文件的列表,$(D)目标文件的目录部分,$(F)目标文件的文件名部分,$*这个变量表示目标模式中“%”及其之前的部分。,m
展开阅读全文