bbb.cpp
Upload User: baoenjiang
Upload Date: 2021-07-11
Package Size: 102k
Code Size: 33k
Development Platform:

Visual C++

  1. /* bbb.cpp - big block BWT compressor version 1, Aug. 31, 2006.
  2. (C) 2006, Matt Mahoney, mmahoney (at) cs.fit.edu
  3. This is free software under GPL, http://www.gnu.org/licenses/gpl.txt
  4. To compress/decompress: bbb command input output
  5. Commands are concatenated, e.g. 
  6.   bbb cfqm10 in out = compress (c) in fast mode (f), quiet (q), 10 MiB block size.
  7.   bbb df = decompress in fast mode.
  8. Commands:
  9.   c = compress (default).
  10.   d = decompress.
  11.   f = fast mode, needs 5x blocksize in memory, default is 1.25x blocksize.
  12.   bN, kN, mN = blocksize N bytes, KiB, MiB (compression only), default = m4.
  13.   q = quiet (no output except for errors).
  14. The compression format is a memory efficient Burrows-Wheeler Transform (BWT) followed 
  15. by a PAQ-like compression using a single order-0 context (no mixing) followed by 5 more
  16. adaptive stages with low order contexts, and bitwise arithmetic coding.
  17. LOW MEMORY BWT
  18. The BWT is able to sort blocks as large as 80% of available memory in slow
  19. mode or 20% in fast mode.  Using larger blocks generally improves compression,
  20. especially for text.  In fast mode, the bytes of a block are sorted by their
  21. right context (with wrap around) before compression with an order 0 model.  
  22. For example, the block "banana" is sorted as follows:
  23.            sorted  
  24.      block context  T
  25.      ----- ------- ---
  26.   0    n    abana   a
  27.   1    n    anaba   a
  28.   2    b    anana   a  <- p (starting point for inverse transform)
  29.   3    a    banan   b
  30.   4    a    nanab   n
  31.   5    a    naban   n
  32. After decompression, the transform is inverted by making a sorted copy of the
  33. block, T, then traversing the block as follows: from position p, find the
  34. next byte in T, then find the matching byte in the block with the same rank,
  35. i.e. if t[p] = the j'th occurrence of byte c, then set p = such that
  36. block[p] = the j'th occurrence of c.  Repeat n times, where n = block size.
  37. The initial value of p is the sorted position of the original first byte,
  38. which must be sent by the compressor.
  39.   Start at p = 2 (transmitted by the compressor).
  40.   Output block[2] = 'b'
  41.   T[2] contains the third 'a'.
  42.   Find the third 'a' in block at position 5.
  43.   Set p = 5.
  44.   output block[5] = 'a'
  45.   T[5] contains the second 'n'
  46.   Find the second 'n' in block at position 1.
  47.   Set p = 1.
  48.   etc...
  49. In fast mode, an array of n pointers into the block of n bytes is sorted
  50. using std::stable_sort() (normally quicksort).  Each pointer uses 4 bytes
  51. of memory, so the program needs 5n total memory.
  52. In slow mode, the block is divided into 16 subblocks and the pointers are
  53. sorted as usual.  Then the pointers are written to 16 temporary files and
  54. merged.  This is fast because the pointers are accessed sequentially.
  55. This requires n/4 bytes for the pointers, plus the original block (5n/4
  56. total), and 4n bytes on disk.
  57. To invert the transform in fast mode, a linked list is built, then traversed,
  58. Note that T can be represented by just the cumulative counts of lexicographically
  59. preceding values (a=0, b=3, c=4, d=4,..., n=4, o=6, ...).  Then the list is 
  60. built by scanning the block and keeping a count of each value.
  61.   block  ptr
  62.   -----  ---
  63.     n     0 -> 4 (count n=5)
  64.     n     1 -> 5 (count n=6)
  65.     b     2 -> 3 (count b=4)  <- p
  66.     a     3 -> 0 (count a=1)
  67.     a     4 -> 1 (count a=2)
  68.     a     5 -> 2 (count a=3)
  69. Then the list is traversed:
  70.   2 -> 3 -> 0 -> 4 -> 1 -> 5
  71.   b    a    n    a    n    a
  72. The linked list requires 4 bytes for each pointer, so again it requires 5n
  73. memory.  In slow mode, instead of building a list, the program searches the
  74. block.  If block[p] is the j'th occurrence of c in T, then the program must
  75. scan the block from the beginning and count j occurrences of c.  To make the
  76. scan faster, the program builds an index of every 16'th occurrence of c, then
  77. searches linearly from there.  The steps are:
  78.   p = start (transmitted by compressor)
  79.   Repeat n times
  80.     Output block[p]
  81.     Find c such that count[c] <= p < count[c+1] by binary search on count[]
  82.     Let j = p - count[c]
  83.     p = index[c][j/16]
  84.     scan p forward (j mod 16) occurrences of c in block
  85. A 2-D index would have variable row lengths, so it is organized into a 1 
  86. dimensional array with each row c having length (count[c+1]-count[c])/16 + 1,
  87. which is at most n/16 + 256 elements.  Each pointer is 4 bytes, so memory usage
  88. is about 5n/4 including the block.  No temporary files are used.
  89. ENTROPY CODING
  90. BWT data is best coded with an order 0 model.  The transformed text tends to
  91. have long runs of identical bytes (e.g. "nnbaaa").  The BWT data is modeled
  92. with a modified PAQ with just one context (no mixing) followed by a 5 stage
  93. SSE (APM) and bitwise arithmetic coding.  Modeling typically takes about
  94. as much time as sorting and unsorting in slow mode.  The model uses about 5 MB
  95. memory.
  96. The order 0 model consists of a mapping: 
  97.              order 1, 2, 3 contexts ----------+
  98.                                               V
  99.   order 0 context -> bit history -> p -> APM chain -> arithmetic coder
  100.                   t1             sm
  101. Bits are coded one at a time.  The arithmetic coder maintains a range
  102. [lo, hi), initially [0, 1) and repeatedly subdivides the range in proportion
  103. to p(0), p(1), the next bit probabilites predicted by the model.  The final
  104. output is the shortest base 256 number x such that lo <= x < hi.  As the leading
  105. bytes of x become known, they are output.  To decompress, the model predictions
  106. are repeated as during compression, then the actual bit is determined by which
  107. half of the subrange contains x.
  108. The model inputs a bytewise order 0 context consisting of the last 0 to 7 bits
  109. of the current byte, plus the number of bits.  There are a total of 255 possible
  110. bitwise contexts.  For each context, a table (t1) maintains an 8 bit state
  111. representing the history of 0 and 1 bits previously seen.  This history is mapped
  112. by another table (a StateMap sm) to a probability, p, that the next bit will be 1.
  113. This table is adaptive: after each prediction, the mapping (state -> p) is adjusted
  114. to improve the last prediction.
  115. The output of the StateMap is passed through a series of 6 more adaptive tables, 
  116. (Adaptive Probability Maps, or APM) each of which maps a context and the input 
  117. probability to an output probability.  The input probability is interpolated between
  118. 33 bins on a nonlinear scale with smaller bins near 0 and 1.  After each prediction,
  119. the corresponding table entries on both sides of p are adjusted to improve the
  120. last prediction.  The APM chain is like this:
  121.       + A11 ->+            +--->---+ +--->---+
  122.       |       |            |       | |       |
  123.   p ->+       +-> A2 -> A3 +-> A4 -+-+-> A5 -+-> Encoder
  124.       |       |
  125.       + A12 ->+
  126. A11 and A12 both take c0 (the preceding bits of the current byte) as additional 
  127. context, but one is fast adapting and the other is slow adapting.  Their 
  128. outputs are averaged.
  129. A2 is an order 1 context (previous byte and current partial byte).
  130. A3 takes the previous (but not current) byte as context, plus 2 bits that depend
  131. on the current run length (0, 1, 2-3, or 4+), the number of times the last
  132. byte was repeated.
  133. A4 takes the current byte and the low 5 bits of the second byte back.
  134. The output is averaged with 3/4 weight to the A3 output with 1/4 weight.
  135. A5 takes a 14 bit hash of an order 3 context (last 3 bytes plus current partial
  136. byte) and is averaged with 1/2 weight to the A4 output.
  137. The StateMap, state table, APM, Encoder, and associated code (Array, squash(), 
  138. stretch()) are taken from PAQ8 with minor non-functional changes (e.g. removing
  139. global context).
  140. */
  141. #include <cstdio>
  142. #include <cstdlib>
  143. #include <cstring>
  144. #include <ctime>
  145. #include <algorithm>
  146. #define NDEBUG  // remove for debugging
  147. #include <cassert>
  148. using namespace std;
  149. // 8, 16, 32 bit unsigned types
  150. typedef unsigned char U8;
  151. typedef unsigned short U16;
  152. typedef unsigned int U32;
  153. //////////////////////////// Array ////////////////////////////
  154. // Array<T, ALIGN> a(n); creates n elements of T initialized to 0 bits.
  155. // Constructors for T are not called.
  156. // Indexing is bounds checked if assertions are on.
  157. // a.size() returns n.
  158. // a.resize(n) changes size to n, padding with 0 bits or truncating.
  159. // Copy and assignment are not supported.
  160. // Memory is aligned on a ALIGN byte boundary (power of 2), default is none.
  161. template <class T, int ALIGN=0> class Array {
  162. private:
  163.   int n;     // user size
  164.   int reserved;  // actual size
  165.   char *ptr; // allocated memory, zeroed
  166.   T* data;   // start of n elements of aligned data
  167.   void create(int i);  // create with size i
  168. public:
  169.   explicit Array(int i=0) {create(i);}
  170.   ~Array();
  171.   T& operator[](int i) {
  172. #ifndef NDEBUG
  173.     if (i<0 || i>=n) fprintf(stderr, "%d out of bounds %dn", i, n), exit(1);
  174. #endif
  175.     return data[i];
  176.   }
  177.   const T& operator[](int i) const {
  178. #ifndef NDEBUG
  179.     if (i<0 || i>=n) fprintf(stderr, "%d out of bounds %dn", i, n), exit(1);
  180. #endif
  181.     return data[i];
  182.   }
  183.   int size() const {return n;}
  184.   void resize(int i);  // change size to i
  185. private:
  186.   Array(const Array&);  // no copy or assignment
  187.   Array& operator=(const Array&);
  188. };
  189. template<class T, int ALIGN> void Array<T, ALIGN>::resize(int i) {
  190.   if (i<=reserved) {
  191.     n=i;
  192.     return;
  193.   }
  194.   char *saveptr=ptr;
  195.   T *savedata=data;
  196.   int saven=n;
  197.   create(i);
  198.   if (savedata && saveptr) {
  199.     memcpy(data, savedata, sizeof(T)*min(i, saven));
  200.     free(saveptr);
  201.   }
  202. }
  203. template<class T, int ALIGN> void Array<T, ALIGN>::create(int i) {
  204.   n=reserved=i;
  205.   if (i<=0) {
  206.     data=0;
  207.     ptr=0;
  208.     return;
  209.   }
  210.   const int sz=ALIGN+n*sizeof(T);
  211.   ptr = (char*)calloc(sz, 1);
  212.   if (!ptr) fprintf(stderr, "Out of memoryn"), exit(1);
  213.   data = (ALIGN ? (T*)(ptr+ALIGN-(((long)ptr)&(ALIGN-1))) : (T*)ptr);
  214.   assert((char*)data>=ptr && (char*)data<=ptr+ALIGN);
  215. }
  216. template<class T, int ALIGN> Array<T, ALIGN>::~Array() {
  217.   free(ptr);
  218. }
  219. ///////////////////////// state table ////////////////////////
  220. // State table:
  221. //   nex(state, 0) = next state if bit y is 0, 0 <= state < 256
  222. //   nex(state, 1) = next state if bit y is 1
  223. //   nex(state, 2) = number of zeros in bit history represented by state
  224. //   nex(state, 3) = number of ones represented
  225. //
  226. // States represent a bit history within some context.
  227. // State 0 is the starting state (no bits seen).
  228. // States 1-30 represent all possible sequences of 1-4 bits.
  229. // States 31-252 represent a pair of counts, (n0,n1), the number
  230. //   of 0 and 1 bits respectively.  If n0+n1 < 16 then there are
  231. //   two states for each pair, depending on if a 0 or 1 was the last
  232. //   bit seen.
  233. // If n0 and n1 are too large, then there is no state to represent this
  234. // pair, so another state with about the same ratio of n0/n1 is substituted.
  235. // Also, when a bit is observed and the count of the opposite bit is large,
  236. // then part of this count is discarded to favor newer data over old.
  237. static const U8 State_table[256][4]={
  238.   {  1,  2, 0, 0},{  3,  5, 1, 0},{  4,  6, 0, 1},{  7, 10, 2, 0}, // 0-3
  239.   {  8, 12, 1, 1},{  9, 13, 1, 1},{ 11, 14, 0, 2},{ 15, 19, 3, 0}, // 4-7
  240.   { 16, 23, 2, 1},{ 17, 24, 2, 1},{ 18, 25, 2, 1},{ 20, 27, 1, 2}, // 8-11
  241.   { 21, 28, 1, 2},{ 22, 29, 1, 2},{ 26, 30, 0, 3},{ 31, 33, 4, 0}, // 12-15
  242.   { 32, 35, 3, 1},{ 32, 35, 3, 1},{ 32, 35, 3, 1},{ 32, 35, 3, 1}, // 16-19
  243.   { 34, 37, 2, 2},{ 34, 37, 2, 2},{ 34, 37, 2, 2},{ 34, 37, 2, 2}, // 20-23
  244.   { 34, 37, 2, 2},{ 34, 37, 2, 2},{ 36, 39, 1, 3},{ 36, 39, 1, 3}, // 24-27
  245.   { 36, 39, 1, 3},{ 36, 39, 1, 3},{ 38, 40, 0, 4},{ 41, 43, 5, 0}, // 28-31
  246.   { 42, 45, 4, 1},{ 42, 45, 4, 1},{ 44, 47, 3, 2},{ 44, 47, 3, 2}, // 32-35
  247.   { 46, 49, 2, 3},{ 46, 49, 2, 3},{ 48, 51, 1, 4},{ 48, 51, 1, 4}, // 36-39
  248.   { 50, 52, 0, 5},{ 53, 43, 6, 0},{ 54, 57, 5, 1},{ 54, 57, 5, 1}, // 40-43
  249.   { 56, 59, 4, 2},{ 56, 59, 4, 2},{ 58, 61, 3, 3},{ 58, 61, 3, 3}, // 44-47
  250.   { 60, 63, 2, 4},{ 60, 63, 2, 4},{ 62, 65, 1, 5},{ 62, 65, 1, 5}, // 48-51
  251.   { 50, 66, 0, 6},{ 67, 55, 7, 0},{ 68, 57, 6, 1},{ 68, 57, 6, 1}, // 52-55
  252.   { 70, 73, 5, 2},{ 70, 73, 5, 2},{ 72, 75, 4, 3},{ 72, 75, 4, 3}, // 56-59
  253.   { 74, 77, 3, 4},{ 74, 77, 3, 4},{ 76, 79, 2, 5},{ 76, 79, 2, 5}, // 60-63
  254.   { 62, 81, 1, 6},{ 62, 81, 1, 6},{ 64, 82, 0, 7},{ 83, 69, 8, 0}, // 64-67
  255.   { 84, 71, 7, 1},{ 84, 71, 7, 1},{ 86, 73, 6, 2},{ 86, 73, 6, 2}, // 68-71
  256.   { 44, 59, 5, 3},{ 44, 59, 5, 3},{ 58, 61, 4, 4},{ 58, 61, 4, 4}, // 72-75
  257.   { 60, 49, 3, 5},{ 60, 49, 3, 5},{ 76, 89, 2, 6},{ 76, 89, 2, 6}, // 76-79
  258.   { 78, 91, 1, 7},{ 78, 91, 1, 7},{ 80, 92, 0, 8},{ 93, 69, 9, 0}, // 80-83
  259.   { 94, 87, 8, 1},{ 94, 87, 8, 1},{ 96, 45, 7, 2},{ 96, 45, 7, 2}, // 84-87
  260.   { 48, 99, 2, 7},{ 48, 99, 2, 7},{ 88,101, 1, 8},{ 88,101, 1, 8}, // 88-91
  261.   { 80,102, 0, 9},{103, 69,10, 0},{104, 87, 9, 1},{104, 87, 9, 1}, // 92-95
  262.   {106, 57, 8, 2},{106, 57, 8, 2},{ 62,109, 2, 8},{ 62,109, 2, 8}, // 96-99
  263.   { 88,111, 1, 9},{ 88,111, 1, 9},{ 80,112, 0,10},{113, 85,11, 0}, // 100-103
  264.   {114, 87,10, 1},{114, 87,10, 1},{116, 57, 9, 2},{116, 57, 9, 2}, // 104-107
  265.   { 62,119, 2, 9},{ 62,119, 2, 9},{ 88,121, 1,10},{ 88,121, 1,10}, // 108-111
  266.   { 90,122, 0,11},{123, 85,12, 0},{124, 97,11, 1},{124, 97,11, 1}, // 112-115
  267.   {126, 57,10, 2},{126, 57,10, 2},{ 62,129, 2,10},{ 62,129, 2,10}, // 116-119
  268.   { 98,131, 1,11},{ 98,131, 1,11},{ 90,132, 0,12},{133, 85,13, 0}, // 120-123
  269.   {134, 97,12, 1},{134, 97,12, 1},{136, 57,11, 2},{136, 57,11, 2}, // 124-127
  270.   { 62,139, 2,11},{ 62,139, 2,11},{ 98,141, 1,12},{ 98,141, 1,12}, // 128-131
  271.   { 90,142, 0,13},{143, 95,14, 0},{144, 97,13, 1},{144, 97,13, 1}, // 132-135
  272.   { 68, 57,12, 2},{ 68, 57,12, 2},{ 62, 81, 2,12},{ 62, 81, 2,12}, // 136-139
  273.   { 98,147, 1,13},{ 98,147, 1,13},{100,148, 0,14},{149, 95,15, 0}, // 140-143
  274.   {150,107,14, 1},{150,107,14, 1},{108,151, 1,14},{108,151, 1,14}, // 144-147
  275.   {100,152, 0,15},{153, 95,16, 0},{154,107,15, 1},{108,155, 1,15}, // 148-151
  276.   {100,156, 0,16},{157, 95,17, 0},{158,107,16, 1},{108,159, 1,16}, // 152-155
  277.   {100,160, 0,17},{161,105,18, 0},{162,107,17, 1},{108,163, 1,17}, // 156-159
  278.   {110,164, 0,18},{165,105,19, 0},{166,117,18, 1},{118,167, 1,18}, // 160-163
  279.   {110,168, 0,19},{169,105,20, 0},{170,117,19, 1},{118,171, 1,19}, // 164-167
  280.   {110,172, 0,20},{173,105,21, 0},{174,117,20, 1},{118,175, 1,20}, // 168-171
  281.   {110,176, 0,21},{177,105,22, 0},{178,117,21, 1},{118,179, 1,21}, // 172-175
  282.   {110,180, 0,22},{181,115,23, 0},{182,117,22, 1},{118,183, 1,22}, // 176-179
  283.   {120,184, 0,23},{185,115,24, 0},{186,127,23, 1},{128,187, 1,23}, // 180-183
  284.   {120,188, 0,24},{189,115,25, 0},{190,127,24, 1},{128,191, 1,24}, // 184-187
  285.   {120,192, 0,25},{193,115,26, 0},{194,127,25, 1},{128,195, 1,25}, // 188-191
  286.   {120,196, 0,26},{197,115,27, 0},{198,127,26, 1},{128,199, 1,26}, // 192-195
  287.   {120,200, 0,27},{201,115,28, 0},{202,127,27, 1},{128,203, 1,27}, // 196-199
  288.   {120,204, 0,28},{205,115,29, 0},{206,127,28, 1},{128,207, 1,28}, // 200-203
  289.   {120,208, 0,29},{209,125,30, 0},{210,127,29, 1},{128,211, 1,29}, // 204-207
  290.   {130,212, 0,30},{213,125,31, 0},{214,137,30, 1},{138,215, 1,30}, // 208-211
  291.   {130,216, 0,31},{217,125,32, 0},{218,137,31, 1},{138,219, 1,31}, // 212-215
  292.   {130,220, 0,32},{221,125,33, 0},{222,137,32, 1},{138,223, 1,32}, // 216-219
  293.   {130,224, 0,33},{225,125,34, 0},{226,137,33, 1},{138,227, 1,33}, // 220-223
  294.   {130,228, 0,34},{229,125,35, 0},{230,137,34, 1},{138,231, 1,34}, // 224-227
  295.   {130,232, 0,35},{233,125,36, 0},{234,137,35, 1},{138,235, 1,35}, // 228-231
  296.   {130,236, 0,36},{237,125,37, 0},{238,137,36, 1},{138,239, 1,36}, // 232-235
  297.   {130,240, 0,37},{241,125,38, 0},{242,137,37, 1},{138,243, 1,37}, // 236-239
  298.   {130,244, 0,38},{245,135,39, 0},{246,137,38, 1},{138,247, 1,38}, // 240-243
  299.   {140,248, 0,39},{249,135,40, 0},{250, 69,39, 1},{ 80,251, 1,39}, // 244-247
  300.   {140,252, 0,40},{249,135,41, 0},{250, 69,40, 1},{ 80,251, 1,40}, // 248-251
  301.   {140,252, 0,41}};  // 253-255 are reserved
  302. #define nex(state,sel) State_table[state][sel]
  303. ///////////////////////////// Squash //////////////////////////////
  304. // return p = 1/(1 + exp(-d)), d scaled by 8 bits, p scaled by 12 bits
  305. int squash(int d) {
  306.   static const int t[33]={
  307.     1,2,3,6,10,16,27,45,73,120,194,310,488,747,1101,
  308.     1546,2047,2549,2994,3348,3607,3785,3901,3975,4022,
  309.     4050,4068,4079,4085,4089,4092,4093,4094};
  310.   if (d>2047) return 4095;
  311.   if (d<-2047) return 0;
  312.   int w=d&127;
  313.   d=(d>>7)+16;
  314.   return (t[d]*(128-w)+t[(d+1)]*w+64) >> 7;
  315. }
  316. //////////////////////////// Stretch ///////////////////////////////
  317. // Inverse of squash. d = ln(p/(1-p)), d scaled by 8 bits, p by 12 bits.
  318. // d has range -2047 to 2047 representing -8 to 8.  p has range 0 to 4095.
  319. class Stretch {
  320.   Array<short> t;
  321. public:
  322.   Stretch();
  323.   int operator()(int p) const {
  324.     assert(p>=0 && p<4096);
  325.     return t[p];
  326.   }
  327. } stretch;
  328. Stretch::Stretch(): t(4096) {
  329.   int pi=0;
  330.   for (int x=-2047; x<=2047; ++x) {  // invert squash()
  331.     int i=squash(x);
  332.     for (int j=pi; j<=i; ++j)
  333.       t[j]=x;
  334.     pi=i+1;
  335.   }
  336.   t[4095]=2047;
  337. }
  338. //////////////////////////// StateMap //////////////////////////
  339. // A StateMap maps a nonstationary counter state to a probability.
  340. // After each mapping, the mapping is adjusted to improve future
  341. // predictions.  Methods:
  342. //
  343. // sm.p(y, cx) converts state cx (0-255) to a probability (0-4095), 
  344. //   and trains by updating the previous prediction with y (0-1).
  345. // Counter state -> probability * 256
  346. class StateMap {
  347. protected:
  348.   int cxt;  // context
  349.   Array<U16> t; // 256 states -> probability * 64K
  350. public:
  351.   StateMap();
  352.   int p(int y, int cx) {
  353.     assert(cx>=0 && cx<t.size());
  354.     t[cxt]+=(y<<16)-t[cxt]+128 >> 8;
  355.     return t[cxt=cx] >> 4;
  356.   }
  357. };
  358. StateMap::StateMap(): cxt(0), t(256) {
  359.   for (int i=0; i<256; ++i) {
  360.     int n0=nex(i,2);
  361.     int n1=nex(i,3);
  362.     if (n0==0) n1*=128;
  363.     if (n1==0) n0*=128;
  364.     t[i] = 65536*(n1+1)/(n0+n1+2);
  365.   }
  366. }
  367. //////////////////////////// APM //////////////////////////////
  368. // APM maps a probability and a context into a new probability
  369. // that bit y will next be 1.  After each guess it updates
  370. // its state to improve future guesses.  Methods:
  371. //
  372. // APM a(N) creates with N contexts, uses 66*N bytes memory.
  373. // a.p(y, pr, cx, rate=8) returned adjusted probability in context cx (0 to
  374. //   N-1).  rate determines the learning rate (smaller = faster, default 8).
  375. //   Probabilities are scaled 12 bits (0-4095).  Update on last bit y (0-1).
  376. class APM {
  377.   int index;     // last p, context
  378.   const int N;   // number of contexts
  379.   Array<U16> t;  // [N][33]:  p, context -> p
  380. public:
  381.   APM(int n);
  382.   int p(int y, int pr=2048, int cxt=0, int rate=8) {
  383.     assert(pr>=0 && pr<4096 && cxt>=0 && cxt<N && rate>0 && rate<32);
  384.     pr=stretch(pr);
  385.     int g=(y<<16)+(y<<rate)-y-y;
  386.     t[index] += g-t[index] >> rate;
  387.     t[index+1] += g-t[index+1] >> rate;
  388.     const int w=pr&127;  // interpolation weight (33 points)
  389.     index=(pr+2048>>7)+cxt*33;
  390.     return t[index]*(128-w)+t[index+1]*w >> 11;
  391.   }
  392. };
  393. // maps p, cxt -> p initially
  394. APM::APM(int n): index(0), N(n), t(n*33) {
  395.   for (int i=0; i<N; ++i)
  396.     for (int j=0; j<33; ++j)
  397.       t[i*33+j] = i==0 ? squash((j-16)*128)*16 : t[j];
  398. }
  399. //////////////////////////// Predictor //////////////////////////
  400. class Predictor {
  401.   int pr;  // next return value of p() (0-4095)
  402. public:
  403.   Predictor(): pr(2048) {}
  404.   int p() const {return pr;}
  405.   void update(int y);
  406. };
  407. void Predictor::update(int y) {
  408.   static int c0=1;  // bitwise context: last 0-7 bits with a leading 1 (1-255)
  409.   static U32 c4=0;  // last 4 whole bytes, last is in low 8 bits
  410.   static int bpos=0; // number of bits in c0 (0-7)
  411.   static Array<U8> t1(256); // context -> state
  412.   static StateMap sm;  // state -> pr
  413.   static U8* cp=&t1[0];  // context pointer
  414.   static int run=0;  // count of consecutive identical bytes (0-65535)
  415.   static int runcxt=0;  // (0-3) if run is 0, 1, 2-3, 4+
  416.   static APM a11(256), a12(256), a2(65536), a3(1024), a4(8192), a5(16384);
  417.   // update model
  418.   *cp=nex(*cp, y);
  419.   // update context
  420.   c0+=c0+y;
  421.   if (++bpos==8) {
  422.     bpos=0;
  423.     c4=c4<<8|c0-256;
  424.     c0=1;
  425.     bpos=0;
  426.     if (((c4^c4>>8)&255)==0) {
  427.       if (run<65535) 
  428.         ++run;
  429.         if (run==1 || run==2 || run==4) runcxt+=256;
  430.     }
  431.     else run=0, runcxt=0;
  432.   }
  433.   // predict
  434.   cp=&t1[c0];
  435.   pr=sm.p(y, *cp);
  436.   pr=a11.p(y, pr, c0, 5)+a12.p(y, pr, c0, 9)+1>>1;
  437.   pr=a2.p(y, pr, c0|c4<<8&0xff00, 7);
  438.   pr=a3.p(y, pr, c4&255|runcxt, 8);
  439.   pr=a4.p(y, pr, c0|c4&0x1f00, 7)*3+pr+2>>2;
  440.   pr=a5.p(y, pr, c0^(c4&0xffffff)*123456791>>18, 7)+pr+1>>1;
  441. //////////////////////////// Encoder ////////////////////////////
  442. // An Encoder does arithmetic encoding.  Methods:
  443. // Encoder(COMPRESS, f) creates encoder for compression to archive f, which
  444. //   must be open past any header for writing in binary mode.
  445. // Encoder(DECOMPRESS, f) creates encoder for decompression from archive f,
  446. //   which must be open past any header for reading in binary mode.
  447. // code(i) in COMPRESS mode compresses bit i (0 or 1) to file f.
  448. // code() in DECOMPRESS mode returns the next decompressed bit from file f.
  449. //   Global y is set to the last bit coded or decoded by code().
  450. // compress(c) in COMPRESS mode compresses one byte.
  451. // decompress() in DECOMPRESS mode decompresses and returns one byte.
  452. // flush() should be called exactly once after compression is done and
  453. //   before closing f.  It does nothing in DECOMPRESS mode.
  454. // size() returns current length of archive
  455. // setFile(f) sets alternate source to FILE* f for decompress() in COMPRESS
  456. //   mode (for testing transforms).
  457. typedef enum {COMPRESS, DECOMPRESS} Mode;
  458. class Encoder {
  459. private:
  460.   Predictor predictor;
  461.   const Mode mode;       // Compress or decompress?
  462.   FILE* archive;         // Compressed data file
  463.   U32 x1, x2;            // Range, initially [0, 1), scaled by 2^32
  464.   U32 x;                 // Decompress mode: last 4 input bytes of archive
  465.   FILE *alt;             // decompress() source in COMPRESS mode
  466.   // Compress bit y or return decompressed bit
  467.   int code(int y=0) {
  468.     int p=predictor.p();
  469.     assert(p>=0 && p<4096);
  470.     p+=p<2048;
  471.     U32 xmid=x1 + (x2-x1>>12)*p + ((x2-x1&0xfff)*p>>12);
  472.     assert(xmid>=x1 && xmid<x2);
  473.     if (mode==DECOMPRESS) y=x<=xmid;
  474.     y ? (x2=xmid) : (x1=xmid+1);
  475.     predictor.update(y);
  476.     while (((x1^x2)&0xff000000)==0) {  // pass equal leading bytes of range
  477.       if (mode==COMPRESS) putc(x2>>24, archive);
  478.       x1<<=8;
  479.       x2=(x2<<8)+255;
  480.       if (mode==DECOMPRESS) x=(x<<8)+(getc(archive)&255);  // EOF is OK
  481.     }
  482.     return y;
  483.   }
  484. public:
  485.   Encoder(Mode m, FILE* f);
  486.   Mode getMode() const {return mode;}
  487.   long size() const {return ftell(archive);}  // length of archive so far
  488.   void flush();  // call this when compression is finished
  489.   void setFile(FILE* f) {alt=f;}
  490.   // Compress one byte
  491.   void compress(int c) {
  492.     assert(mode==COMPRESS);
  493.     for (int i=7; i>=0; --i)
  494.       code((c>>i)&1);
  495.   }
  496.   // Decompress and return one byte
  497.   int decompress() {
  498.     if (mode==COMPRESS) {
  499.       assert(alt);
  500.       return getc(alt);
  501.     }
  502.     else {
  503.       int c=0;
  504.       for (int i=0; i<8; ++i)
  505.         c+=c+code();
  506.       return c;
  507.     }
  508.   }
  509. };
  510. Encoder::Encoder(Mode m, FILE* f): 
  511.     mode(m), archive(f), x1(0), x2(0xffffffff), x(0), alt(0) {
  512.   if (mode==DECOMPRESS) {  // x = first 4 bytes of archive
  513.     for (int i=0; i<4; ++i)
  514.       x=(x<<8)+(getc(archive)&255);
  515.   }
  516. }
  517. void Encoder::flush() {
  518.   if (mode==COMPRESS)
  519.     putc(x1>>24, archive);  // Flush first unequal byte of range
  520. }
  521. ///////////////////////////////// BWT //////////////////////////////
  522. // Globals
  523. bool fast=false;  // transform method: fast uses 5x blocksize memory, slow uses 5x/4
  524. int blockSize=0x400000;  // max BWT block size
  525. int n=0;          // number of elements in block, 0 < n <= blockSize
  526. Array<U8> block;  // [n] text to transform
  527. Array<int> ptr;   // [n] or [n/16] indexes into block to sort
  528. const int PAD=72; // extra bytes in block (copy of beginning)
  529. int pos=0;        // bytes compressed/decompressed so far
  530. bool quiet=false; // q option?
  531. // true if block[a+1...] < block[b+1...] wrapping at n
  532. inline bool lessthan(int a, int b) {
  533.   if (a<0) return false;
  534.   if (b<0) return true;
  535.   int r=block[a+1]-block[b+1];  // an optimization
  536.   if (r) return r<0;
  537.   r=memcmp(&block[a+2], &block[b+2], PAD-8);
  538.   if (r) return r<0;
  539.   if (a<b) {
  540.     int r=memcmp(&block[a+1], &block[b+1], n-b-1);
  541.     if (r) return r<0;
  542.     r=memcmp(&block[a+n-b], &block[0], b-a);
  543.     if (r) return r<0;
  544.     return memcmp(&block[0], &block[b-a], a)<0;
  545.   }
  546.   else {
  547.     int r=memcmp(&block[a+1], &block[b+1], n-a-1);
  548.     if (r) return r<0;
  549.     r=memcmp(&block[0], &block[b+n-a], a-b);
  550.     if (r) return r<0;
  551.     return memcmp(&block[a-b], &block[0], b)<0;
  552.   }
  553. }
  554. // read 4 byte value LSB first, or -1 at EOF
  555. int read4(FILE* f) {
  556.   unsigned int r=getc(f);
  557.   r|=getc(f)<<8;
  558.   r|=getc(f)<<16;
  559.   r|=getc(f)<<24;
  560.   return r;
  561. }
  562. // read n<=blockSize bytes from in to block, BWT, write to out
  563. int encodeBlock(FILE* in, Encoder& en) {
  564.   n=fread(&block[0], 1, blockSize, in);  // n = actual block size
  565.   if (n<1) return 0;
  566.   assert(block.size()>=n+PAD);
  567.   for (int i=0; i<PAD; ++i) block[i+n]=block[i];
  568.   // fast mode: sort the pointers to the block
  569.   if (fast) {
  570.     if (!quiet) printf("sorting     %10d to %10d  r", pos, pos+n);
  571.     assert(ptr.size()>=n);
  572.     for (int i=0; i<n; ++i) ptr[i]=i;
  573.     stable_sort(&ptr[0], &ptr[n], lessthan);  // faster than sort() or qsort()
  574.     int p=min_element(&ptr[0], &ptr[n])-&ptr[0];
  575.     en.compress(n>>24);
  576.     en.compress(n>>16);
  577.     en.compress(n>>8);
  578.     en.compress(n);
  579.     en.compress(p>>24);
  580.     en.compress(p>>16);
  581.     en.compress(p>>8);
  582.     en.compress(p);
  583.     if (!quiet) printf("compressing %10d to %10d  r", pos, pos+n);
  584.     for (int i=0; i<n; ++i) {
  585.       en.compress(block[ptr[i]]);
  586.       if (!quiet && i && (i&0xffff)==0) 
  587.         printf("compressed  %10d of %10d  r", pos+i, pos+n);
  588.     }
  589.     pos+=n;
  590.     return n;
  591.   }
  592.   // slow mode: divide the block into 16 parts, sort them, write the pointers
  593.   // to temporary files, then merge them.
  594.   else {
  595.     // write header
  596.     if (!quiet) printf("writing header at %10d          r", pos);
  597.     int p=0;
  598.     for (int i=1; i<n; ++i)
  599.       if (lessthan(i, 0)) ++p;
  600.     en.compress(n>>24);
  601.     en.compress(n>>16);
  602.     en.compress(n>>8);
  603.     en.compress(n);
  604.     en.compress(p>>24);
  605.     en.compress(p>>16);
  606.     en.compress(p>>8);
  607.     en.compress(p);
  608.     // sort pointers in 16 parts to temporary files
  609.     const int subBlockSize = (n-1)/16+1;  // max size of sub-block
  610.     int start=0, end=subBlockSize;  // range of current sub-block
  611.     FILE* tmp[16];  // temporary files
  612.     for (int i=0; i<16; ++i) {
  613.       if (!quiet) printf("sorting      %10d to %10d  r", pos+start, pos+end);
  614.       tmp[i]=tmpfile();
  615.       if (!tmp[i]) perror("tmpfile()"), exit(1);
  616.       for (int j=start; j<end; ++j) ptr[j-start]=j;
  617.       stable_sort(&ptr[0], &ptr[end-start], lessthan);
  618.       for (int j=start; j<end; ++j) {  // write pointers
  619.         int c=ptr[j-start];
  620.         fprintf(tmp[i], "%c%c%c%c", c, c>>8, c>>16, c>>24);
  621.       }
  622.       start=end;
  623.       end+=subBlockSize;
  624.       if (end>n) end=n;
  625.     }
  626.     // merge sorted pointers
  627.     if (!quiet) printf("merging      %10d to %10d  r", pos, pos+n);
  628.     unsigned int t[16];  // current pointers
  629.     for (int i=0; i<16; ++i) {  // init t
  630.       rewind(tmp[i]);
  631.       t[i]=read4(tmp[i]);
  632.     }
  633.     for (int i=0; i<n; ++i) {  // merge and compress
  634.       int j=min_element(t, t+16, lessthan)-t;
  635.       en.compress(block[t[j]]);
  636.       if (!quiet && i && (i&0xffff)==0) 
  637.         printf("compressed  %10d of %10d  r", pos+i, pos+n);
  638.       t[j]=read4(tmp[j]);
  639.     }
  640.     for (int i=0; i<16; ++i)  // delete tmp files
  641.       fclose(tmp[i]);
  642.     pos+=n;
  643.     return n;
  644.   }
  645. }
  646. // forward BWT
  647. void encode(FILE* in, Encoder& en) {
  648.   block.resize(blockSize+PAD);
  649.   if (fast) ptr.resize(blockSize+1);
  650.   else ptr.resize((blockSize-1)/16+2);
  651.   while (encodeBlock(in, en));
  652.   en.compress(0);  // mark EOF
  653.   en.compress(0);
  654.   en.compress(0);
  655.   en.compress(0);
  656. }
  657. // inverse BWT of one block
  658. int decodeBlock(Encoder& en, FILE* out) {
  659.   // read block size
  660.   int n=en.decompress();
  661.   n=n*256+en.decompress();
  662.   n=n*256+en.decompress();
  663.   n=n*256+en.decompress();
  664.   if (n==0) return n;
  665.   if (!blockSize) {  // first block?  allocate memory
  666.     blockSize = n;
  667.     if (!quiet) printf("block size = %dn", blockSize);
  668.     block.resize(blockSize+PAD);
  669.     if (fast) ptr.resize(blockSize);
  670.     else ptr.resize(blockSize/16+256);
  671.   }
  672.   else if (n<1 || n>blockSize) {
  673.     printf("file corrupted: block=%d max=%dn", n, blockSize);
  674.     exit(1);
  675.   }
  676.   // read pointer to first byte
  677.   int p=en.decompress();
  678.   p=p*256+en.decompress();
  679.   p=p*256+en.decompress();
  680.   p=p*256+en.decompress();
  681.   if (p<0 || p>=n) {
  682.     printf("file corrupted: p=%d n=%dn", p, n);
  683.     exit(1);
  684.   }
  685.   // decompress and read block
  686.   for (int i=0; i<n; ++i) {
  687.     block[i]=en.decompress();
  688.     if (!quiet && i && (i&0xffff)==0)
  689.       printf("decompressed %10d of %10d  r", pos+i, pos+n);
  690.   }
  691.   for (int i=0; i<PAD; ++i) block[i+n]=block[i];  // circular pad
  692.   // count (sort) bytes
  693.   if (!quiet) printf("unsorting    %10d to %10d  r", pos, pos+n);
  694.   Array<int> t(257);  // i -> number of bytes < i in block
  695.   for (int i=0; i<n; ++i)
  696.     ++t[block[i]+1];
  697.   for (int i=1; i<257; ++i)
  698.     t[i]+=t[i-1];
  699.   assert(t[256]==n);
  700.   // fast mode: build linked list
  701.   if (fast) {
  702.     for (int i=0; i<n; ++i)
  703.       ptr[t[block[i]]++]=i;
  704.     assert(t[255]==n);
  705.     // traverse list
  706.     for (int i=0; i<n; ++i) {
  707.       assert(p>=0 && p<n);
  708.       putc(block[p], out);
  709.       p=ptr[p];
  710.     }
  711.     return n;
  712.   }
  713.   // slow: build ptr[t[c]+c+i] = position of i*16'th occurrence of c in block
  714.   Array<int> count(256);  // i -> count of i in block
  715.   for (int i=0; i<n; ++i) {
  716.     int c=block[i];
  717.     if ((count[c]++ & 15)==0)
  718.       ptr[(t[c]>>4)+c+(count[c]>>4)]=i;
  719.   }
  720.   // decode
  721.   int c=block[p];
  722.   for (int i=0; i<n; ++i) {
  723.     assert(p>=0 && p<n);
  724.     putc(c, out);
  725.     // find next c by binary search in t so that t[c] <= p < t[c+1]
  726.     c=127;
  727.     int d=64;
  728.     while (d) {
  729.       if (t[c]>p) c-=d;
  730.       else if (t[c+1]<=p) c+=d;
  731.       else break;
  732.       d>>=1;
  733.     }
  734.     if (c==254 && t[255]<=p && p<t[256]) c=255;
  735.     assert(c>=0 && c<256 && t[c]<=p && p<t[c+1]);
  736.     // find approximate position of p
  737.     int offset=p-t[c];
  738.     const U8* q=&block[ptr[(t[c]>>4)+c+(offset>>4)]];  // start of linear search
  739.     offset&=15;
  740.     // find next p by linear search for offset'th occurrence of c in block
  741.     while (offset--)
  742.       if (*++q != c) q=(const U8*)memchr(q, c, &block[n]-q);
  743.     assert(q && q>=&block[0] && q<&block[n]);
  744.     p=q-&block[0];
  745.   }
  746.   pos+=n;
  747.   return n;
  748. }
  749. // inverse BWT of file
  750. void decode(Encoder& en, FILE* out) {
  751.   while (decodeBlock(en, out));
  752. }
  753. /////////////////////////////// main ////////////////////////////
  754. int main(int argc, char** argv) {
  755.   clock_t start=clock();
  756.   // check for args
  757.   if (argc<4) {
  758.     printf("bbb Big Block BWT file compressor, ver. 1n"
  759.       "(C) 2006, Matt Mahoney.  Free under GPL, http://www.gnu.org/licenses/gpl.txtn"
  760.       "n"
  761.       "To compress/decompress a file: bbb command input outputn"
  762.       "n"
  763.       "Commands:n"
  764.       "c = compress (default),  d = decompress.n"
  765.       "f = fast mode, needs 5x block size memory, default uses 1.25x block size.n"
  766.       "q = quiet (no output except error messages).n"
  767.       "bN, kN, mN = use block size N bytes, KiB, MiB, default = m4 (compression only).n"
  768.       "n"
  769.       "Commands should be concatenated in any order, e.g. bbb cfm100q foo foo.bbbn"
  770.       "means compress foo to foo.bbb in fast mode using 100 MiB block size in quietn"
  771.       "mode.n");
  772.     exit(0);
  773.   }
  774.   // read options
  775.   Mode mode=COMPRESS;
  776.   const char* p=argv[1];
  777.   while (*p) {
  778.     switch (*p) {
  779.       case 'c': mode=COMPRESS; break;
  780.       case 'd': mode=DECOMPRESS; break;
  781.       case 'f': fast=true; break;
  782.       case 'b': blockSize=atoi(p+1); break;
  783.       case 'k': blockSize=atoi(p+1)<<10; break;
  784.       case 'm': blockSize=atoi(p+1)<<20; break;
  785.       case 'q': quiet=true; break;
  786.     }
  787.     ++p;
  788.   }
  789.   if (blockSize<1) printf("Block size must be at least 1n"), exit(1);
  790.   
  791.   // open files
  792.   FILE* in=fopen(argv[2], "rb");
  793.   if (!in) perror(argv[2]), exit(1);
  794.   FILE* out=fopen(argv[3], "wb");
  795.   if (!out) perror(argv[3]), exit(1);
  796.   // encode or decode
  797.   if (mode==COMPRESS) {
  798.     if (!quiet) printf("Compressing %s to %s in %s mode, block size = %dn", 
  799.       argv[2], argv[3], fast ? "fast" : "slow", blockSize);
  800.     Encoder en(COMPRESS, out);
  801.     encode(in, en);
  802.     en.flush();
  803.   }
  804.   else if (mode==DECOMPRESS) {
  805.     blockSize=0;
  806.     if (!quiet) printf("Decompressing %s to %s in %s moden",
  807.       argv[2], argv[3], fast ? "fast" : "slow");
  808.     Encoder en(DECOMPRESS, in);
  809.     decode(en, out);
  810.   }
  811.   if (!quiet) printf("%ld -> %ld in %1.2f sec                  n", ftell(in), ftell(out),
  812.     (clock()-start+0.0)/CLOCKS_PER_SEC);
  813.   return 0;
  814. }