「Bonsai Linuxの楽しみ方」 目次 ==== - Bonsai(盆栽) Linux Projectとは? - 目標 - 特徴 - 開発フロー - 開発環境準備 - カーネル作成 - ユーザランド作成(1) ptxdistを使って自動生成 - ユーザランド作成(2) とにかくCFから起動したい - ユーザランド作成(3) User-mode Linuxを使って仮想的に起動したい - システム構成 Bonsai(盆栽) Linux Projectとは? =============================== 主に技術的興味を満たすために作る*小型計算機研究所流*組み込みLinux作り。 どんなLinuxをどう育てるか、そのプロセスを楽しみ、みんなと共有するプロジェクト。 「そんなの作って何に使うの?」 「育てるだけでイイじゃん、盆栽だもの」 組み込み開発未経験者が気軽に挑戦できるよう、ハード寄りな知識なしで 楽しめるように心掛けています。また、Open Sourceを利用しますので費用も かかりません。Embedded Linux に興味をもったらすぐ試して頂ける、組み 込み開発の第一歩として十分に敷居の低い環境を目指します。 皆で自分のBonsaiを育てましょう。できあがったLinuxは皆さんのオリジナル。 当研究所は何の権利も主張しません、趣味でもお仕事にも自由にお使い下さい(^_^) 目標 ==== - 小容量Compact Flashに収まる小型Linuxの作成 → 16MB CFに収まる(最小3MB) Embedded Linux - 自動化・仮想化された開発環境/手順の開発 → 開発/試験環境としてptxdist, User-mode Linuxの採用 技術に明るい方向けに説明すると・・ Linux Kernel + BusyBox を中心とした小さなLinuxをptxdistで 自動生成し、User-mode Linuxをエミュレーション環境と見立て て動作実験に利用しようという、Embedded Linux開発環境。 特徴 ==== - ハード寄りな知識不要 ハードウェア/BIOS/マシン語など、組み込みに必須と言われている知識 なしに、まず挑戦してみることが可能です。自分で新規に開発する部分は あまりなく、すでにあるオープンソースを組み合わせて利用するだけ。 - 一般的なPCとオープンソースを活用 専用ボード/商用Linux/クロス開発などが不要。組み込み開発取り組みの 敷居を低くしました。同時に開発コストを低減します。 - スクラッチから半自動build Linuxにはソースからカーネルを簡単に作成する仕組みが準備されています。 "ptxdist"の利用により、同様にユーザランドも簡単に作成できるように なりました。ptxdistは必要なソース/パッチを自らネットワーク上よりGET し、コンパイルを行います。数時間でほぼ半自動的にソースからのbuildが できます。 - エミュレータ環境で動作実験 完成したカーネル、ユーザランドをCFに書き込んでの起動試験も可能です が、User-mode Linuxを利用することにより、リブート不要で開発環境上で 仮想的に起動させることが可能です。システムの作り込みに便利です。 - どこでもシステム開発 Linux機があるところならば、どこででもシステム開発ができます。 実機がなくても動作確認ができるということはそのようなメリットもあり ます。どこにでもあるLinux機に、入手が簡単なオープンソースの組み合 わせは、まさに「どこでもシステム開発」環境を実現します。 # Cygwin + coLinuxを使えば、Windows上で開発も可能かも(^_^; - 多くのアーキテクチャに発展可能 解説するにあたり簡単化のためにハイテックシステム社製MicroPCを開発 環境/実行環境として利用しますが、Intel系PCでCFがついた機種なら同様 に作業可能ですし、実行環境がARM,PPCであっても一部手順をのぞき同様 に開発可能です。 - いろいろなシステムへの発展可能 CD-ROM/USB memory bootable、ROM運用可能なシステム、すべて基本は一緒。 様々な発展、応用が考えられます。 開発フロー ========== | 開発環境準備: | PC(Intel互換) + Linux (RedHat, Debian GNU/Linux他) + 高速回線 | Linux Kernel source + ptxdist + User Mode Linux | | <--------------------------+ | | | カーネル作成: | Linux kernelの 仕様決定&build | どんなカーネルが必要なのか | % make menuconfig | 機能/ドライバの検討 | % make dep | | % make bzImage +----------------------------+ | | <--------------------------+ | | | ユーザランド作成(1): | ptxdistを利用し、ユーザランドの仕様決定&build | どんなコマンドやデーモンが | % make menuconig | 必要なのか検討 | % make world | | +----------------------------+ | | <--------------------------+ | | | ユーザランド作成(2)(3): | CFへ直接書き込み起動実験 | 準備したコマンドが使えるか | | boot時にデーモンが起動する | User Mode Linuxを利用し仮想的な起動実験 | のか実験 | % linux ubd0=uml.diff,userland.img eth0=tuntap,,,127.0.0.10 | | +----------------------------+ | v Bonsai Linux 完成 開発環境準備 ============ - ディレクトリ構成 ~/bonsai -+- linux (Kernel作業用) | +- ptxdist (ptxdist作業用) | +- uml (User Mode Linux作業用) | +- bin (各種ツール) | +- src (各種ソース) | +- image (ファイルシステムイメージファイル) | +- conf -+ (設定ファイル保存用) +- dot.config_kernel +- dot.config_ptxdist +- dot.config_uml +- etc /mnt -+- cf (CF mount用) | +- img (image file mount用) - 各種sourceの入手 % cd ~/bonsai/src % wget ftp://ftp.kernel.org/pub/linux/kernel/v2.4/linux-2.4.24.tar.gz % wget http://aleron.dl.sourceforge.net/sourceforge/user-mode-linux/uml-patch-2.4.24-1.bz2 % wget http://www.pengutronix.de/software/ptxdist/ptxdist-0.5.2.tgz % wget http://www.graphviz.org/pub/graphviz/ARCHIVE/graphviz-1.12-1.i386.rpm % cd .. - UMLの準備 % tar zxf src/linux-2.4.24.tar.gz % cd linux-2.4.24 % bzcat ../src/uml-patch-2.4.24-1.bz2 | patch -p1 % cd .. % mv linux-2.4.24 uml % cd uml % make menuconfig ARCH=um Module不使用、proc,tmpfsを利用(devpts,devfsは不使用)。 UMLのためにTUN/TAPとhostfsを使用。 "Code maturity level options" -> OFF "General Setup" -> "Host filesystem" -> ON "Loadable Module support" -> "Enable loadable module support" -> OFF "Character Devices" -> "Unix98 PTY support" -> OFF "Network Devices" -> "Virtual network device" -> Ethertap,TUN/TAP -> ON "File System" -> "Virtual memory file system support" -> ON "File System" -> "/proc file system support" -> ON % make dep ARCH=um % make linux ARCH=um % strip linux % ln -s ./linux ../bin/linux - Kernelのソースを展開 % tar zxf src/linux-2.4.24.tar.gz % ln -s linux-2.4.24 linux - ptxdistのソース展開 % su root # rpm -ivh src/graphviz-1.12-1.i386.rpm # exit % tar zxf src/ptxdist-0.5.2.tgz % ln -s ptxdist-0.5.2 ptxdist カーネル作成 ============ Linuxのカーネルを作成します % cd ~/bonsai/linux % setenv LANG C % make mrproper (既存の.configを消します) (make oldconfig 以前のバージョンの.configがあればコンバート) % make menuconfig (自分好みにカスタマイズ) Moduleは使わない事にします "Loadable Module support" -> "Enable loadable module support" -> OFF % make dep % make clean % make bzImage % ls ~/bonsai/linux/arch/i386/boot/bzImage (コンパイルに約10分(ほぼ最小構成にて)) ユーザランド作成(1) =================== ptxdistを使ってLinuxのユーザランドを作成します % cd ~/bonsai/ptxdist % setenv LANG C % make i386-generic-glibc_config (まずは一般的な設定をロード) % make menuconfig (自分好みにカスタマイズ) - BusyBox General Configration -> Support for devfs -> off General Configration -> Use the devpts filesystem for Unix98 PTYs -> off Login/Password Management Utilities Networking Utilities -> hostname/ifconfig/route/telnetd - Disk and file utils -> GRUB ブートローダとして利用します - Networking Apps -> proftpd BusyboxにはFTPデーモンが含まれていないので別途選びます。 % make world (Eden/667MHz+256MBRAMで約2時間半) % ls ~/bonsai/ptxdist/root (出来上がりを確認) - /devの整備 # cd ~/bonsai/ptxdist/root/dev # cp -dpR /dev/hda[1-6] . # cp -dpR /dev/hdc[1-6] . # cp -dpR /dev/tty[0-3] . # cp -dpR /dev/ttyp[0-3] . # cp -dpR /dev/ptyp[0-3] . # cp -dpR /dev/shm . # cp -dpR /dev/pts . # cp -dpR /dev/console . # cp -dpR /dev/null . # mknod ubd0 b 98 0 # mknod ubd1 b 98 16 # mknod ubd2 b 98 32 # mknod ubd3 b 98 48 - /etcの整備 % mkdir ~/bonsai/ptxdist/root/etc % cd ~/bonsai/ptxdist/root/etc % vi inittab ----- ::sysinit:/etc/init.d/rcS # Start an "askfirst" shell on the console ::askfirst:/bin/sh # login prompt on the console #::respawn:/sbin/getty 38400 console # put a getty on a serial line (for a terminal) #::respawn:/sbin/getty -L ttyS0 9600 vt100 # Stuff to do before rebooting ::ctrlaltdel:/sbin/reboot ::shutdown:/bin/umount -a -r ----- # vi passwd ---- root:x:0:0:Linux User,,,:/:/bin/sh user:x:500:500:Linux User,,,:/:/bin/sh ---- # vi shadow (password:"root") ---- root:$1$$oCLuEVgI1iAqOA8pwkzAg1:12515:0:99999:7::: user::12515:0:99999:7::: ---- # vi group ---- root:x:0: user:x:500: ---- # vi hosts ---- 127.0.0.1 localhost 192.168.2.10 test ---- # vi proftpd.conf ---- ServerName "ProFTPD server" ServerType standalone Port 21 Umask 022 MaxInstances 3 ScoreboardFile /var/log/proftpd.scoreboard PidFile /var/log/proftpd.pid User user Group user AllowAll ---- ユーザランド作成(2) とにかくCFから起動したい ============================================= CFをマウントしカーネルとユーザランドをコピーし、実際にCFからブートします。 起動実験毎にPCのリブートが必要です。 - CFの初期化 # /sbin/fdisk /dev/hdc (CF上にhdc1としてLinuxパーティションを作成) # /sbin/mke2fs /dev/hdc1 (hdc1にext2のファイルシステムを作成) # /bin/mount /dev/hdc1 /mnt/cf (/mnt/cfとしてmount) - ユーザランドの書き込み # cd ~/bonsai/ptxdist/root # tar cf - . | ( cd /mnt/cf ; tar xf - ) - カーネルの書き込み # cp ~/bonsai/linux/arch/i386/boot/bzImage /mnt/cf/boot/bzImage - CF用初期設定ファイルの準備 # vi /mnt/cf/etc/fstab ----- /dev/hdc1 / ext2 errors=remount-ro,noatime 1 1 proc /proc proc defaults 0 0 tmpfs /dev/shm tmpfs size=32m 0 0 ----- # vi /mnt/cf/etc/init.d/rcS ----- #!/bin/sh # host configration hostname="test" address="192.168.2.10" gwaddress="192.168.2.254" echo echo "Bonsai Linux project (build:20040413)" echo # mount /proc file system /bin/mount /proc # mount root file system for fsck check /bin/mount -a # re-mount root file system /bin/mount -o remount,rw /dev/hdc1 / # /tmp and /var on tempfs mkdir /dev/shm/tmp mkdir /dev/shm/var /bin/mount -o bind /dev/shm/tmp /tmp /bin/mount -o bind /dev/shm/var /var chmod -R 1777 /tmp mkdir /var/log # network configure /bin/hostname $hostname /sbin/ifconfig lo 127.0.0.1 netmask 255.0.0.0 /sbin/ifconfig eth0 $address netmask 255.255.255.0 /sbin/route add default gw $gwaddress # network service start /sbin/syslogd /usr/sbin/telnetd /usr/sbin/proftpd & ----- # chmod +x /mnt/cf/etc/init.d/rcS - Boot loaderの書き込み HDからLinuxをbootしCFのMBRにGRUBを書き込む。 sgate1,stage2などはすでにCF上にあることが前提(ptxdistで作成)。 # ls /mnt/cf/boot/grub # /sbin/grub grub> root (hd1,0) hd0かhd1かはBIOSが見つけている順。bootしたデバイスがhd0になる grub> setup (hd1) hd1つまりCFのMBRにGRUBをインストール grub> quit # vi /mnt/cf/boot/grub/grub.conf ----- default=0 timeout=10 title Bonsai Linux root (hd0,0) kernel /boot/bzImage ro root=/dev/hdc1 ----- # cd /mnt/cf/boot/grub # ln -s grub.conf menu.lst ユーザランド作成(3) UMLを使って仮想的に起動したい ================================================== ユーザランドが入ったルートファイルイメージを作成し、UMLを使って仮想的にブートします。 起動実験毎にPCのリブートは必要ありません。 - 空のroot file image(16MB)の作成 % /bin/dd if=/dev/zero of=image/userland.img bs=16777216 count=1 % /sbin/mke2fs image/userland.img % su root # /bin/mount -o loop image/userland.img /mnt/img - ユーザランドを書き込む # cd ~/bonsai/ptxdist/root # tar cf - . | ( cd /mnt/img ; tar xf - ) - カーネルの書き込み カーネルの書き込みは不要です。UMLが起動用のカーネルとなります。 - UML用設定ファイルの準備 # vi /mnt/img/etc/fstab ----- /dev/ubd0 / ext2 errors=remount-ro,noatime 0 1 proc /proc proc defaults 0 0 tmpfs /dev/shm tmpfs size=32m 0 0 ----- # mkdir /mnt/img/etc/init.d # vi /mnt/img/etc/init.d/rcS ----- #!/bin/sh # host configration hostname="test" address="192.168.2.10" gwaddress="192.168.2.254" echo echo "Bonsai Linux project (build:20040413)" echo # mount /proc file system /bin/mount /proc # mount root file system for fsck check /bin/mount -a # re-mount root file system /bin/mount -o remount,rw /dev/ubd0 / # UML用に変更 # /tmp and /var on tempfs mkdir /dev/shm/tmp mkdir /dev/shm/var /bin/mount -o bind /dev/shm/tmp /tmp /bin/mount -o bind /dev/shm/var /var chmod -R 1777 /tmp mkdir /var/log # network configure /bin/hostname $hostname /sbin/ifconfig lo 127.0.0.1 netmask 255.0.0.0 /sbin/ifconfig eth0 $address netmask 255.255.255.0 /sbin/route add default gw $gwaddress # mount HostOS's home as GuestOS's home # UML用に追加 /bin/mount hostfs /home -t hostfs -o /home # # network service start /sbin/syslogd /usr/sbin/telnetd /usr/sbin/proftpd & ----- # chmod +x /mnt/img/etc/init.d/rcS - 起動実験 % umount /mnt/img % ~/bonsai/bin/linux ubd0=uml.diff,image/userland.img eth0=tuntap,,,192.168.2.254 システム構成 ============ $ df -k Filesystem 1k-blocks Used Available Use% Mounted on /dev/hdc1 30349 3491 25291 12% / tmpfs 32768 8 32760 0% /dev/shm tmpfs 32768 8 32760 0% /tmp tmpfs 32768 8 32760 0% /var $ /bin/mount /dev/hdc1 on / type ext2 (rw,bind,noatime,errors=remount-ro) /dev/shm/tmp on /tmp type none (rw,bind) /dev/shm/var on /var type none (rw,bind) $ ps -ef PID Uid VmSize Stat Command 1 root 508 S init 2 root SW [keventd] 3 root SWN [ksoftirqd_CPU0] 4 root SW [kswapd] 5 root SW [bdflush] 6 root SW [kupdated] 7 root SW [khubd] 30 root 388 R /usr/sbin/telnetd 33 root 532 S /bin/sh 34 user 1180 S proftpd: (accepting connections) $ free total used free shared buffers Mem: 240972 4956 236016 0 112 Swap: 0 0 0 Total: 240972 4956 236016