タイトル/名前 | 更新者 | 更新日 |
---|---|---|
技術/Linux/手作りLinuxシステム/05. Boot from Network(PXE) (kernel-2.6.x) | msakamoto-sf | 2011-04-29 15:37:36 |
技術/Linux/手作りLinuxシステム/06. Boot from Network(PXE + NFS + KGDB) (kernel-2.6.x) | msakamoto-sf | 2011-04-29 15:37:25 |
日記/2011/04/23/プログラミング言語の好き嫌い | msakamoto-sf | 2011-04-23 10:22:34 |
日記/2011/04/23/「技術センス」って何だろうなぁ。 | msakamoto-sf | 2011-04-23 09:31:22 |
読書メモ/「体系的に学ぶ 安全なWebアプリケーションの作り方」 | msakamoto-sf | 2011-04-18 10:38:18 |
日記/2011/04/18/フィンランドって選挙でネット活用するのOKなんだ・・・。 | msakamoto-sf | 2011-04-18 08:17:17 |
技術/Linux/uClibc/03, x86(32bit) PC環境でuClibcを試す | msakamoto-sf | 2011-04-12 12:27:56 |
日記/2011/04/12/gccのspecsファイル・・・それがあったか! | msakamoto-sf | 2011-04-12 10:26:57 |
技術/Linux/uClibc/04, 静的リンク -> Segmentation Fault について | msakamoto-sf | 2011-04-11 18:58:06 |
技術/Linux/uClibc/02, "symbol 'stdout': can't resolve symbol in lib" の対処 | msakamoto-sf | 2011-04-11 17:45:28 |
今回はPXE(Preboot Execution Environment)を使ったネットワークブートに挑戦してみます。ローカルHDDのマウントは考慮しません。
ステップ1:SYSLINUXの提供するPXE対応BootLoader, PXELINUXを使ってkernelと初期RAMディスク(initrd)をロードし、そのままinitrdをrootとしてマウントします。
kernelとinitrdは前回: 技術/Linux/手作りLinuxシステム/04. Boot from CD (kernel-2.6.x) と同じで、BootLoaderがISOLINUX(前回)からPXELINUX(今回)に切り替わっただけです。
ステップ2:ステップ3の下準備としてカーネルの起動時メッセージ(dmesgで確認できるアレ)をシリアルコンソールに表示させてみます。
ステップ3:rootファイルシステムをNFS経由でマウントしてます。
本シリーズのまとめとして、KGDBを組み込んだLinuxKernelをPXEでネットワークブートし、シリアルコンソール経由で開発マシン(ホストマシン)からgdbでライブデバッグしてみます。
環境や各種設定は前回 技術/Linux/手作りLinuxシステム/05. Boot from Network(PXE) (kernel-2.6.x) のNFSルートマウント成功からの続きとなります。
開発(=ホスト)マシン: VMware ゲスト, CentOS 5.5 (32bit) ターゲットマシン: VMware ゲスト, (空) VMwareホスト: Win7 SP1, 32bit
ホストマシンとターゲットマシンとは、名前付きパイプを使ったシリアルポートで接続できるようにしています。前回の設定では、ttyS0一つのみとしています。
NFSrootマウント用exports:
# cat /etc/exports /opt/nfsexports/root1 *(rw,sync,no_root_squash)
tftpディレクトリ:
/tftpboot/ pxelinux.0 pxelinux.cfg/default rootfs.gz bzImage bzImageSer bzImageNfs
/tftpboot/pxelinux.cfg/default:
prompt 1 label linux kernel bzImage append initrd=rootfs.gz root=/dev/ram0 label sercons kernel bzImageSer append initrd=rootfs.gz root=/dev/ram0 console=ttyS0,115200 console=tty0 label nfs kernel bzImageNfs append console=ttyS0,115200 console=tty0 root=/dev/nfs rw ip=dhcp \ nfsroot=192.168.240.10:/opt/nfsexports/root1 label nfsdebug kernel bzImageNfs append console=ttyS0,115200 console=tty0 root=/dev/nfs rw ip=dhcp \ nfsroot=192.168.240.10:/opt/nfsexports/root1 nfsrootdebug
KGDBの使い方など参考資料:
面接で返答に困る質問に「好きなプログラミング言語は何ですか?」というのがある。
得意・不得意を感じたことはあるが、「この言語サイコー!」とか「この言語でないと仕事できない!」とか感じたことは一度も無い。
仕事内容に応じて、あるいは客の要望に応じて、適切な言語を選択出来れば良いだけの事だと思っている。
逆に「嫌いな言語、苦手な言語」は存在する。
JavaScript, Perl, Ruby が苦手だし、どちらかというと嫌い。必要であれば使うが、不要であれば自分からわざわざ使わない。
「いろんな書き方が出来る言語」というのが苦手。なぜなら、ある目的を達成するための書き方が複数存在し、それぞれについて「なぜこの書き方なのか?この書き方を採用したときのメリットとデメリットは?」と考えだしてしまうから。
仕事柄、同僚やお客に対して「なぜ自分はこの書き方を採用したのか」を説明する状況が非常に多かった。
「あなたがその書き方でOKと思ったのならそれで良いんじゃない?」で通してくれる場面は殆ど無かった。
時には、「なぜオブジェクト指向とやらを使う必要があるのか?」から説明する必要もあった。
そうした場合に、書き方を決定するために色々なルートがある言語は、「なぜそのルートを選ぶのか?」「なぜ他のルートは使わないのか?」をいちいち説明するのが非常に面倒くさい。
また、単純にその分の学習コストが高い、と感じてしまう。
また、メタプログラミング的なテクニックが使われるRuby, Perlなどは「裏側で何をしているのか」を調べるための学習コストが高い、と感じている。メタプログラミング系でのトラブルに遭遇すると、その原因究明に非常に手間取る。
・・・ということで「嫌いな言語、苦手な言語」を考えてみると、その反義語として「好きな言語、得意な言語」の特徴が明らかになる。
C, Java, PHP, Pythonなど、言語文法の自由度が低い言語。Pythonはそれほど低いわけではないが、「書き方はひとつだけ」という主義は好きだ。
「出来ること、書き方」が制限されるというのは、その分学習コストが低くなる。また、自由度を高めるために凝った概念とかコムズカシイ横文字を導入したりしておらず、説明しやすい。
・・・あのね、同僚とかから質問されるわけですよ。
「JavaとかPHPってメモリの解放とか大丈夫?」
って!!
そういうレベルをいちいち説明してかなくちゃいけない。これがJavaScriptだとかPerlとかRubyと来た日には、JavaScriptのPrototypeチェーンの説明だとかスコープチェーンの説明だとか、Perlの大量の一文字・二文字記号の説明だとかパッケージ・モジュールと後付OOPのblessの説明だとか、BEGIN-ENDブロック使ったソースコードを書き換えるタイプのモジュールの説明だとか、RubyならmixinだのRoRの裏側のメタプログラミングの仕掛けだの、そうしたのをいちいち説明しなくちゃいけなくて、説明したらしたで、極めつけの質問が「うーん、なんでそんなにヤヤコシイ仕組みを使わなくちゃいけないの?」ですから!!
そういった経験があるがために、どちらかというとC言語の文法をベースとした、素直な言語を好むようになったわけです。
※うん、まぁ「お前の説明が下手くそなんだよ」と言われれば返す言葉も無いのですが。
先日の面接で「技術センスってどんなものだと思う?」と質問されて少し考え込んでしまった。
というのも、これまで仕事上で技術センスの「良し悪し」について苛立ったり悩まされたりあるいは驚嘆したりしたことが無いから。もちろんこれまでプログラミングをしてきた実績として、自分自身の技術センスがダメダメなわけではない、という自負はある。
もしかしたら、プログラムソースコードと付き合っていく中で「上手い作り方してるなぁ」とか「ダメダメだなぁ」とか感じたものが、実は「技術センス」の良し悪しだったのかもしれない。
でもそれも、技術センスの「結果」としてソースコードの上手い下手なのかもしれない。
じゃぁ根源的な「技術センス」って何だろうと思い、自分より年下の技術者で「筋が良いな」と感じた人を思い浮かべてみる。
彼・彼女らに共通なのは、「目の前のレイヤーの一つ下のレイヤーまで想像し、調べようとしている」こと。
端的にまとめると「好奇心」となるし、もう少し技術者寄りの言い方をすると「時計やラジオを分解して中の仕組みを覗いてみたい」、そういう姿勢だろう。
ただ、もう二つ、面接で言いそびれた要素がある。
IT技術に絞ると、どの技術もその後ろにはそれを考案し、実装した「人間」が必ずいる。なぜこの技術が開発されたのか?開発者を取り巻く当時の状況は?などなど。
そうした文脈、コンテキストを簡単でも良いので把握しておかないと、その技術の適用範囲、対象を間違えてしまう。
なので、「技術の向こう側にいる、それを開発した人間」を想像できること。これも「技術センス」には必要なことなんじゃないかな、と思う。
勿論「使う人間」も想像できないと駄目なのだけれど、個人的にはニーズが先にあって技術が発達すると考えているので、最初のニーズが開発者自身のひとりだけだったとしても、使う人間を想像するのは必要条件だと考えている。わざわざ明示的に「技術センス」に含める必要は無いかなとも思う。
最後の一つが「A is B, but A is NOT C」を切り分ける、あるいは切り分けようとする「意思」だと思う。
ある現象に目を向けたとき(ソフトウェアバグとか)、それの原因というか実体というか本質を捉えるのには無数の「A is NOT C」を見つける必要があると思う。
なにより、「A is B」を見つけるよりも「A is NOT C」を見つけるほうが大変。原因を取り違えるのは良くあることだけど、それも「A is B」や「A is ALSO D, E, F...」と間違えるのが簡単だから。
逆に「A is NOT C」「A is NOT D」を積み重ねていって、影響しない要素を削り落としていくのは大変。「影響しないことを断定する」のって結構精神的にも怖い。なぜなら、たった一件の肯定で全て覆ってしまうから。
だらだら長くなってしまった。「技術センス」を三行でまとめると:
最後に一点だけ。
技術センスが欠けているからと言ってIT技術者失格、というわけではないと思う。
IT技術者への入り口は沢山あり、技術力を支える基盤も沢山あるだろう。
上で述べた「技術センス」はその中の一つであり、根っこではない。
「技術センスが自分には欠けてるのではないか」と悩んでいるとすれば、「技術センスが無くてもやっていけるだろう」と開き直っても良いし、あるいは技術センスが良いと思われる知り合いを増やして助言なり手助けなりをお願いしてもいいだろう。
或いは「あいつは技術センスがない」と部下や同僚に悩んでいるとすれば、それはその人の一面だけしか見ていないのかもしれない。あるいは、「自分のほうが技術センスが高く優秀だ」という傲慢かもしれない。悩みの大元、自分が他人の無能について悩むときの心の動きについては特に注意して観察する必要がある。
蛇足:
・・・これまで「技術センス」を、どちらかというと「職人的な筋の良さ」の文脈で使っていた。
これに反対する人、あるいは別の文脈で「技術センス」を捉えている人もいるかも知れない。
自分がこれまで仕事上で尊敬できる人はどうだったかというと、必ずしも「職人的な筋の良さ」を感じられる人、あるいは上で述べたような技術センスを有する人ばかりではなかった。
アセンブラからFORTRAN、制御機器の特殊なシーケンスプログラミングを経験した辺りでマネージャに移った人は、対顧客交渉や営業、調整能力に秀でていたと共に人をdriveするのに長けていた。
C言語どっぷりで、C++やオブジェクト指向が分からないと嘆いていた人は、細かいプログラミングテクニックではなく、「システム全体」の設計や評価能力が非常に高かった。コンポーネント間の連携におけるデータの整合性について鋭い感覚を有しており、システム全体として動作するときの矛盾や辻褄の合わない点を真っ先に指摘する役割を担っていた。
そういった、技術センス以外の面で尊敬できる人たちに、随分と助けられてきたことを最後にメモして、だらだらとしたこの記事を締めさせていただきます。
2011年時点での安全なWebアプリ開発まとめ本。
VMPlayerの仮想マシンがCD-ROMで添付されていて、すぐに仮想マシン上で実行出来る点が素晴らしい。
他にも文字コードの問題や携帯サイト開発での注意点など、2011年時点での最新の内容が網羅されている。
PHPだけでなくPerl, Java, .NET の場合についても言及されているので安心。
安全なWebアプリ開発の指南書はどうしても、年を重ねると内容が古くなってしまいがち。当時は安全と思われていた対策や関数が、後になって脆弱性や問題が発見されたり。本書は「2011年時点では」信頼できる書籍だが、数年後もそうであるとは限らない。
継続した情報収集が必要。
また、逆に古い書籍を参照するときは「今の時点ではどうなのか」というのを念頭に置いて読み進める必要がある。
uClibcをPC環境で試すのに自分が使っている方法を紹介します。
環境:
CentOS 5.5 (x86, 32bit) gcc-4.1.2-48.el5 libgcc-4.1.2-48.el5 binutils-2.17.50.0.6-14.el5 uClibc-0.9.31
Buildrootは使いません。
紹介するサンプルでは以下のディレクトリ構成を使っています。"/home/msakamoto/reduced.linux"の部分は適宜読み替えてください。
/home/msakamoto/reduced.linux/uclibc_test2/ uClibc-0.9.31.tar.bz2 uClibc-0.9.31/ uclibc_test/ Makefile ret1.c helloworld.c
その他細かいディレクトリは続いて紹介するMakefile中の変数を適宜調整して対応してください。
最後の砦を崩せた・・・かも。
一段落したら、「やる夫はgccが分からないようです」みたいなAAスレでも作ってみるかな。
ひと通りC言語が使えるようになったけど、gccが何をしてるのかが分からない人向けに。
技術/Linux/uClibc/03, x86(32bit) PC環境でuClibcを試す でも注記していますが、x86(32bit)PC環境でBuildrootを使わずに構築した uClibc を静的リンクしたバイナリの場合、Segmentation Fault で異常終了してしまう現象が確認されています。
自分の環境では、 DODEBUG オプションを有効化してuClibcおよびリンク先のアプリケーションをリビルドするとこの問題を回避できました。
原因までは特定できていませんが、gdbでデバッグして気になった箇所をメモしておきます。
環境は 技術/Linux/uClibc/03, x86(32bit) PC環境でuClibcを試す と同一です。
uClibc-0.9.31を動的リンクしたプログラムの実行時に
symbol 'stdout': can't resolve symbol in lib '.../libc.so.0'
が発生してしまう場合の対処法メモ。
環境:
CentOS 5.5 (x86, 32bit) gcc-4.1.2-48.el5 libgcc-4.1.2-48.el5 binutils-2.17.50.0.6-14.el5 uClibc-0.9.31
Buildrootは使用せず、ホストマシン(=CentOS)のgccをそのまま使用しています。
Buildrootを使用していてなおかつ上記エラーが発生してしまうケースは本記事の対象外です。
古いuClibcを参照していないかなど、基本的な各種ディレクトリ設定を確認して下さい。
また対象プログラムの".interp"セクションが正しいローダを指しているか確認して下さい。
確認例:
$ readelf -x .interp foo
上記を確認した上で、 LDSO_GNU_HASH_SUPPORT を有効にして uClibc をリビルドして下さい。
General Library Settings ---> Enable GNU hash style support
"make defconfig" で設定した場合、LDSO_GNU_HASH_SUPPORT は無効になっています。
これで解決しない場合は、本記事のサポート範囲外です。
予備知識:
上記を踏まえ、LDSO_GNU_HASH_SUPPORTが無効になっていると何が起こるか:
LDSO_GNU_HASH_SUPPORTを有効にしてuClibcをリビルドすることで解決した場合は、以上の内容が原因として考えられます。
参考:
以下、"--hash-style" の実験とuClibcの関連コードの紹介です。