1.CRC校验原理
对于一个给定的(n,k)码,可以证明存在一个最高次幂为m=n-k的多项式G(x)。根据G(x)可以生成K位信息的校验码,而G(x)叫做这个CRC码的生成多项式。
校验码的具体生成过程为:假设要发送的信息用多项式C(X)表示,将C(x)左移m位(可表示成C(x)*2^m),这样C(x)的右边就会空出m位,这就是校验码的位置。用 C(x)*2^m 除以生成多项式G(x)得到的余数就是校验码。(进行的是模二除)
下面是一个根据一个给定的生成多项式求CRC码的例子
假设使用的生成多项式是G(X)=X3+X+1。4位的原始信息为1010,求编码后的码字。
1.将生成多项式G(X)=X3+X+1转换成对应的二进制除数1011。
2.原始信息拓展为n位 10100000
3.用拓展后的和生成多项式进行模二除,余数就是校验位,其中高位不够补0。
最后得到的结果是10100110
2.代码实现
有了编码的原理就能够实现RTL代码了。
下面是CRC5的verilog代码
CRC5:
module CRC5(
input clk,
input rst,
input [4:0] data,
input valid,
output reg [9:0] dataout,
output reg ready
);
reg [9:0] temp;
reg [2:0] cnt;
wire [5:0] xeq;
assign xeq=6'b100101; //x5+x2+1
reg [4:0] datatemp;
//计算周期变化
always @(posedge clk) begin
if(rst) begin
cnt<=3'd0;
end
else if ((valid)&&(cnt==3'd0)) begin
cnt<=3'd1;
end
else if (cnt==3'd6) begin
cnt<=3'd0;
end
else if(cnt!=3'd0)begin
cnt<=cnt+1'd1;
end
else begin
cnt<=3'd0;
end
end
//
always @(posedge clk) begin
if (rst) begin
temp<=10'b0;
datatemp<=5'b0;
ready<=1'b0;
dataout<=10'b0;
end
else if ((valid)&&(cnt==3'd0)) begin
temp<={data,5'b0};
datatemp<=data;
ready<=1'b0;
dataout<=10'b0;
end
else if ((cnt!=3'd6)&&(cnt!=3'd0)) begin
if (temp[9]==1'b1) begin
temp<=((temp^{xeq,4'b0})<<1);
end
else begin
temp<=(temp<<1);
end
end
else if (cnt==3'd6)begin
dataout<={datatemp,temp[9:5]};
ready<=1'b1;
end
else begin
temp<=10'b0;
datatemp<=5'b0;
ready<=1'b0;
dataout<=10'b0;
end
end
endmodule
![]()
结果正确。