Documente Academic
Documente Profesional
Documente Cultură
Referinte Dueck, Robert K., Digital Design with CPLD Applications and VHDL, 2/e
Capitolul 9: Counters and Shift Registers
9.1 Basic Concepts of Digital Counters
9.2 Synchronous Counters
9.3 Design of Synchronous Counters
9.4 Programming Binary Counters in VHDL
9.5 Control Options for Synchronous Counters
9.6 Programming Presettable and Bidirectional Counters in VHDL
1
”Binary coded decimal” - cod in care fiecare cifra individuala a unui numar zecimal este reprezentata de
un numar binar pe 4 biti (exemplu: 905 (zecimal) = 1001 0000 0101 (BCD)).
Notiuni Experimentale
Cerinte
1. Numaratorul BCD
Pasul 1. Scrieti o fisier VHDL pentru numaratorul binar pe 8 biti cu resetare (reset)
asincrona pe front descrescator (active-LOW aynchronous ), incarcare (load) sincrona
pe front crescator, activarea (enable) numaratorului pe front crescator, si directionare
(direction).
Salvati fisierul cu numele ct8bit.vhdl
1. Descrierea aplicaţiei
La fel ca in orice limbaj evoluat de programare proiectarea ierarhizată a
aplicaţiilor in VHDL, prin utilizarea modulelor, permite descrierea proiectului pe mai
multe nivele, îmbunătăţeşte lizibilitatea şi permite reutilizarea unor module.
Un proiect ierarhizat este alcătuit din mai multe module. O aplicaţie poate fi
descrisă la nivelul cel mai de sus (top) printr-o sursă VHDL. În această sursă se definesc
interfeţe corespunzătoare cu alte module situate pe nivele inferioare, module care descriu
părţi componente ale aplicaţiei
Nu există o limită a numărului de nivele ierarhice pe care un proiect poate să-l
conţină. Principalul avantaj al proiectării ierarhizate a unei aplicaţii este acela că
încurajează modularizarea. Alt avantaj este că permite organizarea proiectului pe
nivele corespunzătoare de abstractizare şi detaliu precum si reutilizarea unor
module.
În sursa VHDL de pe nivelul top se vor utiliza cuvintele cheie (instrucţiunile)
component şi PORT MAP pentru a instanţia modulele de pe nivelele inferioare.
Vom ilustra conceptele de ierarhizare, modularizare şi reutilizare cu o aplicaţie
care presupune implementarea unui numărător binar pe 8 biti bidirecţional (poate
număra in sus sau in jos), resetabil (poate fi adus in starea iniţială, starea 0), presetabil
(poate incarca un vector de 8 biti, setand astfel numaratorul cu acest numar). Vectorul de
iesire reprezinta un vector binar pe 8 biti in care primii patru biti reprezinta cifra
unitatilor, iar ultimii 4 cifra zecilor.
Mai intai trebuie implementat un numarator pe 4 biti ce va numara de la 0 la 9
(modulo 10), cu numele count09.vhdl. Acesta va avea toate functionalitatile
numaratorului binar BCD , inclusiv reset asincron pe front descrescator, load sincron pe
front crescator, enable pe front crescator. Mai mult decat atat acesta va returna, pe langa
numarul intre 0 si 9, o valoare pe un bit care va fii 1 atunci cand numaratoarea
crescatoare a ajuns pe pozitia 9 (“1001”) sau numaratoarea descrescatoare a ajuns pe
pozitia 0 (“0000”). Cu ajutorul acestui numarator modulo veti putea realiza un numarator
BCD pe cati digiti doriti.
Atentie! In numele proiectului nu vor fi lasate spatii libere; cuvintele vor fi unite prin
linii sau underline-uri. In caz contrar, programul va ridica o eroare.
Se ajunge la fereastra setarilor proiectului in functie de dispozitivul pentru care va
fi creat. Se va alege:
- produs tinta: Spartan 3;
- simulator: Modelsim-XE VHDL;
- limbaj de programare: VHDL,
apoi se apasa butonul Next.
Sunteti interogati daca doriti crearea unei surse noi pentru proiect. Veti alege
optiunea New Source…, pentru a crea un fisier sursa in cadrul proiectului.
in fereastra aparuta veti selecta:
o tipul fisierului -> se va alege VHDL Module;
o numele fisierului;
o locatia salvarii fisierului
apoi apasati butonul Next.
Atentie! Casuta Add to project trebuie bifata, altfel riscati ca fisierul sa nu fie adaugat in
cadrul proiectului.
Dand Next apare fereastra in care sunt detaliate proprietatile fisierului vhdl;
Apasati Finish si este creat fisierul vhdl in folderul curent al proiectului;
Sariti peste fereastrele de adaugare a unui fisier sursa (considerati fisierul creat
acum ca fiind singurul fisier sursa al proiectului) si de analiza a datelor despre proiect;
Proiectul este creat si, totodata, fisierul sursa vhdl;
Codul sursa propriu-zis va fi scris in zona de architecture;
Forma generala a instructiunilor care pot fi utilizate in cadrul limbajului VHDL
pot fi gasite prin accesarea unor Language Templates, printr-un click pe “beculetul
magic”.
entity count09 is
Port ( clk : in STD_LOGIC;
reset : in STD_LOGIC;
load : in STD_LOGIC;
enable : in STD_LOGIC;
direction : in STD_LOGIC;
carry_in : in STD_LOGIC;
p : in STD_LOGIC_VECTOR (3 downto 0);
carry_out : out STD_LOGIC;
q : out STD_LOGIC_VECTOR (3 downto 0));
end count09;
elsif(direction='0') then
if(count="0000") then
count<="1001";
else
count<=count-1;
end if;
end if;
end if;
end if;
end process;
carry_out<='1' when ((count="0000"and direction='0') or(count ="1001" and direction='1')) else '0';
q<=count;
end Behavioral;
Dupa ce ati scris codul de mai sus in fisierul count09.vhdl trebuie sa verificati
daca aveti erori de sintaxa. Pentru aceasta va duceti in fereastra Sources si selectati
fisierul count09.vhdl, apoi in fereastra Process expandati Synthesize-XST si faceti dublu
click pe Check Syntax. Pentru a vedea daca ati scris corect codul din punct de vedere
sintactic va duceti in fereastra Trancript si selectati Console.
3. Realizarea simularii
pentru Inst_count09_unitati :
clk => CLK,
reset => RESET,
load => LOAD,
enable => ENABLE,
carry_in =>'1',(pentru numaratorul unitatilor
carry_in va fii mereu ‘1’)
direction => DIRECTION,
p => UNITATI_IN,
q =>UNITATI_OUT,
carry_out => carry
pentru Inst_count09_zeci :
clk => CLK,
reset => RESET,
load => LOAD,
enable => ENABLE,
carry_in => CARRY,
direction => DIRECTION,
p => ZECI_IN
q => ZECI_OUT
--carry_out=>(portul carry_out al numaratorului
zecilor nu va fii conectat nicaieri.Acesta ar trebui
conectat la un alt numarator care ar reprezenta
ordinul sutelor).
entity ct2bcd is
Port ( CLK : in STD_LOGIC;
RESET : in STD_LOGIC;
LOAD : in STD_LOGIC;
ENABLE : in STD_LOGIC;
DIRECTION : in STD_LOGIC;
UNITATI_IN : in STD_LOGIC_VECTOR (3 downto 0);
ZECI_IN : in STD_LOGIC_VECTOR (3 downto 0);
UNITATI_OUT : out STD_LOGIC_VECTOR (3 downto 0);
ZECI_OUT : out STD_LOGIC_VECTOR (3 downto 0));
end ct2bcd;
architecture Behavioral of ct2bcd is
COMPONENT count09
PORT(
clk : IN std_logic;
reset : IN std_logic;
load : IN std_logic;
enable : IN std_logic;
carry_in : IN std_logic;
direction : IN std_logic;
p : IN std_logic_vector(3 downto 0);
q : OUT std_logic_vector(3 downto 0);
carry_out : OUT std_logic
);
END COMPONENT;
begin
Inst_count09_unitati: count09 PORT MAP(
clk =>CLK,
reset => RESET,
load => LOAD,
enable => ENABLE,
carry_in =>'1',
direction => DIRECTION,
p => P(3 downto 0),
q => unitati,
carry_out => CARRY
);
Inst_count09_zeci: count09 PORT MAP(
clk => CLK,
reset => RESET,
load => LOAD,
enable => ENABLE,
carry_in => CARRY,
direction => DIRECTION,
p => P(7 downto 4),
q => zeci
--carry_out =>
);
end Behavioral;
entity ct8bit is
Port ( CLK : in STD_LOGIC;
RESET : in STD_LOGIC;
LOAD : in STD_LOGIC;
ENABLE : in STD_LOGIC;
DIRECTION : in STD_LOGIC;
P : in STD_LOGIC_VECTOR (7 downto 0);
Q : out STD_LOGIC_VECTOR (7 downto 0));
end ct8bit;
architecture Behavioral of ct8bit is
signal count: STD_LOGIC_VECTOR (7 downto 0):="00000000";
begin
process(clk,reset)
begin
if(reset'event and reset='0') then
count<="00000000";
elsif(CLK'event and CLK='1') then
if(load='1') then
if(P>"01100011") then
count<="01100011";
else
count<=P;
end if;
elsif(ENABLE='1') then
if(DIRECTION='1') then
if(count="01100011") then
count<="00000000";
else
count<=count+1;
end if;
elsif(DIRECTION='0') then
if(count="00000000") then
count<="01100011";
else
count<=count-1;
end if;
end if;
end if;
end if;
end process;
Q<=count;
end Behavioral;
Se observa ca functia load este sincrona pe front crescator, iar functia reset este
asincrona si active pe front descrescator, avand prioritate fata de load:
Exercitiu:
Folosind cunostintele dobandite in urma parcurgerii acestui laborator,
implementati un multipol logic in VHDL care sa permita afisarea timpului (cronometru
digital) : minute si secunde. Ceasul va avea fuctii de resetare, setarea timpului, activare
(stop/start) si de memorare a timpilor.