Add checks in initialization code

This commit is contained in:
Stella Lau 2017-07-27 15:37:37 -07:00
parent c105f605e6
commit 627621839c
4 changed files with 61 additions and 19 deletions

View File

@ -111,13 +111,25 @@ struct LDM_hashTable {
/** /**
* Create a hash table that can contain size elements. * Create a hash table that can contain size elements.
* The number of buckets is determined by size >> HASH_BUCKET_SIZE_LOG. * The number of buckets is determined by size >> HASH_BUCKET_SIZE_LOG.
*
* Returns NULL if table creation failed.
*/ */
static LDM_hashTable *HASH_createTable(U32 size) { static LDM_hashTable *HASH_createTable(U32 size) {
LDM_hashTable *table = malloc(sizeof(LDM_hashTable)); LDM_hashTable *table = malloc(sizeof(LDM_hashTable));
if (!table) return NULL;
table->numBuckets = size >> HASH_BUCKET_SIZE_LOG; table->numBuckets = size >> HASH_BUCKET_SIZE_LOG;
table->numEntries = size; table->numEntries = size;
table->entries = calloc(size, sizeof(LDM_hashEntry)); table->entries = calloc(size, sizeof(LDM_hashEntry));
table->bucketOffsets = calloc(size >> HASH_BUCKET_SIZE_LOG, sizeof(BYTE)); table->bucketOffsets = calloc(size >> HASH_BUCKET_SIZE_LOG, sizeof(BYTE));
if (!table->entries || !table->bucketOffsets) {
free(table->bucketOffsets);
free(table->entries);
free(table);
return NULL;
}
return table; return table;
} }
@ -566,7 +578,7 @@ static void LDM_putHashOfCurrentPosition(LDM_CCtx *cctx) {
putHashOfCurrentPositionFromHash(cctx, hash); putHashOfCurrentPositionFromHash(cctx, hash);
} }
void LDM_initializeCCtx(LDM_CCtx *cctx, size_t LDM_initializeCCtx(LDM_CCtx *cctx,
const void *src, size_t srcSize, const void *src, size_t srcSize,
void *dst, size_t maxDstSize) { void *dst, size_t maxDstSize) {
cctx->isize = srcSize; cctx->isize = srcSize;
@ -590,16 +602,20 @@ void LDM_initializeCCtx(LDM_CCtx *cctx,
#else #else
cctx->hashTable = HASH_createTable(LDM_HASHTABLESIZE_U32); cctx->hashTable = HASH_createTable(LDM_HASHTABLESIZE_U32);
#endif #endif
if (!cctx->hashTable) return 1;
cctx->stats.minOffset = UINT_MAX; cctx->stats.minOffset = UINT_MAX;
cctx->stats.windowSizeLog = LDM_WINDOW_SIZE_LOG; cctx->stats.windowSizeLog = LDM_WINDOW_SIZE_LOG;
cctx->stats.hashTableSizeLog = LDM_MEMORY_USAGE; cctx->stats.hashTableSizeLog = LDM_MEMORY_USAGE;
cctx->lastPosHashed = NULL; cctx->lastPosHashed = NULL;
cctx->step = 1; // Fixed to be 1 for now. Changing may break things. cctx->step = 1; // Fixed to be 1 for now. Changing may break things.
cctx->nextIp = cctx->ip + cctx->step; cctx->nextIp = cctx->ip + cctx->step;
cctx->nextPosHashed = 0; cctx->nextPosHashed = 0;
return 0;
} }
void LDM_destroyCCtx(LDM_CCtx *cctx) { void LDM_destroyCCtx(LDM_CCtx *cctx) {
@ -726,7 +742,10 @@ size_t LDM_compress(const void *src, size_t srcSize,
U64 forwardMatchLength = 0; U64 forwardMatchLength = 0;
U64 backwardsMatchLength = 0; U64 backwardsMatchLength = 0;
LDM_initializeCCtx(&cctx, src, srcSize, dst, maxDstSize); if (LDM_initializeCCtx(&cctx, src, srcSize, dst, maxDstSize)) {
// Initialization failed.
return 0;
}
#ifdef OUTPUT_CONFIGURATION #ifdef OUTPUT_CONFIGURATION
LDM_outputConfiguration(); LDM_outputConfiguration();
@ -744,8 +763,8 @@ size_t LDM_compress(const void *src, size_t srcSize,
* is less than the minimum match length), then stop searching for matches * is less than the minimum match length), then stop searching for matches
* and encode the final literals. * and encode the final literals.
*/ */
while (LDM_findBestMatch(&cctx, &match, &forwardMatchLength, while (!LDM_findBestMatch(&cctx, &match, &forwardMatchLength,
&backwardsMatchLength) == 0) { &backwardsMatchLength)) {
#ifdef COMPUTE_STATS #ifdef COMPUTE_STATS
cctx.stats.numMatches++; cctx.stats.numMatches++;

View File

@ -82,6 +82,7 @@ typedef struct LDM_DCtx LDM_DCtx;
/** /**
* Compresses src into dst. * Compresses src into dst.
* Returns the compressed size if successful, 0 otherwise.
* *
* NB: This currently ignores maxDstSize and assumes enough space is available. * NB: This currently ignores maxDstSize and assumes enough space is available.
* *
@ -113,8 +114,10 @@ size_t LDM_compress(const void *src, size_t srcSize,
* Initialize the compression context. * Initialize the compression context.
* *
* Allocates memory for the hash table. * Allocates memory for the hash table.
*
* Returns 0 if successful, 1 otherwise.
*/ */
void LDM_initializeCCtx(LDM_CCtx *cctx, size_t LDM_initializeCCtx(LDM_CCtx *cctx,
const void *src, size_t srcSize, const void *src, size_t srcSize,
void *dst, size_t maxDstSize); void *dst, size_t maxDstSize);

View File

@ -2,19 +2,29 @@
#include "ldm.h" #include "ldm.h"
/**
* This function reads the header at the beginning of src and writes
* the compressed and decompressed size to compressedSize and
* decompressedSize.
*
* The header consists of 16 bytes: 8 bytes each in little-endian format
* of the compressed size and the decompressed size.
*/
void LDM_readHeader(const void *src, U64 *compressedSize, void LDM_readHeader(const void *src, U64 *compressedSize,
U64 *decompressedSize) { U64 *decompressedSize) {
const BYTE *ip = (const BYTE *)src; const BYTE *ip = (const BYTE *)src;
*compressedSize = MEM_readLE64(ip); *compressedSize = MEM_readLE64(ip);
ip += sizeof(U64); *decompressedSize = MEM_readLE64(ip + 8);
*decompressedSize = MEM_readLE64(ip);
// ip += sizeof(U64);
} }
/**
* Writes the 16-byte header (8-bytes each of the compressedSize and
* decompressedSize in little-endian format) to memPtr.
*/
void LDM_writeHeader(void *memPtr, U64 compressedSize, void LDM_writeHeader(void *memPtr, U64 compressedSize,
U64 decompressedSize) { U64 decompressedSize) {
MEM_write64(memPtr, compressedSize); MEM_writeLE64(memPtr, compressedSize);
MEM_write64((BYTE *)memPtr + 8, decompressedSize); MEM_writeLE64((BYTE *)memPtr + 8, decompressedSize);
} }
struct LDM_DCtx { struct LDM_DCtx {

View File

@ -12,7 +12,7 @@
#include "ldm.h" #include "ldm.h"
#include "zstd.h" #include "zstd.h"
// #define DECOMPRESS_AND_VERIFY #define DECOMPRESS_AND_VERIFY
/* Compress file given by fname and output to oname. /* Compress file given by fname and output to oname.
* Returns 0 if successful, error code otherwise. * Returns 0 if successful, error code otherwise.
@ -186,9 +186,18 @@ static int compare(FILE *fp0, FILE *fp1) {
} }
/* Verify the input file is the same as the decompressed file. */ /* Verify the input file is the same as the decompressed file. */
static void verify(const char *inpFilename, const char *decFilename) { static int verify(const char *inpFilename, const char *decFilename) {
FILE *inpFp = fopen(inpFilename, "rb"); FILE *inpFp, *decFp;
FILE *decFp = fopen(decFilename, "rb");
if ((inpFp = fopen(inpFilename, "rb")) == NULL) {
perror("Could not open input file\n");
return 1;
}
if ((decFp = fopen(decFilename, "rb")) == NULL) {
perror("Could not open decompressed file\n");
return 1;
}
printf("verify : %s <-> %s\n", inpFilename, decFilename); printf("verify : %s <-> %s\n", inpFilename, decFilename);
{ {
@ -202,6 +211,7 @@ static void verify(const char *inpFilename, const char *decFilename) {
fclose(decFp); fclose(decFp);
fclose(inpFp); fclose(inpFp);
return 0;
} }
#endif #endif