RPM-4.4.9をネイティブコンパイルしてみました。なかなかコンパイルできず試行錯誤していますが、怪しいながらもビルドできたようです(本当に?w)。
/usr/local/srcディレクトリで行います
bzip2のサイトよりbzip2-1.0.4.tar.gzをダウンし作業ディレクトリで展開してビルドします。
make
make install PREFIX=/usr/local/develop
ldconfig
以上
RPMのサイトよりpopt-1.12.tar.gzをダウンし作業ディレクトリで展開してビルドします。popt-1.7が入っていますが、どうもうまく動かず置き換え。
./configure --prefix=/usr/local/develop
make
make install
ldconfig
以上
WebDAV.orgよりneon-0.26.4.tar.gzをダウンし作業デヒレクトリで展開してビルドします(0.27だと一部関数名が変わってしまっていてRPMでは使えなかった)。
./configure \
--prefix=/usr/local/develop \
--enable-shared \
--with-ssl \
--with-libs=/usr/local/ssl
make
make install
ldconfig
以上
RPMはdb1か3を使うそうなのでdb3をビルドしときます。今はOracleに買収されてしまったので、ここからdb-3.3.11.tar.gzをダウンしてきます:
cd db-3.3.11/build_unix
../dist/configure --prefix=/usr/local/db3
make
make install
vim /etc/ld.so.conf ←/usr/local/db3/libを追加
ldconfig
以上
RPMのサイトよりrpm-4.4.9.tar.gzをダウンし作業ディレクトリで展開してビルドします(実際はスクリプトから実行しています)。とにかく散々ビルドに失敗してしまい(INSTALL読んでもサッパリ;;)、手当たり次第にオプションを指定しているので合ってるんだか違うんだか…。当初のconfigure時にrpcgenが動作する箇所があったのですが、既述のglibcの作成で出来上がったものを利用しても動作しませんでした。いろいろWebで調べるとrpcgenで/lib/cppを見ているらしく、しかもパスがハードコーディングされているとのことなので/usr/local/develop/bin/cppを/libにリンクを張って逃げました。今のオプションでもrpcgenが動作しているのかどうかはわかりませんが、プチ情報でしたw:
export LC_ALL=POSIX
export PATH=/usr/local/develop/glibc_bin:$PATH ←glibc_binはglibcをビルドした際に作成したbinやsbinの中身です
export LIBFLAGS="-L/usr/local/develop/lib -L/usr/local/db3/lib -L/usr/local/ssl/lib"
export CFLAGS="-I/usr/local/develop/include -I/usr/local/develop/include/neon -I/usr/local/db3/include -I/usr/local/ssl/include -I/usr/local/develop/include/beecrypt"export LIBS="-I/usr/local/src/Python-2.5/Include" ←これもWebで探し回っている時にあったので、おまじないとして
./configure \--prefix=/usr/local/rpm \
--prefix=/usr/local/develop \ ←インストール先を変更しました
--disable-rpath \
--with-javaglue=no \
--with-selinux=no \
--with-python=no \
--with-apidoc=no \
--with-perl=no \
--with-lua=no \
--with-ssl=/usr/local/ssl \
--with-neon=/usr/local/develop \
--with-tcl=no
makeDESTDIR=/mnt/disk1/share make install ←一旦、別の場所にインストール
cd /usr/local
ln -s /mnt/disk1/share/usr/local/rpm rpm ←正規の場所へリンクを貼る
vim /etc/ld.so.conf ←/usr/local/rpm/libを追加
ldconfig
DESTDIR=/mnt/disk1 make install
cd /mnt/disk1/usr/local
tar cvjf rpm-4.4.9-binary.tar.bz2 develop ←後々の為、完成したバイナリをtarボール化して保存しておく
cd /usr/local
tar xvjf rpm-4.4.9-binary.tar.bz2 ←先に保存したtarボールを展開してインストール
時間は掛かりますがビルドには成功したようです。
make tarで出来上がったバイナリをtarファイルにすることが出来るようですが、作業を/tmpで行うので容量オーバーで失敗してしまいました。Makefileを下記の通り書き換え実行します:
.PHONY: tar
tar:
rm -rf /mnt/disk1/rpm-$(VERSION)
$(MAKE) DESTDIR=/mnt/disk1/rpm-$(VERSION) install
cd /mnt/disk1/rpm-$(VERSION) ; tar cvjf /mnt/disk1/rpm-$(VERSION).tar.bz2 .make tar
やっていることは単純にtarの作成なので/mnt/disk1/share/usr/local/rpmにインストールしたものをtarにしても同じです。実際は、こっちをやりました。
INSTALLに書いてある通りに実行:
mkdir -p /mnt/disk1/var/rpm ←/var/lib/rpmをリンクで作成
cd /var/lib
ln -s /mnt/disk1/var/rpm rpm
rpm --initdb
実行すると、/usr/local/rpm/var/lib/rpm/usr/local/develop/var/lib/rpmが初期化されてました…あら?w ということで最初のリンクは不要かなw
早速出来上がったRPMを使ってみることに。普段、rootユーザでは/rootの.profileにroot用の設定をしているので、PATHに/usr/local/rpm/binを追加。普段は/usr/local/develop/binにPATHを通して使っています。
# rpm --help
Usage: rpm [OPTION...]
Query options (with -q or --query):
-c, --configfiles list all configuration files
-d, --docfiles list all documentation files
--dump dump basic file information
-l, --list list files in package
--queryformat=QUERYFORMAT use the following query format
:
:(以下略)
動いてるっぽい。RPMのワークとしてrootfsのパーティションは使いたくないのでインストールされたままの/usr/local/rpm/src/rpmや/usr/local/rpm/varを使うことに(/usr/local/rpmが/mnt/disk1へのリンクなので)。今まではディストリビューションに付属のRPMしか使ったことがなかったので、自分で設定したことなどなく何をすればよいのやら皆目検討が付きませんが、どうやら.rpmmacorosとかは要るらしい。そこで簡単なのをこしらえ/rootに入れときました:
%_topdir /usr/local/develop/src/rpm
%_var /usr/local/develop/var
超手抜きですが、追々考えるということで。
specファイルを一から手書きは面倒というか無理wなので、簡単そうなtarボールとspecを拾ってきてRPMを作ってみることに。specをちょこっとだけ編集して(--prefix=/usr/local/developとか)、tarボールは/usr/local/rpm/src/rpm/SOURCEに置いて実験してみる:
# rpmbuild -ba /usr/local/rpm/src/rpm/SPECS/fd.spec
しばらくすると、/usr/local/rpm/src/rpm/RPMS/armv5tejlにFDclone-2.09d-ls1.armv5tejl.rpm、/usr/…略…/SRPMSにFDclone-2.09d-ls1.src.rpmが出来上がったようだ。中身もそれっぽいものが入っていましたw
早速、出来上がったRPMを使って意気揚々とインストールを試みる…が、見事に失敗…orz
# rpm -ivh FDclone-2.09d-ls1.armv5tejl.rpm
error: Failed dependencies:
/bin/sh is needed by FDclone-2.09d-ls1.armv5tejl
/usr/local/develop/bin is needed by FDclone-2.09d-ls1.armv5tejl
/usr/local/develop/etc is needed by FDclone-2.09d-ls1.armv5tejl
/usr/local/develop/man/ja is needed by FDclone-2.09d-ls1.armv5tejl
/usr/local/develop/man is needed by FDclone-2.09d-ls1.armv5tejl
/usr/local/rpm/doc is needed by FDclone-2.09d-ls1.armv5tejl
どうやら依存関係がまったくダメのようで、しかし依存ってファイルだけでなくディレクトリも対象なんですか??? --nodepsで強制的にインストールはできましたが、これではRPMの魅力半減です。
いろいろ調べて調整。まずは、specにAutoReq: 0を追加して再構築してみるも変化なし。INSTALLを読み直してみるとvpkg-provides.shを使って仮想パッケージを作って導入しろみたいなことが書いてある(英語なんで解釈が怪しいですが)。確かにrpm --initdb直後で依存するファイルなど登録されていないまっさらな状態です。しかし、肝心のvpkg-provides.shがLinux非対応のようで、スクリプト言語が苦手な私には書き換える根性がありません。仕方ないので手書きでそれっぽいのを作って作成するも、なかなかうまくいきません。
そもそも/bin/shが無いと言って怒るのは納得するのですが、ディレクトリまで登録する必要があるんでしょうか?。/bin/shはbuildやinstall過程を見て勝手に加えられていると思うのですが、AutoReq: 0が効いてないってことでしょうか? specのProvidesにディレクトリやファイル名を山ほど書いても、相変わらず状況は改善しません。Providesはパッケージ名だけでファイルやディレクトリを書いても意味無いんでしょうか?(詳しい方ご教示頂けるとありがたいです、お願いします)。
仕方無いのでダミーのディレクトリを作って云々というのを試してみることに:
Summary: RPM bootstrap dummy package.
Name: ls-gl
Version: 1.0
Release: 7
Group: System Environment/Shells
BuildRoot: %{_tmppath}/%{name}-%{version}-root
License: Freeware
AutoReqProv: 0
Source: bash_bin.tar.bz2 ←既存のbashをbash.orgという名前で単純に圧縮しただけのtarボール
Source1: ldconfig.sh ←既存のldconfigコマンドを呼び出すだけのシェルスクリプト
Source2: openssl.sh ←既存のopensslコマンドを呼び出すだけのシェルスクリプト
Source3: useradd.sh ←既存のuseraddコマンドを呼び出すだけのシェルスクリプト
Source4: userdel.sh ←既存のuserdelコマンドを呼び出すだけのシェルスクリプト
Source5: groupadd.sh ←既存のgroupaddコマンドを呼び出すだけのシェルスクリプト
Source6: groupdel.sh ←既存のgroupdelコマンドを呼び出すだけのシェルスクリプト
%description
Virtual files package for LinkStation LS-GL seriese.
%description(ja)
LinkStation LS-GLシリーズ用の初期設定用仮想ファイルパッケージ
です。既にシステムにインストール済みのファイルをRPMの依存関
係データベースに登録、認識させるためのダミーです。#Provides: /bin/sh
#Provides: /usr/local/develop/arm-none-linux-gnueabi
#Provides: /usr
#Provides: /usr/local
#Provides: /usr/local/develop
#Provides: /usr/local/develop/bin
#Provides: /usr/local/develop/lib
#Provides: /usr/local/develop/etc
#Provides: /usr/local/develop/libexec
#Provides: /usr/local/develop/share
#Provides: /usr/local/develop/include
#Provides: /usr/local/develop/man
#Provides: /bin/bash
%prep
%setup -n bash_bin
%build
%install
rm -rf $RPM_BUILD_ROOT
mkdir -p $RPM_BUILD_ROOT
mkdir -p $RPM_BUILD_ROOT/var/cache
mkdir -p $RPM_BUILD_ROOT/sbin
mkdir -p $RPM_BUILD_ROOT/bin
mkdir -p $RPM_BUILD_ROOT/etc/pam.d
cp bash.org $RPM_BUILD_ROOT/bin ←bash.orgを/binへコピー
mkdir -p $RPM_BUILD_ROOT/usr/bin
mkdir -p $RPM_BUILD_ROOT/usr/sbin
mkdir -p $RPM_BUILD_ROOT/usr/local
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/bin
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/sbin
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/lib
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/lib/mysql
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/etc
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/etc/rc.d/init.d
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/etc/logrotate.d
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/etc/cron.d
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/etc/cron.hourly
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/etc/cron.daily
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/etc/cron.weekly
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/etc/cron.monthly
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/info
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/libexec
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/man/ja
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/info
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/aclocal
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/doc
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/misc
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/locale/ja/LC_MESSAGES
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/locale/en/LC_MESSAGES
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/locale/en@quot/LC_MESSAGES
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/locale/en@boldquot/LC_MESSAGES
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/include
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/man/ja
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/var/log
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/var/lib
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/var/tmp
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/var/run
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/var/cache
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/var/spool
for i in 0 1 2 3 4 5 6 7 8 9 n; do ←man用dirを堀りまくる
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/man/man$i
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/man/ja/man$i
done
for i in 0 1 3; do
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/man/man${i}p
mkdir -p $RPM_BUILD_ROOT/mnt/disk1/develop/share/man/ja/man${i}p
done
cd $RPM_BUILD_ROOT/usr/local
ln -s ../../mnt/disk1/develop develop
cd $RPM_BUILD_ROOT/usr/local/develop/etc
ln -sf ./rc.d/init.d init.d
cd $RPM_BUILD_ROOT/bin
ln -s ./bash.org sh ←bash.orgへのリンクを張る
cp %{_sourcedir}/ldconfig.sh $RPM_BUILD_ROOT/sbin
cp %{_sourcedir}/openssl.sh $RPM_BUILD_ROOT/sbin
cp %{_sourcedir}/useradd.sh $RPM_BUILD_ROOT/sbin
cp %{_sourcedir}/userdel.sh $RPM_BUILD_ROOT/sbin
cp %{_sourcedir}/groupadd.sh $RPM_BUILD_ROOT/sbin
cp %{_sourcedir}/groupdel.sh $RPM_BUILD_ROOT/sbin
%clean
rm -rf $RPM_BUILD_ROOT
%files
%dir /
%dir /var
%dir /var/cache
%dir /etc
%dir /etc/pam.d
%dir /bin
%dir /sbin
%dir /usr
%dir /usr/bin
%dir /usr/sbin
%dir /usr/local
%dir /usr/local/develop
%dir /usr/local/develop/bin
%dir /usr/local/develop/sbin
%dir /usr/local/develop/lib
%dir /usr/local/develop/lib/mysql
%dir /usr/local/develop/etc
%dir /usr/local/develop/etc/init.d
%dir /usr/local/develop/etc/rc.d
%dir /usr/local/develop/etc/rc.d/init.d
%dir /usr/local/develop/etc/logrotate.d
%dir /usr/local/develop/etc/cron.d
%dir /usr/local/develop/etc/cron.daily
%dir /usr/local/develop/etc/cron.hourly
%dir /usr/local/develop/etc/cron.monthly
%dir /usr/local/develop/etc/cron.weekly
%dir /usr/local/develop/info
%dir /usr/local/develop/libexec
%dir /usr/local/develop/share
%dir /usr/local/develop/share/info
%dir /usr/local/develop/share/aclocal
%dir /usr/local/develop/share/doc
%dir /usr/local/develop/share/misc
%dir /usr/local/develop/share/locale
%dir /usr/local/develop/share/locale/*
%dir /usr/local/develop/share/locale/*/LC_MESSAGES
%dir /usr/local/develop/include
%dir /mnt
%dir /mnt/disk1
%dir /mnt/disk1/develop
%dir /usr/local/develop/share/man
%dir /usr/local/develop/share/man/ja
%dir /usr/local/develop/share/man/man[0123456789n]
%dir /usr/local/develop/share/man/ja/man[0123456789n]
%dir /usr/local/develop/share/man/man[013]p
%dir /usr/local/develop/share/man/ja/man[013]p
%dir /usr/local/develop/var
%dir /usr/local/develop/var/log
%dir /usr/local/develop/var/lib
%dir /usr/local/develop/var/tmp
%dir /usr/local/develop/var/run
%dir /usr/local/develop/var/cache
%dir /usr/local/develop/var/spool
/bin/bash.org
/bin/sh
/sbin/ldconfig.sh
/sbin/openssl.sh
/sbin/useradd.sh
/sbin/userdel.sh
/sbin/groupadd.sh
/sbin/groupdel.sh
こんな嘘っぽーいのを書いてrpmbuildしてインストールしてみると改善されたようです。
# rpmbuild -bb ls-gl.spec
# rpm -ivh ls-gl-1.0-l.armv5tejl.rpm
Preparing... ########################################### [100%]
1:ls-gl ########################################### [100%]
# rpm -ivh --test FDclone-2.09d-ls1.armv5tejl.rpm
Preparing... ########################################### [100%]
1:FDclone ########################################### [100%]
# rpm -qa
ls-gl-1.0-l.armv5tejl
FDclone-2.09d-ls1.armv5tejl
本当にこれで解決になってるんだろうか?私にはRPMは謎だらけです…
尚、ls-glはパッケージをアンインストールすると/bin/shを削除してしまうので、アンインストした後で手動で/bin/shのリンクを張らないといけません。
RPM本体を導入する前にRPM本体が依存するものは予め手動で入れておかないといけないのでRPMをTarボールに変換してくれるRPM2TARGZを作成しました(他にもっとよいものがあれば教えてください)。RPM2TARGZはSlackwareから(/Linux/slackware/slackware-12.0/source/a/rpm2tgz)拝借しました。中に入っているgetrpmtypeは作成したrpm4.4.9に対応していないようなのですが無くても動作するようなので使いません:
%define _prefix/usr/local/develop
Summary: A RPM coverto to tarball.
Summary(ja): RPMをTarボールに変換するプログラム
Name: rpm2targz
Version: 1.0
Release: LS
License: GPL
Group: Applications/Archiving
Source: rpm2targz.tar.bz2 ←rpm2targzというdirにrpmoffset.c、rpm2targzを入れて圧縮してあるTarボール
Buildroot: %{_tmppath}/%{name}-%{version}-root
Requires: cpio
%description
convert RPM format file to tar.gz
%prep
%setup -n rpm2targz
%build
#make ←getrpmtype用ですがビルド出来なかったのでコメント(rpmの関数が見つからないようです)
gcc -o rpmoffset rpmoffset.c
%install
rm -rf ${RPM_BUILD_ROOT}
mkdir -p $RPM_BUILD_ROOT%{_prefix}/bin
#cp getrpmtype ${RPM_BUILD_ROOT}%{_prefix}/bin
cp rpmoffset ${RPM_BUILD_ROOT}%{_prefix}/bin
cp rpm2targz ${RPM_BUILD_ROOT}%{_prefix}/bin
%clean
rm -rf $RPM_BUILD_ROOT
%files
%defattr(-,root,root)
%{_prefix}/bin/*
とまぁ、上記のようないい加減ではありますがspecファイルを作ってビルドする。
# rpmbuild -ba rpm2targz.spec
# rpm -ivh rpm2targz-1.0-LS.armv5tejl.rpm
# rpm2targz XXXXX.rpm
適当に自分で作成したRPMファイルに対して使ってみましたがtar.gzは出来上がるようです。
当方はネイティブコンパイルの作成にもあるように、作成した開発環境を/usr/local/developにインストールして使っています(実際は/mnt/disk1に展開して/usr/local/developからリンクを張り、なるべく本来のrootfsを汚さない形で運用しています)。この開発環境をベースに、これまでビルドしたものはmake installで/usr/local/developに導入していましたが、折角rpmを作成したので今後はrpmで運用してみようと思います。そこで、rpm自身も/usr/local/developに導入するようにビルドし直し、これまでmake installで何かと導入してしまったベースの開発環境も破棄してまっさらにな状態から再度RPM環境を作ってみました。
しかし卵が先か鶏が先かという問題もありRPM自身がRPMで管理したいパッケージに依存することもあるので、RPMを動作させるのに最低限必要そうなライブラリだけは手動でランタイムだけ入れておきます(又、RPMパッケージの作成でもこの卵と鶏状態になることがしばしばあるので旧環境も温存しておき適宜切り替えてSRPMのビルドを行っています):
cd /usr/local
rm develop ←これまでの旧開発環境へのリンクを削除
cd /mnt/disk1
mv develop develop.old ←旧開発環境をリネームして温存
tar xvjf develop.tar.bz2 ←ネイティブコンパイルの作成で作成した開発環境を展開
cd /usr/local
ln -s /mnt/disk1/develop develop ←rootfsの/usr/localから新開発環境へリンクを張る
cd /usr/local/develop/lib
cp /mnt/disk1/develop.old/lib/libbeecrypt.so.6.4.0 . ←旧開発環境(/mnt/disk1/develop.old)よりbeecryptのランタイムをコピー
ln -s libbeecrypt.so.6.4.0 libbeecrypt.so.6
cp /mnt/disk1/develop.old/lib/libneon.so.26.0.3 . ←旧開発環境よりneonのランタイムをコピー
ln -s libneon.so.26.0.3 libneon.so.26
ln -s libneon.so.26.0.3 libneon.so
cd /usr/local
tar xvjf rpm-4.4.9-binary.tar.bz2 ←先にビルドしたRPMを/usr/local/developに導入する
ldconfig ←/etc/ld.so.confには予め/usr/local/develop/libを記載しておく
mkdir -p /usr/local/develop/var/tmp ←SRPMビルド時の作業用ディレクトリを作成
mkdir -p /usr/local/develop/var/spool/repackage ←rpm -e用?ディレクトリ作成
rpm --initdb
これでRPM管理に対応した初期開発環境が出来上がった(はずw)。尚、rpmbuildで作業を行うには最低限、make、sed、gawk、grep、bzip2、gzip等のコマンド(busyboxのものは避ける)が必要ですので、これらも旧開発環境からコピーしておき、足りなければ追加します。
そして最初に先述のls-gl仮想パッケージ(ちっとも仮想になってないような…)をインストールして各種PathをRPMのDBに登録しておきます。本来は他のパッケージからの被依存度100%なのでしょうが、何かと都合が悪いので被依存無しにしていますw。
RPMそのものをビルドする人が少ないのか、Webでも余り情報が得られず技量のない私には四苦八苦でしたが、もう少し動作検証しないとちゃんと動いてるんだかどうかわかりませんねw