URL
https://opencores.org/ocsvn/pci_core/pci_core/trunk
Subversion Repositories pci_core
Compare Revisions
- This comparison shows the changes necessary to convert path
/
- from Rev 9 to Rev 10
- ↔ Reverse comparison
Rev 9 → Rev 10
/tags/alpha/vhdl_behav/Ms32pci.vhd
File deleted
/tags/alpha/vhdl_behav/Pci_lib.vhd
File deleted
/tags/alpha/vhdl_behav/Test_pci.vhd
File deleted
/tags/alpha/vhdl_behav/Tg32pci.vhd
File deleted
/tags/alpha/vhdl_behav/PCI.CMD
File deleted
tags/alpha/vhdl_behav/PCI.CMD
Property changes :
Deleted: svn:executable
## -1 +0,0 ##
-*
\ No newline at end of property
Index: tags/first/diagrams/pci.dia
===================================================================
--- tags/first/diagrams/pci.dia (revision 9)
+++ tags/first/diagrams/pci.dia (nonexistent)
@@ -1,64 +0,0 @@
-VGUIformatVersion 1.004000
-
-
-
-
-DEFINE_MODULE: new_unnamed_submodule0
-
- DEFINE_DEVICE_INSTANCES:
- END_DEFINE_DEVICE_INSTANCES.
-
- DEFINE_TOPOLOGY:
- END_DEFINE_TOPOLOGY.
-
-
-END_DEFINE_MODULE.
-
-
-
-DEFINE_MODULE: pci_controller
-
- PORT_LIST( RST_n, CLK, DEVSEL_n, STOP, FRAME_n, TRDY_n,
- IRDY_n, IDSEL, CBE, AD, SERR_n, PERR_n,
- PAR );
-
- DEFINE_DEVICE_INSTANCES:
- trget_machine = Target_machine | 5.600000 4.400000 6.900000 7.300000
- Parity = Parity | 5.600000 2.300000 6.800000 4.200000
- END_DEFINE_DEVICE_INSTANCES.
-
- DEFINE_TOPOLOGY:
- Parity parity_PAR pci_controller PAR half-duplex 0 Std_logic L0 3.500000 2.500000 5.600000 2.500000
- Parity PERR_par_n pci_controller PERR_n half-duplex 0 Std_logic L1 3.500000 2.700000 5.600000 2.700000
- Parity SERR_par_n pci_controller SERR_n half-duplex 0 Std_logic L2 3.500000 2.900000 5.600000 2.900000
- trget_machine AD_trgt Parity AD_trgt simplex 0 Std_logic_vector(31#downto#0) AD 5.600000 3.300000 4.300000 3.300000 4.300000 5.500000 5.600000 5.500000
- pci_controller AD trget_machine AD_trgt half-duplex 0 Std_logic_vector(31#downto#0) AD 5.600000 5.500000 5.300000 5.500000 3.600000 5.500000
- trget_machine CBE_trgt_n Parity CBE_trgt_n simplex 0 Std_logic_vector(3#downto#0) CBE 5.600000 3.700000 4.500000 3.700000 4.500000 5.700000 5.600000 5.700000
- pci_controller CBE trget_machine CBE_trgt_n half-duplex 0 Std_logic_vector(3#downto#0) CBE 5.600000 5.700000 3.600000 5.700000
- pci_controller IDSEL trget_machine IDSEL_trgt simplex 0 Std_logic L7 5.600000 6.000000 3.600000 6.000000
- pci_controller IRDY_n trget_machine IRDY_trgt_n simplex 0 Std_logic L8 5.600000 6.200000 3.600000 6.200000
- trget_machine TRDY_trgt_n pci_controller TRDY_n simplex 0 Std_logic L9 3.600000 6.400000 5.600000 6.400000
- pci_controller FRAME_n trget_machine FRAME_trgt_n simplex 0 Std_logic L10 5.600000 6.600000 3.600000 6.600000
- trget_machine STOP_trgt_n pci_controller STOP simplex 0 Std_logic L11 3.600000 6.800000 5.600000 6.800000
- trget_machine DEVSEL_trgt_n pci_controller DEVSEL_n half-duplex 0 Std_logic L12 3.600000 7.000000 5.600000 7.000000
- pci_controller CLK trget_machine CLK simplex 0 Std_logic CLK 5.600000 4.600000 3.700000 4.600000
- trget_machine CLK Parity CLK simplex 0 Std_logic CLK 5.600000 4.100000 4.800000 4.100000 4.800000 4.600000 5.600000 4.600000
- pci_controller RST_n trget_machine RST_n simplex 0 Std_logic RST_n 5.600000 5.000000 3.700000 5.000000
- trget_machine RST_n Parity RST_n simplex 0 Std_logic RST_n 5.600000 3.900000 4.700000 3.900000 4.700000 5.000000 5.600000 5.000000
- trget_machine ADDR_trgt DEV_NULL simplex 0 Std_logic_vector(LOCALADD#-#1#downto#0) L17 8.900001 4.600000 6.900000 4.600000
- trget_machine DATA_trgt DEV_NULL half-duplex 0 Std_logic_vector(31#downto#0) L17 8.900001 4.900000 6.900000 4.900000
- DEV_NULL unknown_port trget_machine TABORT simplex 0 Std_logic 0 6.900000 7.200000 8.900001 7.200000
- DEV_NULL _ trget_machine TRETRY simplex 0 Std_logic 0 6.900000 7.000000 8.900001 7.000000
- END_DEFINE_TOPOLOGY.
-
-GENERIC: LOCALADD : integer := 64
- ANNOTATION: 3.821249 8.066763 PCI main block diagram
- ANNOTATION: 3.779719 8.403428 PCI OpenCores group
- ANNOTATION: 3.788020 8.736729 Jamil Khatib
- BOUNDINGBOX: 3.700000 7.600000 7.100000 9.000001 7.100000 7.600000 3.700000 7.600000 3.700000 9.000001 7.100000 9.000001
-
-END_DEFINE_MODULE.
-
-
-
-
Index: trunk/Blocks/pci_parity.vhd
===================================================================
--- trunk/Blocks/pci_parity.vhd (revision 9)
+++ trunk/Blocks/pci_parity.vhd (nonexistent)
@@ -1,144 +0,0 @@
--------------------------------------------------------------------------------
--- Title : PCI Parity core
--- Project : PCI target Core
--------------------------------------------------------------------------------
--- File : pci_parity.VHD
--- Author : Jamil Khatib
--- Organization: OpenCores Project
--- Created : 2000/04/1
--- Last update : 2000/04/1
--- Platform :
--- Simulators : Modelsim 5.3XE / Windows98
--- Synthesizers: webfitter - Leonardo / WindowsNT
--- Target : XC9572XL-5-VQ64 - EPF10K100EQC208 Flex10K
--- Dependency :
--------------------------------------------------------------------------------
--- Description: PCI Parity Core
--------------------------------------------------------------------------------
--- Copyright (c) 2000 Jamil Khatib
---
--- This VHDL design file is an open design; you can redistribute it and/or
--- modify it and/or implement it under the terms of the Openip General Public
--- License as it is going to be published by the OpenIPCore Organization and
--- any coming versions of this license.
--- You can check the draft license at
--- http://www.openip.org/oc/license.html
---
--------------------------------------------------------------------------------
--- Revisions :
--- Revision Number : 1
--- Version : 1.0
--- Date : 1st Apr 2000
--- Modifier : Jamil Khatib (khatib@ieee.org)
--- Desccription : Created
---
--- Known bugs : Extending the PAR signals to wait states
--- : SERR is generated upon local side request only
--- : PERR must remain active two clockcycles after the ERR
--------------------------------------------------------------------------------
-library ieee;
-use ieee.std_logic_1164.all;
-
-entity parity is
-
- port (
- -- PCI Interface
- CLK : in std_logic; -- PCI clock
- AD : in std_logic_vector(31 downto 0); -- PCI AD signal
- CBE : in std_logic_vector(3 downto 0); -- C/BE PCI bus signals
- PAR : inout std_logic; -- PAR signal
- SERR_n : inout std_logic; -- SERR# signal
- PERR_n : out std_logic; -- PERR# signal
- -- PERR# signal is output only for target
- -- Local Interface
- ParOperation : in std_logic; -- Parity Operation
- -- Drive PAR or check it
- Par_oe : in std_logic; -- PAR Output Enable
- Locserr_n : in std_logic; -- Local System Error
- LocErrRep_n : out std_logic); -- Local Error Report
- -- used to report parity errors for local interface
- -- and to the configuration register
-
-end parity;
-
-library ieee;
-use ieee.std_logic_1164.all;
--------------------------------------------------------------------------------
-architecture behavior of parity is
-
-begin -- behavior
-
--------------------------------------------------------------------------------
--- purpose: Parity Generation
--- type : sequential
--- inputs : CLK
--- outputs: PAR, LocErrRep
- Paritygen : process (CLK)
-
- variable tmp_par : std_logic; -- temporary parity vriable
- variable par_q : std_logic; -- Next Par signal
- variable perr_q : std_logic; -- Next PERR signal
-
- begin -- process Paritygen
-
- if CLK'event and CLK = '1' then -- rising clock edge
- if Par_oe = '1' then
-
--------------------------------------------------------------------------------
--- PAR signal states:
--- Idel: when no operation on the current target or master
--- PAR = 'Z' , PERR = 'Z'
--- Master Read:
--- Address phase:
--- Master Drives PAR
--- Target Drives PERR
--- Data phase:
--- Target Drives PAR
--- Master Drives PERR
--- Master write:
--- Address and data phase
--- Master Drives PAR
--- Master Drives PERR
--------------------------------------------------------------------------------
--- ParOperation = 1 Calculate and drive PAR Port
--- ParOperation = 0 Calculate and report Parity Errors
--------------------------------------------------------------------------------
- if ParOperation = '1' then -- Drive PAR signal
-
- PAR <= par_q;
- LocErrRep_n <= perr_q;
- PERR_n <= 'Z';
-
- else
-
- PERR_n <= perr_q;
- PAR <= 'Z';
-
- end if;
-
--- No of 1's in AD, CBE & PAR must be even
- tmp_par := CBE(3) xor CBE(2) xor CBE(1) xor CBE(0);
-
- for i in AD'range loop
-
- tmp_par := tmp_par xor AD(i);
-
- end loop; -- i
-
- par_q := tmp_par;
-
- perr_q := tmp_par xor PAR_q;
-
- else
-
- PAR <= 'Z';
- PERR_n <= 'Z';
-
- end if;
- end if;
- end process Paritygen;
--------------------------------------------------------------------------------
-
- SERR_n <= Locserr_n;
--------------------------------------------------------------------------------
-end behavior;
Index: trunk/TestBench/pci_parity_tb.vhd
===================================================================
--- trunk/TestBench/pci_parity_tb.vhd (revision 9)
+++ trunk/TestBench/pci_parity_tb.vhd (nonexistent)
@@ -1,149 +0,0 @@
--------------------------------------------------------------------------------
--- Title : PCI Parity test bench
--- Project : PCI target Core
--------------------------------------------------------------------------------
--- File : pci_parity_tb.VHD
--- Author : Jamil Khatib
--- Organization: OpenCores Project
--- Created : 2000/04/1
--- Last update : 2000/04/1
--- Platform :
--- Simulators : Modelsim 5.3 XE / Windows98
--- Synthesizers:
--- Target :
--- Dependency :
--------------------------------------------------------------------------------
--- Description: PCI Parity test bench
--------------------------------------------------------------------------------
--- Copyright (c) 2000 Jamil Khatib
---
--- This VHDL design file is an open design; you can redistribute it and/or
--- modify it and/or implement it under the terms of the Openip General Public
--- License as it is going to be published by the OpenIPCore Organization and
--- any coming versions of this license.
--- You can check the draft license at
--- http://www.openip.org/oc/license.html
---
--------------------------------------------------------------------------------
--- Revisions :
--- Revision Number : 1
--- Version : 1.0
--- Date : 2st Apr 2000
--- Modifier : Jamil Khatib (khatib@ieee.org)
--- Desccription : Created
---
--- Known bugs :
--------------------------------------------------------------------------------
-library ieee;
-use ieee.std_logic_1164.all;
-
-entity parity_tb is
-
-end parity_tb;
-
-architecture behavior_tb of parity_tb is
- component parity
-
- port (
- -- PCI Interface
- CLK : in std_logic; -- PCI clock
- AD : in std_logic_vector(31 downto 0); -- PCI AD signal
- CBE : in std_logic_vector(3 downto 0); -- C/BE PCI bus signals
- PAR : inout std_logic; -- PAR signal
- SERR_n : inout std_logic; -- SERR# signal
- PERR_n : out std_logic; -- PERR# signal
- -- PERR# signal is output only for target
- -- Local Interface
- ParOperation : in std_logic; -- Parity Operation
- -- Drive PAR or check it
- Par_oe : in std_logic; -- PAR Output Enable
- Locserr_n : in std_logic; -- Local System Error
- LocErrRep_n : out std_logic); -- Local Error Report
- -- used to report parity errors for local interface
- -- and to the configuration register
- end component;
-
- signal clk_tb : std_logic := '0'; -- clock
- signal ad_tb : std_logic_vector(31 downto 0); -- AD signal
- signal cbe_tb : std_logic_vector(3 downto 0); -- C/BE signal
- signal par_tb : std_logic;
- signal serr_tb : std_logic;
- signal perr_tb : std_logic;
-
- signal paroperation_tb : std_logic;
- signal paroe_tb : std_logic;
- signal locserr_tb : std_logic;
- signal locerrrep_tb : std_logic;
-
- signal par_syn_tb : std_logic;
- signal serr_syn_tb : std_logic;
- signal perr_syn_tb : std_logic;
- signal locerrrep_syn_tb : std_logic;
-
-begin -- behavior_tb
-
- clk_tb <= not clk_tb after 30 ns;
-
- UUT : parity
- port map (
- CLK => clk_tb,
- AD => ad_tb,
- CBE => cbe_tb,
- PAR => par_tb,
- SERR_n => serr_tb,
- PERR_n => perr_tb,
- ParOperation => paroperation_tb,
- Par_oe => paroe_tb,
- Locserr_n => locserr_tb,
- LocErrRep_n => locerrrep_tb);
--------------------------------------------------------------------------------
-
- UUT_syn : parity
- port map (
- CLK => clk_tb,
- AD => ad_tb,
- CBE => cbe_tb,
- PAR => par_syn_tb,
- SERR_n => serr_syn_tb,
- PERR_n => perr_syn_tb,
- ParOperation => paroperation_tb,
- Par_oe => paroe_tb,
- Locserr_n => locserr_tb,
- LocErrRep_n => locerrrep_syn_tb);
-
-
- par_tb <= transport 'Z' after 0 ns,
- '1' after 400 ns;
-
- par_syn_tb <= transport 'Z' after 0 ns,
- '1' after 400 ns;
-
- ad_tb <= (others => '1');
- cbe_tb <= transport "1111" after 0 ns,
- "1000" after 200 ns,
- "1111" after 400 ns,
- "1000" after 600 ns;
-
- paroperation_tb <= transport '1' after 0 ns,
- '0' after 400 ns;
- paroe_tb <= transport '1' after 0 ns,
- '0' after 800 ns;
- locserr_tb <= '1';
-
-
-
-end behavior_tb;
-
--- Test bench Configuration
-configuration TESTBENCH_FOR_parity of parity_tb is
- for behavior_tb
- for UUT : parity
- use entity work.parity(behavior);
- end for;
-
- for UUT_syn : parity
- use entity work.parity(STRUCTURE);
- end for;
-
- end for;
-end TESTBENCH_FOR_parity;
Index: trunk/vhdl_behav/readme.txt
===================================================================
--- trunk/vhdl_behav/readme.txt (revision 9)
+++ trunk/vhdl_behav/readme.txt (nonexistent)
@@ -1,32 +0,0 @@
-This models are written in VHDL!
-Author is Ovidiu Lupas!
-
-MASTER model
-generates PCI compliant signals
-checks Target signal compliance with PCI
-checks data received from Target for correctness
-generates assertion reports if Target signals are not PCI compliant
-
-TARGET model
-generates PCI compliant signals
-checks Master signal compliance with PCI
-checks data received from Master for correctness
-generates assertion reports if Master signals are not PCI compliant
-
-Description
-The models are boardlevel simulation models and are useful in the testing phase
-of
-the PCI cores design. The models are 32 bit, 33 MHz PCI compliant but are easy
-upgradable to 64 bit, 66 MHz. The models are free; you can redistribute them
-and/or modify them under the terms of the GNU General Public License as
-published by the Free Software Foundation; either version 2 of the License, or
-(at your option) any later version.
-The models are distributed in the hope that they will be useful, but WITHOUT ANY
-WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
-PARTICULAR PURPOSE. See the GNU General Public License for more details.
-
-Current Status:
-design is available in VHDL from OpenCores CVS via cvsweb
-documentation will be available in short time
-if needed, easy upgradable to 64 bit, 66 MHz
\ No newline at end of file
trunk/vhdl_behav/readme.txt
Property changes :
Deleted: svn:executable
## -1 +0,0 ##
-*
\ No newline at end of property
Index: trunk/vhdl_behav/Tg32pci.vhd
===================================================================
--- trunk/vhdl_behav/Tg32pci.vhd (revision 9)
+++ trunk/vhdl_behav/Tg32pci.vhd (nonexistent)
@@ -1,1283 +0,0 @@
---===================================================================--
---
--- www.OpenCores.Org - January 2000
--- This model adheres to the GNU public license
---
--- Design units : Target device for PCI Local Bus 33 MHz 32 bits
--- (BoardLevel Simulation model)
--- (Entity and architecture)
---
--- File name : Tg32PCI.vhd
---
--- Purpose : The Target device is used to simulate a target
--- device on the PCI-Bus
---
--- Note : This model is modelled after the PCI protocol
--- as described in Xilinx & Altera AppNotes
---
--- There can be used more than one target devices in a
--- design, every device being identified by the three
--- base addresses in generic.
---
--- 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
---===================================================================--
------------------------------------------------------------------------
--- Entity for Target device in a PCI bus 33 MHZ 32 bit configuration
------------------------------------------------------------------------
-library ieee,work;
- use ieee.Std_Logic_1164.all;
- use work.Simulation.all;
- use work.PCI_Def.all;
------------------------------------------------------------------------
------------------------------------------------------------------------
-entity TG32PCI is
- generic (
- devtype : string(1 to 4); -- type of the device (Fast, Medi, Slow)
- tdelay : Time; -- delay time parameter when the device will change
- -- data on AD_Bus (referenced to CLK signal)
- tsetup : Time;
- thold : Time;
- bamem : Std_Logic_Vector(31 downto 0); -- base address for memory
- baio : Std_Logic_Vector(31 downto 0); -- base address for I/O port
- bacfg : Std_Logic_Vector(31 downto 0)); -- base address for cfg space
- port (
- -- Address, Data and Command buses (37)
- AD_Bus : inout Std_Logic_Vector (31 downto 0); -- Address and Data Bus
- C_BE_Bus : in Std_Logic_Vector (3 downto 0); -- Command Bus
- PAR : inout Std_Logic; --
- -- Interface control signals (6)
- FRAME_N : in Std_Logic;
- TRDY_N : inout Std_Logic;
- IRDY_N : in Std_Logic;
- STOP_N : out Std_Logic;
- DEVSEL_N : inout Std_Logic;
- IDSEL : in Std_Logic;
- -- Error reporting signals (2)
- PERR_N : inout Std_Logic;
- SERR_N : inout Std_Logic;
- -- System signals (2)
- CLK : in Std_Logic;
- RST_N : in Std_Logic);
-end TG32PCI; --=================== End of entity ====================--
------------------------------------------------------------------------
--- Architecture for Target device PCI bus 33MHZ 32 bit configuration
------------------------------------------------------------------------
-architecture Behavior of Target32PCI is
- ---------------------------------------------------------------------
- -- Definition of Memory type,
- ---------------------------------------------------------------------
- type MEMORY is array(0 to 255) of Std_Logic_Vector(31 downto 0);
- ---------------------------------------------------------------------
- -- Local declarations
- ---------------------------------------------------------------------
- shared variable addr : Std_Logic_Vector (31 downto 0); -- Address
- shared variable busaddr : Integer; -- address present on bus
- shared variable cfgaddr : Integer; -- current configuration register address
- shared variable memaddr : Integer; -- current memory address
- shared variable ioaddr : Integer; -- current I/O port address
- shared variable IOmem : Memory; -- IOport registers
- shared variable Cfgmem : Memory; -- Configuration registers
- shared variable Mem : Memory; -- memory locations
- shared variable trdywaits : Boolean := false; -- wait enable
- shared variable trdy_st,trdy_nr,trdy_loop : Integer := 0;
- ---------------------------------------------------------------------
- -- Signals
- ---------------------------------------------------------------------
- signal cmd : Std_Logic_Vector (3 downto 0); -- Command bus
- signal Busy : Std_Logic := '0';
- signal IORead : Std_Logic := '0';
- signal IOWrite : Std_Logic := '0';
- signal MemRead : Std_Logic := '0';
- signal MemWrite : Std_Logic := '0';
- signal WaitWrite : Std_Logic := '0';
- signal CfgRead : Std_Logic := '0';
- signal CfgWrite : Std_Logic := '0';
- signal FrameEv : Std_Logic := '0';
- signal CmdBusReady : Std_Logic := '0';
- signal TrnArnd : Std_Logic := '0';
- signal DevAddr : Std_Logic := '0';
- signal ResFin : Std_Logic := '0';
- signal Waits : Std_Logic := '0';
- signal Init : Std_Logic := '0';
-begin--======================== Architecture ========================--
- ---------------------------------------------------------------------
- -- Initialize the memory contents with zeroes
- ---------------------------------------------------------------------
- Initialize : process
- begin
- for i in 0 to 255 loop
- IOmem(i) := x"00000000";
- Mem(i) := x"00000000";
- Cfgmem(i) := x"00000000";
- end loop;
- wait;
- 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 master
- ---------------------------------------------------------------------
- Parity : process(CLK,RST_N)
- variable parbit : Std_Logic;
- variable lastpar : Std_Logic;
- variable errbit : Std_Logic;
- variable pargen : Boolean := false;
- variable errgen : Boolean := false;
- variable cmdbus : Std_Logic_Vector(3 downto 0);
- variable addrbus : Std_Logic_Vector(31 downto 0);
- begin
- if (Falling_Edge(RST_N) or RST_N = '0') then
- PAR <= 'Z';
- PERR_N <= 'Z';
- elsif (CLK'Event and CLK = '1') then -- parity computation on every cycle
- addrbus := AD_Bus;
- cmdbus := C_BE_Bus;
- lastpar := parbit;
- parbit := '0';
- if addrbus /= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ" then
- for I in 0 to 31 loop
- parbit := parbit xor addrbus(i);
- end loop;
- for I in 0 to 3 loop
- parbit := parbit xor cmdbus(I);
- end loop;
- else
- parbit := 'Z';
- end if;
- if PAR = lastpar then -- PERR computation on every cycle
- errbit := '1';
- elsif PAR /= lastpar then
- errbit := '0';
- elsif PAR = 'Z' then
- errbit := 'H';
- end if;
- if ((IORead = '1' or MemRead = '1' or CfgRead = '1') and DevAddr = '1') then
- pargen := true;
- else
- pargen := false;
- end if;
- elsif (CLK'Event and CLK = '0' and DevAddr = '1') then -- parity generation if necessary
- if errgen = true then
- PERR_N <= errbit;
- else
- PERR_N <= 'H';
- end if;
- if pargen = true then
- PAR <= parbit;
- errgen := false;
- else
- PAR <= 'Z';
- errgen := true;
- end if;
- elsif (CLK'Event and CLK = '0' and DevAddr = '0') then --not the selected device
- PAR <= 'Z'; -- by the address
- PERR_N <= 'H';
- SERR_N <= 'Z';
- end if;
- end process;
- ---------------------------------------------------------------------
- -- Implements the command decoding, to receive commands from master
- ---------------------------------------------------------------------
- Decode : process(CLK,FRAME_N,Busy,DevAddr,cmdBusReady,RST_N)
- variable counter : Integer;
- variable devdel : Boolean := false;
- begin
- if (Falling_Edge(RST_N) or RST_N = '0') then
- DEVSEL_N <= 'Z';
- STOP_N <= 'Z';
- Busy <= '0';
- elsif (Frame_N'Event and Frame_N = '0') then -- the target device is awakened by
- FrameEv <= '1'; -- falling_edge of FRAME signal
- counter := 0;
- elsif (Busy'Event and Busy = '0') then
- IOWrite <= '0';
- MemWrite <= '0';
- CfgWrite <= '0';
- WaitWrite <= '0';
- IORead <= '0';
- MemRead <= '0';
- CfgRead <= '0';
- elsif (Busy'Event and Busy = '1') then
- if ( IOWrite = '1' or MemWrite = '1' or CfgWrite = '1' or WaitWrite = '1') then
- report "Target device is selected for write operations!"
- severity Note;
- if devtype = "Fast" then
- DEVSEL_N <= '0' after 8 ns;
- Stop_N <= '1' after 10 ns;
- devdel := false;
- else
- devdel := true;
- counter := 0;
- end if;
- elsif ( IORead = '1' or MemRead = '1' or CfgRead = '1') then
- report "Target device is selected for read operations!"
- severity Note;
- if devtype = "Fast" then
- DEVSEL_N <= '0' after 8 ns;
- Stop_N <= '1' after 10 ns;
- devdel := false;
- else
- devdel := true;
- counter := 0;
- end if;
- end if;
- elsif (DevAddr'Event and DevAddr = '0') then
- Busy <= '0';
- elsif (cmdBusReady'Event and cmdBusReady = '1') then
- TrnArnd <= '0';
- elsif (CLK'Event and CLK = '0') then
- if Busy = '0' and DevAddr = '1' then -- deselect
- DEVSEL_N <= 'H';
- STOP_N <= '1';
- elsif DevAddr = '0' then -- deselect device
- DEVSEL_N <= 'Z';
- STOP_N <= 'Z';
- end if;
- elsif (CLK'Event and CLK = '1') then
- if ResFin = '1' then -- memory reserved mode command
- if MemWrite = '1' then -- master writes to target memory
- if TRDY_N = '0' and IRDY_N = '0' then
- Busy <= '0';
- ResFin <= '0';
- end if;
- elsif MemRead = '1' then -- master reads from target memory
- if TrnArnd = '0' and TRDY_N = '0' and IRDY_N = '0' then
- Busy <= '0';
- ResFin <= '0';
- end if;
- end if;
- end if;
- if devdel = true then
- if devtype = "Medi" then
- if counter = 0 then
- DEVSEL_N <= '0' after 8 ns;
- Stop_N <= '1' after 10 ns;
- devdel := false;
- end if;
- elsif devtype = "Slow" then
- if counter = 1 then
- DEVSEL_N <= '0' after 8 ns;
- Stop_N <= '1' after 10 ns;
- devdel := false;
- else
- counter := counter + 1;
- end if;
- end if;
- end if;
- if FRAME_N = '1' then -- end of cycle
- assert (IRDY_N = '0')
- report "Target device : FRAME signal deassertion error. IRDY is not asserted."
- severity Error;
- if TRDY_N = '0' and IRDY_N = '0' then -- finish the current cycle
- Busy <= '0';
- end if;
- elsif FrameEv = '1' then -- decoding
- FrameEv <= '0';
- assert (FRAME_N'Last_Event >= tsetup)
- report "Target device : Frame setup time violation in decode cycle!"
- severity warning;
- assert (AD_Bus'Last_Event >= tsetup)
- report "Target device : Address setup time violation in decode cycle!"
- severity warning;
- assert (C_BE_Bus'Last_Event >= tsetup)
- report "Target device : Command setup time violation in decode cycle!"
- severity warning;
- addr := AD_Bus;
- case C_BE_Bus is -- decoding the command bus
- when "0001" => -- Special Cycle! Used to transfer from master device the
- -- wait states parameters
- if (addr(31 downto 8) = bacfg(31 downto 8) and IDSEL ='1') then
- WaitWrite <= '1';
- DevAddr <= '1';
- Busy <= '1';
- trdywaits := true;
- else -- this device is not the addressed one,
- DevAddr <= '0'; -- so it is not responding
- trdywaits := false;
- end if;
- cfgaddr := Byte2Int(addr(7 downto 0));
- when "0010" => -- I/O Read! Master reads from target device.
- if addr(31 downto 8) = baio(31 downto 8) then
- DevAddr <= '1';
- Busy <= '1';
- IORead <= '1';
- TrnArnd <= '1';
- ioaddr := Byte2Int(addr(7 downto 0));
- else -- this device is not the addressed one,
- DevAddr <= '0'; -- so it is not responding
- end if;
- when "0011" => -- I/O Write! Master writes to target device.
- if addr(31 downto 8) = baio(31 downto 8) then
- DevAddr <= '1';
- Busy <= '1';
- IOWrite <= '1';
- ioaddr := Byte2Int(addr(7 downto 0));
- else -- this device is not the addressed one,
- DevAddr <= '0'; -- so it is not responding
- end if;
- when "1100" => -- Memory Read! Master reads from target device.
- if addr(31 downto 8) = bamem(31 downto 8) then
- DevAddr <= '1';
- Busy <= '1';
- MemRead <= '1';
- TrnArnd <= '1';
- if addr(1 downto 0) = "01" then -- reserved mode
- ResFin <= '1';
- elsif addr(1 downto 0) = "11" then -- reserved mode
- ResFin <= '1';
- end if;
- memaddr := Byte2Int(addr(7 downto 0));
- else -- this device is not the addressed one,
- DevAddr <= '0'; -- so it is not responding
- end if;
- when "1110" => -- Memory Read Line! Master reads from target device.
- if addr(31 downto 8) = bamem(31 downto 8) then
- DevAddr <= '1';
- Busy <= '1';
- MemRead <= '1';
- TrnArnd <= '1';
- if addr(1 downto 0) = "01" then -- reserved mode
- ResFin <= '1';
- elsif addr(1 downto 0) = "11" then -- reserved mode
- ResFin <= '1';
- end if;
- memaddr := Byte2Int(addr(7 downto 0));
- else -- this device is not the addressed one,
- DevAddr <= '0'; -- so it is not responding
- end if;
- when "1111" => -- Memory Write! Master writes to target device.
- if addr(31 downto 8) = bamem(31 downto 8) then
- DevAddr <= '1';
- Busy <= '1';
- MemWrite <= '1';
- if addr(1 downto 0) = "01" then -- reserved mode
- ResFin <= '1';
- elsif addr(1 downto 0) = "11" then -- reserved mode
- ResFin <= '1';
- end if;
- memaddr := Byte2Int(addr(7 downto 0));
- else -- this device is not the addressed one,
- DevAddr <= '0'; -- so it is not responding
- end if;
- when "0110" => -- Memory Read! Master reads from target device.
- if addr(31 downto 8) = bamem(31 downto 8) then
- DevAddr <= '1';
- Busy <= '1';
- MemRead <= '1';
- TrnArnd <= '1';
- if addr(1 downto 0) = "01" then -- reserved mode
- ResFin <= '1';
- elsif addr(1 downto 0) = "11" then -- reserved mode
- ResFin <= '1';
- end if;
- memaddr := Byte2Int(addr(7 downto 0));
- else -- this device is not the addressed one,
- DevAddr <= '0'; -- so it is not responding
- end if;
- when "0111" => -- Memory Write! Master writes to target device.
- if addr(31 downto 8) = bamem(31 downto 8) then
- DevAddr <= '1';
- Busy <= '1';
- MemWrite <= '1';
- if addr(1 downto 0) = "01" then -- reserved mode
- ResFin <= '1';
- elsif addr(1 downto 0) = "11" then -- reserved mode
- ResFin <= '1';
- end if;
- memaddr := Byte2Int(addr(7 downto 0));
- else -- this device is not the addressed one,
- DevAddr <= '0'; -- so it is not responding
- end if;
- when "1010" => -- Configuration Read! Master reads from target device.
- if (addr(31 downto 8) = bacfg(31 downto 8) and IDSEL = '1') then
- if addr(1 downto 0) = "01" then
- report "Target device: Type 1 configuration access on bus! Ignored."
- severity Note;
- elsif addr(1 downto 0) = "00" then
- CfgRead <= '1';
- TrnArnd <= '1';
- DevAddr <= '1';
- Busy <= '1';
- end if;
- cfgaddr := Byte2Int(addr(7 downto 0));
- else -- this device is not the addressed one,
- DevAddr <= '0'; -- so it is not responding
- end if;
- when "1011" => -- Configuration Write! Master writes to target device.
- if (addr(31 downto 8) = bacfg(31 downto 8) and IDSEL = '1') then
- if addr(1 downto 0) = "01" then
- report "Target device: Type 1 configuration access on bus! Ignored."
- severity Note;
- elsif addr(1 downto 0) = "00" then
- CfgWrite <= '1';
- DevAddr <= '1';
- Busy <= '1';
- end if;
- cfgaddr := Byte2Int(addr(7 downto 0));
- else
- -- this device is not the addressed one,
- DevAddr <= '0'; -- so it is not responding
- end if;
- when "0100" =>
- report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
- severity Warning;
- when "0101" =>
- report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
- severity Warning;
- when "1000" =>
- report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
- severity Warning;
- when "1001" =>
- report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
- severity Warning;
- when "ZZZZ" => null;
- when others =>
- report "Target device: Unknown or invalid command on C/BE bus! Ignored."
- severity Error;
- end case;
- end if;
- -- elsif (Frame_N'Event and Frame_N = '1') then
- end if;
- end process;
- ---------------------------------------------------------------------
- -- Implementation of Write command.
- -- Master writes to Target device.
- ---------------------------------------------------------------------
- WriteProc : process(CLK,RST_N)
- variable waitreg : Std_Logic_Vector(15 downto 0) := x"0000";
- variable Char3_2,Char1,Char0 : Std_Logic_Vector(7 downto 0) := x"00";
- begin
- if (CLK'Event and CLK = '1' and ((IRDY_N = '0' and TRDY_N = '0') or FRAME_N = '1')) then
- assert (AD_Bus'Last_Event >= tsetup)
- report "Target device : Data setup time violation in decode cycle!"
- severity warning;
- assert (C_BE_Bus'Last_Event >= tsetup)
- report "Target device : Byte Enables setup time violation in decode cycle!"
- severity warning;
- if (WaitWrite = '1') then
- Char3_2 := AD_Bus(15 downto 8);
- Char1 := "0000" & AD_Bus(7 downto 4);
- Char0 := "0000" & AD_Bus(3 downto 0);
- trdy_loop := Byte2Int(Char3_2) ;
- trdy_nr := Byte2Int(Char1); -- + 1;
- trdy_st := Byte2Int(Char0);
- elsif IOWrite = '1' then
- -- Master writes to target I/O space
- case addr(1 downto 0) is
- when "00" =>
- if C_BE_Bus = "0000" then
- IOmem(ioaddr) := AD_Bus;
- elsif C_BE_Bus = "1000" then
- IOmem(ioaddr)(23 downto 0) := AD_Bus(23 downto 0);
- elsif C_BE_Bus = "0100" then
- IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
- IOmem(ioaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "1100" then
- IOmem(ioaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "0010" then
- IOmem(ioaddr)(31 downto 16) := AD_Bus(31 downto 16);
- IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1010" then
- IOmem(ioaddr)(23 downto 16) := AD_Bus(23 downto 16);
- IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "0110" then
- IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
- IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1110" then
- IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus(0) = '1' then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when "01" =>
- if C_BE_Bus = "0001" then
- IOmem(ioaddr)(31 downto 8) := AD_Bus(31 downto 8);
- elsif C_BE_Bus = "1001" then
- IOmem(ioaddr)(23 downto 8) := AD_Bus(23 downto 8);
- elsif C_BE_Bus = "0101" then
- IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
- IOmem(ioaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus = "1101" then
- IOmem(ioaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus(1) = '1' then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when "10" =>
- if C_BE_Bus = "0011" then
- IOmem(ioaddr)(31 downto 16) := AD_Bus(31 downto 16);
- elsif C_BE_Bus = "1011" then
- IOmem(ioaddr)(23 downto 16) := AD_Bus(23 downto 16);
- elsif C_BE_Bus(2) = '1' then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when "11" =>
- if C_BE_Bus = "0111" then
- IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
- elsif C_BE_Bus(3) = '1' then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when others =>
- null;
- end case;
- ioaddr := ioaddr + 1;
- elsif MemWrite = '1' then
- -- Master writes to target memory space
- case addr(1 downto 0) is
- when "00" => -- linear incrementing mode
- if C_BE_Bus = "0000" then
- Mem(memaddr) := AD_Bus;
- elsif C_BE_Bus = "0001" then
- Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
- elsif C_BE_Bus = "0010" then
- Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "0011" then
- Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
- elsif C_BE_Bus = "0100" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "0101" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus = "0110" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "0111" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- elsif C_BE_Bus = "1000" then
- Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
- elsif C_BE_Bus = "1001" then
- Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
- elsif C_BE_Bus = "1010" then
- Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1011" then
- Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
- elsif C_BE_Bus = "1100" then
- Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "1101" then
- Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus = "1110" then
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1111" then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- memaddr := memaddr + 1;
- when "01" => -- reserved mode (disconnect after first data phase)
- if C_BE_Bus = "0000" then
- Mem(memaddr) := AD_Bus;
- elsif C_BE_Bus = "0001" then
- Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
- elsif C_BE_Bus = "0010" then
- Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "0011" then
- Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
- elsif C_BE_Bus = "0100" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "0101" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus = "0110" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "0111" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- elsif C_BE_Bus = "1000" then
- Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
- elsif C_BE_Bus = "1001" then
- Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
- elsif C_BE_Bus = "1010" then
- Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1011" then
- Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
- elsif C_BE_Bus = "1100" then
- Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "1101" then
- Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus = "1110" then
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1111" then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when "10" => -- cacheline wrap mode
- if C_BE_Bus = "0000" then
- Mem(memaddr) := AD_Bus;
- elsif C_BE_Bus = "0001" then
- Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
- elsif C_BE_Bus = "0010" then
- Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "0011" then
- Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
- elsif C_BE_Bus = "0100" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "0101" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus = "0110" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "0111" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- elsif C_BE_Bus = "1000" then
- Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
- elsif C_BE_Bus = "1001" then
- Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
- elsif C_BE_Bus = "1010" then
- Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1011" then
- Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
- elsif C_BE_Bus = "1100" then
- Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "1101" then
- Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus = "1110" then
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1111" then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- memaddr := memaddr + 1;
- when "11" => -- reserved mode (disconnect after first data phase)
- if C_BE_Bus = "0000" then
- Mem(memaddr) := AD_Bus;
- elsif C_BE_Bus = "0001" then
- Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
- elsif C_BE_Bus = "0010" then
- Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "0011" then
- Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
- elsif C_BE_Bus = "0100" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "0101" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus = "0110" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "0111" then
- Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
- elsif C_BE_Bus = "1000" then
- Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
- elsif C_BE_Bus = "1001" then
- Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
- elsif C_BE_Bus = "1010" then
- Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1011" then
- Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
- elsif C_BE_Bus = "1100" then
- Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "1101" then
- Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus = "1110" then
- Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1111" then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when others =>
- null;
- end case;
- elsif CfgWrite = '1' then
- -- Master writes to target configuration space
- if C_BE_Bus = "0000" then
- Cfgmem(cfgaddr) := AD_Bus;
- elsif C_BE_Bus = "0001" then
- Cfgmem(cfgaddr)(31 downto 8) := AD_Bus(31 downto 8);
- elsif C_BE_Bus = "0010" then
- Cfgmem(cfgaddr)(31 downto 16) := AD_Bus(31 downto 16);
- Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "0011" then
- Cfgmem(cfgaddr)(31 downto 16) := AD_Bus(31 downto 16);
- elsif C_BE_Bus = "0100" then
- Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Cfgmem(cfgaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "0101" then
- Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Cfgmem(cfgaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus = "0110" then
- Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
- Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "0111" then
- Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
- elsif C_BE_Bus = "1000" then
- Cfgmem(cfgaddr)(23 downto 0) := AD_Bus(23 downto 0);
- elsif C_BE_Bus = "1001" then
- Cfgmem(cfgaddr)(23 downto 8) := AD_Bus(23 downto 8);
- elsif C_BE_Bus = "1010" then
- Cfgmem(cfgaddr)(23 downto 16) := AD_Bus(23 downto 16);
- Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1011" then
- Cfgmem(cfgaddr)(23 downto 16) := AD_Bus(23 downto 16);
- elsif C_BE_Bus = "1100" then
- Cfgmem(cfgaddr)(15 downto 0) := AD_Bus(15 downto 0);
- elsif C_BE_Bus = "1101" then
- Cfgmem(cfgaddr)(15 downto 8) := AD_Bus(15 downto 8);
- elsif C_BE_Bus = "1110" then
- Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
- elsif C_BE_Bus = "1111" then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- cfgaddr := cfgaddr + 1;
- end if;
- end if;
- end process;
- ---------------------------------------------------------------------
- -- Implementation of Read command.
- -- Master read from Target device.
- ---------------------------------------------------------------------
- ReadProc : process(RST_N,CLK,cmdBusReady,IORead,IOWrite,MemRead,MemWrite,CfgRead,CfgWrite)
- variable first : Boolean := true;
- begin
- if (Falling_Edge(RST_N) or RST_N = '0') then
- AD_Bus <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ";
- elsif (CLK'Event and CLK = '0') then
- cmdBusReady <= '0';
- if (first = true or TrnArnd ='1') then
- -- Initialize the AD_Bus to avoid bus conflict
- AD_Bus <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ";
- first := false;
- elsif Init = '1' then
- Init <= '0';
- AD_Bus <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ" after tdelay;
- end if;
- elsif IORead'Event and IORead = '0' then
- Init <= '1';
- elsif MemRead'Event and MemRead = '0' then
- Init <= '1';
- elsif CfgRead'Event and CfgRead = '0' then
- Init <= '1';
- elsif (CLK'Event and CLK = '1' and IRDY_N = '0') then
- if (IORead = '1' or MemRead = '1' or CfgRead = '1') then
- cmd <= C_BE_Bus; -- read the byte enable command
- cmdBusReady <= '1';
- end if;
- elsif (cmdBusReady'Event and cmdBusReady = '0' and TRDY_N = '0') then
- if IORead = '1' then
- -- Master reads from target I/O space
- case addr(1 downto 0) is
- when "00" =>
- if cmd = "0000" then
- AD_Bus <= IOmem(ioaddr) after tdelay;
- elsif cmd = "1000" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 0) <= IOmem(ioaddr)(23 downto 0) after tdelay;
- elsif cmd = "0100" then
- AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- AD_Bus(15 downto 0) <= IOmem(ioaddr)(15 downto 0) after tdelay;
- elsif cmd = "1100" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 0) <= IOmem(ioaddr)(15 downto 0) after tdelay;
- elsif cmd = "0010" then
- AD_Bus(31 downto 16) <= IOmem(ioaddr)(31 downto 16) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
- elsif cmd = "1010" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= IOmem(ioaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
- elsif cmd = "0110" then
- AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
- elsif cmd = "1110" then
- AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
- elsif cmd(0) = '1' then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when "01" =>
- if cmd = "0001" then
- AD_Bus(31 downto 8) <= IOmem(ioaddr)(31 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1001" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 8) <= IOmem(ioaddr)(23 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "0101" then
- AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- AD_Bus(15 downto 8) <= IOmem(ioaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1101" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 8) <= IOmem(ioaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd(1) = '1' then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when "10" =>
- if cmd = "0011" then
- AD_Bus(31 downto 16) <= IOmem(ioaddr)(31 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd = "1011" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= IOmem(ioaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd(2) = '1' then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when "11" =>
- if cmd = "0111" then
- AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
- elsif cmd(3) = '1' then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when others =>
- null;
- end case;
- ioaddr := ioaddr + 1;
- elsif MemRead = '1' then
- -- Master reads from target memory space
- case addr(1 downto 0) is
- when "00" => -- linear incrementing mode
- if cmd = "0000" then
- AD_Bus <= Mem(memaddr) after tdelay;
- elsif cmd = "0001" then
- AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "0010" then
- AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- elsif cmd = "0011" then
- AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd = "0100" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- elsif cmd = "0101" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "0110" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "0111" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
- elsif cmd = "1000" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
- elsif cmd = "1001" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1010" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "1011" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd = "1100" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
- elsif cmd = "1101" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1110" then
- AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "1111" then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- memaddr := memaddr + 1;
- when "01" => -- reserved mode (disconnect after first data phase)
- if cmd = "0000" then
- AD_Bus <= Mem(memaddr) after tdelay;
- elsif cmd = "0001" then
- AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "0010" then
- AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- elsif cmd = "0011" then
- AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd = "0100" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- elsif cmd = "0101" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "0110" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "0111" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
- elsif cmd = "1000" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
- elsif cmd = "1001" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1010" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "1011" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd = "1100" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
- elsif cmd = "1101" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1110" then
- AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "1111" then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when "10" => -- cacheline wrap mode
- if cmd = "0000" then
- AD_Bus <= Mem(memaddr) after tdelay;
- elsif cmd = "0001" then
- AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "0010" then
- AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- elsif cmd = "0011" then
- AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd = "0100" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- elsif cmd = "0101" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "0110" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "0111" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
- elsif cmd = "1000" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
- elsif cmd = "1001" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1010" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "1011" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd = "1100" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
- elsif cmd = "1101" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1110" then
- AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "1111" then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- memaddr := memaddr + 1;
- when "11" => -- reserved mode (disconnect after first data phase)
- if cmd = "0000" then
- AD_Bus <= Mem(memaddr) after tdelay;
- elsif cmd = "0001" then
- AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "0010" then
- AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- elsif cmd = "0011" then
- AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd = "0100" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- elsif cmd = "0101" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "0110" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "0111" then
- AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
- elsif cmd = "1000" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
- elsif cmd = "1001" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1010" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "1011" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd = "1100" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
- elsif cmd = "1101" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1110" then
- AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
- elsif cmd = "1111" then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- when others =>
- null;
- end case;
- elsif CfgRead = '1' then
- -- Master reads from target configuration space
- if cmd = "0000" then
- AD_Bus <= Cfgmem(cfgaddr) after tdelay;
- elsif cmd = "0001" then
- AD_Bus(31 downto 8) <= Cfgmem(cfgaddr)(31 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "0010" then
- AD_Bus(31 downto 16) <= Cfgmem(cfgaddr)(31 downto 16) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
- elsif cmd = "0011" then
- AD_Bus(31 downto 16) <= Cfgmem(cfgaddr)(31 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd = "0100" then
- AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
- AD_Bus(15 downto 0) <= Cfgmem(cfgaddr)(15 downto 0) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- elsif cmd = "0101" then
- AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 16) <= "11111111" after tdelay;
- AD_Bus(15 downto 8) <= Cfgmem(cfgaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "0110" then
- AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
- elsif cmd = "0111" then
- AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
- AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
- elsif cmd = "1000" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 0) <= Cfgmem(cfgaddr)(23 downto 0) after tdelay;
- elsif cmd = "1001" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 8) <= Cfgmem(cfgaddr)(23 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1010" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= Cfgmem(cfgaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 8) <= "11111111" after tdelay;
- AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
- elsif cmd = "1011" then
- AD_Bus(31 downto 24) <= "11111111" after tdelay;
- AD_Bus(23 downto 16) <= Cfgmem(cfgaddr)(23 downto 16) after tdelay;
- AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
- elsif cmd = "1100" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 0) <= Cfgmem(cfgaddr)(15 downto 0) after tdelay;
- elsif cmd = "1101" then
- AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
- AD_Bus(15 downto 8) <= Cfgmem(cfgaddr)(15 downto 8) after tdelay;
- AD_Bus(7 downto 0) <= "11111111" after tdelay;
- elsif cmd = "1110" then
- AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
- AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
- elsif cmd = "1111" then
- report "Target device: Byte Enable word not valid !"
- severity Error;
- end if;
- cfgaddr := cfgaddr + 1;
- end if;
- end if;
- end process;
- ---------------------------------------------------------------------
- -- Implements the wait states process.
- -- Target generates wait states accordingly to wait states parameters
- -- received from master during Special Cycle.
- -- Master reads the parameters from commands file.
- ---------------------------------------------------------------------
- WaitProc : process(CLK,FRAME_N,RST_N)
- variable counter : Integer;
- variable waitcnt : Integer;
- variable start : Boolean;
- begin
- if (Falling_Edge(RST_N) or RST_N = '0') then
- TRDY_N <= 'Z';
- elsif (FRAME_N'Event and FRAME_N = '0') then
- counter := 0;
- start := true;
- TRDY_N <= '1';
- elsif (CLK'Event and CLK = '0') then
- if (Busy = '0' and DevAddr = '0') then -- deselect device
- TRDY_N <= 'H';
- elsif (Busy = '0' and DevAddr = '1') then -- deselect signal
- TRDY_N <= '1';
- end if;
- if (DevAddr = '1' and TrnArnd = '0' and DEVSEL_N = '0') then
- if (counter >= trdy_st and start = true and TRDY_N = '1') then
- -- finish waitstates at start
- TRDY_N <= '0';
- start := false;
- elsif (counter = trdy_loop and TRDY_N = '0') then
- -- random waitstates
- TRDY_N <= '1';
- waits <= '1';
- waitcnt := 1;
- elsif (waitcnt = trdy_nr and waits = '1') then
- -- finish random waitstates
- waits <= '0';
- TRDY_N <= '0';
- elsif waits = '1' then -- count random waitstates
- waitcnt := waitcnt + 1;
- end if;
- end if;
- counter := counter + 1;
- end if;
- end process;
- ---------------------------------------------------------------------
- -- Implements the assertion process for IRDY_N, FRAME_N, and IDSEL
- -- signals.
- ---------------------------------------------------------------------
- AsrtProc : process(CLK,FRAME_N,IRDY_N,IDSEL,AD_Bus)
- variable irdevs : Boolean := false;
- variable idsevs : Boolean := false;
- variable counter : Integer;
- begin
- if Rising_Edge(CLK) and FRAME_N = '0' and IRDY_N = '1' then
- counter := counter + 1;
- if counter >= 8 then
- report"Target device:IRDY is not asserted within 8 clocks from FRAME assertion!"
- severity warning;
- end if;
- end if;
- if AD_Bus'Event then
- assert(CLK'Last_Event <= thold)
- report"Target device: Address or Data hold time violation!"
- severity warning;
- end if;
- if Rising_Edge(CLK) and DevAddr = '1' then
- if irdevs = true then
- irdevs := false;
- assert(IRDY_N'Last_Event >= tsetup)
- report"Target device: IRDY setup time violation in current data transfer!"
- severity warning;
- end if;
- if idsevs = true then
- idsevs := false;
- assert(IDSEL'Last_Event >= tsetup)
- report"Target device: IDSEL setup time violation!"
- severity warning;
- end if;
- if FRAME_N = '0' and IRDY_N = '1' then
- counter := counter + 1 ;
- end if;
- assert (counter <= 8)
- report"Target device: IRDY has not been asserted within 8 clocks from FRAME assertion!"
- severity warning;
- elsif Falling_Edge(FRAME_N) then
- counter := 0;
- elsif Rising_Edge(FRAME_N) then
- assert(CLK'Last_Event <= thold)
- report"Target device: FRAME hold time violation in current data transfer!"
- severity warning;
- elsif Falling_Edge(IRDY_N) and DevAddr = '1' then
- irdevs := true;
- elsif Rising_Edge(IRDY_N) and DevAddr = '1' then
- assert(CLK'Last_Event <= thold)
- report"Target device: IRDY hold time violation in current data transfer!"
- severity warning;
- elsif Rising_Edge(IDSEL) and DevAddr = '1' then
- idsevs := true;
- elsif Falling_Edge(IDSEL) and DevAddr = '1' then
- assert(CLK'Last_Event <= thold)
- report"Target device: IDSEL hold time violation!"
- severity warning;
- end if;
- end process;
-end Behavior; --================ End of architecture ================--
------------------------------------------------------------------------
--- Revision list
--- Version Author Date Changes
---
--- 0.1 Ovidiu Lupas June 09, 2000 New model
------------------------------------------------------------------------
-
Index: trunk/vhdl_behav/PCI.CMD
===================================================================
--- trunk/vhdl_behav/PCI.CMD (revision 9)
+++ trunk/vhdl_behav/PCI.CMD (nonexistent)
@@ -1,59 +0,0 @@
-## CONFIGURE THE FIRST TARGET DEVICE
-## WAIT ADDRESS DATA
-CWAT 00010CF0 0710FF00
-## I/O WRITE DWORD ADDRESS NR. DATA
-WRIO 00000850 01 AABBCCDD
-##
-## I/O READ DWORD ADDRESS NR. DATA
-RDIO 00000850 01 AAXXCCDD
-##
-## I/O WRITE DWORD ADDRESS NR. DATA
-WRIO 00000864 04 AABBCCDD EE00AABB CCDDEE00 AABBCCDD
-##
-## I/O READ DWORD ADDRESS NR. DATA
-RDIO 00000864 04 XXBBXXDD EEXXAABB CCDDXX00 XXBBXXDD
-##
-## CONFIGURE THE SECOND TARGET DEVICE
-## WAIT ADDRESS DATA
-CWAT 00020CF0 0710FF00
-## I/O WRITE DWORD ADDRESS NR. DATA
-WRIO 00001850 01 AABBCCDD
-##
-## I/O READ DWORD ADDRESS NR. DATA
-RDIO 00001850 01 AABBCCDD
-##
-## I/O WRITE DWORD ADDRESS NR. DATA
-WRIO 00001860 03 AABBCCDD EE00AABB CCDDEE00
-##
-## I/O READ DWORD ADDRESS NR. DATA
-RDIO 00001860 03 AABBCCDD EE00AABB CCDDEE00
-##
-## MEMORY WRITE DWORD ADDRESS NR. DATA
-WRSW 00005001 01 55AA66BB
-##
-## MEMORY READ DWORD ADDRESS NR. DATA
-RDSW 00005001 01 55AA66BB
-##
-## MEMORY MULTIPLE WRITE ADDRESS NR. DATA
-WRMW 00005000 02 66AA55BB CCDDBBEE
-##
-## MEMORY MULTIPLE READ ADDRESS NR. DATA
-RDMW 00005000 02 XXAAXXBB CCDDXXEE
-##
-## MEMORY MULTIPLE WRITE ADDRESS NR. DATA
-WRMW 00006010 04 66AA55BB CCDDBBEE 33664455 00000001
-##
-## MEMORY MULTIPLE READ ADDRESS NR. DATA
-RDMW 00006010 04 XXAAXXBB CCDDXXEE 33XX4455 00000001
-##
-## MEMORY READ LINE ADDRESS NR. DATA
-## RDML 00005000 04 00000000 00000000 00000000 00000000
-##
-## CONFIG WRITE DWORD ADDRESS NR. DATA
-WCFG 00010CF8 01 20000001
-##
-## CONFIG READ DWORD ADDRESS NR. DATA
-RCFG 00010CF8 01 20000001
-##
-## EXIT
-ABRT
trunk/vhdl_behav/PCI.CMD
Property changes :
Deleted: svn:executable
## -1 +0,0 ##
-*
\ No newline at end of property
Index: trunk/vhdl_behav/Ms32pci.vhd
===================================================================
--- trunk/vhdl_behav/Ms32pci.vhd (revision 9)
+++ trunk/vhdl_behav/Ms32pci.vhd (nonexistent)
@@ -1,827 +0,0 @@
---===================================================================--
---
--- 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
- end if;
-
- if DEVSEL_N'Last_Event <= tsetup then
- report "DEVSEL_N setup time violation"
- severity Warning;
- end if;
-
- --- inset IRDY_N if loop_irdy =1 and nr_irdy >1
- if loop_irdy =1 then
- while (nr_irdy > 1) loop
- IRDY_N <='1' after tdelay;
- nr_irdy := nr_irdy -1 ;
- wait until FALLING_EDGE(CLK);
- end loop;
- IRDY_N <='0' after tdelay;
- end if;
-
- -- terminate cycle because DEVSEL_N is anactive
- -- (implement command MASTER-ABORT TERMINATION )
- if start_irdy = 0 then -- terminate cycle
- stop := true;
- FRAME_N <='1'; -- after tdelay;
- end if;
-
- -- wait until FALLING_EDGE(CLK);
- -- repeat until all data are read or STOP_N ='0'
- while ((data_number > 0) and (stop = false)) loop -- read cycle
- parity_flag <= true;
- data_number := data_number -1;
- parity_flag <= true;
- data_read := data(data_nr - data_number);
- if data_number = 0 then
- C_BE_Bus(3 downto 0) <=bus_sel(data_nr) after tdelay;
- data_read := data(data_nr);
- else
- C_BE_Bus(3 downto 0) <=bus_sel(data_nr - data_number+1) after tdelay;
- data_read := data(data_nr - data_number);
- end if;
-
- parity_flag <= true;
- if data_number =0 then
- FRAME_N <='1';-- after tdelay;
- end if;
-
- -- 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
- irdy_insert := false;
- end if;
-
- if irdy_insert = true and (data_nr - data_number) = loop_irdy then
- -- insert IRDY ='1' if insert_trdy =true
- while nr_irdy > 1 loop
- nr_irdy := nr_irdy -1 ;
- IRDY_N <= '1' after tdelay; -- insert IRDY
- -- 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
- nr_irdy := 1;
- end if;
- wait until FALLING_EDGE(CLK);
- end loop; -- end loop nr_irdy
- end if; -- end if irdy_insert
-
- -- IRDY_N <= '0' after tdelay;
- if data_number = 0 then
- IRDY_N <= '0' after tdelay;
- end if;
- wait until RISING_EDGE(CLK);
-
- if TRDY_N'Last_Event <= tsetup then -- end of cycle
- report "TRDY_N setup time violation"
- severity Warning;
- end if;
-
- -- wait for TRDY_N = '0' (maxim 8 clock pulse)
- while TRDY_N = '1' and trdy_exit = false loop
- wait until RISING_EDGE(CLK);
- -- wait maxim 8 clock pulse if TRDY is asserted
- trdy_stop := trdy_stop -1;
- if trdy_stop = 0 then
- stop := true;
- report "Target is not responding "
- severity Warning;
- FRAME_N <= '1';-- after tdelay;
- IRDY_N <= '1' after tdelay;
- trdy_exit := true;
- end if;
-
- -- 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
- trdy_exit := true;
- end if;
- end loop; -- end loop TRDY_N=1
-
- Vec2Hex (data_read,str8,Good2);
- report " EXPECTED DATA= "&str8 &""; -- display expected data
-
- Vec2Hex (AD_Bus,str8,Good2);
- report " READ DATA= "&str8 &""; -- display receive data
-
- if AD_Bus'Last_Event <= tsetup then -- end of cycle
- report "AD_BUS setup time violation"
- severity Warning;
- end if;
-
- if ((data_number >0) and (stop =false)) then
- wait until FALLING_EDGE(CLK);
- end if;
-
- wait for thold;
- if AD_Bus'Last_Event <= thold then -- end of cycle
- report "AD_Bus hold time violation"
- severity Warning;
- end if;
- end loop; -- end loop data_number
-
- if RESET =1 or STOP_N ='0' or STOP_N ='L' then
- 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 <= 'H' after tdelay;
- parity_flag <= false;
- end if;
- else
- --------------------------------------------------------------------
- -- BEGIN WRITE CYCLE --
- --------------------------------------------------------------------
- -- adress phase
- parity_flag <= false;
- nr_irdy := nr_irdy;
- 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_read <= 'Z';
- parity(address(31 downto 0), bus_cmd(3 downto 0), parity_temp); -- calculate parity of address cycle
- parity_now <= parity_temp after tdelay;
- wait until FALLING_EDGE(CLK);
- -- end adress phase
-
- REQ_N <='1';
-
- parity_flag <= false;
- IRDY_N <= '0' after tdelay;
- -- wait for 1 ns;
- -- wait for DEVSEL_N = '0'
- -- (implement command MASTER-ABORT TERMINATION if TARGET not respond)
- while ((start_irdy > 0) and (DEVSEL_N ='H' or DEVSEL_N ='Z' or DEVSEL_N ='X') ) loop -- wait for the number of IRDY state
- start_irdy := start_irdy -1; -- from the begining of read cycle
- wait until FALLING_EDGE(CLK);
- end loop;
-
- -- if device not respond then exits the write command
- if start_irdy = 0 then -- terminate cycle
- stop := true;
- FRAME_N <= '1';-- after tdelay;
- end if;
-
- if DEVSEL_N'Last_Event <= tsetup then
- report "DEVSEL_N setup time violation"
- severity Warning;
- end if;
-
- while ((data_number >0) and (stop =false)) loop
- -- data phase
- data_number := data_number -1;
- AD_Bus(31 downto 0) <= data(data_nr - data_number) after tdelay; -- set DATA
- C_BE_Bus(3 downto 0) <= bus_sel(data_nr - data_number) after tdelay; -- set BE#s
- IRDY_N <= '0' after tdelay;
- parity(data(data_nr - data_number), bus_sel(data_nr - data_number), parity_temp); -- calculate parity
- parity_now <= parity_temp after tdelay;
- -- end data phase
-
- if data_number = 0 then
- FRAME_N <= '1';-- after tdelay;
- end if;
-
- -- exit cycle if RST_N,GNT_N or STOP_N are active
- if RESET = 1 or STOP_N= '0' or STOP_N = 'L' then
- stop := true; -- exit cycle
- end if;
-
- wait until RISING_EDGE(CLK);
-
- if TRDY_N'Last_Event <= tsetup then -- end of cycle
- report "TRDY_N setup time violation"
- severity Warning;
- end if;
-
- -- wait for TRDY_N ='0'
- while TRDY_N ='1' and trdy_exit = false loop
- wait until RISING_EDGE(CLK);
- -- wait maxim 8 clock pulse if TRDY is asserted
- trdy_stop := trdy_stop -1;
- if trdy_stop = 0 then
- stop := true;
- report "Target is not responding "
- severity Warning;
- FRAME_N <= '1';-- after tdelay;
- IRDY_N <= '1' after tdelay;
- trdy_exit := true;
- end if;
-
- -- exit cycle if RST_N,GNT_N or STOP_N are active
- if RESET = 1 or STOP_N = '0' or STOP_N = 'L' then
- stop := true; -- exit cycle
- trdy_exit := true;
- end if;
- end loop; -- end loop TRDY=1
-
- if ((data_number > 0) and (stop = false)) then
- wait until FALLING_EDGE(CLK); -- synchronize with PCICLK
- end if;
- -- insert IRDY_N
- if irdy_insert = true and (data_nr -data_number) = loop_irdy
- and data_number >0 and (stop =false) then
- while nr_irdy > 1 loop
- IRDY_N <='1' after tdelay;
- nr_irdy := nr_irdy -1 ;
- if nr_irdy > 0 then
- if data_number > 0 then
- C_BE_Bus(3 downto 0) <=bus_sel(data_nr - data_number +1) after tdelay; -- set BE#s
- parity(data(data_nr - data_number), bus_sel(data_nr - data_number+1), parity_temp); -- calculate parity
- parity_now <= parity_temp after tdelay;
- end if;
- wait until FALLING_EDGE(CLK);
- end if;
-
- if RESET = 1 or STOP_N = '0' or STOP_N = 'L' then
- stop := true; -- exit cycle
- nr_irdy := 1;
- end if;
- end loop; -- end loop nr_irdy
- end if;
- report " WRITE DATA= "&str8 &""; -- display write data
- end loop; -- end loop start_irdy > 0 ...
-
- if RESET = 1 or STOP_N = '0' or STOP_N = 'L' then
- 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 <= 'H' after tdelay;
- parity_flag <= false;
- end if;
- end if; -- end rd_wr = '1'
- end if; -- if RST_N ='0' then
- end READ_WRITE;
- --------------------------------------------------------------------------
- -- Procedure implement instruction WRSW --
- --------------------------------------------------------------------------
- -- Writes single DWORD to memory space!
- procedure WRSW(
- data : in Data_buffer;
- address : inout STD_LOGIC_VECTOR(31 downto 0);
- data_number : in Integer;
- bus_sel : in Data_Enable) is
- variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
- variable str8,str_8 : string(1 to 8);
- variable Good2 : Boolean;
- begin
- bus_cmd := "0111";
- address(1 downto 0) := "00";
- Vec2Hex (data(1),str8,Good2);
- Vec2Hex (address,str_8,Good2);
- report "Write single DWORD to memory space! Address : "&str_8;
- READ_WRITE(address,data,1,bus_cmd,bus_sel,'0');
- end WRSW;
- --------------------------------------------------------------------------
- -- Procedure implement instruction RDSW --
- --------------------------------------------------------------------------
- -- Reads single DWORD from memory space!
- procedure RDSW(
- data : in Data_buffer;
- address : inout STD_LOGIC_VECTOR(31 downto 0);
- data_number : in Integer;
- bus_sel : in Data_Enable) is
- variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
- variable read_data : Data_buffer;
- variable str8,str_8 : string(1 to 8);
- variable Good2 : Boolean;
- begin
- bus_cmd := "0110";
- address(1 downto 0) := "00";
- Vec2Hex (address,str_8,Good2);
- report "Read single DWORD from memory space! Address : "&str_8 ;
- READ_WRITE(address,data,1,bus_cmd,bus_sel,'1');
- end RDSW;
- --------------------------------------------------------------------------
- -- Procedure implements instruction WRMW --
- --------------------------------------------------------------------------
- -- Writes multiple DWORDs to memory space - burst mode
- procedure WRMW(
- data : in Data_buffer;
- address : inout STD_LOGIC_VECTOR(31 downto 0);
- data_number : in Integer;
- bus_sel : in Data_Enable) is
- variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
- variable str8,str_8 : string(1 to 8);
- variable Good2 : Boolean;
- begin
- bus_cmd := "1111";
- address(1 downto 0) := "10";
- Vec2Hex (address,str_8,Good2);
- report "Write multiple DWORDs to memory space! Address : "&str_8 ;
- READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
- end WRMW;
- --------------------------------------------------------------------------
- -- Procedure implements instruction RDMW --
- --------------------------------------------------------------------------
- -- Reads multiple DWORDs from memory space - burst mode
- procedure RDMW(
- data : in Data_buffer;
- address : inout STD_LOGIC_VECTOR(31 downto 0);
- data_number : in Integer;
- bus_sel : in Data_Enable) is
- variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
- variable read_data : Data_buffer;
- variable str8,str_8 : string(1 to 8);
- variable Good2 : Boolean;
- begin
- bus_cmd := "1100";
- address(1 downto 0) := "10";
- Vec2Hex (address,str_8,Good2);
- report "Read multiple DWORDs from memory space! Address : "&str_8;
- READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
- end RDMW;
- --------------------------------------------------------------------------
- -- Procedure implements instruction RDML --
- --------------------------------------------------------------------------
- -- Reads multiple DWORDs from memory space!
- procedure RDML(
- data : in Data_buffer;
- address : inout STD_LOGIC_VECTOR(31 downto 0);
- data_number : in Integer;
- bus_sel : in Data_Enable) is
- variable bus_cmd: STD_LOGIC_VECTOR(3 downto 0);
- variable read_data: Data_buffer;
- variable str8,str_8 : string(1 to 8);
- variable Good2 : Boolean;
- begin
- bus_cmd := "1110";
- address(1 downto 0) := "00";
- Vec2Hex (address,str_8,Good2);
- report "Reads multiple DWORDs from memory space! Address : "&str_8;
- READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
- end RDML;
- --------------------------------------------------------------------------
- -- Procedure implements instruction WCFG --
- --------------------------------------------------------------------------
- -- writes configuration
- procedure WCFG(
- data : in Data_buffer;
- address : inout STD_LOGIC_VECTOR(31 downto 0);
- data_number : in Integer;
- bus_sel : in Data_Enable) is
- variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
- variable read_data : Data_buffer;
- variable str8,str_8 : string(1 to 8);
- variable Good2 : Boolean;
- begin
- bus_cmd :="1011";
- address(1 downto 0) :="00"; -- linear incrementing
- Vec2Hex (address,str_8,Good2);
- report "Configuration write! Address : "&str_8;
- READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
- end WCFG;
- --------------------------------------------------------------------------
- -- Procedure implements instruction RCFG --
- --------------------------------------------------------------------------
- -- reads configuration
- procedure RCFG(
- data : in Data_buffer;
- address : inout STD_LOGIC_VECTOR(31 downto 0);
- data_number : in Integer;
- bus_sel : in Data_Enable) is
- variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
- variable read_data : Data_buffer;
- variable str8,str_8 : string(1 to 8);
- variable Good2 : Boolean;
- begin
- bus_cmd :="1010";
- address(1 downto 0) :="00";
- Vec2Hex (address,str_8,Good2);
- report "Configuration read ! Address : "&str_8;
- READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
- end RCFG;
- --------------------------------------------------------------------------
- -- Procedure implements instruction WRIO --
- --------------------------------------------------------------------------
- -- writes data to IO port
- procedure WRIO(
- data : in Data_buffer;
- address : inout STD_LOGIC_VECTOR(31 downto 0);
- data_number : in Integer;
- bus_sel : in Data_Enable) is
- variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
- variable read_data : Data_buffer;
- variable str8,str_8 : string(1 to 8);
- variable Good2 : Boolean;
- begin
- bus_cmd := "0011";
- address(1 downto 0) := "00";
- Vec2Hex (address,str_8,Good2);
- report "Write DWORD to I/O space! Address : "&str_8;
- READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
- end WRIO;
- --------------------------------------------------------------------------
- -- Procedure implements instruction RDIO --
- --------------------------------------------------------------------------
- -- reads data from IO port
- procedure RDIO(
- data : in Data_buffer;
- address : inout STD_LOGIC_VECTOR(31 downto 0);
- data_number : in Integer;
- bus_sel : in Data_Enable) is
- variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
- variable read_data : Data_buffer;
- variable str8,str_8 : string(1 to 8);
- variable Good2 : Boolean;
- begin
- bus_cmd :="0010";
- address(1 downto 0) :="00";
- Vec2Hex (address,str_8,Good2);
- report "Read DWORD from memory space! Address : "&str_8;
- READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
- end RDIO;
- --------------------------------------------------------------------------
- -- Procedure implements instruction WAIT --
- --------------------------------------------------------------------------
- -- waits
- procedure CWAT(
- data : in Data_buffer;
- address : inout STD_LOGIC_VECTOR(31 downto 0);
- data_number : in Integer;
- bus_sel : in Data_Enable) is
- variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
- variable str8,str_8 : string(1 to 8);
- variable Good2 : Boolean;
- variable byte7_6,byte5,byte4,byte3_2,byte1,byte0 : Integer;
- variable Char7_6,Char5,Char4,Char3_2,Char1,Char0 : Std_Logic_Vector(7 downto 0);
- begin
- Char7_6 := data(1)(31 downto 24);
- irdy_loop := Byte2Int(Char7_6) ;
- Char5 := "0000" & data(1)(23 downto 20);
- irdy_nr := Byte2Int(Char5) + 1;
- Char4 := "0000" & data(1)(19 downto 16);
- irdy_start := Byte2Int(Char4);
- bus_cmd := "0001";
- if irdy_loop = 0 or irdy_nr = 0 then
- irdy_insert := false;
- else
- irdy_insert := true;
- end if;
- READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
- end CWAT;
- --------------------------------------------------------------------------
- -- Procedure implements instruction EXIT --
- --------------------------------------------------------------------------
- -- ends the Master's activity by placing in HighZ all the lines
- procedure ABRT is
- begin
- wait until FALLING_EDGE(CLK); -- synchro cycle
- Init;
- wait;
- end ABRT;
- --------------------------------------------------------------------------
- -- Procedure implements the commands file parser and sequencer --
- --------------------------------------------------------------------------
- procedure Main_case is
- variable Commands : CommandArray(1 to 100);
- variable NumCommands : Natural;
- variable Good : Boolean;
- constant HeaderMsg : String := "Main process:";
- constant MsgSeverity : Severity_Level := Failure;
- variable ErrFlag : Boolean;
- variable PC : Integer;
- begin
- -- Read/Parse the commands file
- FileParser (cmd_file,Commands,NumCommands,ErrFlag);
- data_last_read := FALSE;
- if ErrFlag then
- report HeaderMsg&"Errors found in COMMAND file. Execute halts!!!"
- severity Warning;
- else
- PC := 0;
- wait until RST_N = '1';
- while PC < NumCommands Loop
- if RESET = 1 then
- RESET := 0;
- PC := 0;
- end if;
- while RST_N = '0' loop -- RESET signal is active
- PC := 0; -- if RST_N ='0' restart simulation
- REQ_N <= 'H'; -- request is tri-stated
- wait until Rising_Edge(CLK); -- synchro wait
- end loop;
- if STOP_N = '0' then
- report HeaderMsg&"Wait until signal STOP_N ='0' !";
- wait until STOP_N = '1';
- end if;
- REQ_N <= '0';
-
- PC := PC + 1;
- case Commands(pc).command is
- when "WRSW" =>
- WRSW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
- when "RDSW" =>
- RDSW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
- when "WRMW" =>
- WRMW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
- when "RDMW" =>
- RDMW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
- when "RDML" =>
- RDML(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
- when "WCFG" =>
- WCFG(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
- when "RCFG" =>
- RCFG(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
- when "WRIO" =>
- WRIO(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
- when "RDIO" =>
- RDIO(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
- when "CWAT" =>
- CWAT(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
- when "ABRT" => ABRT;
- when others => null;
- end case;
- end loop;
- end if;
- end Main_Case;
- ---------------------------------------------------------------------
- -- MS32PCI_MAIN : process begins
- ---------------------------------------------------------------------
- begin
- Init;
- Main_case;
- end process;
-end Behavior; --================= End of architecture ===============--
------------------------------------------------------------------------
--- Revision list
--- Version Author Date Changes
---
--- 0.1 Ovidiu Lupas June 09, 2000 New model
------------------------------------------------------------------------
-
Index: trunk/vhdl_behav/Pci_lib.vhd
===================================================================
--- trunk/vhdl_behav/Pci_lib.vhd (revision 9)
+++ trunk/vhdl_behav/Pci_lib.vhd (nonexistent)
@@ -1,793 +0,0 @@
---===================================================================--
---
--- www.OpenCores.Org - June 2000
--- This model adheres to the GNU public license
---
--- Design units : Functions and procedures used in models
---
--- File name : PCI_LIB.vhd
---
--- Purpose : type conversion functions, read commands file
--- procedures
---
--- 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
---===================================================================--
------------------------------------------------------------------------
--- Revision list
--- Version Author Date Changes
---
--- 0.1 Ovidiu Lupas June 09, 2000 New model
------------------------------------------------------------------------
-library IEEE;
-use IEEE.Std_Logic_1164.all;
---
-package Simulation is
--- Definition of the CommandType record array which is used to record
--- the commands from the .cmd file
- type Data_buffer is array(1 to 256) of Std_Logic_Vector(31 downto 0);
- type Data_Enable is array(1 to 256) of Std_Logic_Vector(3 downto 0);
-
- type CommandType is
- record
- command : string(1 to 4);
- addr : Std_Logic_Vector(31 downto 0);
- data : Data_buffer;
- data_nr : Integer;
- enable : Data_Enable;
- end record;
--- Definition of the CommandArray type type which can be used for
--- the commands present in .cmd file
- type CommandArray is array(positive range <>) of CommandType;
-end Simulation; --========== End of package Simulation =============--
---
-library IEEE,STD,work;
-library work;
-use work.Simulation.all;
-use IEEE.Std_Logic_1164.all;
-use STD.textio.all;
---
-package PCI_Def is
- --------------------------------------------------------------------
- -- convert a character to a value from 0 to 15
- --------------------------------------------------------------------
- function digit_value(
- C : Character)
- return integer;
- --------------------------------------------------------------------
- -- Converts unsigned Std_LOGIC_Vector to Integer, leftmost bit is MSB
- -- Error message for unknowns (U, X, W, Z, -), converted to 0
- -- Verifies whether vector is too long (> 16 bits)
- --------------------------------------------------------------------
- function Vec2Int (
- Invector : in Std_Logic_Vector(15 downto 0))
- return Integer;
- --------------------------------------------------------------------
- -- Converts unsigned Std_Logic_Vector to Integer, leftmost bit is MSB
- -- Error message for unknowns (U, X, W, Z, -), converted to 0
- -- Verifies whether vector is too long (> 16 bits)
- --------------------------------------------------------------------
- function Byte2Int (
- Invector : in Std_Logic_Vector(7 downto 0))
- return Integer;
- --------------------------------------------------------------------
- -- Converts unsigned Std_Logic_Vector to Integer, leftmost bit is MSB
- -- Error message for unknowns (U, X, W, Z, -), converted to 0
- -- Verifies whether vector is too long (> 16 bits)
- --------------------------------------------------------------------
- procedure Hex2Bit (
- C : in Character;
- Vector : out Std_Logic_Vector(3 downto 0);
- Good : out Boolean);
- --------------------------------------------------------------------
- -- Converts Hex characters to binary representation
- -- Asserts that no unknown value exists at the time of conversion.
- --------------------------------------------------------------------
- procedure Bit2Hex (
- Vector : in Std_Logic_Vector(3 downto 0);
- C : out Character;
- Good : out Boolean);
- --------------------------------------------------------------------
- -- Converts bit_vector into a hex string
- -- Asserts that no unknown value exists at the time of conversion.
- --------------------------------------------------------------------
- procedure Vec2Hex (
- Value : in Std_Logic_Vector(31 downto 0);
- result : out String(1 to 8);
- Good : out Boolean);
- --------------------------------------------------------------------
- -- read a number from the line
- -- use this if you have hex numbers that are not in VHDL pound-sign format
- --------------------------------------------------------------------
- procedure Read (
- L : inout Line;
- value : out Integer;
- radix : in Positive);
- --------------------------------------------------------------------
- -- reads a hex value and returns a bit_vector value
- --------------------------------------------------------------------
- procedure ReadHex (
- L : inout Line;
- Value : out Std_Logic_Vector;
- Good : out Boolean;
- Enable: out Std_Logic_Vector);
- --------------------------------------------------------------------
- -- Implements the parsing of the cmd file, which specifies the tasks
- -- that are applied to the processor.
- --------------------------------------------------------------------
- procedure FileParser (
- constant file_name : in String;
- variable Commands : inout CommandArray;
- variable NumCommands : out Natural;
- variable ErrFlag : inout Boolean);
-end PCI_Def; --============== End of package header =================--
---
-library IEEE;
-use IEEE.Std_Logic_1164.all;
-library std;
-use std.textio.all;
---
-package body PCI_Def is
- --------------------------------------------------------------------
- -- convert a character to a value from 0 to 15
- --------------------------------------------------------------------
- function digit_value (
- C : Character)
- return integer is
- constant not_digit : integer := -999;
- begin
- if (C ='X') and (C ='x') then
- return 15;
- end if;
- if (C >= '0') and (C <= '9') then
- return (Character'pos(C) - Character'pos('0'));
- elsif (C >= 'a') and (C <= 'f') then
- return (character'pos(c) - character'pos('a') + 10);
- elsif (C >= 'A') and (C <= 'F') then
- return (character'pos(c) - character'pos('A') + 10);
- else
- return not_digit;
- end if;
- end digit_value;
- --------------------------------------------------------------------
- --------------------------------------------------------------------
- function Vec2Int (
- InVector : in Std_Logic_Vector(15 downto 0))
- return Integer is
- constant HeaderMsg : String := "To_Integer:";
- constant MsgSeverity : Severity_Level := Warning;
- variable Value : Integer := 0;
- begin
- if InVector = "UUUUUUUUUUUUUUUU" then
- report HeaderMsg&"The input vector is of type 'U'. Converted to 0"
- severity MsgSeverity;
- elsif InVector = "XXXXXXXXXXXXXXXX" then
- report HeaderMsg&"The input vector is of type 'X'. Converted to 0"
- severity MsgSeverity;
- elsif InVector = "WWWWWWWWWWWWWWWW" then
- report HeaderMsg&"The input vector is of type 'W'. Converted to 0"
- severity MsgSeverity;
- elsif InVector = "ZZZZZZZZZZZZZZZZ" then
- report HeaderMsg&"The input vector is of type 'Z'. Converted to 0"
- severity MsgSeverity;
- else
- for i in 0 to 15 loop
- if (InVector(i) = '1') then
- Value := Value + (2**I);
- end if;
- end loop;
- end if;
- return Value;
- end Vec2Int;
- --------------------------------------------------------------------
- --------------------------------------------------------------------
- function Byte2Int (
- InVector : in Std_Logic_Vector(7 downto 0))
- return Integer is
- constant HeaderMsg : String := "To_Integer:";
- constant MsgSeverity : Severity_Level := Warning;
- variable Value : Integer := 0;
- begin
- for i in 0 to 7 loop
- if (InVector(i) = '1') then
- Value := Value + (2**I);
- end if;
- end loop;
- return Value;
- end Byte2Int;
- --------------------------------------------------------------------
- --------------------------------------------------------------------
- procedure Hex2Bit (
- C : in Character;
- Vector : out Std_Logic_Vector(3 downto 0);
- Good : out Boolean) is
- variable Good1 : Boolean := false;
- constant HeaderMsg : String := "Hex2Bit:";
- constant MsgSeverity : Severity_Level := Error;
- begin
- Good := false;
- case C is
- when '0' => Vector := "0000"; Good1 := true;
- when '1' => Vector := "0001"; Good1 := true;
- when '2' => Vector := "0010"; Good1 := true;
- when '3' => Vector := "0011"; Good1 := true;
- when '4' => Vector := "0100"; Good1 := true;
- when '5' => Vector := "0101"; Good1 := true;
- when '6' => Vector := "0110"; Good1 := true;
- when '7' => Vector := "0111"; Good1 := true;
- when '8' => Vector := "1000"; Good1 := true;
- when '9' => Vector := "1001"; Good1 := true;
- when 'A'|'a' => Vector := "1010"; Good1 := true;
- when 'B'|'b' => Vector := "1011"; Good1 := true;
- when 'C'|'c' => Vector := "1100"; Good1 := true;
- when 'D'|'d' => Vector := "1101"; Good1 := true;
- when 'E'|'e' => Vector := "1110"; Good1 := true;
- when 'F'|'f' => Vector := "1111"; Good1 := true;
- -- extended for std_LOGIC --
- when 'U'|'u' => Vector := "UUUU"; Good1 := true;
- when 'X'|'x' => Vector := "1111"; Good1 := true;
- when 'Z'|'z' => Vector := "ZZZZ"; Good1 := true;
- when 'W'|'w' => Vector := "WWWW"; Good1 := true;
- when 'L'|'l' => Vector := "LLLL"; Good1 := true;
- when 'H'|'h' => Vector := "HHHH"; Good1 := true;
- when '-' => Vector := "----"; Good1 := true;
- when others => Good1 := false;
- end case;
- if not Good1 then
- Vector := "0000";
- report HeaderMsg&"Expected a Hex character (0-F)"
- severity MsgSeverity;
- end if;
- Good := Good1;
- end Hex2Bit;
- --------------------------------------------------------------------
- --------------------------------------------------------------------
- procedure Bit2Hex (
- Vector : Std_Logic_Vector(3 downto 0);
- C : out Character;
- Good : out Boolean) is
- variable Good1 : Boolean := false;
- constant HeaderMsg : String := "Bit2Hex: ";
- constant MsgSeverity : Severity_Level := Error;
- begin
- Good := false;
- case Vector is
- when x"0" => C := '0'; Good1 := true;
- when x"1" => C := '1'; Good1 := true;
- when x"2" => C := '2'; Good1 := true;
- when x"3" => C := '3'; Good1 := true;
- when x"4" => C := '4'; Good1 := true;
- when x"5" => C := '5'; Good1 := true;
- when x"6" => C := '6'; Good1 := true;
- when x"7" => C := '7'; Good1 := true;
- when x"8" => C := '8'; Good1 := true;
- when x"9" => C := '9'; Good1 := true;
- when x"A" => C := 'A'; Good1 := true;
- when x"B" => C := 'B'; Good1 := true;
- when x"C" => C := 'C'; Good1 := true;
- when x"D" => C := 'D'; Good1 := true;
- when x"E" => C := 'E'; Good1 := true;
- when x"F" => C := 'F'; Good1 := true;
- when "ZZZZ" => C := 'Z'; Good1 := true;
- when others => Good1 := false;
- end case;
- if not Good1 then
- C := '0';
- report HeaderMsg&"Expected a Hex character (0-F)"
- severity MsgSeverity;
- end if;
- Good := Good1;
- end Bit2Hex;
- --------------------------------------------------------------------
- --------------------------------------------------------------------
- procedure Vec2Hex (
- Value : in Std_Logic_Vector(31 downto 0);
- Result : out String(1 to 8);
- GOOD : out BOOLEAN) is
- variable OK : Boolean;
- variable C : Character;
- constant NE : Integer := value'length/4; -- number of Hex chars
- variable BV : Std_Logic_Vector(value'length-1 downto 0) := Value;
- variable Res : String(1 to 8);
- constant HeaderMsg : String := "Vec2Hex: ";
- constant MsgSeverity : Severity_Level := Error;
- begin
- if Value'length mod 4 /= 0 then -- Testing if Vector is mod 4
- Good := false;
- report HeaderMsg&"The length of input vector is not modulo 4!"
- severity MsgSeverity;
- return;
- end if;
- Bit2Hex(BV(3 downto 0), C, OK); -- Conversion of the 4 LSB bits
- if not OK then
- Good := false;
- return;
- end if;
- Res := C & Res(2 to NE); -- Places first Char in Result
- for i in 1 to NE-1 loop
- Bit2Hex(BV(4*i+3 downto 4*i), C, OK); -- Converts next Char
- if not OK then
- Good := false;
- return;
- end if;
- Res := Res(1 to i) & C & Res(i+2 to NE);
- end loop;
- for i in 0 to NE-1 loop
- Result (1+i) := Res (NE-i);
- end loop;
- Good := true;
- end Vec2Hex;
- --------------------------------------------------------------------
- --------------------------------------------------------------------
- procedure Read (
- L : inout line;
- Value : out integer;
- Radix : in positive) is
- constant not_digit : integer := -999;
- variable Digit : integer;
- variable Result : integer := 0;
- variable Pos : integer;
- begin
- -- calculate the value
- if (L'length <=0 ) then
- for i in Pos to L'right loop
- digit := digit_value(L(i));
- exit when (Digit = not_digit) or (digit >= radix);
- Result := Result * Radix + digit;
- Pos := Pos + 1;
- end loop;
- Value := Result;
- end if;
- end Read;
- --------------------------------------------------------------------
- --------------------------------------------------------------------
- procedure ReadHex (
- L : inout Line;
- Value : out Std_Logic_Vector;
- Good : out Boolean;
- Enable : out Std_Logic_Vector) is
- variable OK : Boolean;
- variable C : Character;
- constant NE : Integer := value'length/4;
- variable BV : Std_Logic_Vector(value'length-1 downto 0);
- variable TEMP : Std_Logic_Vector(value'length-1 downto 0);
- variable S : String(1 to NE-1);
- constant HeaderMsg : String := "Vec2Hex";
- constant MsgSeverity : Severity_Level := Warning;
- begin
- Enable(3 downto 0) :="0000";
- if Value'length mod 4 /= 0 then -- Testing if Vector is mod 4
- Good := false;
- report HeaderMsg&"The length of input vector is not modulo 4!"
- severity MsgSeverity;
- return;
- end if;
- loop
- read(L, C, OK); -- Finds the first Hex Char
- exit when (((C /= ' ') and (C /= CR) and (C /= HT)) or
- (L'length = 0));
- end loop;
- Hex2Bit(C, BV( 3 downto 0), OK); -- Converts first Hex Char to 4 Bits
- if C ='X' or C ='x' then
- Enable(3) :='1';
- end if;
-
- if not OK then
- Good := false;
- return;
- end if;
- read(L, S, OK); -- Reads the next three Hex Chars
- if not OK then
- Good := false;
- return;
- end if;
- for i in 1 to NE-1 loop
- if s(i) ='X' or s(i) ='x' then
- if i=1 then
- Enable(3):='1';
- end if;
- if i=2 or i=3 then
- Enable(2):='1';
- end if;
- if i=4 or i=5 then
- Enable(1):='1';
- end if;
- if i=6 or i=7 then
- Enable(0):='1';
- end if;
- end if;
- Hex2Bit(s(i), BV(4*i+3 downto 4*i), OK); -- Converts to BitVector
- if not OK then
- Good := false;
- return;
- end if;
- end loop;
- Good := true;
-
- -- for byte
- if (value'length = 8 ) then
- for i in 0 to 3 loop
- TEMP(i) := BV(value'length-4+i);
- end loop;
- for i in 0 to 3 loop
- TEMP(i+4) := BV(value'length-8+i);
- end loop;
- end if;
-
- -- for word
- if (value'length = 16 ) then
- for i in 0 to 3 loop
- TEMP(i) := BV(value'length-4+i);
- end loop;
- for i in 0 to 3 loop
- TEMP(i+4) := BV(value'length-8+i);
- end loop;
- for i in 0 to 3 loop
- TEMP(i+8) := BV(value'length-12+i);
- end loop;
- for i in 0 to 3 loop
- TEMP(i+12) := BV(value'length-16+i);
- end loop;
- end if;
-
- -- for DWORD
- if (value'length =32 ) then
- for i in 0 to 3 loop
- TEMP(i) := BV(value'length-4+i);
- end loop;
- for i in 0 to 3 loop
- TEMP(i+4) := BV(value'length-8+i);
- end loop;
- for i in 0 to 3 loop
- TEMP(i+8) := BV(value'length-12+i);
- end loop;
- for i in 0 to 3 loop
- TEMP(i+12) := BV(value'length-16+i);
- end loop;
- for i in 0 to 3 loop
- TEMP(i+16) := BV(value'length-20+i);
- end loop;
- for i in 0 to 3 loop
- TEMP(i+20) := BV(value'length-24+i);
- end loop;
- for i in 0 to 3 loop
- TEMP(i+24) := BV(value'length-28+i);
- end loop;
- for i in 0 to 3 loop
- TEMP(i+28) := BV(value'length-32+i);
- end loop;
- end if;
-
- Value := TEMP;
- end ReadHex;
- --------------------------------------------------------------------
- --------------------------------------------------------------------
- procedure FileParser (
- constant file_name : in String ;
- variable Commands : inout CommandArray;
- variable NumCommands : out Natural;
- variable ErrFlag : inout Boolean) is
- File CmdFile : text;
- constant HeaderMsg : String := "FileParser:";
- constant MsgSeverity : Severity_Level := Error;
- variable L : Line := NULL;
- variable Linenum : Natural := 0;
- variable LblNum : Natural := 0;
- variable CmdNum : Natural := 0;
- variable EndOfFile : Boolean := false;
- variable Good : Boolean := false;
- variable Int : Integer;
- variable Tm : Time;
- variable C : Character;
- variable Addr : Std_Logic_Vector(31 downto 0);
- variable Data : Std_Logic_Vector(31 downto 0);
- variable Enable : Std_Logic_Vector(3 downto 0);
- variable Vect_count : Std_Logic_Vector(7 downto 0);
- variable Data_word : Std_Logic_Vector(15 downto 0);
- variable Data_byte : Std_Logic_Vector(7 downto 0);
- variable str4 : string(1 to 4);
- variable count_nr : Integer;
- variable count : Integer;
- begin
- ErrFlag := false;
- FILE_OPEN(CmdFile,file_name,READ_MODE);
- loop
- readline(CmdFile,L);
- EndOfFile := endfile(CmdFile);
- CmdNum := CmdNum + 1;
- LineNum := LineNum + 1;
- read(L, str4, Good);
- if not Good then
- CmdNum := CmdNum-1;
- else
- case str4 is
- when "WRSW" => -- write single word command
- readhex(L,Addr,Good,Enable);
- if not Good then
- report HeaderMsg&"Invalid WRSW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
- severity MsgSeverity;
- ErrFlag := true;
- else
- Good := true;
- readhex(L,Data_byte,Good,Enable);
- count_nr := Byte2Int(Data_Byte);
- count := 0;
- for I in 0 to count_nr-1 loop
- readhex(L,Data,Good,Enable);
- if (Good =true) then
- count := count + 1;
- commands(CmdNum).command := "WRSW";
- commands(CmdNum).addr := Addr;
- commands(CmdNum).data(count) := Data;
- commands(CmdNum).data_nr := count_nr;
- commands(CmdNum).enable(count) := Enable;
- else
- report HeaderMsg&"Invalid DATA in WRSW command ";
- end if;
- end loop;
- end if;
-
- when "RDSW" => -- read single word command
- readhex(L,Addr,Good,Enable);
- if not Good then
- report HeaderMsg&"Invalid RDSW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
- severity MsgSeverity;
- ErrFlag := true;
- else
- Good := true;
- readhex(L,Data_byte,Good,Enable);
- count_nr :=Byte2Int(Data_Byte);
- count := 0;
- for I in 0 to count_nr-1 loop
- readhex(L,Data,Good,Enable);
- if (Good =true) then
- count := count + 1;
- commands(CmdNum).command := "RDSW";
- commands(CmdNum).addr := Addr;
- commands(CmdNum).data(count) := Data;
- commands(CmdNum).data_nr := count_nr;
- commands(CmdNum).enable(count) := Enable;
- else
- report HeaderMsg&"Invalid DATA in RDSW command ";
- end if;
- end loop;
- end if;
-
- when "WRMW" => -- write multiple words command
- readhex(L,Addr,Good,Enable);
- if not Good then
- report HeaderMsg&"Invalid WRMW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
- severity MsgSeverity;
- ErrFlag := true;
- else
- Good := true;
- readhex(L,Data_byte,Good,Enable);
- count_nr :=Byte2Int(Data_Byte);
- count := 0;
- for I in 0 to count_nr-1 loop
- readhex(L,Data,Good,Enable);
- if (Good =true) then
- count := count + 1;
- commands(CmdNum).command := "WRMW";
- commands(CmdNum).addr := Addr;
- commands(CmdNum).data(count) := Data;
- commands(CmdNum).data_nr := count_nr;
- commands(CmdNum).enable(count) := Enable;
- else
- report HeaderMsg&"Invalid DATA in WRMW command ";
- end if;
- end loop;
- end if;
-
- when "RDMW" => -- read multiple words command
- readhex(L,Addr,Good,Enable);
- if not Good then
- report HeaderMsg&"Invalid RDMW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
- severity MsgSeverity;
- ErrFlag := true;
- else
- Good := true;
- readhex(L,Data_Byte,Good,Enable);
- count_nr :=Byte2Int(Data_Byte);
- count := 0;
- for I in 0 to count_nr-1 loop
- readhex(L,Data,Good,Enable);
- if (Good =true) then
- count := count + 1;
- commands(CmdNum).command := "RDMW";
- commands(CmdNum).addr := Addr;
- commands(CmdNum).data(count) := Data;
- commands(CmdNum).data_nr := count_nr;
- commands(CmdNum).enable(count) := Enable;
- else
- report HeaderMsg&"Invalid DATA in RDMW command ";
- end if;
- end loop;
- end if;
-
- when "RDML" => -- read multiple words command
- readhex(L,Addr,Good,Enable);
- if not Good then
- report HeaderMsg&"Invalid RDML command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
- severity MsgSeverity;
- ErrFlag := true;
- else
- Good := true;
- readhex(L,Data_Byte,Good,Enable);
- count_nr :=Byte2Int(Data_Byte);
- count := 0;
- for I in 0 to count_nr-1 loop
- readhex(L,Data,Good,Enable);
- if (Good =true) then
- count := count + 1;
- commands(CmdNum).command := "RDML";
- commands(CmdNum).addr := Addr;
- commands(CmdNum).data(count) := Data;
- commands(CmdNum).data_nr := count_nr;
- commands(CmdNum).enable(count) := Enable;
- else
- report HeaderMsg&"Invalid DATA in RDML command ";
- end if;
- end loop;
- end if;
-
- when "WCFG" => -- write to configuration space command
- readhex(L,Addr,Good,Enable);
- if not Good then
- report HeaderMsg&"Invalid WCFG command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
- severity MsgSeverity;
- ErrFlag := true;
- else
- Good := true;
- readhex(L,Data_byte,Good,Enable);
- count_nr :=Byte2Int(Data_Byte);
- count := 0;
- for I in 0 to count_nr-1 loop
- readhex(L,Data,Good,Enable);
- if (Good =true) then
- count := count + 1;
- commands(CmdNum).command := "WCFG";
- commands(CmdNum).addr := Addr;
- commands(CmdNum).data(count) := Data;
- commands(CmdNum).data_nr := count_nr;
- commands(CmdNum).enable(count) := Enable;
- else
- report HeaderMsg&"Invalid DATA in WCFG command ";
- end if;
- end loop;
- end if;
-
- when "RCFG" => -- read from configuration space command
- readhex(L,Addr,Good,Enable);
- if not Good then
- report HeaderMsg&"Invalid RCFG command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
- severity MsgSeverity;
- ErrFlag := true;
- else
- Good := true;
- readhex(L,Data_Byte,Good,Enable);
- count_nr :=Byte2Int(Data_Byte);
- count := 0;
- for I in 0 to count_nr-1 loop
- readhex(L,Data,Good,Enable);
- if (Good =true) then
- count := count + 1;
- commands(CmdNum).command := "RCFG";
- commands(CmdNum).addr := Addr;
- commands(CmdNum).data(count) := Data;
- commands(CmdNum).data_nr := count_nr;
- commands(CmdNum).enable(count) := Enable;
- else
- report HeaderMsg&"Invalid DATA in RCFG command ";
- end if;
- end loop;
- end if;
-
- when "WRIO" => -- write to I/O space command
- readhex(L,Addr,Good,Enable);
- if not Good then
- report HeaderMsg&"Invalid WRIO command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
- severity MsgSeverity;
- ErrFlag := true;
- else
- Good := true;
- readhex(L,Data_byte,Good,Enable);
- count_nr :=Byte2Int(Data_Byte);
- count := 0;
- for I in 0 to count_nr-1 loop
- readhex(L,Data,Good,Enable);
- if (Good = true) then
- count := count + 1;
- commands(CmdNum).command := "WRIO";
- commands(CmdNum).addr := Addr;
- commands(CmdNum).data(count) := Data;
- commands(CmdNum).data_nr := count_nr;
- commands(CmdNum).enable(count) := Enable;
- else
- report HeaderMsg&"Invalid DATA in WRIO command ";
- end if;
- end loop;
- end if;
-
- when "RDIO" => -- read from I/O space command
- readhex(L,Addr,Good,Enable);
- if not Good then
- report HeaderMsg&"Invalid RDIO command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
- severity MsgSeverity;
- ErrFlag := true;
- else
- Good := true;
- readhex(L,Data_Byte,Good,Enable);
- count_nr :=Byte2Int(Data_Byte);
- count := 0;
- for I in 0 to count_nr-1 loop
- readhex(L,Data,Good,Enable);
- if (Good = true) then
- count := count + 1;
- commands(CmdNum).command := "RDIO";
- commands(CmdNum).addr := Addr;
- commands(CmdNum).data(count) := Data;
- commands(CmdNum).data_nr := count_nr;
- commands(CmdNum).enable(count) := Enable;
- else
- report HeaderMsg&"Invalid DATA in RDIO command ";
- end if;
- end loop;
- end if;
-
- when "CWAT" =>
- readhex(L,Addr,Good,Enable);
- if not Good then
- report HeaderMsg&"Invalid CWAT command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
- severity MsgSeverity;
- ErrFlag := true;
- else
- count_nr :=0;
- readhex(L,Data,Good,Enable);
- if (Good = true) then
- count :=count +1;
- commands(CmdNum).command := "WAIT";
- commands(CmdNum).addr := Addr;
- commands(CmdNum).data(1) := Data;
- commands(CmdNum).data_nr := 1;
- commands(CmdNum).enable(1) := Enable;
- else
- report HeaderMsg&"Invalid DATA in CWAT command ";
- end if;
- end if;
-
- when "ABRT" =>
- count :=count + 1;
- commands(CmdNum).command := "ABRT";
- commands(CmdNum).addr := "00000000000000000000000000000000";
- commands(CmdNum).data(1) := "00000000000000000000000000000000";
- commands(CmdNum).data_nr := 1;
- commands(CmdNum).enable(1) := Enable;
-
- when others =>
- CmdNum := CmdNum -1;
- if str4(1 to 2)/= "##" then
- report HeaderMsg & "Invalid command in file: "&file_name&", line #"& integer'image(LineNum) &", "& "Unknown command : "& str4 & l(l'left to l'right)
- severity error;
- ErrFlag := true;
- end if;
- end case;
- end if;
- NumCommands := CmdNum;
- Exit when EndOfFile;
- end loop;
- end FileParser;
- --------------------------------------------------------------------
- --------------------------------------------------------------------
-end PCI_Def; --================ End of package body ================--
Index: trunk/vhdl_behav/Test_pci.vhd
===================================================================
--- trunk/vhdl_behav/Test_pci.vhd (revision 9)
+++ trunk/vhdl_behav/Test_pci.vhd (nonexistent)
@@ -1,226 +0,0 @@
---===================================================================--
---
--- www.OpenCores.Org - January 2000
--- This model adheres to the GNU public license
---
--- Design units : TestBench for PCI devices.
---
--- File name : Test_PCI.vhd
---
--- Purpose : Implements the test bench for PCI 33 MHz, 32 bit devices.
--- It is included one master device and two target devices.
---
--- There can be used more than one target devices in a
--- design, every device being identified by the three
--- base addresses in generic.
---
---
--- Library : PCI_Lib
---
--- Dependencies : IEEE.Std_Logic_1164
---
--- Limitations : None known
---
--- Errors : None known
---
--- Author : Ovidiu Lupas
--- olupas@opencores.org
---
--- Simulator : ModelSim EE version 5.2 on a Windows95 PC
--- ActiveVHDL 3.1 on a Windows95 PC
---===================================================================--
------------------------------------------------------------------------
--- Entity for PCI bus Arbiter and CLK generator
------------------------------------------------------------------------
-library ieee,work;
- use ieee.Std_Logic_1164.all;
- use work.Simulation.all;
- use work.PCI_Def.all;
------------------------------------------------------------------------
------------------------------------------------------------------------
-entity ClkGen is
- generic ( tperiod : Time := 30 ns );
- port (
- REQ_N : in Std_Logic;
- GNT_N : out Std_Logic := '1';
- RST_N : out Std_Logic;
- CLK : out Std_Logic); -- System clock
-end ClkGen; --=================== End of entity =====================--
---========================== Architecture ===========================--
-architecture BEHAV_ClkGen of ClkGen is
-begin--======================== Architecture =================================--
- ---------------------------------------------------------------------
- -- Provide the external clock signal to the processor
- ---------------------------------------------------------------------
- ClkDriver : process
- variable clktmp: std_logic := '0';
- begin
- CLK <= clktmp;
- clktmp := not clktmp;
- wait for tperiod/2;
- end process ClkDriver;
- ---------------------------------------------------------------------
- -- Simulates an external PCI-bus arbiter, which always grants the
- -- access to the bus :)
- ---------------------------------------------------------------------
- Arbiter : process(REQ_N)
- begin
- if Falling_Edge(REQ_N) then
- GNT_N <= '0' after 10 ns;
- elsif Rising_Edge(REQ_N) then
- GNT_N <= '1' after 10 ns;
- end if;
- end process Arbiter;
- ---------------------------------------------------------------------
- -- Provides the reset signal
- ---------------------------------------------------------------------
- RstGen: process
- begin
- RST_N <= '0';
- wait for 100 ns;
- RST_N <= '1';
- wait for 400 ns;
- end process;
-end BEHAV_ClkGen; --============== End of architecture ==============--
------------------------------------------------------------------------
--- TestBench
------------------------------------------------------------------------
-library ieee,work,std;
- use ieee.std_logic_1164.all;
- use work.ClkGen;
------------------------------------------------------------------------
------------------------------------------------------------------------
-entity TESTPCI is
-end TESTPCI;
---========================== Architecture ===========================--
-architecture stimulus of TESTPCI is
- ---------------------------------------------------------------------
- -- Signal declaration
- ---------------------------------------------------------------------
- signal AD_Bus : Std_Logic_Vector (31 downto 0);
- signal C_BE_Bus : Std_Logic_Vector (3 downto 0);
- signal PAR : Std_Logic;
- signal FRAME_N : Std_Logic;
- signal TRDY_N : Std_Logic;
- signal IRDY_N : Std_Logic;
- signal STOP_N : Std_Logic;
- signal DEVSEL_N : Std_Logic;
- signal IDSEL : Std_Logic;
- signal SEL1 : Std_Logic;
- signal SEL2 : Std_Logic;
- signal PERR_N : Std_Logic;
- signal SERR_N : Std_Logic;
- signal REQ_N : Std_Logic;
- signal GNT_N : Std_Logic;
- signal CLK : Std_Logic;
- signal RST_N : Std_Logic;
- ---------------------------------------------------------------------
- -- Component declarations
- ---------------------------------------------------------------------
- component ClkGen
- generic ( tperiod : Time := 30 ns );
- port (
- REQ_N : in Std_Logic;
- GNT_N : out Std_Logic;
- RST_N : out Std_Logic;
- CLK : out Std_Logic); -- System clock
- end component;
- ---------------------------------------------------------------------
- ---------------------------------------------------------------------
- component MS32PCI
- generic (
- cmd_file : string(1 to 7);
- tdelay : Time;
- tsetup : Time;
- thold : Time);
- 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; -- in
- -- 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; -- in
- -- System signals (2)
- CLK : in STD_LOGIC;
- RST_N : in STD_LOGIC); --in
- end component;
- ---------------------------------------------------------------------
- ---------------------------------------------------------------------
- component TG32PCI
- generic (
- devtype : string(1 to 4);
- tdelay : Time;
- tsetup : Time;
- thold : Time;
- bamem : Std_Logic_Vector(31 downto 0); -- hex value
- baio : Std_Logic_Vector(31 downto 0); -- hex value
- bacfg : Std_Logic_Vector(31 downto 0));-- hex value
- port (
- -- Address, Data and Command buses (37)
- AD_Bus : inout Std_Logic_Vector (31 downto 0);
- C_BE_Bus : in Std_Logic_Vector (3 downto 0);
- PAR : inout Std_Logic;
- -- Interface control signals (6)
- FRAME_N : in Std_Logic;
- TRDY_N : inout Std_Logic;
- IRDY_N : in Std_Logic;
- STOP_N : out Std_Logic;
- DEVSEL_N : inout Std_Logic;
- IDSEL : in Std_Logic;
- -- Error reporting signals (2)
- PERR_N : inout Std_Logic;
- SERR_N : inout Std_Logic;
- -- System signals (2)
- CLK : in Std_Logic;
- RST_N : in Std_Logic);
- end component;
-begin --====================== Architecture =========================--
- ---------------------------------------------------------------------
- -- Component instantiation
- ---------------------------------------------------------------------
- UUT1: MS32PCI
- generic map (
- "PCI.CMD",0 ns, 7 ns, 5 ns)
- port map (
- AD_Bus,C_BE_Bus,PAR,FRAME_N,TRDY_N,IRDY_N,STOP_N,DEVSEL_N,
- IDSEL,PERR_N,SERR_N,REQ_N,GNT_N,CLK,RST_N);
- SEL1 <= AD_Bus(16);
- UUT2: TG32PCI
- generic map (
- "Fast",0 ns,0 ns,0 ns,x"00005000",x"00000800",x"00010CF0")
- port map (
- AD_Bus => AD_Bus,C_BE_Bus => C_BE_Bus,PAR => PAR,
- FRAME_N => FRAME_N,TRDY_N => TRDY_N,IRDY_N => IRDY_N,
- STOP_N => STOP_N,DEVSEL_N => DEVSEL_N,IDSEL => SEL1,
- PERR_N => PERR_N,SERR_N => SERR_N,CLK => CLK,RST_N => RST_N);
- SEL2 <= AD_Bus(17);
- UUT3: TG32PCI
- generic map (
- "Medi",0 ns,7 ns,0 ns,x"00006000",x"00001800",x"00020CF0")
- port map (
- AD_Bus => AD_Bus,C_BE_Bus => C_BE_Bus,PAR => PAR,
- FRAME_N => FRAME_N,TRDY_N => TRDY_N,IRDY_N => IRDY_N,
- STOP_N => STOP_N,DEVSEL_N => DEVSEL_N,IDSEL => SEL2,
- PERR_N => PERR_N,SERR_N => SERR_N,CLK => CLK,RST_N => RST_N);
- GEN: ClkGen port map (
- REQ_N,GNT_N,RST_N,CLK);
- ---------------------------------------------------------------------
-end stimulus; --=============== End of architecture =================--
------------------------------------------------------------------------
--- Revision list
--- Version Author Date Changes
---
--- 0.1 Ovidiu Lupas June 09, 2000 New model
------------------------------------------------------------------------
-
Index: trunk/diagrams/pci.dia
===================================================================
--- trunk/diagrams/pci.dia (revision 9)
+++ trunk/diagrams/pci.dia (nonexistent)
@@ -1,64 +0,0 @@
-VGUIformatVersion 1.004000
-
-
-
-
-DEFINE_MODULE: new_unnamed_submodule0
-
- DEFINE_DEVICE_INSTANCES:
- END_DEFINE_DEVICE_INSTANCES.
-
- DEFINE_TOPOLOGY:
- END_DEFINE_TOPOLOGY.
-
-
-END_DEFINE_MODULE.
-
-
-
-DEFINE_MODULE: pci_controller
-
- PORT_LIST( RST_n, CLK, DEVSEL_n, STOP, FRAME_n, TRDY_n,
- IRDY_n, IDSEL, CBE, AD, SERR_n, PERR_n,
- PAR );
-
- DEFINE_DEVICE_INSTANCES:
- trget_machine = Target_machine | 5.600000 4.400000 6.900000 7.300000
- Parity = Parity | 5.600000 2.300000 6.800000 4.200000
- END_DEFINE_DEVICE_INSTANCES.
-
- DEFINE_TOPOLOGY:
- Parity parity_PAR pci_controller PAR half-duplex 0 Std_logic L0 3.500000 2.500000 5.600000 2.500000
- Parity PERR_par_n pci_controller PERR_n half-duplex 0 Std_logic L1 3.500000 2.700000 5.600000 2.700000
- Parity SERR_par_n pci_controller SERR_n half-duplex 0 Std_logic L2 3.500000 2.900000 5.600000 2.900000
- trget_machine AD_trgt Parity AD_trgt simplex 0 Std_logic_vector(31#downto#0) AD 5.600000 3.300000 4.300000 3.300000 4.300000 5.500000 5.600000 5.500000
- pci_controller AD trget_machine AD_trgt half-duplex 0 Std_logic_vector(31#downto#0) AD 5.600000 5.500000 5.300000 5.500000 3.600000 5.500000
- trget_machine CBE_trgt_n Parity CBE_trgt_n simplex 0 Std_logic_vector(3#downto#0) CBE 5.600000 3.700000 4.500000 3.700000 4.500000 5.700000 5.600000 5.700000
- pci_controller CBE trget_machine CBE_trgt_n half-duplex 0 Std_logic_vector(3#downto#0) CBE 5.600000 5.700000 3.600000 5.700000
- pci_controller IDSEL trget_machine IDSEL_trgt simplex 0 Std_logic L7 5.600000 6.000000 3.600000 6.000000
- pci_controller IRDY_n trget_machine IRDY_trgt_n simplex 0 Std_logic L8 5.600000 6.200000 3.600000 6.200000
- trget_machine TRDY_trgt_n pci_controller TRDY_n simplex 0 Std_logic L9 3.600000 6.400000 5.600000 6.400000
- pci_controller FRAME_n trget_machine FRAME_trgt_n simplex 0 Std_logic L10 5.600000 6.600000 3.600000 6.600000
- trget_machine STOP_trgt_n pci_controller STOP simplex 0 Std_logic L11 3.600000 6.800000 5.600000 6.800000
- trget_machine DEVSEL_trgt_n pci_controller DEVSEL_n half-duplex 0 Std_logic L12 3.600000 7.000000 5.600000 7.000000
- pci_controller CLK trget_machine CLK simplex 0 Std_logic CLK 5.600000 4.600000 3.700000 4.600000
- trget_machine CLK Parity CLK simplex 0 Std_logic CLK 5.600000 4.100000 4.800000 4.100000 4.800000 4.600000 5.600000 4.600000
- pci_controller RST_n trget_machine RST_n simplex 0 Std_logic RST_n 5.600000 5.000000 3.700000 5.000000
- trget_machine RST_n Parity RST_n simplex 0 Std_logic RST_n 5.600000 3.900000 4.700000 3.900000 4.700000 5.000000 5.600000 5.000000
- trget_machine ADDR_trgt DEV_NULL simplex 0 Std_logic_vector(LOCALADD#-#1#downto#0) L17 8.900001 4.600000 6.900000 4.600000
- trget_machine DATA_trgt DEV_NULL half-duplex 0 Std_logic_vector(31#downto#0) L17 8.900001 4.900000 6.900000 4.900000
- DEV_NULL unknown_port trget_machine TABORT simplex 0 Std_logic 0 6.900000 7.200000 8.900001 7.200000
- DEV_NULL _ trget_machine TRETRY simplex 0 Std_logic 0 6.900000 7.000000 8.900001 7.000000
- END_DEFINE_TOPOLOGY.
-
-GENERIC: LOCALADD : integer := 64
- ANNOTATION: 3.821249 8.066763 PCI main block diagram
- ANNOTATION: 3.779719 8.403428 PCI OpenCores group
- ANNOTATION: 3.788020 8.736729 Jamil Khatib
- BOUNDINGBOX: 3.700000 7.600000 7.100000 9.000001 7.100000 7.600000 3.700000 7.600000 3.700000 9.000001 7.100000 9.000001
-
-END_DEFINE_MODULE.
-
-
-
-
Index: pci_core/trunk/vhdl_behav/readme.txt
===================================================================
--- pci_core/trunk/vhdl_behav/readme.txt (nonexistent)
+++ pci_core/trunk/vhdl_behav/readme.txt (revision 10)
@@ -0,0 +1,32 @@
+This models are written in VHDL!
+Author is Ovidiu Lupas!
+
+MASTER model
+generates PCI compliant signals
+checks Target signal compliance with PCI
+checks data received from Target for correctness
+generates assertion reports if Target signals are not PCI compliant
+
+TARGET model
+generates PCI compliant signals
+checks Master signal compliance with PCI
+checks data received from Master for correctness
+generates assertion reports if Master signals are not PCI compliant
+
+Description
+The models are boardlevel simulation models and are useful in the testing phase
+of
+the PCI cores design. The models are 32 bit, 33 MHz PCI compliant but are easy
+upgradable to 64 bit, 66 MHz. The models are free; you can redistribute them
+and/or modify them under the terms of the GNU General Public License as
+published by the Free Software Foundation; either version 2 of the License, or
+(at your option) any later version.
+The models are distributed in the hope that they will be useful, but WITHOUT ANY
+WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+PARTICULAR PURPOSE. See the GNU General Public License for more details.
+
+Current Status:
+design is available in VHDL from OpenCores CVS via cvsweb
+documentation will be available in short time
+if needed, easy upgradable to 64 bit, 66 MHz
\ No newline at end of file
pci_core/trunk/vhdl_behav/readme.txt
Property changes :
Added: svn:executable
## -0,0 +1 ##
+*
\ No newline at end of property
Index: pci_core/trunk/vhdl_behav/Tg32pci.vhd
===================================================================
--- pci_core/trunk/vhdl_behav/Tg32pci.vhd (nonexistent)
+++ pci_core/trunk/vhdl_behav/Tg32pci.vhd (revision 10)
@@ -0,0 +1,1283 @@
+--===================================================================--
+--
+-- www.OpenCores.Org - January 2000
+-- This model adheres to the GNU public license
+--
+-- Design units : Target device for PCI Local Bus 33 MHz 32 bits
+-- (BoardLevel Simulation model)
+-- (Entity and architecture)
+--
+-- File name : Tg32PCI.vhd
+--
+-- Purpose : The Target device is used to simulate a target
+-- device on the PCI-Bus
+--
+-- Note : This model is modelled after the PCI protocol
+-- as described in Xilinx & Altera AppNotes
+--
+-- There can be used more than one target devices in a
+-- design, every device being identified by the three
+-- base addresses in generic.
+--
+-- 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
+--===================================================================--
+-----------------------------------------------------------------------
+-- Entity for Target device in a PCI bus 33 MHZ 32 bit configuration
+-----------------------------------------------------------------------
+library ieee,work;
+ use ieee.Std_Logic_1164.all;
+ use work.Simulation.all;
+ use work.PCI_Def.all;
+-----------------------------------------------------------------------
+-----------------------------------------------------------------------
+entity TG32PCI is
+ generic (
+ devtype : string(1 to 4); -- type of the device (Fast, Medi, Slow)
+ tdelay : Time; -- delay time parameter when the device will change
+ -- data on AD_Bus (referenced to CLK signal)
+ tsetup : Time;
+ thold : Time;
+ bamem : Std_Logic_Vector(31 downto 0); -- base address for memory
+ baio : Std_Logic_Vector(31 downto 0); -- base address for I/O port
+ bacfg : Std_Logic_Vector(31 downto 0)); -- base address for cfg space
+ port (
+ -- Address, Data and Command buses (37)
+ AD_Bus : inout Std_Logic_Vector (31 downto 0); -- Address and Data Bus
+ C_BE_Bus : in Std_Logic_Vector (3 downto 0); -- Command Bus
+ PAR : inout Std_Logic; --
+ -- Interface control signals (6)
+ FRAME_N : in Std_Logic;
+ TRDY_N : inout Std_Logic;
+ IRDY_N : in Std_Logic;
+ STOP_N : out Std_Logic;
+ DEVSEL_N : inout Std_Logic;
+ IDSEL : in Std_Logic;
+ -- Error reporting signals (2)
+ PERR_N : inout Std_Logic;
+ SERR_N : inout Std_Logic;
+ -- System signals (2)
+ CLK : in Std_Logic;
+ RST_N : in Std_Logic);
+end TG32PCI; --=================== End of entity ====================--
+-----------------------------------------------------------------------
+-- Architecture for Target device PCI bus 33MHZ 32 bit configuration
+-----------------------------------------------------------------------
+architecture Behavior of Target32PCI is
+ ---------------------------------------------------------------------
+ -- Definition of Memory type,
+ ---------------------------------------------------------------------
+ type MEMORY is array(0 to 255) of Std_Logic_Vector(31 downto 0);
+ ---------------------------------------------------------------------
+ -- Local declarations
+ ---------------------------------------------------------------------
+ shared variable addr : Std_Logic_Vector (31 downto 0); -- Address
+ shared variable busaddr : Integer; -- address present on bus
+ shared variable cfgaddr : Integer; -- current configuration register address
+ shared variable memaddr : Integer; -- current memory address
+ shared variable ioaddr : Integer; -- current I/O port address
+ shared variable IOmem : Memory; -- IOport registers
+ shared variable Cfgmem : Memory; -- Configuration registers
+ shared variable Mem : Memory; -- memory locations
+ shared variable trdywaits : Boolean := false; -- wait enable
+ shared variable trdy_st,trdy_nr,trdy_loop : Integer := 0;
+ ---------------------------------------------------------------------
+ -- Signals
+ ---------------------------------------------------------------------
+ signal cmd : Std_Logic_Vector (3 downto 0); -- Command bus
+ signal Busy : Std_Logic := '0';
+ signal IORead : Std_Logic := '0';
+ signal IOWrite : Std_Logic := '0';
+ signal MemRead : Std_Logic := '0';
+ signal MemWrite : Std_Logic := '0';
+ signal WaitWrite : Std_Logic := '0';
+ signal CfgRead : Std_Logic := '0';
+ signal CfgWrite : Std_Logic := '0';
+ signal FrameEv : Std_Logic := '0';
+ signal CmdBusReady : Std_Logic := '0';
+ signal TrnArnd : Std_Logic := '0';
+ signal DevAddr : Std_Logic := '0';
+ signal ResFin : Std_Logic := '0';
+ signal Waits : Std_Logic := '0';
+ signal Init : Std_Logic := '0';
+begin--======================== Architecture ========================--
+ ---------------------------------------------------------------------
+ -- Initialize the memory contents with zeroes
+ ---------------------------------------------------------------------
+ Initialize : process
+ begin
+ for i in 0 to 255 loop
+ IOmem(i) := x"00000000";
+ Mem(i) := x"00000000";
+ Cfgmem(i) := x"00000000";
+ end loop;
+ wait;
+ 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 master
+ ---------------------------------------------------------------------
+ Parity : process(CLK,RST_N)
+ variable parbit : Std_Logic;
+ variable lastpar : Std_Logic;
+ variable errbit : Std_Logic;
+ variable pargen : Boolean := false;
+ variable errgen : Boolean := false;
+ variable cmdbus : Std_Logic_Vector(3 downto 0);
+ variable addrbus : Std_Logic_Vector(31 downto 0);
+ begin
+ if (Falling_Edge(RST_N) or RST_N = '0') then
+ PAR <= 'Z';
+ PERR_N <= 'Z';
+ elsif (CLK'Event and CLK = '1') then -- parity computation on every cycle
+ addrbus := AD_Bus;
+ cmdbus := C_BE_Bus;
+ lastpar := parbit;
+ parbit := '0';
+ if addrbus /= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ" then
+ for I in 0 to 31 loop
+ parbit := parbit xor addrbus(i);
+ end loop;
+ for I in 0 to 3 loop
+ parbit := parbit xor cmdbus(I);
+ end loop;
+ else
+ parbit := 'Z';
+ end if;
+ if PAR = lastpar then -- PERR computation on every cycle
+ errbit := '1';
+ elsif PAR /= lastpar then
+ errbit := '0';
+ elsif PAR = 'Z' then
+ errbit := 'H';
+ end if;
+ if ((IORead = '1' or MemRead = '1' or CfgRead = '1') and DevAddr = '1') then
+ pargen := true;
+ else
+ pargen := false;
+ end if;
+ elsif (CLK'Event and CLK = '0' and DevAddr = '1') then -- parity generation if necessary
+ if errgen = true then
+ PERR_N <= errbit;
+ else
+ PERR_N <= 'H';
+ end if;
+ if pargen = true then
+ PAR <= parbit;
+ errgen := false;
+ else
+ PAR <= 'Z';
+ errgen := true;
+ end if;
+ elsif (CLK'Event and CLK = '0' and DevAddr = '0') then --not the selected device
+ PAR <= 'Z'; -- by the address
+ PERR_N <= 'H';
+ SERR_N <= 'Z';
+ end if;
+ end process;
+ ---------------------------------------------------------------------
+ -- Implements the command decoding, to receive commands from master
+ ---------------------------------------------------------------------
+ Decode : process(CLK,FRAME_N,Busy,DevAddr,cmdBusReady,RST_N)
+ variable counter : Integer;
+ variable devdel : Boolean := false;
+ begin
+ if (Falling_Edge(RST_N) or RST_N = '0') then
+ DEVSEL_N <= 'Z';
+ STOP_N <= 'Z';
+ Busy <= '0';
+ elsif (Frame_N'Event and Frame_N = '0') then -- the target device is awakened by
+ FrameEv <= '1'; -- falling_edge of FRAME signal
+ counter := 0;
+ elsif (Busy'Event and Busy = '0') then
+ IOWrite <= '0';
+ MemWrite <= '0';
+ CfgWrite <= '0';
+ WaitWrite <= '0';
+ IORead <= '0';
+ MemRead <= '0';
+ CfgRead <= '0';
+ elsif (Busy'Event and Busy = '1') then
+ if ( IOWrite = '1' or MemWrite = '1' or CfgWrite = '1' or WaitWrite = '1') then
+ report "Target device is selected for write operations!"
+ severity Note;
+ if devtype = "Fast" then
+ DEVSEL_N <= '0' after 8 ns;
+ Stop_N <= '1' after 10 ns;
+ devdel := false;
+ else
+ devdel := true;
+ counter := 0;
+ end if;
+ elsif ( IORead = '1' or MemRead = '1' or CfgRead = '1') then
+ report "Target device is selected for read operations!"
+ severity Note;
+ if devtype = "Fast" then
+ DEVSEL_N <= '0' after 8 ns;
+ Stop_N <= '1' after 10 ns;
+ devdel := false;
+ else
+ devdel := true;
+ counter := 0;
+ end if;
+ end if;
+ elsif (DevAddr'Event and DevAddr = '0') then
+ Busy <= '0';
+ elsif (cmdBusReady'Event and cmdBusReady = '1') then
+ TrnArnd <= '0';
+ elsif (CLK'Event and CLK = '0') then
+ if Busy = '0' and DevAddr = '1' then -- deselect
+ DEVSEL_N <= 'H';
+ STOP_N <= '1';
+ elsif DevAddr = '0' then -- deselect device
+ DEVSEL_N <= 'Z';
+ STOP_N <= 'Z';
+ end if;
+ elsif (CLK'Event and CLK = '1') then
+ if ResFin = '1' then -- memory reserved mode command
+ if MemWrite = '1' then -- master writes to target memory
+ if TRDY_N = '0' and IRDY_N = '0' then
+ Busy <= '0';
+ ResFin <= '0';
+ end if;
+ elsif MemRead = '1' then -- master reads from target memory
+ if TrnArnd = '0' and TRDY_N = '0' and IRDY_N = '0' then
+ Busy <= '0';
+ ResFin <= '0';
+ end if;
+ end if;
+ end if;
+ if devdel = true then
+ if devtype = "Medi" then
+ if counter = 0 then
+ DEVSEL_N <= '0' after 8 ns;
+ Stop_N <= '1' after 10 ns;
+ devdel := false;
+ end if;
+ elsif devtype = "Slow" then
+ if counter = 1 then
+ DEVSEL_N <= '0' after 8 ns;
+ Stop_N <= '1' after 10 ns;
+ devdel := false;
+ else
+ counter := counter + 1;
+ end if;
+ end if;
+ end if;
+ if FRAME_N = '1' then -- end of cycle
+ assert (IRDY_N = '0')
+ report "Target device : FRAME signal deassertion error. IRDY is not asserted."
+ severity Error;
+ if TRDY_N = '0' and IRDY_N = '0' then -- finish the current cycle
+ Busy <= '0';
+ end if;
+ elsif FrameEv = '1' then -- decoding
+ FrameEv <= '0';
+ assert (FRAME_N'Last_Event >= tsetup)
+ report "Target device : Frame setup time violation in decode cycle!"
+ severity warning;
+ assert (AD_Bus'Last_Event >= tsetup)
+ report "Target device : Address setup time violation in decode cycle!"
+ severity warning;
+ assert (C_BE_Bus'Last_Event >= tsetup)
+ report "Target device : Command setup time violation in decode cycle!"
+ severity warning;
+ addr := AD_Bus;
+ case C_BE_Bus is -- decoding the command bus
+ when "0001" => -- Special Cycle! Used to transfer from master device the
+ -- wait states parameters
+ if (addr(31 downto 8) = bacfg(31 downto 8) and IDSEL ='1') then
+ WaitWrite <= '1';
+ DevAddr <= '1';
+ Busy <= '1';
+ trdywaits := true;
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ trdywaits := false;
+ end if;
+ cfgaddr := Byte2Int(addr(7 downto 0));
+ when "0010" => -- I/O Read! Master reads from target device.
+ if addr(31 downto 8) = baio(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ IORead <= '1';
+ TrnArnd <= '1';
+ ioaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "0011" => -- I/O Write! Master writes to target device.
+ if addr(31 downto 8) = baio(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ IOWrite <= '1';
+ ioaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "1100" => -- Memory Read! Master reads from target device.
+ if addr(31 downto 8) = bamem(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ MemRead <= '1';
+ TrnArnd <= '1';
+ if addr(1 downto 0) = "01" then -- reserved mode
+ ResFin <= '1';
+ elsif addr(1 downto 0) = "11" then -- reserved mode
+ ResFin <= '1';
+ end if;
+ memaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "1110" => -- Memory Read Line! Master reads from target device.
+ if addr(31 downto 8) = bamem(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ MemRead <= '1';
+ TrnArnd <= '1';
+ if addr(1 downto 0) = "01" then -- reserved mode
+ ResFin <= '1';
+ elsif addr(1 downto 0) = "11" then -- reserved mode
+ ResFin <= '1';
+ end if;
+ memaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "1111" => -- Memory Write! Master writes to target device.
+ if addr(31 downto 8) = bamem(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ MemWrite <= '1';
+ if addr(1 downto 0) = "01" then -- reserved mode
+ ResFin <= '1';
+ elsif addr(1 downto 0) = "11" then -- reserved mode
+ ResFin <= '1';
+ end if;
+ memaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "0110" => -- Memory Read! Master reads from target device.
+ if addr(31 downto 8) = bamem(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ MemRead <= '1';
+ TrnArnd <= '1';
+ if addr(1 downto 0) = "01" then -- reserved mode
+ ResFin <= '1';
+ elsif addr(1 downto 0) = "11" then -- reserved mode
+ ResFin <= '1';
+ end if;
+ memaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "0111" => -- Memory Write! Master writes to target device.
+ if addr(31 downto 8) = bamem(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ MemWrite <= '1';
+ if addr(1 downto 0) = "01" then -- reserved mode
+ ResFin <= '1';
+ elsif addr(1 downto 0) = "11" then -- reserved mode
+ ResFin <= '1';
+ end if;
+ memaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "1010" => -- Configuration Read! Master reads from target device.
+ if (addr(31 downto 8) = bacfg(31 downto 8) and IDSEL = '1') then
+ if addr(1 downto 0) = "01" then
+ report "Target device: Type 1 configuration access on bus! Ignored."
+ severity Note;
+ elsif addr(1 downto 0) = "00" then
+ CfgRead <= '1';
+ TrnArnd <= '1';
+ DevAddr <= '1';
+ Busy <= '1';
+ end if;
+ cfgaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "1011" => -- Configuration Write! Master writes to target device.
+ if (addr(31 downto 8) = bacfg(31 downto 8) and IDSEL = '1') then
+ if addr(1 downto 0) = "01" then
+ report "Target device: Type 1 configuration access on bus! Ignored."
+ severity Note;
+ elsif addr(1 downto 0) = "00" then
+ CfgWrite <= '1';
+ DevAddr <= '1';
+ Busy <= '1';
+ end if;
+ cfgaddr := Byte2Int(addr(7 downto 0));
+ else
+ -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "0100" =>
+ report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
+ severity Warning;
+ when "0101" =>
+ report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
+ severity Warning;
+ when "1000" =>
+ report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
+ severity Warning;
+ when "1001" =>
+ report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
+ severity Warning;
+ when "ZZZZ" => null;
+ when others =>
+ report "Target device: Unknown or invalid command on C/BE bus! Ignored."
+ severity Error;
+ end case;
+ end if;
+ -- elsif (Frame_N'Event and Frame_N = '1') then
+ end if;
+ end process;
+ ---------------------------------------------------------------------
+ -- Implementation of Write command.
+ -- Master writes to Target device.
+ ---------------------------------------------------------------------
+ WriteProc : process(CLK,RST_N)
+ variable waitreg : Std_Logic_Vector(15 downto 0) := x"0000";
+ variable Char3_2,Char1,Char0 : Std_Logic_Vector(7 downto 0) := x"00";
+ begin
+ if (CLK'Event and CLK = '1' and ((IRDY_N = '0' and TRDY_N = '0') or FRAME_N = '1')) then
+ assert (AD_Bus'Last_Event >= tsetup)
+ report "Target device : Data setup time violation in decode cycle!"
+ severity warning;
+ assert (C_BE_Bus'Last_Event >= tsetup)
+ report "Target device : Byte Enables setup time violation in decode cycle!"
+ severity warning;
+ if (WaitWrite = '1') then
+ Char3_2 := AD_Bus(15 downto 8);
+ Char1 := "0000" & AD_Bus(7 downto 4);
+ Char0 := "0000" & AD_Bus(3 downto 0);
+ trdy_loop := Byte2Int(Char3_2) ;
+ trdy_nr := Byte2Int(Char1); -- + 1;
+ trdy_st := Byte2Int(Char0);
+ elsif IOWrite = '1' then
+ -- Master writes to target I/O space
+ case addr(1 downto 0) is
+ when "00" =>
+ if C_BE_Bus = "0000" then
+ IOmem(ioaddr) := AD_Bus;
+ elsif C_BE_Bus = "1000" then
+ IOmem(ioaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "0100" then
+ IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ IOmem(ioaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1100" then
+ IOmem(ioaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0010" then
+ IOmem(ioaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1010" then
+ IOmem(ioaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0110" then
+ IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1110" then
+ IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus(0) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "01" =>
+ if C_BE_Bus = "0001" then
+ IOmem(ioaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "1001" then
+ IOmem(ioaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "0101" then
+ IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ IOmem(ioaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1101" then
+ IOmem(ioaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus(1) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "10" =>
+ if C_BE_Bus = "0011" then
+ IOmem(ioaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "1011" then
+ IOmem(ioaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus(2) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "11" =>
+ if C_BE_Bus = "0111" then
+ IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus(3) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when others =>
+ null;
+ end case;
+ ioaddr := ioaddr + 1;
+ elsif MemWrite = '1' then
+ -- Master writes to target memory space
+ case addr(1 downto 0) is
+ when "00" => -- linear incrementing mode
+ if C_BE_Bus = "0000" then
+ Mem(memaddr) := AD_Bus;
+ elsif C_BE_Bus = "0001" then
+ Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "0010" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0011" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "0100" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0101" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "0110" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0111" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus = "1000" then
+ Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "1001" then
+ Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "1010" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1011" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus = "1100" then
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1101" then
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1110" then
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ memaddr := memaddr + 1;
+ when "01" => -- reserved mode (disconnect after first data phase)
+ if C_BE_Bus = "0000" then
+ Mem(memaddr) := AD_Bus;
+ elsif C_BE_Bus = "0001" then
+ Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "0010" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0011" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "0100" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0101" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "0110" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0111" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus = "1000" then
+ Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "1001" then
+ Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "1010" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1011" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus = "1100" then
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1101" then
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1110" then
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "10" => -- cacheline wrap mode
+ if C_BE_Bus = "0000" then
+ Mem(memaddr) := AD_Bus;
+ elsif C_BE_Bus = "0001" then
+ Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "0010" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0011" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "0100" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0101" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "0110" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0111" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus = "1000" then
+ Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "1001" then
+ Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "1010" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1011" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus = "1100" then
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1101" then
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1110" then
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ memaddr := memaddr + 1;
+ when "11" => -- reserved mode (disconnect after first data phase)
+ if C_BE_Bus = "0000" then
+ Mem(memaddr) := AD_Bus;
+ elsif C_BE_Bus = "0001" then
+ Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "0010" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0011" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "0100" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0101" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "0110" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0111" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus = "1000" then
+ Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "1001" then
+ Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "1010" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1011" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus = "1100" then
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1101" then
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1110" then
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when others =>
+ null;
+ end case;
+ elsif CfgWrite = '1' then
+ -- Master writes to target configuration space
+ if C_BE_Bus = "0000" then
+ Cfgmem(cfgaddr) := AD_Bus;
+ elsif C_BE_Bus = "0001" then
+ Cfgmem(cfgaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "0010" then
+ Cfgmem(cfgaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0011" then
+ Cfgmem(cfgaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "0100" then
+ Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Cfgmem(cfgaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0101" then
+ Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Cfgmem(cfgaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "0110" then
+ Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0111" then
+ Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus = "1000" then
+ Cfgmem(cfgaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "1001" then
+ Cfgmem(cfgaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "1010" then
+ Cfgmem(cfgaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1011" then
+ Cfgmem(cfgaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus = "1100" then
+ Cfgmem(cfgaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1101" then
+ Cfgmem(cfgaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1110" then
+ Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ cfgaddr := cfgaddr + 1;
+ end if;
+ end if;
+ end process;
+ ---------------------------------------------------------------------
+ -- Implementation of Read command.
+ -- Master read from Target device.
+ ---------------------------------------------------------------------
+ ReadProc : process(RST_N,CLK,cmdBusReady,IORead,IOWrite,MemRead,MemWrite,CfgRead,CfgWrite)
+ variable first : Boolean := true;
+ begin
+ if (Falling_Edge(RST_N) or RST_N = '0') then
+ AD_Bus <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ";
+ elsif (CLK'Event and CLK = '0') then
+ cmdBusReady <= '0';
+ if (first = true or TrnArnd ='1') then
+ -- Initialize the AD_Bus to avoid bus conflict
+ AD_Bus <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ";
+ first := false;
+ elsif Init = '1' then
+ Init <= '0';
+ AD_Bus <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ" after tdelay;
+ end if;
+ elsif IORead'Event and IORead = '0' then
+ Init <= '1';
+ elsif MemRead'Event and MemRead = '0' then
+ Init <= '1';
+ elsif CfgRead'Event and CfgRead = '0' then
+ Init <= '1';
+ elsif (CLK'Event and CLK = '1' and IRDY_N = '0') then
+ if (IORead = '1' or MemRead = '1' or CfgRead = '1') then
+ cmd <= C_BE_Bus; -- read the byte enable command
+ cmdBusReady <= '1';
+ end if;
+ elsif (cmdBusReady'Event and cmdBusReady = '0' and TRDY_N = '0') then
+ if IORead = '1' then
+ -- Master reads from target I/O space
+ case addr(1 downto 0) is
+ when "00" =>
+ if cmd = "0000" then
+ AD_Bus <= IOmem(ioaddr) after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= IOmem(ioaddr)(23 downto 0) after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 0) <= IOmem(ioaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= IOmem(ioaddr)(15 downto 0) after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= IOmem(ioaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= IOmem(ioaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
+ elsif cmd(0) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "01" =>
+ if cmd = "0001" then
+ AD_Bus(31 downto 8) <= IOmem(ioaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= IOmem(ioaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= IOmem(ioaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= IOmem(ioaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd(1) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "10" =>
+ if cmd = "0011" then
+ AD_Bus(31 downto 16) <= IOmem(ioaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= IOmem(ioaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd(2) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "11" =>
+ if cmd = "0111" then
+ AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd(3) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when others =>
+ null;
+ end case;
+ ioaddr := ioaddr + 1;
+ elsif MemRead = '1' then
+ -- Master reads from target memory space
+ case addr(1 downto 0) is
+ when "00" => -- linear incrementing mode
+ if cmd = "0000" then
+ AD_Bus <= Mem(memaddr) after tdelay;
+ elsif cmd = "0001" then
+ AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ elsif cmd = "0011" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0111" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ memaddr := memaddr + 1;
+ when "01" => -- reserved mode (disconnect after first data phase)
+ if cmd = "0000" then
+ AD_Bus <= Mem(memaddr) after tdelay;
+ elsif cmd = "0001" then
+ AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ elsif cmd = "0011" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0111" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "10" => -- cacheline wrap mode
+ if cmd = "0000" then
+ AD_Bus <= Mem(memaddr) after tdelay;
+ elsif cmd = "0001" then
+ AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ elsif cmd = "0011" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0111" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ memaddr := memaddr + 1;
+ when "11" => -- reserved mode (disconnect after first data phase)
+ if cmd = "0000" then
+ AD_Bus <= Mem(memaddr) after tdelay;
+ elsif cmd = "0001" then
+ AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ elsif cmd = "0011" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0111" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when others =>
+ null;
+ end case;
+ elsif CfgRead = '1' then
+ -- Master reads from target configuration space
+ if cmd = "0000" then
+ AD_Bus <= Cfgmem(cfgaddr) after tdelay;
+ elsif cmd = "0001" then
+ AD_Bus(31 downto 8) <= Cfgmem(cfgaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= Cfgmem(cfgaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0011" then
+ AD_Bus(31 downto 16) <= Cfgmem(cfgaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
+ AD_Bus(15 downto 0) <= Cfgmem(cfgaddr)(15 downto 0) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= Cfgmem(cfgaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0111" then
+ AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= Cfgmem(cfgaddr)(23 downto 0) after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= Cfgmem(cfgaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Cfgmem(cfgaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Cfgmem(cfgaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= Cfgmem(cfgaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= Cfgmem(cfgaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ cfgaddr := cfgaddr + 1;
+ end if;
+ end if;
+ end process;
+ ---------------------------------------------------------------------
+ -- Implements the wait states process.
+ -- Target generates wait states accordingly to wait states parameters
+ -- received from master during Special Cycle.
+ -- Master reads the parameters from commands file.
+ ---------------------------------------------------------------------
+ WaitProc : process(CLK,FRAME_N,RST_N)
+ variable counter : Integer;
+ variable waitcnt : Integer;
+ variable start : Boolean;
+ begin
+ if (Falling_Edge(RST_N) or RST_N = '0') then
+ TRDY_N <= 'Z';
+ elsif (FRAME_N'Event and FRAME_N = '0') then
+ counter := 0;
+ start := true;
+ TRDY_N <= '1';
+ elsif (CLK'Event and CLK = '0') then
+ if (Busy = '0' and DevAddr = '0') then -- deselect device
+ TRDY_N <= 'H';
+ elsif (Busy = '0' and DevAddr = '1') then -- deselect signal
+ TRDY_N <= '1';
+ end if;
+ if (DevAddr = '1' and TrnArnd = '0' and DEVSEL_N = '0') then
+ if (counter >= trdy_st and start = true and TRDY_N = '1') then
+ -- finish waitstates at start
+ TRDY_N <= '0';
+ start := false;
+ elsif (counter = trdy_loop and TRDY_N = '0') then
+ -- random waitstates
+ TRDY_N <= '1';
+ waits <= '1';
+ waitcnt := 1;
+ elsif (waitcnt = trdy_nr and waits = '1') then
+ -- finish random waitstates
+ waits <= '0';
+ TRDY_N <= '0';
+ elsif waits = '1' then -- count random waitstates
+ waitcnt := waitcnt + 1;
+ end if;
+ end if;
+ counter := counter + 1;
+ end if;
+ end process;
+ ---------------------------------------------------------------------
+ -- Implements the assertion process for IRDY_N, FRAME_N, and IDSEL
+ -- signals.
+ ---------------------------------------------------------------------
+ AsrtProc : process(CLK,FRAME_N,IRDY_N,IDSEL,AD_Bus)
+ variable irdevs : Boolean := false;
+ variable idsevs : Boolean := false;
+ variable counter : Integer;
+ begin
+ if Rising_Edge(CLK) and FRAME_N = '0' and IRDY_N = '1' then
+ counter := counter + 1;
+ if counter >= 8 then
+ report"Target device:IRDY is not asserted within 8 clocks from FRAME assertion!"
+ severity warning;
+ end if;
+ end if;
+ if AD_Bus'Event then
+ assert(CLK'Last_Event <= thold)
+ report"Target device: Address or Data hold time violation!"
+ severity warning;
+ end if;
+ if Rising_Edge(CLK) and DevAddr = '1' then
+ if irdevs = true then
+ irdevs := false;
+ assert(IRDY_N'Last_Event >= tsetup)
+ report"Target device: IRDY setup time violation in current data transfer!"
+ severity warning;
+ end if;
+ if idsevs = true then
+ idsevs := false;
+ assert(IDSEL'Last_Event >= tsetup)
+ report"Target device: IDSEL setup time violation!"
+ severity warning;
+ end if;
+ if FRAME_N = '0' and IRDY_N = '1' then
+ counter := counter + 1 ;
+ end if;
+ assert (counter <= 8)
+ report"Target device: IRDY has not been asserted within 8 clocks from FRAME assertion!"
+ severity warning;
+ elsif Falling_Edge(FRAME_N) then
+ counter := 0;
+ elsif Rising_Edge(FRAME_N) then
+ assert(CLK'Last_Event <= thold)
+ report"Target device: FRAME hold time violation in current data transfer!"
+ severity warning;
+ elsif Falling_Edge(IRDY_N) and DevAddr = '1' then
+ irdevs := true;
+ elsif Rising_Edge(IRDY_N) and DevAddr = '1' then
+ assert(CLK'Last_Event <= thold)
+ report"Target device: IRDY hold time violation in current data transfer!"
+ severity warning;
+ elsif Rising_Edge(IDSEL) and DevAddr = '1' then
+ idsevs := true;
+ elsif Falling_Edge(IDSEL) and DevAddr = '1' then
+ assert(CLK'Last_Event <= thold)
+ report"Target device: IDSEL hold time violation!"
+ severity warning;
+ end if;
+ end process;
+end Behavior; --================ End of architecture ================--
+-----------------------------------------------------------------------
+-- Revision list
+-- Version Author Date Changes
+--
+-- 0.1 Ovidiu Lupas June 09, 2000 New model
+-----------------------------------------------------------------------
+
Index: pci_core/trunk/vhdl_behav/Ms32pci.vhd
===================================================================
--- pci_core/trunk/vhdl_behav/Ms32pci.vhd (nonexistent)
+++ pci_core/trunk/vhdl_behav/Ms32pci.vhd (revision 10)
@@ -0,0 +1,827 @@
+--===================================================================--
+--
+-- 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
+ end if;
+
+ if DEVSEL_N'Last_Event <= tsetup then
+ report "DEVSEL_N setup time violation"
+ severity Warning;
+ end if;
+
+ --- inset IRDY_N if loop_irdy =1 and nr_irdy >1
+ if loop_irdy =1 then
+ while (nr_irdy > 1) loop
+ IRDY_N <='1' after tdelay;
+ nr_irdy := nr_irdy -1 ;
+ wait until FALLING_EDGE(CLK);
+ end loop;
+ IRDY_N <='0' after tdelay;
+ end if;
+
+ -- terminate cycle because DEVSEL_N is anactive
+ -- (implement command MASTER-ABORT TERMINATION )
+ if start_irdy = 0 then -- terminate cycle
+ stop := true;
+ FRAME_N <='1'; -- after tdelay;
+ end if;
+
+ -- wait until FALLING_EDGE(CLK);
+ -- repeat until all data are read or STOP_N ='0'
+ while ((data_number > 0) and (stop = false)) loop -- read cycle
+ parity_flag <= true;
+ data_number := data_number -1;
+ parity_flag <= true;
+ data_read := data(data_nr - data_number);
+ if data_number = 0 then
+ C_BE_Bus(3 downto 0) <=bus_sel(data_nr) after tdelay;
+ data_read := data(data_nr);
+ else
+ C_BE_Bus(3 downto 0) <=bus_sel(data_nr - data_number+1) after tdelay;
+ data_read := data(data_nr - data_number);
+ end if;
+
+ parity_flag <= true;
+ if data_number =0 then
+ FRAME_N <='1';-- after tdelay;
+ end if;
+
+ -- 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
+ irdy_insert := false;
+ end if;
+
+ if irdy_insert = true and (data_nr - data_number) = loop_irdy then
+ -- insert IRDY ='1' if insert_trdy =true
+ while nr_irdy > 1 loop
+ nr_irdy := nr_irdy -1 ;
+ IRDY_N <= '1' after tdelay; -- insert IRDY
+ -- 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
+ nr_irdy := 1;
+ end if;
+ wait until FALLING_EDGE(CLK);
+ end loop; -- end loop nr_irdy
+ end if; -- end if irdy_insert
+
+ -- IRDY_N <= '0' after tdelay;
+ if data_number = 0 then
+ IRDY_N <= '0' after tdelay;
+ end if;
+ wait until RISING_EDGE(CLK);
+
+ if TRDY_N'Last_Event <= tsetup then -- end of cycle
+ report "TRDY_N setup time violation"
+ severity Warning;
+ end if;
+
+ -- wait for TRDY_N = '0' (maxim 8 clock pulse)
+ while TRDY_N = '1' and trdy_exit = false loop
+ wait until RISING_EDGE(CLK);
+ -- wait maxim 8 clock pulse if TRDY is asserted
+ trdy_stop := trdy_stop -1;
+ if trdy_stop = 0 then
+ stop := true;
+ report "Target is not responding "
+ severity Warning;
+ FRAME_N <= '1';-- after tdelay;
+ IRDY_N <= '1' after tdelay;
+ trdy_exit := true;
+ end if;
+
+ -- 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
+ trdy_exit := true;
+ end if;
+ end loop; -- end loop TRDY_N=1
+
+ Vec2Hex (data_read,str8,Good2);
+ report " EXPECTED DATA= "&str8 &""; -- display expected data
+
+ Vec2Hex (AD_Bus,str8,Good2);
+ report " READ DATA= "&str8 &""; -- display receive data
+
+ if AD_Bus'Last_Event <= tsetup then -- end of cycle
+ report "AD_BUS setup time violation"
+ severity Warning;
+ end if;
+
+ if ((data_number >0) and (stop =false)) then
+ wait until FALLING_EDGE(CLK);
+ end if;
+
+ wait for thold;
+ if AD_Bus'Last_Event <= thold then -- end of cycle
+ report "AD_Bus hold time violation"
+ severity Warning;
+ end if;
+ end loop; -- end loop data_number
+
+ if RESET =1 or STOP_N ='0' or STOP_N ='L' then
+ 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 <= 'H' after tdelay;
+ parity_flag <= false;
+ end if;
+ else
+ --------------------------------------------------------------------
+ -- BEGIN WRITE CYCLE --
+ --------------------------------------------------------------------
+ -- adress phase
+ parity_flag <= false;
+ nr_irdy := nr_irdy;
+ 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_read <= 'Z';
+ parity(address(31 downto 0), bus_cmd(3 downto 0), parity_temp); -- calculate parity of address cycle
+ parity_now <= parity_temp after tdelay;
+ wait until FALLING_EDGE(CLK);
+ -- end adress phase
+
+ REQ_N <='1';
+
+ parity_flag <= false;
+ IRDY_N <= '0' after tdelay;
+ -- wait for 1 ns;
+ -- wait for DEVSEL_N = '0'
+ -- (implement command MASTER-ABORT TERMINATION if TARGET not respond)
+ while ((start_irdy > 0) and (DEVSEL_N ='H' or DEVSEL_N ='Z' or DEVSEL_N ='X') ) loop -- wait for the number of IRDY state
+ start_irdy := start_irdy -1; -- from the begining of read cycle
+ wait until FALLING_EDGE(CLK);
+ end loop;
+
+ -- if device not respond then exits the write command
+ if start_irdy = 0 then -- terminate cycle
+ stop := true;
+ FRAME_N <= '1';-- after tdelay;
+ end if;
+
+ if DEVSEL_N'Last_Event <= tsetup then
+ report "DEVSEL_N setup time violation"
+ severity Warning;
+ end if;
+
+ while ((data_number >0) and (stop =false)) loop
+ -- data phase
+ data_number := data_number -1;
+ AD_Bus(31 downto 0) <= data(data_nr - data_number) after tdelay; -- set DATA
+ C_BE_Bus(3 downto 0) <= bus_sel(data_nr - data_number) after tdelay; -- set BE#s
+ IRDY_N <= '0' after tdelay;
+ parity(data(data_nr - data_number), bus_sel(data_nr - data_number), parity_temp); -- calculate parity
+ parity_now <= parity_temp after tdelay;
+ -- end data phase
+
+ if data_number = 0 then
+ FRAME_N <= '1';-- after tdelay;
+ end if;
+
+ -- exit cycle if RST_N,GNT_N or STOP_N are active
+ if RESET = 1 or STOP_N= '0' or STOP_N = 'L' then
+ stop := true; -- exit cycle
+ end if;
+
+ wait until RISING_EDGE(CLK);
+
+ if TRDY_N'Last_Event <= tsetup then -- end of cycle
+ report "TRDY_N setup time violation"
+ severity Warning;
+ end if;
+
+ -- wait for TRDY_N ='0'
+ while TRDY_N ='1' and trdy_exit = false loop
+ wait until RISING_EDGE(CLK);
+ -- wait maxim 8 clock pulse if TRDY is asserted
+ trdy_stop := trdy_stop -1;
+ if trdy_stop = 0 then
+ stop := true;
+ report "Target is not responding "
+ severity Warning;
+ FRAME_N <= '1';-- after tdelay;
+ IRDY_N <= '1' after tdelay;
+ trdy_exit := true;
+ end if;
+
+ -- exit cycle if RST_N,GNT_N or STOP_N are active
+ if RESET = 1 or STOP_N = '0' or STOP_N = 'L' then
+ stop := true; -- exit cycle
+ trdy_exit := true;
+ end if;
+ end loop; -- end loop TRDY=1
+
+ if ((data_number > 0) and (stop = false)) then
+ wait until FALLING_EDGE(CLK); -- synchronize with PCICLK
+ end if;
+ -- insert IRDY_N
+ if irdy_insert = true and (data_nr -data_number) = loop_irdy
+ and data_number >0 and (stop =false) then
+ while nr_irdy > 1 loop
+ IRDY_N <='1' after tdelay;
+ nr_irdy := nr_irdy -1 ;
+ if nr_irdy > 0 then
+ if data_number > 0 then
+ C_BE_Bus(3 downto 0) <=bus_sel(data_nr - data_number +1) after tdelay; -- set BE#s
+ parity(data(data_nr - data_number), bus_sel(data_nr - data_number+1), parity_temp); -- calculate parity
+ parity_now <= parity_temp after tdelay;
+ end if;
+ wait until FALLING_EDGE(CLK);
+ end if;
+
+ if RESET = 1 or STOP_N = '0' or STOP_N = 'L' then
+ stop := true; -- exit cycle
+ nr_irdy := 1;
+ end if;
+ end loop; -- end loop nr_irdy
+ end if;
+ report " WRITE DATA= "&str8 &""; -- display write data
+ end loop; -- end loop start_irdy > 0 ...
+
+ if RESET = 1 or STOP_N = '0' or STOP_N = 'L' then
+ 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 <= 'H' after tdelay;
+ parity_flag <= false;
+ end if;
+ end if; -- end rd_wr = '1'
+ end if; -- if RST_N ='0' then
+ end READ_WRITE;
+ --------------------------------------------------------------------------
+ -- Procedure implement instruction WRSW --
+ --------------------------------------------------------------------------
+ -- Writes single DWORD to memory space!
+ procedure WRSW(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "0111";
+ address(1 downto 0) := "00";
+ Vec2Hex (data(1),str8,Good2);
+ Vec2Hex (address,str_8,Good2);
+ report "Write single DWORD to memory space! Address : "&str_8;
+ READ_WRITE(address,data,1,bus_cmd,bus_sel,'0');
+ end WRSW;
+ --------------------------------------------------------------------------
+ -- Procedure implement instruction RDSW --
+ --------------------------------------------------------------------------
+ -- Reads single DWORD from memory space!
+ procedure RDSW(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "0110";
+ address(1 downto 0) := "00";
+ Vec2Hex (address,str_8,Good2);
+ report "Read single DWORD from memory space! Address : "&str_8 ;
+ READ_WRITE(address,data,1,bus_cmd,bus_sel,'1');
+ end RDSW;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction WRMW --
+ --------------------------------------------------------------------------
+ -- Writes multiple DWORDs to memory space - burst mode
+ procedure WRMW(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "1111";
+ address(1 downto 0) := "10";
+ Vec2Hex (address,str_8,Good2);
+ report "Write multiple DWORDs to memory space! Address : "&str_8 ;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
+ end WRMW;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction RDMW --
+ --------------------------------------------------------------------------
+ -- Reads multiple DWORDs from memory space - burst mode
+ procedure RDMW(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "1100";
+ address(1 downto 0) := "10";
+ Vec2Hex (address,str_8,Good2);
+ report "Read multiple DWORDs from memory space! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
+ end RDMW;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction RDML --
+ --------------------------------------------------------------------------
+ -- Reads multiple DWORDs from memory space!
+ procedure RDML(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd: STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data: Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "1110";
+ address(1 downto 0) := "00";
+ Vec2Hex (address,str_8,Good2);
+ report "Reads multiple DWORDs from memory space! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
+ end RDML;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction WCFG --
+ --------------------------------------------------------------------------
+ -- writes configuration
+ procedure WCFG(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd :="1011";
+ address(1 downto 0) :="00"; -- linear incrementing
+ Vec2Hex (address,str_8,Good2);
+ report "Configuration write! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
+ end WCFG;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction RCFG --
+ --------------------------------------------------------------------------
+ -- reads configuration
+ procedure RCFG(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd :="1010";
+ address(1 downto 0) :="00";
+ Vec2Hex (address,str_8,Good2);
+ report "Configuration read ! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
+ end RCFG;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction WRIO --
+ --------------------------------------------------------------------------
+ -- writes data to IO port
+ procedure WRIO(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "0011";
+ address(1 downto 0) := "00";
+ Vec2Hex (address,str_8,Good2);
+ report "Write DWORD to I/O space! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
+ end WRIO;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction RDIO --
+ --------------------------------------------------------------------------
+ -- reads data from IO port
+ procedure RDIO(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd :="0010";
+ address(1 downto 0) :="00";
+ Vec2Hex (address,str_8,Good2);
+ report "Read DWORD from memory space! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
+ end RDIO;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction WAIT --
+ --------------------------------------------------------------------------
+ -- waits
+ procedure CWAT(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ variable byte7_6,byte5,byte4,byte3_2,byte1,byte0 : Integer;
+ variable Char7_6,Char5,Char4,Char3_2,Char1,Char0 : Std_Logic_Vector(7 downto 0);
+ begin
+ Char7_6 := data(1)(31 downto 24);
+ irdy_loop := Byte2Int(Char7_6) ;
+ Char5 := "0000" & data(1)(23 downto 20);
+ irdy_nr := Byte2Int(Char5) + 1;
+ Char4 := "0000" & data(1)(19 downto 16);
+ irdy_start := Byte2Int(Char4);
+ bus_cmd := "0001";
+ if irdy_loop = 0 or irdy_nr = 0 then
+ irdy_insert := false;
+ else
+ irdy_insert := true;
+ end if;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
+ end CWAT;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction EXIT --
+ --------------------------------------------------------------------------
+ -- ends the Master's activity by placing in HighZ all the lines
+ procedure ABRT is
+ begin
+ wait until FALLING_EDGE(CLK); -- synchro cycle
+ Init;
+ wait;
+ end ABRT;
+ --------------------------------------------------------------------------
+ -- Procedure implements the commands file parser and sequencer --
+ --------------------------------------------------------------------------
+ procedure Main_case is
+ variable Commands : CommandArray(1 to 100);
+ variable NumCommands : Natural;
+ variable Good : Boolean;
+ constant HeaderMsg : String := "Main process:";
+ constant MsgSeverity : Severity_Level := Failure;
+ variable ErrFlag : Boolean;
+ variable PC : Integer;
+ begin
+ -- Read/Parse the commands file
+ FileParser (cmd_file,Commands,NumCommands,ErrFlag);
+ data_last_read := FALSE;
+ if ErrFlag then
+ report HeaderMsg&"Errors found in COMMAND file. Execute halts!!!"
+ severity Warning;
+ else
+ PC := 0;
+ wait until RST_N = '1';
+ while PC < NumCommands Loop
+ if RESET = 1 then
+ RESET := 0;
+ PC := 0;
+ end if;
+ while RST_N = '0' loop -- RESET signal is active
+ PC := 0; -- if RST_N ='0' restart simulation
+ REQ_N <= 'H'; -- request is tri-stated
+ wait until Rising_Edge(CLK); -- synchro wait
+ end loop;
+ if STOP_N = '0' then
+ report HeaderMsg&"Wait until signal STOP_N ='0' !";
+ wait until STOP_N = '1';
+ end if;
+ REQ_N <= '0';
+
+ PC := PC + 1;
+ case Commands(pc).command is
+ when "WRSW" =>
+ WRSW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "RDSW" =>
+ RDSW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "WRMW" =>
+ WRMW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "RDMW" =>
+ RDMW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "RDML" =>
+ RDML(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "WCFG" =>
+ WCFG(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "RCFG" =>
+ RCFG(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "WRIO" =>
+ WRIO(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "RDIO" =>
+ RDIO(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "CWAT" =>
+ CWAT(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "ABRT" => ABRT;
+ when others => null;
+ end case;
+ end loop;
+ end if;
+ end Main_Case;
+ ---------------------------------------------------------------------
+ -- MS32PCI_MAIN : process begins
+ ---------------------------------------------------------------------
+ begin
+ Init;
+ Main_case;
+ end process;
+end Behavior; --================= End of architecture ===============--
+-----------------------------------------------------------------------
+-- Revision list
+-- Version Author Date Changes
+--
+-- 0.1 Ovidiu Lupas June 09, 2000 New model
+-----------------------------------------------------------------------
+
Index: pci_core/trunk/vhdl_behav/Pci_lib.vhd
===================================================================
--- pci_core/trunk/vhdl_behav/Pci_lib.vhd (nonexistent)
+++ pci_core/trunk/vhdl_behav/Pci_lib.vhd (revision 10)
@@ -0,0 +1,793 @@
+--===================================================================--
+--
+-- www.OpenCores.Org - June 2000
+-- This model adheres to the GNU public license
+--
+-- Design units : Functions and procedures used in models
+--
+-- File name : PCI_LIB.vhd
+--
+-- Purpose : type conversion functions, read commands file
+-- procedures
+--
+-- 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
+--===================================================================--
+-----------------------------------------------------------------------
+-- Revision list
+-- Version Author Date Changes
+--
+-- 0.1 Ovidiu Lupas June 09, 2000 New model
+-----------------------------------------------------------------------
+library IEEE;
+use IEEE.Std_Logic_1164.all;
+--
+package Simulation is
+-- Definition of the CommandType record array which is used to record
+-- the commands from the .cmd file
+ type Data_buffer is array(1 to 256) of Std_Logic_Vector(31 downto 0);
+ type Data_Enable is array(1 to 256) of Std_Logic_Vector(3 downto 0);
+
+ type CommandType is
+ record
+ command : string(1 to 4);
+ addr : Std_Logic_Vector(31 downto 0);
+ data : Data_buffer;
+ data_nr : Integer;
+ enable : Data_Enable;
+ end record;
+-- Definition of the CommandArray type type which can be used for
+-- the commands present in .cmd file
+ type CommandArray is array(positive range <>) of CommandType;
+end Simulation; --========== End of package Simulation =============--
+--
+library IEEE,STD,work;
+library work;
+use work.Simulation.all;
+use IEEE.Std_Logic_1164.all;
+use STD.textio.all;
+--
+package PCI_Def is
+ --------------------------------------------------------------------
+ -- convert a character to a value from 0 to 15
+ --------------------------------------------------------------------
+ function digit_value(
+ C : Character)
+ return integer;
+ --------------------------------------------------------------------
+ -- Converts unsigned Std_LOGIC_Vector to Integer, leftmost bit is MSB
+ -- Error message for unknowns (U, X, W, Z, -), converted to 0
+ -- Verifies whether vector is too long (> 16 bits)
+ --------------------------------------------------------------------
+ function Vec2Int (
+ Invector : in Std_Logic_Vector(15 downto 0))
+ return Integer;
+ --------------------------------------------------------------------
+ -- Converts unsigned Std_Logic_Vector to Integer, leftmost bit is MSB
+ -- Error message for unknowns (U, X, W, Z, -), converted to 0
+ -- Verifies whether vector is too long (> 16 bits)
+ --------------------------------------------------------------------
+ function Byte2Int (
+ Invector : in Std_Logic_Vector(7 downto 0))
+ return Integer;
+ --------------------------------------------------------------------
+ -- Converts unsigned Std_Logic_Vector to Integer, leftmost bit is MSB
+ -- Error message for unknowns (U, X, W, Z, -), converted to 0
+ -- Verifies whether vector is too long (> 16 bits)
+ --------------------------------------------------------------------
+ procedure Hex2Bit (
+ C : in Character;
+ Vector : out Std_Logic_Vector(3 downto 0);
+ Good : out Boolean);
+ --------------------------------------------------------------------
+ -- Converts Hex characters to binary representation
+ -- Asserts that no unknown value exists at the time of conversion.
+ --------------------------------------------------------------------
+ procedure Bit2Hex (
+ Vector : in Std_Logic_Vector(3 downto 0);
+ C : out Character;
+ Good : out Boolean);
+ --------------------------------------------------------------------
+ -- Converts bit_vector into a hex string
+ -- Asserts that no unknown value exists at the time of conversion.
+ --------------------------------------------------------------------
+ procedure Vec2Hex (
+ Value : in Std_Logic_Vector(31 downto 0);
+ result : out String(1 to 8);
+ Good : out Boolean);
+ --------------------------------------------------------------------
+ -- read a number from the line
+ -- use this if you have hex numbers that are not in VHDL pound-sign format
+ --------------------------------------------------------------------
+ procedure Read (
+ L : inout Line;
+ value : out Integer;
+ radix : in Positive);
+ --------------------------------------------------------------------
+ -- reads a hex value and returns a bit_vector value
+ --------------------------------------------------------------------
+ procedure ReadHex (
+ L : inout Line;
+ Value : out Std_Logic_Vector;
+ Good : out Boolean;
+ Enable: out Std_Logic_Vector);
+ --------------------------------------------------------------------
+ -- Implements the parsing of the cmd file, which specifies the tasks
+ -- that are applied to the processor.
+ --------------------------------------------------------------------
+ procedure FileParser (
+ constant file_name : in String;
+ variable Commands : inout CommandArray;
+ variable NumCommands : out Natural;
+ variable ErrFlag : inout Boolean);
+end PCI_Def; --============== End of package header =================--
+--
+library IEEE;
+use IEEE.Std_Logic_1164.all;
+library std;
+use std.textio.all;
+--
+package body PCI_Def is
+ --------------------------------------------------------------------
+ -- convert a character to a value from 0 to 15
+ --------------------------------------------------------------------
+ function digit_value (
+ C : Character)
+ return integer is
+ constant not_digit : integer := -999;
+ begin
+ if (C ='X') and (C ='x') then
+ return 15;
+ end if;
+ if (C >= '0') and (C <= '9') then
+ return (Character'pos(C) - Character'pos('0'));
+ elsif (C >= 'a') and (C <= 'f') then
+ return (character'pos(c) - character'pos('a') + 10);
+ elsif (C >= 'A') and (C <= 'F') then
+ return (character'pos(c) - character'pos('A') + 10);
+ else
+ return not_digit;
+ end if;
+ end digit_value;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ function Vec2Int (
+ InVector : in Std_Logic_Vector(15 downto 0))
+ return Integer is
+ constant HeaderMsg : String := "To_Integer:";
+ constant MsgSeverity : Severity_Level := Warning;
+ variable Value : Integer := 0;
+ begin
+ if InVector = "UUUUUUUUUUUUUUUU" then
+ report HeaderMsg&"The input vector is of type 'U'. Converted to 0"
+ severity MsgSeverity;
+ elsif InVector = "XXXXXXXXXXXXXXXX" then
+ report HeaderMsg&"The input vector is of type 'X'. Converted to 0"
+ severity MsgSeverity;
+ elsif InVector = "WWWWWWWWWWWWWWWW" then
+ report HeaderMsg&"The input vector is of type 'W'. Converted to 0"
+ severity MsgSeverity;
+ elsif InVector = "ZZZZZZZZZZZZZZZZ" then
+ report HeaderMsg&"The input vector is of type 'Z'. Converted to 0"
+ severity MsgSeverity;
+ else
+ for i in 0 to 15 loop
+ if (InVector(i) = '1') then
+ Value := Value + (2**I);
+ end if;
+ end loop;
+ end if;
+ return Value;
+ end Vec2Int;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ function Byte2Int (
+ InVector : in Std_Logic_Vector(7 downto 0))
+ return Integer is
+ constant HeaderMsg : String := "To_Integer:";
+ constant MsgSeverity : Severity_Level := Warning;
+ variable Value : Integer := 0;
+ begin
+ for i in 0 to 7 loop
+ if (InVector(i) = '1') then
+ Value := Value + (2**I);
+ end if;
+ end loop;
+ return Value;
+ end Byte2Int;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure Hex2Bit (
+ C : in Character;
+ Vector : out Std_Logic_Vector(3 downto 0);
+ Good : out Boolean) is
+ variable Good1 : Boolean := false;
+ constant HeaderMsg : String := "Hex2Bit:";
+ constant MsgSeverity : Severity_Level := Error;
+ begin
+ Good := false;
+ case C is
+ when '0' => Vector := "0000"; Good1 := true;
+ when '1' => Vector := "0001"; Good1 := true;
+ when '2' => Vector := "0010"; Good1 := true;
+ when '3' => Vector := "0011"; Good1 := true;
+ when '4' => Vector := "0100"; Good1 := true;
+ when '5' => Vector := "0101"; Good1 := true;
+ when '6' => Vector := "0110"; Good1 := true;
+ when '7' => Vector := "0111"; Good1 := true;
+ when '8' => Vector := "1000"; Good1 := true;
+ when '9' => Vector := "1001"; Good1 := true;
+ when 'A'|'a' => Vector := "1010"; Good1 := true;
+ when 'B'|'b' => Vector := "1011"; Good1 := true;
+ when 'C'|'c' => Vector := "1100"; Good1 := true;
+ when 'D'|'d' => Vector := "1101"; Good1 := true;
+ when 'E'|'e' => Vector := "1110"; Good1 := true;
+ when 'F'|'f' => Vector := "1111"; Good1 := true;
+ -- extended for std_LOGIC --
+ when 'U'|'u' => Vector := "UUUU"; Good1 := true;
+ when 'X'|'x' => Vector := "1111"; Good1 := true;
+ when 'Z'|'z' => Vector := "ZZZZ"; Good1 := true;
+ when 'W'|'w' => Vector := "WWWW"; Good1 := true;
+ when 'L'|'l' => Vector := "LLLL"; Good1 := true;
+ when 'H'|'h' => Vector := "HHHH"; Good1 := true;
+ when '-' => Vector := "----"; Good1 := true;
+ when others => Good1 := false;
+ end case;
+ if not Good1 then
+ Vector := "0000";
+ report HeaderMsg&"Expected a Hex character (0-F)"
+ severity MsgSeverity;
+ end if;
+ Good := Good1;
+ end Hex2Bit;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure Bit2Hex (
+ Vector : Std_Logic_Vector(3 downto 0);
+ C : out Character;
+ Good : out Boolean) is
+ variable Good1 : Boolean := false;
+ constant HeaderMsg : String := "Bit2Hex: ";
+ constant MsgSeverity : Severity_Level := Error;
+ begin
+ Good := false;
+ case Vector is
+ when x"0" => C := '0'; Good1 := true;
+ when x"1" => C := '1'; Good1 := true;
+ when x"2" => C := '2'; Good1 := true;
+ when x"3" => C := '3'; Good1 := true;
+ when x"4" => C := '4'; Good1 := true;
+ when x"5" => C := '5'; Good1 := true;
+ when x"6" => C := '6'; Good1 := true;
+ when x"7" => C := '7'; Good1 := true;
+ when x"8" => C := '8'; Good1 := true;
+ when x"9" => C := '9'; Good1 := true;
+ when x"A" => C := 'A'; Good1 := true;
+ when x"B" => C := 'B'; Good1 := true;
+ when x"C" => C := 'C'; Good1 := true;
+ when x"D" => C := 'D'; Good1 := true;
+ when x"E" => C := 'E'; Good1 := true;
+ when x"F" => C := 'F'; Good1 := true;
+ when "ZZZZ" => C := 'Z'; Good1 := true;
+ when others => Good1 := false;
+ end case;
+ if not Good1 then
+ C := '0';
+ report HeaderMsg&"Expected a Hex character (0-F)"
+ severity MsgSeverity;
+ end if;
+ Good := Good1;
+ end Bit2Hex;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure Vec2Hex (
+ Value : in Std_Logic_Vector(31 downto 0);
+ Result : out String(1 to 8);
+ GOOD : out BOOLEAN) is
+ variable OK : Boolean;
+ variable C : Character;
+ constant NE : Integer := value'length/4; -- number of Hex chars
+ variable BV : Std_Logic_Vector(value'length-1 downto 0) := Value;
+ variable Res : String(1 to 8);
+ constant HeaderMsg : String := "Vec2Hex: ";
+ constant MsgSeverity : Severity_Level := Error;
+ begin
+ if Value'length mod 4 /= 0 then -- Testing if Vector is mod 4
+ Good := false;
+ report HeaderMsg&"The length of input vector is not modulo 4!"
+ severity MsgSeverity;
+ return;
+ end if;
+ Bit2Hex(BV(3 downto 0), C, OK); -- Conversion of the 4 LSB bits
+ if not OK then
+ Good := false;
+ return;
+ end if;
+ Res := C & Res(2 to NE); -- Places first Char in Result
+ for i in 1 to NE-1 loop
+ Bit2Hex(BV(4*i+3 downto 4*i), C, OK); -- Converts next Char
+ if not OK then
+ Good := false;
+ return;
+ end if;
+ Res := Res(1 to i) & C & Res(i+2 to NE);
+ end loop;
+ for i in 0 to NE-1 loop
+ Result (1+i) := Res (NE-i);
+ end loop;
+ Good := true;
+ end Vec2Hex;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure Read (
+ L : inout line;
+ Value : out integer;
+ Radix : in positive) is
+ constant not_digit : integer := -999;
+ variable Digit : integer;
+ variable Result : integer := 0;
+ variable Pos : integer;
+ begin
+ -- calculate the value
+ if (L'length <=0 ) then
+ for i in Pos to L'right loop
+ digit := digit_value(L(i));
+ exit when (Digit = not_digit) or (digit >= radix);
+ Result := Result * Radix + digit;
+ Pos := Pos + 1;
+ end loop;
+ Value := Result;
+ end if;
+ end Read;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure ReadHex (
+ L : inout Line;
+ Value : out Std_Logic_Vector;
+ Good : out Boolean;
+ Enable : out Std_Logic_Vector) is
+ variable OK : Boolean;
+ variable C : Character;
+ constant NE : Integer := value'length/4;
+ variable BV : Std_Logic_Vector(value'length-1 downto 0);
+ variable TEMP : Std_Logic_Vector(value'length-1 downto 0);
+ variable S : String(1 to NE-1);
+ constant HeaderMsg : String := "Vec2Hex";
+ constant MsgSeverity : Severity_Level := Warning;
+ begin
+ Enable(3 downto 0) :="0000";
+ if Value'length mod 4 /= 0 then -- Testing if Vector is mod 4
+ Good := false;
+ report HeaderMsg&"The length of input vector is not modulo 4!"
+ severity MsgSeverity;
+ return;
+ end if;
+ loop
+ read(L, C, OK); -- Finds the first Hex Char
+ exit when (((C /= ' ') and (C /= CR) and (C /= HT)) or
+ (L'length = 0));
+ end loop;
+ Hex2Bit(C, BV( 3 downto 0), OK); -- Converts first Hex Char to 4 Bits
+ if C ='X' or C ='x' then
+ Enable(3) :='1';
+ end if;
+
+ if not OK then
+ Good := false;
+ return;
+ end if;
+ read(L, S, OK); -- Reads the next three Hex Chars
+ if not OK then
+ Good := false;
+ return;
+ end if;
+ for i in 1 to NE-1 loop
+ if s(i) ='X' or s(i) ='x' then
+ if i=1 then
+ Enable(3):='1';
+ end if;
+ if i=2 or i=3 then
+ Enable(2):='1';
+ end if;
+ if i=4 or i=5 then
+ Enable(1):='1';
+ end if;
+ if i=6 or i=7 then
+ Enable(0):='1';
+ end if;
+ end if;
+ Hex2Bit(s(i), BV(4*i+3 downto 4*i), OK); -- Converts to BitVector
+ if not OK then
+ Good := false;
+ return;
+ end if;
+ end loop;
+ Good := true;
+
+ -- for byte
+ if (value'length = 8 ) then
+ for i in 0 to 3 loop
+ TEMP(i) := BV(value'length-4+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+4) := BV(value'length-8+i);
+ end loop;
+ end if;
+
+ -- for word
+ if (value'length = 16 ) then
+ for i in 0 to 3 loop
+ TEMP(i) := BV(value'length-4+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+4) := BV(value'length-8+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+8) := BV(value'length-12+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+12) := BV(value'length-16+i);
+ end loop;
+ end if;
+
+ -- for DWORD
+ if (value'length =32 ) then
+ for i in 0 to 3 loop
+ TEMP(i) := BV(value'length-4+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+4) := BV(value'length-8+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+8) := BV(value'length-12+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+12) := BV(value'length-16+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+16) := BV(value'length-20+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+20) := BV(value'length-24+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+24) := BV(value'length-28+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+28) := BV(value'length-32+i);
+ end loop;
+ end if;
+
+ Value := TEMP;
+ end ReadHex;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure FileParser (
+ constant file_name : in String ;
+ variable Commands : inout CommandArray;
+ variable NumCommands : out Natural;
+ variable ErrFlag : inout Boolean) is
+ File CmdFile : text;
+ constant HeaderMsg : String := "FileParser:";
+ constant MsgSeverity : Severity_Level := Error;
+ variable L : Line := NULL;
+ variable Linenum : Natural := 0;
+ variable LblNum : Natural := 0;
+ variable CmdNum : Natural := 0;
+ variable EndOfFile : Boolean := false;
+ variable Good : Boolean := false;
+ variable Int : Integer;
+ variable Tm : Time;
+ variable C : Character;
+ variable Addr : Std_Logic_Vector(31 downto 0);
+ variable Data : Std_Logic_Vector(31 downto 0);
+ variable Enable : Std_Logic_Vector(3 downto 0);
+ variable Vect_count : Std_Logic_Vector(7 downto 0);
+ variable Data_word : Std_Logic_Vector(15 downto 0);
+ variable Data_byte : Std_Logic_Vector(7 downto 0);
+ variable str4 : string(1 to 4);
+ variable count_nr : Integer;
+ variable count : Integer;
+ begin
+ ErrFlag := false;
+ FILE_OPEN(CmdFile,file_name,READ_MODE);
+ loop
+ readline(CmdFile,L);
+ EndOfFile := endfile(CmdFile);
+ CmdNum := CmdNum + 1;
+ LineNum := LineNum + 1;
+ read(L, str4, Good);
+ if not Good then
+ CmdNum := CmdNum-1;
+ else
+ case str4 is
+ when "WRSW" => -- write single word command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid WRSW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_byte,Good,Enable);
+ count_nr := Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "WRSW";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in WRSW command ";
+ end if;
+ end loop;
+ end if;
+
+ when "RDSW" => -- read single word command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid RDSW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "RDSW";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in RDSW command ";
+ end if;
+ end loop;
+ end if;
+
+ when "WRMW" => -- write multiple words command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid WRMW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "WRMW";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in WRMW command ";
+ end if;
+ end loop;
+ end if;
+
+ when "RDMW" => -- read multiple words command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid RDMW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_Byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "RDMW";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in RDMW command ";
+ end if;
+ end loop;
+ end if;
+
+ when "RDML" => -- read multiple words command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid RDML command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_Byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "RDML";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in RDML command ";
+ end if;
+ end loop;
+ end if;
+
+ when "WCFG" => -- write to configuration space command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid WCFG command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "WCFG";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in WCFG command ";
+ end if;
+ end loop;
+ end if;
+
+ when "RCFG" => -- read from configuration space command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid RCFG command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_Byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "RCFG";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in RCFG command ";
+ end if;
+ end loop;
+ end if;
+
+ when "WRIO" => -- write to I/O space command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid WRIO command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good = true) then
+ count := count + 1;
+ commands(CmdNum).command := "WRIO";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in WRIO command ";
+ end if;
+ end loop;
+ end if;
+
+ when "RDIO" => -- read from I/O space command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid RDIO command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_Byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good = true) then
+ count := count + 1;
+ commands(CmdNum).command := "RDIO";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in RDIO command ";
+ end if;
+ end loop;
+ end if;
+
+ when "CWAT" =>
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid CWAT command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ count_nr :=0;
+ readhex(L,Data,Good,Enable);
+ if (Good = true) then
+ count :=count +1;
+ commands(CmdNum).command := "WAIT";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(1) := Data;
+ commands(CmdNum).data_nr := 1;
+ commands(CmdNum).enable(1) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in CWAT command ";
+ end if;
+ end if;
+
+ when "ABRT" =>
+ count :=count + 1;
+ commands(CmdNum).command := "ABRT";
+ commands(CmdNum).addr := "00000000000000000000000000000000";
+ commands(CmdNum).data(1) := "00000000000000000000000000000000";
+ commands(CmdNum).data_nr := 1;
+ commands(CmdNum).enable(1) := Enable;
+
+ when others =>
+ CmdNum := CmdNum -1;
+ if str4(1 to 2)/= "##" then
+ report HeaderMsg & "Invalid command in file: "&file_name&", line #"& integer'image(LineNum) &", "& "Unknown command : "& str4 & l(l'left to l'right)
+ severity error;
+ ErrFlag := true;
+ end if;
+ end case;
+ end if;
+ NumCommands := CmdNum;
+ Exit when EndOfFile;
+ end loop;
+ end FileParser;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+end PCI_Def; --================ End of package body ================--
Index: pci_core/trunk/vhdl_behav/Test_pci.vhd
===================================================================
--- pci_core/trunk/vhdl_behav/Test_pci.vhd (nonexistent)
+++ pci_core/trunk/vhdl_behav/Test_pci.vhd (revision 10)
@@ -0,0 +1,226 @@
+--===================================================================--
+--
+-- www.OpenCores.Org - January 2000
+-- This model adheres to the GNU public license
+--
+-- Design units : TestBench for PCI devices.
+--
+-- File name : Test_PCI.vhd
+--
+-- Purpose : Implements the test bench for PCI 33 MHz, 32 bit devices.
+-- It is included one master device and two target devices.
+--
+-- There can be used more than one target devices in a
+-- design, every device being identified by the three
+-- base addresses in generic.
+--
+--
+-- Library : PCI_Lib
+--
+-- Dependencies : IEEE.Std_Logic_1164
+--
+-- Limitations : None known
+--
+-- Errors : None known
+--
+-- Author : Ovidiu Lupas
+-- olupas@opencores.org
+--
+-- Simulator : ModelSim EE version 5.2 on a Windows95 PC
+-- ActiveVHDL 3.1 on a Windows95 PC
+--===================================================================--
+-----------------------------------------------------------------------
+-- Entity for PCI bus Arbiter and CLK generator
+-----------------------------------------------------------------------
+library ieee,work;
+ use ieee.Std_Logic_1164.all;
+ use work.Simulation.all;
+ use work.PCI_Def.all;
+-----------------------------------------------------------------------
+-----------------------------------------------------------------------
+entity ClkGen is
+ generic ( tperiod : Time := 30 ns );
+ port (
+ REQ_N : in Std_Logic;
+ GNT_N : out Std_Logic := '1';
+ RST_N : out Std_Logic;
+ CLK : out Std_Logic); -- System clock
+end ClkGen; --=================== End of entity =====================--
+--========================== Architecture ===========================--
+architecture BEHAV_ClkGen of ClkGen is
+begin--======================== Architecture =================================--
+ ---------------------------------------------------------------------
+ -- Provide the external clock signal to the processor
+ ---------------------------------------------------------------------
+ ClkDriver : process
+ variable clktmp: std_logic := '0';
+ begin
+ CLK <= clktmp;
+ clktmp := not clktmp;
+ wait for tperiod/2;
+ end process ClkDriver;
+ ---------------------------------------------------------------------
+ -- Simulates an external PCI-bus arbiter, which always grants the
+ -- access to the bus :)
+ ---------------------------------------------------------------------
+ Arbiter : process(REQ_N)
+ begin
+ if Falling_Edge(REQ_N) then
+ GNT_N <= '0' after 10 ns;
+ elsif Rising_Edge(REQ_N) then
+ GNT_N <= '1' after 10 ns;
+ end if;
+ end process Arbiter;
+ ---------------------------------------------------------------------
+ -- Provides the reset signal
+ ---------------------------------------------------------------------
+ RstGen: process
+ begin
+ RST_N <= '0';
+ wait for 100 ns;
+ RST_N <= '1';
+ wait for 400 ns;
+ end process;
+end BEHAV_ClkGen; --============== End of architecture ==============--
+-----------------------------------------------------------------------
+-- TestBench
+-----------------------------------------------------------------------
+library ieee,work,std;
+ use ieee.std_logic_1164.all;
+ use work.ClkGen;
+-----------------------------------------------------------------------
+-----------------------------------------------------------------------
+entity TESTPCI is
+end TESTPCI;
+--========================== Architecture ===========================--
+architecture stimulus of TESTPCI is
+ ---------------------------------------------------------------------
+ -- Signal declaration
+ ---------------------------------------------------------------------
+ signal AD_Bus : Std_Logic_Vector (31 downto 0);
+ signal C_BE_Bus : Std_Logic_Vector (3 downto 0);
+ signal PAR : Std_Logic;
+ signal FRAME_N : Std_Logic;
+ signal TRDY_N : Std_Logic;
+ signal IRDY_N : Std_Logic;
+ signal STOP_N : Std_Logic;
+ signal DEVSEL_N : Std_Logic;
+ signal IDSEL : Std_Logic;
+ signal SEL1 : Std_Logic;
+ signal SEL2 : Std_Logic;
+ signal PERR_N : Std_Logic;
+ signal SERR_N : Std_Logic;
+ signal REQ_N : Std_Logic;
+ signal GNT_N : Std_Logic;
+ signal CLK : Std_Logic;
+ signal RST_N : Std_Logic;
+ ---------------------------------------------------------------------
+ -- Component declarations
+ ---------------------------------------------------------------------
+ component ClkGen
+ generic ( tperiod : Time := 30 ns );
+ port (
+ REQ_N : in Std_Logic;
+ GNT_N : out Std_Logic;
+ RST_N : out Std_Logic;
+ CLK : out Std_Logic); -- System clock
+ end component;
+ ---------------------------------------------------------------------
+ ---------------------------------------------------------------------
+ component MS32PCI
+ generic (
+ cmd_file : string(1 to 7);
+ tdelay : Time;
+ tsetup : Time;
+ thold : Time);
+ 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; -- in
+ -- 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; -- in
+ -- System signals (2)
+ CLK : in STD_LOGIC;
+ RST_N : in STD_LOGIC); --in
+ end component;
+ ---------------------------------------------------------------------
+ ---------------------------------------------------------------------
+ component TG32PCI
+ generic (
+ devtype : string(1 to 4);
+ tdelay : Time;
+ tsetup : Time;
+ thold : Time;
+ bamem : Std_Logic_Vector(31 downto 0); -- hex value
+ baio : Std_Logic_Vector(31 downto 0); -- hex value
+ bacfg : Std_Logic_Vector(31 downto 0));-- hex value
+ port (
+ -- Address, Data and Command buses (37)
+ AD_Bus : inout Std_Logic_Vector (31 downto 0);
+ C_BE_Bus : in Std_Logic_Vector (3 downto 0);
+ PAR : inout Std_Logic;
+ -- Interface control signals (6)
+ FRAME_N : in Std_Logic;
+ TRDY_N : inout Std_Logic;
+ IRDY_N : in Std_Logic;
+ STOP_N : out Std_Logic;
+ DEVSEL_N : inout Std_Logic;
+ IDSEL : in Std_Logic;
+ -- Error reporting signals (2)
+ PERR_N : inout Std_Logic;
+ SERR_N : inout Std_Logic;
+ -- System signals (2)
+ CLK : in Std_Logic;
+ RST_N : in Std_Logic);
+ end component;
+begin --====================== Architecture =========================--
+ ---------------------------------------------------------------------
+ -- Component instantiation
+ ---------------------------------------------------------------------
+ UUT1: MS32PCI
+ generic map (
+ "PCI.CMD",0 ns, 7 ns, 5 ns)
+ port map (
+ AD_Bus,C_BE_Bus,PAR,FRAME_N,TRDY_N,IRDY_N,STOP_N,DEVSEL_N,
+ IDSEL,PERR_N,SERR_N,REQ_N,GNT_N,CLK,RST_N);
+ SEL1 <= AD_Bus(16);
+ UUT2: TG32PCI
+ generic map (
+ "Fast",0 ns,0 ns,0 ns,x"00005000",x"00000800",x"00010CF0")
+ port map (
+ AD_Bus => AD_Bus,C_BE_Bus => C_BE_Bus,PAR => PAR,
+ FRAME_N => FRAME_N,TRDY_N => TRDY_N,IRDY_N => IRDY_N,
+ STOP_N => STOP_N,DEVSEL_N => DEVSEL_N,IDSEL => SEL1,
+ PERR_N => PERR_N,SERR_N => SERR_N,CLK => CLK,RST_N => RST_N);
+ SEL2 <= AD_Bus(17);
+ UUT3: TG32PCI
+ generic map (
+ "Medi",0 ns,7 ns,0 ns,x"00006000",x"00001800",x"00020CF0")
+ port map (
+ AD_Bus => AD_Bus,C_BE_Bus => C_BE_Bus,PAR => PAR,
+ FRAME_N => FRAME_N,TRDY_N => TRDY_N,IRDY_N => IRDY_N,
+ STOP_N => STOP_N,DEVSEL_N => DEVSEL_N,IDSEL => SEL2,
+ PERR_N => PERR_N,SERR_N => SERR_N,CLK => CLK,RST_N => RST_N);
+ GEN: ClkGen port map (
+ REQ_N,GNT_N,RST_N,CLK);
+ ---------------------------------------------------------------------
+end stimulus; --=============== End of architecture =================--
+-----------------------------------------------------------------------
+-- Revision list
+-- Version Author Date Changes
+--
+-- 0.1 Ovidiu Lupas June 09, 2000 New model
+-----------------------------------------------------------------------
+
Index: pci_core/trunk/vhdl_behav/PCI.CMD
===================================================================
--- pci_core/trunk/vhdl_behav/PCI.CMD (nonexistent)
+++ pci_core/trunk/vhdl_behav/PCI.CMD (revision 10)
@@ -0,0 +1,59 @@
+## CONFIGURE THE FIRST TARGET DEVICE
+## WAIT ADDRESS DATA
+CWAT 00010CF0 0710FF00
+## I/O WRITE DWORD ADDRESS NR. DATA
+WRIO 00000850 01 AABBCCDD
+##
+## I/O READ DWORD ADDRESS NR. DATA
+RDIO 00000850 01 AAXXCCDD
+##
+## I/O WRITE DWORD ADDRESS NR. DATA
+WRIO 00000864 04 AABBCCDD EE00AABB CCDDEE00 AABBCCDD
+##
+## I/O READ DWORD ADDRESS NR. DATA
+RDIO 00000864 04 XXBBXXDD EEXXAABB CCDDXX00 XXBBXXDD
+##
+## CONFIGURE THE SECOND TARGET DEVICE
+## WAIT ADDRESS DATA
+CWAT 00020CF0 0710FF00
+## I/O WRITE DWORD ADDRESS NR. DATA
+WRIO 00001850 01 AABBCCDD
+##
+## I/O READ DWORD ADDRESS NR. DATA
+RDIO 00001850 01 AABBCCDD
+##
+## I/O WRITE DWORD ADDRESS NR. DATA
+WRIO 00001860 03 AABBCCDD EE00AABB CCDDEE00
+##
+## I/O READ DWORD ADDRESS NR. DATA
+RDIO 00001860 03 AABBCCDD EE00AABB CCDDEE00
+##
+## MEMORY WRITE DWORD ADDRESS NR. DATA
+WRSW 00005001 01 55AA66BB
+##
+## MEMORY READ DWORD ADDRESS NR. DATA
+RDSW 00005001 01 55AA66BB
+##
+## MEMORY MULTIPLE WRITE ADDRESS NR. DATA
+WRMW 00005000 02 66AA55BB CCDDBBEE
+##
+## MEMORY MULTIPLE READ ADDRESS NR. DATA
+RDMW 00005000 02 XXAAXXBB CCDDXXEE
+##
+## MEMORY MULTIPLE WRITE ADDRESS NR. DATA
+WRMW 00006010 04 66AA55BB CCDDBBEE 33664455 00000001
+##
+## MEMORY MULTIPLE READ ADDRESS NR. DATA
+RDMW 00006010 04 XXAAXXBB CCDDXXEE 33XX4455 00000001
+##
+## MEMORY READ LINE ADDRESS NR. DATA
+## RDML 00005000 04 00000000 00000000 00000000 00000000
+##
+## CONFIG WRITE DWORD ADDRESS NR. DATA
+WCFG 00010CF8 01 20000001
+##
+## CONFIG READ DWORD ADDRESS NR. DATA
+RCFG 00010CF8 01 20000001
+##
+## EXIT
+ABRT
pci_core/trunk/vhdl_behav/PCI.CMD
Property changes :
Added: svn:executable
## -0,0 +1 ##
+*
\ No newline at end of property
Index: pci_core/trunk/TestBench/pci_parity_tb.vhd
===================================================================
--- pci_core/trunk/TestBench/pci_parity_tb.vhd (nonexistent)
+++ pci_core/trunk/TestBench/pci_parity_tb.vhd (revision 10)
@@ -0,0 +1,149 @@
+-------------------------------------------------------------------------------
+-- Title : PCI Parity test bench
+-- Project : PCI target Core
+-------------------------------------------------------------------------------
+-- File : pci_parity_tb.VHD
+-- Author : Jamil Khatib
+-- Organization: OpenCores Project
+-- Created : 2000/04/1
+-- Last update : 2000/04/1
+-- Platform :
+-- Simulators : Modelsim 5.3 XE / Windows98
+-- Synthesizers:
+-- Target :
+-- Dependency :
+-------------------------------------------------------------------------------
+-- Description: PCI Parity test bench
+-------------------------------------------------------------------------------
+-- Copyright (c) 2000 Jamil Khatib
+--
+-- This VHDL design file is an open design; you can redistribute it and/or
+-- modify it and/or implement it under the terms of the Openip General Public
+-- License as it is going to be published by the OpenIPCore Organization and
+-- any coming versions of this license.
+-- You can check the draft license at
+-- http://www.openip.org/oc/license.html
+--
+-------------------------------------------------------------------------------
+-- Revisions :
+-- Revision Number : 1
+-- Version : 1.0
+-- Date : 2st Apr 2000
+-- Modifier : Jamil Khatib (khatib@ieee.org)
+-- Desccription : Created
+--
+-- Known bugs :
+-------------------------------------------------------------------------------
+library ieee;
+use ieee.std_logic_1164.all;
+
+entity parity_tb is
+
+end parity_tb;
+
+architecture behavior_tb of parity_tb is
+ component parity
+
+ port (
+ -- PCI Interface
+ CLK : in std_logic; -- PCI clock
+ AD : in std_logic_vector(31 downto 0); -- PCI AD signal
+ CBE : in std_logic_vector(3 downto 0); -- C/BE PCI bus signals
+ PAR : inout std_logic; -- PAR signal
+ SERR_n : inout std_logic; -- SERR# signal
+ PERR_n : out std_logic; -- PERR# signal
+ -- PERR# signal is output only for target
+ -- Local Interface
+ ParOperation : in std_logic; -- Parity Operation
+ -- Drive PAR or check it
+ Par_oe : in std_logic; -- PAR Output Enable
+ Locserr_n : in std_logic; -- Local System Error
+ LocErrRep_n : out std_logic); -- Local Error Report
+ -- used to report parity errors for local interface
+ -- and to the configuration register
+ end component;
+
+ signal clk_tb : std_logic := '0'; -- clock
+ signal ad_tb : std_logic_vector(31 downto 0); -- AD signal
+ signal cbe_tb : std_logic_vector(3 downto 0); -- C/BE signal
+ signal par_tb : std_logic;
+ signal serr_tb : std_logic;
+ signal perr_tb : std_logic;
+
+ signal paroperation_tb : std_logic;
+ signal paroe_tb : std_logic;
+ signal locserr_tb : std_logic;
+ signal locerrrep_tb : std_logic;
+
+ signal par_syn_tb : std_logic;
+ signal serr_syn_tb : std_logic;
+ signal perr_syn_tb : std_logic;
+ signal locerrrep_syn_tb : std_logic;
+
+begin -- behavior_tb
+
+ clk_tb <= not clk_tb after 30 ns;
+
+ UUT : parity
+ port map (
+ CLK => clk_tb,
+ AD => ad_tb,
+ CBE => cbe_tb,
+ PAR => par_tb,
+ SERR_n => serr_tb,
+ PERR_n => perr_tb,
+ ParOperation => paroperation_tb,
+ Par_oe => paroe_tb,
+ Locserr_n => locserr_tb,
+ LocErrRep_n => locerrrep_tb);
+-------------------------------------------------------------------------------
+
+ UUT_syn : parity
+ port map (
+ CLK => clk_tb,
+ AD => ad_tb,
+ CBE => cbe_tb,
+ PAR => par_syn_tb,
+ SERR_n => serr_syn_tb,
+ PERR_n => perr_syn_tb,
+ ParOperation => paroperation_tb,
+ Par_oe => paroe_tb,
+ Locserr_n => locserr_tb,
+ LocErrRep_n => locerrrep_syn_tb);
+
+
+ par_tb <= transport 'Z' after 0 ns,
+ '1' after 400 ns;
+
+ par_syn_tb <= transport 'Z' after 0 ns,
+ '1' after 400 ns;
+
+ ad_tb <= (others => '1');
+ cbe_tb <= transport "1111" after 0 ns,
+ "1000" after 200 ns,
+ "1111" after 400 ns,
+ "1000" after 600 ns;
+
+ paroperation_tb <= transport '1' after 0 ns,
+ '0' after 400 ns;
+ paroe_tb <= transport '1' after 0 ns,
+ '0' after 800 ns;
+ locserr_tb <= '1';
+
+
+
+end behavior_tb;
+
+-- Test bench Configuration
+configuration TESTBENCH_FOR_parity of parity_tb is
+ for behavior_tb
+ for UUT : parity
+ use entity work.parity(behavior);
+ end for;
+
+ for UUT_syn : parity
+ use entity work.parity(STRUCTURE);
+ end for;
+
+ end for;
+end TESTBENCH_FOR_parity;
Index: pci_core/trunk/Blocks/pci_parity.vhd
===================================================================
--- pci_core/trunk/Blocks/pci_parity.vhd (nonexistent)
+++ pci_core/trunk/Blocks/pci_parity.vhd (revision 10)
@@ -0,0 +1,144 @@
+-------------------------------------------------------------------------------
+-- Title : PCI Parity core
+-- Project : PCI target Core
+-------------------------------------------------------------------------------
+-- File : pci_parity.VHD
+-- Author : Jamil Khatib
+-- Organization: OpenCores Project
+-- Created : 2000/04/1
+-- Last update : 2000/04/1
+-- Platform :
+-- Simulators : Modelsim 5.3XE / Windows98
+-- Synthesizers: webfitter - Leonardo / WindowsNT
+-- Target : XC9572XL-5-VQ64 - EPF10K100EQC208 Flex10K
+-- Dependency :
+-------------------------------------------------------------------------------
+-- Description: PCI Parity Core
+-------------------------------------------------------------------------------
+-- Copyright (c) 2000 Jamil Khatib
+--
+-- This VHDL design file is an open design; you can redistribute it and/or
+-- modify it and/or implement it under the terms of the Openip General Public
+-- License as it is going to be published by the OpenIPCore Organization and
+-- any coming versions of this license.
+-- You can check the draft license at
+-- http://www.openip.org/oc/license.html
+--
+-------------------------------------------------------------------------------
+-- Revisions :
+-- Revision Number : 1
+-- Version : 1.0
+-- Date : 1st Apr 2000
+-- Modifier : Jamil Khatib (khatib@ieee.org)
+-- Desccription : Created
+--
+-- Known bugs : Extending the PAR signals to wait states
+-- : SERR is generated upon local side request only
+-- : PERR must remain active two clockcycles after the ERR
+-------------------------------------------------------------------------------
+library ieee;
+use ieee.std_logic_1164.all;
+
+entity parity is
+
+ port (
+ -- PCI Interface
+ CLK : in std_logic; -- PCI clock
+ AD : in std_logic_vector(31 downto 0); -- PCI AD signal
+ CBE : in std_logic_vector(3 downto 0); -- C/BE PCI bus signals
+ PAR : inout std_logic; -- PAR signal
+ SERR_n : inout std_logic; -- SERR# signal
+ PERR_n : out std_logic; -- PERR# signal
+ -- PERR# signal is output only for target
+ -- Local Interface
+ ParOperation : in std_logic; -- Parity Operation
+ -- Drive PAR or check it
+ Par_oe : in std_logic; -- PAR Output Enable
+ Locserr_n : in std_logic; -- Local System Error
+ LocErrRep_n : out std_logic); -- Local Error Report
+ -- used to report parity errors for local interface
+ -- and to the configuration register
+
+end parity;
+
+library ieee;
+use ieee.std_logic_1164.all;
+-------------------------------------------------------------------------------
+architecture behavior of parity is
+
+begin -- behavior
+
+-------------------------------------------------------------------------------
+-- purpose: Parity Generation
+-- type : sequential
+-- inputs : CLK
+-- outputs: PAR, LocErrRep
+ Paritygen : process (CLK)
+
+ variable tmp_par : std_logic; -- temporary parity vriable
+ variable par_q : std_logic; -- Next Par signal
+ variable perr_q : std_logic; -- Next PERR signal
+
+ begin -- process Paritygen
+
+ if CLK'event and CLK = '1' then -- rising clock edge
+ if Par_oe = '1' then
+
+-------------------------------------------------------------------------------
+-- PAR signal states:
+-- Idel: when no operation on the current target or master
+-- PAR = 'Z' , PERR = 'Z'
+-- Master Read:
+-- Address phase:
+-- Master Drives PAR
+-- Target Drives PERR
+-- Data phase:
+-- Target Drives PAR
+-- Master Drives PERR
+-- Master write:
+-- Address and data phase
+-- Master Drives PAR
+-- Master Drives PERR
+-------------------------------------------------------------------------------
+-- ParOperation = 1 Calculate and drive PAR Port
+-- ParOperation = 0 Calculate and report Parity Errors
+-------------------------------------------------------------------------------
+ if ParOperation = '1' then -- Drive PAR signal
+
+ PAR <= par_q;
+ LocErrRep_n <= perr_q;
+ PERR_n <= 'Z';
+
+ else
+
+ PERR_n <= perr_q;
+ PAR <= 'Z';
+
+ end if;
+
+-- No of 1's in AD, CBE & PAR must be even
+ tmp_par := CBE(3) xor CBE(2) xor CBE(1) xor CBE(0);
+
+ for i in AD'range loop
+
+ tmp_par := tmp_par xor AD(i);
+
+ end loop; -- i
+
+ par_q := tmp_par;
+
+ perr_q := tmp_par xor PAR_q;
+
+ else
+
+ PAR <= 'Z';
+ PERR_n <= 'Z';
+
+ end if;
+ end if;
+ end process Paritygen;
+-------------------------------------------------------------------------------
+
+ SERR_n <= Locserr_n;
+-------------------------------------------------------------------------------
+end behavior;
Index: pci_core/trunk/diagrams/pci.dia
===================================================================
--- pci_core/trunk/diagrams/pci.dia (nonexistent)
+++ pci_core/trunk/diagrams/pci.dia (revision 10)
@@ -0,0 +1,64 @@
+VGUIformatVersion 1.004000
+
+
+
+
+DEFINE_MODULE: new_unnamed_submodule0
+
+ DEFINE_DEVICE_INSTANCES:
+ END_DEFINE_DEVICE_INSTANCES.
+
+ DEFINE_TOPOLOGY:
+ END_DEFINE_TOPOLOGY.
+
+
+END_DEFINE_MODULE.
+
+
+
+DEFINE_MODULE: pci_controller
+
+ PORT_LIST( RST_n, CLK, DEVSEL_n, STOP, FRAME_n, TRDY_n,
+ IRDY_n, IDSEL, CBE, AD, SERR_n, PERR_n,
+ PAR );
+
+ DEFINE_DEVICE_INSTANCES:
+ trget_machine = Target_machine | 5.600000 4.400000 6.900000 7.300000
+ Parity = Parity | 5.600000 2.300000 6.800000 4.200000
+ END_DEFINE_DEVICE_INSTANCES.
+
+ DEFINE_TOPOLOGY:
+ Parity parity_PAR pci_controller PAR half-duplex 0 Std_logic L0 3.500000 2.500000 5.600000 2.500000
+ Parity PERR_par_n pci_controller PERR_n half-duplex 0 Std_logic L1 3.500000 2.700000 5.600000 2.700000
+ Parity SERR_par_n pci_controller SERR_n half-duplex 0 Std_logic L2 3.500000 2.900000 5.600000 2.900000
+ trget_machine AD_trgt Parity AD_trgt simplex 0 Std_logic_vector(31#downto#0) AD 5.600000 3.300000 4.300000 3.300000 4.300000 5.500000 5.600000 5.500000
+ pci_controller AD trget_machine AD_trgt half-duplex 0 Std_logic_vector(31#downto#0) AD 5.600000 5.500000 5.300000 5.500000 3.600000 5.500000
+ trget_machine CBE_trgt_n Parity CBE_trgt_n simplex 0 Std_logic_vector(3#downto#0) CBE 5.600000 3.700000 4.500000 3.700000 4.500000 5.700000 5.600000 5.700000
+ pci_controller CBE trget_machine CBE_trgt_n half-duplex 0 Std_logic_vector(3#downto#0) CBE 5.600000 5.700000 3.600000 5.700000
+ pci_controller IDSEL trget_machine IDSEL_trgt simplex 0 Std_logic L7 5.600000 6.000000 3.600000 6.000000
+ pci_controller IRDY_n trget_machine IRDY_trgt_n simplex 0 Std_logic L8 5.600000 6.200000 3.600000 6.200000
+ trget_machine TRDY_trgt_n pci_controller TRDY_n simplex 0 Std_logic L9 3.600000 6.400000 5.600000 6.400000
+ pci_controller FRAME_n trget_machine FRAME_trgt_n simplex 0 Std_logic L10 5.600000 6.600000 3.600000 6.600000
+ trget_machine STOP_trgt_n pci_controller STOP simplex 0 Std_logic L11 3.600000 6.800000 5.600000 6.800000
+ trget_machine DEVSEL_trgt_n pci_controller DEVSEL_n half-duplex 0 Std_logic L12 3.600000 7.000000 5.600000 7.000000
+ pci_controller CLK trget_machine CLK simplex 0 Std_logic CLK 5.600000 4.600000 3.700000 4.600000
+ trget_machine CLK Parity CLK simplex 0 Std_logic CLK 5.600000 4.100000 4.800000 4.100000 4.800000 4.600000 5.600000 4.600000
+ pci_controller RST_n trget_machine RST_n simplex 0 Std_logic RST_n 5.600000 5.000000 3.700000 5.000000
+ trget_machine RST_n Parity RST_n simplex 0 Std_logic RST_n 5.600000 3.900000 4.700000 3.900000 4.700000 5.000000 5.600000 5.000000
+ trget_machine ADDR_trgt DEV_NULL simplex 0 Std_logic_vector(LOCALADD#-#1#downto#0) L17 8.900001 4.600000 6.900000 4.600000
+ trget_machine DATA_trgt DEV_NULL half-duplex 0 Std_logic_vector(31#downto#0) L17 8.900001 4.900000 6.900000 4.900000
+ DEV_NULL unknown_port trget_machine TABORT simplex 0 Std_logic 0 6.900000 7.200000 8.900001 7.200000
+ DEV_NULL _ trget_machine TRETRY simplex 0 Std_logic 0 6.900000 7.000000 8.900001 7.000000
+ END_DEFINE_TOPOLOGY.
+
+GENERIC: LOCALADD : integer := 64
+ ANNOTATION: 3.821249 8.066763 PCI main block diagram
+ ANNOTATION: 3.779719 8.403428 PCI OpenCores group
+ ANNOTATION: 3.788020 8.736729 Jamil Khatib
+ BOUNDINGBOX: 3.700000 7.600000 7.100000 9.000001 7.100000 7.600000 3.700000 7.600000 3.700000 9.000001 7.100000 9.000001
+
+END_DEFINE_MODULE.
+
+
+
+
Index: pci_core/trunk
===================================================================
--- pci_core/trunk (nonexistent)
+++ pci_core/trunk (revision 10)
pci_core/trunk
Property changes :
Added: svn:mergeinfo
## -0,0 +0,0 ##
Index: pci_core/web_uploads
===================================================================
--- pci_core/web_uploads (nonexistent)
+++ pci_core/web_uploads (revision 10)
pci_core/web_uploads
Property changes :
Added: svn:mergeinfo
## -0,0 +0,0 ##
Index: pci_core/branches
===================================================================
--- pci_core/branches (nonexistent)
+++ pci_core/branches (revision 10)
pci_core/branches
Property changes :
Added: svn:mergeinfo
## -0,0 +0,0 ##
Index: pci_core/tags/alpha/vhdl_behav/Ms32pci.vhd
===================================================================
--- pci_core/tags/alpha/vhdl_behav/Ms32pci.vhd (nonexistent)
+++ pci_core/tags/alpha/vhdl_behav/Ms32pci.vhd (revision 10)
@@ -0,0 +1,827 @@
+--===================================================================--
+--
+-- 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
+ end if;
+
+ if DEVSEL_N'Last_Event <= tsetup then
+ report "DEVSEL_N setup time violation"
+ severity Warning;
+ end if;
+
+ --- inset IRDY_N if loop_irdy =1 and nr_irdy >1
+ if loop_irdy =1 then
+ while (nr_irdy > 1) loop
+ IRDY_N <='1' after tdelay;
+ nr_irdy := nr_irdy -1 ;
+ wait until FALLING_EDGE(CLK);
+ end loop;
+ IRDY_N <='0' after tdelay;
+ end if;
+
+ -- terminate cycle because DEVSEL_N is anactive
+ -- (implement command MASTER-ABORT TERMINATION )
+ if start_irdy = 0 then -- terminate cycle
+ stop := true;
+ FRAME_N <='1'; -- after tdelay;
+ end if;
+
+ -- wait until FALLING_EDGE(CLK);
+ -- repeat until all data are read or STOP_N ='0'
+ while ((data_number > 0) and (stop = false)) loop -- read cycle
+ parity_flag <= true;
+ data_number := data_number -1;
+ parity_flag <= true;
+ data_read := data(data_nr - data_number);
+ if data_number = 0 then
+ C_BE_Bus(3 downto 0) <=bus_sel(data_nr) after tdelay;
+ data_read := data(data_nr);
+ else
+ C_BE_Bus(3 downto 0) <=bus_sel(data_nr - data_number+1) after tdelay;
+ data_read := data(data_nr - data_number);
+ end if;
+
+ parity_flag <= true;
+ if data_number =0 then
+ FRAME_N <='1';-- after tdelay;
+ end if;
+
+ -- 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
+ irdy_insert := false;
+ end if;
+
+ if irdy_insert = true and (data_nr - data_number) = loop_irdy then
+ -- insert IRDY ='1' if insert_trdy =true
+ while nr_irdy > 1 loop
+ nr_irdy := nr_irdy -1 ;
+ IRDY_N <= '1' after tdelay; -- insert IRDY
+ -- 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
+ nr_irdy := 1;
+ end if;
+ wait until FALLING_EDGE(CLK);
+ end loop; -- end loop nr_irdy
+ end if; -- end if irdy_insert
+
+ -- IRDY_N <= '0' after tdelay;
+ if data_number = 0 then
+ IRDY_N <= '0' after tdelay;
+ end if;
+ wait until RISING_EDGE(CLK);
+
+ if TRDY_N'Last_Event <= tsetup then -- end of cycle
+ report "TRDY_N setup time violation"
+ severity Warning;
+ end if;
+
+ -- wait for TRDY_N = '0' (maxim 8 clock pulse)
+ while TRDY_N = '1' and trdy_exit = false loop
+ wait until RISING_EDGE(CLK);
+ -- wait maxim 8 clock pulse if TRDY is asserted
+ trdy_stop := trdy_stop -1;
+ if trdy_stop = 0 then
+ stop := true;
+ report "Target is not responding "
+ severity Warning;
+ FRAME_N <= '1';-- after tdelay;
+ IRDY_N <= '1' after tdelay;
+ trdy_exit := true;
+ end if;
+
+ -- 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
+ trdy_exit := true;
+ end if;
+ end loop; -- end loop TRDY_N=1
+
+ Vec2Hex (data_read,str8,Good2);
+ report " EXPECTED DATA= "&str8 &""; -- display expected data
+
+ Vec2Hex (AD_Bus,str8,Good2);
+ report " READ DATA= "&str8 &""; -- display receive data
+
+ if AD_Bus'Last_Event <= tsetup then -- end of cycle
+ report "AD_BUS setup time violation"
+ severity Warning;
+ end if;
+
+ if ((data_number >0) and (stop =false)) then
+ wait until FALLING_EDGE(CLK);
+ end if;
+
+ wait for thold;
+ if AD_Bus'Last_Event <= thold then -- end of cycle
+ report "AD_Bus hold time violation"
+ severity Warning;
+ end if;
+ end loop; -- end loop data_number
+
+ if RESET =1 or STOP_N ='0' or STOP_N ='L' then
+ 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 <= 'H' after tdelay;
+ parity_flag <= false;
+ end if;
+ else
+ --------------------------------------------------------------------
+ -- BEGIN WRITE CYCLE --
+ --------------------------------------------------------------------
+ -- adress phase
+ parity_flag <= false;
+ nr_irdy := nr_irdy;
+ 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_read <= 'Z';
+ parity(address(31 downto 0), bus_cmd(3 downto 0), parity_temp); -- calculate parity of address cycle
+ parity_now <= parity_temp after tdelay;
+ wait until FALLING_EDGE(CLK);
+ -- end adress phase
+
+ REQ_N <='1';
+
+ parity_flag <= false;
+ IRDY_N <= '0' after tdelay;
+ -- wait for 1 ns;
+ -- wait for DEVSEL_N = '0'
+ -- (implement command MASTER-ABORT TERMINATION if TARGET not respond)
+ while ((start_irdy > 0) and (DEVSEL_N ='H' or DEVSEL_N ='Z' or DEVSEL_N ='X') ) loop -- wait for the number of IRDY state
+ start_irdy := start_irdy -1; -- from the begining of read cycle
+ wait until FALLING_EDGE(CLK);
+ end loop;
+
+ -- if device not respond then exits the write command
+ if start_irdy = 0 then -- terminate cycle
+ stop := true;
+ FRAME_N <= '1';-- after tdelay;
+ end if;
+
+ if DEVSEL_N'Last_Event <= tsetup then
+ report "DEVSEL_N setup time violation"
+ severity Warning;
+ end if;
+
+ while ((data_number >0) and (stop =false)) loop
+ -- data phase
+ data_number := data_number -1;
+ AD_Bus(31 downto 0) <= data(data_nr - data_number) after tdelay; -- set DATA
+ C_BE_Bus(3 downto 0) <= bus_sel(data_nr - data_number) after tdelay; -- set BE#s
+ IRDY_N <= '0' after tdelay;
+ parity(data(data_nr - data_number), bus_sel(data_nr - data_number), parity_temp); -- calculate parity
+ parity_now <= parity_temp after tdelay;
+ -- end data phase
+
+ if data_number = 0 then
+ FRAME_N <= '1';-- after tdelay;
+ end if;
+
+ -- exit cycle if RST_N,GNT_N or STOP_N are active
+ if RESET = 1 or STOP_N= '0' or STOP_N = 'L' then
+ stop := true; -- exit cycle
+ end if;
+
+ wait until RISING_EDGE(CLK);
+
+ if TRDY_N'Last_Event <= tsetup then -- end of cycle
+ report "TRDY_N setup time violation"
+ severity Warning;
+ end if;
+
+ -- wait for TRDY_N ='0'
+ while TRDY_N ='1' and trdy_exit = false loop
+ wait until RISING_EDGE(CLK);
+ -- wait maxim 8 clock pulse if TRDY is asserted
+ trdy_stop := trdy_stop -1;
+ if trdy_stop = 0 then
+ stop := true;
+ report "Target is not responding "
+ severity Warning;
+ FRAME_N <= '1';-- after tdelay;
+ IRDY_N <= '1' after tdelay;
+ trdy_exit := true;
+ end if;
+
+ -- exit cycle if RST_N,GNT_N or STOP_N are active
+ if RESET = 1 or STOP_N = '0' or STOP_N = 'L' then
+ stop := true; -- exit cycle
+ trdy_exit := true;
+ end if;
+ end loop; -- end loop TRDY=1
+
+ if ((data_number > 0) and (stop = false)) then
+ wait until FALLING_EDGE(CLK); -- synchronize with PCICLK
+ end if;
+ -- insert IRDY_N
+ if irdy_insert = true and (data_nr -data_number) = loop_irdy
+ and data_number >0 and (stop =false) then
+ while nr_irdy > 1 loop
+ IRDY_N <='1' after tdelay;
+ nr_irdy := nr_irdy -1 ;
+ if nr_irdy > 0 then
+ if data_number > 0 then
+ C_BE_Bus(3 downto 0) <=bus_sel(data_nr - data_number +1) after tdelay; -- set BE#s
+ parity(data(data_nr - data_number), bus_sel(data_nr - data_number+1), parity_temp); -- calculate parity
+ parity_now <= parity_temp after tdelay;
+ end if;
+ wait until FALLING_EDGE(CLK);
+ end if;
+
+ if RESET = 1 or STOP_N = '0' or STOP_N = 'L' then
+ stop := true; -- exit cycle
+ nr_irdy := 1;
+ end if;
+ end loop; -- end loop nr_irdy
+ end if;
+ report " WRITE DATA= "&str8 &""; -- display write data
+ end loop; -- end loop start_irdy > 0 ...
+
+ if RESET = 1 or STOP_N = '0' or STOP_N = 'L' then
+ 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 <= 'H' after tdelay;
+ parity_flag <= false;
+ end if;
+ end if; -- end rd_wr = '1'
+ end if; -- if RST_N ='0' then
+ end READ_WRITE;
+ --------------------------------------------------------------------------
+ -- Procedure implement instruction WRSW --
+ --------------------------------------------------------------------------
+ -- Writes single DWORD to memory space!
+ procedure WRSW(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "0111";
+ address(1 downto 0) := "00";
+ Vec2Hex (data(1),str8,Good2);
+ Vec2Hex (address,str_8,Good2);
+ report "Write single DWORD to memory space! Address : "&str_8;
+ READ_WRITE(address,data,1,bus_cmd,bus_sel,'0');
+ end WRSW;
+ --------------------------------------------------------------------------
+ -- Procedure implement instruction RDSW --
+ --------------------------------------------------------------------------
+ -- Reads single DWORD from memory space!
+ procedure RDSW(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "0110";
+ address(1 downto 0) := "00";
+ Vec2Hex (address,str_8,Good2);
+ report "Read single DWORD from memory space! Address : "&str_8 ;
+ READ_WRITE(address,data,1,bus_cmd,bus_sel,'1');
+ end RDSW;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction WRMW --
+ --------------------------------------------------------------------------
+ -- Writes multiple DWORDs to memory space - burst mode
+ procedure WRMW(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "1111";
+ address(1 downto 0) := "10";
+ Vec2Hex (address,str_8,Good2);
+ report "Write multiple DWORDs to memory space! Address : "&str_8 ;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
+ end WRMW;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction RDMW --
+ --------------------------------------------------------------------------
+ -- Reads multiple DWORDs from memory space - burst mode
+ procedure RDMW(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "1100";
+ address(1 downto 0) := "10";
+ Vec2Hex (address,str_8,Good2);
+ report "Read multiple DWORDs from memory space! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
+ end RDMW;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction RDML --
+ --------------------------------------------------------------------------
+ -- Reads multiple DWORDs from memory space!
+ procedure RDML(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd: STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data: Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "1110";
+ address(1 downto 0) := "00";
+ Vec2Hex (address,str_8,Good2);
+ report "Reads multiple DWORDs from memory space! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
+ end RDML;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction WCFG --
+ --------------------------------------------------------------------------
+ -- writes configuration
+ procedure WCFG(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd :="1011";
+ address(1 downto 0) :="00"; -- linear incrementing
+ Vec2Hex (address,str_8,Good2);
+ report "Configuration write! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
+ end WCFG;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction RCFG --
+ --------------------------------------------------------------------------
+ -- reads configuration
+ procedure RCFG(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd :="1010";
+ address(1 downto 0) :="00";
+ Vec2Hex (address,str_8,Good2);
+ report "Configuration read ! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
+ end RCFG;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction WRIO --
+ --------------------------------------------------------------------------
+ -- writes data to IO port
+ procedure WRIO(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd := "0011";
+ address(1 downto 0) := "00";
+ Vec2Hex (address,str_8,Good2);
+ report "Write DWORD to I/O space! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
+ end WRIO;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction RDIO --
+ --------------------------------------------------------------------------
+ -- reads data from IO port
+ procedure RDIO(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable read_data : Data_buffer;
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ begin
+ bus_cmd :="0010";
+ address(1 downto 0) :="00";
+ Vec2Hex (address,str_8,Good2);
+ report "Read DWORD from memory space! Address : "&str_8;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'1');
+ end RDIO;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction WAIT --
+ --------------------------------------------------------------------------
+ -- waits
+ procedure CWAT(
+ data : in Data_buffer;
+ address : inout STD_LOGIC_VECTOR(31 downto 0);
+ data_number : in Integer;
+ bus_sel : in Data_Enable) is
+ variable bus_cmd : STD_LOGIC_VECTOR(3 downto 0);
+ variable str8,str_8 : string(1 to 8);
+ variable Good2 : Boolean;
+ variable byte7_6,byte5,byte4,byte3_2,byte1,byte0 : Integer;
+ variable Char7_6,Char5,Char4,Char3_2,Char1,Char0 : Std_Logic_Vector(7 downto 0);
+ begin
+ Char7_6 := data(1)(31 downto 24);
+ irdy_loop := Byte2Int(Char7_6) ;
+ Char5 := "0000" & data(1)(23 downto 20);
+ irdy_nr := Byte2Int(Char5) + 1;
+ Char4 := "0000" & data(1)(19 downto 16);
+ irdy_start := Byte2Int(Char4);
+ bus_cmd := "0001";
+ if irdy_loop = 0 or irdy_nr = 0 then
+ irdy_insert := false;
+ else
+ irdy_insert := true;
+ end if;
+ READ_WRITE(address,data,data_number,bus_cmd,bus_sel,'0');
+ end CWAT;
+ --------------------------------------------------------------------------
+ -- Procedure implements instruction EXIT --
+ --------------------------------------------------------------------------
+ -- ends the Master's activity by placing in HighZ all the lines
+ procedure ABRT is
+ begin
+ wait until FALLING_EDGE(CLK); -- synchro cycle
+ Init;
+ wait;
+ end ABRT;
+ --------------------------------------------------------------------------
+ -- Procedure implements the commands file parser and sequencer --
+ --------------------------------------------------------------------------
+ procedure Main_case is
+ variable Commands : CommandArray(1 to 100);
+ variable NumCommands : Natural;
+ variable Good : Boolean;
+ constant HeaderMsg : String := "Main process:";
+ constant MsgSeverity : Severity_Level := Failure;
+ variable ErrFlag : Boolean;
+ variable PC : Integer;
+ begin
+ -- Read/Parse the commands file
+ FileParser (cmd_file,Commands,NumCommands,ErrFlag);
+ data_last_read := FALSE;
+ if ErrFlag then
+ report HeaderMsg&"Errors found in COMMAND file. Execute halts!!!"
+ severity Warning;
+ else
+ PC := 0;
+ wait until RST_N = '1';
+ while PC < NumCommands Loop
+ if RESET = 1 then
+ RESET := 0;
+ PC := 0;
+ end if;
+ while RST_N = '0' loop -- RESET signal is active
+ PC := 0; -- if RST_N ='0' restart simulation
+ REQ_N <= 'H'; -- request is tri-stated
+ wait until Rising_Edge(CLK); -- synchro wait
+ end loop;
+ if STOP_N = '0' then
+ report HeaderMsg&"Wait until signal STOP_N ='0' !";
+ wait until STOP_N = '1';
+ end if;
+ REQ_N <= '0';
+
+ PC := PC + 1;
+ case Commands(pc).command is
+ when "WRSW" =>
+ WRSW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "RDSW" =>
+ RDSW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "WRMW" =>
+ WRMW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "RDMW" =>
+ RDMW(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "RDML" =>
+ RDML(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "WCFG" =>
+ WCFG(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "RCFG" =>
+ RCFG(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "WRIO" =>
+ WRIO(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "RDIO" =>
+ RDIO(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "CWAT" =>
+ CWAT(Commands(pc).data,Commands(PC).addr,Commands(pc).data_nr,Commands(pc).Enable);
+ when "ABRT" => ABRT;
+ when others => null;
+ end case;
+ end loop;
+ end if;
+ end Main_Case;
+ ---------------------------------------------------------------------
+ -- MS32PCI_MAIN : process begins
+ ---------------------------------------------------------------------
+ begin
+ Init;
+ Main_case;
+ end process;
+end Behavior; --================= End of architecture ===============--
+-----------------------------------------------------------------------
+-- Revision list
+-- Version Author Date Changes
+--
+-- 0.1 Ovidiu Lupas June 09, 2000 New model
+-----------------------------------------------------------------------
+
Index: pci_core/tags/alpha/vhdl_behav/Pci_lib.vhd
===================================================================
--- pci_core/tags/alpha/vhdl_behav/Pci_lib.vhd (nonexistent)
+++ pci_core/tags/alpha/vhdl_behav/Pci_lib.vhd (revision 10)
@@ -0,0 +1,793 @@
+--===================================================================--
+--
+-- www.OpenCores.Org - June 2000
+-- This model adheres to the GNU public license
+--
+-- Design units : Functions and procedures used in models
+--
+-- File name : PCI_LIB.vhd
+--
+-- Purpose : type conversion functions, read commands file
+-- procedures
+--
+-- 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
+--===================================================================--
+-----------------------------------------------------------------------
+-- Revision list
+-- Version Author Date Changes
+--
+-- 0.1 Ovidiu Lupas June 09, 2000 New model
+-----------------------------------------------------------------------
+library IEEE;
+use IEEE.Std_Logic_1164.all;
+--
+package Simulation is
+-- Definition of the CommandType record array which is used to record
+-- the commands from the .cmd file
+ type Data_buffer is array(1 to 256) of Std_Logic_Vector(31 downto 0);
+ type Data_Enable is array(1 to 256) of Std_Logic_Vector(3 downto 0);
+
+ type CommandType is
+ record
+ command : string(1 to 4);
+ addr : Std_Logic_Vector(31 downto 0);
+ data : Data_buffer;
+ data_nr : Integer;
+ enable : Data_Enable;
+ end record;
+-- Definition of the CommandArray type type which can be used for
+-- the commands present in .cmd file
+ type CommandArray is array(positive range <>) of CommandType;
+end Simulation; --========== End of package Simulation =============--
+--
+library IEEE,STD,work;
+library work;
+use work.Simulation.all;
+use IEEE.Std_Logic_1164.all;
+use STD.textio.all;
+--
+package PCI_Def is
+ --------------------------------------------------------------------
+ -- convert a character to a value from 0 to 15
+ --------------------------------------------------------------------
+ function digit_value(
+ C : Character)
+ return integer;
+ --------------------------------------------------------------------
+ -- Converts unsigned Std_LOGIC_Vector to Integer, leftmost bit is MSB
+ -- Error message for unknowns (U, X, W, Z, -), converted to 0
+ -- Verifies whether vector is too long (> 16 bits)
+ --------------------------------------------------------------------
+ function Vec2Int (
+ Invector : in Std_Logic_Vector(15 downto 0))
+ return Integer;
+ --------------------------------------------------------------------
+ -- Converts unsigned Std_Logic_Vector to Integer, leftmost bit is MSB
+ -- Error message for unknowns (U, X, W, Z, -), converted to 0
+ -- Verifies whether vector is too long (> 16 bits)
+ --------------------------------------------------------------------
+ function Byte2Int (
+ Invector : in Std_Logic_Vector(7 downto 0))
+ return Integer;
+ --------------------------------------------------------------------
+ -- Converts unsigned Std_Logic_Vector to Integer, leftmost bit is MSB
+ -- Error message for unknowns (U, X, W, Z, -), converted to 0
+ -- Verifies whether vector is too long (> 16 bits)
+ --------------------------------------------------------------------
+ procedure Hex2Bit (
+ C : in Character;
+ Vector : out Std_Logic_Vector(3 downto 0);
+ Good : out Boolean);
+ --------------------------------------------------------------------
+ -- Converts Hex characters to binary representation
+ -- Asserts that no unknown value exists at the time of conversion.
+ --------------------------------------------------------------------
+ procedure Bit2Hex (
+ Vector : in Std_Logic_Vector(3 downto 0);
+ C : out Character;
+ Good : out Boolean);
+ --------------------------------------------------------------------
+ -- Converts bit_vector into a hex string
+ -- Asserts that no unknown value exists at the time of conversion.
+ --------------------------------------------------------------------
+ procedure Vec2Hex (
+ Value : in Std_Logic_Vector(31 downto 0);
+ result : out String(1 to 8);
+ Good : out Boolean);
+ --------------------------------------------------------------------
+ -- read a number from the line
+ -- use this if you have hex numbers that are not in VHDL pound-sign format
+ --------------------------------------------------------------------
+ procedure Read (
+ L : inout Line;
+ value : out Integer;
+ radix : in Positive);
+ --------------------------------------------------------------------
+ -- reads a hex value and returns a bit_vector value
+ --------------------------------------------------------------------
+ procedure ReadHex (
+ L : inout Line;
+ Value : out Std_Logic_Vector;
+ Good : out Boolean;
+ Enable: out Std_Logic_Vector);
+ --------------------------------------------------------------------
+ -- Implements the parsing of the cmd file, which specifies the tasks
+ -- that are applied to the processor.
+ --------------------------------------------------------------------
+ procedure FileParser (
+ constant file_name : in String;
+ variable Commands : inout CommandArray;
+ variable NumCommands : out Natural;
+ variable ErrFlag : inout Boolean);
+end PCI_Def; --============== End of package header =================--
+--
+library IEEE;
+use IEEE.Std_Logic_1164.all;
+library std;
+use std.textio.all;
+--
+package body PCI_Def is
+ --------------------------------------------------------------------
+ -- convert a character to a value from 0 to 15
+ --------------------------------------------------------------------
+ function digit_value (
+ C : Character)
+ return integer is
+ constant not_digit : integer := -999;
+ begin
+ if (C ='X') and (C ='x') then
+ return 15;
+ end if;
+ if (C >= '0') and (C <= '9') then
+ return (Character'pos(C) - Character'pos('0'));
+ elsif (C >= 'a') and (C <= 'f') then
+ return (character'pos(c) - character'pos('a') + 10);
+ elsif (C >= 'A') and (C <= 'F') then
+ return (character'pos(c) - character'pos('A') + 10);
+ else
+ return not_digit;
+ end if;
+ end digit_value;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ function Vec2Int (
+ InVector : in Std_Logic_Vector(15 downto 0))
+ return Integer is
+ constant HeaderMsg : String := "To_Integer:";
+ constant MsgSeverity : Severity_Level := Warning;
+ variable Value : Integer := 0;
+ begin
+ if InVector = "UUUUUUUUUUUUUUUU" then
+ report HeaderMsg&"The input vector is of type 'U'. Converted to 0"
+ severity MsgSeverity;
+ elsif InVector = "XXXXXXXXXXXXXXXX" then
+ report HeaderMsg&"The input vector is of type 'X'. Converted to 0"
+ severity MsgSeverity;
+ elsif InVector = "WWWWWWWWWWWWWWWW" then
+ report HeaderMsg&"The input vector is of type 'W'. Converted to 0"
+ severity MsgSeverity;
+ elsif InVector = "ZZZZZZZZZZZZZZZZ" then
+ report HeaderMsg&"The input vector is of type 'Z'. Converted to 0"
+ severity MsgSeverity;
+ else
+ for i in 0 to 15 loop
+ if (InVector(i) = '1') then
+ Value := Value + (2**I);
+ end if;
+ end loop;
+ end if;
+ return Value;
+ end Vec2Int;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ function Byte2Int (
+ InVector : in Std_Logic_Vector(7 downto 0))
+ return Integer is
+ constant HeaderMsg : String := "To_Integer:";
+ constant MsgSeverity : Severity_Level := Warning;
+ variable Value : Integer := 0;
+ begin
+ for i in 0 to 7 loop
+ if (InVector(i) = '1') then
+ Value := Value + (2**I);
+ end if;
+ end loop;
+ return Value;
+ end Byte2Int;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure Hex2Bit (
+ C : in Character;
+ Vector : out Std_Logic_Vector(3 downto 0);
+ Good : out Boolean) is
+ variable Good1 : Boolean := false;
+ constant HeaderMsg : String := "Hex2Bit:";
+ constant MsgSeverity : Severity_Level := Error;
+ begin
+ Good := false;
+ case C is
+ when '0' => Vector := "0000"; Good1 := true;
+ when '1' => Vector := "0001"; Good1 := true;
+ when '2' => Vector := "0010"; Good1 := true;
+ when '3' => Vector := "0011"; Good1 := true;
+ when '4' => Vector := "0100"; Good1 := true;
+ when '5' => Vector := "0101"; Good1 := true;
+ when '6' => Vector := "0110"; Good1 := true;
+ when '7' => Vector := "0111"; Good1 := true;
+ when '8' => Vector := "1000"; Good1 := true;
+ when '9' => Vector := "1001"; Good1 := true;
+ when 'A'|'a' => Vector := "1010"; Good1 := true;
+ when 'B'|'b' => Vector := "1011"; Good1 := true;
+ when 'C'|'c' => Vector := "1100"; Good1 := true;
+ when 'D'|'d' => Vector := "1101"; Good1 := true;
+ when 'E'|'e' => Vector := "1110"; Good1 := true;
+ when 'F'|'f' => Vector := "1111"; Good1 := true;
+ -- extended for std_LOGIC --
+ when 'U'|'u' => Vector := "UUUU"; Good1 := true;
+ when 'X'|'x' => Vector := "1111"; Good1 := true;
+ when 'Z'|'z' => Vector := "ZZZZ"; Good1 := true;
+ when 'W'|'w' => Vector := "WWWW"; Good1 := true;
+ when 'L'|'l' => Vector := "LLLL"; Good1 := true;
+ when 'H'|'h' => Vector := "HHHH"; Good1 := true;
+ when '-' => Vector := "----"; Good1 := true;
+ when others => Good1 := false;
+ end case;
+ if not Good1 then
+ Vector := "0000";
+ report HeaderMsg&"Expected a Hex character (0-F)"
+ severity MsgSeverity;
+ end if;
+ Good := Good1;
+ end Hex2Bit;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure Bit2Hex (
+ Vector : Std_Logic_Vector(3 downto 0);
+ C : out Character;
+ Good : out Boolean) is
+ variable Good1 : Boolean := false;
+ constant HeaderMsg : String := "Bit2Hex: ";
+ constant MsgSeverity : Severity_Level := Error;
+ begin
+ Good := false;
+ case Vector is
+ when x"0" => C := '0'; Good1 := true;
+ when x"1" => C := '1'; Good1 := true;
+ when x"2" => C := '2'; Good1 := true;
+ when x"3" => C := '3'; Good1 := true;
+ when x"4" => C := '4'; Good1 := true;
+ when x"5" => C := '5'; Good1 := true;
+ when x"6" => C := '6'; Good1 := true;
+ when x"7" => C := '7'; Good1 := true;
+ when x"8" => C := '8'; Good1 := true;
+ when x"9" => C := '9'; Good1 := true;
+ when x"A" => C := 'A'; Good1 := true;
+ when x"B" => C := 'B'; Good1 := true;
+ when x"C" => C := 'C'; Good1 := true;
+ when x"D" => C := 'D'; Good1 := true;
+ when x"E" => C := 'E'; Good1 := true;
+ when x"F" => C := 'F'; Good1 := true;
+ when "ZZZZ" => C := 'Z'; Good1 := true;
+ when others => Good1 := false;
+ end case;
+ if not Good1 then
+ C := '0';
+ report HeaderMsg&"Expected a Hex character (0-F)"
+ severity MsgSeverity;
+ end if;
+ Good := Good1;
+ end Bit2Hex;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure Vec2Hex (
+ Value : in Std_Logic_Vector(31 downto 0);
+ Result : out String(1 to 8);
+ GOOD : out BOOLEAN) is
+ variable OK : Boolean;
+ variable C : Character;
+ constant NE : Integer := value'length/4; -- number of Hex chars
+ variable BV : Std_Logic_Vector(value'length-1 downto 0) := Value;
+ variable Res : String(1 to 8);
+ constant HeaderMsg : String := "Vec2Hex: ";
+ constant MsgSeverity : Severity_Level := Error;
+ begin
+ if Value'length mod 4 /= 0 then -- Testing if Vector is mod 4
+ Good := false;
+ report HeaderMsg&"The length of input vector is not modulo 4!"
+ severity MsgSeverity;
+ return;
+ end if;
+ Bit2Hex(BV(3 downto 0), C, OK); -- Conversion of the 4 LSB bits
+ if not OK then
+ Good := false;
+ return;
+ end if;
+ Res := C & Res(2 to NE); -- Places first Char in Result
+ for i in 1 to NE-1 loop
+ Bit2Hex(BV(4*i+3 downto 4*i), C, OK); -- Converts next Char
+ if not OK then
+ Good := false;
+ return;
+ end if;
+ Res := Res(1 to i) & C & Res(i+2 to NE);
+ end loop;
+ for i in 0 to NE-1 loop
+ Result (1+i) := Res (NE-i);
+ end loop;
+ Good := true;
+ end Vec2Hex;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure Read (
+ L : inout line;
+ Value : out integer;
+ Radix : in positive) is
+ constant not_digit : integer := -999;
+ variable Digit : integer;
+ variable Result : integer := 0;
+ variable Pos : integer;
+ begin
+ -- calculate the value
+ if (L'length <=0 ) then
+ for i in Pos to L'right loop
+ digit := digit_value(L(i));
+ exit when (Digit = not_digit) or (digit >= radix);
+ Result := Result * Radix + digit;
+ Pos := Pos + 1;
+ end loop;
+ Value := Result;
+ end if;
+ end Read;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure ReadHex (
+ L : inout Line;
+ Value : out Std_Logic_Vector;
+ Good : out Boolean;
+ Enable : out Std_Logic_Vector) is
+ variable OK : Boolean;
+ variable C : Character;
+ constant NE : Integer := value'length/4;
+ variable BV : Std_Logic_Vector(value'length-1 downto 0);
+ variable TEMP : Std_Logic_Vector(value'length-1 downto 0);
+ variable S : String(1 to NE-1);
+ constant HeaderMsg : String := "Vec2Hex";
+ constant MsgSeverity : Severity_Level := Warning;
+ begin
+ Enable(3 downto 0) :="0000";
+ if Value'length mod 4 /= 0 then -- Testing if Vector is mod 4
+ Good := false;
+ report HeaderMsg&"The length of input vector is not modulo 4!"
+ severity MsgSeverity;
+ return;
+ end if;
+ loop
+ read(L, C, OK); -- Finds the first Hex Char
+ exit when (((C /= ' ') and (C /= CR) and (C /= HT)) or
+ (L'length = 0));
+ end loop;
+ Hex2Bit(C, BV( 3 downto 0), OK); -- Converts first Hex Char to 4 Bits
+ if C ='X' or C ='x' then
+ Enable(3) :='1';
+ end if;
+
+ if not OK then
+ Good := false;
+ return;
+ end if;
+ read(L, S, OK); -- Reads the next three Hex Chars
+ if not OK then
+ Good := false;
+ return;
+ end if;
+ for i in 1 to NE-1 loop
+ if s(i) ='X' or s(i) ='x' then
+ if i=1 then
+ Enable(3):='1';
+ end if;
+ if i=2 or i=3 then
+ Enable(2):='1';
+ end if;
+ if i=4 or i=5 then
+ Enable(1):='1';
+ end if;
+ if i=6 or i=7 then
+ Enable(0):='1';
+ end if;
+ end if;
+ Hex2Bit(s(i), BV(4*i+3 downto 4*i), OK); -- Converts to BitVector
+ if not OK then
+ Good := false;
+ return;
+ end if;
+ end loop;
+ Good := true;
+
+ -- for byte
+ if (value'length = 8 ) then
+ for i in 0 to 3 loop
+ TEMP(i) := BV(value'length-4+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+4) := BV(value'length-8+i);
+ end loop;
+ end if;
+
+ -- for word
+ if (value'length = 16 ) then
+ for i in 0 to 3 loop
+ TEMP(i) := BV(value'length-4+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+4) := BV(value'length-8+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+8) := BV(value'length-12+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+12) := BV(value'length-16+i);
+ end loop;
+ end if;
+
+ -- for DWORD
+ if (value'length =32 ) then
+ for i in 0 to 3 loop
+ TEMP(i) := BV(value'length-4+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+4) := BV(value'length-8+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+8) := BV(value'length-12+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+12) := BV(value'length-16+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+16) := BV(value'length-20+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+20) := BV(value'length-24+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+24) := BV(value'length-28+i);
+ end loop;
+ for i in 0 to 3 loop
+ TEMP(i+28) := BV(value'length-32+i);
+ end loop;
+ end if;
+
+ Value := TEMP;
+ end ReadHex;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+ procedure FileParser (
+ constant file_name : in String ;
+ variable Commands : inout CommandArray;
+ variable NumCommands : out Natural;
+ variable ErrFlag : inout Boolean) is
+ File CmdFile : text;
+ constant HeaderMsg : String := "FileParser:";
+ constant MsgSeverity : Severity_Level := Error;
+ variable L : Line := NULL;
+ variable Linenum : Natural := 0;
+ variable LblNum : Natural := 0;
+ variable CmdNum : Natural := 0;
+ variable EndOfFile : Boolean := false;
+ variable Good : Boolean := false;
+ variable Int : Integer;
+ variable Tm : Time;
+ variable C : Character;
+ variable Addr : Std_Logic_Vector(31 downto 0);
+ variable Data : Std_Logic_Vector(31 downto 0);
+ variable Enable : Std_Logic_Vector(3 downto 0);
+ variable Vect_count : Std_Logic_Vector(7 downto 0);
+ variable Data_word : Std_Logic_Vector(15 downto 0);
+ variable Data_byte : Std_Logic_Vector(7 downto 0);
+ variable str4 : string(1 to 4);
+ variable count_nr : Integer;
+ variable count : Integer;
+ begin
+ ErrFlag := false;
+ FILE_OPEN(CmdFile,file_name,READ_MODE);
+ loop
+ readline(CmdFile,L);
+ EndOfFile := endfile(CmdFile);
+ CmdNum := CmdNum + 1;
+ LineNum := LineNum + 1;
+ read(L, str4, Good);
+ if not Good then
+ CmdNum := CmdNum-1;
+ else
+ case str4 is
+ when "WRSW" => -- write single word command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid WRSW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_byte,Good,Enable);
+ count_nr := Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "WRSW";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in WRSW command ";
+ end if;
+ end loop;
+ end if;
+
+ when "RDSW" => -- read single word command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid RDSW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "RDSW";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in RDSW command ";
+ end if;
+ end loop;
+ end if;
+
+ when "WRMW" => -- write multiple words command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid WRMW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "WRMW";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in WRMW command ";
+ end if;
+ end loop;
+ end if;
+
+ when "RDMW" => -- read multiple words command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid RDMW command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_Byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "RDMW";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in RDMW command ";
+ end if;
+ end loop;
+ end if;
+
+ when "RDML" => -- read multiple words command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid RDML command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_Byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "RDML";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in RDML command ";
+ end if;
+ end loop;
+ end if;
+
+ when "WCFG" => -- write to configuration space command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid WCFG command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "WCFG";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in WCFG command ";
+ end if;
+ end loop;
+ end if;
+
+ when "RCFG" => -- read from configuration space command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid RCFG command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_Byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good =true) then
+ count := count + 1;
+ commands(CmdNum).command := "RCFG";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in RCFG command ";
+ end if;
+ end loop;
+ end if;
+
+ when "WRIO" => -- write to I/O space command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid WRIO command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good = true) then
+ count := count + 1;
+ commands(CmdNum).command := "WRIO";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in WRIO command ";
+ end if;
+ end loop;
+ end if;
+
+ when "RDIO" => -- read from I/O space command
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid RDIO command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ Good := true;
+ readhex(L,Data_Byte,Good,Enable);
+ count_nr :=Byte2Int(Data_Byte);
+ count := 0;
+ for I in 0 to count_nr-1 loop
+ readhex(L,Data,Good,Enable);
+ if (Good = true) then
+ count := count + 1;
+ commands(CmdNum).command := "RDIO";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(count) := Data;
+ commands(CmdNum).data_nr := count_nr;
+ commands(CmdNum).enable(count) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in RDIO command ";
+ end if;
+ end loop;
+ end if;
+
+ when "CWAT" =>
+ readhex(L,Addr,Good,Enable);
+ if not Good then
+ report HeaderMsg&"Invalid CWAT command in :"&file_name&", line #"& integer'image(LineNum) &", "&"Address parameter should be 8 hex characters"
+ severity MsgSeverity;
+ ErrFlag := true;
+ else
+ count_nr :=0;
+ readhex(L,Data,Good,Enable);
+ if (Good = true) then
+ count :=count +1;
+ commands(CmdNum).command := "WAIT";
+ commands(CmdNum).addr := Addr;
+ commands(CmdNum).data(1) := Data;
+ commands(CmdNum).data_nr := 1;
+ commands(CmdNum).enable(1) := Enable;
+ else
+ report HeaderMsg&"Invalid DATA in CWAT command ";
+ end if;
+ end if;
+
+ when "ABRT" =>
+ count :=count + 1;
+ commands(CmdNum).command := "ABRT";
+ commands(CmdNum).addr := "00000000000000000000000000000000";
+ commands(CmdNum).data(1) := "00000000000000000000000000000000";
+ commands(CmdNum).data_nr := 1;
+ commands(CmdNum).enable(1) := Enable;
+
+ when others =>
+ CmdNum := CmdNum -1;
+ if str4(1 to 2)/= "##" then
+ report HeaderMsg & "Invalid command in file: "&file_name&", line #"& integer'image(LineNum) &", "& "Unknown command : "& str4 & l(l'left to l'right)
+ severity error;
+ ErrFlag := true;
+ end if;
+ end case;
+ end if;
+ NumCommands := CmdNum;
+ Exit when EndOfFile;
+ end loop;
+ end FileParser;
+ --------------------------------------------------------------------
+ --------------------------------------------------------------------
+end PCI_Def; --================ End of package body ================--
Index: pci_core/tags/alpha/vhdl_behav/Test_pci.vhd
===================================================================
--- pci_core/tags/alpha/vhdl_behav/Test_pci.vhd (nonexistent)
+++ pci_core/tags/alpha/vhdl_behav/Test_pci.vhd (revision 10)
@@ -0,0 +1,226 @@
+--===================================================================--
+--
+-- www.OpenCores.Org - January 2000
+-- This model adheres to the GNU public license
+--
+-- Design units : TestBench for PCI devices.
+--
+-- File name : Test_PCI.vhd
+--
+-- Purpose : Implements the test bench for PCI 33 MHz, 32 bit devices.
+-- It is included one master device and two target devices.
+--
+-- There can be used more than one target devices in a
+-- design, every device being identified by the three
+-- base addresses in generic.
+--
+--
+-- Library : PCI_Lib
+--
+-- Dependencies : IEEE.Std_Logic_1164
+--
+-- Limitations : None known
+--
+-- Errors : None known
+--
+-- Author : Ovidiu Lupas
+-- olupas@opencores.org
+--
+-- Simulator : ModelSim EE version 5.2 on a Windows95 PC
+-- ActiveVHDL 3.1 on a Windows95 PC
+--===================================================================--
+-----------------------------------------------------------------------
+-- Entity for PCI bus Arbiter and CLK generator
+-----------------------------------------------------------------------
+library ieee,work;
+ use ieee.Std_Logic_1164.all;
+ use work.Simulation.all;
+ use work.PCI_Def.all;
+-----------------------------------------------------------------------
+-----------------------------------------------------------------------
+entity ClkGen is
+ generic ( tperiod : Time := 30 ns );
+ port (
+ REQ_N : in Std_Logic;
+ GNT_N : out Std_Logic := '1';
+ RST_N : out Std_Logic;
+ CLK : out Std_Logic); -- System clock
+end ClkGen; --=================== End of entity =====================--
+--========================== Architecture ===========================--
+architecture BEHAV_ClkGen of ClkGen is
+begin--======================== Architecture =================================--
+ ---------------------------------------------------------------------
+ -- Provide the external clock signal to the processor
+ ---------------------------------------------------------------------
+ ClkDriver : process
+ variable clktmp: std_logic := '0';
+ begin
+ CLK <= clktmp;
+ clktmp := not clktmp;
+ wait for tperiod/2;
+ end process ClkDriver;
+ ---------------------------------------------------------------------
+ -- Simulates an external PCI-bus arbiter, which always grants the
+ -- access to the bus :)
+ ---------------------------------------------------------------------
+ Arbiter : process(REQ_N)
+ begin
+ if Falling_Edge(REQ_N) then
+ GNT_N <= '0' after 10 ns;
+ elsif Rising_Edge(REQ_N) then
+ GNT_N <= '1' after 10 ns;
+ end if;
+ end process Arbiter;
+ ---------------------------------------------------------------------
+ -- Provides the reset signal
+ ---------------------------------------------------------------------
+ RstGen: process
+ begin
+ RST_N <= '0';
+ wait for 100 ns;
+ RST_N <= '1';
+ wait for 400 ns;
+ end process;
+end BEHAV_ClkGen; --============== End of architecture ==============--
+-----------------------------------------------------------------------
+-- TestBench
+-----------------------------------------------------------------------
+library ieee,work,std;
+ use ieee.std_logic_1164.all;
+ use work.ClkGen;
+-----------------------------------------------------------------------
+-----------------------------------------------------------------------
+entity TESTPCI is
+end TESTPCI;
+--========================== Architecture ===========================--
+architecture stimulus of TESTPCI is
+ ---------------------------------------------------------------------
+ -- Signal declaration
+ ---------------------------------------------------------------------
+ signal AD_Bus : Std_Logic_Vector (31 downto 0);
+ signal C_BE_Bus : Std_Logic_Vector (3 downto 0);
+ signal PAR : Std_Logic;
+ signal FRAME_N : Std_Logic;
+ signal TRDY_N : Std_Logic;
+ signal IRDY_N : Std_Logic;
+ signal STOP_N : Std_Logic;
+ signal DEVSEL_N : Std_Logic;
+ signal IDSEL : Std_Logic;
+ signal SEL1 : Std_Logic;
+ signal SEL2 : Std_Logic;
+ signal PERR_N : Std_Logic;
+ signal SERR_N : Std_Logic;
+ signal REQ_N : Std_Logic;
+ signal GNT_N : Std_Logic;
+ signal CLK : Std_Logic;
+ signal RST_N : Std_Logic;
+ ---------------------------------------------------------------------
+ -- Component declarations
+ ---------------------------------------------------------------------
+ component ClkGen
+ generic ( tperiod : Time := 30 ns );
+ port (
+ REQ_N : in Std_Logic;
+ GNT_N : out Std_Logic;
+ RST_N : out Std_Logic;
+ CLK : out Std_Logic); -- System clock
+ end component;
+ ---------------------------------------------------------------------
+ ---------------------------------------------------------------------
+ component MS32PCI
+ generic (
+ cmd_file : string(1 to 7);
+ tdelay : Time;
+ tsetup : Time;
+ thold : Time);
+ 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; -- in
+ -- 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; -- in
+ -- System signals (2)
+ CLK : in STD_LOGIC;
+ RST_N : in STD_LOGIC); --in
+ end component;
+ ---------------------------------------------------------------------
+ ---------------------------------------------------------------------
+ component TG32PCI
+ generic (
+ devtype : string(1 to 4);
+ tdelay : Time;
+ tsetup : Time;
+ thold : Time;
+ bamem : Std_Logic_Vector(31 downto 0); -- hex value
+ baio : Std_Logic_Vector(31 downto 0); -- hex value
+ bacfg : Std_Logic_Vector(31 downto 0));-- hex value
+ port (
+ -- Address, Data and Command buses (37)
+ AD_Bus : inout Std_Logic_Vector (31 downto 0);
+ C_BE_Bus : in Std_Logic_Vector (3 downto 0);
+ PAR : inout Std_Logic;
+ -- Interface control signals (6)
+ FRAME_N : in Std_Logic;
+ TRDY_N : inout Std_Logic;
+ IRDY_N : in Std_Logic;
+ STOP_N : out Std_Logic;
+ DEVSEL_N : inout Std_Logic;
+ IDSEL : in Std_Logic;
+ -- Error reporting signals (2)
+ PERR_N : inout Std_Logic;
+ SERR_N : inout Std_Logic;
+ -- System signals (2)
+ CLK : in Std_Logic;
+ RST_N : in Std_Logic);
+ end component;
+begin --====================== Architecture =========================--
+ ---------------------------------------------------------------------
+ -- Component instantiation
+ ---------------------------------------------------------------------
+ UUT1: MS32PCI
+ generic map (
+ "PCI.CMD",0 ns, 7 ns, 5 ns)
+ port map (
+ AD_Bus,C_BE_Bus,PAR,FRAME_N,TRDY_N,IRDY_N,STOP_N,DEVSEL_N,
+ IDSEL,PERR_N,SERR_N,REQ_N,GNT_N,CLK,RST_N);
+ SEL1 <= AD_Bus(16);
+ UUT2: TG32PCI
+ generic map (
+ "Fast",0 ns,0 ns,0 ns,x"00005000",x"00000800",x"00010CF0")
+ port map (
+ AD_Bus => AD_Bus,C_BE_Bus => C_BE_Bus,PAR => PAR,
+ FRAME_N => FRAME_N,TRDY_N => TRDY_N,IRDY_N => IRDY_N,
+ STOP_N => STOP_N,DEVSEL_N => DEVSEL_N,IDSEL => SEL1,
+ PERR_N => PERR_N,SERR_N => SERR_N,CLK => CLK,RST_N => RST_N);
+ SEL2 <= AD_Bus(17);
+ UUT3: TG32PCI
+ generic map (
+ "Medi",0 ns,7 ns,0 ns,x"00006000",x"00001800",x"00020CF0")
+ port map (
+ AD_Bus => AD_Bus,C_BE_Bus => C_BE_Bus,PAR => PAR,
+ FRAME_N => FRAME_N,TRDY_N => TRDY_N,IRDY_N => IRDY_N,
+ STOP_N => STOP_N,DEVSEL_N => DEVSEL_N,IDSEL => SEL2,
+ PERR_N => PERR_N,SERR_N => SERR_N,CLK => CLK,RST_N => RST_N);
+ GEN: ClkGen port map (
+ REQ_N,GNT_N,RST_N,CLK);
+ ---------------------------------------------------------------------
+end stimulus; --=============== End of architecture =================--
+-----------------------------------------------------------------------
+-- Revision list
+-- Version Author Date Changes
+--
+-- 0.1 Ovidiu Lupas June 09, 2000 New model
+-----------------------------------------------------------------------
+
Index: pci_core/tags/alpha/vhdl_behav/Tg32pci.vhd
===================================================================
--- pci_core/tags/alpha/vhdl_behav/Tg32pci.vhd (nonexistent)
+++ pci_core/tags/alpha/vhdl_behav/Tg32pci.vhd (revision 10)
@@ -0,0 +1,1283 @@
+--===================================================================--
+--
+-- www.OpenCores.Org - January 2000
+-- This model adheres to the GNU public license
+--
+-- Design units : Target device for PCI Local Bus 33 MHz 32 bits
+-- (BoardLevel Simulation model)
+-- (Entity and architecture)
+--
+-- File name : Tg32PCI.vhd
+--
+-- Purpose : The Target device is used to simulate a target
+-- device on the PCI-Bus
+--
+-- Note : This model is modelled after the PCI protocol
+-- as described in Xilinx & Altera AppNotes
+--
+-- There can be used more than one target devices in a
+-- design, every device being identified by the three
+-- base addresses in generic.
+--
+-- 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
+--===================================================================--
+-----------------------------------------------------------------------
+-- Entity for Target device in a PCI bus 33 MHZ 32 bit configuration
+-----------------------------------------------------------------------
+library ieee,work;
+ use ieee.Std_Logic_1164.all;
+ use work.Simulation.all;
+ use work.PCI_Def.all;
+-----------------------------------------------------------------------
+-----------------------------------------------------------------------
+entity Target32PCI is
+ generic (
+ devtype : string(1 to 4); -- type of the device (Fast, Medi, Slow)
+ tdelay : Time; -- delay time parameter when the device will change
+ -- data on AD_Bus (referenced to CLK signal)
+ tsetup : Time;
+ thold : Time;
+ bamem : Std_Logic_Vector(31 downto 0); -- base address for memory
+ baio : Std_Logic_Vector(31 downto 0); -- base address for I/O port
+ bacfg : Std_Logic_Vector(31 downto 0)); -- base address for cfg space
+ port (
+ -- Address, Data and Command buses (37)
+ AD_Bus : inout Std_Logic_Vector (31 downto 0); -- Address and Data Bus
+ C_BE_Bus : in Std_Logic_Vector (3 downto 0); -- Command Bus
+ PAR : inout Std_Logic; --
+ -- Interface control signals (6)
+ FRAME_N : in Std_Logic;
+ TRDY_N : inout Std_Logic;
+ IRDY_N : in Std_Logic;
+ STOP_N : out Std_Logic;
+ DEVSEL_N : inout Std_Logic;
+ IDSEL : in Std_Logic;
+ -- Error reporting signals (2)
+ PERR_N : inout Std_Logic;
+ SERR_N : inout Std_Logic;
+ -- System signals (2)
+ CLK : in Std_Logic;
+ RST_N : in Std_Logic);
+end Target32PCI;--================ End of entity ====================--
+-----------------------------------------------------------------------
+-- Architecture for Target device PCI bus 33MHZ 32 bit configuration
+-----------------------------------------------------------------------
+architecture Behavior of Target32PCI is
+ ---------------------------------------------------------------------
+ -- Definition of Memory type,
+ ---------------------------------------------------------------------
+ type MEMORY is array(0 to 255) of Std_Logic_Vector(31 downto 0);
+ ---------------------------------------------------------------------
+ -- Local declarations
+ ---------------------------------------------------------------------
+ shared variable addr : Std_Logic_Vector (31 downto 0); -- Address
+ shared variable busaddr : Integer; -- address present on bus
+ shared variable cfgaddr : Integer; -- current configuration register address
+ shared variable memaddr : Integer; -- current memory address
+ shared variable ioaddr : Integer; -- current I/O port address
+ shared variable IOmem : Memory; -- IOport registers
+ shared variable Cfgmem : Memory; -- Configuration registers
+ shared variable Mem : Memory; -- memory locations
+ shared variable trdywaits : Boolean := false; -- wait enable
+ shared variable trdy_st,trdy_nr,trdy_loop : Integer := 0;
+ ---------------------------------------------------------------------
+ -- Signals
+ ---------------------------------------------------------------------
+ signal cmd : Std_Logic_Vector (3 downto 0); -- Command bus
+ signal Busy : Std_Logic := '0';
+ signal IORead : Std_Logic := '0';
+ signal IOWrite : Std_Logic := '0';
+ signal MemRead : Std_Logic := '0';
+ signal MemWrite : Std_Logic := '0';
+ signal WaitWrite : Std_Logic := '0';
+ signal CfgRead : Std_Logic := '0';
+ signal CfgWrite : Std_Logic := '0';
+ signal FrameEv : Std_Logic := '0';
+ signal CmdBusReady : Std_Logic := '0';
+ signal TrnArnd : Std_Logic := '0';
+ signal DevAddr : Std_Logic := '0';
+ signal ResFin : Std_Logic := '0';
+ signal Waits : Std_Logic := '0';
+ signal Init : Std_Logic := '0';
+begin--======================== Architecture ========================--
+ ---------------------------------------------------------------------
+ -- Initialize the memory contents with zeroes
+ ---------------------------------------------------------------------
+ Initialize : process
+ begin
+ for i in 0 to 255 loop
+ IOmem(i) := x"00000000";
+ Mem(i) := x"00000000";
+ Cfgmem(i) := x"00000000";
+ end loop;
+ wait;
+ 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 master
+ ---------------------------------------------------------------------
+ Parity : process(CLK,RST_N)
+ variable parbit : Std_Logic;
+ variable lastpar : Std_Logic;
+ variable errbit : Std_Logic;
+ variable pargen : Boolean := false;
+ variable errgen : Boolean := false;
+ variable cmdbus : Std_Logic_Vector(3 downto 0);
+ variable addrbus : Std_Logic_Vector(31 downto 0);
+ begin
+ if (Falling_Edge(RST_N) or RST_N = '0') then
+ PAR <= 'Z';
+ PERR_N <= 'Z';
+ elsif (CLK'Event and CLK = '1') then -- parity computation on every cycle
+ addrbus := AD_Bus;
+ cmdbus := C_BE_Bus;
+ lastpar := parbit;
+ parbit := '0';
+ if addrbus /= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ" then
+ for I in 0 to 31 loop
+ parbit := parbit xor addrbus(i);
+ end loop;
+ for I in 0 to 3 loop
+ parbit := parbit xor cmdbus(I);
+ end loop;
+ else
+ parbit := 'Z';
+ end if;
+ if PAR = lastpar then -- PERR computation on every cycle
+ errbit := '1';
+ elsif PAR /= lastpar then
+ errbit := '0';
+ elsif PAR = 'Z' then
+ errbit := 'H';
+ end if;
+ if ((IORead = '1' or MemRead = '1' or CfgRead = '1') and DevAddr = '1') then
+ pargen := true;
+ else
+ pargen := false;
+ end if;
+ elsif (CLK'Event and CLK = '0' and DevAddr = '1') then -- parity generation if necessary
+ if errgen = true then
+ PERR_N <= errbit;
+ else
+ PERR_N <= 'H';
+ end if;
+ if pargen = true then
+ PAR <= parbit;
+ errgen := false;
+ else
+ PAR <= 'Z';
+ errgen := true;
+ end if;
+ elsif (CLK'Event and CLK = '0' and DevAddr = '0') then --not the selected device
+ PAR <= 'Z'; -- by the address
+ PERR_N <= 'H';
+ SERR_N <= 'Z';
+ end if;
+ end process;
+ ---------------------------------------------------------------------
+ -- Implements the command decoding, to receive commands from master
+ ---------------------------------------------------------------------
+ Decode : process(CLK,FRAME_N,Busy,DevAddr,cmdBusReady,RST_N)
+ variable counter : Integer;
+ variable devdel : Boolean := false;
+ begin
+ if (Falling_Edge(RST_N) or RST_N = '0') then
+ DEVSEL_N <= 'Z';
+ STOP_N <= 'Z';
+ Busy <= '0';
+ elsif (Frame_N'Event and Frame_N = '0') then -- the target device is awakened by
+ FrameEv <= '1'; -- falling_edge of FRAME signal
+ counter := 0;
+ elsif (Busy'Event and Busy = '0') then
+ IOWrite <= '0';
+ MemWrite <= '0';
+ CfgWrite <= '0';
+ WaitWrite <= '0';
+ IORead <= '0';
+ MemRead <= '0';
+ CfgRead <= '0';
+ elsif (Busy'Event and Busy = '1') then
+ if ( IOWrite = '1' or MemWrite = '1' or CfgWrite = '1' or WaitWrite = '1') then
+ report "Target device is selected for write operations!"
+ severity Note;
+ if devtype = "Fast" then
+ DEVSEL_N <= '0' after 8 ns;
+ Stop_N <= '1' after 10 ns;
+ devdel := false;
+ else
+ devdel := true;
+ counter := 0;
+ end if;
+ elsif ( IORead = '1' or MemRead = '1' or CfgRead = '1') then
+ report "Target device is selected for read operations!"
+ severity Note;
+ if devtype = "Fast" then
+ DEVSEL_N <= '0' after 8 ns;
+ Stop_N <= '1' after 10 ns;
+ devdel := false;
+ else
+ devdel := true;
+ counter := 0;
+ end if;
+ end if;
+ elsif (DevAddr'Event and DevAddr = '0') then
+ Busy <= '0';
+ elsif (cmdBusReady'Event and cmdBusReady = '1') then
+ TrnArnd <= '0';
+ elsif (CLK'Event and CLK = '0') then
+ if Busy = '0' and DevAddr = '1' then -- deselect
+ DEVSEL_N <= 'H';
+ STOP_N <= '1';
+ elsif DevAddr = '0' then -- deselect device
+ DEVSEL_N <= 'Z';
+ STOP_N <= 'Z';
+ end if;
+ elsif (CLK'Event and CLK = '1') then
+ if ResFin = '1' then -- memory reserved mode command
+ if MemWrite = '1' then -- master writes to target memory
+ if TRDY_N = '0' and IRDY_N = '0' then
+ Busy <= '0';
+ ResFin <= '0';
+ end if;
+ elsif MemRead = '1' then -- master reads from target memory
+ if TrnArnd = '0' and TRDY_N = '0' and IRDY_N = '0' then
+ Busy <= '0';
+ ResFin <= '0';
+ end if;
+ end if;
+ end if;
+ if devdel = true then
+ if devtype = "Medi" then
+ if counter = 0 then
+ DEVSEL_N <= '0' after 8 ns;
+ Stop_N <= '1' after 10 ns;
+ devdel := false;
+ end if;
+ elsif devtype = "Slow" then
+ if counter = 1 then
+ DEVSEL_N <= '0' after 8 ns;
+ Stop_N <= '1' after 10 ns;
+ devdel := false;
+ else
+ counter := counter + 1;
+ end if;
+ end if;
+ end if;
+ if FRAME_N = '1' then -- end of cycle
+ assert (IRDY_N = '0')
+ report "Target device : FRAME signal deassertion error. IRDY is not asserted."
+ severity Error;
+ if TRDY_N = '0' and IRDY_N = '0' then -- finish the current cycle
+ Busy <= '0';
+ end if;
+ elsif FrameEv = '1' then -- decoding
+ FrameEv <= '0';
+ assert (FRAME_N'Last_Event >= tsetup)
+ report "Target device : Frame setup time violation in decode cycle!"
+ severity warning;
+ assert (AD_Bus'Last_Event >= tsetup)
+ report "Target device : Address setup time violation in decode cycle!"
+ severity warning;
+ assert (C_BE_Bus'Last_Event >= tsetup)
+ report "Target device : Command setup time violation in decode cycle!"
+ severity warning;
+ addr := AD_Bus;
+ case C_BE_Bus is -- decoding the command bus
+ when "0001" => -- Special Cycle! Used to transfer from master device the
+ -- wait states parameters
+ if (addr(31 downto 8) = bacfg(31 downto 8) and IDSEL ='1') then
+ WaitWrite <= '1';
+ DevAddr <= '1';
+ Busy <= '1';
+ trdywaits := true;
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ trdywaits := false;
+ end if;
+ cfgaddr := Byte2Int(addr(7 downto 0));
+ when "0010" => -- I/O Read! Master reads from target device.
+ if addr(31 downto 8) = baio(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ IORead <= '1';
+ TrnArnd <= '1';
+ ioaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "0011" => -- I/O Write! Master writes to target device.
+ if addr(31 downto 8) = baio(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ IOWrite <= '1';
+ ioaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "1100" => -- Memory Read! Master reads from target device.
+ if addr(31 downto 8) = bamem(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ MemRead <= '1';
+ TrnArnd <= '1';
+ if addr(1 downto 0) = "01" then -- reserved mode
+ ResFin <= '1';
+ elsif addr(1 downto 0) = "11" then -- reserved mode
+ ResFin <= '1';
+ end if;
+ memaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "1110" => -- Memory Read Line! Master reads from target device.
+ if addr(31 downto 8) = bamem(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ MemRead <= '1';
+ TrnArnd <= '1';
+ if addr(1 downto 0) = "01" then -- reserved mode
+ ResFin <= '1';
+ elsif addr(1 downto 0) = "11" then -- reserved mode
+ ResFin <= '1';
+ end if;
+ memaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "1111" => -- Memory Write! Master writes to target device.
+ if addr(31 downto 8) = bamem(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ MemWrite <= '1';
+ if addr(1 downto 0) = "01" then -- reserved mode
+ ResFin <= '1';
+ elsif addr(1 downto 0) = "11" then -- reserved mode
+ ResFin <= '1';
+ end if;
+ memaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "0110" => -- Memory Read! Master reads from target device.
+ if addr(31 downto 8) = bamem(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ MemRead <= '1';
+ TrnArnd <= '1';
+ if addr(1 downto 0) = "01" then -- reserved mode
+ ResFin <= '1';
+ elsif addr(1 downto 0) = "11" then -- reserved mode
+ ResFin <= '1';
+ end if;
+ memaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "0111" => -- Memory Write! Master writes to target device.
+ if addr(31 downto 8) = bamem(31 downto 8) then
+ DevAddr <= '1';
+ Busy <= '1';
+ MemWrite <= '1';
+ if addr(1 downto 0) = "01" then -- reserved mode
+ ResFin <= '1';
+ elsif addr(1 downto 0) = "11" then -- reserved mode
+ ResFin <= '1';
+ end if;
+ memaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "1010" => -- Configuration Read! Master reads from target device.
+ if (addr(31 downto 8) = bacfg(31 downto 8) and IDSEL = '1') then
+ if addr(1 downto 0) = "01" then
+ report "Target device: Type 1 configuration access on bus! Ignored."
+ severity Note;
+ elsif addr(1 downto 0) = "00" then
+ CfgRead <= '1';
+ TrnArnd <= '1';
+ DevAddr <= '1';
+ Busy <= '1';
+ end if;
+ cfgaddr := Byte2Int(addr(7 downto 0));
+ else -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "1011" => -- Configuration Write! Master writes to target device.
+ if (addr(31 downto 8) = bacfg(31 downto 8) and IDSEL = '1') then
+ if addr(1 downto 0) = "01" then
+ report "Target device: Type 1 configuration access on bus! Ignored."
+ severity Note;
+ elsif addr(1 downto 0) = "00" then
+ CfgWrite <= '1';
+ DevAddr <= '1';
+ Busy <= '1';
+ end if;
+ cfgaddr := Byte2Int(addr(7 downto 0));
+ else
+ -- this device is not the addressed one,
+ DevAddr <= '0'; -- so it is not responding
+ end if;
+ when "0100" =>
+ report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
+ severity Warning;
+ when "0101" =>
+ report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
+ severity Warning;
+ when "1000" =>
+ report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
+ severity Warning;
+ when "1001" =>
+ report "Target device: Reserved Command detected on C/BE bus! Target will not respond."
+ severity Warning;
+ when "ZZZZ" => null;
+ when others =>
+ report "Target device: Unknown or invalid command on C/BE bus! Ignored."
+ severity Error;
+ end case;
+ end if;
+ -- elsif (Frame_N'Event and Frame_N = '1') then
+ end if;
+ end process;
+ ---------------------------------------------------------------------
+ -- Implementation of Write command.
+ -- Master writes to Target device.
+ ---------------------------------------------------------------------
+ WriteProc : process(CLK,RST_N)
+ variable waitreg : Std_Logic_Vector(15 downto 0) := x"0000";
+ variable Char3_2,Char1,Char0 : Std_Logic_Vector(7 downto 0) := x"00";
+ begin
+ if (CLK'Event and CLK = '1' and ((IRDY_N = '0' and TRDY_N = '0') or FRAME_N = '1')) then
+ assert (AD_Bus'Last_Event >= tsetup)
+ report "Target device : Data setup time violation in decode cycle!"
+ severity warning;
+ assert (C_BE_Bus'Last_Event >= tsetup)
+ report "Target device : Byte Enables setup time violation in decode cycle!"
+ severity warning;
+ if (WaitWrite = '1') then
+ Char3_2 := AD_Bus(15 downto 8);
+ Char1 := "0000" & AD_Bus(7 downto 4);
+ Char0 := "0000" & AD_Bus(3 downto 0);
+ trdy_loop := Byte2Int(Char3_2) ;
+ trdy_nr := Byte2Int(Char1); -- + 1;
+ trdy_st := Byte2Int(Char0);
+ elsif IOWrite = '1' then
+ -- Master writes to target I/O space
+ case addr(1 downto 0) is
+ when "00" =>
+ if C_BE_Bus = "0000" then
+ IOmem(ioaddr) := AD_Bus;
+ elsif C_BE_Bus = "1000" then
+ IOmem(ioaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "0100" then
+ IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ IOmem(ioaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1100" then
+ IOmem(ioaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0010" then
+ IOmem(ioaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1010" then
+ IOmem(ioaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0110" then
+ IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1110" then
+ IOmem(ioaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus(0) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "01" =>
+ if C_BE_Bus = "0001" then
+ IOmem(ioaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "1001" then
+ IOmem(ioaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "0101" then
+ IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ IOmem(ioaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1101" then
+ IOmem(ioaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus(1) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "10" =>
+ if C_BE_Bus = "0011" then
+ IOmem(ioaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "1011" then
+ IOmem(ioaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus(2) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "11" =>
+ if C_BE_Bus = "0111" then
+ IOmem(ioaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus(3) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when others =>
+ null;
+ end case;
+ ioaddr := ioaddr + 1;
+ elsif MemWrite = '1' then
+ -- Master writes to target memory space
+ case addr(1 downto 0) is
+ when "00" => -- linear incrementing mode
+ if C_BE_Bus = "0000" then
+ Mem(memaddr) := AD_Bus;
+ elsif C_BE_Bus = "0001" then
+ Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "0010" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0011" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "0100" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0101" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "0110" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0111" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus = "1000" then
+ Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "1001" then
+ Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "1010" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1011" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus = "1100" then
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1101" then
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1110" then
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ memaddr := memaddr + 1;
+ when "01" => -- reserved mode (disconnect after first data phase)
+ if C_BE_Bus = "0000" then
+ Mem(memaddr) := AD_Bus;
+ elsif C_BE_Bus = "0001" then
+ Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "0010" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0011" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "0100" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0101" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "0110" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0111" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus = "1000" then
+ Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "1001" then
+ Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "1010" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1011" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus = "1100" then
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1101" then
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1110" then
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "10" => -- cacheline wrap mode
+ if C_BE_Bus = "0000" then
+ Mem(memaddr) := AD_Bus;
+ elsif C_BE_Bus = "0001" then
+ Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "0010" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0011" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "0100" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0101" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "0110" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0111" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus = "1000" then
+ Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "1001" then
+ Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "1010" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1011" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus = "1100" then
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1101" then
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1110" then
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ memaddr := memaddr + 1;
+ when "11" => -- reserved mode (disconnect after first data phase)
+ if C_BE_Bus = "0000" then
+ Mem(memaddr) := AD_Bus;
+ elsif C_BE_Bus = "0001" then
+ Mem(memaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "0010" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0011" then
+ Mem(memaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "0100" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0101" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "0110" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0111" then
+ Mem(memaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus = "1000" then
+ Mem(memaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "1001" then
+ Mem(memaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "1010" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1011" then
+ Mem(memaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus = "1100" then
+ Mem(memaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1101" then
+ Mem(memaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1110" then
+ Mem(memaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when others =>
+ null;
+ end case;
+ elsif CfgWrite = '1' then
+ -- Master writes to target configuration space
+ if C_BE_Bus = "0000" then
+ Cfgmem(cfgaddr) := AD_Bus;
+ elsif C_BE_Bus = "0001" then
+ Cfgmem(cfgaddr)(31 downto 8) := AD_Bus(31 downto 8);
+ elsif C_BE_Bus = "0010" then
+ Cfgmem(cfgaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0011" then
+ Cfgmem(cfgaddr)(31 downto 16) := AD_Bus(31 downto 16);
+ elsif C_BE_Bus = "0100" then
+ Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Cfgmem(cfgaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "0101" then
+ Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Cfgmem(cfgaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "0110" then
+ Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "0111" then
+ Cfgmem(cfgaddr)(31 downto 24) := AD_Bus(31 downto 24);
+ elsif C_BE_Bus = "1000" then
+ Cfgmem(cfgaddr)(23 downto 0) := AD_Bus(23 downto 0);
+ elsif C_BE_Bus = "1001" then
+ Cfgmem(cfgaddr)(23 downto 8) := AD_Bus(23 downto 8);
+ elsif C_BE_Bus = "1010" then
+ Cfgmem(cfgaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1011" then
+ Cfgmem(cfgaddr)(23 downto 16) := AD_Bus(23 downto 16);
+ elsif C_BE_Bus = "1100" then
+ Cfgmem(cfgaddr)(15 downto 0) := AD_Bus(15 downto 0);
+ elsif C_BE_Bus = "1101" then
+ Cfgmem(cfgaddr)(15 downto 8) := AD_Bus(15 downto 8);
+ elsif C_BE_Bus = "1110" then
+ Cfgmem(cfgaddr)(7 downto 0) := AD_Bus(7 downto 0);
+ elsif C_BE_Bus = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ cfgaddr := cfgaddr + 1;
+ end if;
+ end if;
+ end process;
+ ---------------------------------------------------------------------
+ -- Implementation of Read command.
+ -- Master read from Target device.
+ ---------------------------------------------------------------------
+ ReadProc : process(RST_N,CLK,cmdBusReady,IORead,IOWrite,MemRead,MemWrite,CfgRead,CfgWrite)
+ variable first : Boolean := true;
+ begin
+ if (Falling_Edge(RST_N) or RST_N = '0') then
+ AD_Bus <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ";
+ elsif (CLK'Event and CLK = '0') then
+ cmdBusReady <= '0';
+ if (first = true or TrnArnd ='1') then
+ -- Initialize the AD_Bus to avoid bus conflict
+ AD_Bus <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ";
+ first := false;
+ elsif Init = '1' then
+ Init <= '0';
+ AD_Bus <= "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ" after tdelay;
+ end if;
+ elsif IORead'Event and IORead = '0' then
+ Init <= '1';
+ elsif MemRead'Event and MemRead = '0' then
+ Init <= '1';
+ elsif CfgRead'Event and CfgRead = '0' then
+ Init <= '1';
+ elsif (CLK'Event and CLK = '1' and IRDY_N = '0') then
+ if (IORead = '1' or MemRead = '1' or CfgRead = '1') then
+ cmd <= C_BE_Bus; -- read the byte enable command
+ cmdBusReady <= '1';
+ end if;
+ elsif (cmdBusReady'Event and cmdBusReady = '0' and TRDY_N = '0') then
+ if IORead = '1' then
+ -- Master reads from target I/O space
+ case addr(1 downto 0) is
+ when "00" =>
+ if cmd = "0000" then
+ AD_Bus <= IOmem(ioaddr) after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= IOmem(ioaddr)(23 downto 0) after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 0) <= IOmem(ioaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= IOmem(ioaddr)(15 downto 0) after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= IOmem(ioaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= IOmem(ioaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= IOmem(ioaddr)(7 downto 0) after tdelay;
+ elsif cmd(0) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "01" =>
+ if cmd = "0001" then
+ AD_Bus(31 downto 8) <= IOmem(ioaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= IOmem(ioaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= IOmem(ioaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= IOmem(ioaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd(1) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "10" =>
+ if cmd = "0011" then
+ AD_Bus(31 downto 16) <= IOmem(ioaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= IOmem(ioaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd(2) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "11" =>
+ if cmd = "0111" then
+ AD_Bus(31 downto 24) <= IOmem(ioaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd(3) = '1' then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when others =>
+ null;
+ end case;
+ ioaddr := ioaddr + 1;
+ elsif MemRead = '1' then
+ -- Master reads from target memory space
+ case addr(1 downto 0) is
+ when "00" => -- linear incrementing mode
+ if cmd = "0000" then
+ AD_Bus <= Mem(memaddr) after tdelay;
+ elsif cmd = "0001" then
+ AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ elsif cmd = "0011" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0111" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ memaddr := memaddr + 1;
+ when "01" => -- reserved mode (disconnect after first data phase)
+ if cmd = "0000" then
+ AD_Bus <= Mem(memaddr) after tdelay;
+ elsif cmd = "0001" then
+ AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ elsif cmd = "0011" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0111" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when "10" => -- cacheline wrap mode
+ if cmd = "0000" then
+ AD_Bus <= Mem(memaddr) after tdelay;
+ elsif cmd = "0001" then
+ AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ elsif cmd = "0011" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0111" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ memaddr := memaddr + 1;
+ when "11" => -- reserved mode (disconnect after first data phase)
+ if cmd = "0000" then
+ AD_Bus <= Mem(memaddr) after tdelay;
+ elsif cmd = "0001" then
+ AD_Bus(31 downto 8) <= Mem(memaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ elsif cmd = "0011" then
+ AD_Bus(31 downto 16) <= Mem(memaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0111" then
+ AD_Bus(31 downto 24) <= Mem(memaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= Mem(memaddr)(23 downto 0) after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= Mem(memaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Mem(memaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= Mem(memaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= Mem(memaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Mem(memaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ when others =>
+ null;
+ end case;
+ elsif CfgRead = '1' then
+ -- Master reads from target configuration space
+ if cmd = "0000" then
+ AD_Bus <= Cfgmem(cfgaddr) after tdelay;
+ elsif cmd = "0001" then
+ AD_Bus(31 downto 8) <= Cfgmem(cfgaddr)(31 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0010" then
+ AD_Bus(31 downto 16) <= Cfgmem(cfgaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0011" then
+ AD_Bus(31 downto 16) <= Cfgmem(cfgaddr)(31 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "0100" then
+ AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
+ AD_Bus(15 downto 0) <= Cfgmem(cfgaddr)(15 downto 0) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ elsif cmd = "0101" then
+ AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 16) <= "11111111" after tdelay;
+ AD_Bus(15 downto 8) <= Cfgmem(cfgaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "0110" then
+ AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 8) <= "1111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
+ elsif cmd = "0111" then
+ AD_Bus(31 downto 24) <= Cfgmem(cfgaddr)(31 downto 24) after tdelay;
+ AD_Bus(23 downto 0) <= "111111111111111111111111" after tdelay;
+ elsif cmd = "1000" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 0) <= Cfgmem(cfgaddr)(23 downto 0) after tdelay;
+ elsif cmd = "1001" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 8) <= Cfgmem(cfgaddr)(23 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1010" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Cfgmem(cfgaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 8) <= "11111111" after tdelay;
+ AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1011" then
+ AD_Bus(31 downto 24) <= "11111111" after tdelay;
+ AD_Bus(23 downto 16) <= Cfgmem(cfgaddr)(23 downto 16) after tdelay;
+ AD_Bus(15 downto 0) <= "1111111111111111" after tdelay;
+ elsif cmd = "1100" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 0) <= Cfgmem(cfgaddr)(15 downto 0) after tdelay;
+ elsif cmd = "1101" then
+ AD_Bus(31 downto 16) <= "1111111111111111" after tdelay;
+ AD_Bus(15 downto 8) <= Cfgmem(cfgaddr)(15 downto 8) after tdelay;
+ AD_Bus(7 downto 0) <= "11111111" after tdelay;
+ elsif cmd = "1110" then
+ AD_Bus(31 downto 8) <= "111111111111111111111111" after tdelay;
+ AD_Bus(7 downto 0) <= Cfgmem(cfgaddr)(7 downto 0) after tdelay;
+ elsif cmd = "1111" then
+ report "Target device: Byte Enable word not valid !"
+ severity Error;
+ end if;
+ cfgaddr := cfgaddr + 1;
+ end if;
+ end if;
+ end process;
+ ---------------------------------------------------------------------
+ -- Implements the wait states process.
+ -- Target generates wait states accordingly to wait states parameters
+ -- received from master during Special Cycle.
+ -- Master reads the parameters from commands file.
+ ---------------------------------------------------------------------
+ WaitProc : process(CLK,FRAME_N,RST_N)
+ variable counter : Integer;
+ variable waitcnt : Integer;
+ variable start : Boolean;
+ begin
+ if (Falling_Edge(RST_N) or RST_N = '0') then
+ TRDY_N <= 'Z';
+ elsif (FRAME_N'Event and FRAME_N = '0') then
+ counter := 0;
+ start := true;
+ TRDY_N <= '1';
+ elsif (CLK'Event and CLK = '0') then
+ if (Busy = '0' and DevAddr = '0') then -- deselect device
+ TRDY_N <= 'H';
+ elsif (Busy = '0' and DevAddr = '1') then -- deselect signal
+ TRDY_N <= '1';
+ end if;
+ if (DevAddr = '1' and TrnArnd = '0' and DEVSEL_N = '0') then
+ if (counter >= trdy_st and start = true and TRDY_N = '1') then
+ -- finish waitstates at start
+ TRDY_N <= '0';
+ start := false;
+ elsif (counter = trdy_loop and TRDY_N = '0') then
+ -- random waitstates
+ TRDY_N <= '1';
+ waits <= '1';
+ waitcnt := 1;
+ elsif (waitcnt = trdy_nr and waits = '1') then
+ -- finish random waitstates
+ waits <= '0';
+ TRDY_N <= '0';
+ elsif waits = '1' then -- count random waitstates
+ waitcnt := waitcnt + 1;
+ end if;
+ end if;
+ counter := counter + 1;
+ end if;
+ end process;
+ ---------------------------------------------------------------------
+ -- Implements the assertion process for IRDY_N, FRAME_N, and IDSEL
+ -- signals.
+ ---------------------------------------------------------------------
+ AsrtProc : process(CLK,FRAME_N,IRDY_N,IDSEL,AD_Bus)
+ variable irdevs : Boolean := false;
+ variable idsevs : Boolean := false;
+ variable counter : Integer;
+ begin
+ if Rising_Edge(CLK) and FRAME_N = '0' and IRDY_N = '1' then
+ counter := counter + 1;
+ if counter >= 8 then
+ report"Target device:IRDY is not asserted within 8 clocks from FRAME assertion!"
+ severity warning;
+ end if;
+ end if;
+ if AD_Bus'Event then
+ assert(CLK'Last_Event <= thold)
+ report"Target device: Address or Data hold time violation!"
+ severity warning;
+ end if;
+ if Rising_Edge(CLK) and DevAddr = '1' then
+ if irdevs = true then
+ irdevs := false;
+ assert(IRDY_N'Last_Event >= tsetup)
+ report"Target device: IRDY setup time violation in current data transfer!"
+ severity warning;
+ end if;
+ if idsevs = true then
+ idsevs := false;
+ assert(IDSEL'Last_Event >= tsetup)
+ report"Target device: IDSEL setup time violation!"
+ severity warning;
+ end if;
+ if FRAME_N = '0' and IRDY_N = '1' then
+ counter := counter + 1 ;
+ end if;
+ assert (counter <= 8)
+ report"Target device: IRDY has not been asserted within 8 clocks from FRAME assertion!"
+ severity warning;
+ elsif Falling_Edge(FRAME_N) then
+ counter := 0;
+ elsif Rising_Edge(FRAME_N) then
+ assert(CLK'Last_Event <= thold)
+ report"Target device: FRAME hold time violation in current data transfer!"
+ severity warning;
+ elsif Falling_Edge(IRDY_N) and DevAddr = '1' then
+ irdevs := true;
+ elsif Rising_Edge(IRDY_N) and DevAddr = '1' then
+ assert(CLK'Last_Event <= thold)
+ report"Target device: IRDY hold time violation in current data transfer!"
+ severity warning;
+ elsif Rising_Edge(IDSEL) and DevAddr = '1' then
+ idsevs := true;
+ elsif Falling_Edge(IDSEL) and DevAddr = '1' then
+ assert(CLK'Last_Event <= thold)
+ report"Target device: IDSEL hold time violation!"
+ severity warning;
+ end if;
+ end process;
+end Behavior; --================ End of architecture ================--
+-----------------------------------------------------------------------
+-- Revision list
+-- Version Author Date Changes
+--
+-- 0.1 Ovidiu Lupas June 09, 2000 New model
+-----------------------------------------------------------------------
+
Index: pci_core/tags/alpha/vhdl_behav/PCI.CMD
===================================================================
--- pci_core/tags/alpha/vhdl_behav/PCI.CMD (nonexistent)
+++ pci_core/tags/alpha/vhdl_behav/PCI.CMD (revision 10)
@@ -0,0 +1,59 @@
+## CONFIGURE THE FIRST TARGET DEVICE
+## WAIT ADDRESS DATA
+CWAT 00010CF0 0710FF00
+## I/O WRITE DWORD ADDRESS NR. DATA
+WRIO 00000850 01 AABBCCDD
+##
+## I/O READ DWORD ADDRESS NR. DATA
+RDIO 00000850 01 AAXXCCDD
+##
+## I/O WRITE DWORD ADDRESS NR. DATA
+WRIO 00000864 04 AABBCCDD EE00AABB CCDDEE00 AABBCCDD
+##
+## I/O READ DWORD ADDRESS NR. DATA
+RDIO 00000864 04 XXBBXXDD EEXXAABB CCDDXX00 XXBBXXDD
+##
+## CONFIGURE THE SECOND TARGET DEVICE
+## WAIT ADDRESS DATA
+CWAT 00020CF0 0710FF00
+## I/O WRITE DWORD ADDRESS NR. DATA
+WRIO 00001850 01 AABBCCDD
+##
+## I/O READ DWORD ADDRESS NR. DATA
+RDIO 00001850 01 AABBCCDD
+##
+## I/O WRITE DWORD ADDRESS NR. DATA
+WRIO 00001860 03 AABBCCDD EE00AABB CCDDEE00
+##
+## I/O READ DWORD ADDRESS NR. DATA
+RDIO 00001860 03 AABBCCDD EE00AABB CCDDEE00
+##
+## MEMORY WRITE DWORD ADDRESS NR. DATA
+WRSW 00005001 01 55AA66BB
+##
+## MEMORY READ DWORD ADDRESS NR. DATA
+RDSW 00005001 01 55AA66BB
+##
+## MEMORY MULTIPLE WRITE ADDRESS NR. DATA
+WRMW 00005000 02 66AA55BB CCDDBBEE
+##
+## MEMORY MULTIPLE READ ADDRESS NR. DATA
+RDMW 00005000 02 XXAAXXBB CCDDXXEE
+##
+## MEMORY MULTIPLE WRITE ADDRESS NR. DATA
+WRMW 00006010 04 66AA55BB CCDDBBEE 33664455 00000001
+##
+## MEMORY MULTIPLE READ ADDRESS NR. DATA
+RDMW 00006010 04 XXAAXXBB CCDDXXEE 33XX4455 00000001
+##
+## MEMORY READ LINE ADDRESS NR. DATA
+## RDML 00005000 04 00000000 00000000 00000000 00000000
+##
+## CONFIG WRITE DWORD ADDRESS NR. DATA
+WCFG 00010CF8 01 20000001
+##
+## CONFIG READ DWORD ADDRESS NR. DATA
+RCFG 00010CF8 01 20000001
+##
+## EXIT
+ABRT
pci_core/tags/alpha/vhdl_behav/PCI.CMD
Property changes :
Added: svn:executable
## -0,0 +1 ##
+*
\ No newline at end of property
Index: pci_core/tags/first/diagrams/pci.dia
===================================================================
--- pci_core/tags/first/diagrams/pci.dia (nonexistent)
+++ pci_core/tags/first/diagrams/pci.dia (revision 10)
@@ -0,0 +1,64 @@
+VGUIformatVersion 1.004000
+
+
+
+
+DEFINE_MODULE: new_unnamed_submodule0
+
+ DEFINE_DEVICE_INSTANCES:
+ END_DEFINE_DEVICE_INSTANCES.
+
+ DEFINE_TOPOLOGY:
+ END_DEFINE_TOPOLOGY.
+
+
+END_DEFINE_MODULE.
+
+
+
+DEFINE_MODULE: pci_controller
+
+ PORT_LIST( RST_n, CLK, DEVSEL_n, STOP, FRAME_n, TRDY_n,
+ IRDY_n, IDSEL, CBE, AD, SERR_n, PERR_n,
+ PAR );
+
+ DEFINE_DEVICE_INSTANCES:
+ trget_machine = Target_machine | 5.600000 4.400000 6.900000 7.300000
+ Parity = Parity | 5.600000 2.300000 6.800000 4.200000
+ END_DEFINE_DEVICE_INSTANCES.
+
+ DEFINE_TOPOLOGY:
+ Parity parity_PAR pci_controller PAR half-duplex 0 Std_logic L0 3.500000 2.500000 5.600000 2.500000
+ Parity PERR_par_n pci_controller PERR_n half-duplex 0 Std_logic L1 3.500000 2.700000 5.600000 2.700000
+ Parity SERR_par_n pci_controller SERR_n half-duplex 0 Std_logic L2 3.500000 2.900000 5.600000 2.900000
+ trget_machine AD_trgt Parity AD_trgt simplex 0 Std_logic_vector(31#downto#0) AD 5.600000 3.300000 4.300000 3.300000 4.300000 5.500000 5.600000 5.500000
+ pci_controller AD trget_machine AD_trgt half-duplex 0 Std_logic_vector(31#downto#0) AD 5.600000 5.500000 5.300000 5.500000 3.600000 5.500000
+ trget_machine CBE_trgt_n Parity CBE_trgt_n simplex 0 Std_logic_vector(3#downto#0) CBE 5.600000 3.700000 4.500000 3.700000 4.500000 5.700000 5.600000 5.700000
+ pci_controller CBE trget_machine CBE_trgt_n half-duplex 0 Std_logic_vector(3#downto#0) CBE 5.600000 5.700000 3.600000 5.700000
+ pci_controller IDSEL trget_machine IDSEL_trgt simplex 0 Std_logic L7 5.600000 6.000000 3.600000 6.000000
+ pci_controller IRDY_n trget_machine IRDY_trgt_n simplex 0 Std_logic L8 5.600000 6.200000 3.600000 6.200000
+ trget_machine TRDY_trgt_n pci_controller TRDY_n simplex 0 Std_logic L9 3.600000 6.400000 5.600000 6.400000
+ pci_controller FRAME_n trget_machine FRAME_trgt_n simplex 0 Std_logic L10 5.600000 6.600000 3.600000 6.600000
+ trget_machine STOP_trgt_n pci_controller STOP simplex 0 Std_logic L11 3.600000 6.800000 5.600000 6.800000
+ trget_machine DEVSEL_trgt_n pci_controller DEVSEL_n half-duplex 0 Std_logic L12 3.600000 7.000000 5.600000 7.000000
+ pci_controller CLK trget_machine CLK simplex 0 Std_logic CLK 5.600000 4.600000 3.700000 4.600000
+ trget_machine CLK Parity CLK simplex 0 Std_logic CLK 5.600000 4.100000 4.800000 4.100000 4.800000 4.600000 5.600000 4.600000
+ pci_controller RST_n trget_machine RST_n simplex 0 Std_logic RST_n 5.600000 5.000000 3.700000 5.000000
+ trget_machine RST_n Parity RST_n simplex 0 Std_logic RST_n 5.600000 3.900000 4.700000 3.900000 4.700000 5.000000 5.600000 5.000000
+ trget_machine ADDR_trgt DEV_NULL simplex 0 Std_logic_vector(LOCALADD#-#1#downto#0) L17 8.900001 4.600000 6.900000 4.600000
+ trget_machine DATA_trgt DEV_NULL half-duplex 0 Std_logic_vector(31#downto#0) L17 8.900001 4.900000 6.900000 4.900000
+ DEV_NULL unknown_port trget_machine TABORT simplex 0 Std_logic 0 6.900000 7.200000 8.900001 7.200000
+ DEV_NULL _ trget_machine TRETRY simplex 0 Std_logic 0 6.900000 7.000000 8.900001 7.000000
+ END_DEFINE_TOPOLOGY.
+
+GENERIC: LOCALADD : integer := 64
+ ANNOTATION: 3.821249 8.066763 PCI main block diagram
+ ANNOTATION: 3.779719 8.403428 PCI OpenCores group
+ ANNOTATION: 3.788020 8.736729 Jamil Khatib
+ BOUNDINGBOX: 3.700000 7.600000 7.100000 9.000001 7.100000 7.600000 3.700000 7.600000 3.700000 9.000001 7.100000 9.000001
+
+END_DEFINE_MODULE.
+
+
+
+
Index: pci_core/tags
===================================================================
--- pci_core/tags (nonexistent)
+++ pci_core/tags (revision 10)
pci_core/tags
Property changes :
Added: svn:mergeinfo
## -0,0 +0,0 ##