有寫過 C 語言的人, 都知道, 主程式就是 main(); 而, 程式主體就是左右大括號 {} 包起來.

不論是什麼語法, 都一樣. Verilog也不例外.

只是, 在 Verilog or VHDL 沒有什麼 main 這種規定.

可以取任意名字, 這個是跟 C 有大大大不同的地方.

而~~~為什麼我在這裡要拿 C 跟 Verilog 來比呢?

其實, 這兩種語法用途完全不同, 拿來比是不適當的. 但是, 它們卻在語法上有相似的地方.

我自己不是一個正統的 ASIC 科班出身的工程師, 我一路走來, 從 assembly 到 C 到 VHDL 再到 Verilog.

說真的, VHDL 我學了老半天, 實在是~~我學得~~~有些笨手笨腳的, 最後終究轉戰 Verilog 了. 原因無它, 就是它們對我而言超像的.

扯遠了, 回歸主題~~~

而, 在 Verilog 的世界裡, 都是模組(module) 的模式在進行的.

每個模組(module) 也有像 C 一樣用{}來把程式主體包起來的

但是, 是不同的表示方式.

module  等同於 C 的 {

endmodule  等同於 C 的 }

所以, 要寫一個叫 adder 的 module

module adder ();
endmodule

這樣就好了~~~但是, 一個 module 沒有輸出入, 那不就白搭了嗎?

那我們就來設計一個 {Carry_Out , Sum = A_In + B_In + Carry_In} 的 module

module adder (A_In, B_In, Carry_In, Sum, Carry_Out);
   input A_In, B_In, Carry_In;
   output Sum, Carry_Out;
endmodule

還有另一程寫法

module adder (input A_In,
              input B_In,
              input Carry_In,
              output Sum,
              output Carry_Out
              );
endmodule

那....哪個方式比較好呢? 就大家習慣不同~~~其實個人認為都可以的啦~~~

再來, 怎麼實現呢?

其實, 在 ASIC or FPGA 的世界裡, 常常會有人在提 combination design 跟 synchronize design

就差在, 有沒有 clock 來做同步

我們就先來個 combination design 吧

module adder (A_In, B_In, Carry_In, Sum, Carry_Out);
input A_In, B_In, Carry_In;
output Sum, Carry_Out;
wire Sum, Carry_Out;
assign Sum = ({A_In,B_In,Carry_In} == 3'b000 ) ? 1'b0 :
             ({A_In,B_In,Carry_In} == 3'b001 ) ? 1'b1 :
             ({A_In,B_In,Carry_In} == 3'b010 ) ? 1'b1 :
             ({A_In,B_In,Carry_In} == 3'b011 ) ? 1'b0 :
             ({A_In,B_In,Carry_In} == 3'b100 ) ? 1'b1 :
             ({A_In,B_In,Carry_In} == 3'b101 ) ? 1'b0 :
             ({A_In,B_In,Carry_In} == 3'b110 ) ? 1'b0 : 1'b1;
assign Carry_Out = ({A_In,B_In,Carry_In} == 3'b000 ) ? 1'b0 :
                   ({A_In,B_In,Carry_In} == 3'b001 ) ? 1'b0 :
                   ({A_In,B_In,Carry_In} == 3'b010 ) ? 1'b0 :
                   ({A_In,B_In,Carry_In} == 3'b011 ) ? 1'b1 :
                   ({A_In,B_In,Carry_In} == 3'b100 ) ? 1'b0 :
                   ({A_In,B_In,Carry_In} == 3'b101 ) ? 1'b1 :
                   ({A_In,B_In,Carry_In} == 3'b110 ) ? 1'b1 : 1'b1;
endmodule

再來個 synchronize design

再先再加入一個輸入, 就是 clock 囉!!


module adder (clock, A_In, B_In, Carry_In, Sum, Carry_Out);
input clock, A_In, B_In, Carry_In;
output Sum, Carry_Out;
reg Sum, Carry_Out;
   always @(posedge clcok)
   begin
      case({A_In,B_In,Carry_In})
         3'b000:  begin    Sum <= 1'b0;   Carry_Out <= 1'b0;   end
         3'b001:  begin    Sum <= 1'b1;   Carry_Out <= 1'b0;   end
         3'b010:  begin    Sum <= 1'b1;   Carry_Out <= 1'b0;   end
         3'b011:  begin    Sum <= 1'b0;   Carry_Out <= 1'b1;   end
         3'b100:  begin    Sum <= 1'b1;   Carry_Out <= 1'b0;   end
         3'b101:  begin    Sum <= 1'b0;   Carry_Out <= 1'b1;   end
         3'b110:  begin    Sum <= 1'b0;   Carry_Out <= 1'b1;   end
         3'b111:  begin    Sum <= 1'b1;   Carry_Out <= 1'b1;   end
      endcase
endmodule

當然, 要實現一個加法器, 有很多方式, 這不是唯一或唯二的寫法.

寫程式, 就每個人 coding 習慣不同而有所不同, 大家自己揣摩~~~

 

arrow
arrow
    全站熱搜

    淹死的魚 發表在 痞客邦 留言(0) 人氣()