rpi_start.Sを読む (第8回)
前回の終わりに169行目にジャンプしたところから再開します。
今回読むのは以下の部分です。
[Rn, Rm]はMem[Rn + Rm]ですから、
次に進みます。
セクションから1減算し、ゼロでなければラベル2にジャンプする、という処理になりますね。つまり、今回読んでいるソースはn_secでループしているわけですね。
ループを抜けると、再びラベル3の処理に入ります。そして、新しいMMU_INITマクロで設定したva, pa, n_sec, attrを読み込んで、vaとpaを適切に変換して、また、今回読んだループに入るというわけです。二重ループをこうやって実現しているんですね。
しかし、よくわからないのが173行目にあるbhiのhiです。
これは、キャリーフラグが1かつゼロフラグが0である、という意味になります。
キャリーフラグが1とは桁あふれが発生した場合で、ゼロフラグが0とは命令の結果が0でない(0ならフラグは1)である、という意味です。
なるほど、n_secから1を引いたときにゼロになればゼロフラグが1になりそうです。
一方で、キャリーフラグはn_secつまり0x06や0x10からマイナス1されるだけなので、ちっとも桁あふれなど起きなさそうです。
良く考えると、マイナス1を2の補数で表すと全部の桁が1になります。全部の桁が1に対して正の数を足せば、桁あふれが起きそうな気がします。もしかすると、それでキャリーフラグが立つのかもしれません。
だったら、ゼロフラグだけ見ていればよい気もします。すっきりしないなぁ。
すっきりしませんが、今回読んだ部分をCっぽく書いて終わりにしましょう。
今回読むのは以下の部分です。
169 2: str pa, [l1table, va]
170 add va, va, #4
171 add pa, pa, #(L1_S_SIZE)
172 adds n_sec, n_sec, #-1
173 bhi 2b
まずは169行目から。
169 2: str pa, [l1table, va]
strはストア命令です。無印なので32ビットストアですね。レジスタpaをアドレス[l1table, va]にストアします。角かっこがいやらしいですね。[Rn, Rm]はMem[Rn + Rm]ですから、
*(l1table + va) = pa;ということになります。Ll1_tableは.word 0x4000の空間でしたね。
170 add va, va, #4
171 add pa, pa, #(L1_S_SIZE)
addは加算ですね。L1_S_SIZEはセクションのサイズ、つまり1MBですからva += 4; pa += 0x00100000; /* L1_S_SIZEは1M */となります。
次に進みます。
172 adds n_sec, n_sec, #-1
173 bhi 2b
addsのaddは加算命令で、のこりのsはステータスレジスタの更新あり、でしたね。セクションから1減算し、ゼロでなければラベル2にジャンプする、という処理になりますね。つまり、今回読んでいるソースはn_secでループしているわけですね。
ループを抜けると、再びラベル3の処理に入ります。そして、新しいMMU_INITマクロで設定したva, pa, n_sec, attrを読み込んで、vaとpaを適切に変換して、また、今回読んだループに入るというわけです。二重ループをこうやって実現しているんですね。
しかし、よくわからないのが173行目にあるbhiのhiです。
これは、キャリーフラグが1かつゼロフラグが0である、という意味になります。
キャリーフラグが1とは桁あふれが発生した場合で、ゼロフラグが0とは命令の結果が0でない(0ならフラグは1)である、という意味です。
なるほど、n_secから1を引いたときにゼロになればゼロフラグが1になりそうです。
一方で、キャリーフラグはn_secつまり0x06や0x10からマイナス1されるだけなので、ちっとも桁あふれなど起きなさそうです。
良く考えると、マイナス1を2の補数で表すと全部の桁が1になります。全部の桁が1に対して正の数を足せば、桁あふれが起きそうな気がします。もしかすると、それでキャリーフラグが立つのかもしれません。
だったら、ゼロフラグだけ見ていればよい気もします。すっきりしないなぁ。
すっきりしませんが、今回読んだ部分をCっぽく書いて終わりにしましょう。
do {
*(l1table + va) = pa;
va += 4;
pa += 0x00100000; /* L1_S_SIZEは1M */
} while (--n_sec > 0)
コメント(0件)
- TB-URL http://www.tokuda.net/diary/0810/tb/