diff options
author | Gabor Juhos <juhosg@openwrt.org> | 2007-07-15 15:02:38 +0000 |
---|---|---|
committer | Gabor Juhos <juhosg@openwrt.org> | 2007-07-15 15:02:38 +0000 |
commit | 8e8ccb8ddcd59a6acfe7ea647b25378d2c696033 (patch) | |
tree | 7ce47c5a47830caff3fe9dbead3a9dfb444f9f1f /target/linux/adm5120-2.6/image/lzma-loader/src/LzmaDecode.c | |
parent | b85e93eacda82538fd57e73c1bd64b8eac51eba3 (diff) | |
download | master-187ad058-8e8ccb8ddcd59a6acfe7ea647b25378d2c696033.tar.gz master-187ad058-8e8ccb8ddcd59a6acfe7ea647b25378d2c696033.tar.bz2 master-187ad058-8e8ccb8ddcd59a6acfe7ea647b25378d2c696033.zip |
[adm5120] lzma-loader improvements
* update LzmaDecode.[ch] to 4.16
* speed up decompressing from flash
* uses printf from lzma-loader of generic-2.6 target
* initial support for flash bank switching
git-svn-id: svn://svn.openwrt.org/openwrt/trunk@7975 3c298f89-4303-0410-b956-a3cf2f4a3e73
Diffstat (limited to 'target/linux/adm5120-2.6/image/lzma-loader/src/LzmaDecode.c')
-rw-r--r-- | target/linux/adm5120-2.6/image/lzma-loader/src/LzmaDecode.c | 576 |
1 files changed, 251 insertions, 325 deletions
diff --git a/target/linux/adm5120-2.6/image/lzma-loader/src/LzmaDecode.c b/target/linux/adm5120-2.6/image/lzma-loader/src/LzmaDecode.c index 951700bddf..75a358a9ee 100644 --- a/target/linux/adm5120-2.6/image/lzma-loader/src/LzmaDecode.c +++ b/target/linux/adm5120-2.6/image/lzma-loader/src/LzmaDecode.c @@ -1,8 +1,8 @@ /* LzmaDecode.c - LZMA Decoder + LZMA Decoder (optimized for Speed version) - LZMA SDK 4.05 Copyright (c) 1999-2004 Igor Pavlov (2004-08-25) + LZMA SDK 4.16 Copyright (c) 1999-2005 Igor Pavlov (2005-03-18) http://www.7-zip.org/ LZMA SDK is licensed under two licenses: @@ -12,9 +12,9 @@ follow rules of that license. SPECIAL EXCEPTION: - Igor Pavlov, as the author of this code, expressly permits you to - statically or dynamically link your code (or bind by name) to the - interfaces of this file without subjecting your linked code to the + Igor Pavlov, as the author of this Code, expressly permits you to + statically or dynamically link your Code (or bind by name) to the + interfaces of this file without subjecting your linked Code to the terms of the CPL or GNU LGPL. Any modifications or additions to this file, however, are subject to the LGPL or CPL terms. */ @@ -32,242 +32,44 @@ #define kBitModelTotal (1 << kNumBitModelTotalBits) #define kNumMoveBits 5 -typedef struct _CRangeDecoder -{ - Byte *Buffer; - Byte *BufferLim; - UInt32 Range; - UInt32 Code; - #ifdef _LZMA_IN_CB - ILzmaInCallback *InCallback; - int Result; - #endif - int ExtraBytes; -} CRangeDecoder; +#define RC_READ_BYTE (*Buffer++) -Byte RangeDecoderReadByte(CRangeDecoder *rd) -{ - if (rd->Buffer == rd->BufferLim) - { - #ifdef _LZMA_IN_CB - UInt32 size; - rd->Result = rd->InCallback->Read(rd->InCallback, &rd->Buffer, &size); - rd->BufferLim = rd->Buffer + size; - if (size == 0) - #endif - { - rd->ExtraBytes = 1; - return 0xFF; - } - } - return (*rd->Buffer++); -} +#define RC_INIT2 Code = 0; Range = 0xFFFFFFFF; \ + { int i; for(i = 0; i < 5; i++) { RC_TEST; Code = (Code << 8) | RC_READ_BYTE; }} -/* #define ReadByte (*rd->Buffer++) */ -#define ReadByte (RangeDecoderReadByte(rd)) +#ifdef _LZMA_IN_CB -void RangeDecoderInit(CRangeDecoder *rd, - #ifdef _LZMA_IN_CB - ILzmaInCallback *inCallback - #else - Byte *stream, UInt32 bufferSize - #endif - ) -{ - int i; - #ifdef _LZMA_IN_CB - rd->InCallback = inCallback; - rd->Buffer = rd->BufferLim = 0; - #else - rd->Buffer = stream; - rd->BufferLim = stream + bufferSize; - #endif - rd->ExtraBytes = 0; - rd->Code = 0; - rd->Range = (0xFFFFFFFF); - for(i = 0; i < 5; i++) - rd->Code = (rd->Code << 8) | ReadByte; -} +#define RC_TEST { if (Buffer == BufferLim) \ + { UInt32 size; int result = InCallback->Read(InCallback, &Buffer, &size); if (result != LZMA_RESULT_OK) return result; \ + BufferLim = Buffer + size; if (size == 0) return LZMA_RESULT_DATA_ERROR; }} -#define RC_INIT_VAR UInt32 range = rd->Range; UInt32 code = rd->Code; -#define RC_FLUSH_VAR rd->Range = range; rd->Code = code; -#define RC_NORMALIZE if (range < kTopValue) { range <<= 8; code = (code << 8) | ReadByte; } +#define RC_INIT Buffer = BufferLim = 0; RC_INIT2 -UInt32 RangeDecoderDecodeDirectBits(CRangeDecoder *rd, int numTotalBits) -{ - RC_INIT_VAR - UInt32 result = 0; - int i; - for (i = numTotalBits; i > 0; i--) - { - /* UInt32 t; */ - range >>= 1; +#else - result <<= 1; - if (code >= range) - { - code -= range; - result |= 1; - } - /* - t = (code - range) >> 31; - t &= 1; - code -= range & (t - 1); - result = (result + result) | (1 - t); - */ - RC_NORMALIZE - } - RC_FLUSH_VAR - return result; -} +#define RC_TEST { if (Buffer == BufferLim) return LZMA_RESULT_DATA_ERROR; } -int RangeDecoderBitDecode(CProb *prob, CRangeDecoder *rd) -{ - UInt32 bound = (rd->Range >> kNumBitModelTotalBits) * *prob; - if (rd->Code < bound) - { - rd->Range = bound; - *prob += (kBitModelTotal - *prob) >> kNumMoveBits; - if (rd->Range < kTopValue) - { - rd->Code = (rd->Code << 8) | ReadByte; - rd->Range <<= 8; - } - return 0; - } - else - { - rd->Range -= bound; - rd->Code -= bound; - *prob -= (*prob) >> kNumMoveBits; - if (rd->Range < kTopValue) - { - rd->Code = (rd->Code << 8) | ReadByte; - rd->Range <<= 8; - } - return 1; - } -} +#define RC_INIT(buffer, bufferSize) Buffer = buffer; BufferLim = buffer + bufferSize; RC_INIT2 + +#endif -#define RC_GET_BIT2(prob, mi, A0, A1) \ - UInt32 bound = (range >> kNumBitModelTotalBits) * *prob; \ - if (code < bound) \ - { A0; range = bound; *prob += (kBitModelTotal - *prob) >> kNumMoveBits; mi <<= 1; } \ - else \ - { A1; range -= bound; code -= bound; *prob -= (*prob) >> kNumMoveBits; mi = (mi + mi) + 1; } \ - RC_NORMALIZE +#define RC_NORMALIZE if (Range < kTopValue) { RC_TEST; Range <<= 8; Code = (Code << 8) | RC_READ_BYTE; } -#define RC_GET_BIT(prob, mi) RC_GET_BIT2(prob, mi, ; , ;) +#define IfBit0(p) RC_NORMALIZE; bound = (Range >> kNumBitModelTotalBits) * *(p); if (Code < bound) +#define UpdateBit0(p) Range = bound; *(p) += (kBitModelTotal - *(p)) >> kNumMoveBits; +#define UpdateBit1(p) Range -= bound; Code -= bound; *(p) -= (*(p)) >> kNumMoveBits; -int RangeDecoderBitTreeDecode(CProb *probs, int numLevels, CRangeDecoder *rd) -{ - int mi = 1; - int i; - #ifdef _LZMA_LOC_OPT - RC_INIT_VAR - #endif - for(i = numLevels; i > 0; i--) - { - #ifdef _LZMA_LOC_OPT - CProb *prob = probs + mi; - RC_GET_BIT(prob, mi) - #else - mi = (mi + mi) + RangeDecoderBitDecode(probs + mi, rd); - #endif - } - #ifdef _LZMA_LOC_OPT - RC_FLUSH_VAR - #endif - return mi - (1 << numLevels); -} +#define RC_GET_BIT2(p, mi, A0, A1) IfBit0(p) \ + { UpdateBit0(p); mi <<= 1; A0; } else \ + { UpdateBit1(p); mi = (mi + mi) + 1; A1; } + +#define RC_GET_BIT(p, mi) RC_GET_BIT2(p, mi, ; , ;) -int RangeDecoderReverseBitTreeDecode(CProb *probs, int numLevels, CRangeDecoder *rd) -{ - int mi = 1; - int i; - int symbol = 0; - #ifdef _LZMA_LOC_OPT - RC_INIT_VAR - #endif - for(i = 0; i < numLevels; i++) - { - #ifdef _LZMA_LOC_OPT - CProb *prob = probs + mi; - RC_GET_BIT2(prob, mi, ; , symbol |= (1 << i)) - #else - int bit = RangeDecoderBitDecode(probs + mi, rd); - mi = mi + mi + bit; - symbol |= (bit << i); - #endif - } - #ifdef _LZMA_LOC_OPT - RC_FLUSH_VAR - #endif - return symbol; -} +#define RangeDecoderBitTreeDecode(probs, numLevels, res) \ + { int i = numLevels; res = 1; \ + do { CProb *p = probs + res; RC_GET_BIT(p, res) } while(--i != 0); \ + res -= (1 << numLevels); } -Byte LzmaLiteralDecode(CProb *probs, CRangeDecoder *rd) -{ - int symbol = 1; - #ifdef _LZMA_LOC_OPT - RC_INIT_VAR - #endif - do - { - #ifdef _LZMA_LOC_OPT - CProb *prob = probs + symbol; - RC_GET_BIT(prob, symbol) - #else - symbol = (symbol + symbol) | RangeDecoderBitDecode(probs + symbol, rd); - #endif - } - while (symbol < 0x100); - #ifdef _LZMA_LOC_OPT - RC_FLUSH_VAR - #endif - return symbol; -} - -Byte LzmaLiteralDecodeMatch(CProb *probs, CRangeDecoder *rd, Byte matchByte) -{ - int symbol = 1; - #ifdef _LZMA_LOC_OPT - RC_INIT_VAR - #endif - do - { - int bit; - int matchBit = (matchByte >> 7) & 1; - matchByte <<= 1; - #ifdef _LZMA_LOC_OPT - { - CProb *prob = probs + ((1 + matchBit) << 8) + symbol; - RC_GET_BIT2(prob, symbol, bit = 0, bit = 1) - } - #else - bit = RangeDecoderBitDecode(probs + ((1 + matchBit) << 8) + symbol, rd); - symbol = (symbol << 1) | bit; - #endif - if (matchBit != bit) - { - while (symbol < 0x100) - { - #ifdef _LZMA_LOC_OPT - CProb *prob = probs + symbol; - RC_GET_BIT(prob, symbol) - #else - symbol = (symbol + symbol) | RangeDecoderBitDecode(probs + symbol, rd); - #endif - } - break; - } - } - while (symbol < 0x100); - #ifdef _LZMA_LOC_OPT - RC_FLUSH_VAR - #endif - return symbol; -} #define kNumPosBitsMax 4 #define kNumPosStatesMax (1 << kNumPosBitsMax) @@ -286,19 +88,9 @@ Byte LzmaLiteralDecodeMatch(CProb *probs, CRangeDecoder *rd, Byte matchByte) #define LenHigh (LenMid + (kNumPosStatesMax << kLenNumMidBits)) #define kNumLenProbs (LenHigh + kLenNumHighSymbols) -int LzmaLenDecode(CProb *p, CRangeDecoder *rd, int posState) -{ - if(RangeDecoderBitDecode(p + LenChoice, rd) == 0) - return RangeDecoderBitTreeDecode(p + LenLow + - (posState << kLenNumLowBits), kLenNumLowBits, rd); - if(RangeDecoderBitDecode(p + LenChoice2, rd) == 0) - return kLenNumLowSymbols + RangeDecoderBitTreeDecode(p + LenMid + - (posState << kLenNumMidBits), kLenNumMidBits, rd); - return kLenNumLowSymbols + kLenNumMidSymbols + - RangeDecoderBitTreeDecode(p + LenHigh, kLenNumHighBits, rd); -} #define kNumStates 12 +#define kNumLitStates 7 #define kStartPosModelIndex 4 #define kEndPosModelIndex 14 @@ -333,7 +125,13 @@ StopCompilingDueBUG typedef struct _LzmaVarState { - CRangeDecoder RangeDecoder; + Byte *Buffer; + Byte *BufferLim; + UInt32 Range; + UInt32 Code; + #ifdef _LZMA_IN_CB + ILzmaInCallback *InCallback; + #endif Byte *Dictionary; UInt32 DictionarySize; UInt32 DictionaryPos; @@ -343,8 +141,8 @@ typedef struct _LzmaVarState int lp; int pb; int State; - int PreviousIsMatch; int RemainLen; + Byte TempDictionary[4]; } LzmaVarState; int LzmaDecoderInit( @@ -352,12 +150,16 @@ int LzmaDecoderInit( int lc, int lp, int pb, unsigned char *dictionary, UInt32 dictionarySize, #ifdef _LZMA_IN_CB - ILzmaInCallback *inCallback + ILzmaInCallback *InCallback #else unsigned char *inStream, UInt32 inSize #endif ) { + Byte *Buffer; + Byte *BufferLim; + UInt32 Range; + UInt32 Code; LzmaVarState *vs = (LzmaVarState *)buffer; CProb *p = (CProb *)(buffer + sizeof(LzmaVarState)); UInt32 numProbs = Literal + ((UInt32)LZMA_LIT_SIZE << (lc + lp)); @@ -373,18 +175,24 @@ int LzmaDecoderInit( vs->lp = lp; vs->pb = pb; vs->State = 0; - vs->PreviousIsMatch = 0; vs->RemainLen = 0; dictionary[dictionarySize - 1] = 0; for (i = 0; i < numProbs; i++) p[i] = kBitModelTotal >> 1; - RangeDecoderInit(&vs->RangeDecoder, - #ifdef _LZMA_IN_CB - inCallback - #else - inStream, inSize - #endif - ); + + #ifdef _LZMA_IN_CB + RC_INIT; + #else + RC_INIT(inStream, inSize); + #endif + vs->Buffer = Buffer; + vs->BufferLim = BufferLim; + vs->Range = Range; + vs->Code = Code; + #ifdef _LZMA_IN_CB + vs->InCallback = InCallback; + #endif + return LZMA_RESULT_OK; } @@ -393,10 +201,15 @@ int LzmaDecode(unsigned char *buffer, UInt32 *outSizeProcessed) { LzmaVarState *vs = (LzmaVarState *)buffer; + Byte *Buffer = vs->Buffer; + Byte *BufferLim = vs->BufferLim; + UInt32 Range = vs->Range; + UInt32 Code = vs->Code; + #ifdef _LZMA_IN_CB + ILzmaInCallback *InCallback = vs->InCallback; + #endif CProb *p = (CProb *)(buffer + sizeof(LzmaVarState)); - CRangeDecoder rd = vs->RangeDecoder; int state = vs->State; - int previousIsMatch = vs->PreviousIsMatch; Byte previousByte; UInt32 rep0 = vs->Reps[0], rep1 = vs->Reps[1], rep2 = vs->Reps[2], rep3 = vs->Reps[3]; UInt32 nowPos = 0; @@ -410,13 +223,21 @@ int LzmaDecode(unsigned char *buffer, UInt32 dictionarySize = vs->DictionarySize; UInt32 dictionaryPos = vs->DictionaryPos; + Byte tempDictionary[4]; + if (dictionarySize == 0) + { + dictionary = tempDictionary; + dictionarySize = 1; + tempDictionary[0] = vs->TempDictionary[0]; + } + if (len == -1) { *outSizeProcessed = 0; return LZMA_RESULT_OK; } - while(len > 0 && nowPos < outSize) + while(len != 0 && nowPos < outSize) { UInt32 pos = dictionaryPos - rep0; if (pos >= dictionarySize) @@ -436,7 +257,7 @@ int LzmaDecode( Byte *buffer, UInt32 bufferSize, int lc, int lp, int pb, #ifdef _LZMA_IN_CB - ILzmaInCallback *inCallback, + ILzmaInCallback *InCallback, #else unsigned char *inStream, UInt32 inSize, #endif @@ -445,32 +266,39 @@ int LzmaDecode( { UInt32 numProbs = Literal + ((UInt32)LZMA_LIT_SIZE << (lc + lp)); CProb *p = (CProb *)buffer; - CRangeDecoder rd; + UInt32 i; int state = 0; - int previousIsMatch = 0; Byte previousByte = 0; UInt32 rep0 = 1, rep1 = 1, rep2 = 1, rep3 = 1; UInt32 nowPos = 0; UInt32 posStateMask = (1 << pb) - 1; UInt32 literalPosMask = (1 << lp) - 1; int len = 0; + + Byte *Buffer; + Byte *BufferLim; + UInt32 Range; + UInt32 Code; + if (bufferSize < numProbs * sizeof(CProb)) return LZMA_RESULT_NOT_ENOUGH_MEM; for (i = 0; i < numProbs; i++) - p[i] = kBitModelTotal >> 1; - RangeDecoderInit(&rd, - #ifdef _LZMA_IN_CB - inCallback - #else - inStream, inSize - #endif - ); + p[i] = kBitModelTotal >> 1; + + + #ifdef _LZMA_IN_CB + RC_INIT; + #else + RC_INIT(inStream, inSize); + #endif #endif *outSizeProcessed = 0; while(nowPos < outSize) { + CProb *prob; + UInt32 bound; int posState = (int)( (nowPos #ifdef _LZMA_OUT_READ @@ -478,15 +306,13 @@ int LzmaDecode( #endif ) & posStateMask); - #ifdef _LZMA_IN_CB - if (rd.Result != LZMA_RESULT_OK) - return rd.Result; - #endif - if (rd.ExtraBytes != 0) - return LZMA_RESULT_DATA_ERROR; - if (RangeDecoderBitDecode(p + IsMatch + (state << kNumPosBitsMax) + posState, &rd) == 0) + + prob = p + IsMatch + (state << kNumPosBitsMax) + posState; + IfBit0(prob) { - CProb *probs = p + Literal + (LZMA_LIT_SIZE * + int symbol = 1; + UpdateBit0(prob) + prob = p + Literal + (LZMA_LIT_SIZE * ((( (nowPos #ifdef _LZMA_OUT_READ @@ -495,12 +321,9 @@ int LzmaDecode( ) & literalPosMask) << lc) + (previousByte >> (8 - lc)))); - if (state < 4) state = 0; - else if (state < 10) state -= 3; - else state -= 6; - if (previousIsMatch) + if (state >= kNumLitStates) { - Byte matchByte; + int matchByte; #ifdef _LZMA_OUT_READ UInt32 pos = dictionaryPos - rep0; if (pos >= dictionarySize) @@ -509,39 +332,71 @@ int LzmaDecode( #else matchByte = outStream[nowPos - rep0]; #endif - previousByte = LzmaLiteralDecodeMatch(probs, &rd, matchByte); - previousIsMatch = 0; + // prob += 0x100; + do + { + int bit; + CProb *probLit; + matchByte <<= 1; + bit = (matchByte & 0x100); + probLit = prob + 0x100 + bit + symbol; + RC_GET_BIT2(probLit, symbol, if (bit != 0) break, if (bit == 0) break) + } + while (symbol < 0x100); + // prob -= 0x100; } - else - previousByte = LzmaLiteralDecode(probs, &rd); + while (symbol < 0x100) + { + CProb *probLit = prob + symbol; + RC_GET_BIT(probLit, symbol) + } + previousByte = (Byte)symbol; + outStream[nowPos++] = previousByte; #ifdef _LZMA_OUT_READ dictionary[dictionaryPos] = previousByte; if (++dictionaryPos == dictionarySize) dictionaryPos = 0; #endif + if (state < 4) state = 0; + else if (state < 10) state -= 3; + else state -= 6; } else { - previousIsMatch = 1; - if (RangeDecoderBitDecode(p + IsRep + state, &rd) == 1) + // int isItRep; + UpdateBit1(prob); + prob = p + IsRep + state; + IfBit0(prob) { - if (RangeDecoderBitDecode(p + IsRepG0 + state, &rd) == 0) + UpdateBit0(prob); + rep3 = rep2; + rep2 = rep1; + rep1 = rep0; + state = state < kNumLitStates ? 0 : 3; + prob = p + LenCoder; + } + else + { + UpdateBit1(prob); + prob = p + IsRepG0 + state; + IfBit0(prob) { - if (RangeDecoderBitDecode(p + IsRep0Long + (state << kNumPosBitsMax) + posState, &rd) == 0) + UpdateBit0(prob); + prob = p + IsRep0Long + (state << kNumPosBitsMax) + posState; + IfBit0(prob) { #ifdef _LZMA_OUT_READ UInt32 pos; #endif - if ( - (nowPos + UpdateBit0(prob); + if (nowPos #ifdef _LZMA_OUT_READ + globalPos #endif - ) - == 0) + == 0) return LZMA_RESULT_DATA_ERROR; - state = state < 7 ? 9 : 11; + state = state < kNumLitStates ? 9 : 11; #ifdef _LZMA_OUT_READ pos = dictionaryPos - rep0; if (pos >= dictionarySize) @@ -556,18 +411,33 @@ int LzmaDecode( outStream[nowPos++] = previousByte; continue; } + else + { + UpdateBit1(prob); + } } else { UInt32 distance; - if(RangeDecoderBitDecode(p + IsRepG1 + state, &rd) == 0) + UpdateBit1(prob); + prob = p + IsRepG1 + state; + IfBit0(prob) + { + UpdateBit0(prob); distance = rep1; + } else { - if(RangeDecoderBitDecode(p + IsRepG2 + state, &rd) == 0) + UpdateBit1(prob); + prob = p + IsRepG2 + state; + IfBit0(prob) + { + UpdateBit0(prob); distance = rep2; + } else { + UpdateBit1(prob); distance = rep3; rep3 = rep2; } @@ -576,55 +446,107 @@ int LzmaDecode( rep1 = rep0; rep0 = distance; } - len = LzmaLenDecode(p + RepLenCoder, &rd, posState); - state = state < 7 ? 8 : 11; + state = state < kNumLitStates ? 8 : 11; + prob = p + RepLenCoder; } - else + { + int numBits, offset; + CProb *probLen = prob + LenChoice; + IfBit0(probLen) + { + UpdateBit0(probLen); + probLen = prob + LenLow + (posState << kLenNumLowBits); + offset = 0; + numBits = kLenNumLowBits; + } + else + { + UpdateBit1(probLen); + probLen = prob + LenChoice2; + IfBit0(probLen) + { + UpdateBit0(probLen); + probLen = prob + LenMid + (posState << kLenNumMidBits); + offset = kLenNumLowSymbols; + numBits = kLenNumMidBits; + } + else + { + UpdateBit1(probLen); + probLen = prob + LenHigh; + offset = kLenNumLowSymbols + kLenNumMidSymbols; + numBits = kLenNumHighBits; + } + } + RangeDecoderBitTreeDecode(probLen, numBits, len); + len += offset; + } + + if (state < 4) { int posSlot; - rep3 = rep2; - rep2 = rep1; - rep1 = rep0; - state = state < 7 ? 7 : 10; - len = LzmaLenDecode(p + LenCoder, &rd, posState); - posSlot = RangeDecoderBitTreeDecode(p + PosSlot + + state += kNumLitStates; + prob = p + PosSlot + ((len < kNumLenToPosStates ? len : kNumLenToPosStates - 1) << - kNumPosSlotBits), kNumPosSlotBits, &rd); + kNumPosSlotBits); + RangeDecoderBitTreeDecode(prob, kNumPosSlotBits, posSlot); if (posSlot >= kStartPosModelIndex) { int numDirectBits = ((posSlot >> 1) - 1); - rep0 = ((2 | ((UInt32)posSlot & 1)) << numDirectBits); + rep0 = (2 | ((UInt32)posSlot & 1)); if (posSlot < kEndPosModelIndex) { - rep0 += RangeDecoderReverseBitTreeDecode( - p + SpecPos + rep0 - posSlot - 1, numDirectBits, &rd); + rep0 <<= numDirectBits; + prob = p + SpecPos + rep0 - posSlot - 1; } else { - rep0 += RangeDecoderDecodeDirectBits(&rd, - numDirectBits - kNumAlignBits) << kNumAlignBits; - rep0 += RangeDecoderReverseBitTreeDecode(p + Align, kNumAlignBits, &rd); + numDirectBits -= kNumAlignBits; + do + { + RC_NORMALIZE + Range >>= 1; + rep0 <<= 1; + if (Code >= Range) + { + Code -= Range; + rep0 |= 1; + } + } + while (--numDirectBits != 0); + prob = p + Align; + rep0 <<= kNumAlignBits; + numDirectBits = kNumAlignBits; + } + { + int i = 1; + int mi = 1; + do + { + CProb *prob3 = prob + mi; + RC_GET_BIT2(prob3, mi, ; , rep0 |= i); + i <<= 1; + } + while(--numDirectBits != 0); } } else rep0 = posSlot; - rep0++; - } - if (rep0 == (UInt32)(0)) - { - /* it's for stream version */ - len = -1; - break; + if (++rep0 == (UInt32)(0)) + { + /* it's for stream version */ + len = -1; + break; + } } + + len += kMatchMinLen; if (rep0 > nowPos #ifdef _LZMA_OUT_READ - + globalPos + + globalPos || rep0 > dictionarySize #endif - ) - { + ) return LZMA_RESULT_DATA_ERROR; - } - len += kMatchMinLen; do { #ifdef _LZMA_OUT_READ @@ -638,15 +560,19 @@ int LzmaDecode( #else previousByte = outStream[nowPos - rep0]; #endif - outStream[nowPos++] = previousByte; len--; + outStream[nowPos++] = previousByte; } - while(len > 0 && nowPos < outSize); + while(len != 0 && nowPos < outSize); } } + RC_NORMALIZE; #ifdef _LZMA_OUT_READ - vs->RangeDecoder = rd; + vs->Buffer = Buffer; + vs->BufferLim = BufferLim; + vs->Range = Range; + vs->Code = Code; vs->DictionaryPos = dictionaryPos; vs->GlobalPos = globalPos + nowPos; vs->Reps[0] = rep0; @@ -654,8 +580,8 @@ int LzmaDecode( vs->Reps[2] = rep2; vs->Reps[3] = rep3; vs->State = state; - vs->PreviousIsMatch = previousIsMatch; vs->RemainLen = len; + vs->TempDictionary[0] = tempDictionary[0]; #endif *outSizeProcessed = nowPos; |