ORANGE-4 で超音波距離計 HC-SR04 の出力を読んでみた。
HC-SR04
HC-SR04は、超音波を用いて2cm~450cm程度の距離を計ることができるデバイスである。
Vcc、Trig、Echo、Gnd の4本の端子がついている。
Trig端子に10μsのパルスを入力すると、測定が行われ、結果がEcho端子に出力される。
測定結果は出力されるパルスの長さで表現され、パルスの幅を $T$、音速を $C$ とすると、測定結果の距離は $TC/2$ である。
(すなわち、超音波が測定対象との間を往復するのにかかった時間が、そのままパルスの長さになるのだろう)
測定の間隔は、200ms以上空けることが要求されている。
ORANGE-4 と HC-SR04 との連携
【GMC-4】命令の実行速度を調べる - Qiita
より、ORANGE-4 において
target orange4
ldyi 1
ldi 0
ioctrl
loop:
ldi 1
out
ldi 0
out
jmpf loop
というプログラムで約10μsのパルスを生成できることがわかる。
また、ORANGE-4 は7セグメントLED消灯時、1秒あたり約160,000命令を実行できるというデータもある。
よって、音速を340m/sとすると、1命令実行する間に音は約2mm進み、距離の測定結果は約1mm伸びることになる。
プログラム
このプログラムは、MikeAssembler でアセンブルできる。
target orange4
; ORANGE4 - HC-SR04
; PORT1 - Trig
; PORT2 - Echo
ldyi 1
ldi 0
ioctrl
out
ldyi 2
ldi 2
ioctrl
; HC-SR04 の接続用にキー入力を待機する
connect_wait:
ink
jmpf connect_wait
main_loop:
; 7セグメントLEDを消灯する
scall 0
; 測定結果を初期化する
ldyi 2
ldi 0xf
st
; トリガー信号を送信する
ldyi 1
ldi 1
out
ldi 0
out
; Echoが1になるまで待機する
ldyi 2
start_wait:
in
cpi 1
jmpf start_wait
; Echoが0になるまでの時間を計測する
stop_wait:
add ; Aレジスタはポートから読み取った1
st
in
cpi 0
jmpf stop_wait
; 計測結果を表示する
ld
outn
; 200ms待つ
ldi 1
scall 0xc
; 次の計測へ
jmpf main_loop
以下は、このプログラムの ORANGE-4 モニタ用表現である。
E00:A180F70F71A282F7
E10:00F11E0A28F4A181
E20:F7180F71A2F72C1F
E30:2A64F72C0F325181
E40:ECF15
このプログラムでは、5命令で1周するループ (stop_wait
) を用いてパルスの長さを測定しているため、
測定距離が約5mm伸びるごとに測定結果が「1」増えることが期待できる。
また、今回は4ビットの数値1個のみを用いて測定結果を記録しているため、「16」すなわち約8cmの間の位置しか識別できない。
繰り上がりの処理を追加することで、解像度が落ちる (ループ1周の時間が伸びる) かわりに測定可能な範囲を伸ばせると考えられる。
ORANGE-4のI/Oの仕様を調査してみた (暴走もあるよ) - Qiita
より、ORANGE-4のI/Oポートはリセット時出力状態になっている。
そのため、プログラムを実行する前に HC-SR04、特に出力のEcho端子を接続すると、短絡する恐れがある。
一方、今回のプログラムは測定結果を表すパルスが入力されることを前提としたものになっており、測定処理を開始した後に HC-SR04 を接続すると測定開始の信号が伝わらないため測定結果を表すパルスが入力されず、無限ループに陥る恐れがある。
これを回避するため、プログラムを実行開始し、ポートを初期化した後に HC-SR04 を接続するためのキー入力待ちを設けた。
実行結果
HC-SR04 と測定対象の距離を変えるのに従って、7セグメントLEDに表示している測定結果が変わっている。