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

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



[第40回]


●VHDLプログラムリスト

前回はPIC16F57の7セグメントLED表示プログラムとそれに対応して変更したND80ZSMのND80Zモニタプログラムについて説明をしました。
両者の間にはEPM7128SLC84があってセグメントデータ送受の橋渡しをしています。
もともと当連載の主役はCPLDですから、EPM7128SLC84のVHDLプログラムについて書かないで済ますわけにはいきませんでしょう。
というわけで、今回はそのVHDLプログラムリストです。

--7segx8 and 5x5 key usb interface 19/4/10
-- from ledkey3f
-- 4/11 4/12 4/13 4/15

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
library ARITHMETIC;
use ARITHMETIC.std_logic_arith.all;

entity ledkeyusb1a is
        PORT (
                        KEYOUT:out std_logic_vector(2 downto 0);
                        KEYIN:in std_logic_vector(7 downto 0);
                        AIN:in std_logic_vector(7 downto 0);
                        DINOUT:inout std_logic_vector(7 downto 0);
                        PIC16READ:in std_logic;
                        PIC16AD:in std_logic_vector(1 downto 0);
                        LDATAREADY:out std_logic;
                        LDATAOUT:out std_logic_vector(3 downto 0);
                        PIC18RC:out std_logic_vector(7 downto 0);
                        PIC18RB4:out std_logic;
                        PIC18RB6:out std_logic;
                        USBON:in std_logic;
                        TKND:in std_logic;
                        P25:in std_logic;
                        PIC16RA3:in std_logic;--not used
                        CK12MIN:in std_logic;
                        RESETIN:in std_logic;
                        CK12MOUT:out std_logic;
                        CK12MOUT2:out std_logic;
                        RESETOUT:out std_logic;
                        P21:in std_logic;
                        P52:in std_logic;
                        P65:in std_logic;
                        P67:in std_logic;
                        P69:in std_logic;
                        IOR:in std_logic;
                        IOW:in std_logic);
end ledkeyusb1a;

architecture rtl of ledkeyusb1a is
        signal ldtactiv:std_logic;
        signal readyreset:std_logic;
        signal ldatareadywk:std_logic;
        signal keyoutbf:std_logic_vector(2 downto 0);
        signal keyinbf:std_logic_vector(7 downto 0);
        signal ledadrs:std_logic_vector(2 downto 0);
        signal segment:std_logic_vector(7 downto 0);

begin
        
--ledadrs & segment data set

   process(AIN,IOW)
   begin
        if AIN(7 downto 3)="10001" and IOW='0' then
                ldtactiv<='0';
        else ldtactiv<='1';
        end if;
   end process;
        
   process(ldtactiv)
   begin
        --
        if PIC16READ='0' and PIC16AD="10" then
                ldatareadywk<='1';
        --
        elsif ldtactiv'event and ldtactiv='1' then
                ledadrs<=AIN(2 downto 0);
                segment<=DINOUT;
                ldatareadywk<='0';--
        end if;
   end process;
        
   LDATAREADY<=ldatareadywk;
        
--ledadrs & segment data out

   process(PIC16READ,PIC16AD)
   begin
        if PIC16READ='0' then
        if PIC16AD="00" then
                LDATAOUT<=segment(3 downto 0);
        elsif PIC16AD="01" then 
                LDATAOUT<=segment(7 downto 4);
        elsif PIC16AD="10" then 
                LDATAOUT(2 downto 0)<=ledadrs;
                readyreset<='0';
        else
                LDATAOUT<="1111";
                readyreset<='1';
        end if;
        end if;
   end process;

--key in
   process(AIN,IOW,IOR)
   begin
        if AIN="10011100" and IOW='0' then
                DINOUT<="ZZZZZZZZ";
                if DINOUT(0)='1' then
                        keyoutbf(0)<='Z';
                elsif DINOUT(0)='0' then
                        keyoutbf(0)<='0';
                end if;
                if DINOUT(1)='1' then
                        keyoutbf(1)<='Z';
                elsif DINOUT(1)='0' then
                        keyoutbf(1)<='0';
                end if;
                if DINOUT(2)='1' then
                        keyoutbf(2)<='Z';
                elsif DINOUT(2)='0' then
                        keyoutbf(2)<='0';
                end if;
        elsif AIN="10011100" and IOR='0' then
                keyinbf<=KEYIN;
                DINOUT<=keyinbf;
        elsif AIN="10010100" and IOR='0' then
                DINOUT(7)<=TKND;
        else
                DINOUT<="ZZZZZZZZ";
        end if;
   end process;

        KEYOUT<=keyoutbf;
        CK12MOUT<=CK12MIN;
        CK12MOUT2<=CK12MIN;
        RESETOUT<=RESETIN;
        
end rtl;
ND80ZSMからセグメントデータを受け取ってラッチしているところは、
--ledadrs & segment data set
以下の部分です。
TTL数個分の回路がこれだけの記述で済んでしまいます。
PIC16F57からの要求に応じてセグメントデータと桁表示アドレスを出力しているのは
--ledadrs & segment data out
以下の部分です。
うーん。
どちらもたかだか20行ほどの記述で済んでしまいました。
確かにCPLDは便利だということを実感いたします。

補足ですが。
ALTERAのCPLD用のVHDLプログラムではPIN ASSIGNMENTを指定しません。
ですので上のリストだけでは回路図の端子接続との関係はわかりません。
ALTERAの場合、PIN ASSIGNMENTはPIN PLANNERで指定します([第12回]参照)。
PIN PLANNERで設定すると、QSFファイルにその内容が記述されます。
下がQSFファイルの関係部分のみを取り出したリストです。

set_location_assignment PIN_11 -to AIN[7]
set_location_assignment PIN_15 -to AIN[6]
set_location_assignment PIN_9 -to AIN[5]
set_location_assignment PIN_10 -to AIN[4]
set_location_assignment PIN_6 -to AIN[3]
set_location_assignment PIN_8 -to AIN[2]
set_location_assignment PIN_5 -to AIN[1]
set_location_assignment PIN_4 -to AIN[0]
set_location_assignment PIN_12 -to IOW
set_global_assignment -name MAX7000_DEVICE_IO_STANDARD TTL
set_location_assignment PIN_81 -to DINOUT[7]
set_location_assignment PIN_80 -to DINOUT[6]
set_location_assignment PIN_79 -to DINOUT[5]
set_location_assignment PIN_77 -to DINOUT[4]
set_location_assignment PIN_76 -to DINOUT[3]
set_location_assignment PIN_75 -to DINOUT[2]
set_location_assignment PIN_73 -to DINOUT[1]
set_location_assignment PIN_74 -to DINOUT[0]
set_location_assignment PIN_16 -to IOR
set_location_assignment PIN_51 -to KEYIN[7]
set_location_assignment PIN_50 -to KEYIN[6]
set_location_assignment PIN_49 -to KEYIN[5]
set_location_assignment PIN_48 -to KEYIN[4]
set_location_assignment PIN_46 -to KEYIN[3]
set_location_assignment PIN_45 -to KEYIN[2]
set_location_assignment PIN_44 -to KEYIN[1]
set_location_assignment PIN_41 -to KEYIN[0]
set_location_assignment PIN_40 -to KEYOUT[2]
set_location_assignment PIN_39 -to KEYOUT[1]
set_location_assignment PIN_37 -to KEYOUT[0]
set_location_assignment PIN_57 -to LDATAOUT[3]
set_location_assignment PIN_58 -to LDATAOUT[2]
set_location_assignment PIN_60 -to LDATAOUT[1]
set_location_assignment PIN_63 -to LDATAOUT[0]
set_location_assignment PIN_70 -to RESETIN
set_location_assignment PIN_83 -to CK12MIN
set_location_assignment PIN_22 -to RESETOUT
set_location_assignment PIN_68 -to CK12MOUT
set_location_assignment PIN_20 -to CK12MOUT2
set_location_assignment PIN_25 -to P25
set_location_assignment PIN_34 -to PIC18RB4
set_location_assignment PIN_36 -to PIC18RB6
set_location_assignment PIN_33 -to PIC18RC[7]
set_location_assignment PIN_35 -to PIC18RC[6]
set_location_assignment PIN_24 -to PIC18RC[5]
set_location_assignment PIN_27 -to PIC18RC[4]
set_location_assignment PIN_28 -to PIC18RC[3]
set_location_assignment PIN_31 -to PIC18RC[2]
set_location_assignment PIN_30 -to PIC18RC[1]
set_location_assignment PIN_29 -to PIC18RC[0]
set_location_assignment PIN_18 -to TKND
set_location_assignment PIN_17 -to USBON
set_location_assignment PIN_21 -to P21
set_location_assignment PIN_65 -to P65
set_location_assignment PIN_67 -to P67
set_location_assignment PIN_69 -to P69
set_location_assignment PIN_52 -to P52
set_location_assignment PIN_61 -to PIC16READ
set_location_assignment PIN_54 -to PIC16AD[0]
set_location_assignment PIN_56 -to PIC16AD[1]
set_location_assignment PIN_55 -to LDATAREADY
set_location_assignment PIN_64 -to PIC16RA3

CPLD入門![第40回]
2019.4.29upload

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