VHDL 2019 Example
The following code illustrates the use of records and views. There are 4 files, top.vhd, interface.vhd, source.vhd, and sink.vhd.
The top module is defined as:
-- top.vhd top-module
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.interfaces.all; -- USING PACKAGE HERE!
entity top is
port(clk, rst : in std_logic; data_1_in : in std_logic_vector(3 downto 0);
data_2_in : in std_logic_vector(7 downto 0);
data_1_out : out std_logic_vector(3 downto 0);
data_2_out : out std_logic_vector(7 downto 0););
end;
architecture top_a of top is
signal bus_signal : streaming_bus;
begin
producer : entity work.source port map(clk, rst, data_1_in, data_2_in, bus_signal);
consumer : entity work.sink port map(clk, rst, data_1_out, data_2_out, bus_signal);
end;
interface.vhd defines the streaming_master and
streaming_slave interfaces.
-- interface.vhd
-- Define the streaming_master and streaming_slave interfaces
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
package interfaces is
-- record definition
type streaming_bus is record
data_1 : std_logic_vector(3 downto 0);
data_2 : std_logic_vector(7 downto 0);
end record;
-- Create an interface for the record streaming_bus in the streaming_master mode view
view streaming_master of streaming_bus is
data_1, data_2 : out;
end view;
-- Create an interface for the record streaming_bus in the streaming_master mode view
alias streaming_slave is streaming_master'converse;
end;
source receives input data from the top module and sends it to
sink using the streaming_master interface defined
in interface.vhd.
-- source.vhd
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.interfaces.all; -- USING PACKAGE HERE!
-- source uses "master_interface" as the streaming_master interface
entity source is
-- short form
port(clk, rst : in std_logic;
data_1 : in std_logic_vector(3 downto 0);
data_2 : in std_logic_vector(7 downto 0);
master_interface : view streaming_master);
end;
architecture source_a of source is
signal data_1_net : std_logic_vector(3 downto 0) := (others => '0');
signal data_2_net : std_logic_vector(7 downto 0) := (others => '0');
begin
process(clk,rst)
begin
if rising_edge(clk) then
if rst='1' then -- synchronous reset
data_1_net <= (others => '0');
data_2_net <= (others => '0');
else
data_1_net <= data_1;
data_2_net <= data_2;
end if;
master_interface.data_1 <= data_1_net;
master_interface.data_2 <= data_2_net;
end if;
end process;
end;
sink receives data from source through the
streaming_slave interface defined in
interface.vhd.
-- sink.vhd
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.interfaces.all; -- USING PACKAGE HERE!
entity sink is
port(clk, rst : in std_logic; data_1 : out std_logic_vector(3 downto 0);
data_2 : out std_logic_vector(7 downto 0);
slave_interface: view streaming_slave);
end;
architecture sink_a of sink is
signal data_1_net : std_logic_vector(3 downto 0) := (others => '0');
signal data_2_net : std_logic_vector(7 downto 0) := (others => '0');
begin
process(clk,rst)
begin
if rising_edge(clk) then
if rst='1' then -- synchronous reset
data_1_net <= (others => '0');
data_2_net <= (others => '0');
else
-- processor receives data_1 and data_2 signal from source and
-- inverts it before sending to sink
data_1_net <= not slave_interface.data_1;
data_2_net <= not slave_interface.data_2;
end if;
data_1 <= data_1_net;
data_2 <= data_2_net;
end if;
end process;
end;