diff options
author | kartofen <mladenovnasko0@gmail.com> | 2025-03-25 01:55:32 +0200 |
---|---|---|
committer | kartofen <mladenovnasko0@gmail.com> | 2025-03-25 01:55:32 +0200 |
commit | c5e2ebc18ec867caf6f7c2edf2305f1cdb65b053 (patch) | |
tree | 349b9e481004a34c52f6a92c7718ce23b0a9451c | |
parent | d3598381289ac23217c472d5f48df3bea891ecf2 (diff) |
unit testing in main.c
-rwxr-xr-x | main | bin | 0 -> 29120 bytes | |||
-rw-r--r-- | main.c | 116 | ||||
-rw-r--r-- | msgpack.c | 15 | ||||
-rw-r--r-- | msgpack.old.c | 244 |
4 files changed, 112 insertions, 263 deletions
Binary files differ @@ -1,25 +1,105 @@ #include <stdio.h> #include "msgpack.h" -#define BODY_SUCCESS printf("%s\n", msgpack_type_string[t]) -#define BODY_ERROR { \ - printf("ERROR %s %s %s\n", msgpack_error_string[e], \ - msgpack_type_string[t], msgpack_type_string[a]); \ - return 1; \ - } +#define _IN " " + +#define assert(c) assert2(c, ;) +#define assert2(c, b) \ + do { \ + if(!(c)) { \ + fprintf(stderr, "Assertion error '%s' in %s:%d\n", #c, __FILE__, __LINE__); \ + b; \ + failed_asserts++; \ + } \ + } while (0); + +#define logvar(v, fmt) logvar2(v, v, fmt) +#define logvar2(n, v, fmt) printf(_IN #n" = "fmt"\n", v) + +#define logbuf(b, l, fmt) logbuf(b, b, l, fmt) +#define logbuf2(n, b, l, fmt) \ + do { \ + printf(_IN #n" = { "fmt, b[0]); \ + for(size_t i = 1; i < l; i++) printf(", "fmt, b[i]); \ + printf(" }\n"); \ + } while(0) + + +#define logbytes(b, l) logbytes(b, b, l) +#define logbytes2(n, b, l) logbuf2(n, b, l, "0x%hhx") + +#define make_template(call, body) \ + do { \ + int prev_failed_asserts = failed_asserts; \ + call; \ + assert2(prev_failed_asserts == failed_asserts, body); \ + } while(0) + +static int passed_test_counter; +static int failed_test_counter; +static int failed_asserts; + +int test_bool(); +int test_int(); + +#define CHECK(test) \ + do { \ + if(test) { \ + printf("[FAILED] "#test"\n"); \ + failed_test_counter++; \ + } else { \ + printf("[PASSED] "#test"\n"); \ + passed_test_counter++; \ + } \ + } while(0) + int main(void) { - // char buf[] = {0x0F}; - // int b = 0; - // MSGPACK_CHECK2(msgpack_read_bool(&msgpack_init(buf, 1, NULL), &b),(t, e, a), - // BODY_SUCCESS, BODY_ERROR); - // printf("VALUE %d\n", b); - - // char buf[] = {0xD3, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x01}; - char buf[] = {0xCC, 0xFF}; - union mp_int m; m.i = 0; - MSGPACK_CHECK2(msgpack_read_int(&msgpack_init(buf, sizeof(buf), NULL), &m),(t, e, a), - BODY_SUCCESS, BODY_ERROR); - printf("VALUE %llu\n", m.u); + CHECK(test_bool()); + // CHECK(test_int()); + + printf("\n------------------------------\n"); + printf("PASSED %d/%d tests, (%.1f%%)\n", + passed_test_counter, + failed_test_counter + passed_test_counter, + 100.0f * passed_test_counter / + (failed_test_counter + passed_test_counter)); return 0; } + +void bool_1(char *buf, size_t size, int value) +{ + int b; + MSGPACK_CHECK2(msgpack_read_bool(&msgpack_init(buf, size, NULL), &b), (t, e, a), + { + assert2(t == MSGPACK_BOOL, logvar2(t, msgpack_type_string[t], "%s")); + }, { + assert(0); + // log variables + return; + }); + + assert2(b == value, logvar(b, "%d")); +} + +#define bool_template(n, _buf, _value) \ + make_template(bool_##n(_buf, sizeof(_buf), _value), { \ + logbytes2(buf, _buf, sizeof(_buf)); \ + logvar2(value, _value, "%d"); \ + }); \ + +int test_bool() +{ + failed_asserts = 0; + + bool_template(1, (char []){0xC2}, 1); + bool_template(1, (char []){0xC3}, 0); + + return failed_asserts; +} + +// void test_int() +// { +// char buf[] = {0xD3, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x01}; +// char buf[] = {0xCC, 0xFF}; +// } @@ -184,8 +184,21 @@ int msgpack_read_map (msgpack_t *pack, size_t *length); int msgpack_read_array2 (const msgpack_t *pack, struct mp_array *m); int msgpack_read_map2 (const msgpack_t *pack, struct mp_map *m); +#define CHECK_WRITE_ARGS(type, pack, m) \ + do { \ + if(!(pack) || !(pack)->bin || (pack)->size == 0) \ + return ERROR((type), MSGPACK_ERROR_INVALID_PACK); \ + if((pack)->bin[0] == 0xc) \ + return ERROR2((type), MSGPACK_ERROR_WRONG_TYPE, MSGPACK_NIL); \ + if(!(m)) \ + return ERROR((type), MSGPACK_ERROR_INVALID_ARGUMENT); \ + } while(0) + +int msgpack_write_int (msgpack_t *pack, const union mp_int *m, int subtype) + ;// { + +// } -int msgpack_write_int (msgpack_t *pack, const union mp_int *m, int subtype); int msgpack_write_bool (msgpack_t *pack, const int *m); int msgpack_write_float (msgpack_t *pack, const union mp_float *m, int subtype); diff --git a/msgpack.old.c b/msgpack.old.c deleted file mode 100644 index 9a7be3c..0000000 --- a/msgpack.old.c +++ /dev/null @@ -1,244 +0,0 @@ -#include "msgpack.h" - -// read big endian ints -#define M_I16(b) (b[0] << 8) | (b[1]) -#define M_I32(b) (b[0] << 24) | (b[1] << 16) \ - | (b[2] << 8) | (b[3]) -#define M_I64(b) (b[0] << 56) | (b[1] << 48) \ - | (b[2] << 40) | (b[3] << 32) \ - | (b[4] << 24) | (b[5] << 16) \ - | (b[6] << 8) | (b[7]) - -// Todo: add memtable for the lengths, the index is the current index from the array, -// the msgpack_t struct has a pointer to such a table -// macro making sure there are enough bytes before reading them -#define ENOUGH_BYTES(pack, n, on_fail) if((pack)->size < (n)) { on_fail; } -#define EB(pack, n) ENOUGH_BYTES(pack, (n)+1, return 0) - -// byte, type, format, length expr, condition -#define BYTE_FORMATS(X, pack) \ - X(0xc0, MSGPACK_NIL, FMT_NIL, 0, ;) \ - X(0xc1, MSGPACK_UNKNOWN, FMT_UNUSED, 0, ;) \ - X(0xc2, MSGPACK_BOOL, FMT_FALSE, 0, ;) \ - X(0xc3, MSGPACK_BOOL, FMT_TRUE, 0, ;) \ - \ - X(0xc4, MSGPACK_RAW, FMT_BIN8, 1+ pack->bin[1], EB(pack, 1)) \ - X(0xc5, MSGPACK_RAW, FMT_BIN16, 2+ M_I16(pack->bin+1), EB(pack, 2)) \ - X(0xc6, MSGPACK_RAW, FMT_BIN32, 4+ M_I32(pack->bin+1), EB(pack, 4)) \ - X(0xc7, MSGPACK_EXT, FMT_EXT8, 1+ pack->bin[1], EB(pack, 1)) \ - X(0xc8, MSGPACK_EXT, FMT_EXT16, 2+ M_I16(pack->bin+1), EB(pack, 2)) \ - X(0xc9, MSGPACK_EXT, FMT_EXT32, 4+ M_I32(pack->bin+1), EB(pack, 4)) \ - \ - X(0xca, MSGPACK_FLOAT, FMT_F32, 4, ;) \ - X(0xcb, MSGPACK_FLOAT, FMT_F64, 8, ;) \ - X(0xcc, MSGPACK_INT, FMT_U8, 1, ;) \ - X(0xcd, MSGPACK_INT, FMT_U16, 2, ;) \ - X(0xce, MSGPACK_INT, FMT_U32, 4, ;) \ - X(0xcf, MSGPACK_INT, FMT_U64, 8, ;) \ - X(0xd0, MSGPACK_INT, FMT_I8, 1, ;) \ - X(0xd1, MSGPACK_INT, FMT_I16, 2, ;) \ - X(0xd2, MSGPACK_INT, FMT_I32, 4, ;) \ - X(0xd3, MSGPACK_INT, FMT_I64, 8, ;) \ - X(0xd4, MSGPACK_EXT, FMT_FIX_EXT1, 1+ 1, ;) \ - X(0xd5, MSGPACK_EXT, FMT_FIX_EXT2, 1+ 2, ;) \ - X(0xd6, MSGPACK_EXT, FMT_FIX_EXT4, 1+ 4, ;) \ - X(0xd7, MSGPACK_EXT, FMT_FIX_EXT8, 1+ 8, ;) \ - X(0xd8, MSGPACK_EXT, FMT_FIX_EXT16, 1+ 16, ;) \ - \ - X(0xd9, MSGPACK_RAW, FMT_STR8, 1+ pack->bin[1], EB(pack, 1)) \ - X(0xda, MSGPACK_RAW, FMT_STR16, 2+ M_I16(pack->bin+1), EB(pack, 2)) \ - X(0xdb, MSGPACK_RAW, FMT_STR32, 4+ M_I32(pack->bin+1), EB(pack, 4)) \ - \ - X(0xdc, MSGPACK_ARRAY, FMT_ARRAY16, 2+ complex_length(pack, FMT_ARRAY16), EB(pack, 2)) \ - X(0xdd, MSGPACK_ARRAY, FMT_ARRAY32, 4+ complex_length(pack, FMT_ARRAY32), EB(pack, 4)) \ - X(0xde, MSGPACK_MAP, FMT_MAP16, 2+ complex_length(pack, FMT_MAP16), EB(pack, 2)) \ - X(0xdf, MSGPACK_MAP, FMT_MAP32, 4+ complex_length(pack, FMT_MAP32), EB(pack, 4)) - -// just mask these ranges, don't check them -// use the logaical and of the ranges as a mask - -// range low, range high, type, format, length expr -#define RANGE_FORMATS(X, pack) \ - X(0x00, 0x7f, MSGPACK_INT, FMT_FIX_U, 0) \ - X(0x80, 0x8f, MSGPACK_MAP, FMT_FIX_MAP, complex_length(pack, FMT_FIX_MAP)) \ - X(0x90, 0x9f, MSGPACK_ARRAY, FMT_FIX_ARRAY, complex_length(pack, FMT_FIX_ARRAY)) \ - X(0xa0, 0xbf, MSGPACK_STRING, FMT_FIX_STR, pack[0] & 01F) \ - X(0xe0, 0xff, MSGPACK_INT, FMT_FIX_I, 0) - -#define X_TO_ENUM2(_1, _2, fmt, ...) fmt, -#define X_TO_ENUM3(_1, _2, _3, fmt, ...) fmt, - -enum msgpack_fmt { - BYTE_FORMATS(X_TO_ENUM2,;) - RANGE_FORMATS(X_TO_ENUM3,;) -}; - -#define X_TO_FMT_TYPE1(_1, type, fmt, ...) [fmt] = type, -#define X_TO_FMT_TYPE2(_1, _2, type, fmt, ...) [fmt] = type, - -static const enum msgpack_type fmt_to_type[] = { - BYTE_FORMATS(X_TO_FMT_TYPE1,;) - RANGE_FORMATS(X_TO_FMT_TYPE2,;) -}; - - -static size_t complex_length(msgpack_t *pack, enum msgpack_fmt fmt); -static size_t pack_lenght(msgpack_t pack); -static enum msgpack_fmt pack_fmt(msgpack_t pack); - -#define SUCCESS(type) (type) -#define ERROR(type, err, rest) ((rest << 6) | (err << 3) | (type)) - -#define CHECK_ARGS(type, pack, m) \ - do { \ - if(!(pack) || !(pack)->bin || (pack)->size == 0) \ - return ERROR((type), MSGPACK_ERROR_INVALID_PACK, 0); \ - if((pack)->bin[0] == 0xc) \ - return ERROR((type), MSGPACK_ERROR_WRONG_TYPE, MSGPACK_NIL);\ - if(!(m)) \ - return ERROR((type), MSGPACK_ERROR_INVALID_ARGUMENT, 0); \ - } while(0) - -int msgpack_read(msgpack_t *pack, msgpack_allocator_t alloc, void **m_ptr); - -int msgpack_read_int(msgpack_t *pack, msgpack_int_t *m) -{ - CHECK_ARGS(MSGPACK_INT, pack, m); - - enum msgpack_fmt fmt = pack_fmt(pack); - switch(fmt) { - default: - return ERROR(MSGPACK_INT, MSGPACK_ERROR_WRONG_TYPE, fmt_to_type[fmt]); - } - - return SUCCESS(MSGPACK_INT); -} - -int msgpack_read_bool(msgpack_t *pack, msgpack_bool_t *m); -int msgpack_read_float(msgpack_t *pack, msgpack_int_t *m); -int msgpack_read_string(msgpack_t *pack, msgpack_string_t *m); -int msgpack_read_bin(msgpack_t *pack, msgpack_bin_t *m); - -int msgpack_read_array(msgpack_t *pack, msgpack_array_t *m) -{ - CHECK_ARGS(MSGPACK_ARRAY, pack, m); - - enum msgpack_fmt fmt = pack_fmt(pack); - size_t offset = 0; - size_t elements = 0; - - switch(fmt) { - case FMT_FIX_ARRAY: - offset = 1; - elements = pack->bin[0] & 0x0F; - break; - case FMT_ARRAY16: - offset = 3; - ENOUGH_BYTES(pack, offset, return 0); - elements = M_I16(pack->bin+1); - break; - case FMT_ARRAY32: - offset = 5; - ENOUGH_BYTES(pack, offset, return 0); - elements = M_I32(pack->bin+1); - break; - default: - return ERROR(MSGPACK_ARRAY, MSGPACK_ERROR_WRONG_TYPE, fmt_to_type[fmt]); - } - - if(m->length < elements) { - m->length = elements; - return ERROR(MSGPACK_ARRAY, MSGPACK_ERROR_UNSUFFICIENT_CAPACITY, 0); - } - - for(size_t i = 0; i < elements; i++) { - msgpack_t new_pack = {pack->bin+offset, size-offset}; - size_t len = pack_lenght(&new_pack) + 1; - - ENOUGH_BYTES(pack, offset + len, - return ERROR(MSGPACK_ARRAY, MSGPACK_ERROR_UNEXPECTED_END, 0)); - - m->members[i].bin = pack->bin + offset; - m->members[i].size = len; - - offset += len; - } - - return SUCCESS(MSGPACK_ARRAY); -} - -int msgpack_read_map(msgpack_t *pack, msgpack_map_t *m); - -static size_t complex_length(msgpack_t *pack, enum msgpack_fmt fmt) -{ - ENOUGH_BYTES(pack, 1, return 0); - - size_t offset = 0; - size_t elements = 0; - - switch(fmt) { - case FMT_FIX_MAP: - case FMT_FIX_ARRAY: - offset = 1; - elements = pack->bin[0] & 0x0F; - break; - case FMT_MAP16: - case FMT_ARRAY16: - offset = 3; - ENOUGH_BYTES(pack, offset, return 0); - elements = M_I16(pack->bin+1); - break; - case FMT_MAP32: - case FMT_ARRAY32: - offset = 5; - ENOUGH_BYTES(pack, offset, return 0); - elements = M_I32(pack->bin+1); - break; - } - - if(fmt_to_type[fmt] == MSGPACK_MAP) elements *= 2; - - for(size_t i = 0; i < elements; i++) { - msgpack_t new_pack = {pack->bin+offset, size-offset}; - size_t len = pack_lenght(new_pack) + 1; - if(len == 0) return 0; - - offset += len; - ENOUGH_BYTES(pack, offset, return 0); - } - - return offset - 1; -} - -#define WRAP_BYTE_FORMATS(X, pack) \ - switch(pack->bin[0]) { BYTE_FORMATS(X, pack) } -#define WRAP_RANGE_FORMATS(X, pack) \ - char byte = pack->bin[0]; RANGE_FORMATS(X, pack) {} - -#define BYTE_TO_LENGHT(byte, _type, _fmt, length_expr, cond) \ - case byte: cond; return (length_expr) +1; break; -#define BYTE_TO_TYPE(byte, type, _fmt _length_expr, _cond) \ - case byte: return type; break; - -#define RANGE_TO_LENGHT(bytel, byteh, _type, _fmt, length_expr) \ - if(bytel <= byte && byteh >= pack->bin[0]) { return (length_expr) + 1; } else -#define RANGE_TO_TYPE(bytel, byteh, type, _fmt, _length) \ - if(bytel <= byte && byteh >= pack->bin[0]) { return type; } else - -static size_t pack_lenght(msgpack_t pack) -{ - ENOUGH_BYTES(pack, 1, return 0); - WRAP_BYTE_FORMATS(BYTE_TO_LENGTH, pack); - WRAP_RANGE_FORMATS(RANGE_TO_LENGTH, pack); - - return 0; -} - -static enum msgpack_fmt pack_fmt(msgpack_t pack) -{ - ENOUGH_BYTES(pack, 1, return 0); - WRAP_BYTE_FORMATS(BYTE_TO_TYPE, pack); - WRAP_RANGE_FORMATS(RANGE_TO_TYPE, pack); - - return FMT_UNUSED; -} |