1baa3858d3f5d128a5c8466b700098109edcad5f2repo syncpackage SevenZip.Compression.RangeCoder; 2baa3858d3f5d128a5c8466b700098109edcad5f2repo syncimport java.io.IOException; 3baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 4baa3858d3f5d128a5c8466b700098109edcad5f2repo syncpublic class Encoder 5baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 6baa3858d3f5d128a5c8466b700098109edcad5f2repo sync static final int kTopMask = ~((1 << 24) - 1); 7baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 8baa3858d3f5d128a5c8466b700098109edcad5f2repo sync static final int kNumBitModelTotalBits = 11; 9baa3858d3f5d128a5c8466b700098109edcad5f2repo sync static final int kBitModelTotal = (1 << kNumBitModelTotalBits); 10baa3858d3f5d128a5c8466b700098109edcad5f2repo sync static final int kNumMoveBits = 5; 11baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 12baa3858d3f5d128a5c8466b700098109edcad5f2repo sync java.io.OutputStream Stream; 13baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 14baa3858d3f5d128a5c8466b700098109edcad5f2repo sync long Low; 15baa3858d3f5d128a5c8466b700098109edcad5f2repo sync int Range; 16baa3858d3f5d128a5c8466b700098109edcad5f2repo sync int _cacheSize; 17baa3858d3f5d128a5c8466b700098109edcad5f2repo sync int _cache; 18baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 19baa3858d3f5d128a5c8466b700098109edcad5f2repo sync long _position; 20baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 21baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public void SetStream(java.io.OutputStream stream) 22baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 23baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Stream = stream; 24baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 25baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 26baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public void ReleaseStream() 27baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 28baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Stream = null; 29baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 30baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 31baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public void Init() 32baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 33baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _position = 0; 34baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Low = 0; 35baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Range = -1; 36baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _cacheSize = 1; 37baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _cache = 0; 38baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 39baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 40baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public void FlushData() throws IOException 41baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 42baa3858d3f5d128a5c8466b700098109edcad5f2repo sync for (int i = 0; i < 5; i++) 43baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ShiftLow(); 44baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 45baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 46baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public void FlushStream() throws IOException 47baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 48baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Stream.flush(); 49baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 50baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 51baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public void ShiftLow() throws IOException 52baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 53baa3858d3f5d128a5c8466b700098109edcad5f2repo sync int LowHi = (int)(Low >>> 32); 54baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (LowHi != 0 || Low < 0xFF000000L) 55baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 56baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _position += _cacheSize; 57baa3858d3f5d128a5c8466b700098109edcad5f2repo sync int temp = _cache; 58baa3858d3f5d128a5c8466b700098109edcad5f2repo sync do 59baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 60baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Stream.write(temp + LowHi); 61baa3858d3f5d128a5c8466b700098109edcad5f2repo sync temp = 0xFF; 62baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 63baa3858d3f5d128a5c8466b700098109edcad5f2repo sync while(--_cacheSize != 0); 64baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _cache = (((int)Low) >>> 24); 65baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 66baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _cacheSize++; 67baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Low = (Low & 0xFFFFFF) << 8; 68baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 69baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 70baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public void EncodeDirectBits(int v, int numTotalBits) throws IOException 71baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 72baa3858d3f5d128a5c8466b700098109edcad5f2repo sync for (int i = numTotalBits - 1; i >= 0; i--) 73baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 74baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Range >>>= 1; 75baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (((v >>> i) & 1) == 1) 76baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Low += Range; 77baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if ((Range & Encoder.kTopMask) == 0) 78baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 79baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Range <<= 8; 80baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ShiftLow(); 81baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 82baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 83baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 84baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 85baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 86baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public long GetProcessedSizeAdd() 87baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 88baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return _cacheSize + _position + 4; 89baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 90baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 91baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 92baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 93baa3858d3f5d128a5c8466b700098109edcad5f2repo sync static final int kNumMoveReducingBits = 2; 94baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public static final int kNumBitPriceShiftBits = 6; 95baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 96baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public static void InitBitModels(short []probs) 97baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 98baa3858d3f5d128a5c8466b700098109edcad5f2repo sync for (int i = 0; i < probs.length; i++) 99baa3858d3f5d128a5c8466b700098109edcad5f2repo sync probs[i] = (kBitModelTotal >>> 1); 100baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 101baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 102baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public void Encode(short []probs, int index, int symbol) throws IOException 103baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 104baa3858d3f5d128a5c8466b700098109edcad5f2repo sync int prob = probs[index]; 105baa3858d3f5d128a5c8466b700098109edcad5f2repo sync int newBound = (Range >>> kNumBitModelTotalBits) * prob; 106baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (symbol == 0) 107baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 108baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Range = newBound; 109baa3858d3f5d128a5c8466b700098109edcad5f2repo sync probs[index] = (short)(prob + ((kBitModelTotal - prob) >>> kNumMoveBits)); 110baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 111baa3858d3f5d128a5c8466b700098109edcad5f2repo sync else 112baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 113baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Low += (newBound & 0xFFFFFFFFL); 114baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Range -= newBound; 115baa3858d3f5d128a5c8466b700098109edcad5f2repo sync probs[index] = (short)(prob - ((prob) >>> kNumMoveBits)); 116baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 117baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if ((Range & kTopMask) == 0) 118baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 119baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Range <<= 8; 120baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ShiftLow(); 121baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 122baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 123baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 124baa3858d3f5d128a5c8466b700098109edcad5f2repo sync private static int[] ProbPrices = new int[kBitModelTotal >>> kNumMoveReducingBits]; 125baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 126baa3858d3f5d128a5c8466b700098109edcad5f2repo sync static 127baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 128baa3858d3f5d128a5c8466b700098109edcad5f2repo sync int kNumBits = (kNumBitModelTotalBits - kNumMoveReducingBits); 129baa3858d3f5d128a5c8466b700098109edcad5f2repo sync for (int i = kNumBits - 1; i >= 0; i--) 130baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 131baa3858d3f5d128a5c8466b700098109edcad5f2repo sync int start = 1 << (kNumBits - i - 1); 132baa3858d3f5d128a5c8466b700098109edcad5f2repo sync int end = 1 << (kNumBits - i); 133baa3858d3f5d128a5c8466b700098109edcad5f2repo sync for (int j = start; j < end; j++) 134baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ProbPrices[j] = (i << kNumBitPriceShiftBits) + 135baa3858d3f5d128a5c8466b700098109edcad5f2repo sync (((end - j) << kNumBitPriceShiftBits) >>> (kNumBits - i - 1)); 136baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 137baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 138baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 139baa3858d3f5d128a5c8466b700098109edcad5f2repo sync static public int GetPrice(int Prob, int symbol) 140baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 141baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return ProbPrices[(((Prob - symbol) ^ ((-symbol))) & (kBitModelTotal - 1)) >>> kNumMoveReducingBits]; 142baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 143baa3858d3f5d128a5c8466b700098109edcad5f2repo sync static public int GetPrice0(int Prob) 144baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 145baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return ProbPrices[Prob >>> kNumMoveReducingBits]; 146baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 147baa3858d3f5d128a5c8466b700098109edcad5f2repo sync static public int GetPrice1(int Prob) 148baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 149baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return ProbPrices[(kBitModelTotal - Prob) >>> kNumMoveReducingBits]; 150baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 151baa3858d3f5d128a5c8466b700098109edcad5f2repo sync} 152