AR# 16233


6.3i/6.2i/6.1i/5.2i/5.1i UniSim, SimPrim, Simulation - Block RAM (setup) memory collision violation on CLKA with respect to CLKB (address collision)


Keywords: RTL, RAMB4, RAMB16, violated, respect, Verilog, VHDL, BRAM, block RAM

When I run an RTL simulation, the following types of errors occur for dual-port block RAM:

Message in ISE 6.2i and higher

For both VHDL and Verilog
"Memory Collision Error on RAMB16_S36_S36:<instance_name> at simulation time <time> ns
A write was requested to the same address simultaneously at both Port A and Port B of the RAM. The contents written to the RAM at address location <address> (hex) of Port A and address location <address> (hex) of Port B are unknown."

Message in ISE releases prior to 6.2i

"# Timing Violation Error: Setup time ## violated on RAMB instance <instance_name>.display_zero on CLKA port at simulation time ### ns with respect to CLKB port at simulation time ###. Expected setup time is 100."

# Expected := 0.1 ns; Observed := # ns; At : ### ns
# Time: ### ps Iteration: 1 Instance: <instance_name>"

These violations occur when I write to an address on one port and read from that address on another port. This is a violation because the data that is read on the read port is not valid. In the hardware, the value that is read might be the old data, the new data, or a combination of old and new. In simulation, the output is "X" because the value that is read is unknown. For more information, refer to the Virtex-II Platform FPGA User Guide at:

Go to Design Considerations -> Block SelectRAM Memory -> Conflict Resolution.



You should avoid collisions whenever possible. When an address is written to on one port, your design should not allow a read from the same address on the other port. However, this cannot be avoided in certain applications. As long as the value that is read on the second port is not used in your design, you can safely ignore the violations.

NOTE: For ISE 7.1i and higher, see (Xilinx Answer 21239).


VHDL Work-Around

NOTE: The collision warnings in the simulation are valid! You should disable the collision checks only if you are sure that the warnings can be safely ignored. It is safe to ignore these warnings only if you are not using the data that is read when the violation occurs. For example, in a FIFO application where the read port is always enabled for timing reasons, a violation occurs every time the FIFO is empty and data is written. The violation is valid in this case, but the value that is read is not used in the design, so you can ignore the violation. Use the following to work around similar situations:

1. Add a configuration statement to your testbench that changes the setup in the block RAM model to "0", as shown in the following example:

Example configuration statement:

configuration my_config of testbench is
for behavioral
for uut : top
for behavioral
for ram1, ram2, ram3 : RAMB4_S1_S1 use entity unisim.RAMB4_S1_S1
generic map (SETUP_ALL => 0 ns);
end for;
end for;
end for;
end for;
end my_config;

This configuration statement sets the setup time to "0" for the ram1, ram2, and ram3 instances. All other BRAM in the design still have a setup time and will flag collision warnings. These three RAM should no longer flag collision warnings.

2. Alter the configuration statement based on your design hierarchy, and the entity, architecture, and instance names in your design. The general format is as follows:

configuration <any_config_name> of <entity name in testbench> is
for <architecture name in testbench>
for <instance name given to top level in the testbench> : <entity name of top level>
for <architecture name of top level>
for <instance name for next level of hierarchy> : <entity name in next level of hierarchy>
for <architecture name in next level of hierarchy>
for <BRAM instance name>, <BRAM instance name>, ... : <BRAM model name> use entity unisim.<BRAM model name>
generic map (SETUP_ALL => 0 ns);
end for;
end for;
end for;
end for;
end <config name>;

3. When your design is loaded, the configuration statement in the testbench must be loaded, rather than the architecture.


Verilog Work-Around
If you are certain that the collision violations can be safely ignored, you can work around this issue by disabling the collision warnings on selected block RAM as described below.

Methodology in ISE 6.1i

Perform one of the following:
- Compile the individual RAM models that you are using and define DISABLE_COLLISION_CHECK.
- Set a config option so that CompXLib will disable collision checking for the RAM models that it compiles. Use the appropriate method for your simulator as follows:

- command line: vlog +define+DISABLE_COLLISION_CHECK
- compxlib's compxlib.cfg: OPTION:mti_se:verilog: -source -93 +define+DISABLE_COLLISION_CHECK

- command line: vcs +define+DISABLE_COLLISION_CHECK
- compxlib's compxlib.cfg: OPTION:vcs:verilog: -Mupdate +define+DISABLE_COLLISION_CHECK

- command line: ncvlog -DEFINE DISABLE_COLLISION_CHECK
- command line: ncverilog +define+DISABLE_COLLISION_CHECK
- compxlib's compxlib.cfg: OPTION:ncsim:verilog: -MESSAGES -NOLOG -DEFINE DISABLE_COLLISION_CHECK

You can access information on the "compxlib.cfg" file in the Synthesis and Verification Design located at:

Methodology prior to ISE 6.1i

Add assign statements to your testbench as shown below.


initial begin

assign uut.ram_inst.data_collision = 0;
assign uut.ram_inst.memory_collision = 0;
assign uut.ram_inst.data_collision_a_b = 0;
assign uut.ram_inst.memory_collision_a_b = 0;
assign uut.ram_inst.data_collision_b_a = 0;
assign uut.ram_inst.memory_collision_b_a = 0;
assign uut.ram_inst.address_collision_a_b = 0;
assign uut.ram_inst.address_collision_b_a = 0;
assign uut.ram_inst.address_collision = 0;


This disables the setup violations between the clocks on the ram_inst block RAM instance. All other block RAM in the design retain the setup checks between the clocks. (You must change the "uut.ram_inst" based on the hierarchy of the design. To make this change, begin at the testbench and work down through all the levels of hierarchy using instance names: inst.inst.inst.inst.<reg>.)

The ram_inst should match the name of the instantiation of the RAMB in the top-level files.

This change will still produce the messages, but the output of the block RAM will no longer be Xs.
AR# 16233
日期 11/18/2008
状态 Archive
Type 综合文章
People Also Viewed