1 //////////////////////////////////////////////////////////////////////
3 //// Generic Dual-Port Synchronous RAM ////
5 //// This file is part of memory library available from ////
6 //// http://www.opencores.org/cvsweb.shtml/generic_memories/ ////
9 //// This block is a wrapper with common dual-port ////
10 //// synchronous memory interface for different ////
11 //// types of ASIC and FPGA RAMs. Beside universal memory ////
12 //// interface it also provides behavioral model of generic ////
13 //// dual-port synchronous RAM. ////
14 //// It also contains a fully synthesizeable model for FPGAs. ////
15 //// It should be used in all OPENCORES designs that want to be ////
16 //// portable accross different target technologies and ////
17 //// independent of target memory. ////
19 //// Supported ASIC RAMs are: ////
20 //// - Artisan Dual-Port Sync RAM ////
21 //// - Avant! Two-Port Sync RAM (*) ////
22 //// - Virage 2-port Sync RAM ////
24 //// Supported FPGA RAMs are: ////
25 //// - Generic FPGA (VENDOR_FPGA) ////
26 //// Tested RAMs: Altera, Xilinx ////
27 //// Synthesis tools: LeonardoSpectrum, Synplicity ////
28 //// - Xilinx (VENDOR_XILINX) ////
29 //// - Altera (VENDOR_ALTERA) ////
32 //// - fix Avant! ////
33 //// - add additional RAMs (VS etc) ////
36 //// - Richard Herveille, richard@asics.ws ////
37 //// - Damjan Lampret, lampret@opencores.org ////
39 //////////////////////////////////////////////////////////////////////
41 //// Copyright (C) 2000 Authors and OPENCORES.ORG ////
43 //// This source file may be used and distributed without ////
44 //// restriction provided that this copyright statement is not ////
45 //// removed from the file and that any derivative work contains ////
46 //// the original copyright notice and the associated disclaimer. ////
48 //// This source file is free software; you can redistribute it ////
49 //// and/or modify it under the terms of the GNU Lesser General ////
50 //// Public License as published by the Free Software Foundation; ////
51 //// either version 2.1 of the License, or (at your option) any ////
52 //// later version. ////
54 //// This source is distributed in the hope that it will be ////
55 //// useful, but WITHOUT ANY WARRANTY; without even the implied ////
56 //// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR ////
57 //// PURPOSE. See the GNU Lesser General Public License for more ////
60 //// You should have received a copy of the GNU Lesser General ////
61 //// Public License along with this source; if not, download it ////
62 //// from http://www.opencores.org/lgpl.shtml ////
64 //////////////////////////////////////////////////////////////////////
66 // CVS Revision History
68 // $Log: generic_dpram.v,v $
69 // Revision 1.2 2007-02-11 22:15:39 sithglan
70 // define xilinix and fpga
72 // Revision 1.1 2007/02/11 22:05:26 sithglan
75 // Revision 1.4 2002/09/28 08:18:52 rherveille
76 // Changed synthesizeable FPGA memory implementation.
77 // Fixed some issues with Xilinx BlockRAM
79 // Revision 1.3 2001/11/09 00:34:18 samg
80 // minor changes: unified with all common rams
82 // Revision 1.2 2001/11/08 19:11:31 samg
83 // added valid checks to behvioral model
85 // Revision 1.1.1.1 2001/09/14 09:57:10 rherveille
87 // Files are now compliant to Altera & Xilinx memories.
88 // Memories are now compatible, i.e. drop-in replacements.
89 // Added synthesizeable generic FPGA description.
90 // Created "generic_memories" cvs entry.
92 // Revision 1.1.1.2 2001/08/21 13:09:27 damjan
93 // *** empty log message ***
95 // Revision 1.1 2001/08/20 18:23:20 damjan
98 // Revision 1.1 2001/08/09 13:39:33 lampret
101 // Revision 1.2 2001/07/30 05:38:02 lampret
102 // Adding empty directories required by HDL coding guidelines
106 //`include "timescale.v"
109 `define VENDOR_XILINX
110 //`define VENDOR_ALTERA
112 module generic_dpram(
113 // Generic synchronous dual-port RAM interface
114 rclk, rrst, rce, oe, raddr, do,
115 wclk, wrst, wce, we, waddr, di
119 // Default address and data buses width
121 parameter aw = 5; // number of bits in address-bus
122 parameter dw = 16; // number of bits in data-bus
125 // Generic synchronous double-port RAM interface
128 input rclk; // read clock, rising edge trigger
129 input rrst; // read port reset, active high
130 input rce; // read port chip enable, active high
131 input oe; // output enable, active high
132 input [aw-1:0] raddr; // read address
133 output [dw-1:0] do; // data output
136 input wclk; // write clock, rising edge trigger
137 input wrst; // write port reset, active high
138 input wce; // write port chip enable, active high
139 input we; // write enable, active high
140 input [aw-1:0] waddr; // write address
141 input [dw-1:0] di; // data input
149 // Instantiation synthesizeable FPGA memory
151 // This code has been tested using LeonardoSpectrum and Synplicity.
152 // The code correctly instantiates Altera EABs and Xilinx BlockRAMs.
154 reg [dw-1:0] mem [(1<<aw) -1:0]; // instantiate memory
155 reg [aw-1:0] ra; // register read address
158 always @(posedge rclk)
165 always@(posedge wclk)
173 // Instantiation of FPGA memory:
175 // Virtex/Spartan2 BlockRAMs
177 xilinx_ram_dp xilinx_ram(
198 xilinx_ram.dwidth = dw,
199 xilinx_ram.awidth = aw;
205 // Instantiation of FPGA memory:
207 // Altera FLEX/APEX EABs
209 altera_ram_dp altera_ram(
225 altera_ram.dwidth = dw,
226 altera_ram.awidth = aw;
230 `ifdef VENDOR_ARTISAN
233 // Instantiation of ASIC memory:
235 // Artisan Synchronous Double-Port RAM (ra2sh)
237 art_hsdp #(dw, 1<<aw, aw) artisan_sdp(
262 // Instantiation of ASIC memory:
264 // Avant! Asynchronous Two-Port RAM
283 // Instantiation of ASIC memory:
285 // Virage Synchronous 2-port R/W RAM
287 virage_stp virage_stp(
310 // Generic dual-port synchronous RAM model
314 // Generic RAM's registers and wires
316 reg [dw-1:0] mem [(1<<aw)-1:0]; // RAM content
317 reg [dw-1:0] do_reg; // RAM data output register
320 // Data output drivers
322 assign do = (oe & rce) ? do_reg : {dw{1'bz}};
325 always @(posedge rclk)
327 do_reg <= #1 (we && (waddr==raddr)) ? {dw{1'b x}} : mem[raddr];
330 always @(posedge wclk)
335 // Task prints range of memory
336 // *** Remember that tasks are non reentrant, don't call this task in parallel for multiple instantiations.
338 input [aw-1:0] start;
339 input [aw-1:0] finish;
342 for (rnum=start;rnum<=finish;rnum=rnum+1)
343 $display("Addr %h = %h",rnum,mem[rnum]);
347 `endif // !VENDOR_VIRAGE
348 `endif // !VENDOR_AVANT
349 `endif // !VENDOR_ARTISAN
350 `endif // !VENDOR_ALTERA
351 `endif // !VENDOR_XILINX
352 `endif // !VENDOR_FPGA
361 module altera_ram_dp(
370 q) /* synthesis black_box */;
372 parameter awidth = 7;
373 parameter dwidth = 8;
375 input [dwidth -1:0] data;
376 input [awidth -1:0] wraddress;
377 input [awidth -1:0] rdaddress;
383 output [dwidth -1:0] q;
385 // synopsis translate_off
386 // exemplar translate_off
398 .RdAddress(rdaddress),
405 .WrAddress(wraddress),
410 // exemplar translate_on
411 // synopsis translate_on
414 `endif // VENDOR_ALTERA
417 module xilinx_ram_dp (
431 DOB) /* synthesis black_box */ ;
433 parameter awidth = 7;
434 parameter dwidth = 8;
440 input [awidth-1:0] ADDRA;
441 input [dwidth-1:0] DIA;
443 output [dwidth-1:0] DOA;
449 input [awidth-1:0] ADDRB;
450 input [dwidth-1:0] DIB;
452 output [dwidth-1:0] DOB;
454 // insert simulation model
457 // synopsys translate_off
458 // exemplar translate_off
460 C_MEM_DP_BLOCK_V1_0 #(
507 // exemplar translate_on
508 // synopsys translate_on
511 `endif // VENDOR_XILINX