?? ms32pci.vhd
字號:
--===================================================================--
--
-- www.OpenCores.Org - June 2000
-- This model adheres to the GNU public license
--
-- Design units : Master device for PCI Local Bus 33 MHz 32 bits
-- (BoardLevel Simulation model)
-- (Entity and architecture)
--
-- File name : MS32PCI.vhd
--
-- Purpose : The Master device is used to simulate a master
-- device on the PCI-Bus
--
-- Note : This model is modelled after the PCI protocol
-- as described in Xilinx & Altera AppNotes
--
-- Limitations : None known
--
-- Errors : None known
--
-- Library : PCI_Lib.vhd
--
-- Dependencies : IEEE.Std_Logic_1164
--
-- Author : Ovidiu Lupas
-- olupas@opencores.org
--
-- Simulator : ModelSim EE version 5.2 on a Windows95 PC
-- ActiveVHDL 3.1 on a Windows95 PC
--===================================================================--
library ieee,work;
use ieee.Std_Logic_1164.all;
use work.Simulation.all;
use std.textio.all;
use work.PCI_Def.all;
-----------------------------------------------------------------------
-- ENTITY FOR MASTER PCI SIMULATION MODEL --
-----------------------------------------------------------------------
entity MS32PCI is
generic (
cmd_file : string := "PCI.CMD"; -- the commands file
tdelay : Time := 2 ns; -- delay time parameter
tsetup : Time := 7 ns; -- setup time to be checked
thold : Time := 0 ns); -- hold time to be checked
port (
-- Address, Data and Command buses (37)
AD_Bus : inout STD_LOGIC_VECTOR (31 downto 0);
C_BE_Bus : inout STD_LOGIC_VECTOR (3 downto 0);
PAR : inout STD_LOGIC;
-- Interface control signals (6)
FRAME_N : inout STD_LOGIC;
TRDY_N : in STD_LOGIC;
IRDY_N : inout STD_LOGIC;
STOP_N : in STD_LOGIC;
DEVSEL_N : in STD_LOGIC;
IDSEL : in STD_LOGIC;
-- Error reporting signals (2)
PERR_N : inout STD_LOGIC;
SERR_N : inout STD_LOGIC;
-- Arbitration signals (2)
REQ_N : out STD_LOGIC;
GNT_N : in STD_LOGIC;
-- System signals (2)
CLK : in STD_LOGIC;
RST_N : in STD_LOGIC);
end MS32PCI;--================== End of entity ======================--
-----------------------------------------------------------------------
-- Architecture for Master device : PCI bus 33MHZ 32 bit configuration
-----------------------------------------------------------------------
architecture Behavior of MS32PCI is
---------------------------------------------------------------------
-- Signals
---------------------------------------------------------------------
signal parity_now : Std_Logic; -- internal variable (calculate parity)
signal parity_read : Std_Logic; -- internal variable (parity at read)
signal parity_flag : Boolean; -- internal variable (write ON/OFF on line PERR_N)
signal PAR_READ_TEMP : Std_Logic; -- insert or no signal IRDY_N
signal PAR_READ_FLAG : Std_Logic; -- insert or no signal IRDY_N
---------------------------------------------------------------------
-- Variables
---------------------------------------------------------------------
shared variable RESET : Integer;
begin --======================= Architecture ========================--
---------------------------------------------------------------------
-- Process is used to initialize command
---------------------------------------------------------------------
RSTproc : process(RST_N)
begin
if not RST_N'STABLE and RST_N ='0' then
RESET := 1;
end if;
end process;
---------------------------------------------------------------------
-- Implements the parity generation and parity checking over the
-- AD bus and C/BE bus.
-- Also, generates the PERR_N signal, if the computed parity is not
-- equal with PAR signal, when PAR signal is generated by target
---------------------------------------------------------------------
ParGen : process(CLK)
variable PERR_N_TEMP : Std_Logic;
begin
if not CLK'STABLE and CLK = '0' then
PAR <= parity_now after tdelay; -- PAR ='1','0' or 'Z'
PERR_N <= PERR_N_TEMP after tdelay ;
SERR_N <= PERR_N_TEMP ;
PAR_READ_TEMP <= parity_read ;
if parity_flag = true then
PAR_READ_FLAG <= '1';
else
PAR_READ_FLAG <= '0';
end if;
if PAR_READ_FLAG = '1' then --
if (PAR = PAR_READ_TEMP) then -- MASTER sets PERR_N
PERR_N <= '1' after tdelay;
else
if PAR_READ_TEMP = 'Z' then
PERR_N <= 'H' after tdelay;
else
PERR_N <= '0' after tdelay;
end if;
end if;
else
PERR_N <= 'H' after tdelay;
end if;
end if;
end process;
---------------------------------------------------------------------
-- MAIN PROCESS FOR MASTER --
---------------------------------------------------------------------
MS32PCI_MAIN : process
variable Data_array : Data_buffer; -- data array
variable data_last_read : Boolean;
variable irdy_start : Integer; -- variable is actualize
variable irdy_loop : Integer;
variable irdy_nr : Integer; -- by command WAITC
variable irdy_insert : Boolean; -- assert or not IRDY_N
------------------------------------------------------------------
-- Procedure is used to initialize MASTER and irdy_** variables --
------------------------------------------------------------------
procedure Init is
begin
RESET := 0;
AD_Bus <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ" ; -- Address and Data Bus
C_BE_Bus <= "ZZZZ"; -- Command Bus
PAR <= 'Z';
PERR_N <= 'Z';
REQ_N <= 'H';
SERR_N <= 'H';
irdy_start := 0; -- number of IRDY state
irdy_nr := 0;
irdy_loop := 255;
parity_flag <= false;
if irdy_loop = 0 or irdy_nr = 0 then
irdy_insert := false;
else
irdy_insert := true;
end if;
end Init;
------------------------------------------------------------------
-- This procedure calculate parity of signals address_data(31..0)
-- and c_be(3..0) and return par_bit
------------------------------------------------------------------
procedure PARITY(
address_data : in STD_LOGIC_VECTOR(31 downto 0);
c_be : in STD_LOGIC_VECTOR(3 downto 0);
par_bit : inout STD_LOGIC) is
begin
par_bit := '0';
for I in 0 to 31 loop
par_bit := par_bit xor address_data(I);
end loop;
for I in 0 to 3 loop
par_bit := par_bit xor c_be(I);
end loop;
if (par_bit = 'X' or par_bit = 'U') then
par_bit := 'Z';
end if;
end PARITY;
--------------------------------------------------------------------------
-- This procedure is used for READ_Bus and WRITE_Bus operation --
--------------------------------------------------------------------------
procedure READ_WRITE(
address : in STD_LOGIC_VECTOR(31 downto 0); -- address
data : in Data_buffer; -- data to write operation
data_nr : in Integer; -- number of data DWORD(32 bit)
bus_cmd : in STD_LOGIC_VECTOR(3 downto 0); -- bus command
bus_sel : in Data_Enable; -- C/BE lines
rd_wr : in STD_LOGIC) is -- select read or write operation
variable data_number : Integer; -- number of data to read and write
variable data_read : Std_Logic_Vector(31 downto 0); -- data read
variable data_old : Std_Logic_Vector(31 downto 0); -- data read old
variable stop : Boolean; -- internal variable (determined by STOP_N)
variable str8 : string(1 to 8);
variable Good2 : Boolean;
variable nr_irdy : Integer; -- duration of IRDY pulse
variable loop_irdy : Integer; -- position of IRDY pulse
variable start_irdy : Integer; -- used for master-abord termination
variable parity_temp : Std_Logic; -- internal variable
variable trdy_stop : Integer; -- internal variable
variable trdy_exit : Boolean; -- internal variable
begin
if GNT_N /= '1' then
wait until FALLING_EDGE(CLK); -- start cycle
end if;
while (GNT_N /= '0' and GNT_N /= 'L') and (RESET = 0) loop
wait until FALLING_EDGE(CLK);
AD_Bus(31 downto 0) <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ" after tdelay;
C_BE_Bus(3 downto 0) <= "ZZZZ" after tdelay;
FRAME_N <= 'Z';-- after tdelay;
IRDY_N <= 'Z' after tdelay;
parity_now <= 'Z' after tdelay;
REQ_N <= '0' after tdelay;
end loop;
if (RESET = 0) then
-- exit curent instruction if signal RST_N is active
-- GM
--- acces to the bus has been granted
data_number := data_nr; -- number of DWORDs for transfer
stop := false; --
start_irdy := 3; --
nr_irdy := irdy_nr; -- actualize internal variable
loop_irdy := irdy_loop; -- --"--
irdy_insert := true; -- --"--
trdy_stop := 8; -- wait maximum 8 clock cycles for TRDY
trdy_exit := false;
if rd_wr = '1' then -- READ /WRITE CYCLE
--------------------------------------------------------------------
-- BEGIN READ CYCLE --
--------------------------------------------------------------------
-- address phase
AD_Bus(31 downto 0) <= address(31 downto 0) after tdelay; -- set address
C_BE_Bus(3 downto 0) <= bus_cmd(3 downto 0) after tdelay; -- set command
FRAME_N <= '0';-- after tdelay;
IRDY_N <= '1' after tdelay;
parity_flag <= false;
parity_read <= 'Z' after tdelay;
-- calculate parity of address cycle
parity(address(31 downto 0), bus_cmd(3 downto 0), parity_temp);
parity_now <= parity_temp;
if GNT_N'Last_Event <= tsetup then -- GNT setup time violation ?
report "GNT setup time violation"
severity Warning;
end if;
wait until FALLING_EDGE(CLK); -- make turnarround cycle
-- GM
REQ_N <= '1';
-- END GM
IRDY_N <= '0' after tdelay;
AD_Bus(31 downto 0) <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ" after tdelay;
C_BE_Bus(3 downto 0) <= bus_sel(1) after tdelay;
parity_now <= 'Z';
wait until FALLING_EDGE(CLK); -- end turnarround cycle
-- wait for DEVSEL_N = '0'
-- (implement MASTER-ABORT if TARGET is not responding)
-- wait for the number of IRDY state
while ((start_irdy > 0) and (DEVSEL_N = '1' or DEVSEL_N = 'H' or
DEVSEL_N = 'Z' or DEVSEL_N = 'X') ) loop
start_irdy := start_irdy -1; -- from the begining of read cycle
AD_Bus(31 downto 0) <="ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ" after tdelay;
C_BE_Bus(3 downto 0) <= bus_sel(1) after tdelay;
wait until FALLING_EDGE(CLK);
end loop;
--- exit cycle if RST_N or STOP_N are active
if RESET =1 or STOP_N = '0' or STOP_N ='L' then
stop := true; -- exit cycle
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -