// alu.v
module alu(
input [3:0] i_a, i_b,
input [2:0] i_sel,
output [4:0] o_result
);
function [4:0] f_result; // function을 선언할 때 그 함수를 값으로 생각하는게 나아보인다.
input [3:0] a, b; // module에 선언된 input, output에 대응하는 값
input [2:0] sel; // 인스턴스를 한 모듈에서 한다고 생각하자.
case (sel)
3'b000 : f_result = a;
3'b001 : f_result = a + b;
3'b010 : f_result = a - b;
3'b011 : f_result = a / b;
3'b100 : f_result = a % b;
3'b101 : f_result = a << 1;
3'b110 : f_result = a >> 1;
3'b111 : if(a > b)
f_result = a;
else
f_result = b;
default: $display("default!"); // default는 display로 메시지 띄워주는게 좋아보인다.
endcase
endfunction
assign o_result = f_result(i_a, i_b, i_sel);
endmodule
// alu_tb.v
`timescale 1ns / 1ps
module alu_tb;
reg [3:0] i_a, i_b;
reg [2:0] i_sel;
wire [4:0] o_result;
integer i;
initial
begin
#10
$display("initialize! [%d]", $time);
i_a = 0;
i_b = 0;
i_sel = 0;
#10
$display("result! [%d]", $time);
#10 i_a = 3; i_b = 4;
for(i = 1; i <= 8; i = i + 1)
begin
#20 i_sel = i;
end
end
alu u_alu(
.i_a(i_a),
.i_b(i_b),
.i_sel(i_sel),
.o_result(o_result)
);
endmodule
case문을 사용할 때 always블록을 사용하지 않아도 합성이된다.
function내부에는 reg선언이 불가능해 always를 사용할수없나?
코드가 더 길어지면 function을 사용하는것이 효울적일것 같다.