Grunder i VHDL
Innehåll
Komponentmodell
Kodmodell
Entitet
Arkitektur
Identifierare och objekt
Operationer för relationer
Parallellitet i VHDL
VHDL simulatorn
Komponentmodell
Modell för att beskriva komponenter
Externt gränssnitt
Intern funktion
A B C
X Y
Portar: externa anslutningar till komponenten
Komponentens - Beteende eller - Struktur
VHDL-komponent
Funktion: ett antal parallella processer
VHDL-komponent
Kodmodell
Funktion - arkitektur Gränssnitt (interface) - entitet med portar
Deklaration av entitet
Deklaration av arkitektur
Deklarera VHDL-komponentens gränssnitt
entity mux2 is port (
a: in STD_LOGIC;
b: in STD_LOGIC;
sel: in STD_LOGIC;
y: out STD_LOGIC;
);
end mux2;
MUX 2-1
y
sel a
b
VHDL-komponentens portar
entity mux2 is port (
a: in STD_LOGIC;
b: in STD_LOGIC;
sel: in STD_LOGIC;
y: out STD_LOGIC;
);
end mux2;
port definierar ingångar och utgångar
in/out definierar portens mode
Bestämmer riktningen på dataflödet
std_logic är datatypen för
in- och utsignalerna
Portar i VHDL
Port-deklarationerna är det viktigaste i entitets-deklarationen
Varje port representerar
Komponentens externa pinnar
Varje port har
Port-namn
Mode
Datatyp
En identifierare som du skapar
Riktning på data
Vilka värden porten kan anta
Portarnas olika moder
IN
OUT
BUFFER
INOUT
Signalen går enbart in till komponenten och drivs av någon annan komponent.
Insignalen används på höger sida av en tilldelning:
z <= a OR inport
Signalen går enbart ut från komponenten.
Det går ej att läsa utsignalens värde i komponenten
används på vänster sida i tilldelning: outport <= a OR b
Signalen går enbart ut från komponenten.
Det går att läsa utsignalens värde i komponenten Används på båda sidorna i tilldelning:
buffer_port <= a OR b;
z <= buffer_port OR c;
Signalen kan gå i båda riktningarna, antingen in eller ut -signalens värde kan läsas av komponenten
-Signalen kan också drivas av andra komponenter
I arkitekturen beskrivs funktionen:
Om sel är 0 så läggs värdet på insignalen a ut på utsignalen y.
I annat fall (sel=1) så läggs insignalen b ut på y.
Beskrivning av funktionen i arkitekturen
architecture mux2_arch of mux2 is begin
mux2_1: process(a, b, sel) begin
if sel = '0' then y <= a;
else
y <= b;
end if;
end process mux2_1;
MUX 2-1
y
sel a
b
begin … end för arkitekturen
begin … end för processen
Sekventiella satser (if-then-else) i processen Process
Med sensitivitetslista Namnet på entiteten Namnet på arkitekturen
Arkitektur-deklaration
architecture mux2_arch of mux2 is begin
mux2_1: process(a, b, sel) begin
if sel = '0' then y <= a;
else
y <= b;
end if;
end process mux2_1;
end mux2_arch;
Struktur för arkitekturen
architecture name_arch of name is begin
end name_arch;
Deklaration av signaler
Parallella satser Process 1
Parallella satser Process 2
Parallella satser
Processer och parallella satser exekveras parallellt
Inom en process sker exekveringen sekventiellt (sekventiella satser)
Signaler används för att
kommunicera mellan processer och mellan komponenter samt i parallella satser.
Signaler kan bara deklareras på arkitektur-nivå (ej i processer)
Parallella processer
Exempel på parallella och sekventiella satser
ENTITY ename IS
Ports( a, b, c: IN bit;
y, z, w: OUT bit;
Deklarationer -- inga variabler tillåtna END ename
ARCHITECTURE first OF ename IS
Deklarationer -- inga variabler, men signaler är OK BEGIN
y <= a AND b;
PROCESS (a,b,c)
Deklarationer -- inga signaler, men signaler är OK VARIABLE v: bit;
BEGIN
v1 := (a OR b);
v := v1 AND c;
w <= a XOR v;
END PROCESS;
z <= c XOR b;
END first;
Satserna i processen sker sekventiellt
Identifierare i VHDL
Identifierare
Är namn på saker DU skapar
T.ex. namn på arkitektur, entity, process, variabel, signal
Regler för namn
Får ej vara ett reserverat ord i VHDL (t.ex for och if)
Stora och små bokstäver tolkas lika (case-insensitive)
Första tecknet måste vara en bokstav
Sista tecknet får ej vara underscore (_)
Det får inte finnas två underscore efter varandra (__)
Dataobjekt i VHDL
Objekt är saker som kan hålla ett värde
Objekten har klass och typ (class, type)
Class bestämmer vilka slags operationer man kan göra
Type bestämmer vilka värden som är giltiga
De kan tilldelas ett startvärde (endast för simulering)
De deklareras i entity, architecture, process, eller
package
Klasser i VHDL
Signal
Dess värde ändras som funktion av tiden
Den har en signaldrivare och kan ses som en fysisk ledning
Variable
Dess värde ändras omedelbart vid tilldelning
Inga tidsbegrepp finns relaterade till den
Constant
Dess värde kan inte ändras
File
Värde från extern fil kan skrivas och läsas
Datatyper i VHDL
VHDL har hårda krav på datatyper
Objekt av olika grundtyper kan inte tilldelas varandra direkt
Vid typkonvertering ska konverteringsfunktioner användas
Två huvudkategorier av datatyper
Skalärer (scalar)
Kan anta ett enda värde
Exempel: enumeration, integer, float, physical
Sammansatta (composite)
Kan anta flera värden
Exempel: array, record
Skalärer
Enumeration (uppräkningsbara)
En lista med distinkta värden en variabel kan anta
Ex: type weekday = (mon, tue, wed, thu, fri, sat, sun);
Integer
En mängd heltal – positiva och negativa
En fördefinierad datatyp
Integer är av 32-bitar med tecken –(2 31 -1 till +(2 31 -1)
Ett begränsat område används vid beskrivning av hårdvara
Ex: variable num: integer range –64 to 64
Skalärer
Flyttal
Datatypen för flyttal är den fördefinierade typen real
32-bitars enkel precision
Används inte för hårdvarubeskrivningar
Resulterar i för komplex hårdvara
Physical
Datatyp för fysikaliska storheter
Ex. time, mA, Volt
Har ingen betydelse vid beskrivning av hårdvara
Exempel på uppräkningsbara datatyper
Fördefinierade datatyper (1076)
type boolean is (FALSE, TRUE);
type bit is (’0’,’1’);
Fördefinierade datatyper (1164)
Std_logic
Std_ulogic
Samt arrayer av dessa och dess under-typer
Tillgång till dessa får genom att inkludera biblioteket:
LIBRARY ieee;
Skrivs först i VHDL-programkoden för att inkludera biblioteket
Std_logic
library IEEE;
use IEEE.std_logic_1164.all;
type std_ulogic is ( ‘U’, -- Uninitialized
‘X’ -- Forcing unknown
‘0’ -- Forcing zero
‘1’ -- Forcing one
‘Z’ -- High impedance
‘W’ -- Weak unknown
‘L’ -- Weak zero
‘H’ -- Weak one
‘-’);-- Don’t care
subtype std_logic is resolved std_ulogic;
Definition av std_logic
Sammansatta datatyper
Arrayer
Exempel på deklaration av en bit-vektor om 8 bitar
signal s1: bit_vector(7 downto 0);
variable v1: bit_vector(7 downto 0);
Tilldela bit-vektor det binära talet 11010010
s1 <= ”11010010”;
v1 := ”11010010”;
Tolkas som den mest signifikanta biten Tolkas som den minst signifikanta biten
Operationer som stöds av syntesverktyg
Operationer i VHDL
Relationsoperatorer Aritmetiska operationer
Symbol Operation
= likhet /= olikhet
< Mindre än
> Större än
<= Mindre än eller lika
>= Större än eller lika
Symbol Operation + addidion
- subtraktion
* multiplikation / division
abs absolutvärde rem rest
mod modulus
** exponent
Parallellitet i VHDL
architecture name_arch of name is
begin
end name_arch;
Deklaration av signaler Process 1
Process 2 Process 3 Process 4
Parallella satser
ALU
minne register
K on tr ol le nh et
Varje hårdvarumodul körs parallellt med de andra, därför måste
Stimuli till kretsen (indata)
Respons från kretsen (utdata)
Simulering av VHDL program
010 … 11 011 … 00
011 … 10
000 … 01 110 … 11
111 … 11
VHDL simulator
VHDL beskrivning av den digitala konstruktionen
För varje invektor svarar den med en utvektor
Simulering av sekventiella händelser
Simuleringstid
Är den tid kretsen har simulerats (ej verklig tid)
Delta-fördröjning
Används internt i simulatorn för att köa sekventiella händelser
Om man lägger till ett antal delta-fördröjningar till simuleringstiden så blir simuleringstiden
densamma
Simuleringscykeln för VHDL simulatorn
Starta
simulering Starta
simulering
Uppdatera signaler
Uppdatera
signaler Exekvera
processer Exekvera processer
Avsluta
simulering Avsluta
simulering respons
stimuli
Driv signalvärden som är schemalagda i aktuell simuleringstid
Schemalägg förändringar av signaler i framtida simuleringstid
Endast processer vars insignaler andras aktiveras
Inga nya händelser gör
att simuleringen stannar
Schemaläggning av signaler
Exempel #1, ”inga fördröjningar anges i koden”
Tid a, b, x Drivare (av utgången x) Kommentarer
0ns 1, 0, 0 (0, 0ns) (0, 0ns+) p2 körs p.g.a initiering
0ns + 1, 0, 0 (0, 0ns+)
10ns+ 1, 1, 1 (1,10 ns + )
p2: process(a, b) begin
x <= a and b;
end process p2; x
b a
Vid t=0 antar vi att:
a = ’1’; b = ’0’; x = ’0’
vid t=10 blir sätts b=’1’
10ns 1, 1, 0 (1,10 ns + ) p2 körs p.g.a att b ändras
X är alltid ’0’ i for-loopen X <= a(i) and ’0’ x = ’0’
Ex: VHDL kod för 3-ing. AND
Exempel #4, ”en 3-ingångars AND-grind”
x = a(2)• a(1)• a(0)
and3: process(a) begin
x <= ’1’;
for i in 2 downto 0 loop x <= a(i) and x;
end loop;
end process p3;
0ns + 1,1,1,0 (0, 0ns+)
Tid a2,a1,a0,x Drivare (av utgången x) Kommentarer 0ns 1,1,1,0 (0,0ns) (1,0ns+) (0,0ns+ )
(0,0ns+ ) (0,0ns+ )
and3 körs p.g.a initiering
Det nya värdet för x schemaläggs till en tidpunkt efter for-loopen har körts
Signaltilledelningar ger upphov till parallella händelser
Ordningen på signaltilldelningar i koden spelar ingen roll
Det fungerar inte!!
Genom att använda variabler blir koden sekventiell där ordningen
på satserna spelar roll
Ex: VHDL kod för 3-ing. AND
”en 3-ingångars AND” – använd variabler
and3: process(a)
variable temp: bit;
begin
temp := ’1’;
for i in 2 downto 0 loop tmp := a(i) and temp;
end loop;
end process p3;
Variabeltilldelning sker direkt utan att schemaläggas i framtiden
Det fungerar!!
Variabler kan endast användas i processer
Processer
En process är ett sekventiellt program
Flera processer i en arkitektur exekveras parallellt
Kommunikation mellan processer sker med signaler
Syntax:
[<process_namn>:] process [(sensitivitetslista>)]
[<deklarationer i processen>]
begin
<sekventiella satser>
end process [<process namn>];
Aktiveras om a, b eller c ändrar värde
Aktivering av processer
Aktiv/exekverande
Väntande
Processen aktiveras då:
-signal i sensitivitetslistan ändras
-Signal i wait-satsen ändras
Processen passiveras då:
-end process nås i koden -wait-sats nås i koden
process(a, b, cin) begin
s <= a xor b xor cin;
end process;
process begin
s <= a xor b xor cin; Går i väntande läge
Sekventiella satser
Sekventiella satser finns endast inne i processer
För sekventiella satser gäller
Att deras inbördes ordning i koden spelar roll
Att de exekveras i noll simuleringstid
Att de har absolut inget att göra med sekventiell logik eller tillståndsmaskiner
De sekventiella satserna är
IF-THEN-ELSE
CASE-WHEN
IF-THEN-ELSE
Exekverar första sektionen med satser som följer ett sant villkor
Ingen annan sektion exekveras
label: -- ej nödvändigt if villkor1 then
sats1;
elsif villkor2 then -- ej nödvändig sektion sats2;
else -- ej nödvändig sektion sats3;
end if;
f = xa + x’yb + x’y’zc + x’y’z’d
Logiskt uttryck med IF-THEN …
En serie villkor bildar ett logiskt uttryck
process (x, y, z, a, b) begin
if x = ’1’ then f <= a;
elsif y = ’1’ then f <= b;
elsif z = ’1’ then f <= c;
else
f <= d;
end if;
end process;
Logiskt uttryck med IF-THEN …
Exempel:
process (xbus) begin
if xbus = "111"
then
doitnow <= ’1’;
else
doitnow <= ’0’;
end if;
end process;
Felaktig användning av IF-THEN …
Exempel:
process (xbus) begin
if xbus = "111" then
doitnow <= ’1’; -- en latch kommer att föras in end if;
end process;
D Q
G
D-LATCH
doitnow
Xbus(2) Xbus(1) Xbus(0)
Det finns inget i koden som säger att Utgången ska gå till ’0’
CASE-WHEN satsen
Exekverar endast en sektion som följs av ett giltigt val eller det som följer efter OTHERS
Valen måste vara ömsesidigt uteslutande
Samtliga möjliga val måste anges
Resulterar i en multiplexer-baserad struktur
label:
case selector_expression is when val1 => sats1;
when val2 => sats2;
when val3 => sats3;
when OTHERS => sats4;
end case;
CASE-WHEN – exempel
2:1 Multiplexer
case sel is
when ’0’ => z <= a;
when ’1’ => z <= b;
end case;
a b
sel z 2:1 MUX
Parallella satser
Parallella satser finns på arkitekturnivå
För parallella satser gäller
Att deras inbördes ordning i koden spelar ingen roll
Att resultatet av den schemaläggs som en händelse framtida simuleringstid
De parallella satserna är
With-select-when