screen01 中身確認中の控え
ぐぬぬ。以下の記述がアレ。
The sender waits until the Status field has a 0 in the top bit.
手続き定義が以下あたりの部分。
wait1$: status .req r3 ldr status,[mailbox,#0x18] tst status,#0x80000000 .unreq status bne wait1$
以下な補足が右側にあります。
tst reg,#val computes and reg,#val and compares the result with 0.
んーとマニュアルその他を見る限りでは tst は and 演算するんだけどその結果が 0 であれば zero flag は 1 になるのかな。逆に 0x18 な status を取得した結果、top bit が 1 の場合、結果はゼロにならないので zero flag は 0 で NE な条件を満たす、という理解で良いのかどうか。
上記ループは 0x18 な先頭 bit が 0 になるまで待つ、という事なのか。
Mailbox{Read,Write} は大体把握?
とりあえず MailboxWrite から。
.globl MailboxWrite MailboxWrite: tst r0,#0b1111 movne pc,lr cmp r1,#15 movhi pc,lr
引数チェック。r0 は末端 4bit は 0 でなければならないのと r1 は末端 4bit (本当は 3bit なのかどうか) 以外は 0 でなければならない事を確認。ここでも tst と ne が使われてますね。and して末端 4 bit が 0 でなければ zero flag が 0 になって NE になるのか。
で、レジスタに名前付けて r0 を退避して GetMailboxBase を r0 に取得。
channel .req r1 value.req r2 mov value,r0 push {lr} bl GetMailboxBase mailbox .req r0
んで、Status の確認なループ。
wait1$: status .req r3 ldr status,[mailbox,#0x18] tst status,#0x80000000 .unreq status bne wait1$
最終的に chennel + value => value して
add value,channel .unreq channel
Write なメモリマップに格納。
str value,[mailbox,#0x20] .unreq value .unreq mailbox pop {pc}
もう少し。Read も確認します。Read は入力チャネルのみが渡される模様。
.globl MailboxRead MailboxRead: cmp r0,#15 movhi pc,lr
で、r0 を退避して MailboxBase なアドレス取得。
channel .req r1 mov channel,r0 push {lr} bl GetMailboxBase mailbox .req r0
で、こちらも Status 取得して 30 番目の bit をチェックしてますね。
rightmail$: wait2$: status .req r2 ldr status,[mailbox,#0x18] tst status,#0x40000000 .unreq status bne wait2$
で、準備ができたら Read するのか。
mail .req r2 ldr mail,[mailbox,#0]
次に channel をチェックして invalid なら rightmail まで戻ってます。
inchan .req r3 and inchan,mail,#0b1111 teq inchan,channel .unreq inchan bne rightmail$
で、後始末および r0 に戻り値セット。末端 4 bit は channel なので略ですね。
.unreq mailbox .unreq channel and r0,mail,#0xfffffff0 .unreq mail pop {pc}
これで graphic card との情報のやりとりができるようになった、という事なのか。続きは別途で。
続き
は別途投入な方向で。
最後に再度 tst を
復習。and 演算して結果が 0 になると zero flag が 1 になり、eq な状態になる。逆に結果が 0 以外の場合は zero flag が 0 になって ne な状態になる、って理解で良いのかな。