@@ -44,35 +44,65 @@ begin
4444%
4545% Runs a streaming LFSR over nd data codewords using the generator polynomial
4646% coeffs. The caller-owned lfsr is the shift register; on return, its first
47- % nc cells are the ECC codewords. Addition is XOR; multiplication is delegated
48- % to the caller-supplied rsprod procedure (typically a log/alog table lookup).
47+ % nc cells are the ECC codewords. Addition is XOR; multiplication is inlined
48+ % via the caller-supplied log/alog tables. coeffs is reversed once and log(fb)
49+ % is hoisted out of the inner loop, so each iteration is a single get,
50+ % log-add-mod, alog get, xor and put.
4951%
5052/rsecbinary {
5153
52- 7 dict begin
54+ 10 dict begin
5355
54- /rsprod exch def % Implements GF multiplication.
56+ /gfm1 exch def % GF size minus one (modulus for log-sum)
57+ /rsalog exch def % Anti-log table
58+ /rslog exch def % Log table
5559 /lfsr exch def % Workspace of length at least nc
5660 /nc exch def % Number of ECC codewords to produce
5761 /coeffs exch def % Generator polynomial coefficients
5862 /nd exch def % Number of data codewords
5963 /getdata exch def % Implements fetching nth codeword
6064
61- 0 1 nc 1 sub {lfsr exch 0 put} for
65+ 0 1 nc 1 sub {lfsr exch 0 put} for % Zero LFSR
66+
67+ %
68+ % Reverse coeffs to simplify the inner loop
69+ %
70+ /coeffsrev nc array def
71+ 0 1 nc 1 sub {
72+ /j exch def
73+ coeffsrev j coeffs nc 1 sub j sub get put
74+ } for
6275
6376 0 1 nd 1 sub { % m
64- getdata exec lfsr 0 get xor % fb = data[m] ^ S[0]
65- 0 1 nc 2 sub { % j
66- lfsr exch dup 1 add % ... lfsr j j+1
67- 2 index exch get % ... lfsr j S[j+1]
68- coeffs nc 3 index sub 1 sub get % ... coeffs[nc-1-j]
69- 4 index % ... fb
70- rsprod exec % p = coeffs[nc-1-j] * fb
71- xor put % S[j] = S[j+1] ^ p
72- } for
73- lfsr nc 1 sub coeffs 0 get 3 index % S[nc-1] = coeffs[0] * fb
74- rsprod exec put
75- pop % fb
77+ getdata exec lfsr 0 get xor % fb = data[m] ^ S[0]
78+ dup 0 ne { % fb != 0
79+ rslog exch get % log_fb (replaces fb on stack)
80+ 0 1 nc 2 sub { % j
81+ lfsr exch dup 1 add % ... log_fb lfsr j j+1
82+ 2 index exch get % ... log_fb lfsr j S[j+1]
83+ coeffsrev 2 index get % ... log_fb lfsr j S[j+1] coeffsrev[j]
84+ dup 0 ne {
85+ rslog exch get 4 index add gfm1 mod rsalog exch get
86+ } {
87+ pop 0
88+ } ifelse % ... log_fb lfsr j S[j+1] p
89+ xor put % S[j] = S[j+1] ^ p
90+ } for
91+ lfsr exch nc 1 sub exch % ... lfsr nc-1 log_fb
92+ coeffsrev nc 1 sub get % ... lfsr nc-1 log_fb coeffsrev[nc-1]
93+ dup 0 ne {
94+ rslog exch get exch add gfm1 mod rsalog exch get
95+ } {
96+ pop pop 0
97+ } ifelse
98+ put % S[nc-1] = coeffsrev[nc-1] * fb
99+ } { % fb == 0
100+ pop % drop fb
101+ 0 1 nc 2 sub {
102+ lfsr exch dup 1 add 2 index exch get put
103+ } for
104+ lfsr nc 1 sub 0 put
105+ } ifelse
76106 } for
77107
78108 end
0 commit comments