RPM を使ったパッケージの作成方法 (RPM-BUILD-HOWTO) 古高和禎(ふるたか@原研),furutaka@Flux.tokai.jaeri.go.jp 石岡 尚(ishi), ishioka@PPP01.infoPepper.or.jp 第 0.5 版 96/12/02 この文書では、RPM (Redhat Package Manager) を使ったバイナリパッケージ (*.rpm) 及びソースパッケージ (*.src.rpm) の作成方法を説明します。な お、説明する RPM の機能は、執筆時の最新版である 2.2.9 のものです。 注意: この文書はかなり以前に書かれたものなので、いまどきの Linux 環境 にはあてはまらない箇所があります。 (JF Project) ______________________________________________________________________ 目次 1. 概要 1.1 この文書に書かれている事 1.2 著作権及び配付条件 1.3 フィードバック 2. RHL 以外のディストリビューションへの RPM のインストール 2.1 必要なファイル 2.2 インストール 3. 設定ファイルと作成ツリー 3.1 設定ファイル 3.2 パッケージ作成ツリー 3.3 個人用作成ツリー 4. パッケージ作成の準備 I (パッチ等の作成) 4.1 まずは make 出来るように... 4.2 「仮想」インストール 5. パッケージ作成の準備 II (spec ファイルの記述法) 5.1 spec ファイルの例 5.2 例に登場していないタグ 5.3 %setup マクロのオプションの使用例 5.3.1 ソースのディレクトリ名を指定する (%setup -n ) 5.3.2 ディレクトリを作成してからソースを展開する (%setup -c) 5.3.3 複数ソース、パッチを当てる 5.4 Undocumented (?) %patch functions 6. パッケージ作成 7. 作成したパッケージのテスト 8. 依存性(dependencies)について 8.1 依存性(dependencies) 8.2 仮想パッケージ 8.3 依存性関係の自動的な追加 9. アドバンスト・コース 9.1 パッケージへの電子的署名 10. よくあるトラブル 10.1 日本語環境で用いた場合に Seg.Fault する事への対策 10.2 /etc/rpmrc が無い! 10.3 RPM をアップグレードした際にエラーが出る 11. 謝辞 ______________________________________________________________________ 1. 概要 1.1. この文書に書かれている事 この文書では、Red Hat Software の開発したパッケージマネージメントツー ル、Redhat Package Manager (RPM) を用いたバイナリ及びソースパッケージ の作成方法を解説しています。 この文書では、RPM を用いた、バイナリパッケージのインストール及び更新方 法、情報の問い合わせ方法や検証方法は解説しておりません。これらに関して は、 RPM-HOWTO , RPM-Tips 及び rpm(8) の man page (またはそれらの翻訳)を参照して下さい。 RPM-HOWTO は、山縣 敦 さんが日本語に翻訳 して下さいました。 rpm(8) の man page は、第一筆者が翻訳し、随時 Linux-ML 等に流しており ます。 なお、この文書では、パッケージマネージャを``RPM'' と大文字で表記し、そ れを用いて作られるバイナリパッケージ (*.rpm)及びソースパッケー ジ(*.src.rpm) と区別しています。 1.2. 著作権及び配付条件 この文書の著作権は古高和禎及び石岡尚にあるものとします。 また、この文書は、GPL に従って自由に配付・利用できるものとします。 1.3. フィードバック この文書は、筆者達が package-ML における RPM を使用したパッケージング の実験を通して得た少ない経験及び知識をまとめたものです。 従って、筆者の誤解による誤った記述や欠落してしまっている情報が数多くあ るものと思われます。 誤りや追加すべき情報を発見なさった方は、第一筆者にお知らせ頂ければ、文 書の更新時に訂正/追加を行なって参ります。 2. RHL 以外のディストリビューションへの RPM のインストール RPM とは、Redhat Package Manager の略で、その名の通り Red Hat Software (RHS) の Linux ディストリビューション Red Hat Linux (RHL)用に開発されたツールで、ソフトウェアのインストール、保守、 パッケージングを行ないます。 しかし、RPM は RHL 以外では使えない訳ではありません。むしろ、RHS の面 々が様々な文書で言っているように、「他のディストリビューションでも容易 に使える」のです (実際、最近では、とある理由から Debian ディストリ ビューションで RPM のバイナリパッケージが流通されていた筈です)。ま た、Red Hat 以外のディストリビューションを使用している方も RPM を容易 に使用できる様に、RPM のバイナリを(RPM を用いずに) インストールする方 法が(現在のところix86アーキテクチャのみですが)用意されています。 この節では RHL 以外の ix86 アーキテクチャ用ディストリビューションに RPM をインストールする方法を解説します。 RHL ディストリビューションを 用いている方は、RPM がインストールされていますから、この節は飛ばして構 いません。 (もし、使用している RPM が古いもので、この文書で説明してい る機能が使いたいのに使えない、という場合は、Red Hat 自身による RPM の アップグレード法に従って下さい。) 2.1. 必要なファイル RPM を使用するためには、 o GNU cpio (version 2.4.1 以降のもの) o rpm-2.2.9-1.i386.cpio.gz が必要です。これらのファイルは Red Hat の本家ミラーサイト 及び、そのミラーサイトの対応するディレクトリ (例えば、日本国内なら、 KDD のミラー 等)にあります。 お使いのシステムに既に cpio がインストールされていても、バージョンが古 い場合には (例えば Slackware 3.0 に含まれている ``GNU cpio version 2.3'') RPM が用いる --quiet というオプションが備わっていないので RPM 2.2.9 と組み合わせては使用できません。この場合は、上記ミラーサイト等か ら cpio も ftp し、現在インストールされている cpio と入れ換えておいて 下さい。 2.2. インストール 必要なファイルが揃ったら、root になって、 ``/'' ディレクトリで gunzip < rpm-2.2.9-1.i386.cpio.gz | cpio -ivumd と入力して下さい。 次に RPM の使用するデータベースファイルの準備をしましょう。 まず、root のまま(CWD は何処でも構いません)、 RPM の使用するデータベー スファイルを置くためのディレクトリを作成しましょう。 mkdir /var/lib/rpm そして、 rpm --initdb とすれば、/var/lib/rpm にデータベースファイルが作成されます。 これで RPM のインストールは完了しました。 RPM を用いて、.rpm バイナリ パッケージのインストールを行なう事が出来る筈です! 3. 設定ファイルと作成ツリー 3.1. 設定ファイル RPM に対する設定は、 o /usr/lib/rpmrc, o /etc/rpmrc, o $HOME/.rpmrc という(設定レベルの異なる)三種類のファイルにより行なわれており、夫 々 /usr/lib/rpmrc RHS の勧める RPM の設定が記述されている /etc/rpmrc サイト毎の設定ファイル $HOME/.rpmrc 各個人毎に設定を行なうためのファイル という役割を担っています。この中で、/usr/lib/rpmrcは RPM パッケージ に含まれていますが、/etc/rpmrc 及び $HOME/.rpmrc は各自が作成する必 要があります。 (RPM バージョン 2.2.7 以前は /etc/rpmrc も配付パッ ケージに含まれて いたのですが、バージョン 2.2.8 以降は望ましい設定 値が全て /usr/lib/rpmrc に書かれるようになったため、同梱されなくな りました。 ``/etc/rpmrc が無い!'' 節を参照して下さい。また、バー ジョン 2.2.8 でのバグについては、 ``RPM をアップグレードした際にエ ラーが出る'' 節を参照して下さい。) 3.2. パッケージ作成ツリー RPM は、ディフォルト(即ち、/usr/lib/rpmrcの設定)では、パッケージ作成ツ リーの最上位ディレクトリを topdir: /usr/src/redhat とし、その下にある o BUILD o RPMS o RPMS/{i386,axp,sparc} o SOURCES o SPECS o SRPMS というディレクトリを利用します。 RPM を用いたパッケージを root として作成するためには不可欠ですの で、対応するディレクトリツリーを作成しておいて下さい。 夫々のディレクトリは BUILD ソースを展開し、パッチを当て、make を行なう RPMS/{i386,axp,sparc} 完成したバイナリパッケージ(*.rpm)が置かれる (使用しているシステムが ix86 アーキテクチャなら、RPMS/i386 に置 かれます。) SOURCES ソースファイル、パッチを置く (``glint'' の使用するアイコン用の gif ファイル等もここに置きま す。) SPECS パッケージ作成用の仕様書(spec ファイル)を置く SRPMS 完成したソースパッケージ(*.src.rpm)が置かれる ために用いられます。 この他にも、make して出来たファイルをその下に「仮想的にインストール」 してバイナリパッケージを作成するためのディレクトリ(``BuildRoot:'')も用 いられます。こちらは、作成する各パッケージ毎に設定できますので、 ``spec ファイルを書く際'' に説明します。 3.3. 個人用作成ツリー 以上のディレクトリツリーさえ有れば、root としてパッケージを作成する事 が出来ます。 しかし、/usr/src 以下には(恐らく)書き込み権の無い一般ユーザ「も」自分 のホームディレクトリ以下にパッケージ作成用ディレクトリツリーを設定 し、RPM を用いてパッケージを作成する事が出来ます。 パッケージ作成用ディレクトリツリーを一般ユーザのホームディレクトリ以下 に設定するには、そのユーザの $HOME/.rpmrc ファイル中に topdir: /home/hogehoge/ と書いておき、以下に BUILD, RPMS,... といったサブディレク トリを作成しておけば良いのです。ここでは、ユーザ hogehoge のパッケージ 作成用ディレクトリを、そのホームディレクトリの下の に設定 しています (勿論、 はあなたが使用する実際の作成用ディレク トリに置き換えて下さい)。 以後、 /home/hogehoge/ 等を と記述します。 4. パッケージ作成の準備 I (パッチ等の作成) 4.1. まずは make 出来るように... まずは、オリジナルのソースを展開し、make 出来る様にしましょう。 ここでは、ソースファイルが harehore-1.23.tar.gz というファイルに保存さ れているとします。 1. /SOURCES に harehore-1.23.tar.gz を持って来ます。 2. /BUILD で、オリジナルソースを展開します。必要な(ソフト自体 に対する)パッチも当てましょう。 (新たにディレクトリを作り、そこにファイルを展開する「のでない」アー カイブの場合は、後々のために ``harehore-1.23'' というディレクトリを 作成し、そのディレクトリに移って展開して下さい。) 3. ディレクトリ ``harehore-1.23'' の名前を ``harehore-1.23.orig'' 等に 変更します。 4. 1. の操作を繰り返し、再び ``harehore-1.23'' 中にソースファイルを展 開します。 5. ``harehore-1.23'' に移り、うまくmake 出来るようになるまで変更を加え ます。 6. うまく make 出来るようになったら、make clean 等の操作によりソース・ ディレクトリ内の *.o 等を消去した後、パッケージ作成の為のパッチを作 成し、/SOURCES に置きます。 このために、/BUILD で diff -uNr harehore-1.23.orig harehore-1.23 > ../SOURCES/hare- hore-1.23.patch として下さい。 4.2. 「仮想」インストール RPM は、make して出来たバイナリその他を一度システム上にインストール し、それらを用いてバイナリパッケージを作ります。しかし、これでは、シス テム上に既にインストールされているファイルを上書きしてしまう可能性があ ります。これを避ける為に、あるディレクトリを指定し、それをインストール するディレクトリツリーの最上位ディレクトリに見立てて、そのディレクトリ 以下に「仮想的に」インストールし、バイナリパッケージを作成する事ができ ます。 最上位ディレクトリの指定は、Imakefile 等を用いているプログラムの場合は 変数 DESTDIR で、また GNU のソフトの場合は Makefile の中の PREFIX (prefix) 等で指定する事が出来ます。 しかし、その様な機構が用意されていない場合は、インストールするディレク トリツリーの最上位ディレクトリを指定できるように、 Makefile 等を改造し ておきましょう。 例えば、以下の様な仮想的な Makefile の一部 ---------- BINDIR=/usr/local/bin LIBDIR=/usr/local/lib/harehore ....... install : install -s harehore ${BINDIR} ....... ---------- に対しては、 ---------- installprefix=$(ROOT) BINDIR=$(installprefix)/usr/local/bin LIBDIR=$(installprefix)/usr/local/lib/harehore ....... install : install -s harehore ${BINDIR} ....... ---------- という様に変更を行なって下さい。 この Makefile に施した変更も、patchにして /SOURCES に置いてお きましょう。 (これらの変更を施してから前節の最後で述べた ``diff'' の操 作を行なって patch を作るのでも構いません。) 5. パッケージ作成の準備 II (spec ファイルの記述法) 次はいよいよ、.rpm 及び .src.rpm を作成する為の「仕様書」である spec ファイルを作成します。 5.1. spec ファイルの例 ただズラズラと spec ファイル中に記述すべき項目の説明を羅列しても分かり にくいだけですので、例をあげて説明しましょう。 ここでは、著者の一人が作成した plain2-2.54 用の spec ファイ ル、``plain2-2.54-3.spec'' を例に取って説明します。 注:通常、.rpm 等のファイル名は、 <パッケージ名>-<バージョン番号>-<リリース番号>.<アーキテクチャ>.rpm とします。例えば、i386 向けに作成した plain2 のバージョン 2.54 の 3 番 目の rpm リリースに対しては、 plain2-2.54-3.i386.rpm となるようにします。 以下に上記のspecファイルを示します。右端の数字は解説用のインデックス で、実際のspecファイルには書かれていません。 ---------- plain2-2.54-3.spec ---------- Summary: Plain2 plain text -> LaTeX/troff converter 1. Name: plain2 2. Version: 2.54 3. Release: 3 4. Group: Applications/Publishing/TeX 5. Source: Flux.tokai.jaeri.go.jp:/plain2-2.54.tar.gz 6. Copyright: 7. Packager: Kazuyoshi Furutaka 8. URL: http://Flux.tokai.jaeri.go.jp 9. BuildRoot: /home/furutaka/work/rpm/plain2 10. Patch: Flux.tokai.jaeri.go.jp:/plain2-2.54.patch 11. %package docs 12. Summary: Documents package of plain2 13. Group: Applications/Publishing/TeX 14. %description 15. Plain2 plain text -> LaTeX/troff converter (desc.) 16. %description docs 17. This package contains lots of documentation and Makefile 18. for plain2 plain text -> LaTeX/troff converter. %prep 19. %setup 20. %patch -p1 21. #%patch -p1 22. rm -rf $RPM_BUILD_ROOT -- mkdir -p $RPM_BUILD_ROOT/usr/local/bin 23. mkdir -p $RPM_BUILD_ROOT/usr/local/lib/plain2 -- %build -- cd src 24. make -- %install -- cd src 25. make installprefix="$RPM_BUILD_ROOT" install -- %clean -- rm -rf $RPM_BUILD_ROOT 26. -- %post -- chown -R root.root /usr/local/lib/plain2 27. chown root.root /usr/local/bin/plain2 chown -R root.root /usr/doc/plain2-2.54-2 -- %files -- %dir /usr/local/lib/plain2 ↑ /usr/local/bin/plain2 /usr/local/lib/plain2/OHP.p2 /usr/local/lib/plain2/OHP_t.p2 28. /usr/local/lib/plain2/header.p2 /usr/local/lib/plain2/header_t.p2 /usr/local/lib/plain2/jbook.p2 ↓ /usr/local/lib/plain2/supsnum.p2 -- %files docs 29. %doc doc/* ---------- end of plain2-2.54-2.spec ---------- では、各エントリーについて、順番に説明して行きます。 1.--18. はヘッダで、RPM を用いてパッケージの問い合わせ等に対する返答 や、ソースアーカイブなどの名前を記述しておくのに用いられます。 1. このパッケージ(spec ファイル)の簡単な説明です。 2. パッケージの名前です。 3. パッケージが元にしているソースファイルのバージョン番号です。 (ただし、バージョン番号の中にはハイフン ``-'' を用いる事は出来ませ ん。しようがないので、代わりにアンダースコア ``_'' を使って下さ い。) 4. この (.rpm 及び .src.rpm)パッケージのリリース番号です。 (ソースのバージョンとは関係ありません。) 5. Red Hat LiNUX でのパッケージの分類です。 (日本語環境用配付パッケージ集を作成する時は、独自の分類を考えた方が 良いでしょう。RHL では、 Extensions/Japanese という階層が有ります。 (しかし、そこには ktermしか有りませんが(^^;;) 6. 本来は、オリジナルのソースファイルの一次配布 ftp サイトを記述しま す。 しかし、このように記述し、かつ、自分の topdir: の下の SOURCES ディ レクトリにソースファイルが置いてあれば問題無い様です。) 7. 著作権を記述しておきます。 8. ここには「RPM パッケージの維持」を行なっている人の名前と電子メール アドレスを書いておきます。 (ただし、これを書いておいても rpm -qiしただけでは情報が表示されませ ん。) 9. ここには、パッケージ中のソフトウェアについての情報又は文書への URL を書いておきます。 将来的に RPM がこのタグを使う可能性もあるそうです。 (このタグも、8. と同様 rpm -qi では情報が表示されません。) 10. バイナリ・パッケージを作成する為に「仮想的に」インストールを行なう 際の、最上位ディレクトリを指定します。 11. パッチの置き場所を記述します。 (``Source:''(ソースの置き場所)と同様に、この様な書式で指定し、かつ /SOURCES にパッチファイルが置かれていれば、問題無く動作する ようです。) 12.--14. は、ソースに含まれるファイルの一部を別のパッケージとする場 合のエントリです。(すべてのファイルを単一パッケージとする場合は必要 ありません。) この様にした場合は、(この例の場合) 文書ファイルを含まない plain2-2.54-2.i386.rpm の他に plain2-docs-2.54-2.i386.rpm という文 書ファイルのみを含んだパッケージが作成されます。 12. docs という別パッケージを作成する事を宣言します。 13. 別パッケージの内容の簡単な説明を記述します。 14. 別パッケージに対する分類を記述します。(この例では同じ分類) 15. メインのパッケージ(この例では plain2-2.54-2.i386.rpm)の説明文のタグ です。 16. メインのパッケージの機能等を(アルファベット 50 字程度で) 記述しま す。 17. サブパッケージ(この例では plain2-docs-2.54-2.i386.rpm)の説明文のタ グです。 18. サブパッケージの機能などを記述します。 19. ソースを BUILD ディレクトリに展開し、パッチを当てる、等の作業内容を 記述しておくためのタグです。 20. 実際にソースを展開し、パッチを当てる為の「マクロ」です。動作内容 は、オプション無しでは「ソースを展開し、出来たディレクトリに cd す る」ことです。 オプションには -n , -c, -b #, -a #, -T, -D 等があり、夫々、 -n ソースを展開した後に cd するディレクトリ名を とします。 ディフォルトでは $NAME-$VERSION です。他には、例えば $NAME, ${NAME}${VERSION} 等とする事も出来ます。 (RPM-HOWTO にはこう書いてありますが $NAME は $RPM_PACKAGE_NAME と書かないとダメな様です。) -c ソースファイルを展開する「前に」、指定したディレクトリを作成し、 そこにcd します。上の -n オプションと組み合わせて %setup -n -c とする事により、 というディレクトリを作成し、そこに cd する様 にします。 -b # 展開先ディレクトリにcdする「前に」 # 番目のソース(Source#:)を展 開します。 -a # 展開先ディレクトリに cd した「後で」 # 番目のソース(Source#:) を 展開します。 -T ディフォルトでは、%setupが現れる「毎に」 ``Source:''に示された ソースが展開されてしまいます。そこで、複数のファイルが有る時は、 二番目以降の%setup ではこのオプションを指定して、再び``Source:'' が展開されない様にします。これに先だつ%setupで-b 0 又は -a 0 と 指定して、メインのソース「のみ」を展開しておかなくてはなりませ ん。 -D ディフォルトでは、%setup「毎に」BUILD ディレクトリに展開したもの を消去してしまいます。そこで、このオプションを指定して、二番目以 降のソースを展開する際に(既にBUILD に作成されている)ソースディレ クトリを消去しない様にします。 という機能を持っています。以上のオプション使用法の具体例を ``%setup マクロのオプションの使用例'' 節にて解説していますので、そちらを参照 して下さい。 21. パッチを当てるための「マクロ」です。いくつかのオプションを取る事が 出来ます。 # ヘッダ中に Patch#: で示されている # 番目のパッチを当てます。 -p # patch(1) コマンドに渡すべき、飛び越し可能ディレクトリの階層数を # で指定します。 -P ディフォルトの動作 (Patch もしくは Patch0を当てる) を抑止し、メ インのソースがエラー無く展開できた事(返り値 0)を確かめます。 %patch # -P とする代わりに %patch# と指定する事も出来ます。 この他にも、文書に記述されてはいないが使う事の出来る機能/オプション が幾つかあるようです。 ``Undocumented(?) %patch functions''節を参照 して下さい。 22. コメントです。コメントアウトするには行の最初の文字を '#' にします。 23. 「仮想的にインストールする」ディレクトリを消去し、新たに作り直して おきます。ここで、RPM_BUILD_ROOT は、ヘッダ中で ``BuildRoot:'' によ り指定したディレクトリに展開されます。 このように、%prep や %buildといった各タグの中では shell コマンドを 書いておいて実行させる事が出来ます。 24. %build は実際の make を行なう過程を示すタグです。 25. %install は、インストール過程で行なう作業を記述するタグです。即ち、 「BuildRoot: で指定されたディレクトリ以下に仮想的にインストール」を 行なっています。 26. パッケージ作成終了後に行なう動作を記述するタグです。無くても構いま せん。ここでは、仮想インストールディレクトリの消去を行なっていま す。 27. バイナリ・パッケージのインストール終了後に設定スクリプト等を走らせ る過程のためのタグです。 (ここでは、一般ユーザがパッケージを作成しているために、ファイルの所 有者が作成者になってしまっているので、所有者を root に変更していま す。) 28. %files は、このパッケージが所有するファイルをリストしておくためのタ グです。あるファイルがどのパッケージの所有物であるか問い合わせる際 や、パッケージを削除する際などに用いられます。 この際、各ファイルに %dir, %doc %config 等の印をつけておく事も出来 ます。 %dir これを付けられたディレクトリ「のみ」がこのパッケージ所有のもので あることを示します。これを付けずにディレクトリを指定すると、その ディレクトリ「中のすべてのファイル」がそのパッケージに属すると見 做され、インストールされます。 %doc 文書ファイルである事を示します。ディフォルトでは /usr/doc/$NAME-$VERSION-$RELEASE にインストールされます。 %config 設定ファイルである事を示します。アップグレード時には、古いリリー スパッケージ中でこの印を付けられたファイルに変更が加えられていな い場合はそのまま消去し、変更されていた場合はファイル名に .rpmsave を付けて保存します。 29. サブパッケージ(この場合は docs) の所有するファイルを示すための、別 の %files タグです。サブパッケージを作らない場合は %doc doc/* の行 を 27. に含めておけば良いだけです。 どうですか?分かりましたか? 5.2. 例に登場していないタグ 上で用いられている以外にも、以下のようなタグがあります。 %pre インストール前に行なう動作を記述するタグ %preun アンインストール前に行なう動作を記述するタグ %postun アンインストール後に行なう動作を記述するタグ 例えば、%post には、「一般ユーザとして作成したためファイルの所有者がそ のユーザになってしまっている」ので chown したい場合や、 chmod したい場 合などに用いる事が出来ます。 5.3. %setup マクロのオプションの使用例 5.3.1. ソースのディレクトリ名を指定する (%setup -n ) %setup セクションの -n オプションを使うと、ソースを展開した後で cd し、また %build で作業をするディレクトリの名前を指定することができま す。 kon のソース(kon-0.99.4g.tar.gz) を例に取りましょう。このソースファイ ルを展開すると、 drwx--x--x manabe/dsl 0 Apr 17 16:06 1996 kon/ drwx--x--x manabe/dsl 0 Apr 17 00:53 1996 kon/font/ -rw------- manabe/dsl 4552 May 8 12:39 1994 kon/font/minix.c -rw------- manabe/dsl 491 Apr 6 12:57 1996 kon/font/Makefile (以下略) と、kon というディレクトリの下にソースファイルが展開されます。 一方、RPM は ${RPM_PACKAGE_NAME}-${RPM_PACKAGE_VERSION} というディレク トリ以下にソースが展開されているものとして、 %setup マクロを実行した後 はそのディレクトリに cd しようとします。 この場合は、単に %setup とやるのではなく、 %setup -n kon と指定すれ ば、上記ソースを展開した後 kon というディレクトリに cd します。ま た、%buildの際もこのディレクトリで作業をします。特に、この場合は $RPM_PACKAGE_NAME = kon ですので、 %setup -n $RPM_PACKAGE_NAME とする事も出来ます。 因みに、RPM の中で定義されていて、spec ファイルの中で使う事が出来る変 数としては以下の様なものがあるようです。 (中身は筆者の一人の環境での例 です。) RPM_ARCH=i386 RPM_BUILD_DIR=/home/ishioka/local/work/package/redhat/BUILD RPM_BUILD_ROOT=/home/ishioka/local/work/package/rpm-tmp RPM_DOC_DIR=/usr/doc RPM_OPT_FLAGS=-O2 -m486 -fno-strength-reduce RPM_OS=Linux RPM_PACKAGE_NAME=kon RPM_PACKAGE_RELEASE=0 RPM_PACKAGE_VERSION=0.99.4g RPM_ROOT_DIR=/home/ishioka/local/work/package/rpm-tmp RPM_SOURCE_DIR=/home/ishioka/local/work/package/redhat/SOURCES 5.3.2. ディレクトリを作成してからソースを展開する (%setup -c) %setup -c を使うと、まずソースを展開するディレクトリを作成し、そこに cd したあとでソースを展開してくれます。 例えば、xc32.tar.gz の場合、 ソースを展開すると次のようにカレントディレクトリにファイルを作るの で... tar tzvf ../SOURCES/xc32.tar.gz -rw-rw-r-- 0/1 3343 Jun 14 07:53 1991 .autocis -rw-rw-r-- 0/1 1152 Jun 6 10:56 1991 .uni -rw-rw-r-- 0/1 824 Jun 6 10:56 1991 .callhq -rw-rw-rw- 0/1 4127 Aug 25 10:17 1991 Makefile この様な場合は、 %setup -c -n xc-3.2 と指定して、まず xc-3.2 というディレクトリを作って cdさせ、そこに展開 させます。あとは普通の場合とおなじです。 5.3.3. 複数ソース、パッチを当てる 以下のように複数のソースを順に展開することができます. Source: xc32.tar.gz .......... メインのソース Source1: xc32pat.tar.gz ....... サブソース1 Source2: xc32news.tar.gz ...... サブソース2 %prep %setup -c ..................... (1) %setup -D -a 1 -T ............. (2) %setup -D -a 2 -T ............. (3) (1) では メインのソース(Source: で指定したもの) を展開しています。 xc の場合、カレントディレクトリにファイルを作るので、 -c オプションで先に ディレクトリを作成し、 cd した後で展開させています。 (2), (3)ではサブソースを展開していますが、これも(1) と同様の理由から -c を付加しています。また, それぞれ Source[12]: を指定するために -a # オプションも使っています。ここでは、-D オプションを使って、 (1)で展開 したディレクトリを消去してしまわない様にしています。こうしておかない と、せっかく展開したメインのソースが消されてしまうのです!また、単に -a 2 とだけ指定すると、 Source2 「と Source」 が展開されてしまうの で、-T オプションも指定しています。 5.4. Undocumented (?) %patch functions %path マクロは、パッチファイルが圧縮されていても動作するようです。 (自動的に ``gzip -dc | patch ...'' を行なってくれる。) また、%patchマクロのオプションとしては、 undocumented ではありますが、 下記の様な patch(1) オプションも指定する事が出来るようです。 -b xxx バックアップとして保存するファイルの拡張子を .orig から .xxx に 変更する。 -R リバースパッチを施す。 -E パッチを当てた結果空になったファイルを削除する。 6. パッケージ作成 specファイルを書いてしまえば、あとは /SPECS に移って RPM を 使ってパッケージを作成するだけです。 RPM 構築コマンドの一般的な形は & rpm -bO [作成オプション] + です。 [作成オプション]は man page の翻訳等を参照して頂くことにして、ここでは -bO の部分だけを説明します。 -bO は spec ファイル中で記述したどの過程 (タグ)まで作業を行なうかを指 定するものです。 -bp %prep 過程まで、即ち、ソースを展開してパッチを当てるところまで作 業を行ないます。 -bl %files で記述されたファイルのリストの検査を行ないます。 -bc %build 過程(通常は実行ファイルを make するところ)まで行ないま す。 -bi %install 過程(通常 make install を行なう) までを行ないます。 -bb (%prep, %build, %install を行なってから)バイナリパッケージを作成 します。 -ba (%prep, %build, %install を行なってから)バイナリ及びソースパッ ケージを作成します。 一つだけ [作成オプション] について説明しておきます。 --short-circuit をつけると、(-bc 又は -bi とともに用いた場合は) その前の過程をやらずに いきなり目的とする過程を実行します。 さて、-bb または -ba を指定してパッケージを作成してみましたか?うまく 行けば、 o /RPMS/ にバイナリパッケージ(xxx..rpm)が、 o /SRPMS にソースパッケージ(xxx.src.rpm)が 出来ている筈です。 7. 作成したパッケージのテスト 「でも、お前の作ったのなんて、大丈夫なの?...」 テストに関しては、RPM-HOWTO と重複が多くなるので、改めて多くを述べる事 は致しませんが... 究極のテストは、やはり全く異なるマシンにインストールして使用してみる事 です。 いくら(パッケージを作成した)自分のマシンにインストールしてテストして も、(例えrpm -eしたとしても、何度も何度も make installしたマシンでは、 設定ファイル等が残っていたりして)完全にはテストすることが出来ません。 そ・こ・で... 親しい Linuxer に「こんなのを作ってみたんだけど、使ってみない?」と(甘 い言葉を囁いて)テストしてもらうのが良いのではないでしょうか? (当然の 事ながら、複数の Linux box をお持ちの方は、自分の別のマシンにインス トールしてみれば良い訳ですが。) しかし、まず友達に渡す前に、最低限 rpm -qp --scripts とやって、%pre及び%postインストールスクリプトでとてつもなく変な/愚かな 事をやっていないか?位は確認しておかないと、友達をなくしますよ!!! 8. 依存性(dependencies)について 8.1. 依存性(dependencies) これは非常にばかげた例ですが、先程例に上げた plain2-2.54-3.spec で作ら れるサブパッケージ plain2-docs-2.54-3.i386.rpm に含まれるファイルは plain2 で加工してはじめて TeX のファイルとなるため、 plain2-2.54-3.i386.rpm (plain2 本体)がインストールされていなければなり ません。このような場合には、spec ファイル中に Requires: plain2 と記しておけば、「plain2-docs-2.54-3.i386.rpm をインストールするために は plain2 というパッケージがインストールされていなくてはいけない」とい う依存性関係を明示しておく事が出来ます。もし plain2 がインストールされ ていないのに plain2-docs をインストールしようとすると、 [root@Flux i386]# rpm -ivh plain2-docs-2.54-3.i386.rpm failed dependencies: plain2 is needed by plain2-docs-2.54-3 と表示され、インストールは行なわれません。(依存性関係を無視して無理矢 理インストールしてしまう事も出来る事は出来ます。) (注 : この様に、サブ パッケージで Requires: にメインパッケージを指定する事も出来ます。) Requires: の指定にはバージョン番号を含める事も出来ます。例えば: Requires: perl >= 5.003 同時に複数のパッケージを Requires: に指定する事も出来ます: Requires: perl >= 5.003, python (注 : 複数パッケージの区切りは `,' でも ` ' (空白)でも良いそうです。) ところで、RPM 中のバージョン番号の新旧判断アルゴリズムは大抵の場合うま く働きますが、β版である事を示すために b が付けられている場合もあり、 この時は例えば 5.003b は 5.003 よりも新しいと判断されてしまいます。こ のような事態を回避するために、パッケージにシリアル番号を付けておく事が 出来ます。 Serial: 19 このシリアル番号を持つパッケージを Requires: で指定するには Requires: perl =S 19 とします。 8.2. 仮想パッケージ ここで、あるパッケージを使用するにはなんらかの fortran コンパイラが必 要であるが、コンパイラ自体は fort77(をコンパイラと呼ぶなら) でも g77 でも良いという場合を想像してみましょう。こういう場合には、個々のパッ ケージ (fort77 又は g77) を指定する代わりに「なんらかの fortran コンパ イラ」として仮想的なパッケージを Requires: に指定する事も出来ます: Requires: fortran この時は、fort77 又は g77 パッケージに Provides: fortran という指定がなされていて、且つそれらのいずれがインストールされていれ ば、依存性が満たされ、これに依存するパッケージを正常にインストール(し て使用)する事が出来ます。 8.3. 依存性関係の自動的な追加 しかし、便利な依存性関係も、いちいち全て Requires: で指定しなくてはな らないとしたら、たまったもんではありません。また、そのパッケージが依存 するパッケージをいちいち手で調べて追加していくのも容易ではありません。 そこで、RPM は、パッケージのファイルリスト中に共有ライブラリを必要とす るものがあった場合は、(その so 名が) Requires: に指定されているものと 見做してそのパッケージの依存性リストに自動的に追加して行きます。また、 逆にそのパッケージが供給する共有ライブラリの so 名も自動的に追加されま す。 9. アドバンスト・コース 9.1. パッケージへの電子的署名 RPM で作成したパッケージが本当に query により表示される人が作ったもの かどうか、またパッケージが ftp 等の際に損傷していないかを調べられるよ うに、各パッケージには電子署名を付けておく事が出来ます。 現在は (version 2.2.9) MD5, SIZE, PGP の署名をサポートしています。 MD5, SIZE の署名は常に行なわれます。 PGP 署名をする場合はオプション引数にて指定します。 (PGP の鍵束はディ フォルトでは $HOME/.pgp に置かれていると想定していますが、環境変 数PGPPATH で、もしくは $HOME/.rpmrc ファイル中に pgp_path: という行を 書いておく事によって変更する事が出来ます。) パッケージの作成と同時に PGP 署名をするには、オプション引数に --sign を付け足すだけです。 既存のパッケージに PGP 署名をし直す場合は、 rpm --resign とします。 しかし、この場合は以前付けられていた署名は消去されてしまいます。 新たに PGP 署名を追加したい場合は、 rpm --addsign とします。 (でも、あなたの公開鍵を公開しておかないと、他の人は確かめようがありま せんよ!!!) 10. よくあるトラブル 10.1. 日本語環境で用いた場合に Seg.Fault する事への対策 Q : JE 環境で rpm --help 等とすると Segmentation Fault を起こし て、RPM が死んでしまうのですけれど... rpm -ivh 等は正常に働きます。 A : RPM は、多国語対応化するために GNU gettext utility を使っていま す。そして、環境変数 LANGUAGE, LC_CTYPE, LC_ALL, LANG を順番に調 べて行き、いずれかが設定されていた場合は、対応する gettext の RPM.mo ファイルを /usr/lib/locale//LC_MESSAGES/ に読みに行 きます。 ところが、通常の日本語環境(JE)では、LANG=ja_JP.ujis に設定してい るので、/usr/lib/locale/ja_JP.ujis/LC_MESSAGES/RPM.mo を読みに行 くと、そこに RPM.mo が無いために Segmentation Faultしてしまう、 という事になっているようです。 従って、``export LANG=''とやって、LANG を空にしてみて RPM --help が正常に動作すれば、こういう問題ですので、 export LANGUAGE=C とやっておけば良い筈です。もしくは、日本語化した RPM.mo(筆者の一人 が作成しました) を /usr/lib/locale/ja/LC_MESSAGES/ に置き、 export LANGUAGE=ja などとやっても解決できる筈です。 10.2. /etc/rpmrc が無い! Q : RPM をアップグレードしたら /etc/rpmrc が入ってないのですが。 A : 恐らくバージョン 2.2.8 以降をお使いなのでしょう。バージョン 2.2.8 以降は、望ましいディフォルト設定値が /usr/lib/rpmrc 中に全 て記述されているため、 /etc/rpmrc は配付されなくなりました。勿 論、自分で /etc/rpmrc を作成して設定を書いておく事は有効です。 10.3. RPM をアップグレードした際にエラーが出る Q : RPM をアップグレードする際にエラーが表示されるのですが。 A : バージョン 2.2.8 では、/usr/lib/rpmrc ファイル中に typo があり、 bad option 'arch_cnaon' at /usr/lib/rpmrc:50 と怒られてしまいます。 /usr/lib/rpmrc の上記 ``arch_cnaon'' となっている箇所を ``arch_canon'' に訂正して下さい。 11. 謝辞 この文書を書く上で、多くの方の方からの協力を頂きました。ここに感謝の意 を表したいと思います。 山縣 敦 氏(山縣@都立大さん) 本文書に記述した大部分の事柄の情報源となっている RPM-HOWTO の翻 訳の労を取られるとともに、原稿を通してお読み下さった上で非常に有 益な示唆・指摘を頂きました。 佐藤 大輔 氏(佐藤@東邦大さん) 原稿をお読み頂き、非常に有益な示唆・指摘を頂きました。 瑞慶覧 辰 氏(``ず'' さん) %patch マクロの隠れた機能に関する情報をお寄せ頂きました。 package-ML の皆さん 本文書の元となる多くの貴重な情報及び経験をお寄せ下さいました。 西森 信行 氏 たまたま第一筆者の近くで Slackware を使っていたが為に、第一筆者 の実験台とされ、文句も言わずに(筆者が耳を貸さなかっただけ?) 数 多くのテストを行なって下さいました。