CRC算法
CRC(Cyclic Redundancy Check):循环冗余检验,在链路层被广泛使用的检错技术。
CRC原理介绍:
-
发送端
1、在发送端先将数据分组,每组k个数据。假定要传送的数据是M
2、在数据M后面添加供差错检测的n位冗余码,然后构成一帧发送出去,一共发送(k+n)位(虽然添加n位冗余码增大了数据传送的开销,但是可以进行差错检测,当传输可能出现差错时,付出这种代价是值得的) -
冗余码可以用下面的方法得出
1、用二进制模2运算进行2^n*M(相当于M左移n位)的运算。意思就是在M后面补n个0。现在M就变成了k+n位
2、用M除以收发双方事先商定的长度为n+1的除数P
3、得到的余数R,这个R就是FCS(帧检验序列)。将这个FCS序列加到M上然后发出去 -
接受端
1、在接受端把接受到的数据以帧为单位进行CRC校验
2、把收到的每一个帧都除以同样的除数P,然后检查余数R
3、如果余数R为0,如果在传输过程中没有差错
4、如果出现误码,那么余数R为零的概率是非常小的
例:M=101001,P=1101,n=3
在发送端:
1、M=(2^n*M);
则:M=101001000
2、用M除以P
3、得到余数R也就是FCS,将FCS加到M上,就得到了要发送的帧
M=101001000+FCS=101001001
在接收端:
接收到的每一帧都要进行差错检验,假设收到101001001,P=1101
最后余数R=0,则判定这个帧没有出错。
根据G(x)可以生成K位信息的校验码,而G(x)叫做这个CRC码的生成多项式。校验码的具体生成过程为:假设要发送的信息用多项式C(X)表示,将C(x)左移R位(可表示成C(x)*2R),这样C(x)的右边就会空出R位,这就是校验码的位置。用 C(x)*2R 除以生成多项式G(x)得到的余数就是校验码。
任意一个由二进制位串组成的代码都可以和一个系数仅为‘0’和‘1’取值的多项式一一对应。例如:代码1010111对应的多项式为x6+x4+x2+x+1
这里还有个问题,如果被除数比除数小,那么余数就是被除数本身,比如说只要传一个字节,那么他的CRC就是他自己,为避免这种情况发生,在做除法之前先将他移位,使他大于除数,那么移位多少位呢?这是所选的固定除数有关,左移位数比除数的位数少1,下面是常用标准中的除数: