FC2カウンター FPGAの部屋 ar37425のAXI4 Masterサンプルを試す5(シミュレーション2)
fc2ブログ

FPGAやCPLDの話題やFPGA用のツールの話題などです。 マニアックです。 日記も書きます。

FPGAの部屋

FPGAの部屋の有用と思われるコンテンツのまとめサイトを作りました。Xilinx ISEの初心者の方には、FPGAリテラシーおよびチュートリアルのページをお勧めいたします。

ar37425のAXI4 Masterサンプルを試す5(シミュレーション2)

ar37425のAXI4 Masterサンプルを試す4(シミュレーション)”の続き。

久しぶりにAXI4 Masterの話題。Altium Designer をやっている間にもAXI4 Masterのシミュレーションをいじっていた。やっと動いてきたので紹介する。

まずは、”Atlysボード+VmodCAMのシミュレーション”で紹介したように、Micron社のDDR2 SDRAMのモデルを使用した。
Micron社のDDR2 SDRAMのモデルのインスタンスをテストベンチに追加した。テストベンチをDDR2 SDRAMを使用するように大幅に変更した。

次に、DDR2 SDRAMのモデルを使用するためにデータバス幅とスピードグレードをdefineで指定する。
・Project Navigator のProcessesウインドウのSimulate Behavioral Modelを右クリックして、右クリックメニューの中からProcess Properties...を選択した。

・Specify `define Macro Name and Value にsg25E,x16 を設定する。
Atlys_52_120114.png

これで準備は終了。
シミュレーションを行った。ISimの全画面を下に示す。
Atlys_53_120114.png

Wave画面の拡大図を下に示す。
Atlys_54_120114.png

上図で、黄色の四角で囲ってあるのがDDR2の初期化部分、ピンク色の四角がキャリブレーション。
その後、58.445usecでMCB_DDR2の初期化終了信号のuo_done_cal がアサートされている。その後のトランザクションはAXI Master IPからのアクセスと思われる。

今日はお仕事であまり時間がないので、テストベンチのソースコードを貼って終わりにする。

`timescale 10ps / 1ps

////////////////////////////////////////////////////////////////////////////////
// Company: 
// Engineer:
//
// Create Date:   05:18:27 01/07/2012
// Design Name:   system_top
// Module Name:   H:/HDL/FndtnISEWork/Spartan6/Atlys/test/Atlys_XPS_CamDisp/ISE/Atlys_XPS_CamDisp/system_top_tb.v
// Project Name:  Atlys_XPS_CamDisp
// Target Device:  
// Tool versions:  
// Description: 
//
// Verilog Test Fixture created by ISE for module: system_top
//
// Dependencies:
// 
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
// 
////////////////////////////////////////////////////////////////////////////////

module system_top_tb;
    `include "simulation/ddr2_parameters.vh";

    // Inputs
    reg RS232_Uart_1_sin;
    reg RESET;
    reg [0:4] Push_Buttons_5Bits_TRI_I;
    reg GCLK;
    reg Ethernet_Lite_TX_CLK;
    reg Ethernet_Lite_RX_ER;
    reg Ethernet_Lite_RX_DV;
    reg Ethernet_Lite_RX_CLK;
    reg [3:0] Ethernet_Lite_RXD;
    reg Ethernet_Lite_CRS;
    reg Ethernet_Lite_COL;
    reg [7:0] DIP_Switches_8Bits_TRI_I;

    // Outputs
    wire mcbx_dram_we_n;
    wire mcbx_dram_udm;
    wire mcbx_dram_ras_n;
    wire mcbx_dram_odt;
    wire mcbx_dram_ldm;
    wire mcbx_dram_clk_n;
    wire mcbx_dram_clk;
    wire mcbx_dram_cke;
    wire mcbx_dram_cas_n;
    wire [2:0] mcbx_dram_ba;
    wire [12:0] mcbx_dram_addr;
    wire RS232_Uart_1_sout;
    wire [7:0] LEDs_8Bits_TRI_O;
    wire Ethernet_Lite_TX_EN;
    wire [3:0] Ethernet_Lite_TXD;
    wire Ethernet_Lite_PHY_RST_N;
    wire Ethernet_Lite_MDC;
    wire axi_master_0_ERROR;

    // Bidirs
    wire zio;
    wire rzq;
    wire Ethernet_Lite_MDIO;

    wire    [DQS_BITS-1:0] ddr2_dqs_fpga, ddr2_dqs_sdram;
    wire    [DQS_BITS-1:0] ddr2_dqs_n_fpga, ddr2_dqs_n_sdram;
    wire    [DQ_BITS-1:0] ddr2_dq_fpga, ddr2_dq_sdram;
    reg        [DQS_BITS-1:0] ddr2_dqs_fpgan, ddr2_dqs_sdramn;
    reg        [DQS_BITS-1:0] ddr2_dqs_n_fpgan, ddr2_dqs_n_sdramn;
    reg        [DQ_BITS-1:0] ddr2_dq_fpgan, ddr2_dq_sdramn;
    wire    [2:0] cmd;
    reg        sdram_clk;
    reg        sdram_clkb;
    reg        [12:0] sdram_address;
    reg        [2:0] sdram_ba;
    reg        sdram_cke;
    reg        sdram_rasb, sdram_casb, sdram_web;
    reg        [1:0] sdram_dmn;
    wire    [1:0] sdram_dm;
    reg        sdram_odt;
    wire        reset;
    reg        enable_o;
    
    // Instantiate the Unit Under Test (UUT)
    system_top uut (
        .zio(zio), 
        .rzq(rzq), 
        .mcbx_dram_we_n(mcbx_dram_we_n), 
        .mcbx_dram_udqs_n(ddr2_dqs_n_fpga[1]), 
        .mcbx_dram_udqs(ddr2_dqs_fpga[1]), 
        .mcbx_dram_udm(mcbx_dram_udm), 
        .mcbx_dram_ras_n(mcbx_dram_ras_n), 
        .mcbx_dram_odt(mcbx_dram_odt), 
        .mcbx_dram_ldm(mcbx_dram_ldm), 
        .mcbx_dram_dqs_n(ddr2_dqs_n_fpga[0]), 
        .mcbx_dram_dqs(ddr2_dqs_fpga[0]), 
        .mcbx_dram_dq(ddr2_dq_fpga), 
        .mcbx_dram_clk_n(mcbx_dram_clk_n), 
        .mcbx_dram_clk(mcbx_dram_clk), 
        .mcbx_dram_cke(mcbx_dram_cke), 
        .mcbx_dram_cas_n(mcbx_dram_cas_n), 
        .mcbx_dram_ba(mcbx_dram_ba), 
        .mcbx_dram_addr(mcbx_dram_addr), 
        .RS232_Uart_1_sout(RS232_Uart_1_sout), 
        .RS232_Uart_1_sin(RS232_Uart_1_sin), 
        .RESET(RESET), 
        .Push_Buttons_5Bits_TRI_I(Push_Buttons_5Bits_TRI_I), 
        .LEDs_8Bits_TRI_O(LEDs_8Bits_TRI_O), 
        .GCLK(GCLK), 
        .Ethernet_Lite_TX_EN(Ethernet_Lite_TX_EN), 
        .Ethernet_Lite_TX_CLK(Ethernet_Lite_TX_CLK), 
        .Ethernet_Lite_TXD(Ethernet_Lite_TXD), 
        .Ethernet_Lite_RX_ER(Ethernet_Lite_RX_ER), 
        .Ethernet_Lite_RX_DV(Ethernet_Lite_RX_DV), 
        .Ethernet_Lite_RX_CLK(Ethernet_Lite_RX_CLK), 
        .Ethernet_Lite_RXD(Ethernet_Lite_RXD), 
        .Ethernet_Lite_PHY_RST_N(Ethernet_Lite_PHY_RST_N), 
        .Ethernet_Lite_MDIO(Ethernet_Lite_MDIO), 
        .Ethernet_Lite_MDC(Ethernet_Lite_MDC), 
        .Ethernet_Lite_CRS(Ethernet_Lite_CRS), 
        .Ethernet_Lite_COL(Ethernet_Lite_COL), 
        .DIP_Switches_8Bits_TRI_I(DIP_Switches_8Bits_TRI_I), 
        .axi_master_0_ERROR(axi_master_0_ERROR)
    );

    parameter PERIOD = 1000; // 100MHz clock
    parameter real DUTY_CYCLE = 0.5;
    parameter OFFSET = 0;
    
    initial    // Clock process for clk
    begin
        GCLK = 1'b0;
        #OFFSET;
        forever begin
            GCLK = 1'b0;
            #(PERIOD-(PERIOD*DUTY_CYCLE)) GCLK = 1'b1;
            #(PERIOD*DUTY_CYCLE);
        end
    end

    parameter DELAY_TIME = 200; // 2nsec
    
    assign cmd = {mcbx_dram_ras_n, mcbx_dram_cas_n, mcbx_dram_we_n};
    
    assign reset = ~RESET;
    always @(posedge mcbx_dram_clk, posedge reset)
        if (reset)
            enable_o <= 1'b0;
        else
            if (cmd==3'b100)
                enable_o <= 1'b0;
            else if (cmd==3'b101)
                enable_o <= 1'b1;

    always @ *
        if (enable_o == 1'b1)
            ddr2_dqs_fpgan <= #DELAY_TIME ddr2_dqs_sdram;
        else
            ddr2_dqs_fpgan <= #DELAY_TIME {DQS_BITS{1'bz}};
    
    always @ *
        if (enable_o == 1'b1)
            ddr2_dqs_n_fpgan <= #DELAY_TIME ddr2_dqs_n_sdram;
        else
            ddr2_dqs_n_fpgan <= #DELAY_TIME {DQS_BITS{1'bz}};
    
    always @ *
        if (enable_o == 1'b1)
            ddr2_dq_fpgan <= #DELAY_TIME ddr2_dq_sdram;
        else
            ddr2_dq_fpgan <= #DELAY_TIME {DQ_BITS{1'bz}};

    always @ *
        if (enable_o == 1'b0)
            ddr2_dqs_sdramn <= #DELAY_TIME ddr2_dqs_fpga;
        else
            ddr2_dqs_sdramn <= #DELAY_TIME {DQS_BITS{1'bz}};
    
    always @ *
        if (enable_o == 1'b0)
            ddr2_dqs_n_sdramn <= #DELAY_TIME ddr2_dqs_n_fpga;
        else
            ddr2_dqs_n_sdramn <= #DELAY_TIME {DQS_BITS{1'bz}};
    
    always @ *
        if (enable_o == 1'b0)
            ddr2_dq_sdramn <= #DELAY_TIME ddr2_dq_fpga;
        else
            ddr2_dq_sdramn <= #DELAY_TIME {DQ_BITS{1'bz}};
    
    assign ddr2_dqs_fpga = ddr2_dqs_fpgan;
    assign ddr2_dqs_n_fpga = ddr2_dqs_n_fpgan;
    assign ddr2_dq_fpga = ddr2_dq_fpgan;
    assign ddr2_dqs_sdram = ddr2_dqs_sdramn;
    assign ddr2_dqs_n_sdram = ddr2_dqs_n_sdramn;
    assign ddr2_dq_sdram = ddr2_dq_sdramn;

    always @ * begin
        sdram_clk <= #DELAY_TIME mcbx_dram_clk;
        sdram_clkb <= #DELAY_TIME mcbx_dram_clk_n;
        sdram_address <= #DELAY_TIME mcbx_dram_addr;
        sdram_ba <= #DELAY_TIME mcbx_dram_ba;
        sdram_cke <= #DELAY_TIME mcbx_dram_cke;
        sdram_rasb <= #DELAY_TIME mcbx_dram_ras_n;
        sdram_casb <= #DELAY_TIME mcbx_dram_cas_n;
        sdram_web <= #DELAY_TIME mcbx_dram_we_n;
        sdram_dmn <= #DELAY_TIME {mcbx_dram_udm, mcbx_dram_ldm};
        sdram_odt <= #DELAY_TIME mcbx_dram_odt;
    end
    assign sdram_dm = sdram_dmn;
    
    ddr2 MT47H64M16_25E(
        .dq(ddr2_dq_sdram),
        .dqs(ddr2_dqs_sdram),
        .dqs_n(ddr2_dqs_n_sdram),
        .rdqs_n(),
        .addr(sdram_address),
        .ba(sdram_ba),
        .ck(sdram_clk),
        .ck_n(sdram_clkb),
        .cke(sdram_cke),
        .cs_n(1'b0),
        .ras_n(sdram_rasb),
        .cas_n(sdram_casb),
        .we_n(sdram_web),
        .dm_rdqs(sdram_dm),
        .odt(sdram_odt)
    );

    initial begin
        // Initialize Inputs
        RS232_Uart_1_sin = 0;
        RESET = 1'b0;
        Push_Buttons_5Bits_TRI_I = 0;
        Ethernet_Lite_TX_CLK = 0;
        Ethernet_Lite_RX_ER = 0;
        Ethernet_Lite_RX_DV = 0;
        Ethernet_Lite_RX_CLK = 0;
        Ethernet_Lite_RXD = 0;
        Ethernet_Lite_CRS = 0;
        Ethernet_Lite_COL = 0;
        DIP_Switches_8Bits_TRI_I = 0;

        // Wait 100 ns for global reset to finish
        #10000;
        
        // Add stimulus here
        #5000;
        RESET = 1'b1;
    end
      
endmodule


  1. 2012年01月14日 05:09 |
  2. AXI4 Master IPの作製
  3. | トラックバック:0
  4. | コメント:0

コメント

コメントの投稿


管理者にだけ表示を許可する

トラックバック URL
https://marsee101.blog.fc2.com/tb.php/2034-2d27bf0d
この記事にトラックバックする(FC2ブログユーザー)