DS_DMA
|
00001 00002 ------------------------------------------------------------------------------- 00003 -- 00004 -- (c) Copyright 2009-2011 Xilinx, Inc. All rights reserved. 00005 -- 00006 -- This file contains confidential and proprietary information 00007 -- of Xilinx, Inc. and is protected under U.S. and 00008 -- international copyright and other intellectual property 00009 -- laws. 00010 -- 00011 -- DISCLAIMER 00012 -- This disclaimer is not a license and does not grant any 00013 -- rights to the materials distributed herewith. Except as 00014 -- otherwise provided in a valid license issued to you by 00015 -- Xilinx, and to the maximum extent permitted by applicable 00016 -- law: (1) THESE MATERIALS ARE MADE AVAILABLE "AS IS" AND 00017 -- WITH ALL FAULTS, AND XILINX HEREBY DISCLAIMS ALL WARRANTIES 00018 -- AND CONDITIONS, EXPRESS, IMPLIED, OR STATUTORY, INCLUDING 00019 -- BUT NOT LIMITED TO WARRANTIES OF MERCHANTABILITY, NON- 00020 -- INFRINGEMENT, OR FITNESS FOR ANY PARTICULAR PURPOSE; and 00021 -- (2) Xilinx shall not be liable (whether in contract or tort, 00022 -- including negligence, or under any other theory of 00023 -- liability) for any loss or damage of any kind or nature 00024 -- related to, arising under or in connection with these 00025 -- materials, including for any direct, or any indirect, 00026 -- special, incidental, or consequential loss or damage 00027 -- (including loss of data, profits, goodwill, or any type of 00028 -- loss or damage suffered as a result of any action brought 00029 -- by a third party) even if such damage or loss was 00030 -- reasonably foreseeable or Xilinx had been advised of the 00031 -- possibility of the same. 00032 -- 00033 -- CRITICAL APPLICATIONS 00034 -- Xilinx products are not designed or intended to be fail- 00035 -- safe, or for use in any application requiring fail-safe 00036 -- performance, such as life-support or safety devices or 00037 -- systems, Class III medical devices, nuclear facilities, 00038 -- applications related to the deployment of airbags, or any 00039 -- other applications that could lead to death, personal 00040 -- injury, or severe property or environmental damage 00041 -- (individually and collectively, "Critical 00042 -- Applications"). Customer assumes the sole risk and 00043 -- liability of any use of Xilinx products in Critical 00044 -- Applications, subject only to applicable laws and 00045 -- regulations governing limitations on product liability. 00046 -- 00047 -- THIS COPYRIGHT NOTICE AND DISCLAIMER MUST BE RETAINED AS 00048 -- PART OF THIS FILE AT ALL TIMES. 00049 -- 00050 ------------------------------------------------------------------------------- 00051 -- Project : Virtex-6 Integrated Block for PCI Express 00052 -- File : pcie_brams_v6.vhd 00053 -- Version : 2.3 00054 ---- Description: BlockRAM module for Virtex6 PCIe Block 00055 ---- 00056 ---- 00057 ---- 00058 ---------------------------------------------------------------------------------- 00059 00060 library ieee; 00061 use ieee.std_logic_1164.all; 00062 use ieee.std_logic_unsigned.all; 00063 00064 entity pcie_brams_v6 is 00065 generic ( 00066 -- the number of BRAMs to use 00067 -- supported values are: 00068 -- 1,2,4,8,18 00069 NUM_BRAMS : integer := 0; 00070 00071 -- BRAM read address latency 00072 -- 00073 -- value meaning 00074 -- ==================================================== 00075 -- 0 BRAM read address port sample 00076 -- 1 BRAM read address port sample and a pipeline stage on the address port 00077 RAM_RADDR_LATENCY : integer := 1; 00078 00079 -- BRAM read data latency 00080 -- 00081 -- value meaning 00082 -- ==================================================== 00083 -- 1 no BRAM OREG 00084 -- 2 use BRAM OREG 00085 -- 3 use BRAM OREG and a pipeline stage on the data port 00086 RAM_RDATA_LATENCY : integer := 1; 00087 00088 -- BRAM write latency 00089 -- The BRAM write port is synchronous 00090 -- 00091 -- value meaning 00092 -- ==================================================== 00093 -- 0 BRAM write port sample 00094 -- 1 BRAM write port sample plus pipeline stage 00095 RAM_WRITE_LATENCY : integer := 1 00096 00097 ); 00098 port ( 00099 user_clk_i : in std_logic; 00100 reset_i : in std_logic; 00101 wen : in std_logic; 00102 waddr : in std_logic_vector(12 downto 0); 00103 wdata : in std_logic_vector(71 downto 0); 00104 ren : in std_logic; 00105 rce : in std_logic; 00106 raddr : in std_logic_vector(12 downto 0); 00107 rdata : out std_logic_vector(71 downto 0) 00108 ); 00109 end pcie_brams_v6; 00110 00111 architecture v6_pcie of pcie_brams_v6 is 00112 component pcie_bram_v6 is 00113 generic ( 00114 DOB_REG : integer; 00115 WIDTH : integer 00116 ); 00117 port ( 00118 user_clk_i : in std_logic; 00119 reset_i : in std_logic; 00120 wen_i : in std_logic; 00121 waddr_i : in std_logic_vector(12 downto 0); 00122 wdata_i : in std_logic_vector(WIDTH - 1 downto 0); 00123 ren_i : in std_logic; 00124 rce_i : in std_logic; 00125 raddr_i : in std_logic_vector(12 downto 0); 00126 rdata_o : out std_logic_vector(WIDTH - 1 downto 0) 00127 ); 00128 end component; 00129 00130 FUNCTION to_integer ( 00131 in_val : IN boolean) RETURN integer IS 00132 BEGIN 00133 IF (in_val) THEN 00134 RETURN(1); 00135 ELSE 00136 RETURN(0); 00137 END IF; 00138 END to_integer; 00139 00140 -- turn on the bram output register 00141 constant DOB_REG : integer := to_integer(RAM_RDATA_LATENCY > 1); 00142 00143 -- calculate the data width of the individual brams 00144 function width ( 00145 constant NUM_BRAM : integer) 00146 return integer is 00147 variable WIDTH_BRAM : integer := 1; 00148 begin -- width 00149 00150 if (NUM_BRAM = 1) then 00151 WIDTH_BRAM := 72; 00152 elsif (NUM_BRAM = 2) then 00153 WIDTH_BRAM := 36; 00154 elsif (NUM_BRAM = 4) then 00155 WIDTH_BRAM := 18; 00156 elsif (NUM_BRAM = 8) then 00157 WIDTH_BRAM := 9; 00158 else 00159 WIDTH_BRAM := 4; 00160 end if; 00161 return WIDTH_BRAM; 00162 end width; 00163 00164 constant BRAM_WIDTH : integer := width(NUM_BRAMS); 00165 00166 constant TCQ : integer := 1; 00167 00168 00169 signal wen_int : std_logic; 00170 signal waddr_int : std_logic_vector(12 downto 0); 00171 signal wdata_int : std_logic_vector(71 downto 0); 00172 00173 signal wen_dly : std_logic := '0'; 00174 signal waddr_dly : std_logic_vector(12 downto 0) := (others => '0'); 00175 signal wdata_dly : std_logic_vector(71 downto 0) := (others => '0'); 00176 00177 -- if (RAM_WRITE_LATENCY == 1) 00178 00179 -- model the delays for ram read latency 00180 00181 signal ren_int : std_logic; 00182 signal raddr_int : std_logic_vector(12 downto 0); 00183 signal rdata_int : std_logic_vector(71 downto 0); 00184 00185 signal ren_dly : std_logic; 00186 signal raddr_dly : std_logic_vector(12 downto 0); 00187 signal rdata_dly : std_logic_vector(71 downto 0); 00188 00189 begin 00190 00191 --synthesis translate_off 00192 process 00193 begin 00194 -- $display("[%t] %m NUM_BRAMS %0d DOB_REG %0d WIDTH %0d RAM_WRITE_LATENCY %0d RAM_RADDR_LATENCY %0d RAM_RDATA_LATENCY %0d", now, to_stdlogic(NUM_BRAMS), to_stdlogicvector(DOB_REG, 13), ("00000000000000000000000000000000000000000000000000000000000000000" & WIDTH), to_stdlogic(RAM_WRITE_LATENCY), to_stdlogic(RAM_RADDR_LATENCY), to_stdlogicvector(RAM_RDATA_LATENCY, 13)); 00195 case NUM_BRAMS is 00196 when 1 | 2 | 4 | 8 | 18 => 00197 when others => 00198 -- $display("[%t] %m Error NUM_BRAMS %0d not supported", now, to_stdlogic(NUM_BRAMS)); 00199 -- $finish(); 00200 end case; -- case(NUM_BRAMS) 00201 case RAM_RADDR_LATENCY is 00202 when 0 | 1 => 00203 when others => 00204 -- $display("[%t] %m Error RAM_READ_LATENCY %0d not supported", now, to_stdlogic(RAM_RADDR_LATENCY)); 00205 -- $finish(); 00206 end case; -- case (RAM_RADDR_LATENCY) 00207 case RAM_RDATA_LATENCY is 00208 when 1 | 2 | 3 => 00209 when others => 00210 -- $display("[%t] %m Error RAM_READ_LATENCY %0d not supported", now, to_stdlogic(RAM_RDATA_LATENCY)); 00211 -- $finish(); 00212 end case; -- case (RAM_RDATA_LATENCY) 00213 case RAM_WRITE_LATENCY is 00214 when 0 | 1 => 00215 when others => 00216 -- $display("[%t] %m Error RAM_WRITE_LATENCY %0d not supported", now, to_stdlogic(RAM_WRITE_LATENCY)); 00217 -- $finish(); 00218 end case; -- case(RAM_WRITE_LATENCY) 00219 wait; 00220 end process; 00221 --synthesis translate_on 00222 00223 -- model the delays for ram write latency 00224 wr_lat_2 : if (RAM_WRITE_LATENCY = 1) generate 00225 process (user_clk_i) 00226 begin 00227 if (user_clk_i'event and user_clk_i = '1') then 00228 if (reset_i = '1') then 00229 wen_dly <= '0' after (TCQ)*1 ps; 00230 waddr_dly <= "0000000000000" after (TCQ)*1 ps; 00231 wdata_dly <= "000000000000000000000000000000000000000000000000000000000000000000000000" after (TCQ)*1 ps; 00232 else 00233 wen_dly <= wen after (TCQ)*1 ps; 00234 waddr_dly <= waddr after (TCQ)*1 ps; 00235 wdata_dly <= wdata after (TCQ)*1 ps; 00236 end if; 00237 end if; 00238 end process; 00239 00240 wen_int <= wen_dly; 00241 waddr_int <= waddr_dly; 00242 wdata_int <= wdata_dly; 00243 end generate; 00244 00245 wr_lat_1 : if (RAM_WRITE_LATENCY = 0) generate 00246 wen_int <= wen; 00247 waddr_int <= waddr; 00248 wdata_int <= wdata; 00249 end generate; 00250 00251 raddr_lat_2 : if (RAM_RADDR_LATENCY = 1) generate 00252 00253 process (user_clk_i) 00254 begin 00255 if (user_clk_i'event and user_clk_i = '1') then 00256 if (reset_i = '1') then 00257 ren_dly <= '0' after (TCQ)*1 ps; 00258 raddr_dly <= "0000000000000" after (TCQ)*1 ps; 00259 else 00260 ren_dly <= ren after (TCQ)*1 ps; 00261 raddr_dly <= raddr after (TCQ)*1 ps; 00262 end if; -- else: !if(reset_i) 00263 end if; 00264 end process; 00265 00266 ren_int <= ren_dly; 00267 raddr_int <= raddr_dly; 00268 00269 end generate; -- block: rd_lat_addr_2 00270 00271 raddr_lat_1 : if (not(RAM_RADDR_LATENCY = 1)) generate 00272 ren_int <= ren; 00273 raddr_int <= raddr; 00274 end generate; 00275 00276 rdata_lat_3 : if (RAM_RDATA_LATENCY = 3) generate 00277 00278 process (user_clk_i) 00279 begin 00280 if (user_clk_i'event and user_clk_i = '1') then 00281 if (reset_i = '1') then 00282 rdata_dly <= "000000000000000000000000000000000000000000000000000000000000000000000000" after (TCQ)*1 ps; 00283 else 00284 rdata_dly <= rdata_int after (TCQ)*1 ps; 00285 end if; -- else: !if(reset_i) 00286 end if; 00287 end process; 00288 00289 rdata <= rdata_dly; 00290 00291 end generate; -- block: rd_lat_data_3 00292 00293 rdata_lat_1_2 : if (not(RAM_RDATA_LATENCY = 3)) generate 00294 rdata <= rdata_int after (TCQ)*1 ps; 00295 end generate; 00296 00297 -- instantiate the brams 00298 brams : for i in 0 to NUM_BRAMS - 1 generate 00299 00300 ram : pcie_bram_v6 00301 generic map ( 00302 DOB_REG => DOB_REG, 00303 WIDTH => BRAM_WIDTH 00304 ) 00305 port map ( 00306 user_clk_i => user_clk_i, 00307 reset_i => reset_i, 00308 wen_i => wen_int, 00309 waddr_i => waddr_int, 00310 wdata_i => wdata_int((((i + 1) * BRAM_WIDTH) - 1) downto (i * BRAM_WIDTH)), 00311 ren_i => ren_int, 00312 raddr_i => raddr_int, 00313 rdata_o => rdata_int((((i + 1) * BRAM_WIDTH) - 1) downto (i * BRAM_WIDTH)), 00314 rce_i => rce 00315 ); 00316 end generate; 00317 -- pcie_brams_v6 00318 end v6_pcie; 00319 00320