Skip to content

Commit

Permalink
[compress] add userdata compression support
Browse files Browse the repository at this point in the history
- implement generic plugin for compression
- add zlib compression support

Signed-off-by: Fabio M. Di Nitto <fdinitto@redhat.com>
  • Loading branch information
fabbione committed Aug 17, 2017
1 parent 7704aed commit 2052faa
Show file tree
Hide file tree
Showing 16 changed files with 700 additions and 10 deletions.
5 changes: 5 additions & 0 deletions configure.ac
Expand Up @@ -134,8 +134,13 @@ AC_CHECK_LIB([pthread], [pthread_create])
AC_CHECK_LIB([m], [ceil])
AC_CHECK_LIB([rt], [clock_gettime])

# crypto libraries checks
PKG_CHECK_MODULES([nss],[nss])

# compress libraries checks
# zlib is cheap because it's pulled in by nss
PKG_CHECK_MODULES([zlib], [zlib])

# Checks for header files.
AC_CHECK_HEADERS([fcntl.h])
AC_CHECK_HEADERS([stdlib.h])
Expand Down
9 changes: 7 additions & 2 deletions libknet/Makefile.am
Expand Up @@ -25,6 +25,8 @@ LIBS =
sources = \
common.c \
compat.c \
compress.c \
compress_zlib.c \
crypto.c \
handle.c \
host.c \
Expand Down Expand Up @@ -52,6 +54,8 @@ pkgconfig_DATA = libknet.pc
noinst_HEADERS = \
common.h \
compat.h \
compress.h \
compress_zlib.h \
crypto.h \
host.h \
internals.h \
Expand All @@ -72,12 +76,13 @@ lib_LTLIBRARIES = libknet.la

libknet_la_SOURCES = $(sources)

libknet_la_CFLAGS = $(nss_CFLAGS)
libknet_la_CFLAGS = $(nss_CFLAGS) $(zlib_CFLAGS)

EXTRA_libknet_la_DEPENDENCIES = $(SYMFILE)

libknet_la_LDFLAGS = -Wl,--version-script=$(srcdir)/$(SYMFILE) \
--export-dynamic \
-version-number $(libversion)

libknet_la_LIBADD = $(nss_LIBS) -lrt -lpthread -lm
libknet_la_LIBADD = $(nss_LIBS) $(zlib_LIBS) \
-lrt -lpthread -lm
123 changes: 123 additions & 0 deletions libknet/compress.c
@@ -0,0 +1,123 @@
/*
* Copyright (C) 2010-2017 Red Hat, Inc. All rights reserved.
*
* Author: Fabio M. Di Nitto <fabbione@kronosnet.org>
*
* This software licensed under GPL-2.0+, LGPL-2.0+
*/

#include "config.h"

#include <stdlib.h>
#include <string.h>
#include <errno.h>

#include "internals.h"
#include "compress.h"
#include "logging.h"
#include "compress_zlib.h"

/*
* internal module switch data
*/

/*
* DO NOT CHANGE ORDER HERE OR ONWIRE COMPATIBILITY
* WILL BREAK!
*
* add after zlib and before NULL/NULL/NULL.
*/

compress_model_t compress_modules_cmds[] = {
{ "none", NULL, NULL, NULL },
{ "zlib", zlib_val_level, zlib_compress, zlib_decompress },
{ NULL, NULL, NULL, NULL },
};

static int get_model(const char *model)
{
int idx = 0;

while (compress_modules_cmds[idx].model_name != NULL) {
if (!strcmp(compress_modules_cmds[idx].model_name, model))
return idx;
idx++;
}
return -1;
}

static int get_max_model(void)
{
int idx = 0;
while (compress_modules_cmds[idx].model_name != NULL) {
idx++;
}
return idx - 1;
}

static int val_level(
knet_handle_t knet_h,
int compress_model,
int compress_level)
{
return compress_modules_cmds[compress_model].val_level(knet_h, compress_level);
}

int compress_init(
knet_handle_t knet_h,
struct knet_handle_compress_cfg *knet_handle_compress_cfg)
{
int cmp_model;

knet_h->compress_max_model = get_max_model();
if (!knet_handle_compress_cfg) {
return 0;
}

log_debug(knet_h, KNET_SUB_COMPRESS,
"Initizializing compress module [%s/%d]",
knet_handle_compress_cfg->compress_model, knet_handle_compress_cfg->compress_level);

cmp_model = get_model(knet_handle_compress_cfg->compress_model);
if (cmp_model < 0) {
log_err(knet_h, KNET_SUB_COMPRESS, "compress model %s not supported", knet_handle_compress_cfg->compress_model);
errno = EINVAL;
return -1;
}

if (cmp_model > 0) {
if (val_level(knet_h, cmp_model, knet_handle_compress_cfg->compress_level) < 0) {
log_err(knet_h, KNET_SUB_COMPRESS, "compress level %d not supported for model %s",
knet_handle_compress_cfg->compress_level, knet_handle_compress_cfg->compress_model);
errno = EINVAL;
return -1;
}

}

knet_h->compress_model = cmp_model;
knet_h->compress_level = knet_handle_compress_cfg->compress_level;

return 0;
}

int compress(
knet_handle_t knet_h,
const unsigned char *buf_in,
const ssize_t buf_in_len,
unsigned char *buf_out,
ssize_t *buf_out_len)
{
return compress_modules_cmds[knet_h->compress_model].compress(knet_h, buf_in, buf_in_len, buf_out, buf_out_len);
}

int decompress(
knet_handle_t knet_h,
int compress_model,
const unsigned char *buf_in,
const ssize_t buf_in_len,
unsigned char *buf_out,
ssize_t *buf_out_len)
{
return compress_modules_cmds[compress_model].decompress(knet_h, buf_in, buf_in_len, buf_out, buf_out_len);
}
49 changes: 49 additions & 0 deletions libknet/compress.h
@@ -0,0 +1,49 @@
/*
* Copyright (C) 2010-2017 Red Hat, Inc. All rights reserved.
*
* Author: Fabio M. Di Nitto <fabbione@kronosnet.org>
*
* This software licensed under GPL-2.0+, LGPL-2.0+
*/

#ifndef __KNET_COMPRESS_H__
#define __KNET_COMPRESS_H__

#include "internals.h"

typedef struct {
const char *model_name;
int (*val_level)(knet_handle_t knet_h,
int compress_level);
int (*compress) (knet_handle_t knet_h,
const unsigned char *buf_in,
const ssize_t buf_in_len,
unsigned char *buf_out,
ssize_t *buf_out_len);
int (*decompress)(knet_handle_t knet_h,
const unsigned char *buf_in,
const ssize_t buf_in_len,
unsigned char *buf_out,
ssize_t *buf_out_len);
} compress_model_t;

int compress_init(
knet_handle_t knet_h,
struct knet_handle_compress_cfg *knet_handle_compress_cfg);

int compress(
knet_handle_t knet_h,
const unsigned char *buf_in,
const ssize_t buf_in_len,
unsigned char *buf_out,
ssize_t *buf_out_len);

int decompress(
knet_handle_t knet_h,
int compress_model,
const unsigned char *buf_in,
const ssize_t buf_in_len,
unsigned char *buf_out,
ssize_t *buf_out_len);

#endif
128 changes: 128 additions & 0 deletions libknet/compress_zlib.c
@@ -0,0 +1,128 @@
/*
* Copyright (C) 2010-2017 Red Hat, Inc. All rights reserved.
*
* Author: Fabio M. Di Nitto <fabbione@kronosnet.org>
*
* This software licensed under GPL-2.0+, LGPL-2.0+
*/

#include "config.h"

#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <zlib.h>

#include "internals.h"
#include "compress_zlib.h"
#include "logging.h"

int zlib_val_level(
knet_handle_t knet_h,
int compress_level)
{
if (compress_level < 0) {
log_err(knet_h, KNET_SUB_ZLIBCOMP, "zlib does not support negative compression level %d",
compress_level);
return -1;
}
if (compress_level > 9) {
log_err(knet_h, KNET_SUB_ZLIBCOMP, "zlib does not support compression level higher than 9");
return -1;
}
if (compress_level == 0) {
log_warn(knet_h, KNET_SUB_ZLIBCOMP, "zlib compress level 0 does NOT perform any compression");
}
return 0;
}

int zlib_compress(
knet_handle_t knet_h,
const unsigned char *buf_in,
const ssize_t buf_in_len,
unsigned char *buf_out,
ssize_t *buf_out_len)
{
int zerr = 0, err = 0;
int savederrno = 0;
uLongf destLen = *buf_out_len;

zerr = compress2(buf_out, &destLen,
buf_in, buf_in_len,
knet_h->compress_level);

*buf_out_len = destLen;

switch(zerr) {
case Z_OK:
err = 0;
savederrno = 0;
break;
case Z_MEM_ERROR:
log_debug(knet_h, KNET_SUB_ZLIBCOMP, "zlib compress mem error");
err = -1;
savederrno = ENOMEM;
break;
case Z_BUF_ERROR:
log_debug(knet_h, KNET_SUB_ZLIBCOMP, "zlib compress buf error");
err = -1;
savederrno = ENOBUFS;
break;
case Z_STREAM_ERROR:
log_debug(knet_h, KNET_SUB_ZLIBCOMP, "zlib compress stream error");
err = -1;
savederrno = EINVAL;
break;
default:
log_debug(knet_h, KNET_SUB_ZLIBCOMP, "zlib compress unknown error");
break;
}

errno = savederrno;
return err;
}

int zlib_decompress(
knet_handle_t knet_h,
const unsigned char *buf_in,
const ssize_t buf_in_len,
unsigned char *buf_out,
ssize_t *buf_out_len)
{
int zerr = 0, err = 0;
int savederrno = 0;
uLongf destLen = *buf_out_len;

zerr = uncompress(buf_out, &destLen,
buf_in, buf_in_len);

*buf_out_len = destLen;

switch(zerr) {
case Z_OK:
err = 0;
savederrno = 0;
break;
case Z_MEM_ERROR:
log_debug(knet_h, KNET_SUB_ZLIBCOMP, "zlib decompress mem error");
err = -1;
savederrno = ENOMEM;
break;
case Z_BUF_ERROR:
log_debug(knet_h, KNET_SUB_ZLIBCOMP, "zlib decompress buf error");
err = -1;
savederrno = ENOBUFS;
break;
case Z_DATA_ERROR:
log_debug(knet_h, KNET_SUB_ZLIBCOMP, "zlib decompress data error");
err = -1;
savederrno = EINVAL;
break;
default:
log_debug(knet_h, KNET_SUB_ZLIBCOMP, "zlib unknown error");
break;
}

errno = savederrno;
return err;
}
32 changes: 32 additions & 0 deletions libknet/compress_zlib.h
@@ -0,0 +1,32 @@
/*
* Copyright (C) 2010-2017 Red Hat, Inc. All rights reserved.
*
* Author: Fabio M. Di Nitto <fabbione@kronosnet.org>
*
* This software licensed under GPL-2.0+, LGPL-2.0+
*/

#ifndef __KNET_COMPRESS_ZLIB_H__
#define __KNET_COMPRESS_ZLIB H__

#include "internals.h"

int zlib_val_level(
knet_handle_t knet_h,
int compress_level);

int zlib_compress(
knet_handle_t knet_h,
const unsigned char *buf_in,
const ssize_t buf_in_len,
unsigned char *buf_out,
ssize_t *buf_out_len);

int zlib_decompress(
knet_handle_t knet_h,
const unsigned char *buf_in,
const ssize_t buf_in_len,
unsigned char *buf_out,
ssize_t *buf_out_len);

#endif

0 comments on commit 2052faa

Please sign in to comment.