先日、UFT-8文字コードをターミナルに送ってあげればSBC6303でも日本語表示できることに気がつきました。
極めて当たり前のことだったのですが、UFT-8文字コードをターミナルに送ってあげれば #SBC6303 でも日本語表示できるんですね。 pic.twitter.com/BIRHBa0DqA
— おかずのり (@okazunori68) October 10, 2021
そこで今さらですがSBC6303で「ズンドコチェック」を日本語表記で実装してみます。
「ズンドコチェック」とは2016年に流行ったプログラムです
Javaの講義、試験が「自作関数を作り記述しなさい」って問題だったから
— てくも (@kumiromilk) March 9, 2016
「ズン」「ドコ」のいずれかをランダムで出力し続けて「ズン」「ズン」「ズン」「ズン」「ドコ」の配列が出たら「キ・ヨ・シ!」って出力した後終了って関数作ったら満点で単位貰ってた
さまざまな言語で実装され、中にはPalo Alto Tiny BASICやZ80アセンブラなんてのもありました。
ズンドコチェックの実装
手順は以下の通りです。
- 2値の乱数を発生させる
- 乱数に応じて「ズン」あるいは「ドコ」を出力する
- 「ドコ」の前に「ズン」が4回以上出力されていたら「キ・ヨ・シ!」を出力して終了
- 3回以下であれば先頭に戻る
短いコードなので下記に全てを示します。
; zundoko program
.cr 6301
.lf zundoko
.tf zundoko.s19,s19
; ********************************************************************
; * Include Files *
; ********************************************************************
.in HD6303R_chip.def
.in service_routine.def
; ********************************************************************
; * 変数 Variables *
; ********************************************************************
.sm RAM
.or $80
ZunCount .bs 1 ; zunカウンタ
RndNumber .bs 2 ; 乱数
; ********************************************************************
; * Program Start *
; ********************************************************************
.sm CODE
.or PROGRAM_START
start: ldx #MSG_START
jsr write_line
jsr read_char
set_seed:
.top ldd <FRC ; Free run timer 読み出し
beq :top ; Seedはゼロ以外
std <RndNumber
zundoko_check:
.top clr ZunCount
.loop bsr xorshift_16
bmi :doko
; 乱数が正数だったら
ldx #MSG_ZUN ; print"zun"
jsr write_line
inc ZunCount ; zunカウンタ += 1
bra :loop
.doko ; 乱数が負数だったら
ldx #MSG_DOKO ; print"doko"
jsr write_line
tim #%11111100,<ZunCount
bne :end
; zunカウンタ < 4
bra :top ; zunカウンタ = 0
.end ; zunカウンタ >= 4
ldx #MSG_KIYOSHI ; print"kiyoshi"
jsr write_line
bra start
MSG_START .az "Hit any key.",#CR,#LF
MSG_ZUN .hs e382bae383b3.20.00 ; "ズン ",0
MSG_DOKO .hs e38389e382b3.20.00 ; "ドコ ",0
MSG_KIYOSHI .hs e382ade383bbe383a8e383bbe382b7efbc81 ; "キ・ヨ・シ!"
.hs 0d0a.0d0a.00 ; "\n\n",0
; 16-bit xorshift pseudorandom number generator
xorshift_16:
ldab <RndNumber
lsrb
ldab <RndNumber+1
rorb
eorb <RndNumber
stab <RndNumber
rorb
eorb <RndNumber+1
stab <RndNumber+1
tba
eora <RndNumber
staa <RndNumber
rts
こんな感じですね。
乱数の発生
何かキーを押してもらってプログラムをスタートします(27行目)。
その際にFRCの値を乱数のシード値とします(32行目)。
Xorshiftのシード値はゼロ以外でないといけないので、ゼロの場合はもう一度読み込みます(33行目)。
「ズン」「ドコ」「キ・ヨ・シ!」を出力する
xorshift_16ルーチンを呼ぶとDレジスタに$0001
から$ffff
までの乱数が返ってきます。2値でいいので、Nフラグ(MSB)を見て分岐させます(39行目)。
「ズン」を出力するたびにカウンタ(ZunCount)を+1します。
「ドコ」を出力したらカウンタを確認して4以上になっていたら「キ・ヨ・シ!」を出力して終了します。3以下であればカウンタをクリアして先頭に戻ります。
4以上を判断するのにtim #%11111100,<ZunCountとしています。
4は二進数で表すと%00000100
です。つまりカウンタの上位6ビットのいずれかが”1″になっているかどうかで4以上かどうか判断できます。
tim命令でZunCountと%11111100
のANDを取り、Zフラグが立っていれば4未満、立っていなければ4以上です。
文字列について
SB-Assemblerの.ASディレクティブはASCIIコードしか解釈しないようです。
しょうがないのでPythonでやっつけの変換プログラムを作りました。
string = 'ズンドコキ・ヨ・シ!'
for i in string.encode('utf-8'):
s = str(hex(i))
print(s[2:4], end='')
# result
# e382bae383b3e38389e382b3e382ade383bbe383a8e383bbe382b7efbc81
この結果を.HSディレクティブで定義します。
実行します
3回試してみましたが、うまく表示されました!
コメント