2019.4.28
前へ
次へ
ホームページトップへ戻る

[新連載]CPLD入門!
〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜
いつか使うことになるだろうと思ってはいたのですが。
何を今頃になって、というようなものですが。
ようやく本気で、CPLDと四つに取り組みます。
〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜



[第39回]


●ND80ZSMのモニタプログラムリスト(一部)

今回の回路に対応して変更した部分のND80ZSMのモニタプログラムリストです。
ND80ZSMはND80Z3.5から7セグメントLED回路、5X5キーボード回路、USBインターフェース回路を外して、マイコン独立化セット、新マイコン独立化セットを接続して動作することに特化したボードでした。
しかしND80ZSMにできるだけローコストな7セグメントLED回路と5X5キーボード回路を外付けできれば、ND80Z3.5のローコスト版にすることもできるのではないかと考えたことで、このところの作業となりました。
外付けする回路がND80Z3.5と同じ回路ならば、ND80Z3.5のモニタプログラムをそのまま使うことができます。
キーボード回路はTTLロジック回路をそのままEPM7128SLC84に置き換えただけなので、ND80Z3.5のモニタプログラムをそのまま使えます。
しかし7セグメントLED回路はTTL回路をCPLDに置き換えただけではなくて、DMA回路だったところをPIC16F57に置き換えました。
もともとのND80Z3.5モニタプログラムでは7セグメントLED表示はDMAを利用しているために、RAMのセグメント表示用アドレスにセグメントデータを書き込むだけで済みました。
PIC16F57を利用する今回の回路では、(DMAではないため)セグメントデータをただRAMに書き込むだけでは表示されませんから、そこのところのプログラムをPIC16F57にセグメントデータを送るように書き換える必要があります。
下はその部分です。

07CF CDC005   LEDDP0:CALL SEGCG
07D2 E5       LEDDP:PUSH H
07D3 D5         PUSH D
07D4 C5         PUSH B
07D5 21F8FF     LXI H,DIG
07D8 0608       MVI B,08
07DA 0E88       MVI C,88
07DC CDE907   LEDDP2:CALL LEDDPS
07DF 23         INX H
07E0 0C         INR C
07E1 05         DCR B
07E2 C2DC07     JNZ LEDDP2
07E5 C1         POP B
07E6 D1         POP D
07E7 E1         POP H
07E8 C9         RET
              ;
              LEDDPS:;MOV A,C
                ;OUT 8E;adrs set
07E9 7E         MOV A,M
                ;OUT 8F
07EA ED         DB ED;OUT (C),A
07EB 79         DB 79;
07EC 1604       MVI D,04
07EE CDDF06     CALL D1_2;0.5msec wait
07F1 C9         RET
ND80ZモニタプログラムではSEGCG(16進数データをセグメント表示用データに変換してRAMの表示用アドレスに書き込むプログラム)をCALLするだけで済んでいるところを、その後でPIC16F57にセグメントデータを送出するプログラムを追加しています。
実際にPIC16F57に送る部分はLEDDPSで行なっています。
この部分は試作の過程では当初は最初に表示アドレスを8EにOUTし次に表示データを8FにOUTし、それを8桁分繰り返すというプログラムでした。
これはND80KL/86ボードで行なっているやり方です。
その後にZ80の場合にはOUT (C),r命令を使えば回路もプログラムも簡単になることに気が付いたため、上記のプログラムになりました。
ND80ZモニタプログラムはTK80モニタプログラムとの対比から8080アセンブラを使って書いていますので、リストのように命令コードED79を直接書いています。
OUT (C),Aを実行すると、アドレスバスの下位8ビットに表示アドレスが出力され、データバスに表示データが出力されるので、それをEPM7128SLC84でラッチして、それをPIC16F57が読み込むという仕組みです。
0.5msはPIC16F57が7セグメント表示を行ないながら表示データを落とさないよう確実に読み取るためのウェイトです。
PIC16F57は割込みが使えないのでウェイト時間は必要ですが、0.5msは十分な時間です。

●PIC16F57のプログラムリスト(再掲)

ということで、次はPIC16F57のプログラムです。
PIC16F57のプログラムリストは前回お見せしましたが、説明のため再掲します。

 
;;; 7seg LED disp for ND80ZUS/SM
;18/4/9 4/11 4/12 4/13
;from 7seg2j
;
; 16f57
; internal 12MHz
	#include <p16f5x.inc>
        __CONFIG _CP_OFF & _WDT_ON  & _HS_OSC
;
cf=0
zf=2
f=1
w=0
;
ledcntr equ 0a
tcn1 equ 0b
indata equ 0c
tcn0 equ 0d
;
;digit0 to digit7 are 10 to 17
;
     org 00
;
start
        movlw 0;a0-a3 out
        tris PORTA
        bsf PORTA,3
        movlw 1f;b7-b5 out b4-b0 in
        tris PORTB
        bsf PORTB,7;
        movlw 0
        tris PORTC;rc out
;
;start
        movlw 10
        movwf ledcntr
loop
        clrwdt
;leddisp        
        movf ledcntr,w
        movwf PORTA
        movwf FSR
        movf INDF,w
        movwf PORTC
        incf ledcntr,f
        btfss ledcntr,3
        goto t1ms
        movlw 10
        movwf ledcntr
;
        ;1ms wait
t1ms
        movlw 2
        movwf tcn0
t1ms1
        clrf tcn1
t1ms2
        clrwdt;1
        btfss PORTB,4;data ready? 2
        goto dataread;yes
t1ms3
        decfsz tcn1,f;1
        goto t1ms2;2---6/3*256=0.5ms
        decfsz tcn0,f
        goto t1ms1
        goto loop       
;datain
dataread
        bsf PORTB,5;bit4-7 read
        bcf PORTB,6
        bcf PORTB,7;read
        nop
        movf PORTB,w
        movwf indata
        rlf indata,f
        rlf indata,f
        rlf indata,f
        rlf indata,w
        andlw 0f0
        movwf indata
        bcf PORTB,5;bit 0-3 read
        nop
        movf PORTB,w
        andlw 0f
        iorwf indata,f
        bsf PORTB,6
        nop
        movf PORTB,w
        bsf PORTB,7;read end
        andlw 07;
        iorlw 10
        movwf FSR
        movf indata,w
        movwf INDF;---- 22/3=7us
        goto t1ms3
;
     end
;
PIC16F57が表示データを受け取るのはリストの終わりのところ、datareadです。
PICは7セグメントLEDをダイナミックドライブ表示するため、1mSに一度セグメント表示データと表示桁データを出力します。
1mSは命令を繰り返し実行することで作り出しています。
その繰り返しの中で1mSに512回、RB4をチェックしています。
RB4はEPM7128SLC84につながっていて、その端子はEPM7128SLC84がND80ZモニタプログラムからのデータをラッチするとLになります。
RB0〜RB3にはEPM7128SLC84から表示桁0〜7とセグメントデータの上位4ビットと下位4ビットが3回に分けて出力されます。
3回に分けて出力されるデータはPIC16F57がRB5とRB6で指定します。
RB5=0、RB6=0 セグメントデータ下位4ビット
RB5=1、RB6=0 セグメントデータ上位4ビット
RB5=0、RB6=1 表示桁アドレス(0〜7)
RB7=0のときPIC16F57が読取動作中であることを示します。
このようにしたのはPIC16F57の少ないI/O端子で処理を可能にするための工夫です。
理解を助けるために、PIC16F57周りの回路図を再掲します。

●EPM7128SLC84+PIC16F57回路(7SEGMENT表示部分)

回路図の必要部分を再掲します。
今回は7セグメント表示回路部分のみです。
当初はRA3も使うつもりだったのですがRB0〜RB7だけで済んでしまったため、RA3は実際には使っていません。


●カメレオンロジアナの波形

下は上で説明したPIC16F57の動作(実際にはND80ZモニタとEPM7128SLC84の動作も連動しています)をカメレオンロジアナで観測した波形です。

PROBE00はRB7、PROBE01はRB6、PROBE02はRB5、PROBE04はRB4です。
RB4入力がLになるとRB5=H、RB6=Lが出力されるとともにRB7=Lになります。
その後RB5=0、RB6=0になり、続いてRB5=0、RB6=1になったあと、読み取りを終了した印としてRB7=Hになります。
RB4もHになります。
これで1桁分のデータの送受が完了しました。

下はその0.5mS後の波形です。
次の1桁のデータが上と同じように送受されています。


CPLD入門![第39回]
2019.4.28upload

前へ
次へ
ホームページトップへ戻る