- 论坛徽章:
- 0
|
Peasant_Lee:
“看过了楼主的所讲的原理,拜访! 看了下代码,有一个地方弄不明白。 在 TestEcc.c 中的纠错函数中,有个if判断(下面列出),理论上它的作用应该就是判断s0s1s2 是否共有11个bit为1。但是我就不明白这个判别s0s1s2有11bit个1的条件,请高手指点,先谢谢了!
/* Check for a single bit error */
if( ((s0 ^ (s0 >> 1)) & 0x55) == 0x55 &&
((s1 ^ (s1 >> 1)) & 0x55) == 0x55 &&
((s2 ^ (s2 >> 1)) & 0x54) == 0x54)
{
.................
.................
.................
}
”
hi,Peasant_Lee,你对文中提到的ECC算法还是没太理解清楚,这段if代码就是针对仅有1bit出错的处理。这里我用c5,c4,c3,c2,c1,c0表示列校验结果。根据算法本身如果仅有1bit出错,可知c5,c3,c1分别与c4,c2,c0相反,行校验同理,22bits的中一定有11bits的1,从而列校验中一定有3bits的1,如果我选择c5,c3,c1开始判断,就是判断每2bits的第2bit位,这个道理可以再仔细看看楼主的分析。S2保存了列校验结果,格式为:
bit7 bit6 bit5 bit4 bit3 bit2 bit1 bit0
C5 C4 C3 C2 C1 C0 1 1
那么右移一位的S2再异或未右移的S2,就可以判断出c5,c3,c1是否分别与c4,c2,c0相反,也就是是否仅有1bit出错。S0,S1的算法与S2相同。
有了这个基础,以下纠错的代码就很明了了。
byteoffs = (s1 << 0) & 0x80;
byteoffs |= (s1 << 1) & 0x40;
byteoffs |= (s1 << 2) & 0x20;
byteoffs |= (s1 << 3) & 0x10;
byteoffs |= (s0 >> 4) & 0x08;
byteoffs |= (s0 >> 3) & 0x04;
byteoffs |= (s0 >> 2) & 0x02;
byteoffs |= (s0 >> 1) & 0x01;
bitnum = (s2 >> 5) & 0x04;
bitnum |= (s2 >> 4) & 0x02;
bitnum |= (s2 >> 3) & 0x01;
dat[byteoffs] ^= (1 << bitnum);
从校验原理也可以反推出,如果3bits或以上出错,则可能就无法检测出错误,因为c5,c4,c3,c2,c1,c0的值会发生矛盾,格局有点像二分法,呵呵。 |
|