summaryrefslogtreecommitdiffstats
path: root/decoder.h
diff options
context:
space:
mode:
Diffstat (limited to 'decoder.h')
-rw-r--r--decoder.h20
1 files changed, 14 insertions, 6 deletions
diff --git a/decoder.h b/decoder.h
index 10195b8..922426c 100644
--- a/decoder.h
+++ b/decoder.h
@@ -1,5 +1,5 @@
/* Lunzip - Decompressor for the lzip format
- Copyright (C) 2010-2015 Antonio Diaz Diaz.
+ Copyright (C) 2010-2016 Antonio Diaz Diaz.
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
@@ -60,7 +60,8 @@ static inline void Rd_reset_member_position( struct Range_decoder * const rdec )
static inline uint8_t Rd_get_byte( struct Range_decoder * const rdec )
{
- if( Rd_finished( rdec ) ) return 0xAA; /* make code != 0 */
+ /* 0xFF avoids decoder error if member is truncated at EOS marker */
+ if( Rd_finished( rdec ) ) return 0xFF;
return rdec->buffer[rdec->pos++];
}
@@ -238,6 +239,7 @@ struct LZ_decoder
int stream_pos; /* first byte not yet written to file */
uint32_t crc;
int outfd; /* output file descriptor */
+ bool pos_wrapped;
Bit_model bm_literal[1<<literal_context_bits][0x300];
Bit_model bm_match[states][pos_states];
@@ -288,10 +290,15 @@ static inline void LZd_copy_block( struct LZ_decoder * const d,
const int distance, int len )
{
int i = d->pos - distance - 1;
- if( i < 0 ) i += d->buffer_size;
- if( len < d->buffer_size - max( d->pos, i ) && len <= abs( d->pos - i ) )
+ bool fast;
+ if( i < 0 )
+ { i += d->buffer_size;
+ fast = ( len <= d->buffer_size - i && len <= i - d->pos ); }
+ else
+ fast = ( len < d->buffer_size - d->pos && len <= d->pos - i );
+ if( fast ) /* no wrap, no overlap */
{
- memcpy( d->buffer + d->pos, d->buffer + i, len ); /* no wrap, no overlap */
+ memcpy( d->buffer + d->pos, d->buffer + i, len );
d->pos += len;
}
else for( ; len > 0; --len )
@@ -330,13 +337,14 @@ static inline bool LZd_init( struct LZ_decoder * const d,
d->partial_data_pos = 0;
d->rdec = rde;
d->dictionary_size = dict_size;
- d->buffer_size = min( buffer_size, max( 65536, dict_size ) );
+ d->buffer_size = min( buffer_size, dict_size );
d->buffer = (uint8_t *)malloc( d->buffer_size );
if( !d->buffer ) return false;
d->pos = 0;
d->stream_pos = 0;
d->crc = 0xFFFFFFFFU;
d->outfd = ofd;
+ d->pos_wrapped = false;
Bm_array_init( d->bm_literal[0], (1 << literal_context_bits) * 0x300 );
Bm_array_init( d->bm_match[0], states * pos_states );