2007-12-08 22:42:33 +00:00
|
|
|
///////////////////////////////////////////////////////////////////////////////
|
|
|
|
//
|
|
|
|
/// \file test_filter_flags.c
|
|
|
|
/// \brief Tests Filter Flags coders
|
|
|
|
//
|
|
|
|
// Copyright (C) 2007 Lasse Collin
|
|
|
|
//
|
|
|
|
// This library is free software; you can redistribute it and/or
|
|
|
|
// modify it under the terms of the GNU Lesser General Public
|
|
|
|
// License as published by the Free Software Foundation; either
|
|
|
|
// version 2.1 of the License, or (at your option) any later version.
|
|
|
|
//
|
|
|
|
// This library is distributed in the hope that it will be useful,
|
|
|
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
|
|
// Lesser General Public License for more details.
|
|
|
|
//
|
|
|
|
///////////////////////////////////////////////////////////////////////////////
|
|
|
|
|
|
|
|
#include "tests.h"
|
|
|
|
|
|
|
|
|
|
|
|
static uint8_t buffer[4096];
|
2008-08-28 19:53:15 +00:00
|
|
|
static lzma_filter known_flags;
|
|
|
|
static lzma_filter decoded_flags;
|
2007-12-08 22:42:33 +00:00
|
|
|
static lzma_stream strm = LZMA_STREAM_INIT;
|
|
|
|
|
|
|
|
|
|
|
|
static bool
|
|
|
|
encode(uint32_t known_size)
|
|
|
|
{
|
|
|
|
memcrap(buffer, sizeof(buffer));
|
|
|
|
|
|
|
|
uint32_t tmp;
|
|
|
|
if (lzma_filter_flags_size(&tmp, &known_flags) != LZMA_OK)
|
|
|
|
return true;
|
|
|
|
|
|
|
|
if (tmp != known_size)
|
|
|
|
return true;
|
|
|
|
|
|
|
|
size_t out_pos = 0;
|
2008-08-28 19:53:15 +00:00
|
|
|
if (lzma_filter_flags_encode(&known_flags,
|
|
|
|
buffer, &out_pos, known_size) != LZMA_OK)
|
2007-12-08 22:42:33 +00:00
|
|
|
return true;
|
|
|
|
|
|
|
|
if (out_pos != known_size)
|
|
|
|
return true;
|
|
|
|
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
static bool
|
2008-06-18 15:02:10 +00:00
|
|
|
decode_ret(uint32_t known_size, lzma_ret expected_ret)
|
2007-12-08 22:42:33 +00:00
|
|
|
{
|
|
|
|
memcrap(&decoded_flags, sizeof(decoded_flags));
|
|
|
|
|
2008-06-18 15:02:10 +00:00
|
|
|
size_t pos = 0;
|
|
|
|
if (lzma_filter_flags_decode(&decoded_flags, NULL,
|
|
|
|
buffer, &pos, known_size) != expected_ret
|
|
|
|
|| pos != known_size)
|
2007-12-08 22:42:33 +00:00
|
|
|
return true;
|
|
|
|
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
static bool
|
|
|
|
decode(uint32_t known_size)
|
|
|
|
{
|
2008-06-18 15:02:10 +00:00
|
|
|
if (decode_ret(known_size, LZMA_OK))
|
2007-12-08 22:42:33 +00:00
|
|
|
return true;
|
|
|
|
|
|
|
|
if (known_flags.id != decoded_flags.id)
|
|
|
|
return true;
|
|
|
|
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2008-08-28 19:53:15 +00:00
|
|
|
#if defined(HAVE_ENCODER_SUBBLOCK) && defined(HAVE_DECODER_SUBBLOCK)
|
2007-12-08 22:42:33 +00:00
|
|
|
static void
|
|
|
|
test_subblock(void)
|
|
|
|
{
|
|
|
|
// Test 1
|
|
|
|
known_flags.id = LZMA_FILTER_SUBBLOCK;
|
|
|
|
known_flags.options = NULL;
|
2008-06-18 15:02:10 +00:00
|
|
|
expect(!encode(2));
|
|
|
|
expect(!decode(2));
|
2008-08-28 19:53:15 +00:00
|
|
|
expect(decoded_flags.options == NULL);
|
2007-12-08 22:42:33 +00:00
|
|
|
|
|
|
|
// Test 2
|
2008-06-18 15:02:10 +00:00
|
|
|
buffer[0] = LZMA_FILTER_SUBBLOCK;
|
|
|
|
buffer[1] = 1;
|
|
|
|
buffer[2] = 0;
|
2008-09-13 09:10:43 +00:00
|
|
|
expect(!decode_ret(3, LZMA_OPTIONS_ERROR));
|
2007-12-08 22:42:33 +00:00
|
|
|
}
|
2008-06-18 15:02:10 +00:00
|
|
|
#endif
|
2007-12-08 22:42:33 +00:00
|
|
|
|
|
|
|
|
2008-08-28 19:53:15 +00:00
|
|
|
#if defined(HAVE_ENCODER_X86) && defined(HAVE_DECODER_X86)
|
2007-12-08 22:42:33 +00:00
|
|
|
static void
|
2008-12-31 14:29:39 +00:00
|
|
|
test_bcj(void)
|
2007-12-08 22:42:33 +00:00
|
|
|
{
|
|
|
|
// Test 1
|
|
|
|
known_flags.id = LZMA_FILTER_X86;
|
|
|
|
known_flags.options = NULL;
|
|
|
|
|
2008-06-18 15:02:10 +00:00
|
|
|
expect(!encode(2));
|
|
|
|
expect(!decode(2));
|
2007-12-08 22:42:33 +00:00
|
|
|
expect(decoded_flags.options == NULL);
|
|
|
|
|
|
|
|
// Test 2
|
2008-12-31 14:29:39 +00:00
|
|
|
lzma_options_bcj options;
|
2007-12-08 22:42:33 +00:00
|
|
|
options.start_offset = 0;
|
|
|
|
known_flags.options = &options;
|
2008-06-18 15:02:10 +00:00
|
|
|
expect(!encode(2));
|
|
|
|
expect(!decode(2));
|
2007-12-08 22:42:33 +00:00
|
|
|
expect(decoded_flags.options == NULL);
|
|
|
|
|
|
|
|
// Test 3
|
|
|
|
options.start_offset = 123456;
|
|
|
|
known_flags.options = &options;
|
|
|
|
expect(!encode(6));
|
|
|
|
expect(!decode(6));
|
|
|
|
expect(decoded_flags.options != NULL);
|
|
|
|
|
2008-12-31 14:29:39 +00:00
|
|
|
lzma_options_bcj *decoded = decoded_flags.options;
|
2007-12-08 22:42:33 +00:00
|
|
|
expect(decoded->start_offset == options.start_offset);
|
|
|
|
|
|
|
|
free(decoded);
|
|
|
|
}
|
2008-06-18 15:02:10 +00:00
|
|
|
#endif
|
2007-12-08 22:42:33 +00:00
|
|
|
|
|
|
|
|
2008-08-28 19:53:15 +00:00
|
|
|
#if defined(HAVE_ENCODER_DELTA) && defined(HAVE_DECODER_DELTA)
|
2007-12-08 22:42:33 +00:00
|
|
|
static void
|
|
|
|
test_delta(void)
|
|
|
|
{
|
|
|
|
// Test 1
|
|
|
|
known_flags.id = LZMA_FILTER_DELTA;
|
|
|
|
known_flags.options = NULL;
|
|
|
|
expect(encode(99));
|
|
|
|
|
|
|
|
// Test 2
|
2008-08-28 19:53:15 +00:00
|
|
|
lzma_options_delta options = {
|
|
|
|
.type = LZMA_DELTA_TYPE_BYTE,
|
2008-09-27 20:01:15 +00:00
|
|
|
.dist = 0
|
2008-08-28 19:53:15 +00:00
|
|
|
};
|
2007-12-08 22:42:33 +00:00
|
|
|
known_flags.options = &options;
|
|
|
|
expect(encode(99));
|
|
|
|
|
|
|
|
// Test 3
|
2008-09-27 20:01:15 +00:00
|
|
|
options.dist = LZMA_DELTA_DIST_MIN;
|
2008-06-18 15:02:10 +00:00
|
|
|
expect(!encode(3));
|
|
|
|
expect(!decode(3));
|
2008-09-27 20:01:15 +00:00
|
|
|
expect(((lzma_options_delta *)(decoded_flags.options))->dist
|
|
|
|
== options.dist);
|
2007-12-08 22:42:33 +00:00
|
|
|
|
|
|
|
free(decoded_flags.options);
|
|
|
|
|
|
|
|
// Test 4
|
2008-09-27 20:01:15 +00:00
|
|
|
options.dist = LZMA_DELTA_DIST_MAX;
|
2008-06-18 15:02:10 +00:00
|
|
|
expect(!encode(3));
|
|
|
|
expect(!decode(3));
|
2008-09-27 20:01:15 +00:00
|
|
|
expect(((lzma_options_delta *)(decoded_flags.options))->dist
|
|
|
|
== options.dist);
|
2007-12-08 22:42:33 +00:00
|
|
|
|
|
|
|
free(decoded_flags.options);
|
|
|
|
|
|
|
|
// Test 5
|
2008-09-27 20:01:15 +00:00
|
|
|
options.dist = LZMA_DELTA_DIST_MAX + 1;
|
2007-12-08 22:42:33 +00:00
|
|
|
expect(encode(99));
|
|
|
|
}
|
2008-06-18 15:02:10 +00:00
|
|
|
#endif
|
2007-12-08 22:42:33 +00:00
|
|
|
|
2008-08-28 19:53:15 +00:00
|
|
|
/*
|
2008-06-18 15:02:10 +00:00
|
|
|
#ifdef HAVE_FILTER_LZMA
|
2007-12-08 22:42:33 +00:00
|
|
|
static void
|
|
|
|
validate_lzma(void)
|
|
|
|
{
|
|
|
|
const lzma_options_lzma *known = known_flags.options;
|
|
|
|
const lzma_options_lzma *decoded = decoded_flags.options;
|
|
|
|
|
|
|
|
expect(known->dictionary_size <= decoded->dictionary_size);
|
|
|
|
|
|
|
|
if (known->dictionary_size == 1)
|
|
|
|
expect(decoded->dictionary_size == 1);
|
|
|
|
else
|
|
|
|
expect(known->dictionary_size + known->dictionary_size / 2
|
|
|
|
> decoded->dictionary_size);
|
|
|
|
|
|
|
|
expect(known->literal_context_bits == decoded->literal_context_bits);
|
|
|
|
expect(known->literal_pos_bits == decoded->literal_pos_bits);
|
|
|
|
expect(known->pos_bits == decoded->pos_bits);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
static void
|
|
|
|
test_lzma(void)
|
|
|
|
{
|
|
|
|
// Test 1
|
2008-09-27 16:09:21 +00:00
|
|
|
known_flags.id = LZMA_FILTER_LZMA1;
|
2007-12-08 22:42:33 +00:00
|
|
|
known_flags.options = NULL;
|
|
|
|
expect(encode(99));
|
|
|
|
|
|
|
|
// Test 2
|
|
|
|
lzma_options_lzma options = {
|
|
|
|
.dictionary_size = 0,
|
|
|
|
.literal_context_bits = 0,
|
|
|
|
.literal_pos_bits = 0,
|
|
|
|
.pos_bits = 0,
|
|
|
|
.preset_dictionary = NULL,
|
|
|
|
.preset_dictionary_size = 0,
|
|
|
|
.mode = LZMA_MODE_INVALID,
|
|
|
|
.fast_bytes = 0,
|
|
|
|
.match_finder = LZMA_MF_INVALID,
|
|
|
|
.match_finder_cycles = 0,
|
|
|
|
};
|
|
|
|
|
|
|
|
// Test 3 (empty dictionary not allowed)
|
|
|
|
known_flags.options = &options;
|
|
|
|
expect(encode(99));
|
|
|
|
|
|
|
|
// Test 4 (brute-force test some valid dictionary sizes)
|
2008-06-18 15:02:10 +00:00
|
|
|
options.dictionary_size = LZMA_DICTIONARY_SIZE_MIN;
|
2007-12-08 22:42:33 +00:00
|
|
|
while (options.dictionary_size != LZMA_DICTIONARY_SIZE_MAX) {
|
|
|
|
if (++options.dictionary_size == 5000)
|
|
|
|
options.dictionary_size = LZMA_DICTIONARY_SIZE_MAX - 5;
|
|
|
|
|
2008-06-18 15:02:10 +00:00
|
|
|
expect(!encode(4));
|
|
|
|
expect(!decode(4));
|
2007-12-08 22:42:33 +00:00
|
|
|
validate_lzma();
|
|
|
|
|
|
|
|
free(decoded_flags.options);
|
|
|
|
}
|
|
|
|
|
|
|
|
// Test 5 (too big dictionary size)
|
|
|
|
options.dictionary_size = LZMA_DICTIONARY_SIZE_MAX + 1;
|
|
|
|
expect(encode(99));
|
|
|
|
|
|
|
|
// Test 6 (brute-force test lc/lp/pb)
|
2008-06-18 15:02:10 +00:00
|
|
|
options.dictionary_size = LZMA_DICTIONARY_SIZE_MIN;
|
2007-12-08 22:42:33 +00:00
|
|
|
for (uint32_t lc = LZMA_LITERAL_CONTEXT_BITS_MIN;
|
|
|
|
lc <= LZMA_LITERAL_CONTEXT_BITS_MAX; ++lc) {
|
|
|
|
for (uint32_t lp = LZMA_LITERAL_POS_BITS_MIN;
|
|
|
|
lp <= LZMA_LITERAL_POS_BITS_MAX; ++lp) {
|
|
|
|
for (uint32_t pb = LZMA_POS_BITS_MIN;
|
|
|
|
pb <= LZMA_POS_BITS_MAX; ++pb) {
|
2008-06-20 14:16:32 +00:00
|
|
|
if (lc + lp > LZMA_LITERAL_BITS_MAX)
|
|
|
|
continue;
|
|
|
|
|
2007-12-08 22:42:33 +00:00
|
|
|
options.literal_context_bits = lc;
|
|
|
|
options.literal_pos_bits = lp;
|
|
|
|
options.pos_bits = pb;
|
|
|
|
|
2008-06-18 15:02:10 +00:00
|
|
|
expect(!encode(4));
|
|
|
|
expect(!decode(4));
|
2007-12-08 22:42:33 +00:00
|
|
|
validate_lzma();
|
|
|
|
|
|
|
|
free(decoded_flags.options);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2008-06-18 15:02:10 +00:00
|
|
|
#endif
|
2008-08-28 19:53:15 +00:00
|
|
|
*/
|
2007-12-08 22:42:33 +00:00
|
|
|
|
|
|
|
int
|
2007-12-09 09:03:28 +00:00
|
|
|
main(void)
|
2007-12-08 22:42:33 +00:00
|
|
|
{
|
2008-08-28 19:53:15 +00:00
|
|
|
#if defined(HAVE_ENCODER_SUBBLOCK) && defined(HAVE_DECODER_SUBBLOCK)
|
2007-12-08 22:42:33 +00:00
|
|
|
test_subblock();
|
2008-06-18 15:02:10 +00:00
|
|
|
#endif
|
2008-08-28 19:53:15 +00:00
|
|
|
#if defined(HAVE_ENCODER_X86) && defined(HAVE_DECODER_X86)
|
2008-12-31 14:29:39 +00:00
|
|
|
test_bcj();
|
2008-06-18 15:02:10 +00:00
|
|
|
#endif
|
2008-08-28 19:53:15 +00:00
|
|
|
#if defined(HAVE_ENCODER_DELTA) && defined(HAVE_DECODER_DELTA)
|
2007-12-08 22:42:33 +00:00
|
|
|
test_delta();
|
2008-06-18 15:02:10 +00:00
|
|
|
#endif
|
2008-08-28 19:53:15 +00:00
|
|
|
// #ifdef HAVE_FILTER_LZMA
|
|
|
|
// test_lzma();
|
|
|
|
// #endif
|
2007-12-08 22:42:33 +00:00
|
|
|
|
|
|
|
lzma_end(&strm);
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|