sobel算子的verilog实现,采用了流水线操作
module sobel_computer (
clock ,
reset,
OrigDataEn,
//SobelAluEn,
OrigData,
SobelData
);
input clock ,reset;
input OrigDataEn ;
//input SobelAluEn ;
input [:] OrigData ;
output reg [:] SobelData ; reg [:] prev_row, curr_row, next_row ;
reg [:] data_state ;
reg [:]abs_D ;
//*****************OrigDataEn 维持三个周期,将数据保存到三个reg 中****************
always @ (posedge clock or negedge reset )
if(!reset)
begin
data_state <= 'b00 ;
prev_row <= 'd0 ;
curr_row <= 'd0 ;
next_row <= 'd0 ;
end
else if(OrigDataEn)
begin
case (data_state)
'b00 :
begin
prev_row <= OrigData ;
data_state <= 'b01 ;
end
'b01 :
begin
curr_row <= OrigData ;
data_state <= 'b10 ;
end
'b10 :
begin
next_row <= OrigData ;
//data_state <= 2'b01 ;
end
endcase
end
else
begin
data_state <= 'b00 ;
prev_row <= prev_row << ;
curr_row <= curr_row << ;
next_row <= next_row << ;
end
//----------------------------------------------------------------
//function : 函数名= 内部reg,并返回。不包含 # @ wait,至少一个输入参数
function [:] abs (input signed[:] data);
abs = data[]? (~data[:]+): data[:];
endfunction reg signed [:] Dx,Dy ; //8'b1111_1111 * 6 = 11'd1530 所以采用11bit的Dx 和Dy
reg [:]Orig [-:][-:]; /*
分段方式:[63:56] [55:48] [47:40] [39:32] [31:24] [23:16] [15:8] [7:0]
sobel Dx -1 0 +1
-2 0 +2
-1 0 +1 Dy +1 +2 +1
0 0 0
-1 -2 -1
*/
//**************************************************************
always @ (posedge clock or negedge reset)
if(!reset)
begin
abs_D <= 'd0 ;
Dx <= 'd0 ;
Dy <= 'd0 ;
SobelData <= 'd0 ;
end
else if(!OrigDataEn) //if(SobelAluEn )
begin
Dx <= $signed (~{'b000,Orig[-1][-1]}+1) // * -1
+ $signed(~({'b00,Orig[0][-1]}<<1)+1) // * -2
+ $signed(~{'b000,Orig[1][-1]}+1) // * -1 + $signed({'b000,Orig[-1][1]}) // * 1
+ $signed({'b00,Orig[0][1]}<<1) // * 2
+ $signed ({'b000,Orig[1][1]}) ; // * 1 Dy <= $signed ({'b000,Orig[-1][-1]}) // * 1
+ $signed ({'b00,Orig[-1][0]}<<1) // * 2
+ $signed({'b000,Orig[-1][1]}) // * 1 + $signed(~{'b000,Orig[1][-1]}+1) // * -1
+ $signed(~({'b00,Orig[1][0]}<<1)+1) // * -2
+ $signed(~{'b000,Orig[1][1]}+1) ; // * -1 abs_D <= (abs(Dx) + abs(Dy))>> ;
SobelData <= {SobelData[:],abs_D}; Orig[-][-] <= Orig[-][]; Orig[-][] <= Orig[-][]; Orig[-][] <= prev_row[:];
Orig[][-] <= Orig[][]; Orig[][] <= Orig[][]; Orig[][] <= curr_row[:];
Orig[][-] <= Orig[][]; Orig[][] <= Orig[][]; Orig[][] <= next_row[:];
end endmodule