# 數位邏輯設計實習(作業2) ###### > <font size=5 color="#0080FF" face="微軟正黑體"><b>1410932050 資工2-1 魏庠緯 </b></font> # :memo:實驗目的 ><font size=5 face="微軟正黑體"><b>探討blocking與nonblocking的不同之處。</b></font> # :memo:實驗內容 :::info :pushpin: <font size=5 face="微軟正黑體"><b>電路圖</b></font> ::: >![](https://imgur.com/pRcH787.png) ><font size=5 face="微軟正黑體">使用此電路圖模擬波型,從而比較blocking與nonblocking的不同之處。</font> # :memo:實驗步驟 ><font size=5 face="微軟正黑體"><b>依照題目內容打出以下程式碼並進行比較</b></font> >>blocking.v ```verilog= module blocking( clk, rst_n,a_i,b_i,a_o,b_o); input clk; //宣告clk input rst_n; //宣告rst_n; input a_i,b_i; //宣告兩輸入a_i,b_i output a_o,b_o; //宣告兩輸出a_o,b_o reg a,b; //登入a,b assign a_o = a; //指派a_o = a assign b_o = b; //指派b_o = b always @(posedge clk or negedge rst_n) begin //當 clk 在正邊緣或 rst_n 再負邊緣時執行 if(~rst_n) begin //false rst_n執行 a = a_i; b = b_i; end else begin //true rst_n執行 a = b; b = a; end end endmodule ``` >>blocking_tb.v ```verilog= `timescale 1ns/1ps module blocking_tb; reg clk; reg rst_n; reg a_i, b_i; wire a_o, b_o; parameter PERIOD = 20; parameter real DUTY_CYCLE = 0.5; parameter OFFSET = 0; // clock process initial begin #OFFSET; forever begin clk = 1'b0; #(PERIOD-(PERIOD*DUTY_CYCLE)) clk = 1'b1; #(PERIOD*DUTY_CYCLE); end end initial begin rst_n = 1'b0; a_i = 1'b1; b_i = 1'b0; #5 rst_n = 1'b1; #100 $finish; end initial begin $dumpfile("blocking.vcd"); $dumpvars(0, blocking_tb); end blocking blocking_tb ( .clk(clk), .rst_n(rst_n), .a_i(a_i), .b_i(b_i), .a_o(a_o), .b_o(b_o) ); endmodule ``` >>nonblocking.v ```verilog= module blocking( clk, rst_n,a_i,b_i,a_o,b_o); input clk; //宣告clk input rst_n; //宣告rst_n; input a_i,b_i; //宣告兩輸入a_i,b_i output a_o,b_o; //宣告兩輸出a_o,b_o reg a,b; //登入a,b assign a_o = a; //指派a_o = a assign b_o = b; //指派b_o = b always @(posedge clk or negedge rst_n) begin //當 clk 在正邊緣或 rst_n 再負邊緣時執行 if(~rst_n) begin //false rst_n執行 a <= a_i; b <= b_i; end else begin //true rst_n執行 a <= b; b <= a; end end endmodule ``` >>nonblocking_tb.v ```verilog= `timescale 1ns/1ps module blocking_tb; reg clk; reg rst_n; reg a_i, b_i; wire a_o, b_o; parameter PERIOD = 20; parameter real DUTY_CYCLE = 0.5; parameter OFFSET = 0; // clock process initial begin #OFFSET; forever begin clk = 1'b0; #(PERIOD-(PERIOD*DUTY_CYCLE)) clk = 1'b1; #(PERIOD*DUTY_CYCLE); end end initial begin rst_n = 1'b0; a_i = 1'b1; b_i = 1'b0; #5 rst_n = 1'b1; #100 $finish; end initial begin $dumpfile("blocking.vcd"); $dumpvars(0, blocking_tb); end blocking blocking_tb ( .clk(clk), .rst_n(rst_n), .a_i(a_i), .b_i(b_i), .a_o(a_o), .b_o(b_o) ); endmodule ``` # :memo: 實驗結果 ><font size=5 face="微軟正黑體"><b>make後出來的波型</b></font> blocking.v ![](https://imgur.com/FVQePdz.png) nonblocking.v ![](https://imgur.com/CUQXjb6.png) <font size=5 face="微軟正黑體">由上圖可得知blocking與nonblocking的不同之處在於,blocking是逐行執行的所以後面的值會因為前面的值變化受到影響,nonblocking的執行是2個步驟所以後面的值並不會因為前面的值變化而受到影響。</font> # :memo: 實驗討論 ><font face="微軟正黑體" size=5><b>blocking方面十分得好理解就是一行一行來執行,但nonblocking就不一樣了,它有分兩個動作分別是</b></font> :::info <font size=5 face="微軟正黑體"><b>1.在clk rising edge的一開始執行RHS。 2.在clk rising edge快結束時執行LHS。 <font size=4 color="#E61111" face="微軟正黑體"><b>補充: RHS:在 = 或 <= 右邊的運算式或變數 LHS:在 = 或 <= 左邊的運算式或變數</b></font> </b></font> ::: ><font face="微軟正黑體" size=5><b>所以在 a<=b,b<=a時,一開始先執行RHS,變成a=1,b=0,然後再執行LHS,因此a=0,b=1,所以nonblocking不會跟blocking一樣因為前一值a已經更新了,因而改變了後面b的值。</b></font> # :memo: 實驗心得 ><font face="微軟正黑體" size=5><b>這次的作業內容讓我去找了很多有關於blocking與nonblocking的資料發現了很多新東西也了解到一些新知識,如果以後再遇到就會更快速的運用與解答了,所以我認為這是一次相當不錯的體驗。</b></font>