public byte[] run(byte[] data) { res = new List <byte>(); res.Add(2); BinHelper.writeUint32(res, (uint)data.Length); bits = 9; int dpos = 0; writeBits(data[dpos++]); addMatch(data, 0, 2); int nmatch = 0; while (dpos < data.Length) { int sz = findMatch(data, dpos); dpos += sz; if (matches.Count == 0xEFE) { if (sz < 2) { nmatch++; } else { nmatch = 0; } if (exc == bits - 3 || exc == bits - 4 && nmatch > 5) { clear(); nmatch = 0; } } } if (bpos != 0) { writeBits(0, 8 - bpos); } return(res.ToArray()); }
public byte[] run(byte[] data) { this.data = data; if (data[0] != 2) { throw new Exception("Unknown compression type"); } UInt32 sz = BinHelper.readUInt32(data, 1); byte[] res = new byte[sz]; dpos = 5; int rpos = 0; List <int> ofs = new List <int>(); List <int> cnt = new List <int>(); int bits = 9; int ocnt = 1; while (rpos < sz) { int r = readBits(bits); if (r < 0x100) { if (ofs.Count < 0x1000) { ofs.Add(rpos); cnt.Add(2); } res[rpos++] = (byte)r; } else if (r > 0x100) { if (r <= 0x100 + ofs.Count) { int ps = ofs[r - 0x100 - 1]; int c = cnt[r - 0x100 - 1]; if (ofs.Count < 0x1000) { ofs.Add(rpos); cnt.Add(c + 1); } for (int i = 0; i < c; i++) { res[rpos++] = res[ps++]; if (rpos == res.Length) { break; } } } else { throw new NotImplementedException(); } } else { dpos += bits - exc; bits = 9; ocnt = 1; ofs.Clear(); cnt.Clear(); bitbuf = 0; bpos = 0; exc = 0; } if (ofs.Count >= ocnt * 0x100 && ocnt < 0x0F) { bits++; ocnt <<= 1; ocnt++; } } return(res); }