igzip: Create flag for inflate to return crc of the decompressed data

Change-Id: I2d966f2d4ca135e3c938a9501bf5d2e11d8e92fe
Signed-off-by: Roy Oursler <roy.j.oursler@intel.com>
This commit is contained in:
Roy Oursler 2016-09-26 10:52:28 -07:00 committed by Greg Tucker
parent 4ea4f81138
commit e569ff70e7
4 changed files with 35 additions and 11 deletions

View File

@ -5,6 +5,7 @@
#include "huff_codes.h"
extern int decode_huffman_code_block_stateless(struct inflate_state *);
extern uint32_t crc32_gzip(uint32_t init_crc, const unsigned char *buf, uint64_t len);
/* structure contain lookup data based on RFC 1951 */
struct rfc1951_tables {
@ -1037,6 +1038,8 @@ void isal_inflate_init(struct inflate_state *state)
state->total_out = 0;
state->block_state = ISAL_BLOCK_NEW_HDR;
state->bfinal = 0;
state->crc_flag = 0;
state->crc = 0;
state->type0_block_len = 0;
state->copy_overflow_length = 0;
state->copy_overflow_distance = 0;
@ -1048,11 +1051,13 @@ void isal_inflate_init(struct inflate_state *state)
int isal_inflate_stateless(struct inflate_state *state)
{
uint32_t ret = 0;
uint8_t *start_out = state->next_out;
state->read_in = 0;
state->read_in_length = 0;
state->block_state = ISAL_BLOCK_NEW_HDR;
state->bfinal = 0;
state->crc = 0;
state->total_out = 0;
while (state->block_state != ISAL_BLOCK_FINISH) {
@ -1074,6 +1079,9 @@ int isal_inflate_stateless(struct inflate_state *state)
state->block_state = ISAL_BLOCK_FINISH;
}
if (state->crc_flag)
state->crc = crc32_gzip(state->crc, start_out, state->next_out - start_out);
/* Undo count stuff of bytes read into the read buffer */
state->next_in -= state->read_in_length / 8;
state->avail_in += state->read_in_length / 8;
@ -1084,7 +1092,7 @@ int isal_inflate_stateless(struct inflate_state *state)
int isal_inflate(struct inflate_state *state)
{
uint8_t *next_out = state->next_out;
uint8_t *start_out = state->next_out;
uint32_t avail_out = state->avail_out;
uint32_t copy_size = 0;
int32_t shift_size = 0;
@ -1138,7 +1146,7 @@ int isal_inflate(struct inflate_state *state)
state->tmp_out_valid = state->next_out - state->tmp_out_buffer;
/* Setup state for decompressing into out_buffer */
state->next_out = next_out;
state->next_out = start_out;
state->avail_out = avail_out;
}
@ -1158,6 +1166,10 @@ int isal_inflate(struct inflate_state *state)
|| ret == ISAL_INVALID_SYMBOL) {
/* Set total_out to not count data in tmp_out_buffer */
state->total_out -= state->tmp_out_valid - state->tmp_out_processed;
if (state->crc_flag)
state->crc =
crc32_gzip(state->crc, start_out,
state->next_out - start_out);
return ret;
}
@ -1184,6 +1196,10 @@ int isal_inflate(struct inflate_state *state)
}
}
if (state->crc_flag)
state->crc =
crc32_gzip(state->crc, start_out, state->next_out - start_out);
if (state->block_state != ISAL_BLOCK_INPUT_DONE) {
/* Save decompression history in tmp_out buffer */
if (state->tmp_out_valid == state->tmp_out_processed

View File

@ -291,15 +291,16 @@ uint32_t check_gzip_header(uint8_t * z_buf)
return ret;
}
uint32_t check_gzip_trl(uint64_t gzip_crc, uint8_t * uncompress_buf, uint32_t uncompress_len)
uint32_t check_gzip_trl(uint64_t gzip_trl, uint32_t inflate_crc, uint8_t * uncompress_buf,
uint32_t uncompress_len)
{
uint64_t crc, ret = 0;
uint64_t trl, ret = 0;
uint32_t crc;
crc = find_crc(uncompress_buf, uncompress_len);
trl = ((uint64_t) uncompress_len << 32) | crc;
crc = ((uint64_t) uncompress_len << 32) | crc;
if (crc != gzip_crc)
if (crc != inflate_crc || trl != gzip_trl)
ret = INCORRECT_GZIP_TRAILER;
return ret;
@ -316,6 +317,7 @@ int inflate_stateless_pass(uint8_t * compress_buf, uint64_t compress_len,
state.avail_in = compress_len;
state.next_out = uncompress_buf;
state.avail_out = *uncompress_len;
state.crc_flag = gzip_flag;
ret = isal_inflate_stateless(&state);
@ -324,8 +326,8 @@ int inflate_stateless_pass(uint8_t * compress_buf, uint64_t compress_len,
if (gzip_flag) {
if (!ret)
ret =
check_gzip_trl(*(uint64_t *) state.next_in, uncompress_buf,
*uncompress_len);
check_gzip_trl(*(uint64_t *) state.next_in, state.crc,
uncompress_buf, *uncompress_len);
state.avail_in -= 8;
}
@ -357,6 +359,7 @@ int inflate_multi_pass(uint8_t * compress_buf, uint64_t compress_len,
state->next_out = NULL;
state->avail_in = 0;
state->avail_out = 0;
state->crc_flag = gzip_flag;
if (gzip_flag)
compress_len -= 8;
@ -451,7 +454,7 @@ int inflate_multi_pass(uint8_t * compress_buf, uint64_t compress_len,
if (!ret)
ret =
check_gzip_trl(*(uint64_t *) & compress_buf[compress_len],
uncompress_buf, *uncompress_len);
state->crc, uncompress_buf, *uncompress_len);
}
if (ret == 0 && state->avail_in != 0)
ret = INFLATE_LEFTOVER_INPUT;

View File

@ -63,6 +63,8 @@ FIELD _lit_huff_code, _inflate_huff_code_large_size, _inflate_huff_code_large_al
FIELD _dist_huff_code,_inflate_huff_code_small_size, _inflate_huff_code_small_align
FIELD _block_state, 4, 4
FIELD _bfinal, 4, 4
FIELD _crc_flag, 4, 4
FIELD _crc, 4, 4
FIELD _type0_block_len, 4, 4
FIELD _copy_overflow_len, 4, 4
FIELD _copy_overflow_dist, 4, 4

View File

@ -350,6 +350,8 @@ struct inflate_state {
struct inflate_huff_code_small dist_huff_code; //!< Structure for decoding dist symbols
enum isal_block_state block_state; //!< Current decompression state
uint32_t bfinal; //!< Flag identifying final block
uint32_t crc_flag; //!< Flag identifying whether to track of crc
uint32_t crc; //!< Contains crc of output if crc_flag is set
int32_t type0_block_len; //!< Length left to read of type 0 block when outbuffer overflow occured
int32_t copy_overflow_length; //!< Length left to copy when outbuffer overflow occured
int32_t copy_overflow_distance; //!< Lookback distance when outbuffer overlow occured
@ -501,7 +503,8 @@ void isal_inflate_init(struct inflate_state *state);
* next_in, avail_in and write a decompressed stream to the output buffer
* (updating next_out and avail_out). The function returns when the input buffer
* is empty, the output buffer is full or invalid data is found. The current
* state of the decompression on exit can be read from state->block-state.
* state of the decompression on exit can be read from state->block-state. If
* the crc_flag is set, the gzip crc of the output is stored in state->crc.
*
* @param state Structure holding state information on the compression streams.
* @return ISAL_DECOMP_OK (if everything is ok),