標準TTLだけ(!)でCPUをつくろう!(組立てキットです!)
(ホントは74HC、CMOSなんだけど…)
[第587回]
●整数BASICコンパイラ(SBASIC) FOR〜NEXT
前回、前々回と2回にわたって、100回の加算を行いながら、OUT文を実行して、パルスを出力するプログラムを、Z80アセンブラ(機械語)プログラム、Z80BASIC(インタプリタ)プログラム、SBASIC(コンパイラ)プログラムの3通り書いて、それぞれ実行してその出力パルスをオシロスコープで見てみました。
BASICでは加算命令とIF GOTOとの組み合わせで時間待ちループを作る方法のほかに、FOR NEXT文による方法が考えられます。
そこで今回はFOR NEXT文を使って、パルスを出力してみたいと思います。
まずはZ80BASICです。
前々回([第585回])のプログラムの
B%=B%+1:IF B%<=A% GOTO
のところを
FOR A%=1 TO 100:NEXT A%
に変更しました。
実行結果です。
FOR NEXT文100回のループの実行時間は約20msecです。
[第585回]で100回加算とGOTOを繰り返したプログラムの実行時間は130msecでした。
おお。
大幅に速度アップしました。
プログラムの動作としてはどちらも同じことをやっていても、実行時間は全然異なる結果になりました。
加算プログラムは汎用の計算ルーチンをコールするためにどうしても時間がかかってしまいます。
一方FOR NEXT文は型にはまった動作をすることになりますから、それだけ無駄を省いたプログラムにできるためです。
インタプリタの命令としては、FOR NEXT文の実行時間は「非常に速い」ということが言えると思います。
次はSBASICです。
いつものようにメモ帳(notepad)でソースプログラムを書きました。
'SBASIC TEST3 10/8/19 ORG=$8004 OUT $83,$80 *LOOP:OUT $80,0 FOR A%=1 TO 100:NEXT A% OUT $80,1 FOR A%=1 TO 100:NEXT A% GOTO *LOOP
SBASICコンパイラで機械語のバイナリファイルを作成します。
前回と同じように、コンパイルの結果作成されたバイナリファイルsbtest3.binを逆アセンブラZDAS.COMで逆アセンブルしてみました。
逆アセンブルしてできたリストです。
8004 218300 LD HL,$0083 8007 4D LD C,L 8008 218000 LD HL,$0080 800B ED69 OUT (C),L 800D 218000 LD HL,$0080 8010 4D LD C,L 8011 210000 LD HL,$0000 8014 ED69 OUT (C),L 8016 AF XOR A 8017 320BF2 LD ($F20B),A 801A CD5E3E CALL $3E5E 801D 2140F4 LD HL,$F440 8020 7D LD A,L 8021 110100 LD DE,$0001 8024 73 LD (HL),E 8025 23 INC HL 8026 72 LD (HL),D 8027 116400 LD DE,$0064 802A 010100 LD BC,$0001 802D 213280 LD HL,$8032 8030 08 EX AF,AF' 8031 D9 EXX 8032 CD613E CALL $3E61 8035 218000 LD HL,$0080 8038 4D LD C,L 8039 210100 LD HL,$0001 803C ED69 OUT (C),L 803E CD5E3E CALL $3E5E 8041 2140F4 LD HL,$F440 8044 7D LD A,L 8045 110100 LD DE,$0001 8048 73 LD (HL),E 8049 23 INC HL 804A 72 LD (HL),D 804B 116400 LD DE,$0064 804E 010100 LD BC,$0001 8051 215680 LD HL,$8056 8054 08 EX AF,AF' 8055 D9 EXX 8056 CD613E CALL $3E61 8059 C30D80 JP $800D 805C C9 RET
CALLしているアドレス3E5EはFOR文のサブルーチンです。
3E61はNEXT文のサブルーチンです。
SBASICコンパイラでバイナリファイルとともに作成されたsbtest2.wkファイルです。
0000 'SBASIC TEST3 10/8/19 0000 ORG=$8004 8004 OUT $83,$80 800D *LOOP:800D OUT $80,0 8016 FOR A%=1 TO 100:8032 NEXT A% 8035 OUT $80,1 803E FOR A%=1 TO 100:8056 NEXT A% 8059 GOTO *LOOP 805C
SBASICコンパイラで作成された、機械語のバイナリファイルは、Z80BASICを起動してから、/LDコマンドでメモリにロードします。
機械語サブルーチンコール命令USR($4004)をダイレクトに実行してもよいのですが、今回はJPコマンドを使いました。
実行結果です。
FOR NEXTループ100回の実行時間は5msecほどという結果になりました。
[第585回]で100回加算とGOTOを繰り返したプログラムの実行時間は約4.4msecでした。
あれ。
SBASICコンパイラでは、逆にFOR NEXTのほうが時間がかかってしまいました。
Z80BASICインタプリタでは加算ルーチンよりもFOR NEXTルーチンのほうが効率良く実行されたのですが、SBASICコンパイラでは加算処理とFOR NEXTの処理の実行時間がそれほど差がないということのために、こういう結果になりました。
今回のFOR NEXT文についてはZ80BASICインタプリタの実行速度が結構速かったために、SBASICコンパイラとの差が縮まってしまいましたが、それでもまだインタプリタに比べて、コンパイラのほうが数倍速い、ということに間違いはありません。
2010.8.19upload
前へ
次へ
ホームページトップへ戻る