まず動作クロック(1秒間に処理できるステート数)を調べます。
今回は秋月の3052なので25MHz=25000000Hz。
1ms=0.001sのウェイトなので、25000000/1000=25000。
25000ステートの待ち時間を作れば良い事になります。
で、プログラムのステート時間を調べるのですが、ここに大きな問題があります。
プログラムや、データの置いてあるメモリによって実行速度が違います(実行ステート数表)。
命令 | ニーモニック | 命 令 フ ェ ッ チ | 分 岐 ア ド レ ス リ ー ド | ス タ ッ ク 操 作 | バ イ ト デ ー タ ア ク セ ス | ワ ー ド デ ー タ ア ク セ ス | 内 部 動 作 | プ ロ グ ラ ム 内 部 デ ー タ 内 部 | プ ロ グ ラ ム 内 部 デ ー タ 外 部 | プ ロ グ ラ ム 内 部 I / O | プ ロ グ ラ ム 外 部 デ ー タ 内 部 | プ ロ グ ラ ム 外 部 デ ー タ 外 部 | プ ロ グ ラ ム 外 部 I / O |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|
MOV | MOV.B #xx:8,Rd | 1 | 2 | 2 | 2 | 6 | 6 | 6 |
開発環境は大きく別けて3つ。
1と2の実行速度は2~3倍くらい違います。外部RAMのみ処理落ちしてもROM化すると
動く可能性があります。
LEDの点滅をさせたりするために簡単なウェイト処理を書いてみます。
まず関数の説明を書きます。
;****************************************************************************** ; 1ms ウェイト(25MH で 25000-10) ; ; _Wiat1ms ; 2004/11/06 : 初期バージョン完成 ; ; [書式] void Wait1ms(Uint16 wait) ; ; ; [IN] wait = ウェイト値(ms) ; ; [OUT] なし ; ; [DED] ER0 ;******************************************************************************
C言語からも、アセンブラからも呼べるように宣言。
public _Wait1ms public WAIT_1ms
C言語なら引数をE0に取得(_Wait1ms)。
アセンブラなら既にE0に値が入って呼ばれるので処理なし(WAIT_1ms)。
_Wait1ms: MOV.W @(4,ER7),E0 ; 6:14 E0 = wait WAIT_1ms:
1ms分ループで待つ。ウェイト値(3120と1038)は動作モードによって変更します。
内部 RAM のみなら、以下のようになります。
25000 = 呼び出し時間-セットアップ時間 - ループ時間 x n - リターン時間
n = (25000 - 呼び出し時間 - セットアップ時間 - リターン時間) / ループ時間
n = (25000 - 10 - 6 - 4 - 4 - 4 - 6 - 10) / (4 + 4) = 3119.5 ≒ 3120
MOV.W #3120,R0 ; 4:12 ROM か 内蔵 RAM ; MOV.W #1038,R0 ; 4:12 外部 RAM LOOP_1ms: SUB.W #1,R0 ; 4:12 BNE LOOP_1ms ; 4:12
回数が0になるまで1msウェイト処理へ。
SUB.W #1,E0 ; 4:12 BNE WAIT_1ms ; 4:14
呼び出し元へ処理を戻す。
RTS ; 10:26
まとめるとこんな感じになります。
;****************************************************************************** ; 1ms ウェイト(25MH で 25000-10) ; ; _Wiat1ms ; 2004/11/06 : 初期バージョン完成 ; ; [書式] void Wait1ms(Uint16 wait) ; ; ; [IN] wait = ウェイト値(ms) ; ; [OUT] なし ; ; [DED] ER0 ;****************************************************************************** public _Wait1ms public WAIT_1ms _Wait1ms: MOV.W @(4,ER7),E0 ; 6:14 E0 = wait WAIT_1ms: MOV.W #3120,R0 ; 4:12 ROM か 内蔵 RAM ; MOV.W #1038,R0 ; 4:12 外部 RAM LOOP_1ms: SUB.W #1,R0 ; 4:12 BNE LOOP_1ms ; 4:12 SUB.W #1,E0 ; 4:12 BNE WAIT_1ms ; 4:14 RTS ; 10:26