module CRC16_cal(
input clk,
input rst,
input data_in,
input data_in_valid,
output [15:0] CRC_out,
output reg CRC_finish_flag
);
reg [511:0] data_reg;
reg [5:0] state;
reg [8:0] input_counter;
reg [8:0] shift_counter;
parameter state_input=6'b000001;
parameter state_calculate=6'b000010;
parameter gen_poly=17'b10000100000010001;
assign CRC_out=data_reg[16:1];
always @(posedge clk or posedge rst)
if(rst==1'b1)
begin
CRC_finish_flag<=1'b0;
data_reg<=512'd0;
state<=state_input;
input_counter<=9'd0;
shift_counter<=9'd0;
end
else
begin
case(state)
state_input:
begin
CRC_finish_flag<=1'b0;
if(data_in_valid==1'b1)
begin
data_reg[495]<=data_in;
data_reg[494:0]<=data_reg[495:1];
if(input_counter==9'd495)
begin
state<=state_calculate;
input_counter<=9'd0;
end
else
input_counter<=input_counter+9'd1;
end
end
state_calculate:
begin
if(data_reg[0]==1'b0)
begin
if(shift_counter==9'd495)
begin
CRC_finish_flag<=1'b1;
state<=state_input;
shift_counter<=9'd0;
end
else
begin
shift_counter<=shift_counter+9'd1;
data_reg[510:0]<=data_reg[511:1];
data_reg[511]<=1'b0;
end
end
else
begin
data_reg[16:0]<=data_reg[16:0]^gen_poly;
end
end
default state<=state_input;
endcase
end
endmodule
//以上代码的主体部分则为state_calculate中的一段代码,如下
if(data_reg[0]==1'b0)
begin
data_reg[510:0]<=data_reg[511:1];
data_reg[511]<=1'b0;
end
else
data_reg[16:0]<=data_reg[16:0]^gen_poly;
该段代码循环执行shift_counter次,shift_counter = length(data_CRC) - length(gen_poly) = = 512 - 17 = length(data_org) - 1 = 496 - 1 = 495.
补充:CRC的的“漏警率”为0.0047%