• <li id="00i08"><input id="00i08"></input></li>
  • <sup id="00i08"><tbody id="00i08"></tbody></sup>
    <abbr id="00i08"></abbr>
  • 新聞中心

    EEPW首頁 > 嵌入式系統 > 設計應用 > 通過模塊之間的調用實現自頂向下的設計

    通過模塊之間的調用實現自頂向下的設計

    作者: 時間:2017-10-13 來源:網絡 收藏

    練習十. 通過之間的調用實現自頂向下的設計目的:學習的嵌套使用實現層次化、結構化設計。
    現代硬件系統的設計過程與軟件系統的開發相似,設計一個大規模的集成電路的往往由多層次的引用和組合構成。層次化、結構化的設計過程,能使復雜的系統容易控制和調試。 在Verilog HDL中,上層引用下層模塊與C語言中程序調用有些類似,被引用的子模塊在綜合時作為其父模塊的一部分被綜合,形成相應的電路結構。在進行模塊實例引用時,必須注意的是模塊之間對應的端口,即子模塊的端口與父模塊的內部信號必須明確無誤地一一對應,否則容易產生意想不到的后果。
    下面給出的例子是設計中遇到的一個實例,其功能是將并行數據轉化為串行數據送交外部電路編碼,并將解碼后得到的串行數據轉化為并行數據交由CPU處理。顯而易見,這實際上是兩個獨立的邏輯功能,分別設計為獨立的模塊,然后再合并為一個模塊顯得目的明確、層次清晰。
    // ---------------- p_to_s.v ---------------------------------
    module p_to_s(D_in,T0,data,SEND,ESC,ADD_100);
    output D_in,T0; // D_in是串行輸出,T0是移位時鐘并給
    // CPU中斷,以確定何時給出下個數據。
    input [7:0] data; //并行輸入的數據。
    input SEND,ESC,ADD_100; //SEND、ESC共同決定是否進行并到串
    //的數據轉化。ADD_100決定何時置數。
    wire D_in,T0;
    reg [7:0] DATA_Q,DATA_Q_buf;

    assign T0 = ! (SEND ESC); //形成移位時鐘。.
    assign D_in = DATA_Q[7]; //給出串行數據。

    always @(posedge T0 or negedge ADD_100) //ADD_100下沿置數,T0上沿移位。
    begin
    if(!ADD_100)
    DATA_Q = data;
    else
    begin
    DATA_Q_buf = DATA_Q1; //DATA_Q_buf作為中介,以令綜合器
    DATA_Q = DATA_Q_buf; //能辨明。
    end
    end
    endmodule
    在p_to_s.v中,由于移位運算雖然可綜合,但是不是簡單的RTL級描述,直接用DATA_Q=DATA_Q1的寫法在綜合時會令綜合器產生誤解。另外,在該設計中,由于時鐘T0的頻率較低,所以沒有象以往那樣采用低電平置數,而是采用ADD_100的下降沿置數。
    //--------------------- s_to_p.v ---------------------------
    module s_to_p(T1, data, D_out,DSC,TAKE,ADD_101);
    output T1; //給CPU中斷,以確定CPU何時取轉化
    //得到的并行數據。
    output [7:0] data;
    input D_out, DSC, TAKE, ADD_101; //D_out提供輸入串行數據。DSC、TAKE
    //共同決定何時取數。
    wire [7:0] data;
    wire T1,clk2;
    reg [7:0] data_latch, data_latch_buf;

    assign clk2 = DSC TAKE ; //提供移位時鐘。
    assign T1 = !clk2;

    assign data = (!ADD_101) ? data_latch : 8bz;
    always@(posedge clk2)
    begin
    data_latch_buf = data_latch 1; //data_latch_buf作緩沖
    data_latch = data_latch_buf; //,以令綜合器能辯明。
    data_latch[0] = D_out;
    end
    endmodule
    將上面的兩個模塊合并起來的sys.v的源代碼:
    //------------------- sys.v ---------------------------
    `include ./p_to_s.v
    `include ./s_to_p.v
    module sys(D_in,T0,T1, data, D_out,SEND,ESC,DSC,TAKE,ADD_100,ADD_101);
    input D_out,SEND,ESC,DSC,TAKE,ADD_100,ADD_101;
    inout [7:0] data;
    output D_in,T0,T1;

    p_to_s p_to_s(.D_in(D_in),.T0(T0),.data(data),
    .SEND(SEND),.ESC(ESC),.ADD_100(ADD_100));
    s_to_p s_to_p(.T1(T1),.data(data),.D_out(D_out),
    .DSC(DSC),.TAKE(TAKE),.ADD_101(ADD_101));

    endmodule
    測試模塊源代碼:
    //-------------Top test file for sys.v ------------------
    `TImescale 1ns/100ps
    `include ./sys.v
    module Top;
    reg D_out,SEND,ESC,DSC,TAKE,ADD_100,ADD_101;
    reg[7:0] data_buf;
    wire [7:0] data;
    wire clk2;
    assign data = (ADD_101) ? data_buf : 8bz;
    //data在sys中是inout型變量,ADD_101
    //控制data是作為輸入還是進行輸出。
    assign clk2 =DSC TAKE;
    iniTIal
    begin
    SEND = 0;
    ESC = 0;
    DSC = 1;
    TAKE = 1;
    ADD_100 = 1;
    ADD_101 = 1;
    end
    iniTIal
    begin
    data_buf = 8b10000001;
    #90 ADD_100 = 0;
    #100 ADD_100 = 1;
    end
    always
    begin
    #50;
    SEND = ~SEND;
    ESC = ~ESC;
    end
    iniTIal
    begin
    #1500 ;
    SEND = 0;
    ESC = 0;
    DSC = 1;
    TAKE = 1;
    ADD_100 = 1;
    ADD_101 = 1;
    D_out = 0;
    #1150 ADD_101 = 0;
    #100 ADD_101 =1;
    #100 $stop;
    end
    always
    begin
    #50 ;
    DSC = ~DSC;
    TAKE = ~TAKE;
    end
    always @(negedge clk2) D_out = ~D_out;
    sys sys(.D_in(D_in),.T0(T0),.T1(T1),.data(data),.D_out(D_out),
    .ADD_101(ADD_101), .SEND(SEND),.ESC(ESC),.DSC(DSC),
    .TAKE(TAKE),.ADD_100(ADD_100));
    endmodule
    仿真波形:[[wysiwyg_imageupload:255:]]
    練習:設計一個序列發生器。要求根據輸入的8位并行數據輸出串行數據,如果輸入數據在0—127之間則輸出一位0,如果輸入數據在128—255之間則輸出一位1,同步時鐘觸發;并且和范例8的序列檢測器搭接,形成一個封閉系統。編寫測試模塊,并給出仿真波形。

    本文引用地址:http://www.czjhyjcfj.com/article/201710/365681.htm


    關鍵詞: 模塊 狀態機

    評論


    相關推薦

    技術專區

    關閉
    主站蜘蛛池模板: 重庆市| 那坡县| 应用必备| 左贡县| 瓦房店市| 屯留县| 荔波县| 惠安县| 始兴县| 曲麻莱县| 凌云县| 泰宁县| 慈溪市| 丰顺县| 阳谷县| 铁力市| 库伦旗| 金昌市| 苍溪县| 枣庄市| 张家港市| 巴塘县| 博客| 南靖县| 唐河县| 马边| 锡林浩特市| 连山| 会东县| 普定县| 万州区| 衡南县| 胶南市| 寿阳县| 安康市| 铁岭县| 奇台县| 图们市| 隆德县| 宁武县| 临沭县|