diff options
Diffstat (limited to 'libraries/pack200/src/coding.h')
-rw-r--r-- | libraries/pack200/src/coding.h | 348 |
1 files changed, 174 insertions, 174 deletions
diff --git a/libraries/pack200/src/coding.h b/libraries/pack200/src/coding.h index f9bd6ca2..bfdd252e 100644 --- a/libraries/pack200/src/coding.h +++ b/libraries/pack200/src/coding.h @@ -35,9 +35,9 @@ struct unpacker; #define CODING_D(x) ((x) >> 0 & 0xF) #define CODING_INIT(B, H, S, D) \ - { \ - CODING_SPEC(B, H, S, D), 0, 0, 0, 0, 0, 0, 0, 0 \ - } + { \ + CODING_SPEC(B, H, S, D), 0, 0, 0, 0, 0, 0, 0, 0 \ + } // For debugging purposes, some compilers do not like this and will complain. // #define long do_not_use_C_long_types_use_jlong_or_int @@ -45,126 +45,126 @@ struct unpacker; struct coding { - int spec; // B,H,S,D - - // Handy values derived from the spec: - int B() - { - return CODING_B(spec); - } - int H() - { - return CODING_H(spec); - } - int S() - { - return CODING_S(spec); - } - int D() - { - return CODING_D(spec); - } - int L() - { - return 256 - CODING_H(spec); - } - int min, max; - int umin, umax; - char isSigned, isSubrange, isFullRange, isMalloc; - - coding *init(); // returns self or nullptr if error - coding *initFrom(int spec_) - { - assert(this->spec == 0); - this->spec = spec_; - return init(); - } - - static coding *findBySpec(int spec); - static coding *findBySpec(int B, int H, int S = 0, int D = 0); - static coding *findByIndex(int irregularCodingIndex); - - static uint32_t parse(byte *&rp, int B, int H); - static uint32_t parse_lgH(byte *&rp, int B, int H, int lgH); - static void parseMultiple(byte *&rp, int N, byte *limit, int B, int H); - - uint32_t parse(byte *&rp) - { - return parse(rp, CODING_B(spec), CODING_H(spec)); - } - void parseMultiple(byte *&rp, int N, byte *limit) - { - parseMultiple(rp, N, limit, CODING_B(spec), CODING_H(spec)); - } - - bool canRepresent(int x) - { - return (x >= min && x <= max); - } - bool canRepresentUnsigned(int x) - { - return (x >= umin && x <= umax); - } - - int sumInUnsignedRange(int x, int y); - - int readFrom(byte *&rpVar, int *dbase); - void readArrayFrom(byte *&rpVar, int *dbase, int length, int *values); - void skipArrayFrom(byte *&rpVar, int length) - { - readArrayFrom(rpVar, (int *)NULL, length, (int *)NULL); - } - - void free(); // free self if isMalloc + int spec; // B,H,S,D + + // Handy values derived from the spec: + int B() + { + return CODING_B(spec); + } + int H() + { + return CODING_H(spec); + } + int S() + { + return CODING_S(spec); + } + int D() + { + return CODING_D(spec); + } + int L() + { + return 256 - CODING_H(spec); + } + int min, max; + int umin, umax; + char isSigned, isSubrange, isFullRange, isMalloc; + + coding *init(); // returns self or nullptr if error + coding *initFrom(int spec_) + { + assert(this->spec == 0); + this->spec = spec_; + return init(); + } + + static coding *findBySpec(int spec); + static coding *findBySpec(int B, int H, int S = 0, int D = 0); + static coding *findByIndex(int irregularCodingIndex); + + static uint32_t parse(byte *&rp, int B, int H); + static uint32_t parse_lgH(byte *&rp, int B, int H, int lgH); + static void parseMultiple(byte *&rp, int N, byte *limit, int B, int H); + + uint32_t parse(byte *&rp) + { + return parse(rp, CODING_B(spec), CODING_H(spec)); + } + void parseMultiple(byte *&rp, int N, byte *limit) + { + parseMultiple(rp, N, limit, CODING_B(spec), CODING_H(spec)); + } + + bool canRepresent(int x) + { + return (x >= min && x <= max); + } + bool canRepresentUnsigned(int x) + { + return (x >= umin && x <= umax); + } + + int sumInUnsignedRange(int x, int y); + + int readFrom(byte *&rpVar, int *dbase); + void readArrayFrom(byte *&rpVar, int *dbase, int length, int *values); + void skipArrayFrom(byte *&rpVar, int length) + { + readArrayFrom(rpVar, (int *)NULL, length, (int *)NULL); + } + + void free(); // free self if isMalloc }; enum coding_method_kind { - cmk_ERROR, - cmk_BHS, - cmk_BHS0, - cmk_BHS1, - cmk_BHSD1, - cmk_BHS1D1full, // isFullRange - cmk_BHS1D1sub, // isSubRange - - // special cases hand-optimized (~50% of all decoded values) - cmk_BYTE1, //(1,256) 6% - cmk_CHAR3, //(3,128) 7% - cmk_UNSIGNED5, //(5,64) 13% - cmk_DELTA5, //(5,64,1,1) 5% - cmk_BCI5, //(5,4) 18% - cmk_BRANCH5, //(5,4,2) 4% - // cmk_UNSIGNED5H16, //(5,16) 5% - // cmk_UNSIGNED2H4, //(2,4) 6% - // cmk_DELTA4H8, //(4,8,1,1) 10% - // cmk_DELTA3H16, //(3,16,1,1) 9% - cmk_BHS_LIMIT, - cmk_pop, - cmk_pop_BHS0, - cmk_pop_BYTE1, - cmk_pop_LIMIT, - cmk_LIMIT + cmk_ERROR, + cmk_BHS, + cmk_BHS0, + cmk_BHS1, + cmk_BHSD1, + cmk_BHS1D1full, // isFullRange + cmk_BHS1D1sub, // isSubRange + + // special cases hand-optimized (~50% of all decoded values) + cmk_BYTE1, //(1,256) 6% + cmk_CHAR3, //(3,128) 7% + cmk_UNSIGNED5, //(5,64) 13% + cmk_DELTA5, //(5,64,1,1) 5% + cmk_BCI5, //(5,4) 18% + cmk_BRANCH5, //(5,4,2) 4% + // cmk_UNSIGNED5H16, //(5,16) 5% + // cmk_UNSIGNED2H4, //(2,4) 6% + // cmk_DELTA4H8, //(4,8,1,1) 10% + // cmk_DELTA3H16, //(3,16,1,1) 9% + cmk_BHS_LIMIT, + cmk_pop, + cmk_pop_BHS0, + cmk_pop_BYTE1, + cmk_pop_LIMIT, + cmk_LIMIT }; enum { - BYTE1_spec = CODING_SPEC(1, 256, 0, 0), - CHAR3_spec = CODING_SPEC(3, 128, 0, 0), - UNSIGNED4_spec = CODING_SPEC(4, 256, 0, 0), - UNSIGNED5_spec = CODING_SPEC(5, 64, 0, 0), - SIGNED5_spec = CODING_SPEC(5, 64, 1, 0), - DELTA5_spec = CODING_SPEC(5, 64, 1, 1), - UDELTA5_spec = CODING_SPEC(5, 64, 0, 1), - MDELTA5_spec = CODING_SPEC(5, 64, 2, 1), - BCI5_spec = CODING_SPEC(5, 4, 0, 0), - BRANCH5_spec = CODING_SPEC(5, 4, 2, 0) + BYTE1_spec = CODING_SPEC(1, 256, 0, 0), + CHAR3_spec = CODING_SPEC(3, 128, 0, 0), + UNSIGNED4_spec = CODING_SPEC(4, 256, 0, 0), + UNSIGNED5_spec = CODING_SPEC(5, 64, 0, 0), + SIGNED5_spec = CODING_SPEC(5, 64, 1, 0), + DELTA5_spec = CODING_SPEC(5, 64, 1, 1), + UDELTA5_spec = CODING_SPEC(5, 64, 0, 1), + MDELTA5_spec = CODING_SPEC(5, 64, 2, 1), + BCI5_spec = CODING_SPEC(5, 4, 0, 0), + BRANCH5_spec = CODING_SPEC(5, 4, 2, 0) }; enum { - B_MAX = 5, - C_SLOP = B_MAX * 10 + B_MAX = 5, + C_SLOP = B_MAX * 10 }; struct coding_method; @@ -172,76 +172,76 @@ struct coding_method; // iterator under the control of a meta-coding struct value_stream { - // current coding of values or values - coding c; // B,H,S,D,etc. - coding_method_kind cmk; // type of decoding needed - byte *rp; // read pointer - byte *rplimit; // final value of read pointer - int sum; // partial sum of all values so far (D=1 only) - coding_method *cm; // coding method that defines this stream - - void init(byte *band_rp, byte *band_limit, coding *defc); - void init(byte *band_rp, byte *band_limit, int spec) - { - init(band_rp, band_limit, coding::findBySpec(spec)); - } - - void setCoding(coding *c); - void setCoding(int spec) - { - setCoding(coding::findBySpec(spec)); - } - - // Parse and decode a single value. - int getInt(); - - // Parse and decode a single byte, with no error checks. - int getByte() - { - assert(cmk == cmk_BYTE1); - assert(rp < rplimit); - return *rp++ & 0xFF; - } - - // Used only for asserts. - bool hasValue(); - - void done() - { - assert(!hasValue()); - } - - // Sometimes a value stream has an auxiliary (but there are never two). - value_stream *helper() - { - assert(hasHelper()); - return this + 1; - } - bool hasHelper(); + // current coding of values or values + coding c; // B,H,S,D,etc. + coding_method_kind cmk; // type of decoding needed + byte *rp; // read pointer + byte *rplimit; // final value of read pointer + int sum; // partial sum of all values so far (D=1 only) + coding_method *cm; // coding method that defines this stream + + void init(byte *band_rp, byte *band_limit, coding *defc); + void init(byte *band_rp, byte *band_limit, int spec) + { + init(band_rp, band_limit, coding::findBySpec(spec)); + } + + void setCoding(coding *c); + void setCoding(int spec) + { + setCoding(coding::findBySpec(spec)); + } + + // Parse and decode a single value. + int getInt(); + + // Parse and decode a single byte, with no error checks. + int getByte() + { + assert(cmk == cmk_BYTE1); + assert(rp < rplimit); + return *rp++ & 0xFF; + } + + // Used only for asserts. + bool hasValue(); + + void done() + { + assert(!hasValue()); + } + + // Sometimes a value stream has an auxiliary (but there are never two). + value_stream *helper() + { + assert(hasHelper()); + return this + 1; + } + bool hasHelper(); }; struct coding_method { - value_stream vs0; // initial state snapshot (vs.meta==this) + value_stream vs0; // initial state snapshot (vs.meta==this) - coding_method *next; // what to do when we run out of bytes + coding_method *next; // what to do when we run out of bytes - // these fields are used for pop codes only: - int *fValues; // favored value array - int fVlength; // maximum favored value token - coding_method *uValues; // unfavored value stream + // these fields are used for pop codes only: + int *fValues; // favored value array + int fVlength; // maximum favored value token + coding_method *uValues; // unfavored value stream - // pointer to outer unpacker, for error checks etc. - unpacker *u; + // pointer to outer unpacker, for error checks etc. + unpacker *u; - // Initialize a value stream. - void reset(value_stream *state); + // Initialize a value stream. + void reset(value_stream *state); - // Parse a band header, size a band, and initialize for further action. - // band_rp advances (but not past band_limit), and meta_rp advances. - // The mode gives context, such as "inside a pop". - // The defc and N are the incoming parameters to a meta-coding. - // The value sink is used to collect output values, when desired. - void init(byte *&band_rp, byte *band_limit, byte *&meta_rp, int mode, coding *defc, int N, - intlist *valueSink); + // Parse a band header, size a band, and initialize for further action. + // band_rp advances (but not past band_limit), and meta_rp advances. + // The mode gives context, such as "inside a pop". + // The defc and N are the incoming parameters to a meta-coding. + // The value sink is used to collect output values, when desired. + void init(byte *&band_rp, byte *band_limit, byte *&meta_rp, int mode, coding *defc, int N, + intlist *valueSink); }; |