使用CheckInstall从源码制作RPM安装包
文章目录
一、下载并安装CheckInstall
- RPM安装包 目前最新的包为1.62版,CentOS 6.X的RPM安装包可以下载 checkinstall-1.6.2-1.cnt6.x86_64.rpm 然后:
1sudo rpm -ivh checkinstall-1.6.2-1.cnt6.x86_64.rpm
2sudo ln -s /usr/lib64/checkinstall/installwatch.so /usr/lib64/installwatch.so
3sudo ln -s /usr/lib64/checkinstall/checkinstallrc /etc/checkinstallrc
- 源码包 从官网下载源码 checkinstall-1.6.2.tar.gz 解压:
1tar xvf checkinstall-1.6.2.tar.gz
编译会报错:
1installwatch.c:2942:5: 错误:与‘readlink’类型冲突
2 int readlink(const char *path,char *buf,size_t bufsiz) {
3 ^
4In file included from installwatch.c:41:0:
5/usr/include/unistd.h:828:16: 附注:‘readlink’的上一个声明在此
6 extern ssize_t readlink (__const char *__restrict __path,
7 ^
8installwatch.c:3080:5: 错误:与‘scandir’类型冲突
9 int scandir( const char *dir,struct dirent ***namelist,
10 ^
11In file included from installwatch.c:49:0:
12/usr/include/dirent.h:252:12: 附注:‘scandir’的上一个声明在此
13 extern int scandir (__const char *__restrict __dir,
14 ^
15installwatch.c:3692:5: 错误:与‘scandir64’类型冲突
16 int scandir64( const char *dir,struct dirent64 ***namelist,
17 ^
18In file included from installwatch.c:49:0:
19/usr/include/dirent.h:275:12: 附注:‘scandir64’的上一个声明在此
20 extern int scandir64 (__const char *__restrict __dir,
修改源文件installwatch.c: 101行:
1static int (*true_scandir)( const char *,struct dirent ***,
2 int (*)(const struct dirent *),
3 int (*)(const void *,const void *));
改为:
1static int (*true_scandir)( const char *,struct dirent ***,
2 int (*)(const struct dirent *),
3 int (*)(const struct dirent **,const struct dirent **));
121行:
1static int (*true_scandir64)( const char *,struct dirent64 ***,
2 int (*)(const struct dirent64 *),
3 int (*)(const void *,const void *));
改为:
1static int (*true_scandir64)( const char *,struct dirent64 ***,
2 int (*)(const struct dirent64 *),
3 int (*)(const struct dirent64 **,const struct dirent64 **));
2529行:
1FILE *fopen(const char *pathname, const char *mode) {
2 FILE *result;
改为:
1FILE *fopen(const char *pathname, const char *mode) {
2 FILE *result=0;
2941行:
1#if (GLIBC_MINOR <= 4)
2int readlink(const char *path,char *buf,size_t bufsiz) {
3 int result;
4#else
5ssize_t readlink(const char *path,char *buf,size_t bufsiz) {
6 ssize_t result;
7#endif
改为:
1#if 0
2int readlink(const char *path,char *buf,size_t bufsiz) {
3 int result;
4#else
5ssize_t readlink(const char *path,char *buf,size_t bufsiz) {
6 ssize_t result;
7#endif
3080行:
1int scandir( const char *dir,struct dirent ***namelist,
2 int (*select)(const struct dirent *),
3 int (*compar)(const void *,const void *) ) {
改为:
1int scandir( const char *dir,struct dirent ***namelist,
2 int (*select)(const struct dirent *),
3 int (*compar)(const struct dirent **,const struct dirent **) ) {
3692行:
1int scandir64( const char *dir,struct dirent64 ***namelist,
2 int (*select)(const struct dirent64 *),
3 int (*compar)(const void *,const void *) ) {
改为:
1int scandir64( const char *dir,struct dirent64 ***namelist,
2 int (*select)(const struct dirent64 *),
3 int (*compar)(const struct dirent64 **,const struct dirent64 **) ) {
来一个直观的修改对比:
修改完成后再重新编译。
二、使用CheckInstall
这里使用的CheckInstall的RPM安装包进行安装的。 在使用checkinstall之前需要做一点小修改,以免在执行的过程中报错:
1error: File not found: /root/rpmbuild/BUILDROOT/
编辑/usr/bin/checkinstall
1sudo vim /usr/bin/checkinstall
搜索关键词-bb,笔者的是在2451行,将:
1$RPMBUILD -bb ${RPM_TARGET_FLAG}${ARCHITECTURE} "$SPEC_PATH" &> ${TMP_DIR}/rpmbuild.log
改为:
1$RPMBUILD -bb ${RPM_TARGET_FLAG}${ARCHITECTURE} --buildroot=$BUILD_DIR "$SPEC_PATH" &> ${TMP_DIR}/rpmbuild.log
下面以制作GCC 9.2的安装包为例,在make完成后,使用checkinstall:
1sudo checkinstall
中途可能会出现:
1======================== Installation successful ==========================
2
3Copying files to the temporary directory...OK
4
5Stripping ELF binaries...OK
6
7Compressing man pages...OK
8
9Building file list...OK
10
11/root/rpmbuild has no SOURCES directory. Please write the path to
12the RPM source directory tree:
可以安装rpmdevtools:
1sudo yum install rpm-build -y
2sudo yum install rpmdevtools -y
3sudo rpmdev-setuptree
可以看到/root/rpmbuild目录了
再重新执行前面的checkinstall命令,可以看到成功生成RPM安装包,路径在/root/rpmbuild/RPMS/x86_64目录中,并且已经执行了一次RPM安装包的安装,通过
1rpm -qa | grep gcc
可以看到,如图所示。
从上图中可以看到
1Install RPM package... OK
以及
1Writing backup package... OK
即会自动安装RPM包以及备份,同时生成的安装包默认是在/root/rpmbuild/RPMS/目录,我们可以在执行sudo checkinstall的时候添加参数改变这些行为,改为:
1sudo checkinstall --install=no --backup=no --pakdir=.
这样就会在将生成的RPM包放在当前目录,并且不会在制作RPM完成后自动安装和备份。 每次都这样写岂不是很麻烦,修改/usr/lib64/checkinstall/checkinstallrc中的内容即可:
1PAK_DIR="."
2BACKUP=0
3INSTALL=0
本文所用系统为Centos 6.10
- 原文作者:Witton
- 原文链接:https://wittonbell.github.io/posts/2020/2020-10-29-使用CheckInstall从源码制作RPM安装包/
- 版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 4.0 国际许可协议. 进行许可,非商业转载请注明出处(作者,原文链接),商业转载请联系作者获得授权。