xref: /aosp_15_r20/external/lzma/C/Ppmd7aDec.c (revision f6dc9357d832569d4d1f5d24eacdb3935a1ae8e6)
1 /* Ppmd7aDec.c -- PPMd7a (PPMdH) Decoder
2 2023-09-07 : Igor Pavlov : Public domain
3 This code is based on:
4   PPMd var.H (2001): Dmitry Shkarin : Public domain
5   Carryless rangecoder (1999): Dmitry Subbotin : Public domain */
6 
7 #include "Precomp.h"
8 
9 #include "Ppmd7.h"
10 
11 #define kTop ((UInt32)1 << 24)
12 #define kBot ((UInt32)1 << 15)
13 
14 #define READ_BYTE(p) IByteIn_Read((p)->Stream)
15 
Ppmd7a_RangeDec_Init(CPpmd7_RangeDec * p)16 BoolInt Ppmd7a_RangeDec_Init(CPpmd7_RangeDec *p)
17 {
18   unsigned i;
19   p->Code = 0;
20   p->Range = 0xFFFFFFFF;
21   p->Low = 0;
22 
23   for (i = 0; i < 4; i++)
24     p->Code = (p->Code << 8) | READ_BYTE(p);
25   return (p->Code < 0xFFFFFFFF);
26 }
27 
28 #define RC_NORM(p) \
29   while ((p->Low ^ (p->Low + p->Range)) < kTop \
30     || (p->Range < kBot && ((p->Range = (0 - p->Low) & (kBot - 1)), 1))) { \
31       p->Code = (p->Code << 8) | READ_BYTE(p); \
32       p->Range <<= 8; p->Low <<= 8; }
33 
34 // we must use only one type of Normalization from two: LOCAL or REMOTE
35 #define RC_NORM_LOCAL(p)    // RC_NORM(p)
36 #define RC_NORM_REMOTE(p)   RC_NORM(p)
37 
38 #define R (&p->rc.dec)
39 
40 Z7_FORCE_INLINE
41 // Z7_NO_INLINE
Ppmd7a_RD_Decode(CPpmd7 * p,UInt32 start,UInt32 size)42 static void Ppmd7a_RD_Decode(CPpmd7 *p, UInt32 start, UInt32 size)
43 {
44   start *= R->Range;
45   R->Low += start;
46   R->Code -= start;
47   R->Range *= size;
48   RC_NORM_LOCAL(R)
49 }
50 
51 #define RC_Decode(start, size)  Ppmd7a_RD_Decode(p, start, size);
52 #define RC_DecodeFinal(start, size)  RC_Decode(start, size)  RC_NORM_REMOTE(R)
53 #define RC_GetThreshold(total)  (R->Code / (R->Range /= (total)))
54 
55 
56 #define CTX(ref) ((CPpmd7_Context *)Ppmd7_GetContext(p, ref))
57 typedef CPpmd7_Context * CTX_PTR;
58 #define SUCCESSOR(p) Ppmd_GET_SUCCESSOR(p)
59 void Ppmd7_UpdateModel(CPpmd7 *p);
60 
61 #define MASK(sym)  ((Byte *)charMask)[sym]
62 
63 
Ppmd7a_DecodeSymbol(CPpmd7 * p)64 int Ppmd7a_DecodeSymbol(CPpmd7 *p)
65 {
66   size_t charMask[256 / sizeof(size_t)];
67 
68   if (p->MinContext->NumStats != 1)
69   {
70     CPpmd_State *s = Ppmd7_GetStats(p, p->MinContext);
71     unsigned i;
72     UInt32 count, hiCnt;
73     const UInt32 summFreq = p->MinContext->Union2.SummFreq;
74 
75     if (summFreq > R->Range)
76       return PPMD7_SYM_ERROR;
77 
78     count = RC_GetThreshold(summFreq);
79     hiCnt = count;
80 
81     if ((Int32)(count -= s->Freq) < 0)
82     {
83       Byte sym;
84       RC_DecodeFinal(0, s->Freq)
85       p->FoundState = s;
86       sym = s->Symbol;
87       Ppmd7_Update1_0(p);
88       return sym;
89     }
90 
91     p->PrevSuccess = 0;
92     i = (unsigned)p->MinContext->NumStats - 1;
93 
94     do
95     {
96       if ((Int32)(count -= (++s)->Freq) < 0)
97       {
98         Byte sym;
99         RC_DecodeFinal((hiCnt - count) - s->Freq, s->Freq)
100         p->FoundState = s;
101         sym = s->Symbol;
102         Ppmd7_Update1(p);
103         return sym;
104       }
105     }
106     while (--i);
107 
108     if (hiCnt >= summFreq)
109       return PPMD7_SYM_ERROR;
110 
111     hiCnt -= count;
112     RC_Decode(hiCnt, summFreq - hiCnt)
113 
114     p->HiBitsFlag = PPMD7_HiBitsFlag_3(p->FoundState->Symbol);
115     PPMD_SetAllBitsIn256Bytes(charMask)
116     // i = p->MinContext->NumStats - 1;
117     // do { MASK((--s)->Symbol) = 0; } while (--i);
118     {
119       CPpmd_State *s2 = Ppmd7_GetStats(p, p->MinContext);
120       MASK(s->Symbol) = 0;
121       do
122       {
123         const unsigned sym0 = s2[0].Symbol;
124         const unsigned sym1 = s2[1].Symbol;
125         s2 += 2;
126         MASK(sym0) = 0;
127         MASK(sym1) = 0;
128       }
129       while (s2 < s);
130     }
131   }
132   else
133   {
134     CPpmd_State *s = Ppmd7Context_OneState(p->MinContext);
135     UInt16 *prob = Ppmd7_GetBinSumm(p);
136     UInt32 pr = *prob;
137     UInt32 size0 = (R->Range >> 14) * pr;
138     pr = PPMD_UPDATE_PROB_1(pr);
139 
140     if (R->Code < size0)
141     {
142       Byte sym;
143       *prob = (UInt16)(pr + (1 << PPMD_INT_BITS));
144 
145       // RangeDec_DecodeBit0(size0);
146       R->Range = size0;
147       RC_NORM(R)
148 
149 
150 
151       // sym = (p->FoundState = Ppmd7Context_OneState(p->MinContext))->Symbol;
152       // Ppmd7_UpdateBin(p);
153       {
154         unsigned freq = s->Freq;
155         CTX_PTR c = CTX(SUCCESSOR(s));
156         sym = s->Symbol;
157         p->FoundState = s;
158         p->PrevSuccess = 1;
159         p->RunLength++;
160         s->Freq = (Byte)(freq + (freq < 128));
161         // NextContext(p);
162         if (p->OrderFall == 0 && (const Byte *)c > p->Text)
163           p->MaxContext = p->MinContext = c;
164         else
165           Ppmd7_UpdateModel(p);
166       }
167       return sym;
168     }
169 
170     *prob = (UInt16)pr;
171     p->InitEsc = p->ExpEscape[pr >> 10];
172 
173     // RangeDec_DecodeBit1(size0);
174     R->Low += size0;
175     R->Code -= size0;
176     R->Range = (R->Range & ~((UInt32)PPMD_BIN_SCALE - 1)) - size0;
177     RC_NORM_LOCAL(R)
178 
179     PPMD_SetAllBitsIn256Bytes(charMask)
180     MASK(Ppmd7Context_OneState(p->MinContext)->Symbol) = 0;
181     p->PrevSuccess = 0;
182   }
183 
184   for (;;)
185   {
186     CPpmd_State *s, *s2;
187     UInt32 freqSum, count, hiCnt;
188 
189     CPpmd_See *see;
190     CPpmd7_Context *mc;
191     unsigned numMasked;
192     RC_NORM_REMOTE(R)
193     mc = p->MinContext;
194     numMasked = mc->NumStats;
195 
196     do
197     {
198       p->OrderFall++;
199       if (!mc->Suffix)
200         return PPMD7_SYM_END;
201       mc = Ppmd7_GetContext(p, mc->Suffix);
202     }
203     while (mc->NumStats == numMasked);
204 
205     s = Ppmd7_GetStats(p, mc);
206 
207     {
208       unsigned num = mc->NumStats;
209       unsigned num2 = num / 2;
210 
211       num &= 1;
212       hiCnt = (s->Freq & (UInt32)(MASK(s->Symbol))) & (0 - (UInt32)num);
213       s += num;
214       p->MinContext = mc;
215 
216       do
217       {
218         const unsigned sym0 = s[0].Symbol;
219         const unsigned sym1 = s[1].Symbol;
220         s += 2;
221         hiCnt += (s[-2].Freq & (UInt32)(MASK(sym0)));
222         hiCnt += (s[-1].Freq & (UInt32)(MASK(sym1)));
223       }
224       while (--num2);
225     }
226 
227     see = Ppmd7_MakeEscFreq(p, numMasked, &freqSum);
228     freqSum += hiCnt;
229 
230     if (freqSum > R->Range)
231       return PPMD7_SYM_ERROR;
232 
233     count = RC_GetThreshold(freqSum);
234 
235     if (count < hiCnt)
236     {
237       Byte sym;
238 
239       s = Ppmd7_GetStats(p, p->MinContext);
240       hiCnt = count;
241       // count -= s->Freq & (UInt32)(MASK(s->Symbol));
242       // if ((Int32)count >= 0)
243       {
244         for (;;)
245         {
246           count -= s->Freq & (UInt32)(MASK((s)->Symbol)); s++; if ((Int32)count < 0) break;
247           // count -= s->Freq & (UInt32)(MASK((s)->Symbol)); s++; if ((Int32)count < 0) break;
248         }
249       }
250       s--;
251       RC_DecodeFinal((hiCnt - count) - s->Freq, s->Freq)
252 
253       // new (see->Summ) value can overflow over 16-bits in some rare cases
254       Ppmd_See_UPDATE(see)
255       p->FoundState = s;
256       sym = s->Symbol;
257       Ppmd7_Update2(p);
258       return sym;
259     }
260 
261     if (count >= freqSum)
262       return PPMD7_SYM_ERROR;
263 
264     RC_Decode(hiCnt, freqSum - hiCnt)
265 
266     // We increase (see->Summ) for sum of Freqs of all non_Masked symbols.
267     // new (see->Summ) value can overflow over 16-bits in some rare cases
268     see->Summ = (UInt16)(see->Summ + freqSum);
269 
270     s = Ppmd7_GetStats(p, p->MinContext);
271     s2 = s + p->MinContext->NumStats;
272     do
273     {
274       MASK(s->Symbol) = 0;
275       s++;
276     }
277     while (s != s2);
278   }
279 }
280 
281 #undef kTop
282 #undef kBot
283 #undef READ_BYTE
284 #undef RC_NORM_BASE
285 #undef RC_NORM_1
286 #undef RC_NORM
287 #undef RC_NORM_LOCAL
288 #undef RC_NORM_REMOTE
289 #undef R
290 #undef RC_Decode
291 #undef RC_DecodeFinal
292 #undef RC_GetThreshold
293 #undef CTX
294 #undef SUCCESSOR
295 #undef MASK
296