16.78MHz
Amebaでブログを始めよう!
1 | 2 | 3 | 4 | 5 | 最初次のページへ >>
November 13, 2010

Linux環境の作り方入門 vol.3

テーマ:Linux
(前回の記事はこちら)
今回はひたすら基本的なコマンドをインストールしていく単調な作業。
まずはcoreutilsをインストールする。coreutilsは無いと話にならないdd、cp、lnといった基本的なコマンドをひとまとめにしたもの。とりあえずこれがあれば最低限のファイル操作くらいは出来るようになる。
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/coreutils/coreutils-8.5.tar.xz
$ tar xf coreutils-8.5.tar.xz
$ cd coreutils-8.5
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc --localstatedir=/var --exec-prefix=/
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

検索関連のコマンド(といいつつ密かにgrepは入っていない)をまとめたfindutilsをインストールする。
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/findutils/findutils-4.4.2.tar.gz
$ tar xf findutils-4.4.2.tar.gz
$ cd findutils-4.4.2
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

C言語のできそこないawkのインタプリタgawkを入れる。
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/gawk/gawk-3.1.8.tar.bz2
$ tar xf gawk-3.1.8.tar.bz2
$ cd gawk-3.1.8
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

autotoolsのルールの記述に使われているm4を入れる。(ひょっとするとこれはchroot後でもいいかもしれない)
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/m4/m4-1.4.15.tar.xz
$ tar xf m4-1.4.15.tar.xz
$ cd m4-1.4.15
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

構文解析器bisonを入れる。
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/bison/bison-2.4.3.tar.bz2
$ tar xf bison-2.4.3
$ cd bison-2.4.3
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

roffドキュメント(つまるところマニュアルページ)を読むための文書整形コマンドgroffをインストールする。
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/groff/groff-1.20.1.tar.gz
$ tar xf groff-1.20.1.tar.gz
$ cd groff-1.20.1
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

ストリームエディタことsedを入れる。
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/sed/sed-4.2.1.tar.bz2
$ tar xf sed-4.2.1.tar.bz2
$ cd sed-4.2.1
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

国際化のためのライブラリgettextを入れる。
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/gettext/gettext-0.18.1.1.tar.gz
$ tar xf gettext-0.18.1.1.tar.gz
$ cd gettext-0.18.1.1
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

マニュアルページと並んで歴史あるinfoページを整形するためにtexinfoを入れる。
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/texinfo/texinfo-4.13a.tar.gz
$ tar xf texinfo-4.13a.tar.gz
$ cd texinfo-4.13a
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

様々な種類のライブラリのビルド手順と動的ロード手順を抽象化するlibtoolをインストールする。
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/libtool/libtool-2.4.tar.xz
$ tar xf libtool-2.4.tar.xz
$ cd libtool-2.4
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

ファイル同士を比較するdiffコマンドと関連コマンドからなるdiffutilsインストールする
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/diffutils/diffutils-3.0.tar.xz
$ tar xf diffutils-3.0.tar.xz
$ cd diffutils-3.0
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

(つづく!)
November 12, 2010

Linux環境の作り方入門 vol.2

テーマ:Linux
(前回の記事はこちら)
おなじみのbashをビルドする。bashはDESTDIRを無視するが、バイナリ中にインストールパスを埋め込まないので、prefixで直接インストール先を指定する。
$ ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/bash/bash-4.1.tar.gz
$ tar xf bash-4.1.tar.gz
$ cd bash-4.1
$ mkdir build1
$ cd build1
$ ../configure --prefix=${SYSTEM_BUILD_DIR}/usr/ --exec-prefix=${SYSTEM_BUILD_DIR} --enable-alias \
--enable-arith-for-command --enable-array-variables --enable-command-timing \
--enable-cond-command --enable-cond-regexp --enable-debugger --enable-history \
--enable-extended-glob --enable-job-control --enable-net-redirections \
--enable-process-substitution --enable-progcomp --enable-prompt-string-decoding \
--enable-readline --enable-restricted --enable-select --enable-separate-helpfiles \
--enable-mem-scramble --with-curses --enable-shared --disable-debug \
--mandir=/usr/share/man
$ make
$ make install

続いてアセンブラやリンカ等のバイナリ生成のための基本的なコマンド群binutils
$ ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/binutils/binutils-2.20.1.tar.bz2
$ tar xf binutils-2.20.1.tar.bz2
$ cd binutils-2.20.1
$ mkdir build
$ ../configure --prefix=/usr --disable-debug --enable-shared --sysconfdir=/etc \
--localstatedir=/var --disable-werror
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

そしてgccをインストールするわけだが、最近のgccはいろいろと外部ライブラリを要求するため、先にそれらを入れておく。まずは多倍長整数演算ライブラリgmp
$ ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/gmp/gmp-5.0.1.tar.bz2
$ tar xf gmp-5.0.1.tar.bz2
$ cd gmp-5.0.1
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

次に多倍長浮動小数点数演算ライブラリmpfr
$ ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://www.mpfr.org/mpfr-current/mpfr-3.0.0.tar.bz2
$ tar xf mpfr-3.0.0.tar.bz2
$ cd mpfr-3.0.0
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --enable-shared --sysconfdir=/etc --localstatedir=/var
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

そして複素数演算ライブラリmpcをインストール。
$ ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://www.mpfr.org/mpfr-current/mpfr-3.0.0.tar.bz2
$ tar xf mpfr-3.0.0.tar.bz2
$ cd mpfr-3.0.0
$ mkdir build
$ cd build
$ ../configure --prefix=/usr --enable-shared --sysconfdir=/etc --localstatedir=/var

mpcはgmpとmpfrを使用するため、古い方の環境が古いgccを使っていると、この2つが存在しなくてビルド出来ない可能性がある。その場合新しい環境に先ほどインストールしたgmpとmpfrを使うためにconfigureに以下ので示された2項目を追加する。
$ ../configure --prefix=/usr --enable-shared --sysconfdir=/etc --localstatedir=/var --with-gmp=${SYSTEM_BUILD_DIR}/usr --with-mpfr=${SYSTEM_BUILD_DIR}/usr

後は普通にビルドしてインストール。
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR} make install

gccをビルドする。
$ ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/gcc/gcc-4.5.1/gcc-4.5.1.tar.bz2
$ tar xf gcc-4.5.1.tar.bz2

$ cd gcc-4.5.1
$ ./configure --prefix=/usr --enable-shared --sysconfdir=/etc --localstatedir=/var \ --enable-_cxa_atexit --with-system-zlib --enable-nls --enable-clocale=gnu \
--enable-threads=posix --enable-long-long --enable-c99 --disable-werror \
--enable-languages=c,c++,objc

古い方の環境にgmp、mpfr、mpcが無い場合先ほど同様configureに以下ので示された3項目を追加する。
$ ./configure --prefix=/usr --enable-shared --sysconfdir=/etc --localstatedir=/var \ --enable-_cxa_atexit --with-system-zlib --enable-nls --enable-clocale=gnu \
--enable-threads=posix --enable-long-long --enable-c99 --disable-werror \
--enable-languages=c,c++,objc --with-gmp=${SYSTEM_BUILD_DIR}/usr --with-mpfr=${SYSTEM_BUILD_DIR}/usr --with-mpc=${SYSTEM_BUILD_DIR}/usr

ただし、gccはここで指定したパスを記憶しているため、chroot後に${SYSTEM_BUILD_DIR}/usr以下に必要なライブラリが無いから実行出来ないといった旨のエラーに見舞われる。なのでchroot後に正しいパスを指しているgccを再度ビルドする必要があるが、gccをビルドするためにはとりあえず何とかしてgccに動いてもらう必要があるため、新しい環境の中にシンボリックリンクを張って${SYSTEM_BUILD_DIR}/usrが存在するかのように見せかける。
$ mkdir -p ${SYSTEM_BUILD_DIR}/${SYSTEM_BUILD_DIR}
$ cd ${SYSTEM_BUILD_DIR}/${SYSTEM_BUILD_DIR}
$ ln -s /usr
$ ${SYSTEM_BUILD_DIR}/usr/src/gcc-4.5.1

おもむろにビルド、インストール
$ make
$ DESTDIR=${SYSTEM_BUILD_DIR}
$ make install

(つづく!)
November 11, 2010

Linux環境の作り方入門 vol.1

テーマ:Linux
# 2010/11/12 追記: 一連の作業はrootで行う必要がある。そうしないとインストールされるソフトウェアに適切な所有者とパーミッションが設定されない恐れがある

ディストリビューションを使わずにソースパッケージから自力でLinux環境を構築するのは実はそれほど難しくない。面倒くさいけど。うちでは2004年頃からそうやって用途に応じてLinux環境を作ってるけど、今回PCルータのシステム刷新の為に構築する環境の構築手順を公開してみようと思う。
新しいLinux環境は構築に使うLinux環境のディレクトリツリーの一部にぶら下げる形で作るので、とりあえずまずディレクトリを作る
$ export SYSTEM_BUILD_DIR=/mnt/neo
$ mkdir -p ${SYSTEM_BUILD_DIR}

ソースパッケージによっては通常システムに必ず存在するディレクトリが存在しないとインストールに失敗するものが結構あるので、標準的なPOSIXディレクトリツリーを作っておく。
$ cd ${SYSTEM_BUILD_DIR}
$ mkdir -p ./{bin,boot/grub,dev,etc,home,lib/modules,mnt/{floppy,cdrom},opt,proc,root,sbin,sys,tmp,usr/{bin,include,lib,local,sbin,share/{man/man{1,2,3,4,5,6,7,8},info,doc},src},var/{lock,log,mail,run,spool,tmp,opt,cache,lib/misc,local}}

/usr/manと/usr/share/manで宗教戦争が始まらないようにシンボリックリンクを張っておく
$ cd ${SYSTEM_BUILD_DIR}/usr
$ ln -s share/man
$ ln -s share/info
$ ln -s share/doc

passwdとgroupを作っておく。uid/gidはお好みで
ユーザは最低限uid0のrootとなぜかPOSIXで要求されているbinがあれば良い。
$ cat <${SYSTEM_BUILD_DIR}/etc/passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin::/bin/false
EOF
$ cat <${SYSTEM_BUILD_DIR}/etc/group
root:x:0:
bin:x:1:

boot:x:2:
mnt:x:3:
proc:x:4:
sbin:x:5:
sys:x:6:
share:x:7:
include:x:8:
local:x:9:
etc:x:10:
man:x:11:
doc:x:12:
info:x:13:
daemon:x:14:
staff:x:15:
log:x:16:
jre:x:17:
ssl:x:19:
kmem:x:40:
tty:x:41:
floppy:x:42:
cdrom:x:43:
tape:x:44:
disk:x:45:
lp:x:46:
dialout:x:47:
lan:x:48:
fbdev:x:49:
audio:x:50:
stunnel:x:51:
pppusers:x:52:
midi:x:53:
input:x:54:

nobody:x:65535:
EOF

続いて/dev以下のスペシャルファイルを作るが、手作業で作るのは面倒なのでLFSのMAKEDEVを使う
$ cd ${SYSTEM_BUILD_DIR}/dev/
$ wget http://www.linuxfromscratch.org/~manuel/MAKEDEV-1.7.bz2
$ bzip2 -d MAKEDEV-1.7.bz2
$ chmod 700 MAKEDEV-1.7
$ ./MAKEDEV-1.7

続いてカーネルヘッダをインストールする。
ついでだからここでカーネルコンフィグも済ませておく
カーネルの設定を後回しにしたい場合でも、.configが無いとカーネルヘッダのインストールは失敗するので、テキトーな設定をしておく。
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://www.kernel.org/pub/linux/kernel/v2.6/linux-2.6.36.tar.bz2
$ tar xf linux-2.6.36.tar.bz2
$ ln -s linux-2.6.36 linux
$ cd linux
$ make menuconfig
$ INSTALL_HDR_PATH=${SYSTEM_BUILD_DIR}/usr make headers_install

ここから、chrootしてビルドを行うために最低限必要なソフトウェアをインストールしていくが、LFSで指摘されているように今からビルドするバイナリは構築に使うLinux環境のABI等を引き継いで意図しないバイナリになってしまう恐れがあるため、真面目にやるなら一度スタティックリンクされた一時的なビルド環境を構築して、そこから新しいシステムを構築してやる必要がある。が、実際のところx86 Linux環境ではABIもバイナリフォーマットももう何年も変わっていないので(ARMみたいに最近大きく変わったアーキテクチャだと真面目にやる必要があるかもしれないが)/usr以下にインストールされたgccを使って構築する場合一時的な環境は構築しなくても上手くいく。というわけで今回は一時的な環境は作らずにいきなり本環境を作る。まずはC言語標準ライブラリがないと話にならないので、glibcをインストールする。
$ cd ${SYSTEM_BUILD_DIR}/usr/src
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/glibc/glibc-2.12.1.tar.xz
$ tar xf glibc-2.12.1.tar.xz
$ cd glibc-2.12.1
$ mkdir build
$ cd build

glibcはstack protector等一部の最適化フラグをつけてビルドすると正常に動作しないことが知られているため、ひかえめに最適化フラグを設定する。うちのPCルータはAtomプロセッサなのでAtom向けに最適化。ちなみにgccの最適化は-O0から-03までの4段階だが、-O3は一部のトリッキーなコードでは意図したとおりに動かないかもしれない最適化を含んでいるため、ソースパッケージが自分で-O3を付ける(つまり-O3でのテストが行われている)ソフトウェア以外は-O2までにとどめておくのが無難。
$ export CFLAGS="-O2 -march=atom -msse3 -mfpmath=sse -fforce-addr -fomit-frame-pointer -fstrength-reduce"
$ export CXXFLAGS="-O2 -march=atom -msse3 -mfpmath=sse -fforce-addr -fomit-frame-pointer -fstrength-reduce"
$ ../configure --enable-add-ons --enable-shared --with-fp --with-elf --disable-profile \
--enable-kernel=2.6.20 --with-headers=${SYSTEM_BUILD_DIR}/usr/include
$ make

glibcのインストールはインストール先に/etc/ld.so.confが無いと失敗するため、とりあえず空のファイルでごまかしておく。
$ touch ${SYSTEM_BUILD_DIR}/etc/ld.so.conf
$ make install_root=${SYSTEM_BUILD_DIR} install
$ make install_root=${SYSTEM_BUILD_DIR} localedata/install-locales

続いてncurses。ncursesは様々なターミナルの違いを吸収し、好きな位置に文字列を配置する仕組みを提供するライブラリ。シェルはこれを利用してターミナル上に標準出力を流しているので、これも要れておかないと色々始まらない。
$ cd ${SYSTEM_BUILD_DIR}/usr/src/
$ wget http://ftp.yz.yamagata-u.ac.jp/pub/GNU/ncurses/ncurses-5.7.tar.gz
$ tar xf ncurses-5.7.tar.gz
$ cd ncurses-5.7

ここからは本気の最適化でビルドしていくのでCFLAGSとCXXFLAGSを再設定。
$ export CFLAGS="-O2 -march=atom -msse3 -mfpmath=sse -fno-math-errno -ffast-math -fforce-addr -fomit-frame-pointer -pipe -fstrength-reduce -fno-strict-aliasing -fstack-protector"
$ export CXXFLAGS="-O2 -march=atom -msse3 -mfpmath=sse -fno-math-errno -ffast-math -fforce-addr -fomit-frame-pointer -pipe -fstrength-reduce -fno-strict-aliasing -fstack-protector"

ncursesにはマルチバイト文字に対応しているかどうかとスレッドに対応しているかどうかで4種類のバージョンが存在するので、全部インストールするためには4回ビルドする必要がある。ただ、シェル自体はマルチバイト対応もスレッド対応も要求しておらず、標準のものだけインストールされていればとりあえず動くので今はそれだけ入れる。
$ mkdir build1
$ cd build1
$ ../configure --prefix=/usr --with-install-prefix=${SYSTEM_BUILD_DIR} \
--with-shared --enable-termcap --enable-safe-sprintf --enable-colorfgbg \
--with-develop --enable-symlinks --without-debug --sysconfdir=/etc \
--localstatedir=/var --mandir=/usr/share/man --infodir=/usr/share/info \
--without-ada --with-manpage-symlinks
$ make
$ make install

(つづく!)
November 06, 2010

Write in C

テーマ:Blog
TwitterのほうでWrite in Cのネタが上がってたから以前訳したヤツをあげておこうと思う


自分のコードに山のような問題を見つけたとき、
友人や同僚は私の所をやってきて、
賢者の言葉を放った:
「Cで書け」

納期が迫っていて、
しかも見渡す限りバグだらけの時、
どこかで誰かが呟いた
「Cで書け」

Cで書け、Cで書け、
Cで書け、Cで書け
LISPは化石になってしまった、
Cで書け

私はFORTRANをよく書いた
それは科学計算ではうまくいった
グラフィックに使ったらどうだろう
Cで書け

もし君が30時間近くを
アセンブリのデバッグに費やしているのなら
君はきっと嬉しく思うだろう
Cで書くことを

Cで書け、Cで書け、
Cで書け、Cで書け
BASICなんて使うのはシロートだけだ
Cで書け

Cで書け、Cで書け、
Cで書け、Cで書け
PASCALは何かにつけて不便だ
Cで書け

Cで書け、Cで書け、
Cで書け、Cで書け
COBOLについてもう言及するな
Cで書け

画面がぼやけて見える
エディタを見ていると頭がおかしくなりそうだ
1と0の病気にかかってしまったようだ
Cで書け

大勢の人がTurbo Pascalを信仰している
私のは7だった
私はPROCEDUREという単語にうんざりした
Cで書け

Cで書け、Cで書け、
Cで書け、Cで書け
PL1は80年代のモノだ
Cで書け

Cで書け、Cで書け、
Cで書け、Cで書け
政府はADAが好きだ
Cで書け

米国では本来教育用に作られたプログラミングであるPascalを一番使い慣れているからという理由でそのまま実際の製品開発で使ってしまう開発者が沢山居た時代があるため、この歌には割と切実なものがあるように思う。
October 05, 2010

Spirit2覚書

テーマ:プログラム
昨日Twitterで何となくspiritの中でbind使いたくないなーと呟いたところ、ふじた先生から格好良い書き方を教わったので忘れないうちにまとめておく。
とりあえず、分かったのはspiritのList演算(%)が地味に便利だということ。AがBで区切られているリストを読むとき、馬鹿正直に
+( A >> B )

とか書くと返り値は
vector< tuple< A, B > >

なんてなかなかやらしい型で返ってくる。[]を使ってBを削れば良いんだけど、ここに空白を認めるとか色々ルールが入ってくると面倒くさくなってきて、
spirit::int_[ bind( &vector< int >::push_back, &array, _1 ) ]

必要なとこだけ抜き出せばいいや! とか考えたわけだけど、ドキュメントによると、A % Bの返す値の型はvector< A >らしい。
なにこれ、便利

で、なんかイマドキのSpiritにはPhoenixなるlambda的なものが備わっているらしい。この辺は後ほどがっつりドキュメントを読んでおく必要がありそう。

あと、どうもparseはphrase_parse同様最後の引数でパース結果を受け取れるらしい。phrase_parseだけの機能かと思ってた。変な質問してゴメンナサイ >アキラ先生
1 | 2 | 3 | 4 | 5 | 最初次のページへ >>

Ameba人気のブログ

Amebaトピックス