source: trunk/poppler/mypoppler/poppler/JArithmeticDecoder.cc @ 515

Last change on this file since 515 was 515, checked in by Silvan Scherrer, 9 years ago

updated poppler to 0.20.3

File size: 7.5 KB
Line 
1//========================================================================
2//
3// JArithmeticDecoder.cc
4//
5// Copyright 2002-2004 Glyph & Cog, LLC
6//
7//========================================================================
8
9#include <config.h>
10
11#ifdef USE_GCC_PRAGMAS
12#pragma implementation
13#endif
14
15#include "Object.h"
16#include "Stream.h"
17#include "JArithmeticDecoder.h"
18
19//------------------------------------------------------------------------
20// JArithmeticDecoderStates
21//------------------------------------------------------------------------
22
23JArithmeticDecoderStats::JArithmeticDecoderStats(int contextSizeA) {
24  contextSize = contextSizeA;
25  cxTab = (Guchar *)gmallocn(contextSize, sizeof(Guchar));
26  reset();
27}
28
29JArithmeticDecoderStats::~JArithmeticDecoderStats() {
30  gfree(cxTab);
31}
32
33JArithmeticDecoderStats *JArithmeticDecoderStats::copy() {
34  JArithmeticDecoderStats *stats;
35
36  stats = new JArithmeticDecoderStats(contextSize);
37  memcpy(stats->cxTab, cxTab, contextSize);
38  return stats;
39}
40
41void JArithmeticDecoderStats::reset() {
42  memset(cxTab, 0, contextSize);
43}
44
45void JArithmeticDecoderStats::copyFrom(JArithmeticDecoderStats *stats) {
46  memcpy(cxTab, stats->cxTab, contextSize);
47}
48
49void JArithmeticDecoderStats::setEntry(Guint cx, int i, int mps) {
50  cxTab[cx] = (i << 1) + mps;
51}
52
53//------------------------------------------------------------------------
54// JArithmeticDecoder
55//------------------------------------------------------------------------
56
57Guint JArithmeticDecoder::qeTab[47] = {
58  0x56010000, 0x34010000, 0x18010000, 0x0AC10000,
59  0x05210000, 0x02210000, 0x56010000, 0x54010000,
60  0x48010000, 0x38010000, 0x30010000, 0x24010000,
61  0x1C010000, 0x16010000, 0x56010000, 0x54010000,
62  0x51010000, 0x48010000, 0x38010000, 0x34010000,
63  0x30010000, 0x28010000, 0x24010000, 0x22010000,
64  0x1C010000, 0x18010000, 0x16010000, 0x14010000,
65  0x12010000, 0x11010000, 0x0AC10000, 0x09C10000,
66  0x08A10000, 0x05210000, 0x04410000, 0x02A10000,
67  0x02210000, 0x01410000, 0x01110000, 0x00850000,
68  0x00490000, 0x00250000, 0x00150000, 0x00090000,
69  0x00050000, 0x00010000, 0x56010000
70};
71
72int JArithmeticDecoder::nmpsTab[47] = {
73   1,  2,  3,  4,  5, 38,  7,  8,  9, 10, 11, 12, 13, 29, 15, 16,
74  17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32,
75  33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 45, 46
76};
77
78int JArithmeticDecoder::nlpsTab[47] = {
79   1,  6,  9, 12, 29, 33,  6, 14, 14, 14, 17, 18, 20, 21, 14, 14,
80  15, 16, 17, 18, 19, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29,
81  30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 46
82};
83
84int JArithmeticDecoder::switchTab[47] = {
85  1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0,
86  0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
87  0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
88};
89
90JArithmeticDecoder::JArithmeticDecoder() {
91  str = NULL;
92  dataLen = 0;
93  limitStream = gFalse;
94  nBytesRead = 0;
95}
96
97inline Guint JArithmeticDecoder::readByte() {
98  if (limitStream) {
99    --dataLen;
100    if (dataLen < 0) {
101      return 0xff;
102    }
103  }
104  ++nBytesRead;
105  return (Guint)str->getChar() & 0xff;
106}
107
108JArithmeticDecoder::~JArithmeticDecoder() {
109  cleanup();
110}
111
112void JArithmeticDecoder::start() {
113  buf0 = readByte();
114  buf1 = readByte();
115
116  // INITDEC
117  c = (buf0 ^ 0xff) << 16;
118  byteIn();
119  c <<= 7;
120  ct -= 7;
121  a = 0x80000000;
122}
123
124void JArithmeticDecoder::restart(int dataLenA) {
125  Guint cAdd;
126  GBool prevFF;
127  int k, nBits;
128
129  if (dataLen >= 0) {
130    dataLen = dataLenA;
131  } else if (dataLen == -1) {
132    dataLen = dataLenA;
133    buf1 = readByte();
134  } else {
135    k = (-dataLen - 1) * 8 - ct;
136    dataLen = dataLenA;
137    cAdd = 0;
138    prevFF = gFalse;
139    while (k > 0) {
140      buf0 = readByte();
141      if (prevFF) {
142        cAdd += 0xfe00 - (buf0 << 9);
143        nBits = 7;
144      } else {
145        cAdd += 0xff00 - (buf0 << 8);
146        nBits = 8;
147      }
148      prevFF = buf0 == 0xff;
149      if (k > nBits) {
150        cAdd <<= nBits;
151        k -= nBits;
152      } else {
153        cAdd <<= k;
154        ct = nBits - k;
155        k = 0;
156      }
157    }
158    c += cAdd;
159    buf1 = readByte();
160  }
161}
162
163void JArithmeticDecoder::cleanup() {
164  if (limitStream) {
165    while (dataLen > 0) {
166      buf0 = buf1;
167      buf1 = readByte();
168    }
169  }
170}
171
172int JArithmeticDecoder::decodeBit(Guint context,
173                                  JArithmeticDecoderStats *stats) {
174  int bit;
175  Guint qe;
176  int iCX, mpsCX;
177
178  iCX = stats->cxTab[context] >> 1;
179  mpsCX = stats->cxTab[context] & 1;
180  qe = qeTab[iCX];
181  a -= qe;
182  if (c < a) {
183    if (a & 0x80000000) {
184      bit = mpsCX;
185    } else {
186      // MPS_EXCHANGE
187      if (a < qe) {
188        bit = 1 - mpsCX;
189        if (switchTab[iCX]) {
190          stats->cxTab[context] = (nlpsTab[iCX] << 1) | (1 - mpsCX);
191        } else {
192          stats->cxTab[context] = (nlpsTab[iCX] << 1) | mpsCX;
193        }
194      } else {
195        bit = mpsCX;
196        stats->cxTab[context] = (nmpsTab[iCX] << 1) | mpsCX;
197      }
198      // RENORMD
199      do {
200        if (ct == 0) {
201          byteIn();
202        }
203        a <<= 1;
204        c <<= 1;
205        --ct;
206      } while (!(a & 0x80000000));
207    }
208  } else {
209    c -= a;
210    // LPS_EXCHANGE
211    if (a < qe) {
212      bit = mpsCX;
213      stats->cxTab[context] = (nmpsTab[iCX] << 1) | mpsCX;
214    } else {
215      bit = 1 - mpsCX;
216      if (switchTab[iCX]) {
217        stats->cxTab[context] = (nlpsTab[iCX] << 1) | (1 - mpsCX);
218      } else {
219        stats->cxTab[context] = (nlpsTab[iCX] << 1) | mpsCX;
220      }
221    }
222    a = qe;
223    // RENORMD
224    do {
225      if (ct == 0) {
226        byteIn();
227      }
228      a <<= 1;
229      c <<= 1;
230      --ct;
231    } while (!(a & 0x80000000));
232  }
233  return bit;
234}
235
236int JArithmeticDecoder::decodeByte(Guint context,
237                                   JArithmeticDecoderStats *stats) {
238  int byte;
239  int i;
240
241  byte = 0;
242  for (i = 0; i < 8; ++i) {
243    byte = (byte << 1) | decodeBit(context, stats);
244  }
245  return byte;
246}
247
248GBool JArithmeticDecoder::decodeInt(int *x, JArithmeticDecoderStats *stats) {
249  int s;
250  Guint v;
251  int i;
252
253  prev = 1;
254  s = decodeIntBit(stats);
255  if (decodeIntBit(stats)) {
256    if (decodeIntBit(stats)) {
257      if (decodeIntBit(stats)) {
258        if (decodeIntBit(stats)) {
259          if (decodeIntBit(stats)) {
260            v = 0;
261            for (i = 0; i < 32; ++i) {
262              v = (v << 1) | decodeIntBit(stats);
263            }
264            v += 4436;
265          } else {
266            v = 0;
267            for (i = 0; i < 12; ++i) {
268              v = (v << 1) | decodeIntBit(stats);
269            }
270            v += 340;
271          }
272        } else {
273          v = 0;
274          for (i = 0; i < 8; ++i) {
275            v = (v << 1) | decodeIntBit(stats);
276          }
277          v += 84;
278        }
279      } else {
280        v = 0;
281        for (i = 0; i < 6; ++i) {
282          v = (v << 1) | decodeIntBit(stats);
283        }
284        v += 20;
285      }
286    } else {
287      v = decodeIntBit(stats);
288      v = (v << 1) | decodeIntBit(stats);
289      v = (v << 1) | decodeIntBit(stats);
290      v = (v << 1) | decodeIntBit(stats);
291      v += 4;
292    }
293  } else {
294    v = decodeIntBit(stats);
295    v = (v << 1) | decodeIntBit(stats);
296  }
297
298  if (s) {
299    if (v == 0) {
300      return gFalse;
301    }
302    *x = -(int)v;
303  } else {
304    *x = (int)v;
305  }
306  return gTrue;
307}
308
309int JArithmeticDecoder::decodeIntBit(JArithmeticDecoderStats *stats) {
310  int bit;
311
312  bit = decodeBit(prev, stats);
313  if (prev < 0x100) {
314    prev = (prev << 1) | bit;
315  } else {
316    prev = (((prev << 1) | bit) & 0x1ff) | 0x100;
317  }
318  return bit;
319}
320
321Guint JArithmeticDecoder::decodeIAID(Guint codeLen,
322                                     JArithmeticDecoderStats *stats) {
323  Guint i;
324  int bit;
325
326  prev = 1;
327  for (i = 0; i < codeLen; ++i) {
328    bit = decodeBit(prev, stats);
329    prev = (prev << 1) | bit;
330  }
331  return prev - (1 << codeLen);
332}
333
334void JArithmeticDecoder::byteIn() {
335  if (buf0 == 0xff) {
336    if (buf1 > 0x8f) {
337      if (limitStream) {
338        buf0 = buf1;
339        buf1 = readByte();
340        c = c + 0xff00 - (buf0 << 8);
341      }
342      ct = 8;
343    } else {
344      buf0 = buf1;
345      buf1 = readByte();
346      c = c + 0xfe00 - (buf0 << 9);
347      ct = 7;
348    }
349  } else {
350    buf0 = buf1;
351    buf1 = readByte();
352    c = c + 0xff00 - (buf0 << 8);
353    ct = 8;
354  }
355}
Note: See TracBrowser for help on using the repository browser.