diff options
author | giraffedata <giraffedata@9d0c8265-081b-0410-96cb-a4ca84ce46f8> | 2009-05-02 19:23:42 +0000 |
---|---|---|
committer | giraffedata <giraffedata@9d0c8265-081b-0410-96cb-a4ca84ce46f8> | 2009-05-02 19:23:42 +0000 |
commit | d183dec220bbedbcac8081dc6fa5a81dde9b23f3 (patch) | |
tree | ea0d1ec4702cccffe551cab493ff79ab20bd869b /converter | |
parent | 3fb9822420a65f1fa543e99edb55244ddf2a333a (diff) | |
download | netpbm-mirror-d183dec220bbedbcac8081dc6fa5a81dde9b23f3.tar.gz netpbm-mirror-d183dec220bbedbcac8081dc6fa5a81dde9b23f3.tar.xz netpbm-mirror-d183dec220bbedbcac8081dc6fa5a81dde9b23f3.zip |
Extract whole bytes or words instead of a bit at a time
git-svn-id: http://svn.code.sf.net/p/netpbm/code/trunk@908 9d0c8265-081b-0410-96cb-a4ca84ce46f8
Diffstat (limited to 'converter')
-rw-r--r-- | converter/other/giftopnm.c | 56 |
1 files changed, 48 insertions, 8 deletions
diff --git a/converter/other/giftopnm.c b/converter/other/giftopnm.c index 32023dce..4d2d720b 100644 --- a/converter/other/giftopnm.c +++ b/converter/other/giftopnm.c @@ -42,6 +42,13 @@ #define LOCALCOLORMAP 0x80 #define BitSet(byte, bit) (((byte) & (bit)) == (bit)) +#if !defined(BYTE_ORDER) || !defined(LITTLE_ENDIAN) + /* make sure (BYTE_ORDER == LITTLE_ENDIAN) is FALSE */ + #define BYTE_ORDER 0 + #define LITTLE_ENDIAN 1 +#endif + + static __inline__ bool ReadOK(FILE * const fileP, unsigned char * const buffer, @@ -561,6 +568,45 @@ getCode_init(struct getCodeState * const getCodeStateP) { +static unsigned int +bitsOfLeBuffer(const unsigned char * const buf, + unsigned int const start, + unsigned int const len) { +/*---------------------------------------------------------------------------- + Return a string of 'len' bits (up to 16) starting at bit 'start' of buffer + buf[]. + + In the buffer, the bits are numbered Intel-style, with the first bit of a + byte being the least significant bit. So bit 3 is the "16" bit of the + first byte of buf[]. + + We return the string as an integer such that its pure binary encoding with + the bits numbered Intel-style is the string. E.g. the string 0,1,1 + yields six. +-----------------------------------------------------------------------------*/ + uint32_t codeBlock; + /* The 3 whole bytes of the buffer that contain the requested + bit string + */ + + assert(len <= 16); + + if (BYTE_ORDER == LITTLE_ENDIAN) + /* Fast path */ + codeBlock = *(uint32_t *) & buf[start/8]; + else + /* logic works for little endian too */ + codeBlock = + (buf[start/8+0] << 0) | + (buf[start/8+1] << 8) | + (buf[start/8+2] << 16); + + return (unsigned int) + (codeBlock >> (start % 8)) & ((1 << len) - 1); +} + + + static void getCode_get(struct getCodeState * const gsP, FILE * const ifP, @@ -613,16 +659,10 @@ getCode_get(struct getCodeState * const gsP, bitsUnused, codeSize); } } else { - int i, j; - unsigned int code; - unsigned char * const buf = gsP->buf; - - code = 0; /* initial value */ - for (i = gsP->curbit, j = 0; j < codeSize; ++i, ++j) - code |= ((buf[ i / 8 ] & (1 << (i % 8))) != 0) << j; + *codeP = bitsOfLeBuffer(gsP->buf, gsP->curbit, codeSize); + gsP->curbit += codeSize; *eofP = FALSE; - *codeP = code; } } } |