← 返回博客纠错

汉明码纠错详解(含数学推导)

编码 Hamming(7,4)、计算综合征、纠正每一个单比特位置、扩展到 SECDED,并在不夸大能力边界的前提下验证译码器。

DennyDenny
阅读约需 8 分钟
Chalkboard feature illustration for “汉明码纠错详解(含数学推导)”

**要点速览:**Hamming(7,4) 把四个数据位映射到七个位置。三个奇偶检查使每个位置都对应唯一的非零三位列,因此单比特翻转所产生的综合征,恰好等于该位置的二进制编号。译码器随后可以将其反转。普通 Hamming(7,4) 无法区分双比特错误与某些单比特错误;在假定的错误数量限制内,添加一个全局奇偶位可以把它扩展为 SECDED。

一个奇偶校验位可以报告有奇数个位置发生变化,却无法指出具体是哪一个位置。汉明的构造使用多组相互重叠的奇偶检查。检查失败形成的模式——称为综合征——就像一个地址。

这个想法非常有力,因为编码器、检查器和纠错器都能用异或网络与译码逻辑构建。不过它也有严格边界:除非扩展码加入另一项检查,否则常见的纠正规则假定受保护块内最多只有一个错误。

位的位置安排

从 1 开始为码字位置编号,2 的幂次位置用于存放奇偶位:

位置1234567
角色P1P_1P2P_2D1D_1P4P_4D2D_2D3D_3D4D_4
二进制编号001010011100101110111

每一项奇偶检查对应二进制位置编号中的一个比特:

  • P1P_1 覆盖编号第 0 位为 1 的位置:1、3、5、7。
  • P2P_2 覆盖编号第 1 位为 1 的位置:2、3、6、7。
  • P4P_4 覆盖编号第 2 位为 1 的位置:4、5、6、7。

每个位置都有唯一的非零成员模式。例如位置 5 属于检查 1 和检查 4,因为 5=10125=101_2 。

这种从一开始的编号约定只是为了方便,并无神秘之处:奇偶校验矩阵的各列,正是 1 到 7 的二进制标签。

使用偶校验编码

选择每一个奇偶位,使其完整覆盖集合的异或结果为零:

P1=D1⊕D2⊕D4P_1=D_1\oplus D_2\oplus D_4 P2=D1⊕D3⊕D4P_2=D_1\oplus D_3\oplus D_4 P4=D2⊕D3⊕D4P_4=D_2\oplus D_3\oplus D_4

这些方程使该码成为系统码:原始数据原样出现在位置 3、5、6 与 7,其余位置用于奇偶校验。

只要相应改变检查的期望值,也可以一致地使用奇校验。偶校验让线性代数形式尤其直接,因为每个有效码字的综合征都是零。

编码示例:数据 1011

设定:

D1=1,D2=0,D3=1,D4=1D_1=1,\quad D_2=0,\quad D_3=1,\quad D_4=1

于是:

P1=1⊕0⊕1=0P_1=1\oplus0\oplus1=0 P2=1⊕1⊕1=1P_2=1\oplus1\oplus1=1 P4=0⊕1⊕1=0P_4=0\oplus1\oplus1=0

把这些值放入七个位置:

位置1234567
角色P1P_1P2P_2D1D_1P4P_4D2D_2D3D_3D4D_4
比特0110011

从位置 1 读到位置 7,码字为:

0110011

有些资料会以相反的视觉方向打印码字。只要明确位置约定并始终如一地使用,算术结果仍然正确。

计算综合征

把接收到的位置记为 R1R_1 到 R7R_7,重新计算完整奇偶检查:

S1=R1⊕R3⊕R5⊕R7S_1=R_1\oplus R_3\oplus R_5\oplus R_7 S2=R2⊕R3⊕R6⊕R7S_2=R_2\oplus R_3\oplus R_6\oplus R_7 S4=R4⊕R5⊕R6⊕R7S_4=R_4\oplus R_5\oplus R_6\oplus R_7

把综合征解释为:

S=(S4S2S1)2S=(S_4S_2S_1)_2

有效码字未经改变时,S=000S=000 。如果恰有位置 ii 翻转,所有覆盖 ii 的检查结果都会翻转,最终综合征就是分配给位置 ii 的二进制列。

纠正位置 5 的翻转

在编码示例中翻转位置 5:

sent:     0 1 1 0 0 1 1
received: 0 1 1 0 1 1 1
position: 1 2 3 4 5 6 7

此时:

S1=0⊕1⊕1⊕1=1S_1=0\oplus1\oplus1\oplus1=1 S2=1⊕1⊕1⊕1=0S_2=1\oplus1\oplus1\oplus1=0 S4=0⊕1⊕1⊕1=1S_4=0\oplus1\oplus1\oplus1=1

因此:

S4S2S1=1012=5S_4S_2S_1=101_2=5

在单错误假设下,把接收到的位置 5 取反。纠正后的字回到 0110011,从位置 3、5、6 与 7 提取的数据为 1011 。

奇偶位发生翻转时处理方式完全相同。如果位置 2 改变,综合征就是 010,纠错器会把位置 2 取反。

矩阵视角

使用码字向量

r=[R1 R2 R3 R4 R5 R6 R7]T\mathbf r=[R_1\ R_2\ R_3\ R_4\ R_5\ R_6\ R_7]^T

一种奇偶校验矩阵为:

H=[101010101100110001111]H= \begin{bmatrix} 1&0&1&0&1&0&1\\ 0&1&1&0&0&1&1\\ 0&0&0&1&1&1&1 \end{bmatrix}

综合征为:

s=Hr(mod2)\mathbf s=H\mathbf r\pmod 2

H 的第 ii 列是 ii 的二进制表示,顺序为 (S1,S2,S4)T(S_1,S_2,S_4)^T 。因此,一个只在位置 ii 上为 1 的单比特错误向量,恰好会返回第 ii 列。

这种表达方式比记忆相互重叠的圆圈更容易扩展,也明确展示了线性性质:两个有效码字进行异或,仍会得到另一个有效码字。

为什么普通汉明码无法安全纠正两个错误

Hamming(7,4) 的最小汉明距离为:

dmin⁡=3d_{\min}=3

最小距离为 dmin⁡d_{\min} 的编码能够:

  • 在只判断有效或无效时,检测最多dmin⁡−1d_{\min}-1 个任意错误;或者
  • 采用最近码字判决时,纠正最多⌊(dmin⁡−1)/2⌋\left\lfloor(d_{\min}-1)/2\right\rfloor 个错误。

因此,Hamming(7,4) 能够纠正一个错误。如果不尝试纠正,它也能把双比特损坏检测为“不是有效码字”。但非零的三位综合征无法说明,它究竟来自一个错误,还是某一对特定错误。

标准单错误译码器如果遇到双比特错误,两个错误位置列的异或会等于第三个非零列。译码器随后会把第三个位置取反,从而产生一个与发送码字相差三位的结果。这是误纠正,而不是双错误纠正。

务必声明译码器所假定的错误模型。“综合征非零,所以翻转对应位置”这一规则,只有在系统已经确定最多一个受保护位置出错时才成立。

扩展汉明码与 SECDED

在七位汉明码字上增加一个全局奇偶位 P0P_0 。得到的八位扩展码具有 dmin⁡=4d_{\min}=4,并在假定一个码字中错误不超过两个时,支持单错误纠正、双错误检测(SECDED)。

计算:

  • 位置 1–7 的原始三位综合征 S;
  • 所有八个接收位置上的全局奇偶检查 P。

对于全局偶校验:

综合征 S全局检查 P0–2 个错误假设下的解释操作
0000无错误接受
非零1位置 1–7 中有一个错误纠正位置 S
0001全局奇偶位错误纠正或报告奇偶位错误
非零0两个错误报告不可纠正;不要按单错误纠正

这里的限定十分重要。三个或更多错误可能伪装成表中的其他行。SECDED 并不是不受限制的错误检测器。

真实存储器与通信系统可能使用缩短汉明码、交织、面向符号的编码、BCH 或 Reed–Solomon 码、低密度奇偶校验码、乘积码或专有方案。不能仅凭可见的数据位与检查位宽度,推断系统的 ECC 能力。

汉明码的一般尺寸计算

对于 mm 个数据位和 rr 个汉明奇偶位,综合征模式数量必须足以覆盖每个码字位置以及无错误情况:

2r≥m+r+12^r\ge m+r+1

全长二进制汉明码族采用:

n=2r−1n=2^r-1 k=n−r=2r−r−1k=n-r=2^r-r-1
奇偶位数 r码长 n数据位数 k全长码
374Hamming(7,4)
41511Hamming(15,11)
53126Hamming(31,26)
66357Hamming(63,57)

缩短变体会省略选定的数据位置,同时保留检查结构。扩展变体则添加全局奇偶位,使距离从 3 增加到 4。

讨论开销时必须说明分母。Hamming(7,4) 每 4 个数据位增加 3 个检查位——相对于有效载荷的开销为 75%,或者说检查位占发送字的 3/7。Hamming(63,57) 增加 6/57,相对于有效载荷约为 10.5%;检查位占整个码字的 6/63,约为 9.5%。

硬件架构

一种直接的系统实现包含四个阶段:

data ─▶ parity generator ─▶ codeword
                              │
received word ─▶ check matrix ─▶ syndrome
                                      │
                       syndrome decoder ─▶ one-hot flip mask
received word ───────────────────────────XOR ─▶ corrected word ─▶ extract data

对于 Hamming(7,4):

  • 编码器计算三个奇偶方程;
  • 检查器计算三个综合征方程;
  • 3 到 8 译码器可以生成独热位置掩码,其中输出 0 表示无需纠正;
  • 七只异或门应用该掩码;
  • 通过布线提取位置 3、5、6 与 7。

确切的门数量与时序取决于异或树因式分解、共享项、单元库或 FPGA 映射。宽译码器可能会为综合征计算和纠正加入流水线。如果标志或状态寄存器报告“已纠正”与“不可纠正”,就要让这些信号与对应数据的流水级对齐。

验证计划

对于七位码:

  1. 对所有 16 种可能的数据输入进行编码。
  2. 确认每个编码字的综合征都为零。
  3. 对每个码字分别翻转七个位置中的每一个。
  4. 确认综合征等于发生翻转的位置。
  5. 应用纠正并确认全部 16×7 个用例都恢复原始数据。
  6. 注入有代表性的双比特错误,展示普通单错误译码器为何会误纠正。

对于扩展八位版本:

  1. 重复所有单位置测试,包括全局奇偶位。
  2. 对每一个数据字测试全部 (82)=28\binom82=28 种双位置模式。
  3. 确认每一对都被报告为不可纠正,而且没有任何一对被当作单错误纠正。
  4. 加入断言,确保只有在 S != 0 且全局奇偶不匹配时才启用纠正。

功能仿真能够证明已实现的真值表对已测试或穷举的位模式成立,但不能给出物理软错误率、证明故障相互独立,也无法取代系统级可靠性分析。

常见设计错误

  • 从零开始为位置编号,却仍把综合征解释为从一开始的地址。
  • 反向打印码字,却没有记录这一约定。
  • 使用偶校验编码,却用奇校验进行检查。
  • 未限定错误数量,就纠正每一个非零综合征。
  • 把 SECDED 当成能够检测所有权重大于等于三的错误。
  • 忘记检查位和全局奇偶位本身也可能失效。
  • 比较采用不同分母的“开销百分比”。
  • 假定所有标有 ECC 的产品都实现相同编码。

Hamming(7,4) 的价值在于整个机制清晰可见:唯一的奇偶校验列把一位故障转换成地址。理解这一点后,普通奇偶校验就像只有一行的检查矩阵;更强的分组码,则是同一核心思想的更大版本——用结构化冗余匹配明确的故障模型。

参考资料

将想法变成真正可运行的电路。