ひとつ上へ

結局 v0.2 は作らずじまいだったけど... まぁそういうところもそのまま収録。

TeX ソース

MULT-i でざいなぁずのぉと

M・anon

MULT-i は P/ECE用 μITRON 仕様準拠のリアルタイムカーネルです。本稿では、MULT-i ver.0.1 の制作にあたって、困ったこと、はまったこと、無意味に凝ったこと、ver.0.2 について考えていること、等々を述べます。他のカーネルの P/ECE への移植や、読者が自分のカーネルを作ろうと思った時など、ソースコードだけではわからない点について参考になれば幸いです。

本稿では、00README.TXT で述べられているような基本的なことについては特に説明をしません。

ことのはじめ

それは、確か /.jp の記事だったと思います。slashdot を御存知のかたならご存知とは思いますが、ニュースを伝える記事に、いろいろなコメントが付くようになっているのが slashdot と他のありがちなニュースサイトの違いであり魅力になっています。

(この記事です → スラッシュドット・ジャパン | 開発環境付属、ロイヤリティフリーな新携帯ゲーム機)

で、P/ECE の発売発表と同時に明らかにされたのは、その CPU でした。さっそくいく人かの物好きが仕様書を取り寄せ、Linux を載せるにはアレだ、とかなんだとかコメントが付き、その中に「載せるなら μITRON でしょ」というのがありました。 (これ → #18782 )

(追記。S1C33 用 Linux として Axe の axLinux があります http://www.axe-inc.co.jp/pr/200206171.html

その後しばらく様子見していたんですけど、2001 年の冬コミ準備でサークルのオフラインミーティングをやった時、既に買ったひとの P/ECE を見て、「欲しいぃ ! ! 」とばかりに衝動買いしてしまいました。 (見せてくれたのは ar氏)

買ってしばらくは BlackWings をクリアしてみたりアルカリ電池でも一瞬で消えるのに泣いてみたり、画像回転のデモを作って冬コミで見せびらかしたりしてたんですが、とある日、某コンシューマ携帯ゲーム機用開発環境と P/ECE について比較したウェブ頁で(これ書くために確認しに行ったら消えてました (^^; )P/ECE のカーネルについて「ITRON系?」とか、とんでもなことが書いてあるではないですか。(2ちゃんねるの P/ECE 関係のログを見ても ITRON についての話が出てたりしてるようですが)

ここで一発 ITRON をのせてしまえ、とそれを見た私は発奮して(セロトニン? (笑))しまい、前々から少しずつ調べていた本家カーネルの分析とコンパイラ周辺の分析から得られた情報をもとに、一気に MULT-i を作り上げてしまった、というのが、だいたいの「MULT-i ができるまで」ということになります。

Inside 本家カーネル

P/ECE の未公開部分というのは、知ってる人は知ってるという話ではありますが、やはり独自カーネルを書くとなると、いろいろと不安要素として問題になってきます。例えば、とにかくデバッグするために何らかの出力が欲しいけど、LCD 以外にはてきとうな出力先が無くて、でも... とか。(私はやりませんでしたが、いわゆる「拡張端子」に LED を付けるとか、カーネルを作るなら、とにかく単純で確実なデバッグ手段の確保をおすすめします)そんなわけで、独自カーネルとはいえ、いろいろと本家カーネルに依存しないといけない部分が多くあります。そんなわけで、やはり九州には足を向けて寝られません。

では、MULT-i ver.0.1 が依存している本家カーネル関連の部分を説明しながら、本家カーネルの Inside に迫ってみようと思います。

まず、制作メモの中に残されていた本家カーネルのメモリマップについてのメモを見てみます。

[000000    〜      001FFF       8K       内部 RAM]
(以下,システム 4K)
000000    〜      00001F                ????
000020    〜      0003FF                カーネルサービステーブル
000400    〜      00051F                トラップテーブル
000520    〜      000673                RAM に置くカーネルコードの置場 1
000674    〜      000D6F                カーネルのワークエリア
000E00    〜      000E93                RAM に置くカーネルコードの置場 2
(以下,スタック 4K)
001000    〜      001FFF                スタック
-------------------------------------------------------------------------
040000    〜      04FFFF      64K       内蔵 I/O
-------------------------------------------------------------------------
100000    〜      13FFFF     256K       外部 SRAM (ユーザ)
-------------------------------------------------------------------------
[C00000    〜      C7FFFF     512K       外部 フラッシュROM]
C00000    〜      C01FFF                ブート・ブロック (※)
C02000    〜      endmark               カーネル
C0C000    〜      C27FFF     112K       フォント
C28000    〜      C7FFFF                ファイルシステム

本稿を読もうというかたなら、P/ECE 初の商業本「P/ECE ハンドブック」は持っておられると思うので、それに載っているメモリマップと対照させながら見てみてください(本体の側のには SRAM の容量に誤植があります。綴じ込み附録の側のほうは正しいので本体側のほうに訂正を入れておきましょう)。実はもうひとつ、pceLCDTransDirect のためのデータ形式ってネタもあったんですが、P/ECE 本に載ってたので没りました。

最も本家カーネルに依存している点は、やはりブート・ブロックだと言えます。メモリマップ中にも※マークが付いてますが、電源投入、またはリセット直後の CPU が実行するコードであり、また、方向ボタンの下と SELECT を押している場合には、いわゆる「緊急用カーネル」として動作しているのがここのコードで、これがあるおかげで、全く何もできない独自カーネルを載せてしまっても、元の P/ECE に戻すことができます。

このへんのメモリへの配置をコンパイル時に調整しているのは、pcekn.cm というファイルで、makefile を見るとわかりますが、これを linker に渡して .srf ファイルを生成しています。もしこれを変にいぢると、緊急用カーネルを上書きしてしまうような .srf ファイルが出来てしまいます。気をつけましょう。

緊急用カーネルを起動しない場合、ブート・ブロックにあるコードは、0xc02000〜にあるカーネルコードの先頭 4 バイトに書かれているアドレスに飛びます。「ここまでは変更不可」と pcekn.c に書かれているあたりの直前 10 行ぶんぐらいが、ここらへんの処理のために存在しています。

まず、static const PCETPENT entry_point[1] が、先頭 4 バイトに置かれることになるコードになり、そこにはその直後にある void BootEntry00( void ) のアドレスが書かれています。ブートブロックは BootEntry00 を呼び出し、そこに書かれているインラインアセンブラのコードの通り、関数 void BootEntry( void ) に処理が渡ります。と、このへんまで書いておけばあとは順を追って読めるでしょう。

r8 の罠

カーネルの分析と独自カーネルの制作にあたり、不要そうに見える処理はバッサリと切り捨てています。はじめてカーネルを使わずに動かしたプログラムは、一見普通に動くのですが、時々止まることがありました。その止まり方が、うまく動いている時はずっと動くのに、止まる時は動き出した直後に止まる、というなんとも謎な挙動をしたのです。

いかにも「タイミング絡みで変なことが起きている」という感じに見えて、LCD 関係のコード(後述)とかをいろいろと触ったりしていたのですが、ある時ふと、本家カーネルと比較してみて、BootEntry の先頭の r8 の初期化を取っ払ってしまっているのが気になりました。これかな? と思って r8 を 0 に初期化するようにしてみたところ、安定して動くようになった、ということがありました。

EPSON のC言語処理系のマニュアルとかを眺めてみると、r8 が特定の値に設定されていることを前提に、r8 相対でのアドレッシングを使うようなコードをコンパイラが吐くようになっているようです。特に、-O オプションによって変化するらしいのでよけいにはまっていたような感じです。

サービステーブル

MULT-i では、いまのところ、本家カーネルがカーネルルーチンをアプリから呼ぶために用意している、0x20〜0x3ffのメモリについては、使わずにあけてあります。これ、自分でも忘れていて、これを書くためにソースに目を通していて思い出しました。

LCD

とにかく、動いているかどうかの確認のために、場合によっては暴走する場所を特定するためにも、最低限の画面表示が必要です。最近でこそ LCDC に関する情報も流れていますが、MULT-i 制作当時は本家カーネルのコードを読んで、コマンド体系を推測するしか手がありませんでした。そんなわけで MULT-i は、本家カーネルの LCD 関連部分はほとんどそのまま流用してます。

MULT-i の lcd.c を、本家カーネルの lcd.c と比較してもらうとわかると思いますが、2割〜3割程度削ってあります。使わないコードを削ったつもりです。

他には、本家カーネルでは、速度を稼ぐために LCD 関係のルーチンの一部を内部 RAM に置くようになってます。フラッシュ操作のコードも、フラッシュ操作中はフラッシュにアクセスできないので内部 RAM に置かれます。LCD のコードは、単純に速度の問題なので、MULT-i では普通にフラッシュに置くように変更してあります。

あと、本家カーネルの lcd.cGetLCD で、LCDWK *wp = &lcdwk; //(LCDWK *)0x800; となっているので、一見決め打ちなのかな、と思いますが、v1.15 のコメントにあるように、決め打ちではありません。古いコードをコメントアウトで残してあるだけのようです。

 

v0.2 に手を付ける前に、LCD ドライバを書こうかな、とも考えています。デバッグのためにはテキスト VRAM みたいな仕掛けがあると便利かな、とか思うので。

遅延ディスパッチ

以下の文章中の [x.y.z] のような表現は仕様(μITRON4.0)書中の関連個所を示しています。適宜参照しつつお読みください。

遅延ディスパッチとは

簡単なマルチタスクモニタを作っているうちはあまり問題になりませんが、本格的な(RT)OSを作るとなるとすぐに、非常に大きな問題になるのが、割込みハンドラとディスパッチが絡む、微妙なタイミングでの制御の問題です。

以下、細かい議論になるので、ITRON に慣れていないかたは用語の確認を [3.1] しておいてください。

ある RTOS ベースのリアルタイムシステムを考えてみます。そのシステムでは、優先度の異なる複数のタスクをサポートし、また、割込みハンドラから OS のサービスコールを呼び出して,起床待ち状態にあるタスクを起床させることができるようになっているとします。さらに、割込みハンドラは、タスクのコンテキスト(スタック)を借りて動作することとします(Unix では普通、割込みで即カーネルモードに遷移するので、この辺の感覚は非常に違うと思います)。

さて、このシステムで次のような場合にどんなことが起きるでしょうか?

ちょっと考えれば、割込みハンドラの、サービスコールを呼び出してから以降の部分の処理が、タスクb に CPU が戻るまで実行されないことがわかると思います。これは、割込みハンドラの性質から考えて、とてもまずいわけです。

仕様 [3.5.3] では、ディスパッチャの優先順位が割込みハンドラより低いこと、優先順位の高い処理があるのに、優先順位の低い処理をやってはいけないことが定められており、このような場合に適切な処理をすることが求められています。

仕様書中の補足説明にあるように、この規則は μITRON3.0 までは、割込みハンドラの終了までディスパッチャの起動が遅延される、という「遅延ディスパッチの原則」と呼ばれていました。直感的に便利な表現なので、本節でもこれを使いました。

μITRON4.0 では、研究成果(ref. tbd 確か「ITRON標準ガイドブック2」にあったはず ← 見つからなかった。確か坂村研から出てた論文)からのフィードバックとして、割込みハンドラから呼ばれたサービスコールの処理の実行は、割込みハンドラの終了まで遅延させてよい [3.6.2] という「サービスコールの遅延実行」が規定されています。

(2010年3月追記) リアルタイムOSの内部構造を見てみよう! » 3.処理単位の種類と優先順位 が非常に参考になります。

TRON Chipでの実現

TRON Chip ではこれを考慮した遅延割込み(DI)という機構が考えられました。

坂村研サイトで昔は TRON Chip の仕様書が公開されていたのですが、消えてしまったので、ウェブアーカイブから「遅延割込み」のところを見てください。

http://web.archive.org/web/*/www.sakamura-lab.org/TRON/CHIP/1/1_8/122_124.htm

アーカイブでは図が見られないようなので手元のバックアップから転載しておきます。

図7
図7. 遅延割込みの例

MULT-i でのトリック

MULT-i では、この遅延割込み機能に良く似た仕掛けを実現しています。

典型的なハードウェアの割込み処理機構は、一般に割込み要求レジスタと呼ばれるレジスタが、割込み要求によってセットされ、割込みを受付けたらリセットする、という感じになっています。

なぜか P/ECE の本家カーネルでは、この役割をするレジスタが、ソフトウェア側からも「要求あり」にセットできるという謎な設定で CPU を使うようになっています。

hard.cInitHard の最後のほう、

bp[0x29f] = 0x06;  // 割り込み要因フラグのみ RD/WR方式

というところです。データシートでは S1C33209/221/222 テクニカルマニュアルの FUNCTION PART の Ⅱ-5 ITC(割り込みコントローラ)のところにあります。

MULT-i も、一応本家カーネルにならって(というか、何処にどう影響が出るのか皆目わからないので手が付けられない)、同じ設定で使用しています。

 

P/ECE の CPU には、割り込みレベルという概念があり、外部割り込みには割り込み要因ごとに割り込みレベルという値を設定できます。PSR(プロセッサ状態レジスタ)の IL というフィールドの現在の値よりも大きい割り込みレベルの割り込みのみ、CPU は受け付けます。

ソフトウェアから割り込み要求のセットができるので、割り込みレベル 1(0 以外では一番低い)をディスパッチ専用に割り当て、ディスパッチが必要になったらその割り込み要求をセットするようにすれば、割込みハンドラの処理中(IL > 1)なら割込みハンドラが終了してタスクに戻る(割り込みレベルが 0 になる)時にディスパッチャが起動してディスパッチが起きる、というように、うまく処理できるわけです。

ソースコードでは、mikernel.c の、先頭にあるマクロ REQ_DSPmi_start 関数中の /* 遅延ディスパッチのための仕掛け */ というコメントのあとにあるブロック、dispatch 関数(ディスパッチャ)のあたりが、これに関連する部分ということになります。

おわりに

参考文献

今まで書き忘れてたのですが、P/ECE の CD の中の「資料」というディレクトリの中にあるテキストファイルは非常に参考になります。ぜひ読んでおきましょう。以下、ITRON 関係の参考文献を挙げておきます。

μITRON4.0仕様

T-Engine フォーラムの仕様書のページ http://www.t-engine.org/japanese/spec.html に ITRON 関係の仕様書も置かれています。

2010 年 1 月現在、最新版は 4.03.03 です。トロン協会(アーカイブ)のほうにしか最新版がありませんので注意してください。

ITRON プロジェクトの頁から PDF で拾えます(確認しようと思ったら www.itron.gr.jp が not found になるので高田研にあるほうを書いておきます ← という注は紙版のもの。www.ertl.ics.tut.ac.jp という豊橋技科大ドメインのサーバでしたが今はそこもありません)

旧い版も取れますが、ふつ〜、最新版でいいでしょう。(紙版の時は 4.01 が最新版だった)

紙媒体で欲しい場合はトロン協会から印刷したのを買えますが、会員でないと¥5000 もします(会員は¥3000)。kinko'sで PDF を出力するのとどっちが安いかな、とか考えてしまいますね。(トロン協会は解散しましたが、多分 T-Engine フォーラムから買えると思います 2010/Jan)

トロン協会の話が出たのでトロン協会についてちと書いておきます。基本的に法人によって構成されており、個人で会員にはなれません。会費もけっこうします。ただし、ワーキンググループ(以下 WG)への参加は公開の WG だったら誰でも自由にできます。特に ITRON に関しては公開 WG がさかんにおこなわれており、個人の意見がフィードバックされているようです。また、ITRON については、セミナーも結構開催されてます。参加費がそこそこ手頃のなのもあったように思います。

(2010 年 1 月追記)トロン協会は 2010 年 1 月 15 日に解散になりました。ウェブコンテンツには引き続きアクセスできるようですのでリンクはそのままにしてあります。活動全般は T-Engine フォーラムに引き継がれたようです。また、高田先生による、ITRON の有力な実装のひとつとして TOPPERS プロジェクトがあります。(ところで文字収録センターは?)

μITRON3.0標準ハンドブック改訂新版

http://www.personal-media.co.jp/book/tron/154.html
μITRON3.0の仕様です。「関数名や引数などが大きく変わりました。(中略)現場からはかなりの怒りの声が上がっています。」なんていう文章が、某「乳の詫び状」に載りましたけど( http://www.asahi-net.or.jp/~KI4s-NKMR/wabijo57.html の 2002/07/28)、これをネタに中傷しようとするヤシはまず仕様をちゃんと比べてみてからにしてホスィ。

まぁ、冗談はさておき、結構高価いんですが(¥4000)、μITRON4.0 では削られてしまったネットワーク機能とか色々と面白いので、書店で買えるということも含めて、4.0 の紙媒体版の代わりにこっちを買うというテもありかと思われます。

μITRON4.0標準ガイドブック

http://www.personal-media.co.jp/book/tron/191.html
ITRON の解説書の最新版です。ITRON を作ろう、とか思ったら、とりあえずTM買っておいていいと思います。

C言語でふつ〜な手続き形のプログラミングができて、イベントドリブンも齧ったことがある、という程度の前提は必要かと思いますが、リアルタイムシステムのプログラミングの教科書としてもそこそこ使えると思います。

(2010/Oct/29追記)聞いたところでは、古いガイドブックが ITRON を作りたい人向けだったのに対して、新しいガイドブックは使いたい人向けの内容に力を入れているということなので、作る、という目的の場合「ITRON標準ガイドブック2」も参考になるかもしれません。

ITRON・μITRON標準ハンドブック

ITRON2 と最初の μITRON の仕様。現在品切・増刷未定ですが、PDF で入手可能。

入手は PMC の頁 http://www.personal-media.co.jp/book/tron/079.html から。

内容はかなり古いものですが、のちの μITRON が、ITRON 全体の後継としていろいろと大きな規格になってしまったのに対し、このころの μITRON は、フルセットでもかなり小さいので、勉強用には悪くないと個人的には思います。とりあえずTMタダで PDF が読めますし。

実用 組込みOS構築技法

http://www.kyoritsu-pub.co.jp/shinkan/shin0111_01.html
ITRON の解説ではない RTOS の教科書。TRON のデンパは浴びたくないけど RTOS の勉強はしたい、とか思うんだったらぜひどうぞ。

あと、xxx_yyy() という形のネーミング規則が嫌とかいう場合もどうぞ (^^;

紙版を作った頃には参考文献も少なかったのですが、現在は他にも数多く教科書や参考書が出てますので、特にこれにこだわることもないでしょう。

リアルタイム・オペレーティングシステム講座

http://www.japan-net.or.jp/~etsuko/mtm/mtm.html (現在消滅) にあった、Ryoさんによる解説。だいぶ参考にしました。(紙版では忘れていたので加筆)

NORTi ソースコード

トラ技コンピュータ1992年1月号掲載。小さいが一通り機能が揃った ITRON 実装の全貌を参考にできます。(紙版では忘れていたので加筆)

Free ITRON 大百科 Vol.1 および Vol.2

By Free ITRON クラブ,電脳文化祭実行委員会 (紙版では忘れていたので加筆)

自分のカーネルを作ってみませんか?

MULT-i では、μITRON3.0 のレベル R を目標にしたので、あちこちで設計と実装がうまくいっていないところがあるとも思います。独自カーネルに挑戦するだけなら、もっと手を抜けるところがいろいろとあります。MULT-i ver.0.1 のコードは、とにかく何らかのコードを実行できる最小限度のところまで、本家カーネルを読むにあたって煩雑な部分は削ってありますので、機械語モニタ程度のシステムを載せるのであれば、MULT-i のコードを流用すればすぐにできるでしょう。

本稿によって、ひとりでも、自作カーネルを作ってみよう、と思って実行に移してくれるひとがいれば著者として幸いに思います。

(追加情報。今では YARV の中の人として有名な笹田氏により、開聞(並木研OmicronTiki)が P/ECE に移植されています(このへんにその話が)が、それに協力しました。ET 2003 の話で「P/ECE かよ」ってのもそれの上でやってます。このウィンドウシステムについては SIGOS での発表( NAID: 110002913905 NAID: 110002913927 )とか)。)

謝辞

TRON プロジェクトのプロジェクトリーダー坂村先生、ITRON プロジェクトの高田先生、プロジェクトにかかわってこんにちの ITRON をつくりあげられた多くの研究者やエンジニアの皆様、そしてメーカーに感謝します。

また、なんだかんだ言われながらも P/ECE という遊べるおもちゃを企画し、市場に送り出した AQUAPLUS に、iSmart のハード・ソフトをともに開発された開発者のかたに、そして P/ECE で遊んでいる皆様にも感謝を。

そして、いろいろと思い出させてくれた KS‘兄君’に国土交通大臣賞を。

参考にしてます

P/ECE研究室 紙版では http://north.hokkai.net/~nsawa/ でした
自分は性格的に一発屋なので、コツコツとハードウェアのいじりかたを研究されている Naoyuki Sawa さんには頭が上がりません。

どうやら独自カーネルへの道ということで研究を続けておられるようなので、MULT-i があっさりと追い越される日も近い... かも。

 

銀次郎のパーソナルページ http://www.eps.ddnn.jp/~gin/ (消滅?)
ハードウェア改造とか。どっか参考にさせてもらった記憶があるんですけど... どこだったか記憶が消し飛んでます m(__)m

 

六波羅さんのスペース
フラッシュ換装ネタの技術情報をかなり参考にした... 記憶があります。

 

半年前の自分は他人だ、というのを痛感しました。やはり開発記録はちゃんと付けなければ、といつも思うだけなんですよね。

おくづけ (初版)

      書名 : MULT-iでざいなぁずのぉと
      著者 : M・anon
     頒布者 : BBS電波温泉( http://www.interq.or.jp/earth/rsp/ )
   発行年月日 : 2002年8月11日
    版下出力 : 某プリンタ
 印刷(コピー) : 何処かのコンビニ
      製本 : 人力

おまけ

超断片ウェブサイト Hitode Yamatsuki さんの P/ware のジョークページです。プロジェクト X の TRON の回の記念とのこと。