verilog语法进阶-分布式ram原语

概述

官方提供的原语

   RAM16X1S_1 #(
      .INIT(16'h0000) // Initial contents of RAM
   ) RAM16X1S_1_inst (
      .O(O),       // RAM output
      .A0(A0),     // RAM address[0] input
      .A1(A1),     // RAM address[1] input
      .A2(A2),     // RAM address[2] input
      .A3(A3),     // RAM address[3] input
      .D(D),       // RAM data input
      .WCLK(WCLK), // Write clock input
      .WE(WE)      // Write enable input
   );


   RAM16X1D_1 #(
      .INIT(16'h0000) // Initial contents of RAM
   ) RAM16X1D_1_inst (
      .DPO(DPO),     // Read-only 1-bit data output
      .SPO(SPO),     // Rw/ 1-bit data output
      .A0(A0),       // Rw/ address[0] input bit
      .A1(A1),       // Rw/ address[1] input bit
      .A2(A2),       // Rw/ address[2] input bit
      .A3(A3),       // Rw/ address[3] input bit
      .D(D),         // Write 1-bit data input
      .DPRA0(DPRA0), // Read-only address[0] input bit
      .DPRA1(DPRA1), // Read-only address[1] input bit
      .DPRA2(DPRA2), // Read-only address[2] input bit
      .DPRA3(DPRA3), // Read-only address[3] input bit
      .WCLK(WCLK),   // Write clock input
      .WE(WE)        // Write enable input
   );

内容

  1. 单端分布式ram

  2. 双端分布式ram

1. 单端分布式ram

verilog c代码

module primitive1(
	input clk,
	input write_enable,
	input [1-1:0] input_data,
	output [1-1:0] output_data,
	input [4-1:0] address
    );
 
parameter RAM_WIDTH = 1;
parameter RAM_ADDR_BITS = 4;
 
(* RAM_STYLE="{AUTO | DISTRIBUTED | PIPE_DISTRIBUTED}" *)
reg [RAM_WIDTH-1:0] dram [(2**RAM_ADDR_BITS)-1:0];
 
always @(posedge clk)
  if (write_enable)
	 dram[address] <= input_data; // 写数据
 
assign output_data = dram[address];   //读数据
endmodule	

原语

module primitive1 (
  clk, write_enable, output_data, address, input_data
);
  input clk;
  input write_enable;
  output [0 : 0] output_data;
  input [3 : 0] address;
  input [0 : 0] input_data;
  wire address_0_IBUF_4;
  wire address_1_IBUF_5;
  wire address_2_IBUF_6;
  wire address_3_IBUF_7;
  wire clk_BUFGP_9;
  wire input_data_0_IBUF_11;
  wire output_data_0_OBUF_13;
  wire write_enable_IBUF_15;
  RAM16X1S   Mram_dram (
    .A0(address_0_IBUF_4),
    .A1(address_1_IBUF_5),
    .A2(address_2_IBUF_6),
    .A3(address_3_IBUF_7),
    .D(input_data_0_IBUF_11),
    .WCLK(clk_BUFGP_9),
    .WE(write_enable_IBUF_15),
    .O(output_data_0_OBUF_13)
  );
  IBUF   write_enable_IBUF (
    .I(write_enable),
    .O(write_enable_IBUF_15)
  );
  IBUF   address_3_IBUF (
    .I(address[3]),
    .O(address_3_IBUF_7)
  );
  IBUF   address_2_IBUF (
    .I(address[2]),
    .O(address_2_IBUF_6)
  );
  IBUF   address_1_IBUF (
    .I(address[1]),
    .O(address_1_IBUF_5)
  );
  IBUF   address_0_IBUF (
    .I(address[0]),
    .O(address_0_IBUF_4)
  );
  IBUF   input_data_0_IBUF (
    .I(input_data[0]),
    .O(input_data_0_IBUF_11)
  );
  OBUF   output_data_0_OBUF (
    .I(output_data_0_OBUF_13),
    .O(output_data[0])
  );
  BUFGP   clk_BUFGP (
    .I(clk),
    .O(clk_BUFGP_9)
  );
endmodule

RTL结构图

技术原理图

2. 双端分布式ram

verilog c代码

module primitive1(
	input clk,
	input write_enable,
	input [1-1:0] input_data,
	output [1-1:0] output_data,
	input [4-1:0] write_address,read_address
    );
 
parameter RAM_WIDTH = 1;
parameter RAM_ADDR_BITS = 4;
 
(* RAM_STYLE="{AUTO | DISTRIBUTED | PIPE_DISTRIBUTED}" *)
reg [RAM_WIDTH-1:0] ddram [(2**RAM_ADDR_BITS)-1:0];
 
 
always @(posedge clk)
  if (write_enable)
	 ddram[write_address] <= input_data;
 
assign output_data = ddram[read_address];   
 
endmodule

原语代码

module primitive1 (
  clk, write_enable, output_data, write_address, read_address, input_data
);
  input clk;
  input write_enable;
  output [0 : 0] output_data;
  input [3 : 0] write_address;
  input [3 : 0] read_address;
  input [0 : 0] input_data;
  wire clk_BUFGP_1;
  wire input_data_0_IBUF_3;
  wire output_data_0_OBUF_5;
  wire read_address_0_IBUF_10;
  wire read_address_1_IBUF_11;
  wire read_address_2_IBUF_12;
  wire read_address_3_IBUF_13;
  wire write_address_0_IBUF_18;
  wire write_address_1_IBUF_19;
  wire write_address_2_IBUF_20;
  wire write_address_3_IBUF_21;
  wire write_enable_IBUF_23;
  wire NLW_Mram_ddram_SPO_UNCONNECTED;
  RAM16X1D   Mram_ddram (
    .A0(write_address_0_IBUF_18),
    .A1(write_address_1_IBUF_19),
    .A2(write_address_2_IBUF_20),
    .A3(write_address_3_IBUF_21),
    .D(input_data_0_IBUF_3),
    .DPRA0(read_address_0_IBUF_10),
    .DPRA1(read_address_1_IBUF_11),
    .DPRA2(read_address_2_IBUF_12),
    .DPRA3(read_address_3_IBUF_13),
    .WCLK(clk_BUFGP_1),
    .WE(write_enable_IBUF_23),
    .SPO(NLW_Mram_ddram_SPO_UNCONNECTED),
    .DPO(output_data_0_OBUF_5)
  );
  IBUF   write_enable_IBUF (
    .I(write_enable),
    .O(write_enable_IBUF_23)
  );
  IBUF   write_address_3_IBUF (
    .I(write_address[3]),
    .O(write_address_3_IBUF_21)
  );
  IBUF   write_address_2_IBUF (
    .I(write_address[2]),
    .O(write_address_2_IBUF_20)
  );
  IBUF   write_address_1_IBUF (
    .I(write_address[1]),
    .O(write_address_1_IBUF_19)
  );
  IBUF   write_address_0_IBUF (
    .I(write_address[0]),
    .O(write_address_0_IBUF_18)
  );
  IBUF   read_address_3_IBUF (
    .I(read_address[3]),
    .O(read_address_3_IBUF_13)
  );
  IBUF   read_address_2_IBUF (
    .I(read_address[2]),
    .O(read_address_2_IBUF_12)
  );
  IBUF   read_address_1_IBUF (
    .I(read_address[1]),
    .O(read_address_1_IBUF_11)
  );
  IBUF   read_address_0_IBUF (
    .I(read_address[0]),
    .O(read_address_0_IBUF_10)
  );
  IBUF   input_data_0_IBUF (
    .I(input_data[0]),
    .O(input_data_0_IBUF_3)
  );
  OBUF   output_data_0_OBUF (
    .I(output_data_0_OBUF_5),
    .O(output_data[0])
  );
  BUFGP   clk_BUFGP (
    .I(clk),
    .O(clk_BUFGP_1)
  );
endmodule

RTL结构图

技术原理图

3. 总结

  1. FPGA的LUT可以配置成分布式ram

  2. 分布式ram的原语分为单端和双端