赞
踩
真双端口RAM有两个独立的读写端口,每个端口都可以独立发起读或者写。
1、读和写冲突:如果读和写同时有效,且读和写是同一个地址时,发生RAM读写冲突,此时会把最新的写数据直接赋给读数据,称为写穿通到读
2、写和写冲突:表示两个端口写使能同时有效且写地址相同,此时需要关断一个写,把两个写端口都需要更新的值处理到一个写端口上面,任何的DP RAM 都不支持写和写冲突。
下面展示 功能代码
。
`timescale 1ns / 1ps /// // 读写模块 Verilog 功能代码如下: module dp_ram_ab_rw( input sys_clk, input sys_rst_n ); wire ram_wren; wire ram_rden; wire [7:0] ram_rd_dataa; wire [7:0] ram_rd_datab; wire [7:0] ram_wr_data; wire [4:0] ram_rd_addr; wire [4:0] ram_wr_addr; wire rden_a; wire rden_b; wire wen_a; wire wen_b; wire [7:0] data_a; wire [7:0] data_b; wire [4:0] addr_a; wire [4:0] addr_b; reg [7:0] rw_cnt; reg flag; assign ram_wren = ((rw_cnt >= 8'd0) && (rw_cnt <= 8'd31))? 1'b1:1'b0 ; assign ram_rden = ((rw_cnt >= 8'd1) && (rw_cnt <= 8'd31))? 1'b1:1'b0 ; assign ram_wr_addr = rw_cnt[7:0] ; assign ram_rd_addr = rw_cnt[7:0] - 1'b1 ; assign ram_wr_data = rw_cnt[4:0] ; assign rden_a = flag ? 1'b0 :ram_rden ; assign wen_a = flag ? ram_wren :1'b0 ; assign addr_a = flag ? ram_wr_addr : ram_rd_addr ; assign data_a = flag ? ram_wr_data : 1'b0 ; assign rden_b = flag ? ram_rden : 1'b0; assign wen_b = flag ? 1'b0 : ram_wren; assign addr_b = flag ? ram_rd_addr : ram_wr_addr ; assign data_b = flag ? 1'b0 : ram_wr_data ; always @(posedge sys_clk or negedge sys_rst_n) if(!sys_rst_n) rw_cnt <= 8'd0 ; else if(rw_cnt == 8'd63) rw_cnt <= 8'd0 ; else rw_cnt <= rw_cnt + 1'b1 ; always @(posedge sys_clk or negedge sys_rst_n) if(!sys_rst_n) flag <= 1'b0 ; else if(rw_cnt == 8'd31) flag <= ~flag ; dp_ram_ab_ctl dp_ram_ab_ctl_inst( .clka(sys_clk), .clkb(sys_clk), .wena(wen_a), .wenb(wen_b), .ena (rden_a), .enb (rden_b), .din_a(data_a), .din_b(data_b), .addra(addr_a), .addrb(addr_b), .dout_a(ram_rd_dataa), .dout_b(ram_rd_datab) ); endmodule // 控制模块 Verilog 功能代码如下: module dp_ram_ab_ctl( input clka, input clkb, input wena, input wenb, input ena, input enb, input [7:0] din_a, input [7:0] din_b, input [4:0] addra, input [4:0] addrb, output reg [7:0] dout_a, output reg [7:0] dout_b ); reg [7:0] mem [31:0] ; always @(posedge clka) begin if(wena) mem[addra] <= din_a; if(wenb) mem[addrb] <= din_b; end always @(posedge clka) begin if(ena) dout_a <= mem[addra] ; else dout_a <= 8'hx; end always @(posedge clka) begin if(enb) dout_b <= mem[addra] ; else dout_b <= 8'hx; end endmodule // 仿真模块 Verilog 功能代码如下: module tb_dp_ram_ab( ); reg clk ; reg rst ; initial begin clk = 1'b0 ; rst = 1'b0 ; #300 rst = 1'b1 ; end always #10 clk = ~clk ; dp_ram_ab_rw dp_ram_ab_rw_inst( .sys_clk(clk), .sys_rst_n(rst) ); endmodule
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。