mirror of
https://github.com/intel/isa-l.git
synced 2025-10-28 19:51:56 +01:00
igzip: Create stateless FULL_FLUSH mode
Add flush modes to isal_deflate_stateless. IGZIP_USE_GZIP_FORMAT is not supported because of limitations imposed by the statelessness. Signed-off-by: Roy Oursler <roy.j.oursler@intel.com> Reviewed-by: Greg Tucker <greg.b.tucker@intel.com>
This commit is contained in:
156
igzip/igzip.c
156
igzip/igzip.c
@@ -154,6 +154,44 @@ void sync_flush(struct isal_zstream *stream)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static
|
||||||
|
void sync_flush_stateless(struct isal_zstream *stream)
|
||||||
|
{
|
||||||
|
struct isal_zstate *state = &stream->internal_state;
|
||||||
|
uint64_t bits_to_write = 0xFFFF0000, bits_len;
|
||||||
|
uint64_t code = 0, len = 0, bytes;
|
||||||
|
int flush_size;
|
||||||
|
|
||||||
|
if (stream->avail_out >= 8) {
|
||||||
|
set_buf(&state->bitbuf, stream->next_out, stream->avail_out);
|
||||||
|
|
||||||
|
if (!state->has_eob)
|
||||||
|
get_lit_code(stream->hufftables, 256, &code, &len);
|
||||||
|
|
||||||
|
flush_size = (-(state->bitbuf.m_bit_count + len + 3)) % 8;
|
||||||
|
|
||||||
|
bits_to_write <<= flush_size + 3;
|
||||||
|
bits_len = 32 + len + flush_size + 3;
|
||||||
|
|
||||||
|
#ifdef USE_BITBUFB /* Write Bits Always */
|
||||||
|
state->state = ZSTATE_NEW_HDR;
|
||||||
|
#else /* Not Write Bits Always */
|
||||||
|
state->state = ZSTATE_FLUSH_WRITE_BUFFER;
|
||||||
|
#endif
|
||||||
|
state->has_eob = 0;
|
||||||
|
|
||||||
|
if (len > 0)
|
||||||
|
bits_to_write = (bits_to_write << len) | code;
|
||||||
|
|
||||||
|
write_bits(&state->bitbuf, bits_to_write, bits_len);
|
||||||
|
|
||||||
|
bytes = buffer_used(&state->bitbuf);
|
||||||
|
stream->next_out = buffer_ptr(&state->bitbuf);
|
||||||
|
stream->avail_out -= bytes;
|
||||||
|
stream->total_out += bytes;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static void flush_write_buffer(struct isal_zstream *stream)
|
static void flush_write_buffer(struct isal_zstream *stream)
|
||||||
{
|
{
|
||||||
struct isal_zstate *state = &stream->internal_state;
|
struct isal_zstate *state = &stream->internal_state;
|
||||||
@@ -211,8 +249,10 @@ static uint32_t write_constant_compressed_stateless(struct isal_zstream *stream,
|
|||||||
/* Assumes the repeated char is either 0 or 0xFF. */
|
/* Assumes the repeated char is either 0 or 0xFF. */
|
||||||
memcpy(stream->next_out, repeated_char_header[repeated_char & 1], HEADER_LENGTH);
|
memcpy(stream->next_out, repeated_char_header[repeated_char & 1], HEADER_LENGTH);
|
||||||
|
|
||||||
if (end_of_stream > 0)
|
if (end_of_stream > 0) {
|
||||||
stream->next_out[0] |= 1;
|
stream->next_out[0] |= 1;
|
||||||
|
state->has_eob_hdr = 1;
|
||||||
|
}
|
||||||
|
|
||||||
memset(stream->next_out + HEADER_LENGTH, 0, rep_bytes);
|
memset(stream->next_out + HEADER_LENGTH, 0, rep_bytes);
|
||||||
stream->avail_out -= HEADER_LENGTH + rep_bytes;
|
stream->avail_out -= HEADER_LENGTH + rep_bytes;
|
||||||
@@ -261,6 +301,8 @@ static uint32_t write_constant_compressed_stateless(struct isal_zstream *stream,
|
|||||||
|
|
||||||
write_bits(&state->bitbuf, END_OF_BLOCK, END_OF_BLOCK_LEN);
|
write_bits(&state->bitbuf, END_OF_BLOCK, END_OF_BLOCK_LEN);
|
||||||
|
|
||||||
|
state->has_eob = 1;
|
||||||
|
|
||||||
stream->next_in += repeated_length;
|
stream->next_in += repeated_length;
|
||||||
stream->avail_in -= repeated_length;
|
stream->avail_in -= repeated_length;
|
||||||
stream->total_in += repeated_length;
|
stream->total_in += repeated_length;
|
||||||
@@ -313,15 +355,25 @@ static int isal_deflate_int_stateless(struct isal_zstream *stream, uint8_t * nex
|
|||||||
if (stream->avail_in == repeated_char_length) {
|
if (stream->avail_in == repeated_char_length) {
|
||||||
if (write_constant_compressed_stateless(stream,
|
if (write_constant_compressed_stateless(stream,
|
||||||
stream->next_in[0],
|
stream->next_in[0],
|
||||||
repeated_char_length, 1) != COMP_OK)
|
repeated_char_length,
|
||||||
|
stream->end_of_stream) != COMP_OK)
|
||||||
return STATELESS_OVERFLOW;
|
return STATELESS_OVERFLOW;
|
||||||
|
|
||||||
#ifndef DEFLATE
|
#ifndef DEFLATE
|
||||||
crc32 = crc32_gzip(0x0, next_in, avail_in);
|
crc32 = crc32_gzip(0x0, next_in, avail_in);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* write_trailer_stateless is required because if flushes out the last of the output */
|
if (stream->internal_state.has_eob_hdr) {
|
||||||
if (write_trailer_stateless(stream, avail_in, crc32) != COMP_OK)
|
if (write_trailer_stateless(stream, avail_in, crc32) != COMP_OK)
|
||||||
|
return STATELESS_OVERFLOW;
|
||||||
|
} else if (stream->avail_out >= 8) {
|
||||||
|
sync_flush_stateless(stream);
|
||||||
|
#ifndef USE_BITBUFB
|
||||||
|
flush_write_buffer(stream);
|
||||||
|
if (stream->internal_state.bitbuf.m_bit_count != 0)
|
||||||
|
return STATELESS_OVERFLOW;
|
||||||
|
#endif
|
||||||
|
} else
|
||||||
return STATELESS_OVERFLOW;
|
return STATELESS_OVERFLOW;
|
||||||
return COMP_OK;
|
return COMP_OK;
|
||||||
|
|
||||||
@@ -329,6 +381,7 @@ static int isal_deflate_int_stateless(struct isal_zstream *stream, uint8_t * nex
|
|||||||
if (write_constant_compressed_stateless
|
if (write_constant_compressed_stateless
|
||||||
(stream, stream->next_in[0], repeated_char_length, 0) != COMP_OK)
|
(stream, stream->next_in[0], repeated_char_length, 0) != COMP_OK)
|
||||||
return STATELESS_OVERFLOW;
|
return STATELESS_OVERFLOW;
|
||||||
|
stream->internal_state.has_eob = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (write_deflate_header_unaligned_stateless(stream) != COMP_OK)
|
if (write_deflate_header_unaligned_stateless(stream) != COMP_OK)
|
||||||
@@ -336,6 +389,10 @@ static int isal_deflate_int_stateless(struct isal_zstream *stream, uint8_t * nex
|
|||||||
if (stream->avail_out < 8)
|
if (stream->avail_out < 8)
|
||||||
return STATELESS_OVERFLOW;
|
return STATELESS_OVERFLOW;
|
||||||
|
|
||||||
|
stream->internal_state.file_start = (uint8_t *) & stream->internal_state.buffer;
|
||||||
|
stream->internal_state.b_bytes_processed = 0;
|
||||||
|
reset_match_history(stream);
|
||||||
|
|
||||||
isal_deflate_body_stateless(stream);
|
isal_deflate_body_stateless(stream);
|
||||||
|
|
||||||
if (!stream->internal_state.has_eob)
|
if (!stream->internal_state.has_eob)
|
||||||
@@ -345,7 +402,17 @@ static int isal_deflate_int_stateless(struct isal_zstream *stream, uint8_t * nex
|
|||||||
crc32 = crc32_gzip(0x0, next_in, avail_in);
|
crc32 = crc32_gzip(0x0, next_in, avail_in);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (write_trailer_stateless(stream, avail_in, crc32) != COMP_OK)
|
if (stream->internal_state.has_eob_hdr) {
|
||||||
|
if (write_trailer_stateless(stream, avail_in, crc32) != COMP_OK)
|
||||||
|
return STATELESS_OVERFLOW;
|
||||||
|
} else if (stream->avail_out >= 8) {
|
||||||
|
sync_flush_stateless(stream);
|
||||||
|
#ifndef USE_BITBUFB
|
||||||
|
flush_write_buffer(stream);
|
||||||
|
if (stream->internal_state.bitbuf.m_bit_count != 0)
|
||||||
|
return STATELESS_OVERFLOW;
|
||||||
|
#endif
|
||||||
|
} else
|
||||||
return STATELESS_OVERFLOW;
|
return STATELESS_OVERFLOW;
|
||||||
|
|
||||||
return COMP_OK;
|
return COMP_OK;
|
||||||
@@ -388,9 +455,12 @@ static int write_stored_block_stateless(struct isal_zstream *stream,
|
|||||||
avail_in -= copy_size;
|
avail_in -= copy_size;
|
||||||
|
|
||||||
/* Handle BFINAL bit */
|
/* Handle BFINAL bit */
|
||||||
if (avail_in == 0)
|
if (avail_in == 0) {
|
||||||
stored_blk_hdr |= 0x1;
|
if (stream->flush == NO_FLUSH || stream->end_of_stream) {
|
||||||
|
stored_blk_hdr |= 0x1;
|
||||||
|
stream->internal_state.has_eob_hdr = 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
memcpy(stream->next_out, &stored_blk_hdr, STORED_BLK_HDR_BZ);
|
memcpy(stream->next_out, &stored_blk_hdr, STORED_BLK_HDR_BZ);
|
||||||
stream->next_out += STORED_BLK_HDR_BZ;
|
stream->next_out += STORED_BLK_HDR_BZ;
|
||||||
|
|
||||||
@@ -401,11 +471,13 @@ static int write_stored_block_stateless(struct isal_zstream *stream,
|
|||||||
} while (avail_in != 0);
|
} while (avail_in != 0);
|
||||||
|
|
||||||
#ifndef DEFLATE
|
#ifndef DEFLATE
|
||||||
gzip_trl = stream->avail_in;
|
if (stream->internal_state.has_eob_hdr) {
|
||||||
gzip_trl <<= 32;
|
gzip_trl = stream->avail_in;
|
||||||
gzip_trl |= crc32 & 0xFFFFFFFF;
|
gzip_trl <<= 32;
|
||||||
memcpy(stream->next_out, &gzip_trl, gzip_trl_bytes);
|
gzip_trl |= crc32 & 0xFFFFFFFF;
|
||||||
stream->next_out += gzip_trl_bytes;
|
memcpy(stream->next_out, &gzip_trl, gzip_trl_bytes);
|
||||||
|
stream->next_out += gzip_trl_bytes;
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
stream->avail_in = 0;
|
stream->avail_in = 0;
|
||||||
@@ -418,10 +490,11 @@ static inline void reset_match_history(struct isal_zstream *stream)
|
|||||||
uint16_t *head = stream->internal_state.head;
|
uint16_t *head = stream->internal_state.head;
|
||||||
int i = 0;
|
int i = 0;
|
||||||
|
|
||||||
for (i = 0; i < sizeof(state->head) / 2; i++)
|
for (i = 0; i < sizeof(state->head) / 2; i++) {
|
||||||
head[i] =
|
head[i] =
|
||||||
(uint16_t) (state->b_bytes_processed + state->buffer - state->file_start -
|
(uint16_t) (state->b_bytes_processed + state->buffer - state->file_start -
|
||||||
(IGZIP_D + 1));
|
(IGZIP_D + 1));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void isal_deflate_init_01(struct isal_zstream *stream)
|
void isal_deflate_init_01(struct isal_zstream *stream)
|
||||||
@@ -458,13 +531,25 @@ void isal_deflate_init_01(struct isal_zstream *stream)
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void isal_deflate_stateless_init(struct isal_zstream *stream)
|
||||||
|
{
|
||||||
|
stream->total_in = 0;
|
||||||
|
stream->total_out = 0;
|
||||||
|
stream->hufftables = (struct isal_hufftables *)&hufftables_default;
|
||||||
|
stream->flush = NO_FLUSH;
|
||||||
|
stream->end_of_stream = 0;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
int isal_deflate_stateless(struct isal_zstream *stream)
|
int isal_deflate_stateless(struct isal_zstream *stream)
|
||||||
{
|
{
|
||||||
uint8_t *next_in = stream->next_in;
|
uint8_t *next_in = stream->next_in;
|
||||||
const uint32_t avail_in = stream->avail_in;
|
const uint32_t avail_in = stream->avail_in;
|
||||||
|
const uint32_t total_in = stream->total_in;
|
||||||
|
|
||||||
uint8_t *next_out = stream->next_out;
|
uint8_t *next_out = stream->next_out;
|
||||||
const uint32_t avail_out = stream->avail_out;
|
const uint32_t avail_out = stream->avail_out;
|
||||||
|
const uint32_t total_out = stream->total_out;
|
||||||
|
|
||||||
uint32_t crc32 = 0;
|
uint32_t crc32 = 0;
|
||||||
uint32_t stored_len;
|
uint32_t stored_len;
|
||||||
@@ -472,6 +557,15 @@ int isal_deflate_stateless(struct isal_zstream *stream)
|
|||||||
uint32_t min_len;
|
uint32_t min_len;
|
||||||
uint32_t select_stored_blk = 0;
|
uint32_t select_stored_blk = 0;
|
||||||
|
|
||||||
|
/* Final block has already been written */
|
||||||
|
stream->internal_state.has_eob_hdr = 0;
|
||||||
|
init(&stream->internal_state.bitbuf);
|
||||||
|
if (stream->flush == NO_FLUSH)
|
||||||
|
stream->end_of_stream = 1;
|
||||||
|
|
||||||
|
if (stream->flush != NO_FLUSH && stream->flush != FULL_FLUSH)
|
||||||
|
return INVALID_FLUSH;
|
||||||
|
|
||||||
if (avail_in == 0)
|
if (avail_in == 0)
|
||||||
stored_len = STORED_BLK_HDR_BZ;
|
stored_len = STORED_BLK_HDR_BZ;
|
||||||
else
|
else
|
||||||
@@ -507,19 +601,26 @@ int isal_deflate_stateless(struct isal_zstream *stream)
|
|||||||
if (!select_stored_blk) {
|
if (!select_stored_blk) {
|
||||||
if (isal_deflate_int_stateless(stream, next_in, avail_in) == COMP_OK)
|
if (isal_deflate_int_stateless(stream, next_in, avail_in) == COMP_OK)
|
||||||
return COMP_OK;
|
return COMP_OK;
|
||||||
|
else {
|
||||||
|
if (stream->flush == FULL_FLUSH) {
|
||||||
|
stream->internal_state.file_start =
|
||||||
|
(uint8_t *) & stream->internal_state.buffer;
|
||||||
|
reset_match_history(stream);
|
||||||
|
}
|
||||||
|
stream->internal_state.has_eob_hdr = 0;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (avail_out < stored_len)
|
if (avail_out < stored_len)
|
||||||
return STATELESS_OVERFLOW;
|
return STATELESS_OVERFLOW;
|
||||||
|
|
||||||
isal_deflate_init(stream);
|
|
||||||
|
|
||||||
stream->next_in = next_in;
|
stream->next_in = next_in;
|
||||||
stream->avail_in = avail_in;
|
stream->avail_in = avail_in;
|
||||||
stream->total_in = 0;
|
stream->total_in = total_in;
|
||||||
|
|
||||||
stream->next_out = next_out;
|
stream->next_out = next_out;
|
||||||
stream->avail_out = avail_out;
|
stream->avail_out = avail_out;
|
||||||
stream->total_out = 0;
|
stream->total_out = total_out;
|
||||||
|
|
||||||
#ifndef DEFLATE
|
#ifndef DEFLATE
|
||||||
crc32 = crc32_gzip(0x0, next_in, avail_in);
|
crc32 = crc32_gzip(0x0, next_in, avail_in);
|
||||||
@@ -654,6 +755,11 @@ static int write_deflate_header_stateless(struct isal_zstream *stream)
|
|||||||
|
|
||||||
memcpy(stream->next_out, hufftables->deflate_hdr, hufftables->deflate_hdr_count);
|
memcpy(stream->next_out, hufftables->deflate_hdr, hufftables->deflate_hdr_count);
|
||||||
|
|
||||||
|
if (stream->end_of_stream == 0)
|
||||||
|
*stream->next_out -= 1;
|
||||||
|
else
|
||||||
|
state->has_eob_hdr = 1;
|
||||||
|
|
||||||
stream->avail_out -= hufftables->deflate_hdr_count;
|
stream->avail_out -= hufftables->deflate_hdr_count;
|
||||||
stream->total_out += hufftables->deflate_hdr_count;
|
stream->total_out += hufftables->deflate_hdr_count;
|
||||||
stream->next_out += hufftables->deflate_hdr_count;
|
stream->next_out += hufftables->deflate_hdr_count;
|
||||||
@@ -692,6 +798,18 @@ static int write_deflate_header_unaligned_stateless(struct isal_zstream *stream)
|
|||||||
header_next = (uint64_t *) hufftables->deflate_hdr;
|
header_next = (uint64_t *) hufftables->deflate_hdr;
|
||||||
header_end = header_next + hufftables->deflate_hdr_count / 8;
|
header_end = header_next + hufftables->deflate_hdr_count / 8;
|
||||||
|
|
||||||
|
header_bits = *header_next;
|
||||||
|
|
||||||
|
if (stream->end_of_stream == 0)
|
||||||
|
header_bits--;
|
||||||
|
else
|
||||||
|
state->has_eob_hdr = 1;
|
||||||
|
|
||||||
|
write_bits(&state->bitbuf, header_bits, 32);
|
||||||
|
header_bits >>= 32;
|
||||||
|
write_bits(&state->bitbuf, header_bits, 32);
|
||||||
|
header_next++;
|
||||||
|
|
||||||
/* Write out Complete Header bits */
|
/* Write out Complete Header bits */
|
||||||
for (; header_next < header_end; header_next++) {
|
for (; header_next < header_end; header_next++) {
|
||||||
header_bits = *header_next;
|
header_bits = *header_next;
|
||||||
@@ -759,7 +877,7 @@ void write_header(struct isal_zstream *stream)
|
|||||||
|
|
||||||
if (state->count == 0 && count > 0) {
|
if (state->count == 0 && count > 0) {
|
||||||
if (!stream->end_of_stream)
|
if (!stream->end_of_stream)
|
||||||
*stream->next_out &= 0xfe;
|
*stream->next_out -= 1;
|
||||||
else
|
else
|
||||||
state->has_eob_hdr = 1;
|
state->has_eob_hdr = 1;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -404,8 +404,10 @@ int inflate_check(uint8_t * z_buf, int z_size, uint8_t * in_buf, int in_size)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (gstream.avail_in != 0)
|
if (gstream.avail_in != 0) {
|
||||||
|
printf("leftover = %d\n", gstream.avail_in);
|
||||||
return INFLATE_LEFTOVER_INPUT;
|
return INFLATE_LEFTOVER_INPUT;
|
||||||
|
}
|
||||||
|
|
||||||
if (gstream.total_out != in_size)
|
if (gstream.total_out != in_size)
|
||||||
return INFLATE_INCORRECT_OUTPUT_SIZE;
|
return INFLATE_INCORRECT_OUTPUT_SIZE;
|
||||||
@@ -699,23 +701,23 @@ int compress_single_pass(uint8_t * data, uint32_t data_size, uint8_t * compresse
|
|||||||
|
|
||||||
/* Statelessly compress the input buffer into the output buffer */
|
/* Statelessly compress the input buffer into the output buffer */
|
||||||
int compress_stateless(uint8_t * data, uint32_t data_size, uint8_t * compressed_buf,
|
int compress_stateless(uint8_t * data, uint32_t data_size, uint8_t * compressed_buf,
|
||||||
uint32_t * compressed_size)
|
uint32_t * compressed_size, uint32_t flush_type)
|
||||||
{
|
{
|
||||||
int ret = IGZIP_COMP_OK;
|
int ret = IGZIP_COMP_OK;
|
||||||
struct isal_zstream stream;
|
struct isal_zstream stream;
|
||||||
|
|
||||||
create_rand_repeat_data((uint8_t *) & stream, sizeof(stream));
|
create_rand_repeat_data((uint8_t *) & stream, sizeof(stream));
|
||||||
|
|
||||||
isal_deflate_init(&stream);
|
isal_deflate_stateless_init(&stream);
|
||||||
|
|
||||||
if (hufftables != NULL)
|
if (hufftables != NULL)
|
||||||
stream.hufftables = hufftables;
|
stream.hufftables = hufftables;
|
||||||
|
|
||||||
stream.avail_in = data_size;
|
stream.avail_in = data_size;
|
||||||
stream.end_of_stream = 1;
|
|
||||||
stream.next_in = data;
|
stream.next_in = data;
|
||||||
stream.flush = NO_FLUSH;
|
stream.flush = flush_type;
|
||||||
|
if (flush_type != NO_FLUSH)
|
||||||
|
stream.end_of_stream = 1;
|
||||||
stream.avail_out = *compressed_size;
|
stream.avail_out = *compressed_size;
|
||||||
stream.next_out = compressed_buf;
|
stream.next_out = compressed_buf;
|
||||||
|
|
||||||
@@ -733,6 +735,8 @@ int compress_stateless(uint8_t * data, uint32_t data_size, uint8_t * compressed_
|
|||||||
if (ret != IGZIP_COMP_OK) {
|
if (ret != IGZIP_COMP_OK) {
|
||||||
if (ret == STATELESS_OVERFLOW)
|
if (ret == STATELESS_OVERFLOW)
|
||||||
return COMPRESS_OUT_BUFFER_OVERFLOW;
|
return COMPRESS_OUT_BUFFER_OVERFLOW;
|
||||||
|
else if (ret == INVALID_FLUSH)
|
||||||
|
return INVALID_FLUSH_ERROR;
|
||||||
else
|
else
|
||||||
return COMPRESS_GENERAL_ERROR;
|
return COMPRESS_GENERAL_ERROR;
|
||||||
}
|
}
|
||||||
@@ -750,6 +754,99 @@ int compress_stateless(uint8_t * data, uint32_t data_size, uint8_t * compressed_
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Statelessly compress the input buffer into the output buffer */
|
||||||
|
int compress_stateless_full_flush(uint8_t * data, uint32_t data_size, uint8_t * compressed_buf,
|
||||||
|
uint32_t * compressed_size)
|
||||||
|
{
|
||||||
|
int ret = IGZIP_COMP_OK;
|
||||||
|
uint8_t *in_buf = NULL, *out_buf = compressed_buf;
|
||||||
|
uint32_t in_size = 0;
|
||||||
|
uint32_t in_processed = 00;
|
||||||
|
struct isal_zstream stream;
|
||||||
|
uint32_t loop_count = 0;
|
||||||
|
|
||||||
|
#ifdef VERBOSE
|
||||||
|
printf("Starting Stateless Compress Full Flush\n");
|
||||||
|
#endif
|
||||||
|
|
||||||
|
create_rand_repeat_data((uint8_t *) & stream, sizeof(stream));
|
||||||
|
|
||||||
|
isal_deflate_stateless_init(&stream);
|
||||||
|
|
||||||
|
if (hufftables != NULL)
|
||||||
|
stream.hufftables = hufftables;
|
||||||
|
|
||||||
|
stream.flush = FULL_FLUSH;
|
||||||
|
stream.end_of_stream = 0;
|
||||||
|
stream.avail_out = *compressed_size;
|
||||||
|
stream.next_out = compressed_buf;
|
||||||
|
|
||||||
|
while (1) {
|
||||||
|
loop_count++;
|
||||||
|
|
||||||
|
/* Randomly choose size of the next out buffer */
|
||||||
|
in_size = rand() % (data_size + 1);
|
||||||
|
|
||||||
|
/* Limit size of buffer to be smaller than maximum */
|
||||||
|
if (in_size >= data_size - in_processed) {
|
||||||
|
in_size = data_size - in_processed;
|
||||||
|
stream.end_of_stream = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
stream.avail_in = in_size;
|
||||||
|
|
||||||
|
if (in_size != 0) {
|
||||||
|
if (in_buf != NULL) {
|
||||||
|
free(in_buf);
|
||||||
|
in_buf = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
in_buf = malloc(in_size);
|
||||||
|
if (in_buf == NULL) {
|
||||||
|
ret = MALLOC_FAILED;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
memcpy(in_buf, data + in_processed, in_size);
|
||||||
|
in_processed += in_size;
|
||||||
|
|
||||||
|
stream.next_in = in_buf;
|
||||||
|
}
|
||||||
|
|
||||||
|
out_buf = stream.next_out;
|
||||||
|
|
||||||
|
ret = isal_deflate_stateless(&stream);
|
||||||
|
assert(stream.internal_state.bitbuf.m_bit_count == 0);
|
||||||
|
|
||||||
|
assert(compressed_buf == stream.next_out - stream.total_out);
|
||||||
|
if (ret)
|
||||||
|
break;
|
||||||
|
|
||||||
|
/* Verify that blocks are independent */
|
||||||
|
ret = inflate_check(out_buf, stream.next_out - out_buf, in_buf, in_size);
|
||||||
|
|
||||||
|
if (ret == INFLATE_INVALID_LOOK_BACK_DISTANCE) {
|
||||||
|
break;
|
||||||
|
} else
|
||||||
|
ret = 0;
|
||||||
|
|
||||||
|
/* Check if the compression is completed */
|
||||||
|
if (in_processed == data_size) {
|
||||||
|
*compressed_size = stream.total_out;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
if (in_buf != NULL)
|
||||||
|
free(in_buf);
|
||||||
|
|
||||||
|
if (ret == STATELESS_OVERFLOW && loop_count >= MAX_LOOPS)
|
||||||
|
ret = COMPRESS_LOOP_COUNT_OVERFLOW;
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
/* Compress the input data into the output buffer where the input buffer and
|
/* Compress the input data into the output buffer where the input buffer and
|
||||||
* is randomly segmented to test for independence of blocks in full flush
|
* is randomly segmented to test for independence of blocks in full flush
|
||||||
* compression*/
|
* compression*/
|
||||||
@@ -913,7 +1010,7 @@ int compress_swap_flush(uint8_t * data, uint32_t data_size, uint8_t * compressed
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Test deflate_stateless */
|
/* Test deflate_stateless */
|
||||||
int test_compress_stateless(uint8_t * in_data, uint32_t in_size)
|
int test_compress_stateless(uint8_t * in_data, uint32_t in_size, uint32_t flush_type)
|
||||||
{
|
{
|
||||||
int ret = IGZIP_COMP_OK;
|
int ret = IGZIP_COMP_OK;
|
||||||
uint32_t z_size, overflow;
|
uint32_t z_size, overflow;
|
||||||
@@ -939,7 +1036,26 @@ int test_compress_stateless(uint8_t * in_data, uint32_t in_size)
|
|||||||
|
|
||||||
create_rand_repeat_data(z_buf, z_size);
|
create_rand_repeat_data(z_buf, z_size);
|
||||||
|
|
||||||
ret = compress_stateless(in_buf, in_size, z_buf, &z_size);
|
/* If flush type is invalid */
|
||||||
|
if (flush_type != NO_FLUSH && flush_type != FULL_FLUSH) {
|
||||||
|
ret = compress_stateless(in_buf, in_size, z_buf, &z_size, flush_type);
|
||||||
|
|
||||||
|
if (ret != INVALID_FLUSH_ERROR)
|
||||||
|
print_error(ret);
|
||||||
|
else
|
||||||
|
ret = 0;
|
||||||
|
|
||||||
|
if (z_buf != NULL)
|
||||||
|
free(z_buf);
|
||||||
|
|
||||||
|
if (in_buf != NULL)
|
||||||
|
free(in_buf);
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Else test valid flush type */
|
||||||
|
ret = compress_stateless(in_buf, in_size, z_buf, &z_size, flush_type);
|
||||||
|
|
||||||
if (!ret)
|
if (!ret)
|
||||||
ret = inflate_check(z_buf, z_size, in_buf, in_size);
|
ret = inflate_check(z_buf, z_size, in_buf, in_size);
|
||||||
@@ -957,6 +1073,7 @@ int test_compress_stateless(uint8_t * in_data, uint32_t in_size)
|
|||||||
free(z_buf);
|
free(z_buf);
|
||||||
z_buf = NULL;
|
z_buf = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
print_error(ret);
|
print_error(ret);
|
||||||
if (ret)
|
if (ret)
|
||||||
return ret;
|
return ret;
|
||||||
@@ -979,7 +1096,7 @@ int test_compress_stateless(uint8_t * in_data, uint32_t in_size)
|
|||||||
|
|
||||||
create_rand_repeat_data(z_buf, z_size);
|
create_rand_repeat_data(z_buf, z_size);
|
||||||
|
|
||||||
ret = compress_stateless(in_buf, in_size, z_buf, &z_size);
|
ret = compress_stateless(in_buf, in_size, z_buf, &z_size, flush_type);
|
||||||
if (!ret)
|
if (!ret)
|
||||||
ret = inflate_check(z_buf, z_size, in_buf, in_size);
|
ret = inflate_check(z_buf, z_size, in_buf, in_size);
|
||||||
#ifdef VERBOSE
|
#ifdef VERBOSE
|
||||||
@@ -1009,7 +1126,7 @@ int test_compress_stateless(uint8_t * in_data, uint32_t in_size)
|
|||||||
return MALLOC_FAILED;
|
return MALLOC_FAILED;
|
||||||
}
|
}
|
||||||
|
|
||||||
overflow = compress_stateless(in_buf, in_size, z_buf, &z_size);
|
overflow = compress_stateless(in_buf, in_size, z_buf, &z_size, flush_type);
|
||||||
|
|
||||||
if (overflow != COMPRESS_OUT_BUFFER_OVERFLOW) {
|
if (overflow != COMPRESS_OUT_BUFFER_OVERFLOW) {
|
||||||
#ifdef VERBOSE
|
#ifdef VERBOSE
|
||||||
@@ -1026,12 +1143,51 @@ int test_compress_stateless(uint8_t * in_data, uint32_t in_size)
|
|||||||
printf("Data: ");
|
printf("Data: ");
|
||||||
print_uint8_t(in_buf, in_size);
|
print_uint8_t(in_buf, in_size);
|
||||||
#endif
|
#endif
|
||||||
ret = OVERFLOW_TEST_ERROR;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
print_error(ret);
|
if (ret) {
|
||||||
|
if (z_buf != NULL) {
|
||||||
|
free(z_buf);
|
||||||
|
z_buf = NULL;
|
||||||
|
}
|
||||||
|
if (in_buf != NULL)
|
||||||
|
free(in_buf);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (flush_type == FULL_FLUSH) {
|
||||||
|
if (z_buf != NULL)
|
||||||
|
free(z_buf);
|
||||||
|
|
||||||
|
z_size = 2 * in_size + MAX_LOOPS * (hdr_bytes + trl_bytes + 5);
|
||||||
|
|
||||||
|
z_buf = malloc(z_size);
|
||||||
|
|
||||||
|
if (z_buf == NULL)
|
||||||
|
return MALLOC_FAILED;
|
||||||
|
|
||||||
|
create_rand_repeat_data(z_buf, z_size);
|
||||||
|
|
||||||
|
/* Else test valid flush type */
|
||||||
|
ret = compress_stateless_full_flush(in_buf, in_size, z_buf, &z_size);
|
||||||
|
|
||||||
|
if (!ret)
|
||||||
|
ret = inflate_check(z_buf, z_size, in_buf, in_size);
|
||||||
|
else if (ret == COMPRESS_LOOP_COUNT_OVERFLOW)
|
||||||
|
ret = 0;
|
||||||
|
|
||||||
|
print_error(ret);
|
||||||
|
#ifdef VERBOSE
|
||||||
|
if (ret) {
|
||||||
|
printf("Compressed array: ");
|
||||||
|
print_uint8_t(z_buf, z_size);
|
||||||
|
printf("\n");
|
||||||
|
printf("Data: ");
|
||||||
|
print_uint8_t(in_buf, in_size);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
if (z_buf != NULL)
|
if (z_buf != NULL)
|
||||||
free(z_buf);
|
free(z_buf);
|
||||||
|
|
||||||
@@ -1315,7 +1471,11 @@ int test_compress_file(char *file_name)
|
|||||||
fread(in_buf, 1, in_size, in_file);
|
fread(in_buf, 1, in_size, in_file);
|
||||||
}
|
}
|
||||||
|
|
||||||
ret |= test_compress_stateless(in_buf, in_size);
|
ret |= test_compress_stateless(in_buf, in_size, NO_FLUSH);
|
||||||
|
ret |= test_compress_stateless(in_buf, in_size, SYNC_FLUSH);
|
||||||
|
#ifndef IGZIP_USE_GZIP_FORMAT
|
||||||
|
ret |= test_compress_stateless(in_buf, in_size, FULL_FLUSH);
|
||||||
|
#endif
|
||||||
ret |= test_compress(in_buf, in_size, NO_FLUSH);
|
ret |= test_compress(in_buf, in_size, NO_FLUSH);
|
||||||
ret |= test_compress(in_buf, in_size, SYNC_FLUSH);
|
ret |= test_compress(in_buf, in_size, SYNC_FLUSH);
|
||||||
ret |= test_compress(in_buf, in_size, FULL_FLUSH);
|
ret |= test_compress(in_buf, in_size, FULL_FLUSH);
|
||||||
@@ -1421,7 +1581,7 @@ int main(int argc, char *argv[])
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (argc > 1) {
|
if (argc > 1) {
|
||||||
printf("igzip_rand_test files: ");
|
printf("igzip_rand_test files: ");
|
||||||
|
|
||||||
for (i = 1; i < argc; i++) {
|
for (i = 1; i < argc; i++) {
|
||||||
ret |= test_compress_file(argv[i]);
|
ret |= test_compress_file(argv[i]);
|
||||||
@@ -1434,13 +1594,13 @@ int main(int argc, char *argv[])
|
|||||||
fin_ret |= ret;
|
fin_ret |= ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
printf("igzip_rand_test stateless: ");
|
printf("igzip_rand_test stateless: ");
|
||||||
|
|
||||||
ret = test_compress_stateless((uint8_t *) str1, sizeof(str1));
|
ret = test_compress_stateless((uint8_t *) str1, sizeof(str1), NO_FLUSH);
|
||||||
if (ret)
|
if (ret)
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
ret |= test_compress_stateless((uint8_t *) str2, sizeof(str2));
|
ret |= test_compress_stateless((uint8_t *) str2, sizeof(str2), NO_FLUSH);
|
||||||
if (ret)
|
if (ret)
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
@@ -1451,7 +1611,7 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
create_rand_repeat_data(in_buf, in_size);
|
create_rand_repeat_data(in_buf, in_size);
|
||||||
|
|
||||||
ret |= test_compress_stateless(in_buf, in_size);
|
ret |= test_compress_stateless(in_buf, in_size, NO_FLUSH);
|
||||||
|
|
||||||
in_buf -= offset;
|
in_buf -= offset;
|
||||||
|
|
||||||
@@ -1464,14 +1624,78 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
for (i = 0; i < RANDOMS / 16; i++) {
|
for (i = 0; i < RANDOMS / 16; i++) {
|
||||||
create_rand_repeat_data(in_buf, PAGE_SIZE);
|
create_rand_repeat_data(in_buf, PAGE_SIZE);
|
||||||
ret |= test_compress_stateless(in_buf, PAGE_SIZE); // good for efence
|
ret |= test_compress_stateless(in_buf, PAGE_SIZE, NO_FLUSH); // good for efence
|
||||||
|
}
|
||||||
|
|
||||||
|
fin_ret |= ret;
|
||||||
|
|
||||||
|
ret = test_compress_stateless((uint8_t *) str1, sizeof(str1), SYNC_FLUSH);
|
||||||
|
if (ret)
|
||||||
|
return ret;
|
||||||
|
|
||||||
|
ret |= test_compress_stateless((uint8_t *) str2, sizeof(str2), SYNC_FLUSH);
|
||||||
|
if (ret)
|
||||||
|
return ret;
|
||||||
|
|
||||||
|
for (i = 0; i < 16; i++) {
|
||||||
|
in_size = rand() % (IBUF_SIZE + 1);
|
||||||
|
offset = rand() % (IBUF_SIZE + 1 - in_size);
|
||||||
|
in_buf += offset;
|
||||||
|
|
||||||
|
create_rand_repeat_data(in_buf, in_size);
|
||||||
|
|
||||||
|
ret |= test_compress_stateless(in_buf, in_size, SYNC_FLUSH);
|
||||||
|
|
||||||
|
in_buf -= offset;
|
||||||
|
|
||||||
|
if (ret)
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
fin_ret |= ret;
|
fin_ret |= ret;
|
||||||
|
|
||||||
printf("%s\n", ret ? "Fail" : "Pass");
|
printf("%s\n", ret ? "Fail" : "Pass");
|
||||||
|
|
||||||
printf("igzip_rand_test NO_FLUSH: ");
|
#ifndef IGZIP_USE_GZIP_FORMAT
|
||||||
|
printf("igzip_rand_test stateless FULL_FLUSH: ");
|
||||||
|
|
||||||
|
ret = test_compress_stateless((uint8_t *) str1, sizeof(str1), FULL_FLUSH);
|
||||||
|
if (ret)
|
||||||
|
return ret;
|
||||||
|
|
||||||
|
ret |= test_compress_stateless((uint8_t *) str2, sizeof(str2), FULL_FLUSH);
|
||||||
|
if (ret)
|
||||||
|
return ret;
|
||||||
|
|
||||||
|
for (i = 0; i < RANDOMS; i++) {
|
||||||
|
in_size = rand() % (IBUF_SIZE + 1);
|
||||||
|
offset = rand() % (IBUF_SIZE + 1 - in_size);
|
||||||
|
in_buf += offset;
|
||||||
|
|
||||||
|
create_rand_repeat_data(in_buf, in_size);
|
||||||
|
|
||||||
|
ret |= test_compress_stateless(in_buf, in_size, FULL_FLUSH);
|
||||||
|
|
||||||
|
in_buf -= offset;
|
||||||
|
|
||||||
|
if (i % (RANDOMS / 16) == 0)
|
||||||
|
printf(".");
|
||||||
|
|
||||||
|
if (ret)
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (i = 0; i < RANDOMS / 16; i++) {
|
||||||
|
create_rand_repeat_data(in_buf, PAGE_SIZE);
|
||||||
|
ret |= test_compress_stateless(in_buf, PAGE_SIZE, FULL_FLUSH); // good for efence
|
||||||
|
}
|
||||||
|
|
||||||
|
fin_ret |= ret;
|
||||||
|
|
||||||
|
printf("%s\n", ret ? "Fail" : "Pass");
|
||||||
|
#endif
|
||||||
|
|
||||||
|
printf("igzip_rand_test stateful NO_FLUSH: ");
|
||||||
|
|
||||||
ret = test_compress((uint8_t *) str1, sizeof(str1), NO_FLUSH);
|
ret = test_compress((uint8_t *) str1, sizeof(str1), NO_FLUSH);
|
||||||
if (ret)
|
if (ret)
|
||||||
@@ -1502,7 +1726,7 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
printf("%s\n", ret ? "Fail" : "Pass");
|
printf("%s\n", ret ? "Fail" : "Pass");
|
||||||
|
|
||||||
printf("igzip_rand_test SYNC_FLUSH: ");
|
printf("igzip_rand_test stateful SYNC_FLUSH: ");
|
||||||
|
|
||||||
ret = test_compress((uint8_t *) str1, sizeof(str1), SYNC_FLUSH);
|
ret = test_compress((uint8_t *) str1, sizeof(str1), SYNC_FLUSH);
|
||||||
if (ret)
|
if (ret)
|
||||||
@@ -1533,7 +1757,7 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
printf("%s\n", ret ? "Fail" : "Pass");
|
printf("%s\n", ret ? "Fail" : "Pass");
|
||||||
|
|
||||||
printf("igzip_rand_test FULL_FLUSH: ");
|
printf("igzip_rand_test stateful FULL_FLUSH: ");
|
||||||
|
|
||||||
ret = test_compress((uint8_t *) str1, sizeof(str1), FULL_FLUSH);
|
ret = test_compress((uint8_t *) str1, sizeof(str1), FULL_FLUSH);
|
||||||
if (ret)
|
if (ret)
|
||||||
@@ -1581,7 +1805,7 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
printf("%s\n", ret ? "Fail" : "Pass");
|
printf("%s\n", ret ? "Fail" : "Pass");
|
||||||
|
|
||||||
printf("igzip_rand_test Change Flush: ");
|
printf("igzip_rand_test stateful Change Flush: ");
|
||||||
|
|
||||||
ret = test_flush((uint8_t *) str1, sizeof(str1));
|
ret = test_flush((uint8_t *) str1, sizeof(str1));
|
||||||
if (ret)
|
if (ret)
|
||||||
@@ -1612,7 +1836,7 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
printf("%s\n", ret ? "Fail" : "Pass");
|
printf("%s\n", ret ? "Fail" : "Pass");
|
||||||
|
|
||||||
printf("igzip rand test finished: %s\n",
|
printf("igzip rand test finished: %s\n",
|
||||||
fin_ret ? "Some tests failed" : "All tests passed");
|
fin_ret ? "Some tests failed" : "All tests passed");
|
||||||
|
|
||||||
return fin_ret != IGZIP_COMP_OK;
|
return fin_ret != IGZIP_COMP_OK;
|
||||||
|
|||||||
@@ -317,6 +317,15 @@ int isal_create_hufftables_subset(struct isal_hufftables * hufftables,
|
|||||||
void isal_deflate_init(struct isal_zstream *stream);
|
void isal_deflate_init(struct isal_zstream *stream);
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Initialize compression stream data structure
|
||||||
|
*
|
||||||
|
* @param stream Structure holding state information on the compression streams.
|
||||||
|
* @returns none
|
||||||
|
*/
|
||||||
|
void isal_deflate_stateless_init(struct isal_zstream *stream);
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Fast data (deflate) compression for storage applications.
|
* @brief Fast data (deflate) compression for storage applications.
|
||||||
*
|
*
|
||||||
|
|||||||
Reference in New Issue
Block a user