示例#1
0
        private bool ReadTables20()
        {
            byte[] BitLength = new byte[Compress.BC20];
            byte[] Table = new byte[Compress.MC20 * 4];
            int    TableSize, N, I;

            if (inAddr > readTop - 25)
            {
                if (!unpReadBuf())
                {
                    return(false);
                }
            }
            int BitField = GetBits();

            UnpAudioBlock = (BitField & 0x8000);

            if (0 == (BitField & 0x4000))
            {
                // memset(UnpOldTable20,0,sizeof(UnpOldTable20));
                Utility.Fill(UnpOldTable20, (byte)0);
            }
            AddBits(2);

            if (UnpAudioBlock != 0)
            {
                UnpChannels = ((Utility.URShift(BitField, 12)) & 3) + 1;
                if (UnpCurChannel >= UnpChannels)
                {
                    UnpCurChannel = 0;
                }
                AddBits(2);
                TableSize = Compress.MC20 * UnpChannels;
            }
            else
            {
                TableSize = Compress.NC20 + Compress.DC20 + Compress.RC20;
            }
            for (I = 0; I < Compress.BC20; I++)
            {
                BitLength[I] = (byte)(Utility.URShift(GetBits(), 12));
                AddBits(4);
            }
            UnpackUtility.makeDecodeTables(BitLength, 0, BD, Compress.BC20);
            I = 0;
            while (I < TableSize)
            {
                if (inAddr > readTop - 5)
                {
                    if (!unpReadBuf())
                    {
                        return(false);
                    }
                }
                int Number = this.decodeNumber(BD);
                if (Number < 16)
                {
                    Table[I] = (byte)((Number + UnpOldTable20[I]) & 0xf);
                    I++;
                }
                else if (Number == 16)
                {
                    N = (Utility.URShift(GetBits(), 14)) + 3;
                    AddBits(2);
                    while (N-- > 0 && I < TableSize)
                    {
                        Table[I] = Table[I - 1];
                        I++;
                    }
                }
                else
                {
                    if (Number == 17)
                    {
                        N = (Utility.URShift(GetBits(), 13)) + 3;
                        AddBits(3);
                    }
                    else
                    {
                        N = (Utility.URShift(GetBits(), 9)) + 11;
                        AddBits(7);
                    }
                    while (N-- > 0 && I < TableSize)
                    {
                        Table[I++] = 0;
                    }
                }
            }
            if (inAddr > readTop)
            {
                return(true);
            }
            if (UnpAudioBlock != 0)
            {
                for (I = 0; I < UnpChannels; I++)
                {
                    UnpackUtility.makeDecodeTables(Table, I * Compress.MC20, MD[I], Compress.MC20);
                }
            }
            else
            {
                UnpackUtility.makeDecodeTables(Table, 0, LD, Compress.NC20);
                UnpackUtility.makeDecodeTables(Table, Compress.NC20, DD, Compress.DC20);
                UnpackUtility.makeDecodeTables(Table, Compress.NC20 + Compress.DC20, RD, Compress.RC20);
            }
            // memcpy(UnpOldTable20,Table,sizeof(UnpOldTable20));
            for (int i = 0; i < UnpOldTable20.Length; i++)
            {
                UnpOldTable20[i] = Table[i];
            }
            return(true);
        }
示例#2
0
 private int decodeNumber(Decode RD)
 {
     return(UnpackUtility.decodeNumber(this, RD));
 }
示例#3
0
        private bool ReadTables20()
        {
            int num;
            int num3;

            byte[] lenTab  = new byte[0x13];
            byte[] buffer2 = new byte[0x404];
            if ((base.inAddr > (base.readTop - 0x19)) && !base.unpReadBuf())
            {
                return(false);
            }
            int bits = base.GetBits();

            this.UnpAudioBlock = bits & 0x8000;
            if (0 == (bits & 0x4000))
            {
                Utility.Fill <byte>(this.UnpOldTable20, 0);
            }
            base.AddBits(2);
            if (this.UnpAudioBlock != 0)
            {
                this.UnpChannels = (Utility.URShift(bits, 12) & 3) + 1;
                if (this.UnpCurChannel >= this.UnpChannels)
                {
                    this.UnpCurChannel = 0;
                }
                base.AddBits(2);
                num = 0x101 * this.UnpChannels;
            }
            else
            {
                num = 0x176;
            }
            for (num3 = 0; num3 < 0x13; num3++)
            {
                lenTab[num3] = (byte)Utility.URShift(base.GetBits(), 12);
                base.AddBits(4);
            }
            UnpackUtility.makeDecodeTables(lenTab, 0, this.BD, 0x13);
            num3 = 0;
            while (num3 < num)
            {
                if ((base.inAddr > (base.readTop - 5)) && !base.unpReadBuf())
                {
                    return(false);
                }
                int num5 = this.decodeNumber(this.BD);
                if (num5 < 0x10)
                {
                    buffer2[num3] = (byte)((num5 + this.UnpOldTable20[num3]) & 15);
                    num3++;
                }
                else
                {
                    int num2;
                    if (num5 == 0x10)
                    {
                        num2 = Utility.URShift(base.GetBits(), 14) + 3;
                        base.AddBits(2);
                        while ((num2-- > 0) && (num3 < num))
                        {
                            buffer2[num3] = buffer2[num3 - 1];
                            num3++;
                        }
                    }
                    else
                    {
                        if (num5 == 0x11)
                        {
                            num2 = Utility.URShift(base.GetBits(), 13) + 3;
                            base.AddBits(3);
                        }
                        else
                        {
                            num2 = Utility.URShift(base.GetBits(), 9) + 11;
                            base.AddBits(7);
                        }
                        while ((num2-- > 0) && (num3 < num))
                        {
                            buffer2[num3++] = 0;
                        }
                    }
                }
            }
            if (base.inAddr <= base.readTop)
            {
                if (this.UnpAudioBlock != 0)
                {
                    for (num3 = 0; num3 < this.UnpChannels; num3++)
                    {
                        UnpackUtility.makeDecodeTables(buffer2, num3 * 0x101, this.MD[num3], 0x101);
                    }
                }
                else
                {
                    UnpackUtility.makeDecodeTables(buffer2, 0, this.LD, 0x12a);
                    UnpackUtility.makeDecodeTables(buffer2, 0x12a, this.DD, 0x30);
                    UnpackUtility.makeDecodeTables(buffer2, 0x15a, this.RD, 0x1c);
                }
                for (int i = 0; i < this.UnpOldTable20.Length; i++)
                {
                    this.UnpOldTable20[i] = buffer2[i];
                }
            }
            return(true);
        }
示例#4
0
        private bool readTables()
        {
            byte[] bitLength = new byte[Compress.BC];

            byte[] table = new byte[Compress.HUFF_TABLE_SIZE];
            if (inAddr > readTop - 25)
            {
                if (!unpReadBuf())
                {
                    return(false);
                }
            }
            AddBits((8 - inBit) & 7);
            long bitField = GetBits() & unchecked ((int)0xffFFffFF);

            if ((bitField & 0x8000) != 0)
            {
                unpBlockType = BlockTypes.BLOCK_PPM;
                return(ppm.decodeInit(this, ppmEscChar));
            }
            unpBlockType = BlockTypes.BLOCK_LZ;

            prevLowDist     = 0;
            lowDistRepCount = 0;

            if ((bitField & 0x4000) == 0)
            {
                Utility.Fill(unpOldTable, (byte)0); // memset(UnpOldTable,0,sizeof(UnpOldTable));
            }
            AddBits(2);

            for (int i = 0; i < Compress.BC; i++)
            {
                int length = (Utility.URShift(GetBits(), 12)) & 0xFF;
                AddBits(4);
                if (length == 15)
                {
                    int zeroCount = (Utility.URShift(GetBits(), 12)) & 0xFF;
                    AddBits(4);
                    if (zeroCount == 0)
                    {
                        bitLength[i] = 15;
                    }
                    else
                    {
                        zeroCount += 2;
                        while (zeroCount-- > 0 && i < bitLength.Length)
                        {
                            bitLength[i++] = 0;
                        }
                        i--;
                    }
                }
                else
                {
                    bitLength[i] = (byte)length;
                }
            }

            UnpackUtility.makeDecodeTables(bitLength, 0, BD, Compress.BC);

            int TableSize = Compress.HUFF_TABLE_SIZE;

            for (int i = 0; i < TableSize;)
            {
                if (inAddr > readTop - 5)
                {
                    if (!unpReadBuf())
                    {
                        return(false);
                    }
                }
                int Number = this.decodeNumber(BD);
                if (Number < 16)
                {
                    table[i] = (byte)((Number + unpOldTable[i]) & 0xf);
                    i++;
                }
                else if (Number < 18)
                {
                    int N;
                    if (Number == 16)
                    {
                        N = (Utility.URShift(GetBits(), 13)) + 3;
                        AddBits(3);
                    }
                    else
                    {
                        N = (Utility.URShift(GetBits(), 9)) + 11;
                        AddBits(7);
                    }
                    while (N-- > 0 && i < TableSize)
                    {
                        table[i] = table[i - 1];
                        i++;
                    }
                }
                else
                {
                    int N;
                    if (Number == 18)
                    {
                        N = (Utility.URShift(GetBits(), 13)) + 3;
                        AddBits(3);
                    }
                    else
                    {
                        N = (Utility.URShift(GetBits(), 9)) + 11;
                        AddBits(7);
                    }
                    while (N-- > 0 && i < TableSize)
                    {
                        table[i++] = 0;
                    }
                }
            }
            tablesRead = true;
            if (inAddr > readTop)
            {
                return(false);
            }
            UnpackUtility.makeDecodeTables(table, 0, LD, Compress.NC);
            UnpackUtility.makeDecodeTables(table, Compress.NC, DD, Compress.DC);
            UnpackUtility.makeDecodeTables(table, Compress.NC + Compress.DC, LDD, Compress.LDC);
            UnpackUtility.makeDecodeTables(table, Compress.NC + Compress.DC + Compress.LDC, RD, Compress.RC);

            // memcpy(unpOldTable,table,sizeof(unpOldTable));

            Array.Copy(table, 0, unpOldTable, 0, unpOldTable.Length);
            return(true);
        }
示例#5
0
 private int decodeNumber(BitDecode BD)
 {
     return(UnpackUtility.decodeNumber(this, BD));
 }
示例#6
0
        private void unpack29(bool solid)
        {
            int[]  DDecode = new int[Compress.DC];
            byte[] DBits   = new byte[Compress.DC];

            int Bits;

            if (DDecode[1] == 0)
            {
                int Dist = 0, BitLength = 0, Slot = 0;
                for (int I = 0; I < DBitLengthCounts.Length; I++, BitLength++)
                {
                    int count = DBitLengthCounts[I];
                    for (int J = 0; J < count; J++, Slot++, Dist += (1 << BitLength))
                    {
                        DDecode[Slot] = Dist;
                        DBits[Slot]   = (byte)BitLength;
                    }
                }
            }

            fileExtracted = true;

            if (!suspended)
            {
                unpInitData(solid);
                if (!unpReadBuf())
                {
                    return;
                }
                if ((!solid || !tablesRead) && !readTables())
                {
                    return;
                }
            }

            if (ppmError)
            {
                return;
            }

            while (true)
            {
                unpPtr &= Compress.MAXWINMASK;

                if (inAddr > readBorder)
                {
                    if (!unpReadBuf())
                    {
                        break;
                    }
                }
                // System.out.println(((wrPtr - unpPtr) &
                // Compress.MAXWINMASK)+":"+wrPtr+":"+unpPtr);
                if (((wrPtr - unpPtr) & Compress.MAXWINMASK) < 260 && wrPtr != unpPtr)
                {
                    UnpWriteBuf();
                    if (destUnpSize <= 0)
                    {
                        return;
                    }
                    if (suspended)
                    {
                        fileExtracted = false;
                        return;
                    }
                }
                if (unpBlockType == BlockTypes.BLOCK_PPM)
                {
                    int Ch = ppm.decodeChar();
                    if (Ch == -1)
                    {
                        ppmError = true;
                        break;
                    }
                    if (Ch == ppmEscChar)
                    {
                        int NextCh = ppm.decodeChar();
                        if (NextCh == 0)
                        {
                            if (!readTables())
                            {
                                break;
                            }
                            continue;
                        }
                        if (NextCh == 2 || NextCh == -1)
                        {
                            break;
                        }
                        if (NextCh == 3)
                        {
                            if (!readVMCodePPM())
                            {
                                break;
                            }
                            continue;
                        }
                        if (NextCh == 4)
                        {
                            int  Distance = 0, Length = 0;
                            bool failed = false;
                            for (int I = 0; I < 4 && !failed; I++)
                            {
                                int ch = ppm.decodeChar();
                                if (ch == -1)
                                {
                                    failed = true;
                                }
                                else
                                {
                                    if (I == 3)
                                    {
                                        // Bug fixed
                                        Length = ch & 0xff;
                                    }
                                    else
                                    {
                                        // Bug fixed
                                        Distance = (Distance << 8) + (ch & 0xff);
                                    }
                                }
                            }
                            if (failed)
                            {
                                break;
                            }
                            copyString(Length + 32, Distance + 2);
                            continue;
                        }
                        if (NextCh == 5)
                        {
                            int Length = ppm.decodeChar();
                            if (Length == -1)
                            {
                                break;
                            }
                            copyString(Length + 4, 1);
                            continue;
                        }
                    }
                    window[unpPtr++] = (byte)Ch;
                    continue;
                }

                //int Number = this.decodeNumber(LD);
                int Number = UnpackUtility.decodeNumber(this, LD);
                if (Number < 256)
                {
                    window[unpPtr++] = (byte)Number;
                    continue;
                }
                if (Number >= 271)
                {
                    int Length = LDecode[Number -= 271] + 3;
                    if ((Bits = LBits[Number]) > 0)
                    {
                        Length += Utility.URShift(GetBits(), (16 - Bits));
                        AddBits(Bits);
                    }

                    //int DistNumber = this.decodeNumber(DD);
                    int DistNumber = UnpackUtility.decodeNumber(this, DD);

                    int Distance = DDecode[DistNumber] + 1;
                    if ((Bits = DBits[DistNumber]) > 0)
                    {
                        if (DistNumber > 9)
                        {
                            if (Bits > 4)
                            {
                                Distance += ((Utility.URShift(GetBits(), (20 - Bits))) << 4);
                                AddBits(Bits - 4);
                            }
                            if (lowDistRepCount > 0)
                            {
                                lowDistRepCount--;
                                Distance += prevLowDist;
                            }
                            else
                            {
                                //int LowDist = this.decodeNumber(LDD);
                                int LowDist = UnpackUtility.decodeNumber(this, LDD);
                                if (LowDist == 16)
                                {
                                    lowDistRepCount = Compress.LOW_DIST_REP_COUNT - 1;
                                    Distance       += prevLowDist;
                                }
                                else
                                {
                                    Distance   += LowDist;
                                    prevLowDist = LowDist;
                                }
                            }
                        }
                        else
                        {
                            Distance += Utility.URShift(GetBits(), (16 - Bits));
                            AddBits(Bits);
                        }
                    }

                    if (Distance >= 0x2000)
                    {
                        Length++;
                        if (Distance >= 0x40000L)
                        {
                            Length++;
                        }
                    }

                    insertOldDist(Distance);
                    insertLastMatch(Length, Distance);

                    copyString(Length, Distance);
                    continue;
                }
                if (Number == 256)
                {
                    if (!readEndOfBlock())
                    {
                        break;
                    }
                    continue;
                }
                if (Number == 257)
                {
                    if (!readVMCode())
                    {
                        break;
                    }
                    continue;
                }
                if (Number == 258)
                {
                    if (lastLength != 0)
                    {
                        copyString(lastLength, lastDist);
                    }
                    continue;
                }
                if (Number < 263)
                {
                    int DistNum  = Number - 259;
                    int Distance = oldDist[DistNum];
                    for (int I = DistNum; I > 0; I--)
                    {
                        oldDist[I] = oldDist[I - 1];
                    }
                    oldDist[0] = Distance;

                    //int LengthNumber = this.decodeNumber(RD);
                    int LengthNumber = UnpackUtility.decodeNumber(this, RD);
                    int Length       = LDecode[LengthNumber] + 2;
                    if ((Bits = LBits[LengthNumber]) > 0)
                    {
                        Length += Utility.URShift(GetBits(), (16 - Bits));
                        AddBits(Bits);
                    }
                    insertLastMatch(Length, Distance);
                    copyString(Length, Distance);
                    continue;
                }
                if (Number < 272)
                {
                    int Distance = SDDecode[Number -= 263] + 1;
                    if ((Bits = SDBits[Number]) > 0)
                    {
                        Distance += Utility.URShift(GetBits(), (16 - Bits));
                        AddBits(Bits);
                    }
                    insertOldDist(Distance);
                    insertLastMatch(2, Distance);
                    copyString(2, Distance);
                    continue;
                }
            }
            UnpWriteBuf();
        }
示例#7
0
        private void unpack29(bool solid)
        {
            int  num5;
            bool flag2;

            int[]  numArray = new int[60];
            byte[] buffer   = new byte[60];
            if (numArray[1] == 0)
            {
                int num2  = 0;
                int num3  = 0;
                int index = 0;
                num5 = 0;
                while (num5 < DBitLengthCounts.Length)
                {
                    int num6 = DBitLengthCounts[num5];
                    int num7 = 0;
                    while (num7 < num6)
                    {
                        numArray[index] = num2;
                        buffer[index]   = (byte)num3;
                        num7++;
                        index++;
                        num2 += ((int)1) << num3;
                    }
                    num5++;
                    num3++;
                }
            }
            this.fileExtracted = true;
            if (!base.suspended)
            {
                this.unpInitData(solid);
                if (!base.unpReadBuf() || !((solid && this.tablesRead) || this.readTables()))
                {
                    return;
                }
            }
            if (this.ppmError)
            {
                return;
            }
Label_0751:
            flag2        = true;
            base.unpPtr &= Compress.MAXWINMASK;
            if ((base.inAddr <= base.readBorder) || base.unpReadBuf())
            {
                int num10;
                int num11;
                if ((((base.wrPtr - base.unpPtr) & Compress.MAXWINMASK) < 260) && (base.wrPtr != base.unpPtr))
                {
                    this.UnpWriteBuf();
                    if (base.destUnpSize <= 0L)
                    {
                        return;
                    }
                    if (base.suspended)
                    {
                        this.fileExtracted = false;
                        return;
                    }
                }
                if (this.unpBlockType == BlockTypes.BLOCK_PPM)
                {
                    int num8 = this.ppm.decodeChar();
                    if (num8 == -1)
                    {
                        this.ppmError = true;
                        goto Label_0759;
                    }
                    if (num8 == this.ppmEscChar)
                    {
                        switch (this.ppm.decodeChar())
                        {
                        case 0:
                            if (this.readTables())
                            {
                                goto Label_0751;
                            }
                            goto Label_0759;

                        case 2:
                        case -1:
                            goto Label_0759;

                        case 3:
                            if (this.readVMCodePPM())
                            {
                                goto Label_0751;
                            }
                            goto Label_0759;

                        case 4:
                        {
                            num10 = 0;
                            num11 = 0;
                            bool flag = false;
                            for (num5 = 0; (num5 < 4) && !flag; num5++)
                            {
                                int num12 = this.ppm.decodeChar();
                                if (num12 == -1)
                                {
                                    flag = true;
                                }
                                else if (num5 == 3)
                                {
                                    num11 = num12 & 0xff;
                                }
                                else
                                {
                                    num10 = (num10 << 8) + (num12 & 0xff);
                                }
                            }
                            if (flag)
                            {
                                goto Label_0759;
                            }
                            this.copyString(num11 + 0x20, num10 + 2);
                            goto Label_0751;
                        }

                        case 5:
                            num11 = this.ppm.decodeChar();
                            if (num11 == -1)
                            {
                                goto Label_0759;
                            }
                            this.copyString(num11 + 4, 1);
                            goto Label_0751;
                        }
                    }
                    base.window[base.unpPtr++] = (byte)num8;
                }
                else
                {
                    int num13 = UnpackUtility.decodeNumber(this, base.LD);
                    if (num13 < 0x100)
                    {
                        base.window[base.unpPtr++] = (byte)num13;
                    }
                    else
                    {
                        int num;
                        if (num13 >= 0x10f)
                        {
                            num11 = Unpack20.LDecode[num13 -= 0x10f] + 3;
                            num   = Unpack20.LBits[num13];
                            if (num > 0)
                            {
                                num11 += Utility.URShift(base.GetBits(), (int)(0x10 - num));
                                base.AddBits(num);
                            }
                            int num14 = UnpackUtility.decodeNumber(this, base.DD);
                            num10 = numArray[num14] + 1;
                            num   = buffer[num14];
                            if (num > 0)
                            {
                                if (num14 > 9)
                                {
                                    if (num > 4)
                                    {
                                        num10 += Utility.URShift(base.GetBits(), (int)(20 - num)) << 4;
                                        base.AddBits(num - 4);
                                    }
                                    if (this.lowDistRepCount > 0)
                                    {
                                        this.lowDistRepCount--;
                                        num10 += this.prevLowDist;
                                    }
                                    else
                                    {
                                        int num15 = UnpackUtility.decodeNumber(this, base.LDD);
                                        if (num15 == 0x10)
                                        {
                                            this.lowDistRepCount = 15;
                                            num10 += this.prevLowDist;
                                        }
                                        else
                                        {
                                            num10           += num15;
                                            this.prevLowDist = num15;
                                        }
                                    }
                                }
                                else
                                {
                                    num10 += Utility.URShift(base.GetBits(), (int)(0x10 - num));
                                    base.AddBits(num);
                                }
                            }
                            if (num10 >= 0x2000)
                            {
                                num11++;
                                if (num10 >= 0x40000L)
                                {
                                    num11++;
                                }
                            }
                            this.insertOldDist(num10);
                            this.insertLastMatch(num11, num10);
                            this.copyString(num11, num10);
                        }
                        else
                        {
                            switch (num13)
                            {
                            case 0x100:
                                if (this.readEndOfBlock())
                                {
                                    goto Label_0751;
                                }
                                goto Label_0759;

                            case 0x101:
                                if (this.readVMCode())
                                {
                                    goto Label_0751;
                                }
                                goto Label_0759;

                            case 0x102:
                                if (base.lastLength != 0)
                                {
                                    this.copyString(base.lastLength, base.lastDist);
                                }
                                goto Label_0751;
                            }
                            if (num13 < 0x107)
                            {
                                int num16 = num13 - 0x103;
                                num10 = base.oldDist[num16];
                                for (num5 = num16; num5 > 0; num5--)
                                {
                                    base.oldDist[num5] = base.oldDist[num5 - 1];
                                }
                                base.oldDist[0] = num10;
                                int num17 = UnpackUtility.decodeNumber(this, base.RD);
                                num11 = Unpack20.LDecode[num17] + 2;
                                num   = Unpack20.LBits[num17];
                                if (num > 0)
                                {
                                    num11 += Utility.URShift(base.GetBits(), (int)(0x10 - num));
                                    base.AddBits(num);
                                }
                                this.insertLastMatch(num11, num10);
                                this.copyString(num11, num10);
                            }
                            else if (num13 < 0x110)
                            {
                                num10 = Unpack20.SDDecode[num13 -= 0x107] + 1;
                                num   = Unpack20.SDBits[num13];
                                if (num > 0)
                                {
                                    num10 += Utility.URShift(base.GetBits(), (int)(0x10 - num));
                                    base.AddBits(num);
                                }
                                this.insertOldDist(num10);
                                this.insertLastMatch(2, num10);
                                this.copyString(2, num10);
                            }
                        }
                    }
                }
                goto Label_0751;
            }
Label_0759:
            this.UnpWriteBuf();
        }
示例#8
0
        private bool readTables()
        {
            int num2;

            byte[] lenTab  = new byte[20];
            byte[] buffer2 = new byte[Compress.HUFF_TABLE_SIZE];
            if ((base.inAddr > (base.readTop - 0x19)) && !base.unpReadBuf())
            {
                return(false);
            }
            base.AddBits((8 - base.inBit) & 7);
            long num = base.GetBits() & -1;

            if ((num & 0x8000L) != 0L)
            {
                this.unpBlockType = BlockTypes.BLOCK_PPM;
                return(this.ppm.decodeInit(this, this.ppmEscChar));
            }
            this.unpBlockType    = BlockTypes.BLOCK_LZ;
            this.prevLowDist     = 0;
            this.lowDistRepCount = 0;
            if ((num & 0x4000L) == 0L)
            {
                Utility.Fill <byte>(this.unpOldTable, 0);
            }
            base.AddBits(2);
            for (num2 = 0; num2 < 20; num2++)
            {
                int num3 = Utility.URShift(base.GetBits(), 12) & 0xff;
                base.AddBits(4);
                if (num3 == 15)
                {
                    int num4 = Utility.URShift(base.GetBits(), 12) & 0xff;
                    base.AddBits(4);
                    if (num4 == 0)
                    {
                        lenTab[num2] = 15;
                    }
                    else
                    {
                        num4 += 2;
                        while ((num4-- > 0) && (num2 < lenTab.Length))
                        {
                            lenTab[num2++] = 0;
                        }
                        num2--;
                    }
                }
                else
                {
                    lenTab[num2] = (byte)num3;
                }
            }
            UnpackUtility.makeDecodeTables(lenTab, 0, base.BD, 20);
            int num5 = Compress.HUFF_TABLE_SIZE;

            num2 = 0;
            while (num2 < num5)
            {
                if ((base.inAddr > (base.readTop - 5)) && !base.unpReadBuf())
                {
                    return(false);
                }
                int num6 = this.decodeNumber(base.BD);
                if (num6 < 0x10)
                {
                    buffer2[num2] = (byte)((num6 + this.unpOldTable[num2]) & 15);
                    num2++;
                }
                else
                {
                    int num7;
                    if (num6 < 0x12)
                    {
                        if (num6 == 0x10)
                        {
                            num7 = Utility.URShift(base.GetBits(), 13) + 3;
                            base.AddBits(3);
                        }
                        else
                        {
                            num7 = Utility.URShift(base.GetBits(), 9) + 11;
                            base.AddBits(7);
                        }
                        while ((num7-- > 0) && (num2 < num5))
                        {
                            buffer2[num2] = buffer2[num2 - 1];
                            num2++;
                        }
                    }
                    else
                    {
                        if (num6 == 0x12)
                        {
                            num7 = Utility.URShift(base.GetBits(), 13) + 3;
                            base.AddBits(3);
                        }
                        else
                        {
                            num7 = Utility.URShift(base.GetBits(), 9) + 11;
                            base.AddBits(7);
                        }
                        while ((num7-- > 0) && (num2 < num5))
                        {
                            buffer2[num2++] = 0;
                        }
                    }
                }
            }
            this.tablesRead = true;
            if (base.inAddr > base.readTop)
            {
                return(false);
            }
            UnpackUtility.makeDecodeTables(buffer2, 0, base.LD, 0x12b);
            UnpackUtility.makeDecodeTables(buffer2, 0x12b, base.DD, 60);
            UnpackUtility.makeDecodeTables(buffer2, 0x167, base.LDD, 0x11);
            UnpackUtility.makeDecodeTables(buffer2, 0x178, base.RD, 0x1c);
            Buffer.BlockCopy(buffer2, 0, this.unpOldTable, 0, this.unpOldTable.Length);
            return(true);
        }