JBig2_HuffmanTable.cpp revision e6986e1e8d4a57987f47c215490cb080a65ee29a
1e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov// Copyright 2014 PDFium Authors. All rights reserved. 2e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov// Use of this source code is governed by a BSD-style license that can be 3e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov// found in the LICENSE file. 4e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov 5e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com 6e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov 7e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov#include "JBig2_HuffmanTable.h" 8e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov#include "JBig2_BitStream.h" 9e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov#include <string.h> 10e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov 11e6986e1e8d4a57987f47c215490cb080a65ee29aSvet GanovCJBig2_HuffmanTable::CJBig2_HuffmanTable(const JBig2TableLine *pTable, int nLines, 12e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov FX_BOOL bHTOOB) 13e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov{ 14e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov init(); 15e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov m_bOK = parseFromStandardTable(pTable, nLines, bHTOOB); 16e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov} 17e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov 18e6986e1e8d4a57987f47c215490cb080a65ee29aSvet GanovCJBig2_HuffmanTable::CJBig2_HuffmanTable(CJBig2_BitStream *pStream) 19e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov{ 20e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov init(); 21e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov m_bOK = parseFromCodedBuffer(pStream); 22e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov} 23e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov 24e6986e1e8d4a57987f47c215490cb080a65ee29aSvet GanovCJBig2_HuffmanTable::~CJBig2_HuffmanTable() 25e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov{ 26e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(CODES) { 27e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov m_pModule->JBig2_Free(CODES); 28e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 29e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(PREFLEN) { 30e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov m_pModule->JBig2_Free(PREFLEN); 31e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 32e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(RANGELEN) { 33e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov m_pModule->JBig2_Free(RANGELEN); 34e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 35e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(RANGELOW) { 36e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov m_pModule->JBig2_Free(RANGELOW); 37e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 38e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov} 39e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganovvoid CJBig2_HuffmanTable::init() 40e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov{ 41e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov HTOOB = FALSE; 42e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov NTEMP = 0; 43e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CODES = NULL; 44e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov PREFLEN = NULL; 45e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELEN = NULL; 46e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELOW = NULL; 47e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov} 48e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganovint CJBig2_HuffmanTable::parseFromStandardTable(const JBig2TableLine *pTable, int nLines, FX_BOOL bHTOOB) 49e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov{ 50e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov int CURLEN, LENMAX, CURCODE, CURTEMP, i; 51e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov int *LENCOUNT; 52e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov int *FIRSTCODE; 53e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov HTOOB = bHTOOB; 54e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov NTEMP = nLines; 55e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CODES = (int*)m_pModule->JBig2_Malloc2(sizeof(int), NTEMP); 56e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov PREFLEN = (int*)m_pModule->JBig2_Malloc2(sizeof(int), NTEMP); 57e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELEN = (int*)m_pModule->JBig2_Malloc2(sizeof(int), NTEMP); 58e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELOW = (int*)m_pModule->JBig2_Malloc2(sizeof(int), NTEMP); 59e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov LENMAX = 0; 60e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov for(i = 0; i < NTEMP; i++) { 61e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov PREFLEN[i] = pTable[i].PREFLEN; 62e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELEN[i] = pTable[i].RANDELEN; 63e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELOW[i] = pTable[i].RANGELOW; 64e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(PREFLEN[i] > LENMAX) { 65e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov LENMAX = PREFLEN[i]; 66e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 67e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 68e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov LENCOUNT = (int*)m_pModule->JBig2_Malloc2(sizeof(int), (LENMAX + 1)); 69e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov JBIG2_memset(LENCOUNT, 0, sizeof(int) * (LENMAX + 1)); 70e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov FIRSTCODE = (int*)m_pModule->JBig2_Malloc2(sizeof(int), (LENMAX + 1)); 71e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov for(i = 0; i < NTEMP; i++) { 72e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov LENCOUNT[PREFLEN[i]] ++; 73e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 74e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURLEN = 1; 75e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov FIRSTCODE[0] = 0; 76e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov LENCOUNT[0] = 0; 77e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov while(CURLEN <= LENMAX) { 78e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov FIRSTCODE[CURLEN] = (FIRSTCODE[CURLEN - 1] + LENCOUNT[CURLEN - 1]) << 1; 79e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURCODE = FIRSTCODE[CURLEN]; 80e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURTEMP = 0; 81e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov while(CURTEMP < NTEMP) { 82e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(PREFLEN[CURTEMP] == CURLEN) { 83e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CODES[CURTEMP] = CURCODE; 84e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURCODE = CURCODE + 1; 85e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 86e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURTEMP = CURTEMP + 1; 87e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 88e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURLEN = CURLEN + 1; 89e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 90e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov m_pModule->JBig2_Free(LENCOUNT); 91e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov m_pModule->JBig2_Free(FIRSTCODE); 92e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov return 1; 93e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov} 94e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov 95e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov#define HT_CHECK_MEMORY_ADJUST \ 96e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(NTEMP >= nSize) \ 97e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov { \ 98e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov nSize += 16; \ 99e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov PREFLEN = (int*)m_pModule->JBig2_Realloc(PREFLEN,sizeof(int)*nSize); \ 100e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELEN = (int*)m_pModule->JBig2_Realloc(RANGELEN,sizeof(int)*nSize); \ 101e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELOW = (int*)m_pModule->JBig2_Realloc(RANGELOW,sizeof(int)*nSize); \ 102e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 103e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganovint CJBig2_HuffmanTable::parseFromCodedBuffer(CJBig2_BitStream *pStream) 104e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov{ 105e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov unsigned char HTPS, HTRS; 106e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov FX_DWORD HTLOW, HTHIGH; 107e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov FX_DWORD CURRANGELOW; 108e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov FX_DWORD nSize = 16; 109e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov int CURLEN, LENMAX, CURCODE, CURTEMP; 110e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov int *LENCOUNT; 111e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov int *FIRSTCODE; 112e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov unsigned char cTemp; 113e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(pStream->read1Byte(&cTemp) == -1) { 114e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov goto failed; 115e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 116e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov HTOOB = cTemp & 0x01; 117e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov HTPS = ((cTemp >> 1) & 0x07) + 1; 118e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov HTRS = ((cTemp >> 4) & 0x07) + 1; 119e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(pStream->readInteger(&HTLOW) == -1 || 120e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov pStream->readInteger(&HTHIGH) == -1 || 121e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov HTLOW > HTHIGH) { 122e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov goto failed; 123e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 124e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov PREFLEN = (int*)m_pModule->JBig2_Malloc2(sizeof(int), nSize); 125e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELEN = (int*)m_pModule->JBig2_Malloc2(sizeof(int), nSize); 126e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELOW = (int*)m_pModule->JBig2_Malloc2(sizeof(int), nSize); 127e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURRANGELOW = HTLOW; 128e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov NTEMP = 0; 129e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov do { 130e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov HT_CHECK_MEMORY_ADJUST 131e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if((pStream->readNBits(HTPS, &PREFLEN[NTEMP]) == -1) || 132e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov (pStream->readNBits(HTRS, &RANGELEN[NTEMP]) == -1)) { 133e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov goto failed; 134e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 135e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELOW[NTEMP] = CURRANGELOW; 136e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURRANGELOW = CURRANGELOW + (1 << RANGELEN[NTEMP]); 137e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov NTEMP = NTEMP + 1; 138e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } while(CURRANGELOW < HTHIGH); 139e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov HT_CHECK_MEMORY_ADJUST 140e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(pStream->readNBits(HTPS, &PREFLEN[NTEMP]) == -1) { 141e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov goto failed; 142e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 143e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELEN[NTEMP] = 32; 144e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELOW[NTEMP] = HTLOW - 1; 145e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov NTEMP = NTEMP + 1; 146e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov HT_CHECK_MEMORY_ADJUST 147e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(pStream->readNBits(HTPS, &PREFLEN[NTEMP]) == -1) { 148e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov goto failed; 149e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 150e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELEN[NTEMP] = 32; 151e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov RANGELOW[NTEMP] = HTHIGH; 152e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov NTEMP = NTEMP + 1; 153e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(HTOOB) { 154e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov HT_CHECK_MEMORY_ADJUST 155e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(pStream->readNBits(HTPS, &PREFLEN[NTEMP]) == -1) { 156e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov goto failed; 157e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 158e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov NTEMP = NTEMP + 1; 159e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 160e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CODES = (int*)m_pModule->JBig2_Malloc2(sizeof(int), NTEMP); 161e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov LENMAX = 0; 162e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov for(int i = 0; i < NTEMP; i++) { 163e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(PREFLEN[i] > LENMAX) { 164e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov LENMAX = PREFLEN[i]; 165e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 166e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 167e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov LENCOUNT = (int*)m_pModule->JBig2_Malloc2(sizeof(int), (LENMAX + 1)); 168e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov JBIG2_memset(LENCOUNT, 0, sizeof(int) * (LENMAX + 1)); 169e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov FIRSTCODE = (int*)m_pModule->JBig2_Malloc2(sizeof(int), (LENMAX + 1)); 170e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov for(int i = 0; i < NTEMP; i++) { 171e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov LENCOUNT[PREFLEN[i]] ++; 172e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 173e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURLEN = 1; 174e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov FIRSTCODE[0] = 0; 175e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov LENCOUNT[0] = 0; 176e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov while(CURLEN <= LENMAX) { 177e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov FIRSTCODE[CURLEN] = (FIRSTCODE[CURLEN - 1] + LENCOUNT[CURLEN - 1]) << 1; 178e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURCODE = FIRSTCODE[CURLEN]; 179e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURTEMP = 0; 180e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov while(CURTEMP < NTEMP) { 181e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov if(PREFLEN[CURTEMP] == CURLEN) { 182e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CODES[CURTEMP] = CURCODE; 183e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURCODE = CURCODE + 1; 184e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 185e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURTEMP = CURTEMP + 1; 186e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 187e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov CURLEN = CURLEN + 1; 188e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov } 189e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov m_pModule->JBig2_Free(LENCOUNT); 190e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov m_pModule->JBig2_Free(FIRSTCODE); 191e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov return TRUE; 192e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganovfailed: 193e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov return FALSE; 194e6986e1e8d4a57987f47c215490cb080a65ee29aSvet Ganov} 195