From 0f868ed3e85538f73ab3262e4bec864507652a0a Mon Sep 17 00:00:00 2001
From: Dominik Loidolt <dominik.loidolt@univie.ac.at>
Date: Tue, 27 Jun 2023 19:16:25 +0200
Subject: [PATCH] Change max_used_bit from global variable to cmp_cfg field

---
 cmp_tool.c                                |   1 +
 include/cmp_data_types.h                  |  92 ----
 include/cmp_entity.h                      |   3 -
 include/cmp_icu.h                         |   6 +
 include/cmp_max_used_bits.h               |  71 +++
 include/cmp_max_used_bits_list.h          |  39 ++
 include/cmp_support.h                     |   6 +-
 include/list.h                            | 437 +++++++++++++++
 lib/cmp_data_types.c                      |  79 +--
 lib/cmp_entity.c                          | 158 +-----
 lib/cmp_icu.c                             | 133 +++--
 lib/cmp_max_used_bits.c                   | 148 +++++
 lib/cmp_max_used_bits_list.c              | 140 +++++
 lib/cmp_rdcu_cfg.c                        |   1 +
 lib/cmp_support.c                         |  73 ++-
 lib/decmp.c                               | 225 ++++++--
 lib/meson.build                           |   4 +-
 test/cmp_data_types/test_cmp_data_types.c |  63 ---
 test/cmp_decmp/test_cmp_decmp.c           | 226 ++++----
 test/cmp_entity/test_cmp_entity.c         | 626 +---------------------
 test/cmp_icu/test_cmp_icu.c               | 375 +++++++------
 test/cmp_icu/test_decmp.c                 | 626 +++++++++++++++++++++-
 22 files changed, 2138 insertions(+), 1394 deletions(-)
 create mode 100644 include/cmp_max_used_bits.h
 create mode 100644 include/cmp_max_used_bits_list.h
 create mode 100644 include/list.h
 create mode 100644 lib/cmp_max_used_bits.c
 create mode 100644 lib/cmp_max_used_bits_list.c

diff --git a/cmp_tool.c b/cmp_tool.c
index 6532bfc..890e167 100644
--- a/cmp_tool.c
+++ b/cmp_tool.c
@@ -157,6 +157,7 @@ int main(int argc, char **argv)
 	struct cmp_cfg cfg = {0}; /* compressor configuration struct */
 
 	cfg.data_type = DATA_TYPE_IMAGETTE; /* use imagette as default data type */
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE; /* define max_used_bits default */
 
 	/* show help if no arguments are provided */
 	if (argc < 2) {
diff --git a/include/cmp_data_types.h b/include/cmp_data_types.h
index 693a953..734621e 100644
--- a/include/cmp_data_types.h
+++ b/include/cmp_data_types.h
@@ -43,90 +43,6 @@
 /* size of the source data header structure for multi entry packet */
 #define MULTI_ENTRY_HDR_SIZE 12
 
-#define MAX_USED_NC_IMAGETTE_BITS		16
-#define MAX_USED_SATURATED_IMAGETTE_BITS	16 /* TBC */
-#define MAX_USED_FC_IMAGETTE_BITS		16 /* TBC */
-
-#define MAX_USED_F_FX_BITS	21 /* max exp. int value: (1.078*10^5)/0.1 = 1,078,000 -> 21 bits */
-#define MAX_USED_F_EFX_BITS	MAX_USED_F_FX_BITS /* we use the same as f_fx */
-#define MAX_USED_F_NCOB_BITS	20 /* max exp. int value: 6/10^−5 = 6*10^5 -> 20 bits */
-#define MAX_USED_F_ECOB_BITS	32 /* TBC */
-
-#define MAX_USED_S_FX_EXPOSURE_FLAGS_BITS	2 /* 2 flags + 6 spare bits */
-#define MAX_USED_S_FX_BITS			24 /* max exp. int value: (1.078*10^5-34.71)/0.01 = 10,780,000-> 24 bits */
-#define MAX_USED_S_EFX_BITS			MAX_USED_S_FX_BITS /* we use the same as s_fx */
-#define MAX_USED_S_NCOB_BITS			MAX_USED_F_NCOB_BITS
-#define MAX_USED_S_ECOB_BITS			32 /* TBC */
-
-#define MAX_USED_L_FX_EXPOSURE_FLAGS_BITS	24 /* 24 flags */
-#define MAX_USED_L_FX_BITS			MAX_USED_S_FX_BITS
-#define MAX_USED_L_FX_VARIANCE_BITS		32 /* no maximum value is given in PLATO-LESIA-PDC-TN-0054 */
-#define MAX_USED_L_EFX_BITS			MAX_USED_L_FX_BITS /* we use the same as l_fx */
-#define MAX_USED_L_NCOB_BITS			MAX_USED_F_NCOB_BITS
-#define MAX_USED_L_ECOB_BITS			32 /* TBC */
-#define MAX_USED_L_COB_VARIANCE_BITS		25 /* max exp int value: 0.1739/10^−8 = 17390000 -> 25 bits */
-
-#define MAX_USED_NC_OFFSET_MEAN_BITS		2 /* no maximum value is given in PLATO-LESIA-PDC-TN-0054 */
-#define MAX_USED_NC_OFFSET_VARIANCE_BITS	10 /* max exp. int value: 9.31/0.01 = 931 -> 10 bits */
-
-#define MAX_USED_NC_BACKGROUND_MEAN_BITS		16 /* max exp. int value: (391.8-(-50))/0.01 = 44,180 -> 16 bits */
-#define MAX_USED_NC_BACKGROUND_VARIANCE_BITS		16 /* max exp. int value: 6471/0.1 = 64710 -> 16 bit */
-#define MAX_USED_NC_BACKGROUND_OUTLIER_PIXELS_BITS	5 /* maximum = 16 -> 5 bits */
-
-#define MAX_USED_SMEARING_MEAN_BITS		15 /* max exp. int value: (219.9 - -50)/0.01 = 26.990 */
-#define MAX_USED_SMEARING_VARIANCE_MEAN_BITS	16 /* no maximum value is given in PLATO-LESIA-PDC-TN-0054 */
-#define MAX_USED_SMEARING_OUTLIER_PIXELS_BITS	11 /* maximum = 1200 -> 11 bits */
-
-#define MAX_USED_FC_OFFSET_MEAN_BITS		32 /* no maximum value is given in PLATO-LESIA-PDC-TN-0054 */
-#define MAX_USED_FC_OFFSET_VARIANCE_BITS	9  /* max exp. int value: 342/1 = 342 -> 9 bits */
-#define MAX_USED_FC_OFFSET_PIXEL_IN_ERROR_BITS	16 /* TBC */
-
-#define MAX_USED_FC_BACKGROUND_MEAN_BITS		10 /* max exp. int value: (35.76-(-50))/0.1 = 858 -> 10 bits*/
-#define MAX_USED_FC_BACKGROUND_VARIANCE_BITS		6 /* max exp. int value: 53.9/1 = 54 -> 6 bits */
-#define MAX_USED_FC_BACKGROUND_OUTLIER_PIXELS_BITS	16 /* TBC */
-
-
-/**
- * @brief Structure holding the maximum length of the different data product types in bits
- */
-
-struct cmp_max_used_bits {
-	uint8_t version;
-	unsigned int s_exp_flags;
-	unsigned int s_fx;
-	unsigned int s_efx;
-	unsigned int s_ncob; /* s_ncob_x and s_ncob_y */
-	unsigned int s_ecob; /* s_ecob_x and s_ncob_y */
-	unsigned int f_fx;
-	unsigned int f_efx;
-	unsigned int f_ncob; /* f_ncob_x and f_ncob_y */
-	unsigned int f_ecob; /* f_ecob_x and f_ncob_y */
-	unsigned int l_exp_flags;
-	unsigned int l_fx;
-	unsigned int l_fx_variance;
-	unsigned int l_efx;
-	unsigned int l_ncob; /* l_ncob_x and l_ncob_y */
-	unsigned int l_ecob; /* l_ecob_x and l_ncob_y */
-	unsigned int l_cob_variance; /* l_cob_x_variance and l_cob_y_variance */
-	unsigned int nc_imagette;
-	unsigned int saturated_imagette;
-	unsigned int nc_offset_mean;
-	unsigned int nc_offset_variance;
-	unsigned int nc_background_mean;
-	unsigned int nc_background_variance;
-	unsigned int nc_background_outlier_pixels;
-	unsigned int smearing_mean;
-	unsigned int smearing_variance_mean;
-	unsigned int smearing_outlier_pixels;
-	unsigned int fc_imagette;
-	unsigned int fc_offset_mean;
-	unsigned int fc_offset_variance;
-	unsigned int fc_offset_pixel_in_error;
-	unsigned int fc_background_mean;
-	unsigned int fc_background_variance;
-	unsigned int fc_background_outlier_pixels;
-};
-
 
 /**
  * @brief source data header structure for multi entry packet
@@ -334,14 +250,6 @@ struct smearing {
 } __attribute__((packed));
 
 
-/*
- * Set and read the max_used_bits registry, which specify how many bits are
- * needed to represent the highest possible value.
- */
-uint8_t cmp_get_max_used_bits_version(void);
-struct cmp_max_used_bits cmp_get_max_used_bits(void);
-void cmp_set_max_used_bits(const struct cmp_max_used_bits *set_max_used_bits);
-
 
 size_t size_of_a_sample(enum cmp_data_type data_type);
 uint32_t cmp_cal_size_of_data(uint32_t samples, enum cmp_data_type data_type);
diff --git a/include/cmp_entity.h b/include/cmp_entity.h
index 35bb79d..8f6d657 100644
--- a/include/cmp_entity.h
+++ b/include/cmp_entity.h
@@ -159,9 +159,6 @@ size_t cmp_ent_build(struct cmp_entity *ent, uint32_t version_id,
 		     uint64_t start_time, uint64_t end_time, uint16_t model_id,
 		     uint8_t model_counter, struct cmp_cfg *cfg, int cmp_size_bits);
 
-/* read in a compression entity header */
-int cmp_ent_read_header(struct cmp_entity *ent, struct cmp_cfg *cfg);
-
 /*
  * write the compression parameters from a compression configuration into the
  * compression entity header
diff --git a/include/cmp_icu.h b/include/cmp_icu.h
index 4cba66f..75f8114 100644
--- a/include/cmp_icu.h
+++ b/include/cmp_icu.h
@@ -28,14 +28,17 @@
 struct cmp_cfg cmp_cfg_icu_create(enum cmp_data_type data_type, enum cmp_mode cmp_mode,
 				  uint32_t model_value, uint32_t lossy_par);
 
+/* set up the different data buffers for an ICU compression */
 uint32_t cmp_cfg_icu_buffers(struct cmp_cfg *cfg, void *data_to_compress,
 			     uint32_t data_samples, void *model_of_data,
 			     void *updated_model, uint32_t *compressed_data,
 			     uint32_t compressed_data_len_samples);
 
+ /* set up the configuration parameters for an ICU imagette compression */
 int cmp_cfg_icu_imagette(struct cmp_cfg *cfg, uint32_t cmp_par,
 			 uint32_t spillover_par);
 
+/* set up the configuration parameters for a flux/COB compression */
 int cmp_cfg_fx_cob(struct cmp_cfg *cfg,
 		   uint32_t cmp_par_exp_flags, uint32_t spillover_exp_flags,
 		   uint32_t cmp_par_fx, uint32_t spillover_fx,
@@ -44,11 +47,14 @@ int cmp_cfg_fx_cob(struct cmp_cfg *cfg,
 		   uint32_t cmp_par_ecob, uint32_t spillover_ecob,
 		   uint32_t cmp_par_fx_cob_variance, uint32_t spillover_fx_cob_variance);
 
+/* set up the configuration parameters for an auxiliary science data compression */
 int cmp_cfg_aux(struct cmp_cfg *cfg,
 		uint32_t cmp_par_mean, uint32_t spillover_mean,
 		uint32_t cmp_par_variance, uint32_t spillover_variance,
 		uint32_t cmp_par_pixels_error, uint32_t spillover_pixels_error);
 
+/* set up the max_used_bits used for the compression */
+int cmp_cfg_icu_max_used_bits(struct cmp_cfg *cfg, const struct cmp_max_used_bits *max_used_bits_repo);
 
 /* start the compression */
 int icu_compress_data(const struct cmp_cfg *cfg);
diff --git a/include/cmp_max_used_bits.h b/include/cmp_max_used_bits.h
new file mode 100644
index 0000000..ba9db08
--- /dev/null
+++ b/include/cmp_max_used_bits.h
@@ -0,0 +1,71 @@
+/**
+ * @file   cmp_max_used_bits.h
+ * @author Dominik Loidolt (dominik.loidolt@univie.ac.at)
+ * @date   2023
+ *
+ * @copyright GPLv2
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * @brief definition and consents of the cmp_max_used_bits structure
+ */
+
+#ifndef CMP_MAX_USED_BITS_H
+#define CMP_MAX_USED_BITS_H
+
+#include <stdint.h>
+
+
+/* predefined maximum used bits registry constants */
+extern const struct cmp_max_used_bits MAX_USED_BITS_SAFE;
+extern const struct cmp_max_used_bits MAX_USED_BITS_V1;
+
+
+/**
+ * @brief Structure holding the maximum length of the different data product types in bits
+ */
+
+struct cmp_max_used_bits {
+	uint8_t version;
+	unsigned int s_exp_flags;
+	unsigned int s_fx;
+	unsigned int s_efx;
+	unsigned int s_ncob; /* s_ncob_x and s_ncob_y */
+	unsigned int s_ecob; /* s_ecob_x and s_ncob_y */
+	unsigned int f_fx;
+	unsigned int f_efx;
+	unsigned int f_ncob; /* f_ncob_x and f_ncob_y */
+	unsigned int f_ecob; /* f_ecob_x and f_ncob_y */
+	unsigned int l_exp_flags;
+	unsigned int l_fx;
+	unsigned int l_fx_variance;
+	unsigned int l_efx;
+	unsigned int l_ncob; /* l_ncob_x and l_ncob_y */
+	unsigned int l_ecob; /* l_ecob_x and l_ncob_y */
+	unsigned int l_cob_variance; /* l_cob_x_variance and l_cob_y_variance */
+	unsigned int nc_imagette;
+	unsigned int saturated_imagette;
+	unsigned int nc_offset_mean;
+	unsigned int nc_offset_variance;
+	unsigned int nc_background_mean;
+	unsigned int nc_background_variance;
+	unsigned int nc_background_outlier_pixels;
+	unsigned int smearing_mean;
+	unsigned int smearing_variance_mean;
+	unsigned int smearing_outlier_pixels;
+	unsigned int fc_imagette;
+	unsigned int fc_offset_mean;
+	unsigned int fc_offset_variance;
+	unsigned int fc_offset_pixel_in_error;
+	unsigned int fc_background_mean;
+	unsigned int fc_background_variance;
+	unsigned int fc_background_outlier_pixels;
+};
+
+#endif /* CMP_MAX_USED_BITS_H */
diff --git a/include/cmp_max_used_bits_list.h b/include/cmp_max_used_bits_list.h
new file mode 100644
index 0000000..82a4cce
--- /dev/null
+++ b/include/cmp_max_used_bits_list.h
@@ -0,0 +1,39 @@
+/**
+ * @file   cmp_max_used_bits_list.h
+ * @author Dominik Loidolt (dominik.loidolt@univie.ac.at)
+ * @date   2023
+ *
+ * @copyright GPLv2
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * @brief Implement a list that can hold an arbitrary number of different
+ *	cmp_max_used_bits structs
+ *
+ * @warning not intended for use with the flight software
+ */
+
+
+#ifndef _CMP_MAX_USED_LIST_H_
+#define _CMP_MAX_USED_LIST_H_
+
+#include <stdint.h>
+
+#include <cmp_data_types.h>
+
+
+struct cmp_max_used_bits *cmp_max_used_bits_list_get(uint8_t version);
+
+int cmp_max_used_bits_list_add(struct cmp_max_used_bits const *item);
+
+int cmp_max_used_bits_list_delet(uint8_t version);
+
+void cmp_max_used_bits_list_empty(void);
+
+#endif /* _CMP_MAX_USED_LIST_H_ */
diff --git a/include/cmp_support.h b/include/cmp_support.h
index d696bf4..3319206 100644
--- a/include/cmp_support.h
+++ b/include/cmp_support.h
@@ -22,6 +22,8 @@
 #include <stdint.h>
 #include <stddef.h>
 
+#include <cmp_max_used_bits.h>
+
 
 /* return code if the bitstream buffer is too small to store the whole bitstream */
 #define CMP_ERROR_SMALL_BUF -2
@@ -181,7 +183,7 @@ struct cmp_cfg {
 	uint32_t ap2_spill;         /**< Adaptive 2 Golomb parameter; HW only */
 	uint32_t cmp_par_exp_flags; /**< Compression parameter for exposure flags compression */
 	uint32_t spill_exp_flags;   /**< Spillover threshold parameter for exposure flags compression */
-	uint32_t cmp_par_fx;	    /**< Compression parameter for normal flux compression */
+	uint32_t cmp_par_fx;        /**< Compression parameter for normal flux compression */
 	uint32_t spill_fx;          /**< Spillover threshold parameter for normal flux compression */
 	uint32_t cmp_par_ncob;      /**< Compression parameter for normal center of brightness compression */
 	uint32_t spill_ncob;        /**< Spillover threshold parameter for normal center of brightness compression */
@@ -197,6 +199,7 @@ struct cmp_cfg {
 	uint32_t spill_variance;    /**< Spillover threshold parameter for auxiliary science variance compression */
 	uint32_t cmp_par_pixels_error; /**< Compression parameter for auxiliary science outlier pixels number compression */
 	uint32_t spill_pixels_error; /**< Spillover threshold parameter for auxiliary science outlier pixels number compression */
+	const struct cmp_max_used_bits *max_used_bits; /**< the maximum length of the different data products types in bits */
 };
 
 
@@ -296,6 +299,7 @@ unsigned int cmp_bit_to_4byte(unsigned int cmp_size_bit);
 int cmp_cfg_icu_is_invalid(const struct cmp_cfg *cfg);
 int cmp_cfg_gen_par_is_invalid(const struct cmp_cfg *cfg, enum check_opt opt);
 int cmp_cfg_icu_buffers_is_invalid(const struct cmp_cfg *cfg);
+int cmp_cfg_icu_max_used_bits_out_of_limit(const struct cmp_max_used_bits *max_used_bits_repo);
 int cmp_cfg_imagette_is_invalid(const struct cmp_cfg *cfg, enum check_opt opt);
 int cmp_cfg_fx_cob_is_invalid(const struct cmp_cfg *cfg);
 int cmp_cfg_aux_is_invalid(const struct cmp_cfg *cfg);
diff --git a/include/list.h b/include/list.h
new file mode 100644
index 0000000..78bc5f0
--- /dev/null
+++ b/include/list.h
@@ -0,0 +1,437 @@
+/**
+ * @file include/list.h
+ * @ingroup linked_list
+ *
+ * @note This list implementation was shamelessly stolen and modified from the
+ *       linux kernel's include/linux/list.h
+ *       Its API (if you will) is used in this (currently non-GPL) project as
+ *       under the assumption that the inclusion of header files does not
+ *       automatically imply derivative work, see
+ *       http://lkml.iu.edu//hypermail/linux/kernel/0301.1/0362.html
+ *
+ *       No explicit copyright or author statement is given in the original
+ *       file, so we assume per the Linux COPYING file:
+ *
+ * @author Linus Torvalds (and others who actually wrote the linux kernel
+ *         version)
+ * @author Armin Luntzer (armin.luntzer@univie.ac.at) (local modifications or
+ *         extensions)
+ *
+ * @copyright
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * @defgroup linked_list Linked Lists
+ * @brief a modified doubly-linked list implementation from the linux kernel
+ *
+ *
+ * This is a (slightly modified) doubly-linked list implementation from the
+ * Linux kernel. An easy to understand explanation of
+ * how it works and is used can be found here
+ * http://kernelnewbies.org/FAQ/LinkedLists
+ *
+ * Be smart
+ * -----
+ * It is a valid to criticise linked lists as generally performing badly
+ * if you traverse their entries at high frequency rather than just
+ * manipulating them. This can be especially true (and has been demonstrated
+ * numerous times) for implementations like std:list.
+ *
+ * Please consider the following though: linked lists are not inherently
+ * slow because of how they work algorithmically (*the opposite is true*),
+ * but rather because how their cache hit (or miss) rate is in
+ * configurations where entries are randomly scattered in memory rather
+ * than layed out in one big chunk.
+ *
+ * Be smart. Don't do that. Allocate a pool in a __single chunk__ and enjoy the
+ * cache performance. Do not use larger chunks than the page size of your
+ * platform if you have MMU support. If you need more than that, you probably
+ * need to redesign your program anyways.
+ *
+ * This does of course not apply as long as you do access your lists only
+ * at slow rates (i.e. in the order of several tens of ms) or if performance
+ * is not at all critial.
+ *
+ */
+
+#ifndef LIST_H
+#define LIST_H
+
+#ifdef LIST_HEAD
+#undef LIST_HEAD
+#endif
+
+struct list_head {
+	struct list_head *next, *prev;
+};
+
+#define LIST_HEAD_INIT(name) { &(name), &(name) }
+
+#define LIST_HEAD(name) \
+	struct list_head name = LIST_HEAD_INIT(name)
+
+static inline void __list_add(struct list_head *new, struct list_head *prev, struct list_head *next)
+{
+	next->prev = new;
+	new->next  = next;
+	new->prev  = prev;
+	prev->next = new;
+}
+
+/**
+ * @brief add a new entry
+ * @param new: new entry to be added
+ * @param head: list head to add it after
+ *
+ * Insert a new entry after the specified head.
+ * This is good for implementing stacks.
+ */
+
+static inline void list_add(struct list_head *new, struct list_head *head)
+{
+	__list_add(new, head, head->next);
+}
+
+static inline void INIT_LIST_HEAD(struct list_head *list)
+{
+	list->next = list;
+	list->prev = list;
+}
+
+
+/**
+ * @brief get the struct for this entry
+ * @param ptr:	the &struct list_head pointer.
+ * @param type:	the type of the struct this is embedded in.
+ * @param member:	the name of the list_struct within the struct.
+ */
+#define list_entry(ptr, type, member) \
+	((type *)((char *)(ptr)-(unsigned long)(&((type *)0)->member)))
+
+/**
+ * list_first_entry - get the first element from a list
+ * @ptr:	the list head to take the element from.
+ * @type:	the type of the struct this is embedded in.
+ * @member:	the name of the list_head within the struct.
+ *
+ * Note, that list is expected to be not empty.
+ */
+#define list_first_entry(ptr, type, member) \
+	list_entry((ptr)->next, type, member)
+
+/**
+ * list_last_entry - get the last element from a list
+ * @ptr:	the list head to take the element from.
+ * @type:	the type of the struct this is embedded in.
+ * @member:	the name of the list_head within the struct.
+ *
+ * Note, that list is expected to be not empty.
+ */
+#define list_last_entry(ptr, type, member) \
+	list_entry((ptr)->prev, type, member)
+
+/**
+ * list_first_entry_or_null - get the first element from a list
+ * @ptr:	the list head to take the element from.
+ * @type:	the type of the struct this is embedded in.
+ * @member:	the name of the list_head within the struct.
+ *
+ * Note that if the list is empty, it returns NULL.
+ */
+#define list_first_entry_or_null(ptr, type, member) ({ \
+	struct list_head *head__ = (ptr); \
+	struct list_head *pos__ = READ_ONCE(head__->next); \
+	pos__ != head__ ? list_entry(pos__, type, member) : NULL; \
+})
+
+/**
+ * list_next_entry - get the next element in list
+ * @pos:	the type * to cursor
+ * @member:	the name of the list_head within the struct.
+ */
+#define list_next_entry(pos, member) \
+	list_entry((pos)->member.next, typeof(*(pos)), member)
+
+/**
+ * list_prev_entry - get the prev element in list
+ * @pos:	the type * to cursor
+ * @member:	the name of the list_head within the struct.
+ */
+#define list_prev_entry(pos, member) \
+	list_entry((pos)->member.prev, typeof(*(pos)), member)
+
+/**
+ * list_for_each	-	iterate over a list
+ * @pos:	the &struct list_head to use as a loop cursor.
+ * @head:	the head for your list.
+ */
+#define list_for_each(pos, head) \
+	for (pos = (head)->next; pos != (head); pos = pos->next)
+
+/**
+ * @brief iterate over list of given type
+ * @param pos:	the type * to use as a loop counter.
+ * @param head:	the head for your list.
+ * @param member:	the name of the list_struct within the struct.
+ * @param note	modified to use __typeof__()
+ */
+
+#define list_for_each_entry(pos, head, member)				\
+	for (pos = list_entry((head)->next, __typeof__(*pos), member);	\
+	     &pos->member != (head); 					\
+	     pos = list_entry(pos->member.next, __typeof__(*pos), member))
+
+
+/**
+ * @brief iterate over list of given type safe against removal of list entry
+ * @param pos:	the type * to use as a loop counter.
+ * @param n:		another type * to use as temporary storage
+ * @param head:	the head for your list.
+ * @param member:	the name of the list_struct within the struct.
+ */
+#define list_for_each_entry_safe(pos, n, head, member)			\
+	for (pos = list_entry((head)->next, __typeof__(*pos), member),	\
+	     n = list_entry(pos->member.next, __typeof__(*pos), member);\
+	     &pos->member != (head); 					\
+	     pos = n, n = list_entry(n->member.next, __typeof__(*pos), member))
+
+
+/**
+ * @brief iterator wrapper start
+ * @param pos:	the type * to use as a loop counter.
+ * @param head:	the head for your list.
+ * @param member:	the name of the list_struct within the struct.
+ * @param type:	the type of struct
+ * @param warning	requires list_entry_while() to close statement
+ * @param note	this construction is necessary for a truly circular list that is "headless"
+ * @param note	and can be iterated from any starting element without additional overhead
+ * @param note	compared to the LIST_HEAD/list_for_each_entry approach
+ * @param todo	check if this is functional for all targets (confirmed: gcc 4.8.2)
+ */
+
+#define list_entry_do(pos, head, member, type)		\
+	{						\
+	pos = list_entry((head), type, member);		\
+	do						\
+	{						\
+
+
+/**
+ * @brief list iterator wrapper stop
+ * @param pos:	the type * to use as a loop counter.
+ * @param head:	the head for your list.
+ * @param member:	the name of the list_struct within the struct.
+ * @param type:	the type of struct
+ * @param warning	requires list_entry_do() to open statement
+ * @param note	see list_entry_while()
+ */
+
+#define list_entry_while(pos, head, member, type)		\
+	}							\
+	while (pos = list_entry(pos->member.next, type, member),\
+	       &pos->member != head); 				\
+	}
+
+/**
+ * @brief the list entry do-while equivalent fo a code block
+ * @param pos:	the type * to use as a loop counter.
+ * @param head:	the head for your list.
+ * @param member:	the name of the list_struct within the struct.
+ * @param type:	the type of struct
+ * @param _CODE_:	a code segment
+ * @param note	see list_entry_while(), list_entry_do()
+ */
+
+#define list_entry_do_while(pos, head, member, type, _CODE_) \
+	list_entry_do(pos,head,member,type)		     \
+	{						     \
+		_CODE_;					     \
+	} list_entry_while(pos,head,member,type)
+
+
+/**
+ * @brief reverse iterate over list of given type
+ * @param pos:	the type * to use as a loop counter.
+ * @param head:	the head for your list.
+ * @param member:	the name of the list_struct within the struct.
+ * (slightly modified in case there is no typeof() functionality in target compiler)
+ */
+
+#define list_for_each_entry_rev(pos, head, member)			\
+	for (pos = list_entry((head)->prev, __typeof__(*pos), member);	\
+	     &pos->member != (head); 					\
+	     pos = list_entry(pos->member.prev, __typeof(*pos), member))
+
+
+/*
+ * @brief delete a list entry by making the prev/next entries
+ *        point to each other.
+ *
+ * This is only for internal list manipulation where we know
+ * the prev/next entries already!
+ */
+static inline void __list_del(struct list_head *prev, struct list_head *next)
+{
+	next->prev = prev;
+	prev->next = next;
+}
+
+
+/**
+ * @brief deletes entry from list.
+ * @param entry: the element to delete from the list.
+ * @note list_empty on entry does not return true after this,
+ *       the entry is in an undefined state.
+ */
+
+static inline void list_del(struct list_head *entry)
+{
+	__list_del(entry->prev, entry->next);
+	entry->next = (void *) 0;
+	entry->prev = (void *) 0;
+}
+
+
+/**
+ * @brief deletes entry from list.
+ * @param entry: the element to delete from the list.
+ * @brief list_empty() on entry does not return true after this, the entry is
+ *        in an undefined state.
+ */
+
+static inline void __list_del_entry(struct list_head *entry)
+{
+	__list_del(entry->prev, entry->next);
+}
+
+/**
+ * @brief deletes entry from list and reinitialize it.
+ * @param entry: the element to delete from the list.
+ */
+static inline void list_del_init(struct list_head *entry)
+{
+	__list_del_entry(entry);
+	INIT_LIST_HEAD(entry);
+}
+
+/**
+ * @brief delete from one list and add as another's head
+ * @param list the entry to move
+ * @param head the head that will precede our entry
+ */
+static inline void list_move(struct list_head *list, struct list_head *head)
+{
+	__list_del_entry(list);
+	list_add(list, head);
+}
+
+
+/**
+ * @brief add a new entry
+ * @param new: new entry to be added
+ * @param head: list head to add it before
+ *
+ * Insert a new entry before the specified head.
+ * This is useful for implementing queues.
+ */
+
+static inline void list_add_tail(struct list_head *new, struct list_head *head)
+{
+	__list_add(new, head->prev, head);
+}
+
+
+/**
+ * @brief replace old entry by new one
+ * @param old : the element to be replaced
+ * @param new : the new element to insert
+ *
+ * If @param old was empty, it will be overwritten.
+ */
+
+static inline void list_replace(struct list_head *old,
+				struct list_head *new)
+{
+	new->next = old->next;
+	new->next->prev = new;
+	new->prev = old->prev;
+	new->prev->next = new;
+}
+
+
+/**
+ * @brief replace entry1 with entry2 and re-add entry1 at entry2's position
+ * @param entry1: the location to place entry2
+ * @param entry2: the location to place entry1
+ */
+static inline void list_swap(struct list_head *entry1,
+			     struct list_head *entry2)
+{
+	struct list_head *pos = entry2->prev;
+
+	list_del(entry2);
+	list_replace(entry1, entry2);
+	if (pos == entry1)
+		pos = entry2;
+	list_add(entry1, pos);
+}
+
+/**
+ * @brief tests whether a list is empty
+ * @param head: the list to test.
+ */
+
+static inline int list_empty(struct list_head *head)
+{
+	return head->next == head;
+}
+
+/**
+ * @brief tests whether there is at least one element in the list
+ * @param head: the list to test.
+ */
+
+static inline int list_filled(struct list_head *head)
+{
+	return head->next != head;
+}
+
+
+/**
+ * @brief delete from one list and add as another's tail
+ * @param list: the entry to move
+ * @param head: the head that will follow our entry
+ */
+
+static inline void list_move_tail(struct list_head *list,
+				  struct list_head *head)
+{
+        __list_del(list->prev, list->next);
+        list_add_tail(list, head);
+}
+
+
+/**
+ * @brief rotate the list to the left
+ * @param head: the head of the list
+ */
+
+static inline void list_rotate_left(struct list_head *head)
+{
+        struct list_head *first;
+
+        if (!list_empty(head)) {
+                first = head->next;
+                list_move_tail(first, head);
+        }
+}
+
+
+#endif
diff --git a/lib/cmp_data_types.c b/lib/cmp_data_types.c
index 373dd51..333f5b4 100644
--- a/lib/cmp_data_types.c
+++ b/lib/cmp_data_types.c
@@ -2,7 +2,6 @@
  * @file    cmp_data_types.c
  * @author  Dominik Loidolt (dominik.loidolt@univie.ac.at)
  * @date    2020
- * @brief   collection of functions to handle the different compression data types
  *
  * @copyright GPLv2
  * This program is free software; you can redistribute it and/or modify it
@@ -14,6 +13,7 @@
  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
  * more details.
  *
+ * @brief collection of functions to handle the different compression data types
  */
 
 
@@ -27,83 +27,6 @@
 #include <byteorder.h>
 
 
-/* the maximum length of the different data products types in bits */
-struct cmp_max_used_bits max_used_bits = {
-	0, /* default version */
-	MAX_USED_S_FX_EXPOSURE_FLAGS_BITS, /* s_fx_exp_flags */
-	MAX_USED_S_FX_BITS, /* s_fx */
-	MAX_USED_S_EFX_BITS, /* s_efx */
-	MAX_USED_S_NCOB_BITS, /* s_ncob_x and s_ncob_y */
-	MAX_USED_S_ECOB_BITS, /* s_ecob_x and s_ncob_y */
-	MAX_USED_F_FX_BITS, /* f_fx */
-	MAX_USED_F_EFX_BITS, /* f_efx */
-	MAX_USED_F_NCOB_BITS, /* f_ncob_x and f_ncob_y */
-	MAX_USED_F_ECOB_BITS, /* f_ecob_x and f_ncob_y */
-	MAX_USED_L_FX_EXPOSURE_FLAGS_BITS, /* l_fx_exp_flags */
-	MAX_USED_L_FX_BITS, /* l_fx */
-	MAX_USED_L_FX_VARIANCE_BITS, /* l_fx_variance */
-	MAX_USED_L_EFX_BITS, /* l_efx */
-	MAX_USED_L_NCOB_BITS, /* l_ncob_x and l_ncob_y */
-	MAX_USED_L_ECOB_BITS, /* l_ecob_x and l_ncob_y */
-	MAX_USED_L_COB_VARIANCE_BITS, /* l_cob_x_variance and l_cob_y_variance */
-	MAX_USED_NC_IMAGETTE_BITS, /* nc_imagette */
-	MAX_USED_SATURATED_IMAGETTE_BITS, /* saturated_imagette */
-	MAX_USED_NC_OFFSET_MEAN_BITS, /* nc_offset_mean */
-	MAX_USED_NC_OFFSET_VARIANCE_BITS, /* nc_offset_variance */
-	MAX_USED_NC_BACKGROUND_MEAN_BITS, /* nc_background_mean */
-	MAX_USED_NC_BACKGROUND_VARIANCE_BITS, /* nc_background_variance */
-	MAX_USED_NC_BACKGROUND_OUTLIER_PIXELS_BITS, /* nc_background_outlier_pixels */
-	MAX_USED_SMEARING_MEAN_BITS, /* smearing_mean */
-	MAX_USED_SMEARING_VARIANCE_MEAN_BITS, /* smearing_variance_mean */
-	MAX_USED_SMEARING_OUTLIER_PIXELS_BITS, /* smearing_outlier_pixels */
-	MAX_USED_FC_IMAGETTE_BITS, /* fc_imagette */
-	MAX_USED_FC_OFFSET_MEAN_BITS, /* fc_offset_mean */
-	MAX_USED_FC_OFFSET_VARIANCE_BITS, /* fc_offset_variance */
-	MAX_USED_FC_OFFSET_PIXEL_IN_ERROR_BITS, /* fc_offset_pixel_in_error */
-	MAX_USED_FC_BACKGROUND_MEAN_BITS, /* fc_background_mean */
-	MAX_USED_FC_BACKGROUND_VARIANCE_BITS, /* fc_background_variance */
-	MAX_USED_FC_BACKGROUND_OUTLIER_PIXELS_BITS /* fc_background_outlier_pixels */
-};
-
-
-/**
- * @brief sets the maximum length of the different data product types
- *
- * @param set_max_used_bits	pointer to a structure with the maximum length
- *				of the different data product types in bits
- */
-
-void cmp_set_max_used_bits(const struct cmp_max_used_bits *set_max_used_bits)
-{
-	if (set_max_used_bits)
-		max_used_bits = *set_max_used_bits;
-}
-
-
-/**
- * @brief get the maximum length of the different data product types
- *
- * @returns a structure with the used maximum length of the different data
- *	product types in bits
- */
-
-struct cmp_max_used_bits cmp_get_max_used_bits(void)
-{
-	return max_used_bits;
-}
-
-
-/**
- * @brief get the version record form the max used bits registry
- *
- * @returns version of the max used bits registry
- */
-
-uint8_t cmp_get_max_used_bits_version(void)
-{
-	return max_used_bits.version;
-}
-
 
 /**
  * @brief calculate the size of a sample for the different compression data type
diff --git a/lib/cmp_entity.c b/lib/cmp_entity.c
index abf2a54..3726183 100644
--- a/lib/cmp_entity.c
+++ b/lib/cmp_entity.c
@@ -344,7 +344,7 @@ int cmp_ent_set_data_type(struct cmp_entity *ent, enum cmp_data_type data_type,
 	if (raw_mode_flag)
 		data_type |= 1U << RAW_BIT_DATA_TYPE_POS;
 
-	ent->data_type = cpu_to_be16(data_type);
+	ent->data_type = cpu_to_be16((uint16_t)data_type);
 
 	return 0;
 }
@@ -367,7 +367,7 @@ int cmp_ent_set_cmp_mode(struct cmp_entity *ent, enum cmp_mode cmp_mode_used)
 	if (cmp_mode_used > UINT8_MAX)
 		return -1;
 
-	ent->cmp_mode_used = cmp_mode_used;
+	ent->cmp_mode_used = (uint8_t)cmp_mode_used;
 
 	return 0;
 }
@@ -390,7 +390,7 @@ int cmp_ent_set_model_value(struct cmp_entity *ent, uint32_t model_value_used)
 	if (model_value_used > UINT8_MAX)
 		return -1;
 
-	ent->model_value_used = model_value_used;
+	ent->model_value_used = (uint8_t)model_value_used;
 
 	return 0;
 }
@@ -413,7 +413,7 @@ int cmp_ent_set_model_id(struct cmp_entity *ent, uint32_t model_id)
 	if (model_id > UINT16_MAX)
 		return -1;
 
-	ent->model_id = cpu_to_be16(model_id);
+	ent->model_id = cpu_to_be16((uint16_t)model_id);
 
 	return 0;
 }
@@ -436,7 +436,7 @@ int cmp_ent_set_model_counter(struct cmp_entity *ent, uint32_t model_counter)
 	if (model_counter > UINT8_MAX)
 		return -1;
 
-	ent->model_counter = model_counter;
+	ent->model_counter = (uint8_t)model_counter;
 
 	return 0;
 }
@@ -481,7 +481,7 @@ int cmp_ent_set_lossy_cmp_par(struct cmp_entity *ent, uint32_t lossy_cmp_par_use
 	if (lossy_cmp_par_used > UINT16_MAX)
 		return -1;
 
-	ent->lossy_cmp_par_used = cpu_to_be16(lossy_cmp_par_used);
+	ent->lossy_cmp_par_used = cpu_to_be16((uint16_t)lossy_cmp_par_used);
 
 	return 0;
 }
@@ -505,7 +505,7 @@ int cmp_ent_set_ima_spill(struct cmp_entity *ent, uint32_t spill_used)
 	if (spill_used > UINT16_MAX)
 		return -1;
 
-	ent->ima.spill_used = cpu_to_be16(spill_used);
+	ent->ima.spill_used = cpu_to_be16((uint16_t)spill_used);
 
 	return 0;
 }
@@ -530,7 +530,7 @@ int cmp_ent_set_ima_golomb_par(struct cmp_entity *ent, uint32_t golomb_par_used)
 	if (golomb_par_used > UINT8_MAX)
 		return -1;
 
-	ent->ima.golomb_par_used = golomb_par_used;
+	ent->ima.golomb_par_used = (uint8_t)golomb_par_used;
 
 	return 0;
 }
@@ -555,7 +555,7 @@ int cmp_ent_set_ima_ap1_spill(struct cmp_entity *ent, uint32_t ap1_spill_used)
 	if (ap1_spill_used > UINT16_MAX)
 		return -1;
 
-	ent->ima.ap1_spill_used = cpu_to_be16(ap1_spill_used);
+	ent->ima.ap1_spill_used = cpu_to_be16((uint16_t)ap1_spill_used);
 
 	return 0;
 }
@@ -580,7 +580,7 @@ int cmp_ent_set_ima_ap1_golomb_par(struct cmp_entity *ent, uint32_t ap1_golomb_p
 	if (ap1_golomb_par_used > UINT8_MAX)
 		return -1;
 
-	ent->ima.ap1_golomb_par_used = ap1_golomb_par_used;
+	ent->ima.ap1_golomb_par_used = (uint8_t)ap1_golomb_par_used;
 
 	return 0;
 }
@@ -605,7 +605,7 @@ int cmp_ent_set_ima_ap2_spill(struct cmp_entity *ent, uint32_t ap2_spill_used)
 	if (ap2_spill_used > UINT16_MAX)
 		return -1;
 
-	ent->ima.ap2_spill_used = cpu_to_be16(ap2_spill_used);
+	ent->ima.ap2_spill_used = cpu_to_be16((uint16_t)ap2_spill_used);
 
 	return 0;
 }
@@ -630,7 +630,7 @@ int cmp_ent_set_ima_ap2_golomb_par(struct cmp_entity *ent, uint32_t ap2_golomb_p
 	if (ap2_golomb_par_used > UINT8_MAX)
 		return -1;
 
-	ent->ima.ap2_golomb_par_used = ap2_golomb_par_used;
+	ent->ima.ap2_golomb_par_used = (uint8_t)ap2_golomb_par_used;
 
 	return 0;
 }
@@ -683,7 +683,7 @@ int cmp_ent_set_non_ima_cmp_par1(struct cmp_entity *ent, uint32_t cmp_par_1_used
 	if (cmp_par_1_used > UINT16_MAX)
 		return -1;
 
-	ent->non_ima.cmp_par_1_used = cpu_to_be16(cmp_par_1_used);
+	ent->non_ima.cmp_par_1_used = cpu_to_be16((uint16_t)cmp_par_1_used);
 
 	return 0;
 }
@@ -736,7 +736,7 @@ int cmp_ent_set_non_ima_cmp_par2(struct cmp_entity *ent, uint32_t cmp_par_2_used
 	if (cmp_par_2_used > UINT16_MAX)
 		return -1;
 
-	ent->non_ima.cmp_par_2_used = cpu_to_be16(cmp_par_2_used);
+	ent->non_ima.cmp_par_2_used = cpu_to_be16((uint16_t)cmp_par_2_used);
 
 	return 0;
 }
@@ -789,7 +789,7 @@ int cmp_ent_set_non_ima_cmp_par3(struct cmp_entity *ent, uint32_t cmp_par_3_used
 	if (cmp_par_3_used > UINT16_MAX)
 		return -1;
 
-	ent->non_ima.cmp_par_3_used = cpu_to_be16(cmp_par_3_used);
+	ent->non_ima.cmp_par_3_used = cpu_to_be16((uint16_t)cmp_par_3_used);
 
 	return 0;
 }
@@ -842,7 +842,7 @@ int cmp_ent_set_non_ima_cmp_par4(struct cmp_entity *ent, uint32_t cmp_par_4_used
 	if (cmp_par_4_used > UINT16_MAX)
 		return -1;
 
-	ent->non_ima.cmp_par_4_used = cpu_to_be16(cmp_par_4_used);
+	ent->non_ima.cmp_par_4_used = cpu_to_be16((uint16_t)cmp_par_4_used);
 
 	return 0;
 }
@@ -895,7 +895,7 @@ int cmp_ent_set_non_ima_cmp_par5(struct cmp_entity *ent, uint32_t cmp_par_5_used
 	if (cmp_par_5_used > UINT16_MAX)
 		return -1;
 
-	ent->non_ima.cmp_par_5_used = cpu_to_be16(cmp_par_5_used);
+	ent->non_ima.cmp_par_5_used = cpu_to_be16((uint16_t)cmp_par_5_used);
 
 	return 0;
 }
@@ -948,7 +948,7 @@ int cmp_ent_set_non_ima_cmp_par6(struct cmp_entity *ent, uint32_t cmp_par_6_used
 	if (cmp_par_6_used > UINT16_MAX)
 		return -1;
 
-	ent->non_ima.cmp_par_6_used = cpu_to_be16(cmp_par_6_used);
+	ent->non_ima.cmp_par_6_used = cpu_to_be16((uint16_t)cmp_par_6_used);
 
 	return 0;
 }
@@ -1827,7 +1827,10 @@ int cmp_ent_write_cmp_pars(struct cmp_entity *ent, const struct cmp_cfg *cfg,
 		return -1;
 	if (cmp_ent_set_model_value(ent, cfg->model_value))
 		return -1;
-	cmp_ent_set_max_used_bits_version(ent, cmp_get_max_used_bits_version());
+	if (cfg->max_used_bits)
+		cmp_ent_set_max_used_bits_version(ent, cfg->max_used_bits->version);
+	else
+		cmp_ent_set_max_used_bits_version(ent, 0);
 	if (cmp_ent_set_lossy_cmp_par(ent, cfg->round))
 		return -1;
 
@@ -2131,117 +2134,6 @@ size_t cmp_ent_build(struct cmp_entity *ent, uint32_t version_id,
 }
 
 
-/**
- * @brief read in an imagette compression entity header to a
- *	compression configuration
- *
- * @param ent	pointer to a compression entity
- * @param cfg	pointer to a compression configuration
- *
- * @returns 0 on success; otherwise error
- */
-
-int cmp_ent_read_header(struct cmp_entity *ent, struct cmp_cfg *cfg)
-{
-	int32_t samples;
-
-	if (!cfg)
-		return -1;
-
-	cfg->data_type = cmp_ent_get_data_type(ent);
-	if (cmp_data_type_is_invalid(cfg->data_type)) {
-		debug_print("Error: Compression data type not supported.\n");
-		return -1;
-	}
-
-	cfg->cmp_mode = cmp_ent_get_cmp_mode(ent);
-	if (cmp_ent_get_data_type_raw_bit(ent) != (cfg->cmp_mode == CMP_MODE_RAW)) {
-		debug_print("Error: The entity's raw data bit does not match up with the compression mode.\n");
-		return -1;
-	}
-	cfg->model_value = cmp_ent_get_model_value(ent);
-	cfg->round = cmp_ent_get_lossy_cmp_par(ent);
-	cfg->buffer_length = cmp_ent_get_cmp_data_size(ent);
-
-	samples = cmp_input_size_to_samples(cmp_ent_get_original_size(ent), cfg->data_type);
-	if (samples < 0) {
-		debug_print("Error: original_size and data product type in the compression header field are not compatible.\n");
-		cfg->samples = 0;
-		return -1;
-	}
-
-	cfg->samples = (uint32_t)samples;
-
-	cfg->icu_output_buf = cmp_ent_get_data_buf(ent);
-
-
-	if (cfg->cmp_mode == CMP_MODE_RAW)
-		/* no specific header is used for raw data we are done */
-		return 0;
-
-	switch (cfg->data_type) {
-	case DATA_TYPE_IMAGETTE_ADAPTIVE:
-	case DATA_TYPE_SAT_IMAGETTE_ADAPTIVE:
-	case DATA_TYPE_F_CAM_IMAGETTE_ADAPTIVE:
-		cfg->ap1_golomb_par = cmp_ent_get_ima_ap1_golomb_par(ent);
-		cfg->ap1_spill = cmp_ent_get_ima_ap1_spill(ent);
-		cfg->ap2_golomb_par = cmp_ent_get_ima_ap2_golomb_par(ent);
-		cfg->ap2_spill = cmp_ent_get_ima_ap2_spill(ent);
-		/* fall through */
-	case DATA_TYPE_IMAGETTE:
-	case DATA_TYPE_SAT_IMAGETTE:
-	case DATA_TYPE_F_CAM_IMAGETTE:
-		cfg->spill = cmp_ent_get_ima_spill(ent);
-		cfg->golomb_par = cmp_ent_get_ima_golomb_par(ent);
-		break;
-	case DATA_TYPE_OFFSET:
-	case DATA_TYPE_BACKGROUND:
-	case DATA_TYPE_SMEARING:
-		cfg->cmp_par_mean = cmp_ent_get_non_ima_cmp_par1(ent);
-		cfg->spill_mean = cmp_ent_get_non_ima_spill1(ent);
-		cfg->cmp_par_variance = cmp_ent_get_non_ima_cmp_par2(ent);
-		cfg->spill_variance = cmp_ent_get_non_ima_spill2(ent);
-		cfg->cmp_par_pixels_error = cmp_ent_get_non_ima_cmp_par3(ent);
-		cfg->spill_pixels_error = cmp_ent_get_non_ima_spill3(ent);
-		break;
-	case DATA_TYPE_S_FX:
-	case DATA_TYPE_S_FX_EFX:
-	case DATA_TYPE_S_FX_NCOB:
-	case DATA_TYPE_S_FX_EFX_NCOB_ECOB:
-	case DATA_TYPE_L_FX:
-	case DATA_TYPE_L_FX_EFX:
-	case DATA_TYPE_L_FX_NCOB:
-	case DATA_TYPE_L_FX_EFX_NCOB_ECOB:
-	case DATA_TYPE_F_FX:
-	case DATA_TYPE_F_FX_EFX:
-	case DATA_TYPE_F_FX_NCOB:
-	case DATA_TYPE_F_FX_EFX_NCOB_ECOB:
-		cfg->cmp_par_exp_flags = cmp_ent_get_non_ima_cmp_par1(ent);
-		cfg->spill_exp_flags = cmp_ent_get_non_ima_spill1(ent);
-		cfg->cmp_par_fx = cmp_ent_get_non_ima_cmp_par2(ent);
-		cfg->spill_fx = cmp_ent_get_non_ima_spill2(ent);
-		cfg->cmp_par_ncob = cmp_ent_get_non_ima_cmp_par3(ent);
-		cfg->spill_ncob = cmp_ent_get_non_ima_spill3(ent);
-		cfg->cmp_par_efx = cmp_ent_get_non_ima_cmp_par4(ent);
-		cfg->spill_efx = cmp_ent_get_non_ima_spill4(ent);
-		cfg->cmp_par_ecob = cmp_ent_get_non_ima_cmp_par5(ent);
-		cfg->spill_ecob = cmp_ent_get_non_ima_spill5(ent);
-		cfg->cmp_par_fx_cob_variance = cmp_ent_get_non_ima_cmp_par6(ent);
-		cfg->spill_fx_cob_variance = cmp_ent_get_non_ima_spill6(ent);
-		break;
-	case DATA_TYPE_F_CAM_OFFSET:
-	case DATA_TYPE_F_CAM_BACKGROUND:
-	/* LCOV_EXCL_START */
-	case DATA_TYPE_UNKNOWN:
-	default:
-		return -1;
-	/* LCOV_EXCL_STOP */
-	}
-
-	return 0;
-}
-
-
 #ifdef HAS_TIME_H
 /*
  * @brief Covert a calendar time expressed as a struct tm object to time since
@@ -2320,11 +2212,11 @@ uint64_t cmp_ent_create_timestamp(const struct timespec *ts)
 		clock_gettime(CLOCK_REALTIME, &now);
 	}
 
-	seconds = ((double)now.tv_sec + 1.0e-9 * now.tv_nsec) -
-		  ((double)epoch.tv_sec + 1.0e-9 * epoch.tv_nsec);
+	seconds = ((double)now.tv_sec + 1.0e-9 * (double)now.tv_nsec) -
+		  ((double)epoch.tv_sec + 1.0e-9 * (double)epoch.tv_nsec);
 
 	coarse = (uint64_t)seconds;
-	fine = (uint64_t)((seconds - coarse) * 256 * 256);
+	fine = (uint64_t)((seconds - (double)coarse) * 256 * 256);
 
 	return (coarse << 16) + fine;
 }
diff --git a/lib/cmp_icu.c b/lib/cmp_icu.c
index 445e4d1..6ad7af2 100644
--- a/lib/cmp_icu.c
+++ b/lib/cmp_icu.c
@@ -40,9 +40,6 @@
 #include <cmp_entity.h>
 
 
-/* maximum used bits registry */
-extern struct cmp_max_used_bits max_used_bits;
-
 
 /**
  * @brief pointer to a code word generation function
@@ -93,6 +90,7 @@ struct cmp_cfg cmp_cfg_icu_create(enum cmp_data_type data_type, enum cmp_mode cm
 	cfg.cmp_mode = cmp_mode;
 	cfg.model_value = model_value;
 	cfg.round = lossy_par;
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE;
 
 	if (cmp_cfg_gen_par_is_invalid(&cfg, ICU_CHECK))
 		cfg.data_type = DATA_TYPE_UNKNOWN;
@@ -102,7 +100,7 @@ struct cmp_cfg cmp_cfg_icu_create(enum cmp_data_type data_type, enum cmp_mode cm
 
 
 /**
- * @brief setup the different data buffers for an ICU compression
+ * @brief set up the different data buffers for an ICU compression
  *
  * @param cfg			pointer to a compression configuration (created
  *				with the cmp_cfg_icu_create() function)
@@ -157,6 +155,33 @@ uint32_t cmp_cfg_icu_buffers(struct cmp_cfg *cfg, void *data_to_compress,
 }
 
 
+/**
+ * @brief set up the maximum length of the different data products types for
+ *	an ICU compression
+ *
+ * @param cfg		pointer to a compression configuration (created with the
+ *			cmp_cfg_icu_create() function)
+ * @param max_used_bits	pointer to a max_used_bits struct containing the maximum
+ *			length of the different data products types
+ *
+ * @returns 0 if all max_used_bits parameters are valid, non-zero if parameters are invalid
+ *
+ * @note the cmp_cfg_icu_create() function set the max_used_bits configuration to
+ *	MAX_USED_BITS_SAFE
+ */
+
+int cmp_cfg_icu_max_used_bits(struct cmp_cfg *cfg, const struct cmp_max_used_bits *max_used_bits)
+{
+	if (cfg)
+		cfg->max_used_bits = max_used_bits;
+
+	if (cmp_cfg_icu_max_used_bits_out_of_limit(max_used_bits))
+		return -1;
+
+	return 0;
+}
+
+
 /**
  * @brief set up the configuration parameters for an ICU imagette compression
  *
@@ -830,7 +855,7 @@ static int compress_imagette(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup, cfg->golomb_par, cfg->spill,
-				      cfg->round, max_used_bits.nc_imagette, cfg);
+				      cfg->round, cfg->max_used_bits->nc_imagette, cfg);
 	if (err)
 		return -1;
 
@@ -926,11 +951,11 @@ static int compress_s_fx(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_exp_flag, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				      cfg->round, max_used_bits.s_exp_flags, cfg);
+				      cfg->round, cfg->max_used_bits->s_exp_flags, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.s_fx, cfg);
+				      cfg->round, cfg->max_used_bits->s_fx, cfg);
 	if (err)
 		return -1;
 
@@ -998,15 +1023,15 @@ static int compress_s_fx_efx(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_exp_flag, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				      cfg->round, max_used_bits.s_exp_flags, cfg);
+				      cfg->round, cfg->max_used_bits->s_exp_flags, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.s_fx, cfg);
+				      cfg->round, cfg->max_used_bits->s_fx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				      cfg->round, max_used_bits.s_efx, cfg);
+				      cfg->round, cfg->max_used_bits->s_efx, cfg);
 	if (err)
 		return -1;
 
@@ -1080,15 +1105,15 @@ static int compress_s_fx_ncob(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_exp_flag, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				      cfg->round, max_used_bits.s_exp_flags, cfg);
+				      cfg->round, cfg->max_used_bits->s_exp_flags, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.s_fx, cfg);
+				      cfg->round, cfg->max_used_bits->s_fx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				      cfg->round, max_used_bits.s_ncob, cfg);
+				      cfg->round, cfg->max_used_bits->s_ncob, cfg);
 	if (err)
 		return -1;
 
@@ -1169,23 +1194,23 @@ static int compress_s_fx_efx_ncob_ecob(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_exp_flag, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				      cfg->round, max_used_bits.s_exp_flags, cfg);
+				      cfg->round, cfg->max_used_bits->s_exp_flags, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.s_fx, cfg);
+				      cfg->round, cfg->max_used_bits->s_fx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				      cfg->round, max_used_bits.s_ncob, cfg);
+				      cfg->round, cfg->max_used_bits->s_ncob, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				      cfg->round, max_used_bits.s_efx, cfg);
+				      cfg->round, cfg->max_used_bits->s_efx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_ecob, cfg->cmp_par_ecob, cfg->spill_ecob,
-				      cfg->round, max_used_bits.s_ecob, cfg);
+				      cfg->round, cfg->max_used_bits->s_ecob, cfg);
 	if (err)
 		return -1;
 
@@ -1283,7 +1308,7 @@ static int compress_f_fx(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.f_fx, cfg);
+				      cfg->round, cfg->max_used_bits->f_fx, cfg);
 	if (err)
 		return -1;
 
@@ -1345,11 +1370,11 @@ static int compress_f_fx_efx(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.f_fx, cfg);
+				      cfg->round, cfg->max_used_bits->f_fx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				      cfg->round, max_used_bits.f_efx, cfg);
+				      cfg->round, cfg->max_used_bits->f_efx, cfg);
 	if (err)
 		return -1;
 
@@ -1417,11 +1442,11 @@ static int compress_f_fx_ncob(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.f_fx, cfg);
+				      cfg->round, cfg->max_used_bits->f_fx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				      cfg->round, max_used_bits.f_ncob, cfg);
+				      cfg->round, cfg->max_used_bits->f_ncob, cfg);
 	if (err)
 		return -1;
 
@@ -1495,19 +1520,19 @@ static int compress_f_fx_efx_ncob_ecob(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.f_fx, cfg);
+				      cfg->round, cfg->max_used_bits->f_fx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				      cfg->round, max_used_bits.f_ncob, cfg);
+				      cfg->round, cfg->max_used_bits->f_ncob, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				      cfg->round, max_used_bits.f_efx, cfg);
+				      cfg->round, cfg->max_used_bits->f_efx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_ecob, cfg->cmp_par_ecob, cfg->spill_ecob,
-				      cfg->round, max_used_bits.f_ecob, cfg);
+				      cfg->round, cfg->max_used_bits->f_ecob, cfg);
 	if (err)
 		return -1;
 
@@ -1599,15 +1624,15 @@ static int compress_l_fx(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_exp_flag, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				      cfg->round, max_used_bits.l_exp_flags, cfg);
+				      cfg->round, cfg->max_used_bits->l_exp_flags, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.l_fx, cfg);
+				      cfg->round, cfg->max_used_bits->l_fx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_fx_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				      cfg->round, max_used_bits.l_fx_variance, cfg);
+				      cfg->round, cfg->max_used_bits->l_fx_variance, cfg);
 	if (err)
 		return -1;
 
@@ -1681,19 +1706,19 @@ static int compress_l_fx_efx(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_exp_flag, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				      cfg->round, max_used_bits.l_exp_flags, cfg);
+				      cfg->round, cfg->max_used_bits->l_exp_flags, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.l_fx, cfg);
+				      cfg->round, cfg->max_used_bits->l_fx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				      cfg->round, max_used_bits.l_efx, cfg);
+				      cfg->round, cfg->max_used_bits->l_efx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_fx_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				      cfg->round, max_used_bits.l_fx_variance, cfg);
+				      cfg->round, cfg->max_used_bits->l_fx_variance, cfg);
 	if (err)
 		return -1;
 
@@ -1774,24 +1799,24 @@ static int compress_l_fx_ncob(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_exp_flag, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				      cfg->round, max_used_bits.l_exp_flags, cfg);
+				      cfg->round, cfg->max_used_bits->l_exp_flags, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.l_fx, cfg);
+				      cfg->round, cfg->max_used_bits->l_fx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				      cfg->round, max_used_bits.l_ncob, cfg);
+				      cfg->round, cfg->max_used_bits->l_ncob, cfg);
 	if (err)
 		return -1;
 	/* we use compression parameter for both variance data fields */
 	err = configure_encoder_setup(&setup_fx_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				      cfg->round, max_used_bits.l_fx_variance, cfg);
+				      cfg->round, cfg->max_used_bits->l_fx_variance, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_cob_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				      cfg->round, max_used_bits.l_cob_variance, cfg);
+				      cfg->round, cfg->max_used_bits->l_cob_variance, cfg);
 	if (err)
 		return -1;
 
@@ -1890,32 +1915,32 @@ static int compress_l_fx_efx_ncob_ecob(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_exp_flag, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				      cfg->round, max_used_bits.l_exp_flags, cfg);
+				      cfg->round, cfg->max_used_bits->l_exp_flags, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				      cfg->round, max_used_bits.l_fx, cfg);
+				      cfg->round, cfg->max_used_bits->l_fx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				      cfg->round, max_used_bits.l_ncob, cfg);
+				      cfg->round, cfg->max_used_bits->l_ncob, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				      cfg->round, max_used_bits.l_efx, cfg);
+				      cfg->round, cfg->max_used_bits->l_efx, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_ecob, cfg->cmp_par_ecob, cfg->spill_ecob,
-				      cfg->round, max_used_bits.l_ecob, cfg);
+				      cfg->round, cfg->max_used_bits->l_ecob, cfg);
 	if (err)
 		return -1;
 	/* we use compression parameter for both variance data fields */
 	err = configure_encoder_setup(&setup_fx_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				      cfg->round, max_used_bits.l_fx_variance, cfg);
+				      cfg->round, cfg->max_used_bits->l_fx_variance, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_cob_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				      cfg->round, max_used_bits.l_cob_variance, cfg);
+				      cfg->round, cfg->max_used_bits->l_cob_variance, cfg);
 	if (err)
 		return -1;
 
@@ -2030,11 +2055,11 @@ static int compress_nc_offset(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_mean, cfg->cmp_par_mean, cfg->spill_mean,
-				      cfg->round, max_used_bits.nc_offset_mean, cfg);
+				      cfg->round, cfg->max_used_bits->nc_offset_mean, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_var, cfg->cmp_par_variance, cfg->spill_variance,
-				      cfg->round, max_used_bits.nc_offset_variance, cfg);
+				      cfg->round, cfg->max_used_bits->nc_offset_variance, cfg);
 	if (err)
 		return -1;
 
@@ -2101,15 +2126,15 @@ static int compress_nc_background(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_mean, cfg->cmp_par_mean, cfg->spill_mean,
-				      cfg->round, max_used_bits.nc_background_mean, cfg);
+				      cfg->round, cfg->max_used_bits->nc_background_mean, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_var, cfg->cmp_par_variance, cfg->spill_variance,
-				      cfg->round, max_used_bits.nc_background_variance, cfg);
+				      cfg->round, cfg->max_used_bits->nc_background_variance, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_pix, cfg->cmp_par_pixels_error, cfg->spill_pixels_error,
-				      cfg->round, max_used_bits.nc_background_outlier_pixels, cfg);
+				      cfg->round, cfg->max_used_bits->nc_background_outlier_pixels, cfg);
 	if (err)
 		return -1;
 
@@ -2183,15 +2208,15 @@ static int compress_smearing(const struct cmp_cfg *cfg)
 	}
 
 	err = configure_encoder_setup(&setup_mean, cfg->cmp_par_mean, cfg->spill_mean,
-				      cfg->round, max_used_bits.smearing_mean, cfg);
+				      cfg->round, cfg->max_used_bits->smearing_mean, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_var_mean, cfg->cmp_par_variance, cfg->spill_variance,
-				      cfg->round, max_used_bits.smearing_variance_mean, cfg);
+				      cfg->round, cfg->max_used_bits->smearing_variance_mean, cfg);
 	if (err)
 		return -1;
 	err = configure_encoder_setup(&setup_pix, cfg->cmp_par_pixels_error, cfg->spill_pixels_error,
-				      cfg->round, max_used_bits.smearing_outlier_pixels, cfg);
+				      cfg->round, cfg->max_used_bits->smearing_outlier_pixels, cfg);
 	if (err)
 		return -1;
 
diff --git a/lib/cmp_max_used_bits.c b/lib/cmp_max_used_bits.c
new file mode 100644
index 0000000..b37a1c2
--- /dev/null
+++ b/lib/cmp_max_used_bits.c
@@ -0,0 +1,148 @@
+/**
+ * @file   cmp_max_used_bits.c
+ * @author Dominik Loidolt (dominik.loidolt@univie.ac.at)
+ * @date   2023
+ *
+ * @copyright GPLv2
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * @brief definition and consents of the cmp_max_used_bits structure
+ */
+
+
+#include <stdint.h>
+#include <stdio.h>
+
+#include <cmp_data_types.h>
+
+#define MAX_USED_NC_IMAGETTE_BITS		16
+#define MAX_USED_SATURATED_IMAGETTE_BITS	16 /* TBC */
+#define MAX_USED_FC_IMAGETTE_BITS		16 /* TBC */
+
+#define MAX_USED_F_FX_BITS	21 /* max exp. int value: (1.078*10^5)/0.1 = 1,078,000 -> 21 bits */
+#define MAX_USED_F_EFX_BITS	MAX_USED_F_FX_BITS /* we use the same as f_fx */
+#define MAX_USED_F_NCOB_BITS	20 /* max exp. int value: 6/10^−5 = 6*10^5 -> 20 bits */
+#define MAX_USED_F_ECOB_BITS	32 /* TBC */
+
+#define MAX_USED_S_FX_EXPOSURE_FLAGS_BITS	2 /* 2 flags + 6 spare bits */
+#define MAX_USED_S_FX_BITS			24 /* max exp. int value: (1.078*10^5-34.71)/0.01 = 10,780,000-> 24 bits */
+#define MAX_USED_S_EFX_BITS			MAX_USED_S_FX_BITS /* we use the same as s_fx */
+#define MAX_USED_S_NCOB_BITS			MAX_USED_F_NCOB_BITS
+#define MAX_USED_S_ECOB_BITS			32 /* TBC */
+
+#define MAX_USED_L_FX_EXPOSURE_FLAGS_BITS	24 /* 24 flags */
+#define MAX_USED_L_FX_BITS			MAX_USED_S_FX_BITS
+#define MAX_USED_L_FX_VARIANCE_BITS		32 /* no maximum value is given in PLATO-LESIA-PDC-TN-0054 */
+#define MAX_USED_L_EFX_BITS			MAX_USED_L_FX_BITS /* we use the same as l_fx */
+#define MAX_USED_L_NCOB_BITS			MAX_USED_F_NCOB_BITS
+#define MAX_USED_L_ECOB_BITS			32 /* TBC */
+#define MAX_USED_L_COB_VARIANCE_BITS		25 /* max exp int value: 0.1739/10^−8 = 17390000 -> 25 bits */
+
+#define MAX_USED_NC_OFFSET_MEAN_BITS		2 /* no maximum value is given in PLATO-LESIA-PDC-TN-0054 */
+#define MAX_USED_NC_OFFSET_VARIANCE_BITS	10 /* max exp. int value: 9.31/0.01 = 931 -> 10 bits */
+
+#define MAX_USED_NC_BACKGROUND_MEAN_BITS		16 /* max exp. int value: (391.8-(-50))/0.01 = 44,180 -> 16 bits */
+#define MAX_USED_NC_BACKGROUND_VARIANCE_BITS		16 /* max exp. int value: 6471/0.1 = 64710 -> 16 bit */
+#define MAX_USED_NC_BACKGROUND_OUTLIER_PIXELS_BITS	5 /* maximum = 16 -> 5 bits */
+
+#define MAX_USED_SMEARING_MEAN_BITS		15 /* max exp. int value: (219.9 - -50)/0.01 = 26.990 */
+#define MAX_USED_SMEARING_VARIANCE_MEAN_BITS	16 /* no maximum value is given in PLATO-LESIA-PDC-TN-0054 */
+#define MAX_USED_SMEARING_OUTLIER_PIXELS_BITS	11 /* maximum = 1200 -> 11 bits */
+
+#define MAX_USED_FC_OFFSET_MEAN_BITS		32 /* no maximum value is given in PLATO-LESIA-PDC-TN-0054 */
+#define MAX_USED_FC_OFFSET_VARIANCE_BITS	9  /* max exp. int value: 342/1 = 342 -> 9 bits */
+#define MAX_USED_FC_OFFSET_PIXEL_IN_ERROR_BITS	16 /* TBC */
+
+#define MAX_USED_FC_BACKGROUND_MEAN_BITS		10 /* max exp. int value: (35.76-(-50))/0.1 = 858 -> 10 bits*/
+#define MAX_USED_FC_BACKGROUND_VARIANCE_BITS		6 /* max exp. int value: 53.9/1 = 54 -> 6 bits */
+#define MAX_USED_FC_BACKGROUND_OUTLIER_PIXELS_BITS	16 /* TBC */
+
+
+#define member_bit_size(type, member) sizeof(((type *)0)->member)*8
+
+
+/* a safe the different data products types in bits */
+const struct cmp_max_used_bits MAX_USED_BITS_SAFE = {
+	0, /* default version */
+	member_bit_size(struct s_fx_efx_ncob_ecob, exp_flags), /* s_fx_exp_flags */
+	member_bit_size(struct s_fx_efx_ncob_ecob, fx), /* s_fx */
+	member_bit_size(struct s_fx_efx_ncob_ecob, efx), /* s_efx */
+	member_bit_size(struct s_fx_efx_ncob_ecob, ncob_x), /* s_ncob_x and s_ncob_y */
+	member_bit_size(struct s_fx_efx_ncob_ecob, ecob_x), /* s_ecob_x and s_ncob_y */
+	member_bit_size(struct f_fx_efx_ncob_ecob, fx), /* f_fx */
+	member_bit_size(struct f_fx_efx_ncob_ecob, efx), /* f_efx */
+	member_bit_size(struct f_fx_efx_ncob_ecob, ncob_x), /* f_ncob_x and f_ncob_y */
+	member_bit_size(struct f_fx_efx_ncob_ecob, ecob_x), /* f_ecob_x and f_ncob_y */
+	/* member_bit_size(struct l_fx_efx_ncob_ecob, exp_flags), /1* l_fx_exp_flags *1/ */
+	24,
+	member_bit_size(struct l_fx_efx_ncob_ecob, fx), /* l_fx */
+	member_bit_size(struct l_fx_efx_ncob_ecob, fx_variance), /* l_fx_variance */
+	member_bit_size(struct l_fx_efx_ncob_ecob, efx), /* l_efx */
+	member_bit_size(struct l_fx_efx_ncob_ecob, ncob_x), /* l_ncob_x and l_ncob_y */
+	member_bit_size(struct l_fx_efx_ncob_ecob, ecob_x), /* l_ecob_x and l_ncob_y */
+	member_bit_size(struct l_fx_efx_ncob_ecob, cob_x_variance), /* l_cob_x_variance and l_cob_y_variance */
+	sizeof(uint16_t)*8, /* nc_imagette */
+	sizeof(uint16_t)*8, /* saturated_imagette */
+	member_bit_size(struct nc_offset, mean), /* nc_offset_mean */
+	member_bit_size(struct nc_offset, variance), /* nc_offset_variance */
+	member_bit_size(struct nc_background, mean), /* nc_background_mean */
+	member_bit_size(struct nc_background, variance), /* nc_background_variance */
+	member_bit_size(struct nc_background, outlier_pixels), /* nc_background_outlier_pixels */
+	member_bit_size(struct smearing, mean), /* smearing_mean */
+	member_bit_size(struct smearing, variance_mean), /* smearing_variance_mean */
+	member_bit_size(struct smearing, outlier_pixels), /* smearing_outlier_pixels */
+	sizeof(uint32_t)*8, /* TBC */ /* fc_imagette */
+	sizeof(uint32_t)*8, /* TBC */ /* fc_offset_mean */
+	sizeof(uint32_t)*8, /* TBC */ /* fc_offset_variance */
+	sizeof(uint32_t)*8, /* TBC */ /* fc_offset_pixel_in_error */
+	sizeof(uint32_t)*8, /* TBC */ /* fc_background_mean */
+	sizeof(uint32_t)*8, /* TBC */ /* fc_background_variance */
+	sizeof(uint32_t)*8, /* TBC */ /* fc_background_outlier_pixels */
+};
+
+
+/* the maximum length of the different data products types in bits */
+const struct cmp_max_used_bits MAX_USED_BITS_V1 = {
+	1, /* default version */
+	MAX_USED_S_FX_EXPOSURE_FLAGS_BITS, /* s_fx_exp_flags */
+	MAX_USED_S_FX_BITS, /* s_fx */
+	MAX_USED_S_EFX_BITS, /* s_efx */
+	MAX_USED_S_NCOB_BITS, /* s_ncob_x and s_ncob_y */
+	MAX_USED_S_ECOB_BITS, /* s_ecob_x and s_ncob_y */
+	MAX_USED_F_FX_BITS, /* f_fx */
+	MAX_USED_F_EFX_BITS, /* f_efx */
+	MAX_USED_F_NCOB_BITS, /* f_ncob_x and f_ncob_y */
+	MAX_USED_F_ECOB_BITS, /* f_ecob_x and f_ncob_y */
+	MAX_USED_L_FX_EXPOSURE_FLAGS_BITS, /* l_fx_exp_flags */
+	MAX_USED_L_FX_BITS, /* l_fx */
+	MAX_USED_L_FX_VARIANCE_BITS, /* l_fx_variance */
+	MAX_USED_L_EFX_BITS, /* l_efx */
+	MAX_USED_L_NCOB_BITS, /* l_ncob_x and l_ncob_y */
+	MAX_USED_L_ECOB_BITS, /* l_ecob_x and l_ncob_y */
+	MAX_USED_L_COB_VARIANCE_BITS, /* l_cob_x_variance and l_cob_y_variance */
+	MAX_USED_NC_IMAGETTE_BITS, /* nc_imagette */
+	MAX_USED_SATURATED_IMAGETTE_BITS, /* saturated_imagette */
+	MAX_USED_NC_OFFSET_MEAN_BITS, /* nc_offset_mean */
+	MAX_USED_NC_OFFSET_VARIANCE_BITS, /* nc_offset_variance */
+	MAX_USED_NC_BACKGROUND_MEAN_BITS, /* nc_background_mean */
+	MAX_USED_NC_BACKGROUND_VARIANCE_BITS, /* nc_background_variance */
+	MAX_USED_NC_BACKGROUND_OUTLIER_PIXELS_BITS, /* nc_background_outlier_pixels */
+	MAX_USED_SMEARING_MEAN_BITS, /* smearing_mean */
+	MAX_USED_SMEARING_VARIANCE_MEAN_BITS, /* smearing_variance_mean */
+	MAX_USED_SMEARING_OUTLIER_PIXELS_BITS, /* smearing_outlier_pixels */
+	MAX_USED_FC_IMAGETTE_BITS, /* fc_imagette */
+	MAX_USED_FC_OFFSET_MEAN_BITS, /* fc_offset_mean */
+	MAX_USED_FC_OFFSET_VARIANCE_BITS, /* fc_offset_variance */
+	MAX_USED_FC_OFFSET_PIXEL_IN_ERROR_BITS, /* fc_offset_pixel_in_error */
+	MAX_USED_FC_BACKGROUND_MEAN_BITS, /* fc_background_mean */
+	MAX_USED_FC_BACKGROUND_VARIANCE_BITS, /* fc_background_variance */
+	MAX_USED_FC_BACKGROUND_OUTLIER_PIXELS_BITS /* fc_background_outlier_pixels */
+};
+
diff --git a/lib/cmp_max_used_bits_list.c b/lib/cmp_max_used_bits_list.c
new file mode 100644
index 0000000..bc66d9e
--- /dev/null
+++ b/lib/cmp_max_used_bits_list.c
@@ -0,0 +1,140 @@
+/**
+ * @file   cmp_max_used_bits_list.c
+ * @author Dominik Loidolt (dominik.loidolt@univie.ac.at)
+ * @date   2023
+ *
+ * @copyright GPLv2
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * @brief Implement a list that can hold an arbitrary number of different
+ *	cmp_max_used_bits structs
+ *
+ * @warning not intended for use with the flight software
+ */
+
+
+#include <stdlib.h>
+#include <assert.h>
+
+#include <list.h>
+#include <cmp_max_used_bits.h>
+
+
+struct list_item {
+	struct list_head list;
+	struct cmp_max_used_bits data;
+};
+
+LIST_HEAD(max_used_bits_list);
+
+
+/**
+ * @brief get an item from the max_used_bits list
+ *
+ * @param version  version identifier of the max_used_bits list item
+ *
+ * @returns a pointer to the max_used_bits structure with the corresponding version
+ *	on success; NULL if no list item has the version number
+ */
+
+const struct cmp_max_used_bits *cmp_max_used_bits_list_get(uint8_t version)
+{
+	struct list_item *list_ptr = NULL ;
+	switch (version) {
+	case 0:
+		return &MAX_USED_BITS_SAFE;
+	case 1:
+		return &MAX_USED_BITS_V1;
+
+	}
+
+	list_for_each_entry (list_ptr, &max_used_bits_list, list) {
+		if (list_ptr->data.version == version)
+			return &list_ptr->data;
+	}
+	return NULL;
+}
+
+
+/**
+ * @brief add a max_used_bits item to the list
+ *
+ * @param item  pointer to the cmp_max_used_bits struct to add to the list
+ *
+ * @note if there is an item in the list with the same version number, it will
+ *	be overwritten
+ * @returns 0 on success; 1 if an existing entry is overwritten; -1 on error
+ */
+
+int cmp_max_used_bits_list_add(struct cmp_max_used_bits const *item)
+{
+	struct list_item *item_ptr = NULL;
+	struct cmp_max_used_bits *p;
+
+	if (!item)
+		return -1;
+	if (item->version <= 16)
+		return -1;
+
+	p = (struct cmp_max_used_bits *)cmp_max_used_bits_list_get(item->version);
+	if (p) {
+		*p = *item; /* replace existing list entry */
+		return 1;
+	}
+
+	item_ptr = (struct list_item *)malloc(sizeof(struct list_item));
+	if (!item_ptr)
+		return -1;
+
+	item_ptr->data = *item;
+	list_add(&item_ptr->list, &max_used_bits_list);
+
+	return 0;
+}
+
+
+/**
+ * @brief delete a max_used_bits item from the list
+ *
+ * @param version  version identifier of the max_used_bits list entry to be deleted
+ *
+ * @note if no max_used_bits list item has the version identifier, nothing happens
+ */
+
+void cmp_max_used_bits_list_delet(uint8_t version)
+{
+	struct list_item *list_ptr = NULL ;
+	struct list_item *tmp = NULL ;
+
+	list_for_each_entry_safe (list_ptr, tmp, &max_used_bits_list, list) {
+		if (list_ptr->data.version == version) {
+			list_del(&list_ptr->list);
+			free(list_ptr);
+			list_ptr = NULL;
+		}
+	}
+}
+
+
+/**
+ * @brief delete all max_used_bits item from the list
+ */
+
+void cmp_max_used_bits_list_empty(void)
+{
+	struct list_item *list_ptr = NULL ;
+	struct list_item *tmp = NULL ;
+
+	list_for_each_entry_safe (list_ptr, tmp, &max_used_bits_list, list) {
+		list_del(&list_ptr->list);
+		free(list_ptr);
+		list_ptr = NULL;
+	}
+}
diff --git a/lib/cmp_rdcu_cfg.c b/lib/cmp_rdcu_cfg.c
index 750a35e..0efd4a9 100644
--- a/lib/cmp_rdcu_cfg.c
+++ b/lib/cmp_rdcu_cfg.c
@@ -53,6 +53,7 @@ struct cmp_cfg rdcu_cfg_create(enum cmp_data_type data_type, enum cmp_mode cmp_m
 	cfg.cmp_mode = cmp_mode;
 	cfg.model_value = model_value;
 	cfg.round = lossy_par;
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE;
 
 	if (cmp_cfg_gen_par_is_invalid(&cfg, RDCU_CHECK))
 		cfg.data_type = DATA_TYPE_UNKNOWN;
diff --git a/lib/cmp_support.c b/lib/cmp_support.c
index e718ba4..7bc88b2 100644
--- a/lib/cmp_support.c
+++ b/lib/cmp_support.c
@@ -490,9 +490,9 @@ int cmp_cfg_gen_par_is_invalid(const struct cmp_cfg *cfg, enum check_opt opt)
 /**
  * @brief check if the ICU buffer parameters are invalid
  *
- * @param cfg	pointer to the compressor configuration
- *
- * @returns 0 if the buffer parameters are valid, otherwise invalid
+* @param cfg	pointer to the compressor configuration
+*
+* @returns 0 if the buffer parameters are valid, otherwise invalid
  */
 
 int cmp_cfg_icu_buffers_is_invalid(const struct cmp_cfg *cfg)
@@ -560,6 +560,70 @@ int cmp_cfg_icu_buffers_is_invalid(const struct cmp_cfg *cfg)
 }
 
 
+/**
+ * @brief check if all entries in the max_used_bits structure are in the allowed range
+ *
+* @param max_used_bits	pointer to max_used_bits structure to check
+*
+* @returns 0 if all entries are valid, otherwise one or more entries are invalid
+ */
+
+
+int cmp_cfg_icu_max_used_bits_out_of_limit(const struct cmp_max_used_bits *max_used_bits)
+{
+#define CHECK_MAX_USED_BITS_LIMIT(entry) \
+	do { \
+	if (max_used_bits->entry > MAX_USED_BITS_SAFE.entry) { \
+		debug_print("Error: The " #entry " entry in the max_used_bits structure is too large (actual: %x, max: %x).\n",  max_used_bits->entry, MAX_USED_BITS_SAFE.entry); \
+		error++; \
+	} \
+	} while (0)
+
+	int error = 0;
+
+	if (!max_used_bits) {
+		debug_print("Error: The pointer to the max_used_bits structure is NULL.\n");
+		return 1;
+	}
+
+	CHECK_MAX_USED_BITS_LIMIT(s_exp_flags);
+	CHECK_MAX_USED_BITS_LIMIT(s_fx);
+	CHECK_MAX_USED_BITS_LIMIT(s_efx);
+	CHECK_MAX_USED_BITS_LIMIT(s_ncob);
+	CHECK_MAX_USED_BITS_LIMIT(s_ecob);
+	CHECK_MAX_USED_BITS_LIMIT(f_fx);
+	CHECK_MAX_USED_BITS_LIMIT(f_efx);
+	CHECK_MAX_USED_BITS_LIMIT(f_ncob);
+	CHECK_MAX_USED_BITS_LIMIT(f_ecob);
+	CHECK_MAX_USED_BITS_LIMIT(l_exp_flags);
+	CHECK_MAX_USED_BITS_LIMIT(l_fx);
+	CHECK_MAX_USED_BITS_LIMIT(l_fx_variance);
+	CHECK_MAX_USED_BITS_LIMIT(l_efx);
+	CHECK_MAX_USED_BITS_LIMIT(l_ncob);
+	CHECK_MAX_USED_BITS_LIMIT(l_ecob);
+	CHECK_MAX_USED_BITS_LIMIT(l_cob_variance);
+	CHECK_MAX_USED_BITS_LIMIT(nc_imagette);
+	CHECK_MAX_USED_BITS_LIMIT(saturated_imagette);
+	CHECK_MAX_USED_BITS_LIMIT(nc_offset_mean);
+	CHECK_MAX_USED_BITS_LIMIT(nc_offset_variance);
+	CHECK_MAX_USED_BITS_LIMIT(nc_background_mean);
+	CHECK_MAX_USED_BITS_LIMIT(nc_background_variance);
+	CHECK_MAX_USED_BITS_LIMIT(nc_background_outlier_pixels);
+	CHECK_MAX_USED_BITS_LIMIT(smearing_mean);
+	CHECK_MAX_USED_BITS_LIMIT(smearing_variance_mean);
+	CHECK_MAX_USED_BITS_LIMIT(smearing_outlier_pixels);
+	CHECK_MAX_USED_BITS_LIMIT(fc_imagette);
+	CHECK_MAX_USED_BITS_LIMIT(fc_offset_mean);
+	CHECK_MAX_USED_BITS_LIMIT(fc_offset_variance);
+	CHECK_MAX_USED_BITS_LIMIT(fc_offset_pixel_in_error);
+	CHECK_MAX_USED_BITS_LIMIT(fc_background_mean);
+	CHECK_MAX_USED_BITS_LIMIT(fc_background_variance);
+	CHECK_MAX_USED_BITS_LIMIT(fc_background_outlier_pixels);
+
+	return error;
+}
+
+
 /**
  * @brief check if the combination of the different compression parameters is invalid
  *
@@ -872,6 +936,9 @@ int cmp_cfg_icu_is_invalid(const struct cmp_cfg *cfg)
 
 	cfg_invalid += cmp_cfg_icu_buffers_is_invalid(cfg);
 
+	if (cfg->cmp_mode != CMP_MODE_RAW)
+		cfg_invalid += cmp_cfg_icu_max_used_bits_out_of_limit(cfg->max_used_bits);
+
 	if (cmp_imagette_data_type_is_used(cfg->data_type))
 		cfg_invalid += cmp_cfg_imagette_is_invalid(cfg, ICU_CHECK);
 	else if (cmp_fx_cob_data_type_is_used(cfg->data_type))
diff --git a/lib/decmp.c b/lib/decmp.c
index ea8cecd..41d90a6 100644
--- a/lib/decmp.c
+++ b/lib/decmp.c
@@ -29,15 +29,14 @@
 #include "cmp_debug.h"
 #include "cmp_support.h"
 #include "cmp_data_types.h"
+#include "cmp_max_used_bits.h"
+#include "cmp_max_used_bits_list.h"
 #include "cmp_entity.h"
 
 
 #define MAX_CW_LEN 32 /* maximum Golomb code word bit length */
 
 
-/* maximum used bits registry */
-extern struct cmp_max_used_bits max_used_bits;
-
 
 /**
  * @brief function pointer to a code word decoder function
@@ -579,7 +578,7 @@ static int decompress_imagette(struct cmp_cfg *cfg)
 	uint16_t model;
 
 	err = configure_decoder_setup(&setup, cfg->golomb_par, cfg->spill,
-				      cfg->round, max_used_bits.nc_imagette, cfg);
+				      cfg->round, cfg->max_used_bits->nc_imagette, cfg);
 	if (err)
 		return -1;
 
@@ -685,10 +684,10 @@ static int decompress_s_fx(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_exp_flags, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				    cfg->round, max_used_bits.s_exp_flags, cfg))
+				    cfg->round, cfg->max_used_bits->s_exp_flags, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.s_fx, cfg))
+				    cfg->round, cfg->max_used_bits->s_fx, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -757,13 +756,13 @@ static int decompress_s_fx_efx(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_exp_flags, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				    cfg->round, max_used_bits.s_exp_flags, cfg))
+				    cfg->round, cfg->max_used_bits->s_exp_flags, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.s_fx, cfg))
+				    cfg->round, cfg->max_used_bits->s_fx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				    cfg->round, max_used_bits.s_efx, cfg))
+				    cfg->round, cfg->max_used_bits->s_efx, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -840,13 +839,13 @@ static int decompress_s_fx_ncob(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_exp_flags, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				    cfg->round, max_used_bits.s_exp_flags, cfg))
+				    cfg->round, cfg->max_used_bits->s_exp_flags, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.s_fx, cfg))
+				    cfg->round, cfg->max_used_bits->s_fx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				    cfg->round, max_used_bits.s_ncob, cfg))
+				    cfg->round, cfg->max_used_bits->s_ncob, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -931,19 +930,19 @@ static int decompress_s_fx_efx_ncob_ecob(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_exp_flags, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				    cfg->round, max_used_bits.s_exp_flags, cfg))
+				    cfg->round, cfg->max_used_bits->s_exp_flags, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.s_fx, cfg))
+				    cfg->round, cfg->max_used_bits->s_fx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				    cfg->round, max_used_bits.s_ncob, cfg))
+				    cfg->round, cfg->max_used_bits->s_ncob, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				    cfg->round, max_used_bits.s_efx, cfg))
+				    cfg->round, cfg->max_used_bits->s_efx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_ecob, cfg->cmp_par_ecob, cfg->spill_ecob,
-				    cfg->round, max_used_bits.s_ecob, cfg))
+				    cfg->round, cfg->max_used_bits->s_ecob, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -1052,7 +1051,7 @@ static int decompress_f_fx(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.f_fx, cfg))
+				    cfg->round, cfg->max_used_bits->f_fx, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -1112,10 +1111,10 @@ static int decompress_f_fx_efx(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.f_fx, cfg))
+				    cfg->round, cfg->max_used_bits->f_fx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				    cfg->round, max_used_bits.f_efx, cfg))
+				    cfg->round, cfg->max_used_bits->f_efx, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -1184,10 +1183,10 @@ static int decompress_f_fx_ncob(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.f_fx, cfg))
+				    cfg->round, cfg->max_used_bits->f_fx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				    cfg->round, max_used_bits.f_ncob, cfg))
+				    cfg->round, cfg->max_used_bits->f_ncob, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -1264,16 +1263,16 @@ static int decompress_f_fx_efx_ncob_ecob(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.f_fx, cfg))
+				    cfg->round, cfg->max_used_bits->f_fx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				    cfg->round, max_used_bits.f_ncob, cfg))
+				    cfg->round, cfg->max_used_bits->f_ncob, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				    cfg->round, max_used_bits.f_efx, cfg))
+				    cfg->round, cfg->max_used_bits->f_efx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_ecob, cfg->cmp_par_ecob, cfg->spill_ecob,
-				    cfg->round, max_used_bits.f_ecob, cfg))
+				    cfg->round, cfg->max_used_bits->f_ecob, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -1374,13 +1373,13 @@ static int decompress_l_fx(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_exp_flags, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				    cfg->round, max_used_bits.l_exp_flags, cfg))
+				    cfg->round, cfg->max_used_bits->l_exp_flags, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.l_fx, cfg))
+				    cfg->round, cfg->max_used_bits->l_fx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				    cfg->round, max_used_bits.l_fx_variance, cfg))
+				    cfg->round, cfg->max_used_bits->l_fx_variance, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -1457,16 +1456,16 @@ static int decompress_l_fx_efx(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_exp_flags, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				    cfg->round, max_used_bits.l_exp_flags, cfg))
+				    cfg->round, cfg->max_used_bits->l_exp_flags, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.l_fx, cfg))
+				    cfg->round, cfg->max_used_bits->l_fx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				    cfg->round, max_used_bits.l_efx, cfg))
+				    cfg->round, cfg->max_used_bits->l_efx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				    cfg->round, max_used_bits.l_fx_variance, cfg))
+				    cfg->round, cfg->max_used_bits->l_fx_variance, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -1552,19 +1551,19 @@ static int decompress_l_fx_ncob(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_exp_flags, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				    cfg->round, max_used_bits.l_exp_flags, cfg))
+				    cfg->round, cfg->max_used_bits->l_exp_flags, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.l_fx, cfg))
+				    cfg->round, cfg->max_used_bits->l_fx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				    cfg->round, max_used_bits.l_ncob, cfg))
+				    cfg->round, cfg->max_used_bits->l_ncob, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				    cfg->round, max_used_bits.l_fx_variance, cfg))
+				    cfg->round, cfg->max_used_bits->l_fx_variance, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_cob_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				    cfg->round, max_used_bits.l_cob_variance, cfg))
+				    cfg->round, cfg->max_used_bits->l_cob_variance, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -1674,25 +1673,25 @@ static int decompress_l_fx_efx_ncob_ecob(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_exp_flags, cfg->cmp_par_exp_flags, cfg->spill_exp_flags,
-				    cfg->round, max_used_bits.l_exp_flags, cfg))
+				    cfg->round, cfg->max_used_bits->l_exp_flags, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx, cfg->cmp_par_fx, cfg->spill_fx,
-				    cfg->round, max_used_bits.l_fx, cfg))
+				    cfg->round, cfg->max_used_bits->l_fx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_ncob, cfg->cmp_par_ncob, cfg->spill_ncob,
-				    cfg->round, max_used_bits.l_ncob, cfg))
+				    cfg->round, cfg->max_used_bits->l_ncob, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_efx, cfg->cmp_par_efx, cfg->spill_efx,
-				    cfg->round, max_used_bits.l_efx, cfg))
+				    cfg->round, cfg->max_used_bits->l_efx, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_ecob, cfg->cmp_par_ecob, cfg->spill_ecob,
-				    cfg->round, max_used_bits.l_ecob, cfg))
+				    cfg->round, cfg->max_used_bits->l_ecob, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_fx_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				    cfg->round, max_used_bits.l_fx_variance, cfg))
+				    cfg->round, cfg->max_used_bits->l_fx_variance, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_cob_var, cfg->cmp_par_fx_cob_variance, cfg->spill_fx_cob_variance,
-				    cfg->round, max_used_bits.l_cob_variance, cfg))
+				    cfg->round, cfg->max_used_bits->l_cob_variance, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -1825,10 +1824,10 @@ static int decompress_nc_offset(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_mean, cfg->cmp_par_mean, cfg->spill_mean,
-				    cfg->round, max_used_bits.nc_offset_mean, cfg))
+				    cfg->round, cfg->max_used_bits->nc_offset_mean, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_var, cfg->cmp_par_variance, cfg->spill_variance,
-				    cfg->round, max_used_bits.nc_offset_variance, cfg))
+				    cfg->round, cfg->max_used_bits->nc_offset_variance, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -1897,13 +1896,13 @@ static int decompress_nc_background(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_mean, cfg->cmp_par_mean, cfg->spill_mean,
-				    cfg->round, max_used_bits.nc_background_mean, cfg))
+				    cfg->round, cfg->max_used_bits->nc_background_mean, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_var, cfg->cmp_par_variance, cfg->spill_variance,
-				    cfg->round, max_used_bits.nc_background_variance, cfg))
+				    cfg->round, cfg->max_used_bits->nc_background_variance, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_pix, cfg->cmp_par_pixels_error, cfg->spill_pixels_error,
-				    cfg->round, max_used_bits.nc_background_outlier_pixels, cfg))
+				    cfg->round, cfg->max_used_bits->nc_background_outlier_pixels, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -1980,13 +1979,13 @@ static int decompress_smearing(const struct cmp_cfg *cfg)
 	}
 
 	if (configure_decoder_setup(&setup_mean, cfg->cmp_par_mean, cfg->spill_mean,
-				    cfg->round, max_used_bits.smearing_mean, cfg))
+				    cfg->round, cfg->max_used_bits->smearing_mean, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_var, cfg->cmp_par_variance, cfg->spill_variance,
-				    cfg->round, max_used_bits.smearing_variance_mean, cfg))
+				    cfg->round, cfg->max_used_bits->smearing_variance_mean, cfg))
 		return -1;
 	if (configure_decoder_setup(&setup_pix, cfg->cmp_par_pixels_error, cfg->spill_pixels_error,
-				    cfg->round, max_used_bits.smearing_outlier_pixels, cfg))
+				    cfg->round, cfg->max_used_bits->smearing_outlier_pixels, cfg))
 		return -1;
 
 	for (i = 0; ; i++) {
@@ -2048,6 +2047,9 @@ static int decompressed_data_internal(struct cmp_cfg *cfg)
 	if (!cfg->icu_output_buf)
 		return -1;
 
+	if (!cfg->max_used_bits)
+		return -1;
+
 	data_size = cmp_cal_size_of_data(cfg->samples, cfg->data_type);
 	if (!cfg->input_buf || !data_size)
 		return data_size;
@@ -2143,6 +2145,122 @@ static int decompressed_data_internal(struct cmp_cfg *cfg)
 }
 
 
+/**
+ * @brief read in an imagette compression entity header to a
+ *	compression configuration
+ *
+ * @param ent	pointer to a compression entity
+ * @param cfg	pointer to a compression configuration
+ *
+ * @returns 0 on success; otherwise error
+ */
+
+static int cmp_ent_read_header(struct cmp_entity *ent, struct cmp_cfg *cfg)
+{
+	int32_t samples;
+
+	if (!cfg)
+		return -1;
+
+	cfg->data_type = cmp_ent_get_data_type(ent);
+	if (cmp_data_type_is_invalid(cfg->data_type)) {
+		debug_print("Error: Compression data type not supported.\n");
+		return -1;
+	}
+
+	cfg->cmp_mode = cmp_ent_get_cmp_mode(ent);
+	if (cmp_ent_get_data_type_raw_bit(ent) != (cfg->cmp_mode == CMP_MODE_RAW)) {
+		debug_print("Error: The entity's raw data bit does not match up with the compression mode.\n");
+		return -1;
+	}
+	cfg->model_value = cmp_ent_get_model_value(ent);
+	cfg->round = cmp_ent_get_lossy_cmp_par(ent);
+	cfg->buffer_length = cmp_ent_get_cmp_data_size(ent);
+
+	samples = cmp_input_size_to_samples(cmp_ent_get_original_size(ent), cfg->data_type);
+	if (samples < 0) {
+		debug_print("Error: original_size and data product type in the compression header are not compatible.\n");
+		cfg->samples = 0;
+		return -1;
+	}
+
+	cfg->samples = (uint32_t)samples;
+
+	cfg->icu_output_buf = cmp_ent_get_data_buf(ent);
+
+	cfg->max_used_bits = cmp_max_used_bits_list_get(cmp_ent_get_max_used_bits_version(ent));
+	if (!cfg->max_used_bits) {
+		debug_print("Error: The Max. Used Bits Registry Version in the compression header is unknown.\n");
+		return -1;
+	}
+
+	if (cfg->cmp_mode == CMP_MODE_RAW)
+		/* no specific header is used for raw data we are done */
+		return 0;
+
+	switch (cfg->data_type) {
+	case DATA_TYPE_IMAGETTE_ADAPTIVE:
+	case DATA_TYPE_SAT_IMAGETTE_ADAPTIVE:
+	case DATA_TYPE_F_CAM_IMAGETTE_ADAPTIVE:
+		cfg->ap1_golomb_par = cmp_ent_get_ima_ap1_golomb_par(ent);
+		cfg->ap1_spill = cmp_ent_get_ima_ap1_spill(ent);
+		cfg->ap2_golomb_par = cmp_ent_get_ima_ap2_golomb_par(ent);
+		cfg->ap2_spill = cmp_ent_get_ima_ap2_spill(ent);
+		/* fall through */
+	case DATA_TYPE_IMAGETTE:
+	case DATA_TYPE_SAT_IMAGETTE:
+	case DATA_TYPE_F_CAM_IMAGETTE:
+		cfg->spill = cmp_ent_get_ima_spill(ent);
+		cfg->golomb_par = cmp_ent_get_ima_golomb_par(ent);
+		break;
+	case DATA_TYPE_OFFSET:
+	case DATA_TYPE_BACKGROUND:
+	case DATA_TYPE_SMEARING:
+		cfg->cmp_par_mean = cmp_ent_get_non_ima_cmp_par1(ent);
+		cfg->spill_mean = cmp_ent_get_non_ima_spill1(ent);
+		cfg->cmp_par_variance = cmp_ent_get_non_ima_cmp_par2(ent);
+		cfg->spill_variance = cmp_ent_get_non_ima_spill2(ent);
+		cfg->cmp_par_pixels_error = cmp_ent_get_non_ima_cmp_par3(ent);
+		cfg->spill_pixels_error = cmp_ent_get_non_ima_spill3(ent);
+		break;
+	case DATA_TYPE_S_FX:
+	case DATA_TYPE_S_FX_EFX:
+	case DATA_TYPE_S_FX_NCOB:
+	case DATA_TYPE_S_FX_EFX_NCOB_ECOB:
+	case DATA_TYPE_L_FX:
+	case DATA_TYPE_L_FX_EFX:
+	case DATA_TYPE_L_FX_NCOB:
+	case DATA_TYPE_L_FX_EFX_NCOB_ECOB:
+	case DATA_TYPE_F_FX:
+	case DATA_TYPE_F_FX_EFX:
+	case DATA_TYPE_F_FX_NCOB:
+	case DATA_TYPE_F_FX_EFX_NCOB_ECOB:
+		cfg->cmp_par_exp_flags = cmp_ent_get_non_ima_cmp_par1(ent);
+		cfg->spill_exp_flags = cmp_ent_get_non_ima_spill1(ent);
+		cfg->cmp_par_fx = cmp_ent_get_non_ima_cmp_par2(ent);
+		cfg->spill_fx = cmp_ent_get_non_ima_spill2(ent);
+		cfg->cmp_par_ncob = cmp_ent_get_non_ima_cmp_par3(ent);
+		cfg->spill_ncob = cmp_ent_get_non_ima_spill3(ent);
+		cfg->cmp_par_efx = cmp_ent_get_non_ima_cmp_par4(ent);
+		cfg->spill_efx = cmp_ent_get_non_ima_spill4(ent);
+		cfg->cmp_par_ecob = cmp_ent_get_non_ima_cmp_par5(ent);
+		cfg->spill_ecob = cmp_ent_get_non_ima_spill5(ent);
+		cfg->cmp_par_fx_cob_variance = cmp_ent_get_non_ima_cmp_par6(ent);
+		cfg->spill_fx_cob_variance = cmp_ent_get_non_ima_spill6(ent);
+		break;
+	case DATA_TYPE_F_CAM_OFFSET:
+	case DATA_TYPE_F_CAM_BACKGROUND:
+	/* LCOV_EXCL_START */
+	case DATA_TYPE_UNKNOWN:
+	default:
+		return -1;
+	/* LCOV_EXCL_STOP */
+	}
+
+	return 0;
+}
+
+
 /**
  * @brief decompress a compression entity
  *
@@ -2224,6 +2342,7 @@ int decompress_rdcu_data(uint32_t *compressed_data, const struct cmp_info *info,
 	cfg.samples = info->samples_used;
 	cfg.icu_output_buf = compressed_data;
 	cfg.buffer_length = cmp_bit_to_4byte(info->cmp_size);
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE;
 
 	return decompressed_data_internal(&cfg);
 }
diff --git a/lib/meson.build b/lib/meson.build
index 9a4f44d..2d35635 100644
--- a/lib/meson.build
+++ b/lib/meson.build
@@ -12,7 +12,9 @@ cmplib_sources = files([
   'cmp_rdcu_cfg.c',
   'cmp_rdcu.c',
   'rdcu_cmd.c',
-  'rdcu_rmap.c'
+  'rdcu_rmap.c',
+  'cmp_max_used_bits.c',
+  'cmp_max_used_bits_list.c'
 ])
 
 cmp_lib = static_library('cmp_lib',
diff --git a/test/cmp_data_types/test_cmp_data_types.c b/test/cmp_data_types/test_cmp_data_types.c
index 403143c..2057348 100644
--- a/test/cmp_data_types/test_cmp_data_types.c
+++ b/test/cmp_data_types/test_cmp_data_types.c
@@ -23,69 +23,6 @@
 #include <cmp_data_types.h>
 
 
-/**
- * @test cmp_set_max_us
- */
-
-void test_cmp_set_max_used_bits(void)
-{
-	struct cmp_max_used_bits set_max_used_bits = cmp_get_max_used_bits();
-
-	cmp_set_max_used_bits(&set_max_used_bits);
-	cmp_set_max_used_bits(NULL);
-}
-
-
-/**
- * @test cmp_get_max_used_bits
- */
-
-void test_cmp_get_max_used_bits(void)
-{
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
-
-	TEST_ASSERT_EQUAL_INT(max_used_bits.nc_imagette, MAX_USED_NC_IMAGETTE_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.saturated_imagette, MAX_USED_SATURATED_IMAGETTE_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.fc_imagette, MAX_USED_FC_IMAGETTE_BITS);
-
-	TEST_ASSERT_EQUAL_INT(max_used_bits.f_fx, MAX_USED_F_FX_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.f_efx, MAX_USED_F_EFX_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.f_ncob, MAX_USED_F_NCOB_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.f_ecob, MAX_USED_F_ECOB_BITS);
-
-	TEST_ASSERT_EQUAL_INT(max_used_bits.s_exp_flags, MAX_USED_S_FX_EXPOSURE_FLAGS_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.s_fx, MAX_USED_S_FX_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.s_efx, MAX_USED_S_EFX_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.s_ncob, MAX_USED_S_NCOB_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.s_ecob, MAX_USED_S_ECOB_BITS);
-
-	TEST_ASSERT_EQUAL_INT(max_used_bits.l_fx_variance, MAX_USED_L_FX_VARIANCE_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.l_efx, MAX_USED_L_EFX_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.l_ncob, MAX_USED_L_NCOB_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.l_ecob, MAX_USED_L_ECOB_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.l_cob_variance, MAX_USED_L_COB_VARIANCE_BITS);
-
-	TEST_ASSERT_EQUAL_INT(max_used_bits.nc_offset_mean, MAX_USED_NC_OFFSET_MEAN_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.nc_offset_variance, MAX_USED_NC_OFFSET_VARIANCE_BITS);
-
-	TEST_ASSERT_EQUAL_INT(max_used_bits.nc_background_mean, MAX_USED_NC_BACKGROUND_MEAN_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.nc_background_variance, MAX_USED_NC_BACKGROUND_VARIANCE_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.nc_background_outlier_pixels, MAX_USED_NC_BACKGROUND_OUTLIER_PIXELS_BITS);
-
-	TEST_ASSERT_EQUAL_INT(max_used_bits.smearing_mean, MAX_USED_SMEARING_MEAN_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.smearing_variance_mean, MAX_USED_SMEARING_VARIANCE_MEAN_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.smearing_outlier_pixels, MAX_USED_SMEARING_OUTLIER_PIXELS_BITS);
-
-	TEST_ASSERT_EQUAL_INT(max_used_bits.fc_offset_mean, MAX_USED_FC_OFFSET_MEAN_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.fc_offset_variance, MAX_USED_FC_OFFSET_VARIANCE_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.fc_offset_pixel_in_error, MAX_USED_FC_OFFSET_PIXEL_IN_ERROR_BITS);
-
-	TEST_ASSERT_EQUAL_INT(max_used_bits.fc_background_mean, MAX_USED_FC_BACKGROUND_MEAN_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.fc_background_variance, MAX_USED_FC_BACKGROUND_VARIANCE_BITS);
-	TEST_ASSERT_EQUAL_INT(max_used_bits.fc_background_outlier_pixels, MAX_USED_FC_BACKGROUND_OUTLIER_PIXELS_BITS);
-}
-
-
 /**
  * @test size_of_a_sample
  */
diff --git a/test/cmp_decmp/test_cmp_decmp.c b/test/cmp_decmp/test_cmp_decmp.c
index 77de318..ffc9963 100644
--- a/test/cmp_decmp/test_cmp_decmp.c
+++ b/test/cmp_decmp/test_cmp_decmp.c
@@ -108,221 +108,220 @@ uint32_t random_between(unsigned int min, unsigned int max)
 }
 
 
-static void gen_ima_data(uint16_t *data, uint32_t samples)
+static void gen_ima_data(uint16_t *data, uint32_t samples, const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++)
-		data[i] = random_between(0, set_n_bits(max_used_bits.nc_imagette));
+		data[i] = (uint16_t)random_between(0, set_n_bits(max_used_bits->nc_imagette));
 }
 
 
-static void gen_offset_data(struct nc_offset *data, uint32_t samples)
+static void gen_offset_data(struct nc_offset *data, uint32_t samples,
+			    const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].mean = random_between(0, set_n_bits(max_used_bits.nc_offset_mean));
-		data[i].variance = random_between(0, set_n_bits(max_used_bits.nc_offset_variance));
+		data[i].mean = random_between(0, set_n_bits(max_used_bits->nc_offset_mean));
+		data[i].variance = random_between(0, set_n_bits(max_used_bits->nc_offset_variance));
 	}
 }
 
 
-static void gen_background_data(struct nc_background *data, uint32_t samples)
+static void gen_background_data(struct nc_background *data, uint32_t samples,
+				const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].mean = random_between(0, set_n_bits(max_used_bits.nc_background_mean));
-		data[i].variance = random_between(0, set_n_bits(max_used_bits.nc_background_variance));
-		data[i].outlier_pixels = random_between(0, set_n_bits(max_used_bits.nc_background_outlier_pixels));
+		data[i].mean = random_between(0, set_n_bits(max_used_bits->nc_background_mean));
+		data[i].variance = random_between(0, set_n_bits(max_used_bits->nc_background_variance));
+		data[i].outlier_pixels = random_between(0, set_n_bits(max_used_bits->nc_background_outlier_pixels));
 	}
 }
 
 
-static void gen_smearing_data(struct smearing *data, uint32_t samples)
+static void gen_smearing_data(struct smearing *data, uint32_t samples,
+			      const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].mean = random_between(0, set_n_bits(max_used_bits.smearing_mean));
-		data[i].variance_mean = random_between(0, set_n_bits(max_used_bits.smearing_variance_mean));
-		data[i].outlier_pixels = random_between(0, set_n_bits(max_used_bits.smearing_outlier_pixels));
+		data[i].mean = random_between(0, set_n_bits(max_used_bits->smearing_mean));
+		data[i].variance_mean = random_between(0, set_n_bits(max_used_bits->smearing_variance_mean));
+		data[i].outlier_pixels = random_between(0, set_n_bits(max_used_bits->smearing_outlier_pixels));
 	}
 }
 
 
-static void gen_s_fx_data(struct s_fx *data, uint32_t samples)
+static void gen_s_fx_data(struct s_fx *data, uint32_t samples,
+			  const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits.s_exp_flags));
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.s_fx));
+		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits->s_exp_flags));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->s_fx));
 	}
 }
 
 
-static void gen_s_fx_efx_data(struct s_fx_efx *data, uint32_t samples)
+static void gen_s_fx_efx_data(struct s_fx_efx *data, uint32_t samples,
+			      const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits.s_exp_flags));
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.s_fx));
-		data[i].efx = random_between(0, set_n_bits(max_used_bits.s_efx));
+		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits->s_exp_flags));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->s_fx));
+		data[i].efx = random_between(0, set_n_bits(max_used_bits->s_efx));
 	}
 }
 
 
-static void gen_s_fx_ncob_data(struct s_fx_ncob *data, uint32_t samples)
+static void gen_s_fx_ncob_data(struct s_fx_ncob *data, uint32_t samples,
+			       const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits.s_exp_flags));
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.s_fx));
-		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits.s_ncob));
-		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits.s_ncob));
+		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits->s_exp_flags));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->s_fx));
+		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits->s_ncob));
+		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits->s_ncob));
 	}
 }
 
 
-static void gen_s_fx_efx_ncob_ecob_data(struct s_fx_efx_ncob_ecob *data, uint32_t samples)
+static void gen_s_fx_efx_ncob_ecob_data(struct s_fx_efx_ncob_ecob *data, uint32_t samples,
+					const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits.s_exp_flags));
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.s_fx));
-		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits.s_ncob));
-		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits.s_ncob));
-		data[i].efx = random_between(0, set_n_bits(max_used_bits.s_efx));
-		data[i].ecob_x = random_between(0, set_n_bits(max_used_bits.s_ecob));
-		data[i].ecob_y = random_between(0, set_n_bits(max_used_bits.s_ecob));
+		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits->s_exp_flags));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->s_fx));
+		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits->s_ncob));
+		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits->s_ncob));
+		data[i].efx = random_between(0, set_n_bits(max_used_bits->s_efx));
+		data[i].ecob_x = random_between(0, set_n_bits(max_used_bits->s_ecob));
+		data[i].ecob_y = random_between(0, set_n_bits(max_used_bits->s_ecob));
 	}
 }
 
 
-static void gen_f_fx_data(struct f_fx *data, uint32_t samples)
+static void gen_f_fx_data(struct f_fx *data, uint32_t samples,
+			  const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++)
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.f_fx));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->f_fx));
 }
 
 
-static void gen_f_fx_efx_data(struct f_fx_efx *data, uint32_t samples)
+static void gen_f_fx_efx_data(struct f_fx_efx *data, uint32_t samples,
+			      const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.f_fx));
-		data[i].efx = random_between(0, set_n_bits(max_used_bits.f_efx));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->f_fx));
+		data[i].efx = random_between(0, set_n_bits(max_used_bits->f_efx));
 	}
 }
 
 
-static void gen_f_fx_ncob_data(struct f_fx_ncob *data, uint32_t samples)
+static void gen_f_fx_ncob_data(struct f_fx_ncob *data, uint32_t samples,
+			       const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.f_fx));
-		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits.f_ncob));
-		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits.f_ncob));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->f_fx));
+		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits->f_ncob));
+		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits->f_ncob));
 	}
 }
 
 
-static void gen_f_fx_efx_ncob_ecob_data(struct f_fx_efx_ncob_ecob *data, uint32_t samples)
+static void gen_f_fx_efx_ncob_ecob_data(struct f_fx_efx_ncob_ecob *data, uint32_t samples,
+					const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.f_fx));
-		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits.f_ncob));
-		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits.f_ncob));
-		data[i].efx = random_between(0, set_n_bits(max_used_bits.f_efx));
-		data[i].ecob_x = random_between(0, set_n_bits(max_used_bits.f_ecob));
-		data[i].ecob_y = random_between(0, set_n_bits(max_used_bits.f_ecob));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->f_fx));
+		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits->f_ncob));
+		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits->f_ncob));
+		data[i].efx = random_between(0, set_n_bits(max_used_bits->f_efx));
+		data[i].ecob_x = random_between(0, set_n_bits(max_used_bits->f_ecob));
+		data[i].ecob_y = random_between(0, set_n_bits(max_used_bits->f_ecob));
 	}
 }
 
 
-static void gen_l_fx_data(struct l_fx *data, uint32_t samples)
+static void gen_l_fx_data(struct l_fx *data, uint32_t samples,
+			  const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits.l_exp_flags));
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.l_fx));
-		data[i].fx_variance = random_between(0, set_n_bits(max_used_bits.l_fx_variance));
+		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits->l_exp_flags));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->l_fx));
+		data[i].fx_variance = random_between(0, set_n_bits(max_used_bits->l_fx_variance));
 	}
 }
 
 
-static void gen_l_fx_efx_data(struct l_fx_efx *data, uint32_t samples)
+static void gen_l_fx_efx_data(struct l_fx_efx *data, uint32_t samples,
+			      const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits.l_exp_flags));
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.l_fx));
-		data[i].efx = random_between(0, set_n_bits(max_used_bits.l_efx));
-		data[i].fx_variance = random_between(0, set_n_bits(max_used_bits.l_fx_variance));
+		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits->l_exp_flags));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->l_fx));
+		data[i].efx = random_between(0, set_n_bits(max_used_bits->l_efx));
+		data[i].fx_variance = random_between(0, set_n_bits(max_used_bits->l_fx_variance));
 	}
 }
 
 
-static void gen_l_fx_ncob_data(struct l_fx_ncob *data, uint32_t samples)
+static void gen_l_fx_ncob_data(struct l_fx_ncob *data, uint32_t samples,
+			       const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits.l_exp_flags));
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.l_fx));
-		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits.l_ncob));
-		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits.l_ncob));
-		data[i].fx_variance = random_between(0, set_n_bits(max_used_bits.l_fx_variance));
-		data[i].cob_x_variance = random_between(0, set_n_bits(max_used_bits.l_cob_variance));
-		data[i].cob_y_variance = random_between(0, set_n_bits(max_used_bits.l_cob_variance));
+		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits->l_exp_flags));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->l_fx));
+		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits->l_ncob));
+		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits->l_ncob));
+		data[i].fx_variance = random_between(0, set_n_bits(max_used_bits->l_fx_variance));
+		data[i].cob_x_variance = random_between(0, set_n_bits(max_used_bits->l_cob_variance));
+		data[i].cob_y_variance = random_between(0, set_n_bits(max_used_bits->l_cob_variance));
 	}
 }
 
 
-static void gen_l_fx_efx_ncob_ecob_data(struct l_fx_efx_ncob_ecob *data, uint32_t samples)
+static void gen_l_fx_efx_ncob_ecob_data(struct l_fx_efx_ncob_ecob *data, uint32_t samples,
+					const struct cmp_max_used_bits *max_used_bits)
 {
 	uint32_t i;
-	struct cmp_max_used_bits max_used_bits = cmp_get_max_used_bits();
 
 	for (i = 0; i < samples; i++) {
-		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits.l_exp_flags));
-		data[i].fx = random_between(0, set_n_bits(max_used_bits.l_fx));
-		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits.l_ncob));
-		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits.l_ncob));
-		data[i].efx = random_between(0, set_n_bits(max_used_bits.l_efx));
-		data[i].ecob_x = random_between(0, set_n_bits(max_used_bits.l_ecob));
-		data[i].ecob_y = random_between(0, set_n_bits(max_used_bits.l_ecob));
-		data[i].fx_variance = random_between(0, set_n_bits(max_used_bits.l_fx_variance));
-		data[i].cob_x_variance = random_between(0, set_n_bits(max_used_bits.l_cob_variance));
-		data[i].cob_y_variance = random_between(0, set_n_bits(max_used_bits.l_cob_variance));
+		data[i].exp_flags = random_between(0, set_n_bits(max_used_bits->l_exp_flags));
+		data[i].fx = random_between(0, set_n_bits(max_used_bits->l_fx));
+		data[i].ncob_x = random_between(0, set_n_bits(max_used_bits->l_ncob));
+		data[i].ncob_y = random_between(0, set_n_bits(max_used_bits->l_ncob));
+		data[i].efx = random_between(0, set_n_bits(max_used_bits->l_efx));
+		data[i].ecob_x = random_between(0, set_n_bits(max_used_bits->l_ecob));
+		data[i].ecob_y = random_between(0, set_n_bits(max_used_bits->l_ecob));
+		data[i].fx_variance = random_between(0, set_n_bits(max_used_bits->l_fx_variance));
+		data[i].cob_x_variance = random_between(0, set_n_bits(max_used_bits->l_cob_variance));
+		data[i].cob_y_variance = random_between(0, set_n_bits(max_used_bits->l_cob_variance));
 	}
 }
 
@@ -332,11 +331,13 @@ static void gen_l_fx_efx_ncob_ecob_data(struct l_fx_efx_ncob_ecob *data, uint32_
  *
  * @param samples	number of random test samples
  * @param data_type	compression data type of the test data
+ * @param max_used_bits	pointer to a max_used_bits structure
  *
  * @returns a pointer to the generated random test data
  */
 
-void *generate_random_test_data(uint32_t samples, enum cmp_data_type data_type)
+void *generate_random_test_data(uint32_t samples, enum cmp_data_type data_type,
+				const struct cmp_max_used_bits *max_used_bits)
 {
 	size_t data_size = cmp_cal_size_of_data(samples, data_type);
 	void *data = malloc(data_size);
@@ -363,52 +364,52 @@ void *generate_random_test_data(uint32_t samples, enum cmp_data_type data_type)
 	case DATA_TYPE_SAT_IMAGETTE_ADAPTIVE:
 	case DATA_TYPE_F_CAM_IMAGETTE:
 	case DATA_TYPE_F_CAM_IMAGETTE_ADAPTIVE:
-		gen_ima_data(data, samples);
+		gen_ima_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_OFFSET:
-		gen_offset_data(data, samples);
+		gen_offset_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_BACKGROUND:
-		gen_background_data(data, samples);
+		gen_background_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_SMEARING:
-		gen_smearing_data(data, samples);
+		gen_smearing_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_S_FX:
-		gen_s_fx_data(data, samples);
+		gen_s_fx_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_S_FX_EFX:
-		gen_s_fx_efx_data(data, samples);
+		gen_s_fx_efx_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_S_FX_NCOB:
-		gen_s_fx_ncob_data(data, samples);
+		gen_s_fx_ncob_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_S_FX_EFX_NCOB_ECOB:
-		gen_s_fx_efx_ncob_ecob_data(data, samples);
+		gen_s_fx_efx_ncob_ecob_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_L_FX:
-		gen_l_fx_data(data, samples);
+		gen_l_fx_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_L_FX_EFX:
-		gen_l_fx_efx_data(data, samples);
+		gen_l_fx_efx_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_L_FX_NCOB:
-		gen_l_fx_ncob_data(data, samples);
+		gen_l_fx_ncob_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_L_FX_EFX_NCOB_ECOB:
-		gen_l_fx_efx_ncob_ecob_data(data, samples);
+		gen_l_fx_efx_ncob_ecob_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_F_FX:
-		gen_f_fx_data(data, samples);
+		gen_f_fx_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_F_FX_EFX:
-		gen_f_fx_efx_data(data, samples);
+		gen_f_fx_efx_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_F_FX_NCOB:
-		gen_f_fx_ncob_data(data, samples);
+		gen_f_fx_ncob_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_F_FX_EFX_NCOB_ECOB:
-		gen_f_fx_efx_ncob_ecob_data(data, samples);
+		gen_f_fx_efx_ncob_ecob_data(data, samples, max_used_bits);
 		break;
 	case DATA_TYPE_F_CAM_OFFSET: /* TODO: implement this */
 	case DATA_TYPE_F_CAM_BACKGROUND: /* TODO: implement this */
@@ -424,7 +425,6 @@ void *generate_random_test_data(uint32_t samples, enum cmp_data_type data_type)
  * @brief generate random compression configuration
  *
  * @param cfg	pointer to a compression configuration
- *
  */
 
 void generate_random_cmp_par(struct cmp_cfg *cfg)
@@ -587,8 +587,8 @@ void test_random_compression_decompression(void)
 		/* generate random data*/
 		uint32_t samples = random_between(1, 430179/CMP_BUFFER_FAKTOR);
 		uint32_t model_value = random_between(0, MAX_MODEL_VALUE);
-		void *data_to_compress1 = generate_random_test_data(samples, data_type);
-		void *data_to_compress2 = generate_random_test_data(samples, data_type);
+		void *data_to_compress1 = generate_random_test_data(samples, data_type, &MAX_USED_BITS_V1);
+		void *data_to_compress2 = generate_random_test_data(samples, data_type, &MAX_USED_BITS_V1);
 		void *updated_model = calloc(1, cmp_cal_size_of_data(samples, data_type));
 		/* for (cmp_mode = CMP_MODE_RAW; cmp_mode <= CMP_MODE_STUFF; cmp_mode++) { */
 		for (cmp_mode = CMP_MODE_RAW; cmp_mode <= CMP_MODE_DIFF_MULTI; cmp_mode++) {
diff --git a/test/cmp_entity/test_cmp_entity.c b/test/cmp_entity/test_cmp_entity.c
index 439222d..a36c92d 100644
--- a/test/cmp_entity/test_cmp_entity.c
+++ b/test/cmp_entity/test_cmp_entity.c
@@ -72,7 +72,7 @@ void test_cmp_ent_cal_hdr_size(void)
 	hdr_size = cmp_ent_cal_hdr_size(data_type, raw_mode_flag);
 	TEST_ASSERT_EQUAL_INT(0, hdr_size);
 
-	data_type = ~0;
+	data_type = (enum cmp_data_type)~0;
 	hdr_size = cmp_ent_cal_hdr_size(data_type, raw_mode_flag);
 	TEST_ASSERT_EQUAL_INT(0, hdr_size);
 
@@ -82,7 +82,7 @@ void test_cmp_ent_cal_hdr_size(void)
 	hdr_size = cmp_ent_cal_hdr_size(data_type, raw_mode_flag);
 	TEST_ASSERT_EQUAL_INT(0, hdr_size);
 
-	data_type = ~0;
+	data_type = (enum cmp_data_type)~0;
 	hdr_size = cmp_ent_cal_hdr_size(data_type, raw_mode_flag);
 	TEST_ASSERT_EQUAL_INT(0, hdr_size);
 }
@@ -1365,7 +1365,7 @@ void test_cmp_ent_get_cmp_data(void)
 
 	size = cmp_ent_get_cmp_data(ent, NULL, 0);
 	TEST_ASSERT_EQUAL_INT(12, size);
-	data_buf = malloc(size); TEST_ASSERT_NOT_NULL(data_buf);
+	data_buf = malloc((size_t)size); TEST_ASSERT_NOT_NULL(data_buf);
 
 	size = cmp_ent_get_cmp_data(ent, data_buf, 12);
 	TEST_ASSERT_EQUAL_INT(12, size);
@@ -1422,543 +1422,6 @@ void test_cmp_ent_get_cmp_data_size(void)
 }
 
 
-/**
- * @test cmp_ent_write_cmp_pars
- * @test cmp_ent_read_header
- */
-
-void test_cmp_ent_write_cmp_pars(void)
-{
-	int error;
-	struct cmp_entity *ent;
-	struct cmp_cfg cfg = {0}, cfg_read = {0};
-	int cmp_size_bits;
-	uint32_t size;
-	struct cmp_max_used_bits max_used_bits = {0};
-
-	/* set up max used bit version */
-	max_used_bits.version = 42;
-	cmp_set_max_used_bits(&max_used_bits);
-
-	cmp_size_bits = 93;
-	/** RAW mode test **/
-	/* create imagette raw mode configuration */
-	cfg.data_type = DATA_TYPE_IMAGETTE;
-	cfg.cmp_mode = CMP_MODE_RAW;
-	cfg.model_value = 11;
-	cfg.round = 2;
-	cfg.samples = 9;
-
-	/* create a compression entity */
-	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
-	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_FALSE(error);
-
-	TEST_ASSERT_EQUAL_INT(cfg.data_type, cmp_ent_get_data_type(ent));
-	TEST_ASSERT_EQUAL_INT(1, cmp_ent_get_data_type_raw_bit(ent));
-	TEST_ASSERT_EQUAL_INT(12, cmp_ent_get_cmp_data_size(ent));
-
-	TEST_ASSERT_EQUAL_INT(cmp_cal_size_of_data(cfg.samples, cfg.data_type), cmp_ent_get_original_size(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_mode, cmp_ent_get_cmp_mode(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.model_value, cmp_ent_get_model_value(ent));
-	TEST_ASSERT_EQUAL_INT(max_used_bits.version, cmp_ent_get_max_used_bits_version(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.round, cmp_ent_get_lossy_cmp_par(ent));
-
-	error = cmp_ent_read_header(ent, &cfg_read);
-	TEST_ASSERT_FALSE(error);
-	cfg.icu_output_buf = cmp_ent_get_data_buf(ent); /* quick fix that both cfg are equal */
-	cfg.buffer_length = 12; /* quick fix that both cfg are equal */
-	TEST_ASSERT_EQUAL_MEMORY(&cfg, &cfg_read, sizeof(struct cmp_cfg));
-
-	free(ent);
-	memset(&cfg, 0, sizeof(struct cmp_cfg));
-	memset(&cfg_read, 0, sizeof(struct cmp_cfg));
-
-	/** imagette test **/
-	/* create imagette mode configuration */
-	cfg.data_type = DATA_TYPE_IMAGETTE;
-	cfg.cmp_mode = CMP_MODE_MODEL_ZERO;
-	cfg.model_value = 11;
-	cfg.round = 2;
-	cfg.samples = 9;
-	cfg.spill = MIN_IMA_SPILL;
-	cfg.golomb_par = MAX_IMA_GOLOMB_PAR;
-
-	/* create a compression entity */
-	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
-	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_FALSE(error);
-
-	TEST_ASSERT_EQUAL_INT(cfg.data_type, cmp_ent_get_data_type(ent));
-	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_data_type_raw_bit(ent));
-	TEST_ASSERT_EQUAL_INT(12, cmp_ent_get_cmp_data_size(ent));
-
-	TEST_ASSERT_EQUAL_INT(cmp_cal_size_of_data(cfg.samples, cfg.data_type), cmp_ent_get_original_size(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_mode, cmp_ent_get_cmp_mode(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.model_value, cmp_ent_get_model_value(ent));
-	TEST_ASSERT_EQUAL_INT(max_used_bits.version, cmp_ent_get_max_used_bits_version(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.round, cmp_ent_get_lossy_cmp_par(ent));
-
-	TEST_ASSERT_EQUAL_INT(cfg.spill, cmp_ent_get_ima_spill(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.golomb_par, cmp_ent_get_ima_golomb_par(ent));
-
-	error = cmp_ent_read_header(ent, &cfg_read);
-	TEST_ASSERT_FALSE(error);
-	cfg.icu_output_buf = cmp_ent_get_data_buf(ent); /* quick fix that both cfg are equal */
-	cfg.buffer_length = 12; /* quick fix that both cfg are equal */
-	TEST_ASSERT_EQUAL_MEMORY(&cfg, &cfg_read, sizeof(struct cmp_cfg));
-
-	free(ent);
-	memset(&cfg, 0, sizeof(struct cmp_cfg));
-	memset(&cfg_read, 0, sizeof(struct cmp_cfg));
-
-	/** adaptive imagette test **/
-	/* create a configuration */
-	cfg.data_type = DATA_TYPE_IMAGETTE_ADAPTIVE;
-	cfg.cmp_mode = CMP_MODE_MODEL_ZERO;
-	cfg.model_value = 11;
-	cfg.round = 2;
-	cfg.samples = 9;
-	cfg.spill = MIN_IMA_SPILL;
-	cfg.golomb_par = MAX_IMA_GOLOMB_PAR;
-	cfg.ap1_spill = 555;
-	cfg.ap1_golomb_par = 14;
-	cfg.ap2_spill = 333;
-	cfg.ap2_golomb_par = 43;
-
-	/* create a compression entity */
-	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
-	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_FALSE(error);
-
-	TEST_ASSERT_EQUAL_INT(cfg.data_type, cmp_ent_get_data_type(ent));
-	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_data_type_raw_bit(ent));
-	TEST_ASSERT_EQUAL_INT(12, cmp_ent_get_cmp_data_size(ent));
-
-	TEST_ASSERT_EQUAL_INT(cmp_cal_size_of_data(cfg.samples, cfg.data_type), cmp_ent_get_original_size(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_mode, cmp_ent_get_cmp_mode(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.model_value, cmp_ent_get_model_value(ent));
-	TEST_ASSERT_EQUAL_INT(max_used_bits.version, cmp_ent_get_max_used_bits_version(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.round, cmp_ent_get_lossy_cmp_par(ent));
-
-	TEST_ASSERT_EQUAL_INT(cfg.spill, cmp_ent_get_ima_spill(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.golomb_par, cmp_ent_get_ima_golomb_par(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.ap1_spill, cmp_ent_get_ima_ap1_spill(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.ap1_golomb_par, cmp_ent_get_ima_ap1_golomb_par(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.ap2_spill, cmp_ent_get_ima_ap2_spill(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.ap2_golomb_par, cmp_ent_get_ima_ap2_golomb_par(ent));
-
-	error = cmp_ent_read_header(ent, &cfg_read);
-	TEST_ASSERT_FALSE(error);
-	cfg.icu_output_buf = cmp_ent_get_data_buf(ent); /* quick fix that both cfg are equal */
-	cfg.buffer_length = 12; /* quick fix that both cfg are equal */
-	TEST_ASSERT_EQUAL_MEMORY(&cfg, &cfg_read, sizeof(struct cmp_cfg));
-
-	free(ent);
-	memset(&cfg, 0, sizeof(struct cmp_cfg));
-	memset(&cfg_read, 0, sizeof(struct cmp_cfg));
-
-	/** flux cob data type test **/
-	/* create configuration */
-	cfg.data_type = DATA_TYPE_S_FX_EFX_NCOB_ECOB;
-	cfg.cmp_mode = CMP_MODE_MODEL_ZERO;
-	cfg.model_value = 11;
-	cfg.round = 2;
-	cfg.samples = 9;
-	cfg.spill_exp_flags = 1;
-	cfg.spill_fx = 2;
-	cfg.spill_ncob = 3;
-	cfg.spill_efx = 4;
-	cfg.spill_ecob = 5;
-	cfg.spill_fx_cob_variance = 6;
-	cfg.cmp_par_exp_flags = 7;
-	cfg.cmp_par_fx = 8;
-	cfg.cmp_par_ncob = 9;
-	cfg.cmp_par_efx = 10;
-	cfg.cmp_par_ecob = 11;
-	cfg.cmp_par_fx_cob_variance = 12;
-
-	/* create a compression entity */
-	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
-	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_FALSE(error);
-
-	TEST_ASSERT_EQUAL_INT(cfg.data_type, cmp_ent_get_data_type(ent));
-	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_data_type_raw_bit(ent));
-	TEST_ASSERT_EQUAL_INT(12, cmp_ent_get_cmp_data_size(ent));
-
-	TEST_ASSERT_EQUAL_INT(cmp_cal_size_of_data(cfg.samples, cfg.data_type), cmp_ent_get_original_size(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_mode, cmp_ent_get_cmp_mode(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.model_value, cmp_ent_get_model_value(ent));
-	TEST_ASSERT_EQUAL_INT(max_used_bits.version, cmp_ent_get_max_used_bits_version(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.round, cmp_ent_get_lossy_cmp_par(ent));
-
-
-	TEST_ASSERT_EQUAL_INT(cfg.spill_exp_flags, cmp_ent_get_non_ima_spill1(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.spill_fx, cmp_ent_get_non_ima_spill2(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.spill_ncob, cmp_ent_get_non_ima_spill3(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.spill_efx, cmp_ent_get_non_ima_spill4(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.spill_ecob, cmp_ent_get_non_ima_spill5(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.spill_fx_cob_variance, cmp_ent_get_non_ima_spill6(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_exp_flags, cmp_ent_get_non_ima_cmp_par1(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_fx, cmp_ent_get_non_ima_cmp_par2(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_ncob, cmp_ent_get_non_ima_cmp_par3(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_efx, cmp_ent_get_non_ima_cmp_par4(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_ecob, cmp_ent_get_non_ima_cmp_par5(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_fx_cob_variance, cmp_ent_get_non_ima_cmp_par6(ent));
-
-	error = cmp_ent_read_header(ent, &cfg_read);
-	TEST_ASSERT_FALSE(error);
-	cfg.icu_output_buf = cmp_ent_get_data_buf(ent); /* quick fix that both cfg are equal */
-	cfg.buffer_length = 12; /* quick fix that both cfg are equal */
-	TEST_ASSERT_EQUAL_MEMORY(&cfg, &cfg_read, sizeof(struct cmp_cfg));
-
-	free(ent);
-	memset(&cfg, 0, sizeof(struct cmp_cfg));
-	memset(&cfg_read, 0, sizeof(struct cmp_cfg));
-
-	/** auxiliary data data_type test **/
-	/* create configuration */
-	cfg.data_type = DATA_TYPE_SMEARING;
-	cfg.cmp_mode = CMP_MODE_MODEL_ZERO;
-	cfg.model_value = 11;
-	cfg.round = 2;
-	cfg.samples = 9;
-	cfg.spill_mean = 1;
-	cfg.spill_variance = 2;
-	cfg.spill_pixels_error = 3;
-	cfg.cmp_par_mean = 7;
-	cfg.cmp_par_variance = 8;
-	cfg.cmp_par_pixels_error = 9;
-
-	/* create a compression entity */
-	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
-	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_FALSE(error);
-
-	TEST_ASSERT_EQUAL_INT(cfg.data_type, cmp_ent_get_data_type(ent));
-	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_data_type_raw_bit(ent));
-	TEST_ASSERT_EQUAL_INT(12, cmp_ent_get_cmp_data_size(ent));
-
-	TEST_ASSERT_EQUAL_INT(cmp_cal_size_of_data(cfg.samples, cfg.data_type), cmp_ent_get_original_size(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_mode, cmp_ent_get_cmp_mode(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.model_value, cmp_ent_get_model_value(ent));
-	TEST_ASSERT_EQUAL_INT(max_used_bits.version, cmp_ent_get_max_used_bits_version(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.round, cmp_ent_get_lossy_cmp_par(ent));
-
-
-	TEST_ASSERT_EQUAL_INT(cfg.spill_mean, cmp_ent_get_non_ima_spill1(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.spill_variance, cmp_ent_get_non_ima_spill2(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.spill_pixels_error, cmp_ent_get_non_ima_spill3(ent));
-	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_spill4(ent));
-	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_spill5(ent));
-	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_spill6(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_mean, cmp_ent_get_non_ima_cmp_par1(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_variance, cmp_ent_get_non_ima_cmp_par2(ent));
-	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_pixels_error, cmp_ent_get_non_ima_cmp_par3(ent));
-	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_cmp_par4(ent));
-	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_cmp_par5(ent));
-	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_cmp_par6(ent));
-
-	error = cmp_ent_read_header(ent, &cfg_read);
-	TEST_ASSERT_FALSE(error);
-	cfg.icu_output_buf = cmp_ent_get_data_buf(ent); /* quick fix that both cfg are equal */
-	cfg.buffer_length = 12; /* quick fix that both cfg are equal */
-	TEST_ASSERT_EQUAL_MEMORY(&cfg, &cfg_read, sizeof(struct cmp_cfg));
-
-	free(ent);
-	memset(&cfg, 0, sizeof(struct cmp_cfg));
-	memset(&cfg_read, 0, sizeof(struct cmp_cfg));
-
-	/** Error Cases **/
-	/* create imagette raw mode configuration */
-	cfg.data_type = DATA_TYPE_IMAGETTE;
-	cfg.cmp_mode = CMP_MODE_MODEL_ZERO;
-	cfg.model_value = 11;
-	cfg.round = 2;
-	cfg.samples = 9;
-
-	/* create a compression entity */
-	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
-	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-
-
-	/* ent = NULL */
-	error = cmp_ent_write_cmp_pars(NULL, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-
-	/* cfg = NULL */
-	error = cmp_ent_write_cmp_pars(ent, NULL, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-
-	/* cmp_size_bits negative */
-	error = cmp_ent_write_cmp_pars(ent, &cfg, -1);
-	TEST_ASSERT_TRUE(error);
-
-	/* data_type mismatch */
-	cfg.data_type = DATA_TYPE_S_FX;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.data_type = DATA_TYPE_IMAGETTE;
-
-	/* compressed data to big for compression entity */
-	error = cmp_ent_write_cmp_pars(ent, &cfg, 97);
-	TEST_ASSERT_TRUE(error);
-
-	/* original_size to high */
-	cfg.samples = 0x800000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.samples = 0x7FFFFF;
-
-	/* cmp_mode to high */
-	cfg.cmp_mode = 0x100;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.cmp_mode = 0xFF;
-
-	/* max model_value to high */
-	cfg.model_value = 0x100;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.model_value = 0xFF;
-
-	/*  max used bit version to high */
-	TEST_ASSERT_EQUAL_INT(1, sizeof(max_used_bits.version));
-#if 0
-	max_used_bits.version = 0x100;
-	cmp_set_max_used_bits(&max_used_bits);
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	max_used_bits.version = 42;
-	cmp_set_max_used_bits(&max_used_bits);
-#endif
-
-	/* max lossy_cmp_par to high */
-	cfg.round = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.round = 0xFFFF;
-
-	/* The entity's raw data bit is not set, but the configuration contains raw data */
-	cfg.cmp_mode = CMP_MODE_RAW;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.cmp_mode = CMP_MODE_MODEL_MULTI;
-
-	/* The entity's raw data bit is set, but the configuration contains no raw data */
-	cmp_ent_set_data_type(ent, cfg.data_type, 1); /* set raw bit */
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cmp_ent_set_data_type(ent, cfg.data_type, 0);
-
-	/* spill to high */
-	cfg.spill = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.spill = 0xFFFF;
-
-	/* golomb_par to high */
-	cfg.golomb_par = 0x100;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.golomb_par = 0xFF;
-
-
-	cmp_ent_set_data_type(ent, DATA_TYPE_SAT_IMAGETTE_ADAPTIVE, 0);
-	cfg.data_type = DATA_TYPE_SAT_IMAGETTE_ADAPTIVE;
-	cmp_size_bits = 1;
-	/* adaptive 1 spill to high */
-	cfg.ap1_spill = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.ap1_spill = 0xFFFF;
-
-	/* adaptive 1  golomb_par to high */
-	cfg.ap1_golomb_par = 0x100;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.ap1_golomb_par = 0xFF;
-
-	/* adaptive 2 spill to high */
-	cfg.ap2_spill = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.ap2_spill = 0xFFFF;
-
-	/* adaptive 2  golomb_par to high */
-	cfg.ap2_golomb_par = 0x100;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.ap2_golomb_par = 0xFF;
-
-	cmp_ent_set_data_type(ent, DATA_TYPE_OFFSET, 0);
-	cfg.data_type = DATA_TYPE_OFFSET;
-
-	free(ent);
-
-	/* create a compression entity */
-	cfg.data_type = DATA_TYPE_OFFSET;
-	cfg.samples = 9;
-	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
-	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
-	TEST_ASSERT_NOT_EQUAL_INT(0, size);
-
-	/* mean cmp_par to high */
-	cfg.cmp_par_mean = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.cmp_par_mean = 0xFFFF;
-
-	/* mean spill to high */
-	cfg.spill_mean = 0x1000000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.spill_mean = 0xFFFFFF;
-
-	/* variance cmp_par to high */
-	cfg.cmp_par_variance = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.cmp_par_variance = 0xFFFF;
-
-	/* variance spill to high */
-	cfg.spill_variance = 0x1000000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.spill_variance = 0xFFFFFF;
-
-	/* pixels_error cmp_par to high */
-	cfg.cmp_par_pixels_error = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.cmp_par_pixels_error = 0xFFFF;
-
-	/* pixels_error spill to high */
-	cfg.spill_pixels_error = 0x1000000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.spill_pixels_error = 0xFFFFFF;
-
-
-	cmp_ent_set_data_type(ent, DATA_TYPE_F_FX_EFX_NCOB_ECOB, 0);
-	cfg.data_type = DATA_TYPE_F_FX_EFX_NCOB_ECOB;
-
-	/* exp_flags cmp_par to high */
-	cfg.cmp_par_exp_flags = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.cmp_par_exp_flags = 0xFFFF;
-
-	/* exp_flags spill to high */
-	cfg.spill_exp_flags = 0x1000000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.spill_exp_flags = 0xFFFFFF;
-
-	/* fx cmp_par to high */
-	cfg.cmp_par_fx = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.cmp_par_fx = 0xFFFF;
-
-	/* fx spill to high */
-	cfg.spill_fx = 0x1000000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.spill_fx = 0xFFFFFF;
-
-	/* ncob cmp_par to high */
-	cfg.cmp_par_ncob = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.cmp_par_ncob = 0xFFFF;
-
-	/* ncob spill to high */
-	cfg.spill_ncob = 0x1000000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.spill_ncob = 0xFFFFFF;
-
-	/* efx cmp_par to high */
-	cfg.cmp_par_efx = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.cmp_par_efx = 0xFFFF;
-
-	/* efx spill to high */
-	cfg.spill_efx = 0x1000000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.spill_efx = 0xFFFFFF;
-
-	/* ecob cmp_par to high */
-	cfg.cmp_par_ecob = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.cmp_par_ecob = 0xFFFF;
-
-	/* ecob spill to high */
-	cfg.spill_ecob = 0x1000000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.spill_ecob = 0xFFFFFF;
-
-	/* fx_cob_variance cmp_par to high */
-	cfg.cmp_par_fx_cob_variance = 0x10000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.cmp_par_fx_cob_variance = 0xFFFF;
-
-	/* fx_cob_variance spill to high */
-	cfg.spill_fx_cob_variance = 0x1000000;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	cfg.spill_fx_cob_variance = 0xFFFFFF;
-
-	/* test data type = DATA_TYPE_UNKNOWN */
-	cmp_ent_set_data_type(ent, DATA_TYPE_UNKNOWN, 0);
-	cfg.data_type = DATA_TYPE_UNKNOWN;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-
-	/* test data type = DATA_TYPE_F_CAM_BACKGROUND +1 */
-	cmp_ent_set_data_type(ent, DATA_TYPE_F_CAM_BACKGROUND + 1, 0);
-	cfg.data_type = DATA_TYPE_F_CAM_BACKGROUND + 1;
-	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
-	TEST_ASSERT_TRUE(error);
-	free(ent);
-}
 
 
 /**
@@ -1972,21 +1435,12 @@ void test_cmp_ent_write_rdcu_cmp_pars(void)
 	struct cmp_entity *ent;
 	struct cmp_info info;
 	struct cmp_cfg cfg;
-	struct cmp_max_used_bits max_used_bits = {0};
-
-	/* set up max used bit version */
-	max_used_bits.version = 42;
-	cmp_set_max_used_bits(&max_used_bits);
 
 	info.cmp_mode_used = CMP_MODE_DIFF_ZERO;
 	info.spill_used = 42;
 	info.golomb_par_used = 23;
 	info.samples_used = 9;
 	info.cmp_size = 96;
-	/* info.ap1_cmp_size = 100; */
-	/* info.ap2_cmp_size = 3; */
-	/* info.rdcu_new_model_adr_used = 0x100; */
-	/* info.rdcu_cmp_adr_used= 0x300; */
 	info.model_value_used = 6;
 	info.round_used = 1;
 	info.cmp_err = 0;
@@ -2355,7 +1809,7 @@ void test_cmp_ent_build(void)
 
 	/* set up max used bit version */
 	max_used_bits.version = 42;
-	cmp_set_max_used_bits(&max_used_bits);
+	cfg.max_used_bits = &max_used_bits;
 
 	version_id = 42;
 	start_time = 100;
@@ -2470,74 +1924,6 @@ void test_cmp_ent_build(void)
 }
 
 
-/**
- * @test cmp_ent_read_header
- */
-
-void test_cmp_ent_read_header_error_cases(void)
-
-{
-	int error;
-	uint32_t size;
-	struct cmp_entity *ent;
-	struct cmp_cfg cfg;
-
-	/* create a entity */
-	size = cmp_ent_create(NULL, DATA_TYPE_IMAGETTE, 1, 10);
-	TEST_ASSERT_EQUAL_UINT32(sizeof(struct cmp_entity), size);
-	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
-	size = cmp_ent_create(ent, DATA_TYPE_IMAGETTE, 1, 10);
-	TEST_ASSERT_EQUAL_UINT32(sizeof(struct cmp_entity), size);
-
-	/* ent = NULL */
-	error = cmp_ent_read_header(NULL, &cfg);
-	TEST_ASSERT_TRUE(error);
-	/* this should work */
-	error = cmp_ent_read_header(ent, &cfg);
-	TEST_ASSERT_FALSE(error);
-
-	/* cfg = NULL */
-	error = cmp_ent_read_header(ent, NULL);
-	TEST_ASSERT_TRUE(error);
-	/* this should work */
-	error = cmp_ent_read_header(ent, &cfg);
-	TEST_ASSERT_FALSE(error);
-
-	/* unknown data type */
-	cmp_ent_set_data_type(ent, DATA_TYPE_UNKNOWN, 1);
-	error = cmp_ent_read_header(ent, &cfg);
-	TEST_ASSERT_TRUE(error);
-	/* unknown data type */
-	cmp_ent_set_data_type(ent, DATA_TYPE_F_CAM_BACKGROUND+1, 1);
-	error = cmp_ent_read_header(ent, &cfg);
-	TEST_ASSERT_TRUE(error);
-	/* this should work */
-	cmp_ent_set_data_type(ent, DATA_TYPE_IMAGETTE, 1);
-	error = cmp_ent_read_header(ent, &cfg);
-	TEST_ASSERT_FALSE(error);
-
-	/* cmp_mode CMP_MODE_RAW and no raw data bit */
-	cmp_ent_set_data_type(ent, DATA_TYPE_IMAGETTE, 0);
-	error = cmp_ent_read_header(ent, &cfg);
-	TEST_ASSERT_TRUE(error);
-	/* this should work */
-	cmp_ent_set_data_type(ent, DATA_TYPE_IMAGETTE, 1);
-	error = cmp_ent_read_header(ent, &cfg);
-	TEST_ASSERT_FALSE(error);
-
-	/* original_size and data product type not compatible */
-	cmp_ent_set_original_size(ent, 11);
-	error = cmp_ent_read_header(ent, &cfg);
-	TEST_ASSERT_TRUE(error);
-	/* this should work */
-	cmp_ent_set_original_size(ent, 12);
-	error = cmp_ent_read_header(ent, &cfg);
-	TEST_ASSERT_FALSE(error);
-
-	free(ent);
-}
-
-
 /**
  * @test cmp_ent_create_timestamp
  */
@@ -2598,7 +1984,7 @@ void test_cmp_ent_print(void)
 
 	/* set up max used bit version */
 	max_used_bits.version = 42;
-	cmp_set_max_used_bits(&max_used_bits);
+	cfg.max_used_bits = &max_used_bits;
 
 	version_id = 42;
 	start_time = 100;
@@ -2653,7 +2039,7 @@ void test_cmp_ent_parse(void)
 
 	/* set up max used bit version */
 	max_used_bits.version = 42;
-	cmp_set_max_used_bits(&max_used_bits);
+	cfg.max_used_bits = &max_used_bits;
 
 	version_id = 42;
 	start_time = 100;
diff --git a/test/cmp_icu/test_cmp_icu.c b/test/cmp_icu/test_cmp_icu.c
index 26a7f38..3a338c4 100644
--- a/test/cmp_icu/test_cmp_icu.c
+++ b/test/cmp_icu/test_cmp_icu.c
@@ -2382,17 +2382,23 @@ void test_compress_imagette_diff(void)
 {
 	uint16_t data[] = {0xFFFF, 1, 0, 42, 0x8000, 0x7FFF, 0xFFFF};
 	uint32_t output_buf[3] = {0xFFFF, 0xFFFF, 0xFFFF};
+	uint32_t output_buf_size;
 	struct cmp_cfg cfg = {0};
-	int cmp_size;
+	int error, cmp_size;
 
-	cfg.data_type = DATA_TYPE_IMAGETTE;
-	cfg.cmp_mode = CMP_MODE_DIFF_ZERO;
-	cfg.input_buf = data;
-	cfg.samples = 7;
-	cfg.golomb_par = 1;
-	cfg.spill = 8;
-	cfg.icu_output_buf = (uint32_t *)output_buf;
-	cfg.buffer_length = 7;
+	uint32_t golomb_par = 1;
+	uint32_t spill = 8;
+	uint32_t samples = 7;
+
+	cfg = cmp_cfg_icu_create(DATA_TYPE_IMAGETTE, CMP_MODE_DIFF_ZERO,
+				 CMP_PAR_UNUSED, CMP_LOSSLESS);
+	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
+	output_buf_size = cmp_cfg_icu_buffers(&cfg, data, samples, NULL, NULL,
+					      (uint32_t *)output_buf, samples);
+	TEST_ASSERT_EQUAL_INT(samples*sizeof(uint16_t), output_buf_size);
+
+	error = cmp_cfg_icu_imagette(&cfg, golomb_par, spill);
+	TEST_ASSERT_FALSE(error);
 
 	cmp_size = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(66, cmp_size);
@@ -2416,21 +2422,24 @@ void test_compress_imagette_model(void)
 	uint16_t data[]  = {0x0000, 0x0001, 0x0042, 0x8000, 0x7FFF, 0xFFFF, 0xFFFF};
 	uint16_t model[] = {0x0000, 0xFFFF, 0xF301, 0x8FFF, 0x0000, 0xFFFF, 0x0000};
 	uint16_t model_up[7] = {0};
-	uint32_t output_buf[3] = {0xFFFF, 0xFFFF, 0xFFFF};
+	uint32_t output_buf[3] = {~0U, ~0U, ~0U};
+	uint32_t output_buf_size;
 	struct cmp_cfg cfg = {0};
-	int cmp_size;
-
-	cfg.data_type = DATA_TYPE_IMAGETTE;
-	cfg.cmp_mode = CMP_MODE_MODEL_MULTI;
-	cfg.input_buf = data;
-	cfg.model_buf = model;
-	cfg.icu_new_model_buf = model_up;
-	cfg.samples = 7;
-	cfg.golomb_par = 3;
-	cfg.spill = 8;
-	cfg.model_value = 8;
-	cfg.icu_output_buf = (uint32_t *)output_buf;
-	cfg.buffer_length = 8;
+	uint32_t model_value = 8;
+	uint32_t samples = 7;
+	uint32_t buffer_length = 8;
+	uint32_t golomb_par = 3;
+	uint32_t spill = 8;
+	int cmp_size, error;
+
+	cfg = cmp_cfg_icu_create(DATA_TYPE_IMAGETTE, CMP_MODE_MODEL_MULTI,
+				 model_value, CMP_LOSSLESS);
+	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
+	output_buf_size = cmp_cfg_icu_buffers(&cfg, data, samples, model, model_up,
+					      output_buf, buffer_length);
+	TEST_ASSERT_EQUAL_INT(buffer_length*sizeof(uint16_t), output_buf_size);
+	error = cmp_cfg_icu_imagette(&cfg, golomb_par, spill);
+	TEST_ASSERT_FALSE(error);
 
 	cmp_size = icu_compress_data(&cfg);
 
@@ -2465,7 +2474,7 @@ void test_compress_imagette_stuff(void)
 	uint32_t output_buf[4] = {0};
 	struct cmp_cfg cfg = {0};
 
-	int cmp_size;
+	int cmp_size, error;
 	uint8_t output_buf_exp[] = {
 		0x00, 0x00, 0x00, 0x01,
 		0x00, 0x23, 0x00, 0x42,
@@ -2473,13 +2482,20 @@ void test_compress_imagette_stuff(void)
 		0xFF, 0xFF, 0x00, 0x00};
 	uint32_t *output_buf_exp_32;
 
-	cfg.data_type = DATA_TYPE_IMAGETTE;
-	cfg.cmp_mode = CMP_MODE_STUFF;
-	cfg.input_buf = data;
-	cfg.samples = 7;
-	cfg.icu_output_buf = (uint32_t *)output_buf;
-	cfg.buffer_length = 8;
-	cfg.golomb_par = 16; /* how many used bits has the maximum data value */
+	uint32_t samples = 7;
+	uint32_t buffer_length = 8;
+	uint32_t cmp_par = 16; /* how many used bits has the maximum data value */
+	uint32_t output_buf_size;
+
+
+	cfg = cmp_cfg_icu_create(DATA_TYPE_IMAGETTE, CMP_MODE_STUFF,
+				 CMP_PAR_UNUSED, CMP_LOSSLESS);
+	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
+	output_buf_size = cmp_cfg_icu_buffers(&cfg, data, samples, NULL, NULL,
+					      output_buf, buffer_length);
+	TEST_ASSERT_EQUAL_INT(buffer_length*sizeof(uint16_t), output_buf_size);
+	error = cmp_cfg_icu_imagette(&cfg, cmp_par, CMP_PAR_UNUSED);
+	TEST_ASSERT_FALSE(error);
 
 	cmp_size = icu_compress_data(&cfg);
 
@@ -2503,6 +2519,7 @@ void test_compress_imagette_raw(void)
 	struct cmp_cfg cfg = {0};
 	int cmp_size;
 
+	cfg.cmp_mode = CMP_MODE_RAW;
 	cfg.data_type = DATA_TYPE_IMAGETTE;
 	cfg.model_buf = NULL;
 	cfg.input_buf = data;
@@ -2528,6 +2545,7 @@ void test_compress_imagette_raw(void)
 	cfg.samples = 7;
 	cfg.icu_output_buf = NULL;
 	cfg.buffer_length = 7;
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE;
 
 	cmp_size = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(7*16, cmp_size);
@@ -2540,6 +2558,7 @@ void test_compress_imagette_raw(void)
 	cfg.samples = 7;
 	cfg.icu_output_buf = (uint32_t *)output_buf;
 	cfg.buffer_length = 7;
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE;
 
 	cmp_size = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_size);
@@ -2552,6 +2571,7 @@ void test_compress_imagette_raw(void)
 	cfg.samples = 7;
 	cfg.icu_output_buf = (uint32_t *)output_buf;
 	cfg.buffer_length = 6; /* the buffer is to small */
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE;
 
 	cmp_size = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(CMP_ERROR_SMALL_BUF, cmp_size);
@@ -2567,7 +2587,7 @@ void test_compress_imagette_error_cases(void)
 	uint16_t data[] = {0xFFFF, 1, 0, 42, 0x8000, 0x7FFF, 0xFFFF};
 	uint32_t output_buf[2] = {0xFFFF, 0xFFFF};
 	struct cmp_cfg cfg = {0};
-	int cmp_size;
+	int cmp_size, error;
 	struct cmp_max_used_bits my_max_used_bits;
 
 	cfg.data_type = DATA_TYPE_IMAGETTE;
@@ -2578,6 +2598,7 @@ void test_compress_imagette_error_cases(void)
 	cfg.spill = 8;
 	cfg.icu_output_buf = NULL;
 	cfg.buffer_length = 0;
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE;
 
 	cmp_size = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(0, cmp_size);
@@ -2592,6 +2613,7 @@ void test_compress_imagette_error_cases(void)
 	cfg.spill = 8;
 	cfg.icu_output_buf = (uint32_t *)output_buf;
 	cfg.buffer_length = 4;
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE;
 
 	cmp_size = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(CMP_ERROR_SMALL_BUF, cmp_size);
@@ -2605,6 +2627,7 @@ void test_compress_imagette_error_cases(void)
 	cfg.spill = 8;
 	cfg.icu_output_buf = (uint32_t *)output_buf;
 	cfg.buffer_length = 1;
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE;
 
 	cmp_size = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(CMP_ERROR_SMALL_BUF, cmp_size);
@@ -2618,6 +2641,7 @@ void test_compress_imagette_error_cases(void)
 	cfg.spill = 8;
 	cfg.icu_output_buf = (uint32_t *)output_buf;
 	cfg.buffer_length = 4;
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE;
 	cmp_size = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_size);
 
@@ -2626,9 +2650,10 @@ void test_compress_imagette_error_cases(void)
 	TEST_ASSERT_EQUAL_INT(-1, cmp_size);
 
 	/* error in setup */
-	my_max_used_bits = cmp_get_max_used_bits();
+	my_max_used_bits = MAX_USED_BITS_SAFE;
 	my_max_used_bits.nc_imagette = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	error = cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+	TEST_ASSERT_TRUE(error);
 	cfg.data_type = DATA_TYPE_IMAGETTE;
 	cfg.cmp_mode = CMP_MODE_DIFF_ZERO;
 	cfg.input_buf = data;
@@ -2637,6 +2662,7 @@ void test_compress_imagette_error_cases(void)
 	cfg.spill = 8;
 	cfg.icu_output_buf = (uint32_t *)output_buf;
 	cfg.buffer_length = 4;
+	cfg.max_used_bits = &my_max_used_bits;
 
 	cmp_size = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_size);
@@ -2800,6 +2826,7 @@ void test_compress_s_fx_staff(void)
 	TEST_ASSERT_NOT_NULL(cfg.icu_output_buf);
 	cfg.cmp_par_exp_flags = 2;
 	cfg.cmp_par_fx = 21;
+	cfg.max_used_bits = &MAX_USED_BITS_V1;
 
 	/* generate input data */
 	hdr = cfg.input_buf;
@@ -2900,10 +2927,10 @@ void test_compress_s_fx_model_multi(void)
 	model[5].fx = 0x001FFFFF;
 	memcpy(hdr->entry, model, sizeof(model));
 
-	my_max_used_bits = cmp_get_max_used_bits();
+	my_max_used_bits = MAX_USED_BITS_SAFE;
 	my_max_used_bits.s_exp_flags = 2;
 	my_max_used_bits.s_fx = 21;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 
 	cmp_size = icu_compress_data(&cfg);
 
@@ -2951,13 +2978,9 @@ void test_compress_s_fx_error_cases(void)
 	uint32_t spillover_fx = 8;
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct s_fx)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct s_fx)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct s_fx *data_p = (struct s_fx *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
-	my_max_used_bits.s_exp_flags = 2;
-	my_max_used_bits.s_fx = 21;
-	cmp_set_max_used_bits(&my_max_used_bits);
-
 	cfg = cmp_cfg_icu_create(DATA_TYPE_S_FX, CMP_MODE_DIFF_ZERO, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
 
@@ -2972,6 +2995,11 @@ void test_compress_s_fx_error_cases(void)
 						   NULL, (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
 
+	my_max_used_bits.s_exp_flags = 2;
+	my_max_used_bits.s_fx = 21;
+	error = cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+	TEST_ASSERT_FALSE(error);
+
 	/* test if data are higher than max used bits value */
 	data_p[0].fx = 0x200000; /* has more than 21 bits (my_max_used_bits.s_fx) */
 	cmp_bits = icu_compress_data(&cfg);
@@ -2980,19 +3008,18 @@ void test_compress_s_fx_error_cases(void)
 	/* compressed data are to small for the compressed_data buffer */
 	my_max_used_bits.s_exp_flags = 8;
 	my_max_used_bits.s_fx = 32;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	error = cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+	TEST_ASSERT_FALSE(error);
 	memset(data_to_compress, 0xff, sizeof(data_to_compress));
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(CMP_ERROR_SMALL_BUF, cmp_bits);
 
 	my_max_used_bits.s_exp_flags = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.s_exp_flags = 32;
 	my_max_used_bits.s_fx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -3014,14 +3041,9 @@ void test_compress_s_fx_efx_error_cases(void)
 	uint32_t spillover_efx = cmp_icu_max_spill(MAX_NON_IMA_GOLOMB_PAR);
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+2*sizeof(struct s_fx_efx)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct s_fx_efx)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct s_fx_efx *data_p = (struct s_fx_efx *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
-	my_max_used_bits.s_exp_flags = 2;
-	my_max_used_bits.s_fx = 21;
-	my_max_used_bits.s_efx = 16;
-	cmp_set_max_used_bits(&my_max_used_bits);
-
 	cfg = cmp_cfg_icu_create(DATA_TYPE_S_FX_EFX, CMP_MODE_DIFF_MULTI, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
 
@@ -3036,6 +3058,12 @@ void test_compress_s_fx_efx_error_cases(void)
 						   NULL, (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
 
+	my_max_used_bits.s_exp_flags = 2;
+	my_max_used_bits.s_fx = 21;
+	my_max_used_bits.s_efx = 16;
+	error = cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+	TEST_ASSERT_FALSE(error);
+
 	/* test if data are higher than max used bits value */
 	data_p[0].exp_flags = 0x4; /* has more than 2 bits (my_max_used_bits.s_exp_flags) */
 	cmp_bits = icu_compress_data(&cfg);
@@ -3053,21 +3081,21 @@ void test_compress_s_fx_efx_error_cases(void)
 
 	/* error case exp_flag setup */
 	my_max_used_bits.s_exp_flags = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	/* error case fx setup */
 	my_max_used_bits.s_exp_flags = 2;
 	my_max_used_bits.s_fx = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	/* error case efx setup */
 	my_max_used_bits.s_fx = 21;
 	my_max_used_bits.s_efx = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -3090,14 +3118,13 @@ void test_compress_s_fx_ncob_error_cases(void)
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct s_fx_ncob)] = {0};
 	uint8_t model_data[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct s_fx_ncob)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct s_fx_ncob)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct s_fx_ncob *data_p = (struct s_fx_ncob *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
 
 	my_max_used_bits.s_exp_flags = 2;
 	my_max_used_bits.s_fx = 21;
 	my_max_used_bits.s_ncob = 31;
-	cmp_set_max_used_bits(&my_max_used_bits);
 
 	cfg = cmp_cfg_icu_create(DATA_TYPE_S_FX_NCOB, CMP_MODE_MODEL_ZERO, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
@@ -3108,6 +3135,9 @@ void test_compress_s_fx_ncob_error_cases(void)
 			       CMP_PAR_UNUSED, CMP_PAR_UNUSED, CMP_PAR_UNUSED);
 	TEST_ASSERT_FALSE(error);
 
+	error = cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+	TEST_ASSERT_FALSE(error);
+
 	compressed_data_size = cmp_cfg_icu_buffers(&cfg, data_to_compress, 3, model_data,
 						   NULL, (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
@@ -3134,21 +3164,21 @@ void test_compress_s_fx_ncob_error_cases(void)
 
 	/* error case exp_flag setup */
 	my_max_used_bits.s_exp_flags = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	/* error case fx setup */
 	my_max_used_bits.s_exp_flags = 2;
 	my_max_used_bits.s_fx = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	/* error case efx setup */
 	my_max_used_bits.s_fx = 21;
 	my_max_used_bits.s_ncob = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -3175,17 +3205,10 @@ void test_compress_s_fx_efx_ncob_ecob_error_cases(void)
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct s_fx_efx_ncob_ecob)] = {0};
 	uint8_t model_data[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct s_fx_efx_ncob_ecob)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct s_fx_efx_ncob_ecob)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct s_fx_efx_ncob_ecob *data_p = (struct s_fx_efx_ncob_ecob *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
 
-	my_max_used_bits.s_exp_flags = 2;
-	my_max_used_bits.s_fx = 21;
-	my_max_used_bits.s_ncob = 31;
-	my_max_used_bits.s_efx = 23;
-	my_max_used_bits.s_ecob = 7;
-	cmp_set_max_used_bits(&my_max_used_bits);
-
 	cfg = cmp_cfg_icu_create(DATA_TYPE_S_FX_EFX_NCOB_ECOB, CMP_MODE_MODEL_ZERO, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
 
@@ -3200,6 +3223,14 @@ void test_compress_s_fx_efx_ncob_ecob_error_cases(void)
 						   NULL, (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
 
+	my_max_used_bits.s_exp_flags = 2;
+	my_max_used_bits.s_fx = 21;
+	my_max_used_bits.s_ncob = 31;
+	my_max_used_bits.s_efx = 23;
+	my_max_used_bits.s_ecob = 7;
+	error = cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+	TEST_ASSERT_FALSE(error);
+
 	/* the compressed_data buffer is to small */
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(CMP_ERROR_SMALL_BUF, cmp_bits);
@@ -3237,33 +3268,33 @@ void test_compress_s_fx_efx_ncob_ecob_error_cases(void)
 
 	/* error case exp_flag setup */
 	my_max_used_bits.s_exp_flags = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	/* error case fx setup */
 	my_max_used_bits.s_exp_flags = 32;
 	my_max_used_bits.s_fx = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	/* error case efx setup */
 	my_max_used_bits.s_fx = 32;
 	my_max_used_bits.s_ncob = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.s_ncob = 32;
 	my_max_used_bits.s_efx = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.s_efx = 32;
 	my_max_used_bits.s_ecob = 33;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 	my_max_used_bits.s_ecob = 32;
@@ -3282,10 +3313,10 @@ void test_compress_f_fx_error_cases(void)
 	uint32_t spillover_fx = 8;
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct f_fx)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct f_fx)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 
 	my_max_used_bits.f_fx = 23;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 
 	cfg = cmp_cfg_icu_create(DATA_TYPE_F_FX, CMP_MODE_DIFF_ZERO, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
@@ -3305,7 +3336,7 @@ void test_compress_f_fx_error_cases(void)
 	TEST_ASSERT_EQUAL_INT(CMP_ERROR_SMALL_BUF, cmp_bits);
 
 	my_max_used_bits.f_fx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -3325,12 +3356,12 @@ void test_compress_f_fx_efx_error_cases(void)
 	uint32_t spillover_efx = 8;
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+2*sizeof(struct f_fx_efx)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct f_fx_efx)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct f_fx_efx *data_p = (struct f_fx_efx *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
 	my_max_used_bits.f_fx = 23;
 	my_max_used_bits.f_efx = 31;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 
 	cfg = cmp_cfg_icu_create(DATA_TYPE_F_FX_EFX, CMP_MODE_DIFF_ZERO, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
@@ -3354,19 +3385,19 @@ void test_compress_f_fx_efx_error_cases(void)
 
 	/* efx value is to big for the max used bits values */
 	data_p[0].efx = 0x80000000;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(CMP_ERROR_HIGH_VALUE, cmp_bits);
 	data_p[0].efx = 0x7FFFFFFF;
 
 	my_max_used_bits.f_fx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.f_fx = 32;
 	my_max_used_bits.f_efx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -3386,12 +3417,12 @@ void test_compress_f_fx_ncob_error_cases(void)
 	uint32_t spillover_ncob = 8;
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+2*sizeof(struct f_fx_ncob)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct f_fx_ncob)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct f_fx_ncob *data_p = (struct f_fx_ncob *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
 	my_max_used_bits.f_fx = 31;
 	my_max_used_bits.f_ncob = 23;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 
 	cfg = cmp_cfg_icu_create(DATA_TYPE_F_FX_NCOB, CMP_MODE_DIFF_ZERO, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
@@ -3413,24 +3444,24 @@ void test_compress_f_fx_ncob_error_cases(void)
 
 	/* value is to big for the max used bits values */
 	data_p[0].ncob_x = 0x800000;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(CMP_ERROR_HIGH_VALUE, cmp_bits);
 	data_p[0].ncob_x = 0x7FFFFF;
 	data_p[0].ncob_y = 0x800000;
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(CMP_ERROR_HIGH_VALUE, cmp_bits);
 	data_p[0].ncob_y = 0x7FFFFF;
 
 	my_max_used_bits.f_fx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.f_fx = 32;
 	my_max_used_bits.f_ncob = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -3454,15 +3485,9 @@ void test_compress_f_fx_efx_ncob_ecob(void)
 	uint32_t spillover_ecob = 55;
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+4*sizeof(struct f_fx_efx_ncob_ecob)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct f_fx_efx_ncob_ecob)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct f_fx_efx_ncob_ecob *data_p = (struct f_fx_efx_ncob_ecob *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
-	my_max_used_bits.f_fx = 31;
-	my_max_used_bits.f_ncob = 3;
-	my_max_used_bits.f_efx = 16;
-	my_max_used_bits.f_ecob = 8;
-	cmp_set_max_used_bits(&my_max_used_bits);
-
 	cfg = cmp_cfg_icu_create(DATA_TYPE_F_FX_EFX_NCOB_ECOB, CMP_MODE_DIFF_ZERO, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
 
@@ -3476,6 +3501,12 @@ void test_compress_f_fx_efx_ncob_ecob(void)
 						   (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
 
+	my_max_used_bits.f_fx = 31;
+	my_max_used_bits.f_ncob = 3;
+	my_max_used_bits.f_efx = 16;
+	my_max_used_bits.f_ecob = 8;
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+
 	/* value is to big for the max used bits values */
 	data_p[3].fx = 0x80000000;
 	cmp_bits = icu_compress_data(&cfg);
@@ -3508,25 +3539,25 @@ void test_compress_f_fx_efx_ncob_ecob(void)
 	data_p[3].ecob_y = 0x100-1;
 
 	my_max_used_bits.f_fx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.f_fx = 32;
 	my_max_used_bits.f_ncob = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.f_ncob = 32;
 	my_max_used_bits.f_efx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.f_efx = 32;
 	my_max_used_bits.f_ecob = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -3548,15 +3579,9 @@ void test_compress_l_fx_error_cases(void)
 	uint32_t spillover_fx_cob_variance = 8;
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct l_fx)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct l_fx)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct l_fx *data_p = (struct l_fx *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
-	my_max_used_bits.l_exp_flags = 23;
-	my_max_used_bits.l_fx = 31;
-	my_max_used_bits.l_efx = 1;
-	my_max_used_bits.l_fx_variance = 23;
-	cmp_set_max_used_bits(&my_max_used_bits);
-
 	cfg = cmp_cfg_icu_create(DATA_TYPE_L_FX, CMP_MODE_DIFF_ZERO, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
 
@@ -3570,6 +3595,12 @@ void test_compress_l_fx_error_cases(void)
 						   (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
 
+	my_max_used_bits.l_exp_flags = 23;
+	my_max_used_bits.l_fx = 31;
+	my_max_used_bits.l_efx = 1;
+	my_max_used_bits.l_fx_variance = 23;
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+
 	/* value is to big for the max used bits values */
 	data_p[2].exp_flags = 0x800000;
 	cmp_bits = icu_compress_data(&cfg);
@@ -3588,19 +3619,19 @@ void test_compress_l_fx_error_cases(void)
 	data_p[0].fx_variance = 0x800000-1;
 
 	my_max_used_bits.l_exp_flags = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_exp_flags = 32;
 	my_max_used_bits.l_fx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_fx = 32;
 	my_max_used_bits.l_fx_variance = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -3624,15 +3655,9 @@ void test_compress_l_fx_efx_error_cases(void)
 	uint32_t spillover_fx_cob_variance = 8;
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct l_fx_efx)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct l_fx_efx)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct l_fx_efx *data_p = (struct l_fx_efx *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
-	my_max_used_bits.l_exp_flags = 23;
-	my_max_used_bits.l_fx = 31;
-	my_max_used_bits.l_efx = 1;
-	my_max_used_bits.l_fx_variance = 23;
-	cmp_set_max_used_bits(&my_max_used_bits);
-
 	cfg = cmp_cfg_icu_create(DATA_TYPE_L_FX_EFX, CMP_MODE_DIFF_ZERO, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
 
@@ -3646,6 +3671,12 @@ void test_compress_l_fx_efx_error_cases(void)
 						   (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
 
+	my_max_used_bits.l_exp_flags = 23;
+	my_max_used_bits.l_fx = 31;
+	my_max_used_bits.l_efx = 1;
+	my_max_used_bits.l_fx_variance = 23;
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+
 	/* value is to big for the max used bits values */
 	data_p[2].exp_flags = 0x800000;
 	cmp_bits = icu_compress_data(&cfg);
@@ -3669,25 +3700,25 @@ void test_compress_l_fx_efx_error_cases(void)
 	data_p[0].fx_variance = 0x800000-1;
 
 	my_max_used_bits.l_exp_flags = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_exp_flags = 32;
 	my_max_used_bits.l_fx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_fx = 32;
 	my_max_used_bits.l_efx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_efx = 32;
 	my_max_used_bits.l_fx_variance = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -3711,16 +3742,9 @@ void test_compress_l_fx_ncob_error_cases(void)
 	uint32_t spillover_fx_cob_variance = 8;
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct l_fx_ncob)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct l_fx_ncob)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct l_fx_ncob *data_p = (struct l_fx_ncob *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
-	my_max_used_bits.l_exp_flags = 23;
-	my_max_used_bits.l_fx = 31;
-	my_max_used_bits.l_ncob = 2;
-	my_max_used_bits.l_fx_variance = 23;
-	my_max_used_bits.l_cob_variance = 11;
-	cmp_set_max_used_bits(&my_max_used_bits);
-
 	cfg = cmp_cfg_icu_create(DATA_TYPE_L_FX_NCOB, CMP_MODE_DIFF_ZERO, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
 
@@ -3734,6 +3758,13 @@ void test_compress_l_fx_ncob_error_cases(void)
 						   (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
 
+	my_max_used_bits.l_exp_flags = 23;
+	my_max_used_bits.l_fx = 31;
+	my_max_used_bits.l_ncob = 2;
+	my_max_used_bits.l_fx_variance = 23;
+	my_max_used_bits.l_cob_variance = 11;
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+
 	/* value is to big for the max used bits values */
 	data_p[2].exp_flags = 0x800000;
 	cmp_bits = icu_compress_data(&cfg);
@@ -3772,31 +3803,31 @@ void test_compress_l_fx_ncob_error_cases(void)
 	data_p[2].cob_y_variance = 0x800-1;
 
 	my_max_used_bits.l_exp_flags = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_exp_flags = 32;
 	my_max_used_bits.l_fx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_fx = 32;
 	my_max_used_bits.l_ncob = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_ncob = 32;
 	my_max_used_bits.l_fx_variance = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_fx_variance = 32;
 	my_max_used_bits.l_cob_variance = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -3824,18 +3855,9 @@ void test_compress_l_fx_efx_ncob_ecob_error_cases(void)
 	uint32_t spillover_fx_cob_variance = 8;
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct l_fx_efx_ncob_ecob)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct l_fx_efx_ncob_ecob)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct l_fx_efx_ncob_ecob *data_p = (struct l_fx_efx_ncob_ecob *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
-	my_max_used_bits.l_exp_flags = 23;
-	my_max_used_bits.l_fx = 31;
-	my_max_used_bits.l_ncob = 2;
-	my_max_used_bits.l_efx = 1;
-	my_max_used_bits.l_ecob = 3;
-	my_max_used_bits.l_fx_variance = 23;
-	my_max_used_bits.l_cob_variance = 11;
-	cmp_set_max_used_bits(&my_max_used_bits);
-
 	cfg = cmp_cfg_icu_create(DATA_TYPE_L_FX_EFX_NCOB_ECOB, CMP_MODE_DIFF_ZERO, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
 
@@ -3849,6 +3871,15 @@ void test_compress_l_fx_efx_ncob_ecob_error_cases(void)
 						   (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
 
+	my_max_used_bits.l_exp_flags = 23;
+	my_max_used_bits.l_fx = 31;
+	my_max_used_bits.l_ncob = 2;
+	my_max_used_bits.l_efx = 1;
+	my_max_used_bits.l_ecob = 3;
+	my_max_used_bits.l_fx_variance = 23;
+	my_max_used_bits.l_cob_variance = 11;
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+
 	/* value is to big for the max used bits values */
 	data_p[2].exp_flags = 0x800000;
 	cmp_bits = icu_compress_data(&cfg);
@@ -3902,43 +3933,43 @@ void test_compress_l_fx_efx_ncob_ecob_error_cases(void)
 	data_p[2].cob_y_variance = 0x800-1;
 
 	my_max_used_bits.l_exp_flags = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_exp_flags = 32;
 	my_max_used_bits.l_fx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_fx = 32;
 	my_max_used_bits.l_ncob = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_ncob = 32;
 	my_max_used_bits.l_efx = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_efx = 32;
 	my_max_used_bits.l_ecob = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_ecob = 32;
 	my_max_used_bits.l_fx_variance = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.l_fx_variance = 32;
 	my_max_used_bits.l_cob_variance = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -3958,13 +3989,9 @@ void test_compress_nc_offset_error_cases(void)
 	uint32_t spillover_variance = cmp_icu_max_spill(MAX_NON_IMA_GOLOMB_PAR);
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct nc_offset)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct nc_offset)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct nc_offset *data_p = (struct nc_offset *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
-	my_max_used_bits.nc_offset_mean = 1;
-	my_max_used_bits.nc_offset_variance = 31;
-	cmp_set_max_used_bits(&my_max_used_bits);
-
 	cfg = cmp_cfg_icu_create(DATA_TYPE_OFFSET, CMP_MODE_DIFF_MULTI, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
 
@@ -3977,6 +4004,10 @@ void test_compress_nc_offset_error_cases(void)
 						   (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
 
+	my_max_used_bits.nc_offset_mean = 1;
+	my_max_used_bits.nc_offset_variance = 31;
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+
 	/* value is to big for the max used bits values */
 	data_p[0].mean = 0x2;
 	cmp_bits = icu_compress_data(&cfg);
@@ -3990,13 +4021,13 @@ void test_compress_nc_offset_error_cases(void)
 	data_p[1].variance = 0x80000000-1;
 
 	my_max_used_bits.nc_offset_mean = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.nc_offset_mean = 32;
 	my_max_used_bits.nc_offset_variance = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -4018,14 +4049,9 @@ void test_compress_nc_background_error_cases(void)
 	uint32_t spillover_pixels_error = 42;
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct nc_background)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct nc_background)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct nc_background *data_p = (struct nc_background *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
-	my_max_used_bits.nc_background_mean = 1;
-	my_max_used_bits.nc_background_variance = 31;
-	my_max_used_bits.nc_background_outlier_pixels = 2;
-	cmp_set_max_used_bits(&my_max_used_bits);
-
 	cfg = cmp_cfg_icu_create(DATA_TYPE_BACKGROUND, CMP_MODE_DIFF_MULTI, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
 
@@ -4038,6 +4064,11 @@ void test_compress_nc_background_error_cases(void)
 						   (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
 
+	my_max_used_bits.nc_background_mean = 1;
+	my_max_used_bits.nc_background_variance = 31;
+	my_max_used_bits.nc_background_outlier_pixels = 2;
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+
 	/* value is to big for the max used bits values */
 	data_p[0].mean = 0x2;
 	cmp_bits = icu_compress_data(&cfg);
@@ -4056,19 +4087,19 @@ void test_compress_nc_background_error_cases(void)
 	data_p[1].outlier_pixels = 0x3;
 
 	my_max_used_bits.nc_background_mean = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.nc_background_mean = 32;
 	my_max_used_bits.nc_background_variance = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.nc_background_variance = 32;
 	my_max_used_bits.nc_background_outlier_pixels = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
@@ -4090,14 +4121,9 @@ void test_compress_smearing_error_cases(void)
 	uint32_t spillover_pixels_error = 42;
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE+3*sizeof(struct smearing)] = {0};
 	uint8_t compressed_data[MULTI_ENTRY_HDR_SIZE+1*sizeof(struct smearing)] = {0};
-	struct cmp_max_used_bits my_max_used_bits = {0};
+	struct cmp_max_used_bits my_max_used_bits = MAX_USED_BITS_SAFE;
 	struct smearing *data_p = (struct smearing *)&data_to_compress[MULTI_ENTRY_HDR_SIZE];
 
-	my_max_used_bits.smearing_mean = 1;
-	my_max_used_bits.smearing_variance_mean = 15;
-	my_max_used_bits.smearing_outlier_pixels = 2;
-	cmp_set_max_used_bits(&my_max_used_bits);
-
 	cfg = cmp_cfg_icu_create(DATA_TYPE_SMEARING, CMP_MODE_DIFF_MULTI, 0, CMP_LOSSLESS);
 	TEST_ASSERT(cfg.data_type != DATA_TYPE_UNKNOWN);
 
@@ -4110,6 +4136,11 @@ void test_compress_smearing_error_cases(void)
 						   (uint32_t *)compressed_data, 1);
 	TEST_ASSERT_EQUAL_INT(sizeof(compressed_data), compressed_data_size);
 
+	my_max_used_bits.smearing_mean = 1;
+	my_max_used_bits.smearing_variance_mean = 15;
+	my_max_used_bits.smearing_outlier_pixels = 2;
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
+
 	/* value is to big for the max used bits values */
 	data_p[0].mean = 0x2;
 	cmp_bits = icu_compress_data(&cfg);
@@ -4128,19 +4159,19 @@ void test_compress_smearing_error_cases(void)
 	data_p[1].outlier_pixels = 0x3;
 
 	my_max_used_bits.smearing_mean = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.smearing_mean = 32;
 	my_max_used_bits.smearing_variance_mean = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 
 	my_max_used_bits.smearing_variance_mean = 32;
 	my_max_used_bits.smearing_outlier_pixels = 33; /* more than 32 bits are not allowed */
-	cmp_set_max_used_bits(&my_max_used_bits);
+	cmp_cfg_icu_max_used_bits(&cfg, &my_max_used_bits);
 	cmp_bits = icu_compress_data(&cfg);
 	TEST_ASSERT_EQUAL_INT(-1, cmp_bits);
 }
diff --git a/test/cmp_icu/test_decmp.c b/test/cmp_icu/test_decmp.c
index b00c09c..599f50a 100644
--- a/test/cmp_icu/test_decmp.c
+++ b/test/cmp_icu/test_decmp.c
@@ -392,6 +392,7 @@ void test_decompress_imagette_model(void)
 	cfg.model_value = 16;
 	cfg.golomb_par = 4;
 	cfg.spill = 48;
+	cfg.max_used_bits = &MAX_USED_BITS_SAFE;
 
 	stream_pos = decompress_imagette(&cfg);
 	TEST_ASSERT_EQUAL_INT(15, stream_pos);
@@ -417,7 +418,7 @@ void test_cmp_decmp_s_fx_diff(void)
 	int err;
 
 	struct cmp_entity *ent;
-	const uint32_t MAX_VALUE = ~(~0U << MAX_USED_S_FX_BITS);
+	const uint32_t MAX_VALUE = ~(~0U << MAX_USED_BITS_V1.s_fx);
 	struct s_fx data_entry[DATA_SAMPLES] = {
 		{0, 0}, {1, 23}, {2, 42}, {3, MAX_VALUE}, {3, MAX_VALUE>>1} };
 	uint8_t data_to_compress[MULTI_ENTRY_HDR_SIZE + sizeof(data_entry)];
@@ -599,6 +600,9 @@ void test_imagette_random(void)
 	error = cmp_cfg_icu_imagette(&cfg, golomb_par, spill);
 	TEST_ASSERT_FALSE(error);
 
+	error = cmp_cfg_icu_max_used_bits(&cfg, &MAX_USED_BITS_V1);
+	TEST_ASSERT_FALSE(error);
+
 	/* print_cfg(&cfg, 0); */
 	s = icu_compress_data_entity(NULL, &cfg);
 	TEST_ASSERT_TRUE(s);
@@ -636,7 +640,7 @@ void test_s_fx_diff(void)
 {
 	size_t s, i;
 	uint8_t cmp_entity[88] = {
-		0x80, 0x00, 0x00, 0x09, 0x00, 0x00, 0x58, 0x00, 0x00, 0x20, 0x04, 0xEE, 0x21, 0xBD, 0xB0, 0x1C, 0x04, 0xEE, 0x21, 0xBD, 0xB0, 0x41, 0x00, 0x08, 0x02, 0x08, 0xD0, 0x10, 0x00, 0x00, 0x00, 0x00,
+		0x80, 0x00, 0x00, 0x09, 0x00, 0x00, 0x58, 0x00, 0x00, 0x20, 0x04, 0xEE, 0x21, 0xBD, 0xB0, 0x1C, 0x04, 0xEE, 0x21, 0xBD, 0xB0, 0x41, 0x00, 0x08, 0x02, 0x08, 0xD0, 0x10, 0x00, 0x01, 0x00, 0x00,
 		0x00, 0x00, 0x0A, 0x00, 0x01, 0x00, 0x00, 0x0A, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
 		0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0xAE, 0xDE, 0x00, 0x00, 0x00, 0x73, 0xFF, 0xFF, 0xF8, 0x00, 0x00, 0x00,
 	};
@@ -645,7 +649,7 @@ void test_s_fx_diff(void)
 	struct multi_entry_hdr *hdr = (struct multi_entry_hdr *)result_data;
 	struct s_fx *data = (struct s_fx *)hdr->entry;
 	/* put some dummy data in the header*/
-	for (i = 0; i < sizeof(*hdr); ++i)
+	for (i = 0; i < sizeof(*hdr); i++)
 		result_data[i] = i;
 	data[0].exp_flags = 0;
 	data[0].fx = 0;
@@ -673,7 +677,7 @@ void test_s_fx_model(void)
 {
 	size_t s, i;
 	uint8_t compressed_data_buf[92] = {
-		0x80, 0x00, 0x00, 0x09, 0x00, 0x00, 0x5C, 0x00, 0x00, 0x20, 0x04, 0xF0, 0xC2, 0xD3, 0x47, 0xE4, 0x04, 0xF0, 0xC2, 0xD3, 0x48, 0x16, 0x00, 0x08, 0x03, 0x08, 0xD0, 0x10, 0x01, 0x00, 0x00, 0x00,
+		0x80, 0x00, 0x00, 0x09, 0x00, 0x00, 0x5C, 0x00, 0x00, 0x20, 0x04, 0xF0, 0xC2, 0xD3, 0x47, 0xE4, 0x04, 0xF0, 0xC2, 0xD3, 0x48, 0x16, 0x00, 0x08, 0x03, 0x08, 0xD0, 0x10, 0x01, 0x01, 0x00, 0x00,
 		0x00, 0x00, 0x0A, 0x00, 0x01, 0x00, 0x00, 0x0A, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
 		0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x3B, 0xFF, 0xFF, 0xEF, 0xFF, 0xFF, 0x5B, 0xFF, 0xFF, 0xEF, 0xFF, 0xFF, 0x5D, 0x80, 0x00, 0x00,
 	};
@@ -749,18 +753,17 @@ void test_random_compression_decompression(void)
 	struct cmp_entity *cmp_ent;
 	void *decompressed_data;
 	void *decompressed_up_model = NULL;
+	int error;
 
-	srand(0); /* TODO:XXX*/
 	puts("--------------------------------------------------------------");
 
 	/* for (cfg.data_type = DATA_TYPE_IMAGETTE; TODO:!! implement this */
 	/*      cfg.data_type < DATA_TYPE_F_CAM_BACKGROUND+1; cfg.data_type++) { */
 	for (cfg.data_type = DATA_TYPE_IMAGETTE;
 	     cfg.data_type < DATA_TYPE_F_CAM_IMAGETTE_ADAPTIVE+1; cfg.data_type++) {
+		error = cmp_cfg_icu_max_used_bits(&cfg, &MAX_USED_BITS_V1);
+		TEST_ASSERT_FALSE(error);
 		cfg.samples = my_random(1, 0x30000);
-			if (cfg.data_type == DATA_TYPE_OFFSET)
-				puts("FADF");
-
 		cfg.buffer_length = (CMP_ENTITY_MAX_SIZE - NON_IMAGETTE_HEADER_SIZE - MULTI_ENTRY_HDR_SIZE)/size_of_a_sample(cfg.data_type);;
 		s = cmp_cal_size_of_data(cfg.samples, cfg.data_type);
 		printf("%s\n", data_type2string(cfg.data_type));
@@ -856,6 +859,613 @@ void test_random_compression_decompression(void)
 	}
 }
 
+
+/**
+ * @test cmp_ent_write_cmp_pars
+ * @test cmp_ent_read_header
+ */
+
+void test_cmp_ent_write_cmp_pars(void)
+{
+	int error;
+	struct cmp_entity *ent;
+	struct cmp_cfg cfg = {0}, cfg_read = {0};
+	int cmp_size_bits;
+	uint32_t size;
+	struct cmp_max_used_bits max_used_bits = MAX_USED_BITS_SAFE;
+
+	/* set up max used bit version */
+	max_used_bits.version = 42;
+	cmp_max_used_bits_list_add(&max_used_bits);
+
+	cmp_size_bits = 93;
+	/** RAW mode test **/
+	/* create imagette raw mode configuration */
+	cfg.data_type = DATA_TYPE_IMAGETTE;
+	cfg.cmp_mode = CMP_MODE_RAW;
+	cfg.model_value = 11;
+	cfg.round = 2;
+	cfg.samples = 9;
+	cfg.max_used_bits = cmp_max_used_bits_list_get(42);
+
+	/* create a compression entity */
+	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
+	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_FALSE(error);
+
+	TEST_ASSERT_EQUAL_INT(cfg.data_type, cmp_ent_get_data_type(ent));
+	TEST_ASSERT_EQUAL_INT(1, cmp_ent_get_data_type_raw_bit(ent));
+	TEST_ASSERT_EQUAL_INT(12, cmp_ent_get_cmp_data_size(ent));
+
+	TEST_ASSERT_EQUAL_INT(cmp_cal_size_of_data(cfg.samples, cfg.data_type), cmp_ent_get_original_size(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_mode, cmp_ent_get_cmp_mode(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.model_value, cmp_ent_get_model_value(ent));
+	TEST_ASSERT_EQUAL_INT(max_used_bits.version, cmp_ent_get_max_used_bits_version(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.round, cmp_ent_get_lossy_cmp_par(ent));
+
+	error = cmp_ent_read_header(ent, &cfg_read);
+	TEST_ASSERT_FALSE(error);
+	cfg.icu_output_buf = cmp_ent_get_data_buf(ent); /* quick fix that both cfg are equal */
+	cfg.buffer_length = 12; /* quick fix that both cfg are equal */
+	TEST_ASSERT_EQUAL_MEMORY(&cfg, &cfg_read, sizeof(struct cmp_cfg));
+
+	free(ent);
+	memset(&cfg, 0, sizeof(struct cmp_cfg));
+	memset(&cfg_read, 0, sizeof(struct cmp_cfg));
+
+	/** imagette test **/
+	/* create imagette mode configuration */
+	cfg.data_type = DATA_TYPE_IMAGETTE;
+	cfg.cmp_mode = CMP_MODE_MODEL_ZERO;
+	cfg.model_value = 11;
+	cfg.round = 2;
+	cfg.samples = 9;
+	cfg.spill = MIN_IMA_SPILL;
+	cfg.golomb_par = MAX_IMA_GOLOMB_PAR;
+	cfg.max_used_bits = cmp_max_used_bits_list_get(42);
+
+	/* create a compression entity */
+	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
+	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_FALSE(error);
+
+	TEST_ASSERT_EQUAL_INT(cfg.data_type, cmp_ent_get_data_type(ent));
+	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_data_type_raw_bit(ent));
+	TEST_ASSERT_EQUAL_INT(12, cmp_ent_get_cmp_data_size(ent));
+
+	TEST_ASSERT_EQUAL_INT(cmp_cal_size_of_data(cfg.samples, cfg.data_type), cmp_ent_get_original_size(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_mode, cmp_ent_get_cmp_mode(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.model_value, cmp_ent_get_model_value(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.max_used_bits->version, cmp_ent_get_max_used_bits_version(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.round, cmp_ent_get_lossy_cmp_par(ent));
+
+	TEST_ASSERT_EQUAL_INT(cfg.spill, cmp_ent_get_ima_spill(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.golomb_par, cmp_ent_get_ima_golomb_par(ent));
+
+	error = cmp_ent_read_header(ent, &cfg_read);
+	TEST_ASSERT_FALSE(error);
+	cfg.icu_output_buf = cmp_ent_get_data_buf(ent); /* quick fix that both cfg are equal */
+	cfg.buffer_length = 12; /* quick fix that both cfg are equal */
+	TEST_ASSERT_EQUAL_MEMORY(&cfg, &cfg_read, sizeof(struct cmp_cfg));
+
+	free(ent);
+	memset(&cfg, 0, sizeof(struct cmp_cfg));
+	memset(&cfg_read, 0, sizeof(struct cmp_cfg));
+
+	/** adaptive imagette test **/
+	/* create a configuration */
+	cfg.data_type = DATA_TYPE_IMAGETTE_ADAPTIVE;
+	cfg.cmp_mode = CMP_MODE_MODEL_ZERO;
+	cfg.model_value = 11;
+	cfg.round = 2;
+	cfg.samples = 9;
+	cfg.spill = MIN_IMA_SPILL;
+	cfg.golomb_par = MAX_IMA_GOLOMB_PAR;
+	cfg.ap1_spill = 555;
+	cfg.ap1_golomb_par = 14;
+	cfg.ap2_spill = 333;
+	cfg.ap2_golomb_par = 43;
+	cfg.max_used_bits = cmp_max_used_bits_list_get(42);
+
+	/* create a compression entity */
+	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
+	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_FALSE(error);
+
+	TEST_ASSERT_EQUAL_INT(cfg.data_type, cmp_ent_get_data_type(ent));
+	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_data_type_raw_bit(ent));
+	TEST_ASSERT_EQUAL_INT(12, cmp_ent_get_cmp_data_size(ent));
+
+	TEST_ASSERT_EQUAL_INT(cmp_cal_size_of_data(cfg.samples, cfg.data_type), cmp_ent_get_original_size(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_mode, cmp_ent_get_cmp_mode(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.model_value, cmp_ent_get_model_value(ent));
+	TEST_ASSERT_EQUAL_INT(max_used_bits.version, cmp_ent_get_max_used_bits_version(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.round, cmp_ent_get_lossy_cmp_par(ent));
+
+	TEST_ASSERT_EQUAL_INT(cfg.spill, cmp_ent_get_ima_spill(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.golomb_par, cmp_ent_get_ima_golomb_par(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.ap1_spill, cmp_ent_get_ima_ap1_spill(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.ap1_golomb_par, cmp_ent_get_ima_ap1_golomb_par(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.ap2_spill, cmp_ent_get_ima_ap2_spill(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.ap2_golomb_par, cmp_ent_get_ima_ap2_golomb_par(ent));
+
+	error = cmp_ent_read_header(ent, &cfg_read);
+	TEST_ASSERT_FALSE(error);
+	cfg.icu_output_buf = cmp_ent_get_data_buf(ent); /* quick fix that both cfg are equal */
+	cfg.buffer_length = 12; /* quick fix that both cfg are equal */
+	TEST_ASSERT_EQUAL_MEMORY(&cfg, &cfg_read, sizeof(struct cmp_cfg));
+
+	free(ent);
+	memset(&cfg, 0, sizeof(struct cmp_cfg));
+	memset(&cfg_read, 0, sizeof(struct cmp_cfg));
+
+	/** flux cob data type test **/
+	/* create configuration */
+	cfg.data_type = DATA_TYPE_S_FX_EFX_NCOB_ECOB;
+	cfg.cmp_mode = CMP_MODE_MODEL_ZERO;
+	cfg.model_value = 11;
+	cfg.round = 2;
+	cfg.samples = 9;
+	cfg.spill_exp_flags = 1;
+	cfg.spill_fx = 2;
+	cfg.spill_ncob = 3;
+	cfg.spill_efx = 4;
+	cfg.spill_ecob = 5;
+	cfg.spill_fx_cob_variance = 6;
+	cfg.cmp_par_exp_flags = 7;
+	cfg.cmp_par_fx = 8;
+	cfg.cmp_par_ncob = 9;
+	cfg.cmp_par_efx = 10;
+	cfg.cmp_par_ecob = 11;
+	cfg.cmp_par_fx_cob_variance = 12;
+	cfg.max_used_bits = cmp_max_used_bits_list_get(42);
+
+	/* create a compression entity */
+	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
+	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_FALSE(error);
+
+	TEST_ASSERT_EQUAL_INT(cfg.data_type, cmp_ent_get_data_type(ent));
+	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_data_type_raw_bit(ent));
+	TEST_ASSERT_EQUAL_INT(12, cmp_ent_get_cmp_data_size(ent));
+
+	TEST_ASSERT_EQUAL_INT(cmp_cal_size_of_data(cfg.samples, cfg.data_type), cmp_ent_get_original_size(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_mode, cmp_ent_get_cmp_mode(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.model_value, cmp_ent_get_model_value(ent));
+	TEST_ASSERT_EQUAL_INT(max_used_bits.version, cmp_ent_get_max_used_bits_version(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.round, cmp_ent_get_lossy_cmp_par(ent));
+
+
+	TEST_ASSERT_EQUAL_INT(cfg.spill_exp_flags, cmp_ent_get_non_ima_spill1(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.spill_fx, cmp_ent_get_non_ima_spill2(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.spill_ncob, cmp_ent_get_non_ima_spill3(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.spill_efx, cmp_ent_get_non_ima_spill4(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.spill_ecob, cmp_ent_get_non_ima_spill5(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.spill_fx_cob_variance, cmp_ent_get_non_ima_spill6(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_exp_flags, cmp_ent_get_non_ima_cmp_par1(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_fx, cmp_ent_get_non_ima_cmp_par2(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_ncob, cmp_ent_get_non_ima_cmp_par3(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_efx, cmp_ent_get_non_ima_cmp_par4(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_ecob, cmp_ent_get_non_ima_cmp_par5(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_fx_cob_variance, cmp_ent_get_non_ima_cmp_par6(ent));
+
+	error = cmp_ent_read_header(ent, &cfg_read);
+	TEST_ASSERT_FALSE(error);
+	cfg.icu_output_buf = cmp_ent_get_data_buf(ent); /* quick fix that both cfg are equal */
+	cfg.buffer_length = 12; /* quick fix that both cfg are equal */
+	TEST_ASSERT_EQUAL_MEMORY(&cfg, &cfg_read, sizeof(struct cmp_cfg));
+
+	free(ent);
+	memset(&cfg, 0, sizeof(struct cmp_cfg));
+	memset(&cfg_read, 0, sizeof(struct cmp_cfg));
+
+	/** auxiliary data data_type test **/
+	/* create configuration */
+	cfg.data_type = DATA_TYPE_SMEARING;
+	cfg.cmp_mode = CMP_MODE_MODEL_ZERO;
+	cfg.model_value = 11;
+	cfg.round = 2;
+	cfg.samples = 9;
+	cfg.spill_mean = 1;
+	cfg.spill_variance = 2;
+	cfg.spill_pixels_error = 3;
+	cfg.cmp_par_mean = 7;
+	cfg.cmp_par_variance = 8;
+	cfg.cmp_par_pixels_error = 9;
+	cfg.max_used_bits = cmp_max_used_bits_list_get(42);
+
+	/* create a compression entity */
+	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
+	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_FALSE(error);
+
+	TEST_ASSERT_EQUAL_INT(cfg.data_type, cmp_ent_get_data_type(ent));
+	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_data_type_raw_bit(ent));
+	TEST_ASSERT_EQUAL_INT(12, cmp_ent_get_cmp_data_size(ent));
+
+	TEST_ASSERT_EQUAL_INT(cmp_cal_size_of_data(cfg.samples, cfg.data_type), cmp_ent_get_original_size(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_mode, cmp_ent_get_cmp_mode(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.model_value, cmp_ent_get_model_value(ent));
+	TEST_ASSERT_EQUAL_INT(max_used_bits.version, cmp_ent_get_max_used_bits_version(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.round, cmp_ent_get_lossy_cmp_par(ent));
+
+
+	TEST_ASSERT_EQUAL_INT(cfg.spill_mean, cmp_ent_get_non_ima_spill1(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.spill_variance, cmp_ent_get_non_ima_spill2(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.spill_pixels_error, cmp_ent_get_non_ima_spill3(ent));
+	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_spill4(ent));
+	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_spill5(ent));
+	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_spill6(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_mean, cmp_ent_get_non_ima_cmp_par1(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_variance, cmp_ent_get_non_ima_cmp_par2(ent));
+	TEST_ASSERT_EQUAL_INT(cfg.cmp_par_pixels_error, cmp_ent_get_non_ima_cmp_par3(ent));
+	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_cmp_par4(ent));
+	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_cmp_par5(ent));
+	TEST_ASSERT_EQUAL_INT(0, cmp_ent_get_non_ima_cmp_par6(ent));
+
+	error = cmp_ent_read_header(ent, &cfg_read);
+	TEST_ASSERT_FALSE(error);
+	cfg.icu_output_buf = cmp_ent_get_data_buf(ent); /* quick fix that both cfg are equal */
+	cfg.buffer_length = 12; /* quick fix that both cfg are equal */
+	TEST_ASSERT_EQUAL_MEMORY(&cfg, &cfg_read, sizeof(struct cmp_cfg));
+
+	free(ent);
+	memset(&cfg, 0, sizeof(struct cmp_cfg));
+	memset(&cfg_read, 0, sizeof(struct cmp_cfg));
+
+	/** Error Cases **/
+	/* create imagette raw mode configuration */
+	cfg.data_type = DATA_TYPE_IMAGETTE;
+	cfg.cmp_mode = CMP_MODE_MODEL_ZERO;
+	cfg.model_value = 11;
+	cfg.round = 2;
+	cfg.samples = 9;
+	cfg.max_used_bits = cmp_max_used_bits_list_get(42);
+
+	/* create a compression entity */
+	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
+	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+
+
+	/* ent = NULL */
+	error = cmp_ent_write_cmp_pars(NULL, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+
+	/* cfg = NULL */
+	error = cmp_ent_write_cmp_pars(ent, NULL, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+
+	/* cmp_size_bits negative */
+	error = cmp_ent_write_cmp_pars(ent, &cfg, -1);
+	TEST_ASSERT_TRUE(error);
+
+	/* data_type mismatch */
+	cfg.data_type = DATA_TYPE_S_FX;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.data_type = DATA_TYPE_IMAGETTE;
+
+	/* compressed data to big for compression entity */
+	error = cmp_ent_write_cmp_pars(ent, &cfg, 97);
+	TEST_ASSERT_TRUE(error);
+
+	/* original_size to high */
+	cfg.samples = 0x800000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.samples = 0x7FFFFF;
+
+	/* cmp_mode to high */
+	cfg.cmp_mode = 0x100;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.cmp_mode = 0xFF;
+
+	/* max model_value to high */
+	cfg.model_value = 0x100;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.model_value = 0xFF;
+
+	/*  max used bit version to high */
+	TEST_ASSERT_EQUAL_INT(1, sizeof(max_used_bits.version));
+
+	/* max lossy_cmp_par to high */
+	cfg.round = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.round = 0xFFFF;
+
+	/* The entity's raw data bit is not set, but the configuration contains raw data */
+	cfg.cmp_mode = CMP_MODE_RAW;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.cmp_mode = CMP_MODE_MODEL_MULTI;
+
+	/* The entity's raw data bit is set, but the configuration contains no raw data */
+	cmp_ent_set_data_type(ent, cfg.data_type, 1); /* set raw bit */
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cmp_ent_set_data_type(ent, cfg.data_type, 0);
+
+	/* spill to high */
+	cfg.spill = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.spill = 0xFFFF;
+
+	/* golomb_par to high */
+	cfg.golomb_par = 0x100;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.golomb_par = 0xFF;
+
+
+	cmp_ent_set_data_type(ent, DATA_TYPE_SAT_IMAGETTE_ADAPTIVE, 0);
+	cfg.data_type = DATA_TYPE_SAT_IMAGETTE_ADAPTIVE;
+	cmp_size_bits = 1;
+	/* adaptive 1 spill to high */
+	cfg.ap1_spill = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.ap1_spill = 0xFFFF;
+
+	/* adaptive 1  golomb_par to high */
+	cfg.ap1_golomb_par = 0x100;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.ap1_golomb_par = 0xFF;
+
+	/* adaptive 2 spill to high */
+	cfg.ap2_spill = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.ap2_spill = 0xFFFF;
+
+	/* adaptive 2  golomb_par to high */
+	cfg.ap2_golomb_par = 0x100;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.ap2_golomb_par = 0xFF;
+
+	cmp_ent_set_data_type(ent, DATA_TYPE_OFFSET, 0);
+	cfg.data_type = DATA_TYPE_OFFSET;
+
+	free(ent);
+
+	/* create a compression entity */
+	cfg.data_type = DATA_TYPE_OFFSET;
+	cfg.samples = 9;
+	size = cmp_ent_create(NULL, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
+	size = cmp_ent_create(ent, cfg.data_type, cfg.cmp_mode == CMP_MODE_RAW, 12);
+	TEST_ASSERT_NOT_EQUAL_INT(0, size);
+
+	/* mean cmp_par to high */
+	cfg.cmp_par_mean = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.cmp_par_mean = 0xFFFF;
+
+	/* mean spill to high */
+	cfg.spill_mean = 0x1000000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.spill_mean = 0xFFFFFF;
+
+	/* variance cmp_par to high */
+	cfg.cmp_par_variance = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.cmp_par_variance = 0xFFFF;
+
+	/* variance spill to high */
+	cfg.spill_variance = 0x1000000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.spill_variance = 0xFFFFFF;
+
+	/* pixels_error cmp_par to high */
+	cfg.cmp_par_pixels_error = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.cmp_par_pixels_error = 0xFFFF;
+
+	/* pixels_error spill to high */
+	cfg.spill_pixels_error = 0x1000000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.spill_pixels_error = 0xFFFFFF;
+
+
+	cmp_ent_set_data_type(ent, DATA_TYPE_F_FX_EFX_NCOB_ECOB, 0);
+	cfg.data_type = DATA_TYPE_F_FX_EFX_NCOB_ECOB;
+
+	/* exp_flags cmp_par to high */
+	cfg.cmp_par_exp_flags = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.cmp_par_exp_flags = 0xFFFF;
+
+	/* exp_flags spill to high */
+	cfg.spill_exp_flags = 0x1000000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.spill_exp_flags = 0xFFFFFF;
+
+	/* fx cmp_par to high */
+	cfg.cmp_par_fx = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.cmp_par_fx = 0xFFFF;
+
+	/* fx spill to high */
+	cfg.spill_fx = 0x1000000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.spill_fx = 0xFFFFFF;
+
+	/* ncob cmp_par to high */
+	cfg.cmp_par_ncob = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.cmp_par_ncob = 0xFFFF;
+
+	/* ncob spill to high */
+	cfg.spill_ncob = 0x1000000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.spill_ncob = 0xFFFFFF;
+
+	/* efx cmp_par to high */
+	cfg.cmp_par_efx = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.cmp_par_efx = 0xFFFF;
+
+	/* efx spill to high */
+	cfg.spill_efx = 0x1000000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.spill_efx = 0xFFFFFF;
+
+	/* ecob cmp_par to high */
+	cfg.cmp_par_ecob = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.cmp_par_ecob = 0xFFFF;
+
+	/* ecob spill to high */
+	cfg.spill_ecob = 0x1000000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.spill_ecob = 0xFFFFFF;
+
+	/* fx_cob_variance cmp_par to high */
+	cfg.cmp_par_fx_cob_variance = 0x10000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.cmp_par_fx_cob_variance = 0xFFFF;
+
+	/* fx_cob_variance spill to high */
+	cfg.spill_fx_cob_variance = 0x1000000;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	cfg.spill_fx_cob_variance = 0xFFFFFF;
+
+	/* test data type = DATA_TYPE_UNKNOWN */
+	cmp_ent_set_data_type(ent, DATA_TYPE_UNKNOWN, 0);
+	cfg.data_type = DATA_TYPE_UNKNOWN;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+
+	/* test data type = DATA_TYPE_F_CAM_BACKGROUND +1 */
+	cmp_ent_set_data_type(ent, DATA_TYPE_F_CAM_BACKGROUND + 1, 0);
+	cfg.data_type = DATA_TYPE_F_CAM_BACKGROUND + 1;
+	error = cmp_ent_write_cmp_pars(ent, &cfg, cmp_size_bits);
+	TEST_ASSERT_TRUE(error);
+	free(ent);
+	cmp_max_used_bits_list_empty();
+}
+
+
+/**
+ * @test cmp_ent_read_header
+ */
+
+void test_cmp_ent_read_header_error_cases(void)
+
+{
+	int error;
+	uint32_t size;
+	struct cmp_entity *ent;
+	struct cmp_cfg cfg;
+
+	/* create a entity */
+	size = cmp_ent_create(NULL, DATA_TYPE_IMAGETTE, 1, 10);
+	TEST_ASSERT_EQUAL_UINT32(sizeof(struct cmp_entity), size);
+	ent = malloc(size); TEST_ASSERT_NOT_NULL(ent);
+	size = cmp_ent_create(ent, DATA_TYPE_IMAGETTE, 1, 10);
+	TEST_ASSERT_EQUAL_UINT32(sizeof(struct cmp_entity), size);
+
+	/* ent = NULL */
+	error = cmp_ent_read_header(NULL, &cfg);
+	TEST_ASSERT_TRUE(error);
+	/* this should work */
+	error = cmp_ent_read_header(ent, &cfg);
+	TEST_ASSERT_FALSE(error);
+
+	/* cfg = NULL */
+	error = cmp_ent_read_header(ent, NULL);
+	TEST_ASSERT_TRUE(error);
+	/* this should work */
+	error = cmp_ent_read_header(ent, &cfg);
+	TEST_ASSERT_FALSE(error);
+
+	/* unknown data type */
+	cmp_ent_set_data_type(ent, DATA_TYPE_UNKNOWN, 1);
+	error = cmp_ent_read_header(ent, &cfg);
+	TEST_ASSERT_TRUE(error);
+	/* unknown data type */
+	cmp_ent_set_data_type(ent, DATA_TYPE_F_CAM_BACKGROUND+1, 1);
+	error = cmp_ent_read_header(ent, &cfg);
+	TEST_ASSERT_TRUE(error);
+	/* this should work */
+	cmp_ent_set_data_type(ent, DATA_TYPE_IMAGETTE, 1);
+	error = cmp_ent_read_header(ent, &cfg);
+	TEST_ASSERT_FALSE(error);
+
+	/* cmp_mode CMP_MODE_RAW and no raw data bit */
+	cmp_ent_set_data_type(ent, DATA_TYPE_IMAGETTE, 0);
+	error = cmp_ent_read_header(ent, &cfg);
+	TEST_ASSERT_TRUE(error);
+	/* this should work */
+	cmp_ent_set_data_type(ent, DATA_TYPE_IMAGETTE, 1);
+	error = cmp_ent_read_header(ent, &cfg);
+	TEST_ASSERT_FALSE(error);
+
+	/* original_size and data product type not compatible */
+	cmp_ent_set_original_size(ent, 11);
+	error = cmp_ent_read_header(ent, &cfg);
+	TEST_ASSERT_TRUE(error);
+	/* this should work */
+	cmp_ent_set_original_size(ent, 12);
+	error = cmp_ent_read_header(ent, &cfg);
+	TEST_ASSERT_FALSE(error);
+
+	free(ent);
+}
+
+
 void test_decompression_error_cases(void)
 {
 	/* error cases model decompression without a model Buffer */
-- 
GitLab