v11-0004-Tests-for-Delta-Frame-of-Reference-unit.patch
text/x-patch
Filename: v11-0004-Tests-for-Delta-Frame-of-Reference-unit.patch
Type: text/x-patch
Part: 3
Patch
Same data as JSON:
GET /api/v1/attachments/:id/patch
the parsed metadata as JSON — format, series position, per-file stats; never the diff bytes.
API reference →
Format: format-patch
Series: patch v11-0004
Subject: Tests for Delta Frame of Reference unit.
| File | + | − |
|---|---|---|
| src/test/dfor/.gitignore | 1 | 0 |
| src/test/dfor/Makefile | 2 | 1 |
| src/test/dfor/meson.build | 2 | 0 |
| src/test/dfor/test_dfor_u16.c | 371 | 0 |
From 523c5a08010e8882e9bf2f601f1e85092a5c61b3 Mon Sep 17 00:00:00 2001
From: Evgeny Voropaev <evorop@gmail.com>
Date: Mon, 13 Apr 2026 23:18:07 +0800
Subject: [PATCH v11 4/5] Tests for Delta Frame of Reference unit.
The unit test is implemented as a C program (ELF executable). The test
can be run with the 'make check-unit'. Tests support the TAP protocol
and are executed using the Prove utility.
Author: Evgeny Voropaev <evgeny.voropaev@tantorlabs.com> <evorop@gmail.com>
Reviewed by: Andrey Borodin <x4mmm@yandex-team.ru>
---
src/test/dfor/.gitignore | 1 +
src/test/dfor/Makefile | 3 +-
src/test/dfor/meson.build | 2 +
src/test/dfor/test_dfor_u16.c | 371 ++++++++++++++++++++++++++++++++++
4 files changed, 376 insertions(+), 1 deletion(-)
create mode 100644 src/test/dfor/test_dfor_u16.c
diff --git a/src/test/dfor/.gitignore b/src/test/dfor/.gitignore
index 0d77a51216b..447e95c0c09 100644
--- a/src/test/dfor/.gitignore
+++ b/src/test/dfor/.gitignore
@@ -1,3 +1,4 @@
test_bitpack_u16
+test_dfor_u16
test_uniqsortvect_u16
test_vect_u16
diff --git a/src/test/dfor/Makefile b/src/test/dfor/Makefile
index 4fc9f4bc1ba..2ca98f76a0f 100644
--- a/src/test/dfor/Makefile
+++ b/src/test/dfor/Makefile
@@ -33,7 +33,8 @@ LIBTAP_OBJS = $(top_builddir)/src/test/libtap/tap.o
TESTS= test_vect_u16 \
test_uniqsortvect_u16 \
- test_bitpack_u16
+ test_bitpack_u16 \
+ test_dfor_u16
$(TESTS:%=%.o): CPPFLAGS += -I$(top_builddir)/src/test -DFRONTEND
diff --git a/src/test/dfor/meson.build b/src/test/dfor/meson.build
index ce762c52430..4a760ab68fa 100644
--- a/src/test/dfor/meson.build
+++ b/src/test/dfor/meson.build
@@ -8,6 +8,7 @@ dfor_dir = join_paths(meson.project_source_root(), 'src/backend/lib')
dfor_sources = files(
join_paths(dfor_dir, 'vect_u16.c'),
join_paths(dfor_dir, 'bitpack_u16.c'),
+ join_paths(dfor_dir, 'dfor_u16.c'),
)
dfor_test_lib = static_library(
@@ -36,6 +37,7 @@ test_names = [
'test_vect_u16',
'test_uniqsortvect_u16',
'test_bitpack_u16',
+ 'test_dfor_u16',
]
foreach t : test_names
diff --git a/src/test/dfor/test_dfor_u16.c b/src/test/dfor/test_dfor_u16.c
new file mode 100644
index 00000000000..322b714ba38
--- /dev/null
+++ b/src/test/dfor/test_dfor_u16.c
@@ -0,0 +1,371 @@
+/*
+ * test_dfor.c
+ */
+
+#include "lib/bitpack_u16.h"
+#include "lib/dfor_u16.h"
+#include "lib/vect_u16.h"
+#include "libtap/tap.h"
+#include "test.h"
+
+void test_delta_calculation(size_t cnt, uint16_t inArr[], size_t cntDelta,
+ uint16_t marDeltasExpected[], size_t cntWidth,
+ uint16_t marWidthsExpected[], size_t cntStat,
+ uint16_t marWidthsStatExpected[]);
+
+void test_calc_exceptions(size_t numDeltas, size_t numWidths,
+ uint16_t marWidths[], size_t numCounts,
+ uint16_t marCounts[], size_t szAwaitedWidth,
+ size_t cntAwaitedExcCount);
+
+void test_dfor(size_t cnt, uint16_t arr[], excalg_t isExcUsage,
+ size_t widDeltaAwaited, size_t cntExcCntAwaited,
+ size_t widExcWidAwaited, size_t widExcPosWidAwaited,
+ size_t cntBitsCountAwaited, size_t cntByteCountAwaited,
+ float flMinRatioAwaited, uint8_t u8arPackAwaited[]);
+
+void
+test_delta_calculation(size_t cnt, uint16_t inArr[], size_t cntDelta,
+ uint16_t marDeltasExpected[], size_t cntWidth,
+ uint16_t marWidthsExpected[], size_t cntStat,
+ uint16_t marWidthsStatExpected[])
+{
+ vect_u16_t vDeltas;
+ vect_u16_t vWidthCounters;
+ uniqsortvect_u16_t usvDeltaWidths;
+ vect_u16_t awaited;
+ int res;
+
+ printf("------------------------------------------------\n");
+ printf("Test\n");
+ printf("------------------------------------------------\n");
+
+ printf(" inArr:");
+ for (size_t i = 0; i < cnt; i++)
+ printf(" %u", (uint32_t)inArr[i]);
+ printf("\n");
+
+ vect_u16_init(&vDeltas, 0, NULL);
+ vect_u16_init(&usvDeltaWidths, 0, NULL);
+ vect_u16_init(&vWidthCounters, 0, NULL);
+
+ /* Tested function */
+ res = dfor_u16_calc_deltas(cnt, inArr, &vDeltas, &usvDeltaWidths,
+ &vWidthCounters);
+ cmp_ok(res, "==", 0);
+
+ printf(" Delta expected:");
+ for (size_t i = 0; i < cntDelta; i++)
+ printf(" %u", (uint32_t)marDeltasExpected[i]);
+ printf("\n");
+
+ printf(" Delta fact: ");
+ vect_u16_print(&vDeltas);
+
+ cmp_ok(vDeltas.cnt, "==", cnt, "The Delta count is OK.");
+ vect_u16_init(&awaited, 0, NULL);
+ vect_u16_fill(&awaited, cnt, marDeltasExpected);
+ cmp_ok(vect_u16_compare(&vDeltas, &awaited), "==", 0,
+ "All deltas are calculated properly");
+ vect_u16_clear(&awaited);
+
+ printf(" Width expected:");
+ for (size_t i = 0; i < cntWidth; i++)
+ printf(" %u", (uint32_t)marWidthsExpected[i]);
+ printf("\n");
+
+ printf(" Width fact: ");
+ vect_u16_print(&usvDeltaWidths);
+
+ cmp_ok(usvDeltaWidths.cnt, "==", cntWidth, "The Width count is OK.");
+
+ /* don't really need initialisation after vect_clean having been done
+ * above*/
+ /* vect_u16_init(&awaited, 0, NULL); */
+
+ vect_u16_fill(&awaited, cntWidth, marWidthsExpected);
+ cmp_ok(vect_u16_compare(&usvDeltaWidths, &awaited), "==", 0,
+ "All delta widths is OK.");
+ vect_u16_clear(&awaited);
+
+ printf(" Statistics expected:");
+ for (size_t i = 0; i < cntStat; i++)
+ printf(" %u", (uint32_t)marWidthsStatExpected[i]);
+ printf("\n");
+
+ printf(" Statistics fact: ");
+ vect_u16_print(&vWidthCounters);
+
+ cmp_ok(
+ usvDeltaWidths.cnt, "==", vWidthCounters.cnt,
+ "The count of statistics of widths is equal to the count of widths.");
+
+ /* don't really need initialisation after vect_clean having been done
+ * above*/
+ vect_u16_fill(&awaited, cntStat, marWidthsStatExpected);
+ cmp_ok(vect_u16_compare(&vWidthCounters, &awaited), "==", 0,
+ "Width statistics is OK.");
+ vect_u16_clear(&awaited);
+
+ vect_u16_clear(&vDeltas);
+ vect_u16_clear(&usvDeltaWidths);
+ vect_u16_clear(&vWidthCounters);
+}
+
+void
+test_calc_exceptions(size_t numDeltas, size_t numWidths, uint16_t marWidths[],
+ size_t numCounts, uint16_t marCounts[],
+ size_t szAwaitedWidth, size_t cntAwaitedExcCount)
+{
+ int res;
+ vect_u16_t vWidthCounters;
+ uniqsortvect_u16_t usvDeltaWidths;
+ size_t width, cntExceptions;
+
+ vect_u16_init(&usvDeltaWidths, 0, NULL);
+ vect_u16_fill(&usvDeltaWidths, numWidths, marWidths);
+
+ vect_u16_init(&vWidthCounters, 0, NULL);
+ vect_u16_fill(&vWidthCounters, numCounts, marCounts);
+
+ res = dfor_u16_calc_width(numDeltas, &usvDeltaWidths, &vWidthCounters,
+ &width, &cntExceptions);
+ cmp_ok(res, "==", 0);
+ cmp_ok(width, "==", szAwaitedWidth, "Width is OK.");
+ cmp_ok(cntExceptions, "==", cntAwaitedExcCount, "Exceptions num is OK");
+
+ vect_u16_clear(&usvDeltaWidths);
+ vect_u16_clear(&vWidthCounters);
+}
+
+void
+test_dfor(size_t cnt, uint16_t arr[], excalg_t isExcUsage,
+ size_t widDeltaWidthAwaited, size_t cntExcCntAwaited,
+ size_t widExcWidAwaited, size_t widExcPosWidAwaited,
+ size_t cntBitsCountAwaited, size_t cntByteCountAwaited,
+ float flMinRatioAwaited, uint8_t u8arPackAwaited[])
+{
+ int res;
+ dfor_meta_t dfor;
+ dfor_stats_t stats;
+ uniqsortvect_u16_t extracted;
+
+ res = dfor_u16_pack(cnt, arr, isExcUsage, &dfor, 0, NULL);
+ cmp_ok(res, "==", 0, "dfor_pack func has processed OK.");
+ cmp_ok(dfor.item_cnt, "==", cnt, "Count of deltas is OK.");
+ cmp_ok(dfor.delta_wid, "==", widDeltaWidthAwaited, "Delta width is OK.");
+ cmp_ok(dfor.exc_cnt, "==", cntExcCntAwaited, "Exception count is OK.");
+ cmp_ok(dfor.exc_wid, "==", widExcWidAwaited, "Exception width is OK.");
+ cmp_ok(dfor.exc_pos_wid, "==", widExcPosWidAwaited,
+ "Exception position width is OK.");
+ ok(dfor.pack != NULL, "Pack is created (not NULL).");
+
+ stats = dfor_u16_calc_stats(dfor);
+ cmp_ok(stats.nbits, "==", cntBitsCountAwaited, "Bits count is OK.");
+ cmp_ok(dfor.nbytes, "==", cntByteCountAwaited, "Bytes count is OK.");
+ ok(stats.ratio > flMinRatioAwaited, "Compression ratio is OK.");
+
+ if (u8arPackAwaited != NULL)
+ ok(0 == memcmp(dfor.pack, u8arPackAwaited, cntByteCountAwaited),
+ "Pack content is OK.");
+ else
+ ok(0 == 0, "Pack content check is skipped.");
+
+ test_print_u16_array(cnt, (uint16_t *)arr, "\n\nOriginal integer array");
+ test_print_u8_array(dfor.nbytes, dfor.pack, "Compressed integer array");
+ printf("Compression ratio:%f\n\n", stats.ratio);
+
+ vect_u16_init(&extracted, 0, NULL);
+
+ dfor_u16_unpack(&dfor, &extracted, 0, NULL);
+ cmp_ok(extracted.cnt, "==", cnt, "Extracted count is OK");
+ cmp_ok(0, "==", memcmp(arr, extracted.m, cnt),
+ "Extracted array is equal to original");
+
+ free(dfor.pack);
+ vect_u16_clear(&extracted);
+}
+
+int
+main(void)
+{
+ plan(130);
+ printf("========================================\n");
+ printf("Test DELTA CALCULATION\n");
+ {
+ test_delta_calculation(
+ 10, (uint16_t[]) { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }, /* inArr */
+ 10,
+ (uint16_t[]) { 0, 1, 1, 1, 1, 1, 1, 1, 1,
+ 1 }, /* marDeltasExpected*/
+ 1, (uint16_t[]) { 1 }, /* marWidthsExpected */
+ 1, (uint16_t[]) { 10 } /* marWidthsStatExpected */);
+
+ test_delta_calculation(
+ 10, (uint16_t[]) { 1, 3, 5, 7, 9, 11, 13, 15, 17, 19 }, /* inArr */
+ 10,
+ (uint16_t[]) { 1, 2, 2, 2, 2, 2, 2, 2, 2,
+ 2 }, /* marDeltasExpected*/
+ 2, (uint16_t[]) { 1, 2 }, /* marWidthsExpected */
+ 2, (uint16_t[]) { 1, 9 } /* marWidthsStatExpected */);
+
+ test_delta_calculation(
+ 14,
+ (uint16_t[]) { 100, 200, 300, 400, 401, 402, 403, 404, 406, 408,
+ 410, 412, 414, 416 }, /* inArr */
+ 14,
+ (uint16_t[]) { 100, 100, 100, 100, 1, 1, 1, 1, 2, 2, 2, 2, 2,
+ 2 }, /* marDeltasExpected*/
+ 3, (uint16_t[]) { 1, 2, 7 }, /* marWidthsExpected */
+ 3, (uint16_t[]) { 4, 6, 4 } /* marWidthsStatExpected */);
+
+ test_delta_calculation(1, (uint16_t[]) { 123 }, /* inArr */
+ 1, (uint16_t[]) { 123 }, /* marDeltasExpected*/
+ 1, (uint16_t[]) { 7 }, /* marWidthsExpected */
+ 1,
+ (uint16_t[]) { 1 } /* marWidthsStatExpected */);
+
+ test_delta_calculation(0, NULL, /* inArr */
+ 0, NULL, /* marDeltasExpected*/
+ 0, NULL, /* marWidthsExpected */
+ 0, NULL /* marWidthsStatExpected */);
+ }
+ printf("Test DELTA CALCULATION PASSED\n");
+ printf("========================================\n\n");
+
+ printf("========================================\n");
+ printf("Test EXCEPTIONS CALCULATION\n");
+ {
+ int res;
+ vect_u16_t vWidthCounters;
+ uniqsortvect_u16_t usvDeltaWidths;
+ size_t width, cntExceptions;
+
+ vect_u16_init(&usvDeltaWidths, 0, NULL);
+ vect_u16_fill(&usvDeltaWidths, 3, (uint16_t[]) { 1, 2, 7 });
+
+ vect_u16_init(&vWidthCounters, 0, NULL);
+ vect_u16_fill(&vWidthCounters, 3, (uint16_t[]) { 4, 6, 4 }); // 4+6+4=14
+
+ res = dfor_u16_calc_width(14, &usvDeltaWidths, &vWidthCounters, &width,
+ &cntExceptions);
+ cmp_ok(res, "==", 0);
+ cmp_ok(width, "==", 7, "Widths={1,2,7}, Counters={4,6,4} => width=7");
+ cmp_ok(cntExceptions, "==", 0,
+ "Widths={1,2,7}, Counters={4,6,4} => excptions_num=0");
+ }
+
+ test_calc_exceptions(14, 3, (uint16_t[]) { 1, 2, 7 }, /* widths of deltas*/
+ 3, (uint16_t[]) { 4, 6, 4 }, /* statistics */
+ 7, /* width of short deltas */
+ 0); /* number of exceptions*/
+
+ test_calc_exceptions(14, 3, (uint16_t[]) { 1, 2, 7 }, /* widths */
+ 3, (uint16_t[]) { 6, 7, 1 }, /* stat */
+ 2, 1); /* short deltas width, exceptions count*/
+
+ test_calc_exceptions(40, 3, (uint16_t[]) { 5, 6, 12 }, /* widths */
+ 3, (uint16_t[]) { 36, 2, 2 }, /* stat */
+ 5, 4); /* short deltas width, exceptions count*/
+
+ test_calc_exceptions(40, 4, (uint16_t[]) { 5, 6, 7, 12 }, 4,
+ (uint16_t[]) { 36, 1, 1, 2 }, 5, 4);
+
+ test_calc_exceptions(40, 4, (uint16_t[]) { 5, 6, 7, 12 }, 4,
+ (uint16_t[]) { 35, 1, 2, 2 }, 6, 4);
+
+ test_calc_exceptions(40, 4, (uint16_t[]) { 5, 6, 7, 12 }, 4,
+ (uint16_t[]) { 34, 1, 2, 3 }, 7, 3);
+
+ test_calc_exceptions(40, 4, (uint16_t[]) { 5, 6, 7, 12 }, 4,
+ (uint16_t[]) { 1, 34, 2, 3 }, 7, 3);
+
+ test_calc_exceptions(40, 4, (uint16_t[]) { 5, 6, 7, 12 }, 4,
+ (uint16_t[]) { 1, 33, 2, 4 }, 7, 4);
+
+ test_calc_exceptions(40, 4, (uint16_t[]) { 5, 6, 7, 12 }, 4,
+ (uint16_t[]) { 1, 32, 2, 5 }, 12, 0);
+
+ printf("Test EXCEPTIONS CALCULATION PASSED\n");
+ printf("========================================\n\n");
+
+ printf("========================================\n");
+ printf("Test DELTA FRAME OF REFERENCES PACKING\n");
+
+ test_dfor(16,
+ (uint16_t[]) { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14,
+ 15 }, /* cnt, array */
+ DFOR_EXC_DONT_USE, /* flag on use of exceptions */
+ 1, /* awaited width of short deltas */
+ 0, /* awaited count of exceptions */
+ 0, /* awaited exception width*/
+ 0, /* awaited exception position width*/
+ 16, /* awaited bits count */
+ 2, /* cntByteCountAwaited */
+ 15.99, /* awaited ratio min value (ratio >= 15.99) */
+ (uint8_t[]) { 0xFE, 0xFF });
+
+ test_dfor(16,
+ (uint16_t[]) { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14,
+ 15 }, /* cnt, array */
+ DFOR_EXC_USE, /* flag on use of exceptions */
+ 1, /* awaited width of short deltas */
+ 0, /* awaited count of exceptions */
+ 0, /* awaited exception width*/
+ 0, /* awaited exception position width*/
+ 16, /* awaited bits count */
+ 2, /* cntByteCountAwaited */
+ 15.99, /* awaited ratio min value (ratio >= 15.99) */
+ (uint8_t[]) { 0xFE, 0xFF });
+
+ test_dfor(16,
+ (uint16_t[]) { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14,
+ 1023 }, /* cnt, array */
+ DFOR_EXC_DONT_USE, /* flag on use of exceptions */
+ 10, /* awaited width of short deltas */
+ 0, /* awaited count of exceptions */
+ 0, /* awaited exception width*/
+ 0, /* awaited exception position width*/
+ 10 * 16, /* awaited bits count */
+ 20, /* awaited bytes count */
+ 1.5, /* awaited ratio min value */
+ (uint8_t[]) { 0x00, 0x04, 0x10, 0x40, 0x00, 0x01, 0x04,
+ 0x10, 0x40, 0x00, 0x01, 0x04, 0x10, 0x40,
+ 0x00, 0x01, 0x04, 0x10, 0x40, 0xFC });
+
+ test_dfor(16,
+ (uint16_t[]) { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14,
+ 1023 }, /* cnt, array */
+ DFOR_EXC_USE, /* flag on use of exceptions */
+ 1, /* awaited width of short deltas */
+ 1, /* awaited count of exceptions */
+ 9, /* awaited exception width*/
+ 4, /* awaited exception position width*/
+ 16 * 1 + 9 + 4, /* awaited bits count */
+ 4, /* awaited bytes count */
+ 7.99, /* awaited ratio min value */
+ (uint8_t[]) { 0xFE, 0xFF, 0xF8, 0x1F });
+
+ test_dfor(30, /* cnt */
+ (uint16_t[]) { 0, 1, 2, 3, 4,
+ 5, 6, 7, 8, 9,
+ /* delta=2, pos=10, deltapos=10 */ 11, 12, 13, 14, 15,
+ 16, 17, 18, 19, 20,
+ 21, 22, 23, 24, 25,
+ /* delta=3, pos=25, deltapos=15 */ 28, 29, 30, 31,
+ /* delta=3, pos=29, deltapos=4 */ 34 }, /* array */
+ DFOR_EXC_USE, /* flag on use of exceptions */
+ 1, /* awaited width of short deltas */
+ 3, /* awaited count of exceptions */
+ 1, /* awaited exception width*/
+ 4, /* awaited exception position width*/
+ 30 * 1 + 3 * 1 + 3 * 4, /* awaited bits count */
+ 6, /* awaited bytes count */
+ 9.99, /* awaited ratio min value */
+ (uint8_t[]) { 0xFE, 0xFB, 0xFF, 0xFF, 0xF5, 0x09 });
+
+ printf("Test DELTA FRAME OF REFERENCES PACKING PASSED\n");
+ printf("========================================\n\n");
+
+ done_testing();
+}
--
2.53.0