|

楼主 |
发表于 2003-2-14 23:05:02
|
显示全部楼层
3.4 Exclusiveos :
此域定义软件包适用的操作系统。其描述格式为:
Exclusiveos : 操作系统1 [操作系统2] ...
注: []为可选项,操作系统之间以空格分隔。例如:
Exclusiveos : linux solaris
4. 目录相关
4.1 Prefix :
此域定义可重定位的目录前缀,可在描述文件中书写多次。其描述格式为:
Prefix : 目录前缀1 [目录前缀2] ...
注: []为可选项,各目录前缀之间均以空格分隔。例如:
Prefix : /usr /etc
它也可写作:
Prefix : /usr
Prefix : /etc
RPM利用可重定位的目录前缀,实现了软件包的重定位安装,使软件中的文件不必固定在某个绝对位置,这种做法很好。LZE软件包描术文件lze-6.0-2.spec中就定义了一个可重定位的前缀/usr(见第15行),这样,安装时就可将该包中在/usr目录下的文件重定位到用户指定的目录,如:
# rpm -i --prefix /tmp lze-6.0-2.i386.rpm
#
或者:
# rpm -i --relocate /usr=/tmp lze-6.0-2.i386.rpm
#
注: 此命令安装lze包,将其中含/usr重定位目录前缀的文件定位到/tmp目录。如包中
的/usr/bin/lze文件安装后,因重定位而成了/tmp/bin/lze。(RPM安装命令使用方法请参考<<精通RPM之二--安装篇>>)
4.2 Buildroot :
此域定义的是软件包所包含的文件共有的根目录,此根目录仅供RPM建立软件包时使用。即当RPM建立软件包时,将设定此目录为根(调用chroot函数),提取所需文件,生成软件包。
例如: 当Buildroot设定为/tmp时,对于LZE包描述文件中所包含的/usr/bin/lze文件,RPM实际打包的则是/tmp/usr/bin/lze,但对生成的包查询后可以发现:原文件名并未改变,还是/usr/bin/lze。
如此说来,这就很有意思了。一般用户通过设定Buildroot,也可以象超级用户(root)那样自由地建立各种各样的软件包了,即使包中有那些唯有超级用户才可以操作的目录或文件。安装这样的包与安装由超级用户建立的包,是没有什么分别的。
此域的描述格式很简单:
Buildroot : 目录
如,上例可定义为:
Buildroot : /tmp
5. 源码相关
下列四个域均是为制作源码包而设计的。源码包里有什么?用户可以通过查询包的文件列表得到,命令是“rpm -qpl 源码包文件”(请参阅<<精通RPM之五--查询篇>>有关内容)。一般情况下,源码包里有这么四类文件: 一是程序源码(SOURCE),二是源码补丁(PATCH),三是软件包描述文件,四是图标文件(ICON)。通过安装源码包,用户可以轻松地实现现场编译、连接和应用,同时更方便了软件开发者与软件包制作者:他们维护程序容易了,并且维护过后可以很快地生成执行代码包与源码包。这,也是所有人钟爱RPM的重要原因之一。
5.1 Source :
此域定义RPM打包时要包含的程序源码文件。这些文件一般先用tar命令打包,然后再用gzip压缩。一个描述文件中可包含多个Source域,当有多个这样的域时,需要进行编号:第1个编为Source0(也可直接用Source),第2个编为Source1,第3个编为Source2等等。此域的描述格式为:
Source[编号] : 源码文件
注: []所括为可选项。具体用法如:
Source0 : lze-6.0-2.tar.gz
Source1 : lzeime-wb-6.0-2.tar.gz
Source2 : lzeime-py-6.0-2.tar.gz
Source3 : lze-lib-6.0-2.tar.gz
注: 此域域值可以采用URL(统一资源定位)的形式,如LZE描述文件第14行。采用这种形式,主要是给其它用户提供该源码的位置信息。在RPM制作源包时,它提取的是最后的文件名lze-6.0-2.tar.gz,而不是http://zhsoft.myetang.com/lze-6.0-2.tar.gz(URL前面的内容被RPM忽略了)。
5.2 NoSource :
在上例中,假如在打包时不想包含Source1与Source2定义的文件,那该怎么办?
办法之一是将其所在行删除掉;
办法之二是将其所在行注释掉(即所在行前面加#号);
办法之三就是定义Nosource域,此域可重复。其描述格式为:
NoSource : 源码域编号
本例可写作:
NoSource : 1
NoSource : 2
注: 其中的1与2为编号,表示Source1和Source2。
注意: 如果软件包描述文件中没有NoSource域,则RPM生成的源码包名字格式为"软件名-版本号-释出号.src.rpm"。如果使用了NoSource域,则RPM生成的源码包名字格式为"软件名-版本号-释出号.nosrc.rpm"(单从名字就可看出源码包包含的文件不完整)。
5.3 Patch :
Patch的本义是补丁,用在这里指的是源程序的补丁,它是用diff命令比较新老源程序所产生的输出(命令为“diff -Nur 旧文件 新文件 >补丁文件”),而系统中的patch命令又可利用此输出将老版本的源程序升级为新版本。
此域定义RPM制作源码包时所要包含的补丁文件,该文件的命名建议用"软件名-版本号.补丁功能.patch"的格式。一个软件包描述文件中可有多个Patch域,当有多个这样的域时,也需要象Source域那样进行编号(注:第1个域编为Patch0,也可省略0,用Patch)。
此域的描述格式为:
Patch[编号] : 源码补丁文件
注: []所括为可选项。具体用法如:
Patch0 : blather-4.5-bugfix.patch
Patch1 : blather-4.5-config.patch
Patch2 : blather-4.5-somethingelse.patch
注: 此域的域值也可以象Source域一样,采用URL的形式,RPM仅提取其中的文件名供其使用。
5.4 NoPatch :
此域的功能类似NoSource,其定义的编号对应的补丁文件RPM不作打包处理。此域在描述文件中可重复出现。如上例,若不想让源码包包含Patch0与Patch2域所指示的补丁文件,则可在描述文件写上这么两行:
NoPatch : 0
NoPatch : 2
注意: 如果软件包描述文件中没有NoPatch域,则RPM生成的源码包名字格式为"软件名-版本号-释出号.src.rpm"。如果使用了NoPatch域,则RPM生成的源码包名字格式为"软件名-版本号-释出号.nosrc.rpm"(单从名字就可看出源码包包含的文件不完整)。
三、功能段
见第19-86(即文件头以下的部分)。
何谓功能段?可以这么说,功能段是描述软件包的重要数据和操作指令的段落,它包括段名与段内容两部分。没有功能段,RPM便制作不出任何包裹文件。功能段的段名都是以百分号(%)开始的,占用一行。功能段的段内容范围是这样界定的:它从该功能段段名下一行开始到下一个功能段段名的前一行或到描述文件结束。如LZE描述文件,%description段是从第19行到第28行(%prep段从第29行开始),第19行为段名,第20-28行为段内容。而%prep段是从第29行到第32行(第33行%build段开始),其段名在第29行,段内容在第30-32行。另外要注意的是,各个功能段的位置是自由的,可放在文件头以下的任何位置,不必拘泥某一固定位置。
必选的功能段
描述文件中,必选的功能段有:
1. %description
本段是描述段,段的内容是对软件包进行较为详细的介绍,不象文件头的Summary域仅用一句话说明。介绍的文本形式自由,可任意换行,不受限制。具体请参见LZE描述文件第20-27行。
本段段名描述格式是:
%description [子包选项]
其中,子包选项的格式为:[-n] 子包名
注: []所括为可选项。
三种形式的描述段段名:
(1) 段名格式为“%description”时:
本功能段描述的内容是关于父包的。父包也可叫作主软件包,它用软件名来命令,其名字格式是:软件名-版本号-释出号.体系.rpm。如:lze-6.0-2.i386.rpm。
(2) 段名格式为“%description 子包名”时:
本功能段描述的内容是关于子包的。子包选项中没有-n选项时,子包是用软件名加子包名的形式命名,格式为: 软件名-子包名-版本号-释出号.体系.rpm。如分成两个子包的LZE软件:lze-bin-6.0-2.i386.rpm(执行程序包),lze-config-6.0-2.i386.rpm(配置文件包)。
(3) 段名格式为“%description -n 子包名”时:
本功能段描述的内容也是关于子包的。当子包选项中有-n选项时,子包直接采用子包名的形式命名。它不包含软件名,命名格式为: 子包名-版本号-释出号.体系.rpm。如分成两个子包的LZE软件: bin-6.0-2.i386.rpm(执行程序包),config-6.0-2.i386.rpm(配置文件包)。注意:这种类型的子包内容通常是可被其它软件包共用的函数库,如果专用,则尽量不要采用这样形式来定义子包。
2. %files
本段是文件段,它定义的是软件包需要包含哪些文件。本段通常放在描述文件尾部,以便于添加文件名,便于编辑。
本段段名描述格式为:
%files [子包选项] [-f 文件名]
注: []所括为可选项。
当没有任何选项时,本段内容定义的是父包要打包的文件列表;
当有子包选项时,本段内容定义的则是子包要打包的文件列表;
当选择-f选项时,RPM除了从文件段读取打包文件列表外,还将从指定的文件中读取要打包的文件列表。指定的文件中,一个文件名占用一行。此选项方便了软件包制作者,他们可以通过程序自动产生有关软件的文件列表,并将其写入到一个特定的文件中,这样制作软件包时,只需引用一下这个文件,RPM就会自动从这个文件中读取文件名并将其加入包中。如果没有此选项,软件包制作者只能在文件段里,将要打包的文件名一个一个写进去,有点麻烦。
文件段的内容格式为:
[修饰符1 [修饰符2] ...] 文件名
其中:修饰符是可选的,一个文件可以有多个修饰符,文件名必须以/开头(绝对路径形式)。
修饰符有以下几类:
(1) 文件相关
* %doc :
此修饰符设定文件类型为说明文档(参见LZE描述文件第72,73行);
* %config :
此修饰符设定文件类型为配置文件(参见LZE描述文件第70,71行);
* %config(missingok) :
此修饰符设定文件类型为配置文件,且此文件可丢失。即使丢失了,RPM在卸载软件包时并不认为这是个错误,并不报错。
此修饰符通常用于那些软件包安装后建立的符号连接文件,如/etc/rc.d/rc2.d/S55named等。此类文件在软件包卸载后可能需要删除,所以丢失了也不要紧。
* %config(noreplace) :
此修饰符设定文件类型为配置文件,且如果安装时系统中有同名的文件,则软件包中的这个文件将换个名字安装,其文件名后缀加个.rpmnew。(如果不用此修饰符,则安装时RPM若发现有同名文件,则RPM会将系统中的这个文件换个名字,其后缀加上.rpmorig,而软件包中的文件则还用原来的名字。)在软件包卸载时,系统中的同名文件被RPM换个名字保存起来,其后缀加上了.rpmsave。
如描述文件的文件段中定义了这么一行:
%config(noreplace) /etc/hello
则制成的包在安装时,若系统中已有此文件/etc/hello,则RPM会提示:
warning: /etc/hello created as /etc/hello.rpmnew
这表明包中的/etc/hello文件被创建为/etc/hello.rpmnew文件了。
如果卸载这个软件包,则系统中的/etc/hello将会改名为/etc/hello.rpmsave。
* %ghost :
此修饰符所修饰的文件,其内容不被包含到软件包中。这样的文件一般是日志文件(log file)一类的文件,其文件属性(文件名,属主,属组等)很重要,但是文件内容并不重要。用此修饰符后,RPM仅将其文件属性加入包中。
* %attr :
此修饰符设定文件的属性信息,使用格式为:
%attr(权限,属主,属组)
注: 权限常用数字形式(八进制),属主和属组可以是数字,也可以是字符串。如果文件的权限,属主和属组想使用系统默认值,则可用减号(-)表示它。
如下例采用两个修饰符,定义/etc/funkey.def文件的权限为755,属主默认,属组为root,类型为配置文件:
%attr(755,-,root) %config /etc/funkey.def
* %verify :
此修饰符设定文件需要校验的那些属性。这些属性有 wner(属主),group(属组),mode(权限),md5(MD5检查和),size(大小),maj(主设备号),min(从设备号),symlink(符号连接),mtime(最后修改时间)。
此修饰符使用格式为:
%verify([not] owner group mode md5 size maj min symlink mtime)
注: not可选。当选用not时,表明需要校验除选定属性以外的那些属性。
如下例指示RPM校验/dev/ttyS0文件时,要校验其权限,MD5检查和,大小,主设备号,从设备号,符号连接和最后修改时间共七项属性信息:
%verify(mode md5 size maj min symlink mtime) /dev/ttyS0
这也可以采用not选项来实现,因为除去属主owner和属组group两项属性,剩下的就是需要校验的属性了:
%verify(not owner group) /dev/ttyS0
(2) 目录相关
* %docdir :
此修饰符定义说明文档前缀,这样,后面所有含指定文件名作为前缀的文件,RPM打包时会将其类型统一设定为说明文档。
例如某描述文件的文件段中有这么三行:
/root/readme
%docdir /root
/root/mydoc.txt
此例指明/root为说明文档的前缀,因为/root/mydoc.txt在%docdir的下一行,所以RPM打包时会设定此文件的类型为说明文档。而/root/readme文件则不做此设定,因为它在%docdir定义之前。
通过此修饰符,用户可以很方便地设定说明文档一类的文件,因为它们通常固定在某个目录下面,有着共同的前缀。
* %dir :
RPM在制作软件包时,如果要打包的文件是个目录,那么RPM会将该目录下面的所有文件包含到软件包中。(注意:如果要打包的文件是个符号连接,此符号连接又指向一个目录,则RPM并不会将其视作目录,只会把它当为普通文件处理。)如果仅想将这个目录名包含到软件包中,制作者用此修饰符修饰一下这个目录名就行了。
如: /etc是个系统目录,其下有多个文件,如果想将其均加入包中,描述文件的文件段里可写上这么一行:
/etc
如果仅想包含此目录,则可用:
%dir /etc
(3) 另类修饰符
此类只有一个%defattr。说它是另类修饰符,是由于它设定的是默认的文件属性,而非特定的某个文件。它一般放在文件段内容的第一行。
其使用格式为:
%defattr(权限,属主,属组)
其中: 权限,属主和属组都可以使用减号(-)。使用减号的属性将由系统设定。
例如: %defattr(022,zzz,zhsoft) 设定其后的所有文件权限为022,属主为zzz,属组为zhsoft;又如: %defattr(-,zzz,-) 则是设定其后的所有文件属主为zzz,权限与属组由系统设置。
可选的功能段
描述文件中,可选功能段的内容都是些脚本程序。(LZE描述文件中多个脚本程序中仅含一个echo命令)
可选的功能段的描述格式为:
功能段名 [子包选项]
注: 子包选项为"[-n] 子包名"。当无子包选项时,段内容描述的是父包的脚本程序。当有子包选项时,段内容则是描述子包的脚本程序。
可选的功能段可分为如下三类:
1. 建包用功能段:
RPM通过源程序来建立一个软件包时,要执行预处理,编译,安装和清理四项操作,分别对应于%prep,%build,%install和%clean四个段。
下面按其执行顺序逐段进行说明:
1.1 %prep :
此为预处理段,其内容为预处理脚本程序。该程序完成以下任务:
* 建立软件编译用目录;
* 将源程序解压缩;
* 通过打补丁,升级源程序;
* 执行其它一些操作,使源程序随时可进行编译。
在此脚本程序中,可使用如下两个宏命令:
1.1.1 %setup
这个宏利用系统中的gzip与tar等命令,来解压源程序包。RPM会自动探测源程序包是否压缩,如果压缩,它会用gzip将其解压缩,否则直接用tar命令展开包中文件。其使用格式为:
%setup [-n name] [-c] [-D] [-T] [-b N] [-a N]
注: []所括为可选项。
(1) 当没有任何选项时:
这个宏用来解压默认的源程序包(由文件头Source或Source0域指定)。注意:源程序包中的文件应用"软件名-版本号"作为其上层目录,这样%setup宏就可以正常工作。如果不以"软件名-版本号"作为其上层目录,则%setup宏工作时有一个指令"cd 软件名-版本号"(转目录)会因为系统中没有此目录而出错退出(除非在此宏上面加上建立此目录的命令)。如LZE软件源程序所在的目录为lze-6.0,我需要用命令"tar cvzf lze-6.0-2.src.tgz lze-6.0"将源程序打包并压缩,这样的包就可以被%setup宏正确使用了。
下面是%setup宏命令所执行的一系列命令: (指令前面为行号)
1 cd /usr/src/dist/BUILD
2 echo "预处理脚本程序(prep)开始执行"
3 cd /usr/src/dist/BUILD
4 rm -rf lze-6.0
5 /bin/gzip -dc /usr/src/dist/SOURCES/lze-6.0-2.src.tgz | tar -xvvf -
6 STATUS=$?
7 if [ $STATUS -ne 0 ]; then
8exit $STATUS
9 fi
10 cd lze-6.0
11 [ `/usr/bin/id -u` = '0' ] && /bin/chown -Rhf root .
12 [ `/usr/bin/id -u` = '0' ] && /bin/chgrp -Rhf root .
13 /bin/chmod -Rf a+rX,g-w,o-w .
14 exit 1
看,第10行就有一个转到lze-6.0目录的命令,如果没有这个目录,程序就会出错退出了。也许你要问:这些指令你是怎么知道的?其实这很简单,只要在%setup宏下面加上一句"exit 1"命令,让预处理脚本程序非正常退出即可。这样RPM所执行的预处理脚本程序作为临时文件在其退出时并未删除,只要看一下这个文件(在/var/tmp目录下以rpm-tmp开头)就知道%setup宏命令做什么了。
(2) -n name :
上面已经谈到,源程序包中的文件应采用"软件名-版本号"作为上层目录。如果用了别的什么目录(如name),%setup宏无法正常工作,那该怎么办?没关系,可以用-n选项,引用一下这个目录(name)就行了。假如我的LZE源程序包中的文件是以lze为上层目录,那么我就可以用"%setup -n lze"宏命令来解压缩该包。
(3) -c :
此选项的作用是创建上层目录("软件名-版本号"目录)并转到这个目录。对于LZE软件,其效果相当于在上例的第4行与第5行之间加上这么两行命令:
mkdir -p lze-6.0
cd lze-6.0
它适用的情况是:有的源程序包是在源程序所在目录下打的包,所以其中的文件都没有上层目录。这样的话,要想正确解压,必须创建上层目录。
(4) -D :
本选项的作用是在解压源程序包之前不要删除软件的上层目录(软件名-版本号)。在上例中,其效果是不执行第4行的命令(rm -rf lze-6.0)。
(5) -T :
本选项的作用是不解压默认的源程序包(由文件头的Source或Source0域所定义)。在上例中,其效果是不执行第5-9行的命令:第5行是解压源程序包(用gzip -dc将包的内容解压缩到管道中,再由tar -xvvf -从管道中读取数据并展开),第6-9行是检查解压命令的返回值,非0时执行非正常退出。
(6) -b N :
本选项指示RPM在转到上层目录前解压第N个源程序包(由文件头SourceN域定义)。这适用于含上层目录的源程序包。注意:如果使用此选项时不同时使用-T选项,则RPM解压的是两个源程序包,一个是默认的包(由Source或Source0域定义),一个是-b选项指定的包(由SourceN域定义)。这样,当N等于0时,默认的源程序包将被解压两次。所以,如果想仅解压指定源程序包,请同时使用-T选项,以禁止解压默认的源程序包。
下面的宏命令仅解压第1个源程序包,然后转到上层目录:
%setup -b 1 -T
(7) -a N :本选项指示RPM在转到上层目录后再解压第N个源程序包(由文件头SourceN域定义)。这适用于不含上层目录的源程序包。使用本选项时,一般加上-c选项,以创建上层目录并转到此目录。注意:如果使用此选项时不同时使用-T选项,则RPM解压的是两个源程序包,一个是默认的包(由Source或Source0域定义),一个是-a选项指定的包(由SourceN域定义)。这样,当N等于0时,默认的源程序包将被解压两次。所以,如果想仅解压指定源程序包,请同时使用-T选项,以禁止解压默认的源程序包。 |
|