0、如果懒得打包
直接根据目标机器的环境进行编译,然后将可执行文件发过去就好了。如果可执行文件还是太大,可以用strip(脱衣服),就是扒掉调试用的符号信息等,一般能压缩到原来的一成不止。
strip your_executable_file
这时候再用nm,就查不到符号信息了。
1、主要使用场景
1、当目标机中不存在编译环境时,可以先在本地环境中编译打包,然后直接在目标机中用rpm -ivh *.rpm安装即可。
2、当需要在目标机中安装多个软件或者增加多个文件时,可以将整体打成RPM包,方便使用。
2、打包过程
1、安装rpmdevtools
yum install rpmdevtools
2、生成rpm打包目录,生成的目录在用户根目录(~)下。
rpmdev-setuptree
3、进入SPEC目录,并生成模板文件
cd rpmbuild/SPECS
rpmdev-newspec tar.spec
4、将要打包的源码以tar.gz的格式移动到SOURCES目录
mv ~/source.tar.gz ../SOURCES
5、编写spec文件
在spec文件运行时,定义的宏会主动读取/usr/lib/rpm/macros中的变量
RPM_BUILD_DIR ~/rpmbuild/BUILD
RPM_BUILD_ROOT ~/rpmbuild/BUILDROOT
6、生成RPM包
rpmbuild -ba test.spec
生成的RPM包在rpmbuild/RPMS目录下。
3、gnu编译规则
三部曲:
./configure
make
make install
1、常用configure参数(根据目标机器的实际环境参数进行修改,若修改生成目标程序的名字,可以在–program-prefix=后面赋值,这代表着给程序加前缀)
./configure --build=x86_64-redhat-linux-gnu --host=x86_64-redhat-linux-gnu --program-prefix= --disable-dependency-tracking --prefix=/usr --exec-prefix=/usr --bindir=/usr/bin --sbindir=/usr/sbin --sysconfdir=/etc --datadir=/usr/share --includedir=/usr/include --libdir=/usr/lib64 --libexecdir=/usr/libexec --localstatedir=/var --sharedstatedir=/var/lib --mandir=/usr/share/man --infodir=/usr/share/info DEFAULT_RMT_DIR=/etc RSH=/usr/bin/ssh
2、gnu输入参数处理argp
argp编程,使用gnu的argp进行入参分析。在前边用长短参数定义好,在数组options中:
{"flow-control", 'e', N_("threshold"), 0,
N_("set threshold for flow control"), GRID+1 },
入参分析使用函数argp_parse
argp是入参分析的核心结构体,包括要分析的选项和对应的处理函数。
中间传入的parse_opt函数有三个入参,第一个是前置选项(key),第二个是紧跟的参数(arg),如-e 10MB 或者–flow-control=10mb。
argp_parse (&argp, argc, argv, ARGP_IN_ORDER, &idx, &args);
static struct argp argp = {
options,
parse_opt,
N_("[FILE]..."),
doc,
NULL,
tar_help_filter,
NULL
};
parse_opt (int key, char *arg, struct argp_state *state)
3、gnu提供了一些c函数的封装,考虑了错误处理和异常情况,很省心,建议用,如:
safe_read();
full_write();
xmalloc();
xfork();
等
附录:
1、spec基本信息
Name: 软件名称
Version: 软件版本
Release: 发布次数 如: 1%{?dist}
Summary: 软件说明
Group: 软件分组
License: 授权模式,例如 GPL,即自由软件
URL: 源码包的URL地址,可随意填写
Source0: 源码包,可指定多个,下面可用%{SOURCE0}变量引用
BuildRoot: 编译过程中的中间存档目录,考虑到多用户的环境,一般定义为:
%{_tmppath}/%{name}-%{version}-%{release}-root ,
后面可使用$RPM_BUILD_ROOT 方式引用
BuildArch: 平台 %{_arch}
BuildRequires: 编译过程依赖的工具
Requires: 打包生成的rpm包安装时所依赖的软件包
%description 说明文档
%prep 准备部分,比如创建目录,解压源码包等,可使用%setup内部函数
%build 在BUILD目录编译,可使用%configure内部函数,或者其他编译工具,如cmake, perl等
%install 安装到BUILDROOT虚拟目录
%clean 清理文件
%files 将指定的文件添加到rpm包中,文档类型可用%doc,配置文件可 用%config
%changelog 更新记录.格式: 第一行 "* 日期 作者 " 第二行 "- 更新内容"
最终的生成的rpm名称: {Name}-{Version}-{Relesae}-{BuildArch}.rpm
2、spec代码实例(git和wget)
Name: git
Version: 2.10
Release: 1%{?dist}
Summary: this is the test code
License: GPL
URL: http://www.hao123.com
Source0: %{name}-%{version}.tar.gz
BuildRoot: %{_tmppath}/%{name}-%{version}-root
BuildRequires: automake
Requires: rpm
%description
%prep
%setup -q
%build
autoconf
./configure --prefix=/opt/git/
make %{?_smp_mflags}
%install
make DESTDIR=$RPM_BUILD_ROOT install
%clean
[ "$RPM_BUILD_ROOT" != "/" ] && rm -rf "$RPM_BUILD_ROOT"
make clean
%files
%defattr (-,root,root)
/opt/git/
%changelog
# This is a sample spec file for wget
%define _topdir /home/strike/mywget
%define name wget
%define release 1
%define version 1.12
%define buildroot %{_topdir}/%{name}-%{version}-root
BuildRoot: %{buildroot}
Summary: GNU wget
License: GPL
Name: %{name}
Version: %{version}
Release: %{release}
Source: %{name}-%{version}.tar.gz
Prefix: /usr
Group: Development/Tools
%description
The GNU wget program downloads files from the Internet using the command-line.
%prep
%setup -q
%build
./configure
make
%install
make install prefix=$RPM_BUILD_ROOT/usr
%files
%defattr(-,root,root)
/usr/local/bin/wget
%doc %attr(0444,root,root) /usr/local/share/man/man1/wget.1