From 11ad72e3d7f414b68f7a928152709f9ed29404e8 Mon Sep 17 00:00:00 2001 From: Geoffrey Allott Date: Sat, 30 Jul 2022 21:43:17 +0100 Subject: [PATCH] initial commit --- .gitignore | 2 ++ Makefile | 30 +++++++++++++++++++ src/floor_log2.h | 22 ++++++++++++++ src/tans_bit_reader.h | 13 +++++++++ src/tans_bit_writer.h | 13 +++++++++ src/tans_buf_bit_reader.c | 36 +++++++++++++++++++++++ src/tans_buf_bit_reader.h | 12 ++++++++ src/tans_buf_bit_writer.c | 46 +++++++++++++++++++++++++++++ src/tans_buf_bit_writer.h | 12 ++++++++ src/tans_constants.h | 4 +++ src/tans_decode_st.c | 24 ++++++++++++++++ src/tans_decode_st.h | 12 ++++++++ src/tans_decode_tbl.c | 17 +++++++++++ src/tans_decode_tbl.h | 15 ++++++++++ src/tans_encode_st.c | 23 +++++++++++++++ src/tans_encode_st.h | 13 +++++++++ src/tans_encode_tbl.c | 12 ++++++++ src/tans_encode_tbl.h | 15 ++++++++++ src/tans_file_bit_reader.c | 56 ++++++++++++++++++++++++++++++++++++ src/tans_file_bit_reader.h | 15 ++++++++++ src/tans_freq_tbl.h | 7 +++++ src/tans_symbol_tbl.c | 32 +++++++++++++++++++++ src/tans_symbol_tbl.h | 17 +++++++++++ test/test.h | 33 +++++++++++++++++++++ test/test_tans_bit_reader | Bin 0 -> 27064 bytes test/test_tans_bit_reader.c | 49 +++++++++++++++++++++++++++++++ test/test_tans_bit_writer | Bin 0 -> 25016 bytes test/test_tans_bit_writer.c | 42 +++++++++++++++++++++++++++ test/test_tans_encode_st | Bin 0 -> 28912 bytes test/test_tans_encode_st.c | 37 ++++++++++++++++++++++++ 30 files changed, 609 insertions(+) create mode 100644 .gitignore create mode 100644 Makefile create mode 100644 src/floor_log2.h create mode 100644 src/tans_bit_reader.h create mode 100644 src/tans_bit_writer.h create mode 100644 src/tans_buf_bit_reader.c create mode 100644 src/tans_buf_bit_reader.h create mode 100644 src/tans_buf_bit_writer.c create mode 100644 src/tans_buf_bit_writer.h create mode 100644 src/tans_constants.h create mode 100644 src/tans_decode_st.c create mode 100644 src/tans_decode_st.h create mode 100644 src/tans_decode_tbl.c create mode 100644 src/tans_decode_tbl.h create mode 100644 src/tans_encode_st.c create mode 100644 src/tans_encode_st.h create mode 100644 src/tans_encode_tbl.c create mode 100644 src/tans_encode_tbl.h create mode 100644 src/tans_file_bit_reader.c create mode 100644 src/tans_file_bit_reader.h create mode 100644 src/tans_freq_tbl.h create mode 100644 src/tans_symbol_tbl.c create mode 100644 src/tans_symbol_tbl.h create mode 100644 test/test.h create mode 100755 test/test_tans_bit_reader create mode 100644 test/test_tans_bit_reader.c create mode 100755 test/test_tans_bit_writer create mode 100644 test/test_tans_bit_writer.c create mode 100755 test/test_tans_encode_st create mode 100644 test/test_tans_encode_st.c diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..50a3785 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +*.o +.*.sw* diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..cedffbd --- /dev/null +++ b/Makefile @@ -0,0 +1,30 @@ +CFLAGS = -Isrc -g -Wall -Wextra -Wconversion + +OBJS = $(patsubst %.c, %.o, $(wildcard src/*.o)) +TEST_OBJS = $(patsubst %.c, %.o, $(wildcard test/*.o)) +TESTS = $(patsubst %.c, %, $(wildcard test/*.c)) +RUN_TESTS = $(addprefix run_, $(TESTS)) + +default: $(RUN_TESTS) + +$(RUN_TESTS): run_%: % + $^ + +all: $(OBJS) + +$(OBJS): %.o: %.h src/tans_constants.h +$(TEST_OBJS): test/test.h $(OBJS) + +test/test_tans_bit_reader.o: src/tans_buf_bit_reader.h src/tans_file_bit_reader.h src/tans_bit_reader.h +test/test_tans_bit_reader: src/tans_buf_bit_reader.o src/tans_file_bit_reader.o +test/test_tans_bit_writer.o: src/tans_buf_bit_writer.h src/tans_bit_writer.h +test/test_tans_bit_writer: src/tans_buf_bit_writer.o +test/test_tans_encode_st.o: src/tans_buf_bit_writer.h src/tans_bit_writer.h src/tans_encode_st.h src/tans_symbol_tbl.h src/tans_freq_tbl.h +test/test_tans_encode_st: src/tans_buf_bit_writer.o src/tans_encode_st.o src/tans_encode_tbl.o src/tans_symbol_tbl.o + +clean: + rm -f $(OBJS) + rm -f $(TEST_OBJS) + rm -f $(TESTS) + +.PHONY: default all clean $(RUN_TESTS) diff --git a/src/floor_log2.h b/src/floor_log2.h new file mode 100644 index 0000000..24c2e0e --- /dev/null +++ b/src/floor_log2.h @@ -0,0 +1,22 @@ +#pragma once + +static uint16_t floor_log2(uint16_t x) +{ + if (x <= 1) return 0; + if (x <= 2) return 1; + if (x <= 4) return 2; + if (x <= 8) return 3; + if (x <= 16) return 4; + if (x <= 32) return 5; + if (x <= 64) return 6; + if (x <= 128) return 7; + if (x <= 256) return 8; + if (x <= 512) return 9; + if (x <= 1024) return 10; + if (x <= 2048) return 11; + if (x <= 4096) return 12; + if (x <= 8192) return 13; + if (x <= 16384) return 14; + if (x <= 32768) return 15; + /*if (x <= 65536)*/ return 16; +} diff --git a/src/tans_bit_reader.h b/src/tans_bit_reader.h new file mode 100644 index 0000000..dc139f8 --- /dev/null +++ b/src/tans_bit_reader.h @@ -0,0 +1,13 @@ +#pragma once + +#include + +struct tans_bit_reader; + +struct tans_bit_reader_ops { + uint16_t (*read)(struct tans_bit_reader *self, uint8_t bits); +}; + +struct tans_bit_reader { + const struct tans_bit_reader_ops *vtable; +}; diff --git a/src/tans_bit_writer.h b/src/tans_bit_writer.h new file mode 100644 index 0000000..119c138 --- /dev/null +++ b/src/tans_bit_writer.h @@ -0,0 +1,13 @@ +#pragma once + +#include + +struct tans_bit_writer; + +struct tans_bit_writer_ops { + uint16_t (*write)(struct tans_bit_writer *self, uint16_t value, uint8_t bits); +}; + +struct tans_bit_writer { + const struct tans_bit_writer_ops *vtable; +}; diff --git a/src/tans_buf_bit_reader.c b/src/tans_buf_bit_reader.c new file mode 100644 index 0000000..564549e --- /dev/null +++ b/src/tans_buf_bit_reader.c @@ -0,0 +1,36 @@ +#include "tans_buf_bit_reader.h" + +static uint16_t tans_buf_bit_reader_read(struct tans_bit_reader *reader, uint8_t bits) +{ + struct tans_buf_bit_reader *self = (struct tans_buf_bit_reader *) reader; + uint32_t bit = self->bit % 8; + uint32_t byte = self->bit / 8; + + if (bits == 0 || self->bit + bits > self->len * 8) { + return (uint16_t) -1; + } + + self->bit += bits; + + if (bit + bits <= 8) { + return (uint16_t) (((1 << bits) - 1) & (self->buf[byte] >> bit)); + } else if (bit + bits <= 16) { + return (uint16_t) (((1 << bits) - 1) & ((self->buf[byte] | (self->buf[byte+1] << 8)) >> bit)); + } else if (bit + bits <= 24) { + return (uint16_t) (((1 << bits) - 1) & ((self->buf[byte] | (self->buf[byte+1] << 8) | (self->buf[byte+2] << 16)) >> bit)); + } else { + return (uint16_t) -1; + } +} + +static const struct tans_bit_reader_ops vtable = { + .read = tans_buf_bit_reader_read, +}; + +void tans_buf_bit_reader_init(struct tans_buf_bit_reader *self, const uint8_t *buf, uint32_t len) +{ + self->vtable = &vtable; + self->bit = 0; + self->len = len; + self->buf = buf; +} diff --git a/src/tans_buf_bit_reader.h b/src/tans_buf_bit_reader.h new file mode 100644 index 0000000..71d7d07 --- /dev/null +++ b/src/tans_buf_bit_reader.h @@ -0,0 +1,12 @@ +#pragma once + +#include "tans_bit_reader.h" + +struct tans_buf_bit_reader { + const struct tans_bit_reader_ops *vtable; + uint32_t bit; + uint32_t len; + const uint8_t *buf; +}; + +void tans_buf_bit_reader_init(struct tans_buf_bit_reader *self, const uint8_t *buf, uint32_t len); diff --git a/src/tans_buf_bit_writer.c b/src/tans_buf_bit_writer.c new file mode 100644 index 0000000..20186a1 --- /dev/null +++ b/src/tans_buf_bit_writer.c @@ -0,0 +1,46 @@ +#include "tans_buf_bit_writer.h" + +static uint16_t tans_buf_bit_writer_write(struct tans_bit_writer *writer, uint16_t value, uint8_t bits) +{ + struct tans_buf_bit_writer *self = (struct tans_buf_bit_writer *) writer; + uint32_t bit = self->bit % 8; + uint32_t byte = self->bit / 8; + + if (bits == 0) { + return 0; + } + + if (self->bit + bits > self->len * 8) { + return (uint16_t) -1; + } + + self->bit += bits; + + if (bit + bits <= 8) { + self->buf[byte] |= (uint8_t) ((value & ((1 << bits) - 1)) << bit); + return bits; + } else if (bit + bits <= 16) { + self->buf[byte] |= (uint8_t) ((value << bit) & 0xff); + self->buf[byte+1] |= (uint8_t) ((value & ((1 << bits) - 1)) >> (8 - bit)); + return bits; + } else if (bit + bits <= 24) { + self->buf[byte] |= (uint8_t) ((value << bit) & 0xff); + self->buf[byte+1] |= (uint8_t) ((value >> (8 - bit)) & 0xff); + self->buf[byte+2] |= (uint8_t) ((value & ((1 << bits) - 1)) >> (16 - bit)); + return bits; + } else { + return (uint16_t) -1; + } +} + +static const struct tans_bit_writer_ops vtable = { + .write = tans_buf_bit_writer_write, +}; + +void tans_buf_bit_writer_init(struct tans_buf_bit_writer *self, uint8_t *buf, uint32_t len) +{ + self->vtable = &vtable; + self->bit = 0; + self->len = len; + self->buf = buf; +} diff --git a/src/tans_buf_bit_writer.h b/src/tans_buf_bit_writer.h new file mode 100644 index 0000000..20d1488 --- /dev/null +++ b/src/tans_buf_bit_writer.h @@ -0,0 +1,12 @@ +#pragma once + +#include "tans_bit_writer.h" + +struct tans_buf_bit_writer { + const struct tans_bit_writer_ops *vtable; + uint32_t bit; + uint32_t len; + uint8_t *buf; +}; + +void tans_buf_bit_writer_init(struct tans_buf_bit_writer *self, uint8_t *buf, uint32_t len); diff --git a/src/tans_constants.h b/src/tans_constants.h new file mode 100644 index 0000000..ea031f2 --- /dev/null +++ b/src/tans_constants.h @@ -0,0 +1,4 @@ +#pragma once + +#define TANS_R 10 +#define TANS_L (1 << TANS_R) diff --git a/src/tans_decode_st.c b/src/tans_decode_st.c new file mode 100644 index 0000000..c5077fc --- /dev/null +++ b/src/tans_decode_st.c @@ -0,0 +1,24 @@ +#include "tans_decode_st.h" + +void tans_decode_st_init(struct tans_decode_st *self, struct tans_symbol_tbl *symbol_tbl) +{ + tans_decode_tbl_init(&self->decode_tbl, symbol_tbl); + self->x = 0; +} + +uint16_t tans_decode_st_next(struct tans_decode_st *self, struct tans_bit_reader *bit_reader) +{ + uint8_t ret; + uint16_t read; + struct tans_decode_tbl_entry t = self->decode_tbl.entries[self->x]; + + read = bit_reader->vtable->read(bit_reader, t.nb_bits); + if (read == -1) { + return -1; + } + + ret = t.symbol; + self->x = t.new_x + read; + + return (uint16_t) ret; +} diff --git a/src/tans_decode_st.h b/src/tans_decode_st.h new file mode 100644 index 0000000..09165a8 --- /dev/null +++ b/src/tans_decode_st.h @@ -0,0 +1,12 @@ +#pragma once + +#include "tans_decode_tbl.h" +#include "tans_bit_reader.h" + +struct tans_decode_st { + struct tans_decode_tbl decode_tbl; + uint16_t x; +}; + +void tans_decode_st_init(struct tans_decode_st *self, struct tans_symbol_tbl *symbol_tbl); +uint16_t tans_decode_st_next(struct tans_decode_st *self, struct tans_bit_reader *bit_reader); diff --git a/src/tans_decode_tbl.c b/src/tans_decode_tbl.c new file mode 100644 index 0000000..e3feb24 --- /dev/null +++ b/src/tans_decode_tbl.c @@ -0,0 +1,17 @@ +#include "tans_decode_tbl.h" + +#include "floor_log2.h" + +void tans_decode_tbl_init(struct tans_decode_tbl *self, struct tans_symbol_tbl *symbol_tbl) +{ + uint16_t i; + uint16_t x; + uint8_t s; + + for (i = 0; i < TANS_L; ++i) { + s = self->entries[i].symbol = symbol_tbl->symbol[i]; + x = symbol_tbl->entries[s].next++; + self->entries[s].nb_bits = TANS_R - floor_log2(x); + self->entries[s].new_x = (x << self->entries[s].nb_bits) - TANS_L; + } +} diff --git a/src/tans_decode_tbl.h b/src/tans_decode_tbl.h new file mode 100644 index 0000000..e191176 --- /dev/null +++ b/src/tans_decode_tbl.h @@ -0,0 +1,15 @@ +#pragma once + +#include "tans_symbol_tbl.h" + +struct tans_decode_tbl_entry { + uint8_t symbol; + uint8_t nb_bits; + uint16_t new_x; +}; + +struct tans_decode_tbl { + struct tans_decode_tbl_entry entries[TANS_L]; +}; + +void tans_decode_tbl_init(struct tans_decode_tbl *self, struct tans_symbol_tbl *symbol_tbl); diff --git a/src/tans_encode_st.c b/src/tans_encode_st.c new file mode 100644 index 0000000..d6c7232 --- /dev/null +++ b/src/tans_encode_st.c @@ -0,0 +1,23 @@ +#include "tans_encode_st.h" + +void tans_encode_st_init(struct tans_encode_st *self, const struct tans_symbol_tbl *symbol_tbl) +{ + self->symbol_tbl = *symbol_tbl; + tans_encode_tbl_init(&self->encode_tbl, &self->symbol_tbl); + self->x = 0; +} + +uint16_t tans_encode_st_next(struct tans_encode_st *self, struct tans_bit_writer *bit_writer, uint8_t symbol) +{ + uint8_t nb_bits; + uint16_t written; + + nb_bits = (uint8_t) ((self->x + TANS_L + self->symbol_tbl.entries[symbol].nb) >> (TANS_R + 1)); + written = bit_writer->vtable->write(bit_writer, self->x + TANS_L, nb_bits); + if (written != nb_bits) { + return (uint16_t) -1; + } + self->x = self->encode_tbl.entries[self->symbol_tbl.entries[symbol].start + ((self->x + TANS_L) >> nb_bits)].x; + + return written; +} diff --git a/src/tans_encode_st.h b/src/tans_encode_st.h new file mode 100644 index 0000000..e31ef79 --- /dev/null +++ b/src/tans_encode_st.h @@ -0,0 +1,13 @@ +#pragma once + +#include "tans_encode_tbl.h" +#include "tans_bit_writer.h" + +struct tans_encode_st { + struct tans_symbol_tbl symbol_tbl; + struct tans_encode_tbl encode_tbl; + uint16_t x; +}; + +void tans_encode_st_init(struct tans_encode_st *self, const struct tans_symbol_tbl *symbol_tbl); +uint16_t tans_encode_st_next(struct tans_encode_st *self, struct tans_bit_writer *bit_writer, uint8_t symbol); diff --git a/src/tans_encode_tbl.c b/src/tans_encode_tbl.c new file mode 100644 index 0000000..a60ebdc --- /dev/null +++ b/src/tans_encode_tbl.c @@ -0,0 +1,12 @@ +#include "tans_encode_tbl.h" + +void tans_encode_tbl_init(struct tans_encode_tbl *self, struct tans_symbol_tbl *symbol_tbl) +{ + uint8_t s; + uint16_t x; + + for (x = TANS_L; x < TANS_L << 1; ++x) { + s = symbol_tbl->symbol[x-TANS_L]; + self->entries[symbol_tbl->entries[s].start + symbol_tbl->entries[s].next++].x = x - TANS_L; + } +} diff --git a/src/tans_encode_tbl.h b/src/tans_encode_tbl.h new file mode 100644 index 0000000..79ccf30 --- /dev/null +++ b/src/tans_encode_tbl.h @@ -0,0 +1,15 @@ +#pragma once + +#include "tans_constants.h" +#include "tans_symbol_tbl.h" + +struct tans_encode_tbl_entry { + uint16_t x; +}; + +struct tans_encode_tbl { + // TODO verify size of entries table + struct tans_encode_tbl_entry entries[TANS_L]; +}; + +void tans_encode_tbl_init(struct tans_encode_tbl *self, struct tans_symbol_tbl *symbol_tbl); diff --git a/src/tans_file_bit_reader.c b/src/tans_file_bit_reader.c new file mode 100644 index 0000000..fa79ddd --- /dev/null +++ b/src/tans_file_bit_reader.c @@ -0,0 +1,56 @@ +#include "tans_file_bit_reader.h" + +#include +#include +#include + +static uint16_t tans_file_bit_reader_read(struct tans_bit_reader *reader, uint8_t bits) +{ + struct tans_file_bit_reader *self = (struct tans_file_bit_reader *) reader; + ssize_t bytes_read; + uint32_t bit = self->bit % 8; + uint32_t byte = self->bit / 8; + + if (bits == 0) { + return (uint16_t) -1; + } + + while (self->len * 8 - self->bit < bits) { + memmove(self->buf, self->buf + byte, self->len - byte); + bytes_read = read(self->fd, self->buf + self->len, sizeof self->buf - self->len); + if (bytes_read <= 0) { + return (uint16_t) -1; + } + self->len += (uint32_t) bytes_read; + } + + self->bit += bits; + + if (bit + bits <= 8) { + return (uint16_t) (((1 << bits) - 1) & (self->buf[byte] >> bit)); + } else if (bit + bits <= 16) { + return (uint16_t) (((1 << bits) - 1) & ((self->buf[byte] >> bit) | (self->buf[byte+1] << (8 - bit)))); + } else if (bit + bits <= 24) { + return (uint16_t) (((1 << bits) - 1) & ((self->buf[byte] >> bit) | ((self->buf[byte+1] | (self->buf[byte+2] << 8)) << (8 - bit)))); + } else { + return (uint16_t) -1; + } +} + +static const struct tans_bit_reader_ops vtable = { + .read = tans_file_bit_reader_read, +}; + +int tans_file_bit_reader_init(struct tans_file_bit_reader *self, const char *filename) +{ + self->vtable = &vtable; + self->fd = open(filename, O_RDONLY | O_CLOEXEC); + self->bit = 0; + self->len = 0; + + if (self->fd == -1) { + return -1; + } + + return 0; +} diff --git a/src/tans_file_bit_reader.h b/src/tans_file_bit_reader.h new file mode 100644 index 0000000..4e29dc3 --- /dev/null +++ b/src/tans_file_bit_reader.h @@ -0,0 +1,15 @@ +#pragma once + +#include "tans_bit_reader.h" + +#define TANS_FILE_BIT_READER_BUFSZ 1024 + +struct tans_file_bit_reader { + const struct tans_bit_reader_ops *vtable; + int fd; + uint32_t bit; + uint32_t len; + uint8_t buf[TANS_FILE_BIT_READER_BUFSZ]; +}; + +int tans_file_bit_reader_init(struct tans_file_bit_reader *self, const char *filename); diff --git a/src/tans_freq_tbl.h b/src/tans_freq_tbl.h new file mode 100644 index 0000000..d2ff754 --- /dev/null +++ b/src/tans_freq_tbl.h @@ -0,0 +1,7 @@ +#pragma once + +#include + +struct tans_freq_tbl { + uint16_t freq[256]; +}; diff --git a/src/tans_symbol_tbl.c b/src/tans_symbol_tbl.c new file mode 100644 index 0000000..a1237b9 --- /dev/null +++ b/src/tans_symbol_tbl.c @@ -0,0 +1,32 @@ +#include "tans_symbol_tbl.h" + +#include "floor_log2.h" + +int tans_symbol_tbl_init(struct tans_symbol_tbl *self, const struct tans_freq_tbl *freq_tbl) +{ + uint16_t x, step, s, i, start, freq, k; + + x = 0; + step = TANS_L*5/8 + 3; + start = 0; + + for (s = 0; s < 256; ++s) { + freq = freq_tbl->freq[s]; + self->entries[s].start = start; + self->entries[s].next = freq; + k = TANS_R - floor_log2(freq); + self->entries[s].nb = (uint16_t) ((k << (TANS_R + 1)) - (freq << k)); + start += freq; + for (i = 0; i < freq; ++i) { + self->symbol[x] = (uint8_t) s; + x += step; + x %= TANS_L; + } + } + + if (start != TANS_L) { // freq entries must add up to TANS_L + return -1; + } + + return 0; +} diff --git a/src/tans_symbol_tbl.h b/src/tans_symbol_tbl.h new file mode 100644 index 0000000..985928c --- /dev/null +++ b/src/tans_symbol_tbl.h @@ -0,0 +1,17 @@ +#pragma once + +#include "tans_constants.h" +#include "tans_freq_tbl.h" + +struct tans_symbol_tbl_entry { + uint16_t nb; + uint16_t start; + uint16_t next; +}; + +struct tans_symbol_tbl { + uint8_t symbol[TANS_L]; + struct tans_symbol_tbl_entry entries[256]; +}; + +int tans_symbol_tbl_init(struct tans_symbol_tbl *self, const struct tans_freq_tbl *freq_tbl); diff --git a/test/test.h b/test/test.h new file mode 100644 index 0000000..d9888ea --- /dev/null +++ b/test/test.h @@ -0,0 +1,33 @@ +#pragma once + +#include + +enum test_result { + TEST_SUCCESS = 0x100, + TEST_SKIP = 0x101, + TEST_FAILURE = 0x102, +}; + +#define ASSERT_EQ(lhs, rhs) do { \ + long a = (long) (lhs), b = (long) (rhs); \ + if ((a) != (b)) { \ + printf("ERROR: " #lhs " (%ld) != " #rhs " (%ld)\n", (a), (b)); \ + return TEST_FAILURE; \ + } \ + } while(0) + +#define ASSERT_NE(lhs, rhs) do { \ + long a = (long) (lhs), b = (long) (rhs); \ + if ((a) == (b)) { \ + printf("ERROR: " #lhs " (%ld) == " #rhs " (%ld)\n", (a), (b)); \ + return TEST_FAILURE; \ + } \ + } while(0) + +#define RUN_TEST(test_fn) switch (test_fn()) { \ + case TEST_SUCCESS: printf("PASS: " #test_fn "\n"); break; \ + case TEST_SKIP: printf("SKIP: " #test_fn "\n"); break; \ + case TEST_FAILURE: printf("FAIL: " #test_fn "\n"); return 1; \ + default: printf("FAIL: " #test_fn "\n"); return 1; \ +} + diff --git a/test/test_tans_bit_reader b/test/test_tans_bit_reader new file mode 100755 index 0000000000000000000000000000000000000000..1f43ac2e1d48193b8b27405aa82891ad24f4730f GIT binary patch literal 27064 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 tans_bit_reader *) &bit_reader, 0), (uint16_t) -1); + + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 8), 1); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 4), 0xf); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 6), 0x2f); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 2), 0); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 16), 0x3fe0); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 8), 0xd0); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 7), 0x0f); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 1), 1); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 3), 0); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 5), 0x18); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 4), 0xf); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 1), (uint16_t) -1); + + return TEST_SUCCESS; +} + +enum test_result test_tans_file_bit_reader(void) +{ + struct tans_file_bit_reader bit_reader; + uint8_t bits; + + ASSERT_EQ(tans_file_bit_reader_init(&bit_reader, "/dev/zero"), 0); + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, 0), (uint16_t) -1); + + for (bits = 1; bits <= 16; ++bits) { + ASSERT_EQ(bit_reader.vtable->read((struct tans_bit_reader *) &bit_reader, bits), 0); + } + + return TEST_SUCCESS; +} + +int main(void) +{ + RUN_TEST(test_tans_buf_bit_reader); + RUN_TEST(test_tans_file_bit_reader); +} diff --git a/test/test_tans_bit_writer b/test/test_tans_bit_writer new file mode 100755 index 0000000000000000000000000000000000000000..e8fe9ba558d043ea4b15362c9ba889ec13bb7c8e GIT binary patch literal 25016 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, 0, 0), 0); + + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 1, 8), 8); + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 0xf, 4), 4); + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 0x2f, 6), 6); + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 0, 2), 2); + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 0x3fe0, 16), 16); + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 0xd0, 8), 8); + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 0x0f, 7), 7); + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 1, 1), 1); + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 0, 3), 3); + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 0x18, 5), 5); + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 0xf, 4), 4); + ASSERT_EQ(bit_writer->vtable->write(bit_writer, 0, 1), (uint16_t) -1); + + ASSERT_EQ(buf[0], 0x01); + ASSERT_EQ(buf[1], 0xff); + ASSERT_EQ(buf[2], 0x02); + ASSERT_EQ(buf[3], 0xfe); + ASSERT_EQ(buf[4], 0x03); + ASSERT_EQ(buf[5], 0xfd); + ASSERT_EQ(buf[6], 0x08); + ASSERT_EQ(buf[7], 0xfc); + + return TEST_SUCCESS; +} + +int main(void) +{ + RUN_TEST(test_tans_buf_bit_writer); +} diff --git a/test/test_tans_encode_st b/test/test_tans_encode_st new file mode 100755 index 0000000000000000000000000000000000000000..5721161949d6887f15969f708c87c50ae00fe60c GIT binary patch literal 28912 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 literal 0 HcmV?d00001 diff --git a/test/test_tans_encode_st.c b/test/test_tans_encode_st.c new file mode 100644 index 0000000..a7bb884 --- /dev/null +++ b/test/test_tans_encode_st.c @@ -0,0 +1,37 @@ +#include "test.h" + +#include "tans_buf_bit_writer.h" +#include "tans_encode_st.h" + +enum test_result test_tans_encode_st_equal_freq(void) +{ + struct tans_freq_tbl freq_tbl; + struct tans_symbol_tbl symbol_tbl; + struct tans_encode_st encode_st; + struct tans_buf_bit_writer buf_bit_writer; + struct tans_bit_writer *bit_writer = (struct tans_bit_writer *) &buf_bit_writer; + uint8_t data[8] = {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08}; + uint8_t buf[8] = {0}; + uint16_t i; + + for (i = 0; i < 256; ++i) { + freq_tbl.freq[i] = TANS_L / 256; + } + ASSERT_EQ(tans_symbol_tbl_init(&symbol_tbl, &freq_tbl), 0); + tans_encode_st_init(&encode_st, &symbol_tbl); + tans_buf_bit_writer_init(&buf_bit_writer, buf, sizeof buf); + + for (i = 0; i < sizeof data; ++i) { + ASSERT_NE(tans_encode_st_next(&encode_st, bit_writer, data[i]), (uint16_t) -1); + } + + ASSERT_EQ(buf_bit_writer.bit, buf_bit_writer.len * 8); + ASSERT_EQ(tans_encode_st_next(&encode_st, bit_writer, 0), (uint16_t) -1); + + return TEST_SUCCESS; +} + +int main(void) +{ + RUN_TEST(test_tans_encode_st_equal_freq); +} -- 2.34.1