0460 test: add core NSS helper unit coverage

This commit is contained in:
Mario Fetka
2026-06-13 07:58:25 +00:00
committed by Mario Fetka
parent 7d7ce69933
commit db258348bd
15 changed files with 303 additions and 11 deletions

17
AI.md
View File

@@ -47,7 +47,7 @@ unfinished work out of `TODO.md` merely because its architecture is documented.
Latest patch marker expected in an up-to-date bundle:
- `0459 test: isolate FLAIM smoke test work directories`
- `0460 test: add core NSS helper unit coverage`
When a later chat receives a new `mars-nwe-master` bundle, compare `git log -1`
with this marker. If the uploaded bundle already contains this commit subject,
@@ -67,17 +67,16 @@ The active line is expected to include:
Last generated patch:
- `0459 test: isolate FLAIM smoke test work directories`
- `0460 test: add core NSS helper unit coverage`
Purpose of that patch:
- Fix FLAIM smoke tests that can fail after stale or root-owned build-tree
work directories are left behind. The mars-nwe FLAIM API smoke now creates a
unique temporary work directory derived from the configured base path instead
of reusing `tests/flaim/flaim-api` directly. Apply the matching mars-flaim
submodule patch for the imported `nwflaim.database.create-and-check` CTest
script, which similarly avoids the fixed `third_party/flaim/ctest/nwflaim-db`
directory.
- Add focused CTest coverage for the imported low-level NSS helper line in
`libnwcore`: bit operations, bitmap allocation/search, CRC/hash behavior,
xCtype classification/case conversion, xString compatibility helpers, and
UTF-8/Unicode round-trips. Keep the tests in subsystem directories under
`tests/core/` so later codepage, byte-converter, GUID/ID, UTC, and Unicode
table tests can be added without flattening the test tree.
Rejected or superseded patches that must not be reused as-is:

View File

@@ -9,8 +9,11 @@ exercise outside the normal install flow.
`tests/core` contains normal CTest unit tests for `libnwcore` facilities.
Keep them grouped by core subsystem: `tests/core/ini` covers the shared
`nw_ini_*` reader/writer facade, `tests/core/log` covers the `nwlog_*`
level-mask facade, and future Unicode/codepage/UTF-8/byte/bitmap tests should
get their own sibling subdirectories instead of being added as a flat list.
level-mask facade, and imported NSS low-level helpers are covered by sibling
subdirectories such as `tests/core/bit`, `tests/core/bitmap`,
`tests/core/crc`, `tests/core/xctype`, `tests/core/xstring`, and
`tests/core/utf8`. Future Unicode/codepage/byte coverage should keep using
new focused sibling subdirectories instead of being added as a flat list.
`tests/tui` contains non-interactive `libnwtui` smoke tests. These tests must
not require a real terminal or compare full-screen terminal output; test widget

View File

@@ -4,3 +4,9 @@
add_subdirectory(ini)
add_subdirectory(log)
add_subdirectory(bit)
add_subdirectory(bitmap)
add_subdirectory(crc)
add_subdirectory(xctype)
add_subdirectory(xstring)
add_subdirectory(utf8)

View File

@@ -0,0 +1,9 @@
add_executable(test_nwcore_bit
test_nwcore_bit.c)
target_compile_features(test_nwcore_bit PRIVATE c_std_99)
target_include_directories(test_nwcore_bit PRIVATE
"${CMAKE_SOURCE_DIR}/include/core")
target_link_libraries(test_nwcore_bit PRIVATE mars_nwe::core)
add_test(NAME nwcore_bit COMMAND test_nwcore_bit)

View File

@@ -0,0 +1,36 @@
#include "bit.h"
#include <stdint.h>
#include <stdio.h>
#define CHECK(expr) \
do { \
if (!(expr)) { \
fprintf(stderr, "CHECK failed at %s:%d: %s\n", __FILE__, __LINE__, #expr); \
return 1; \
} \
} while (0)
int main(void)
{
CHECK(LB_CountBits(0) == 0);
CHECK(LB_CountBits(1) == 1);
CHECK(LB_CountBits((NINT)0x0000f0f0U) == 8);
CHECK(LB_CountBits((NINT)0xffffffffU) == 32);
CHECK(LB_findHighBit(0) == (NINT)-1);
CHECK(LB_findHighBit(1) == 0);
CHECK(LB_findHighBit(0x10) == 4);
CHECK(LB_findHighBit((NINT)0x80000000U) == 31);
CHECK(LB_findLowBit(0) == (NINT)-1);
CHECK(LB_findLowBit(1) == 0);
CHECK(LB_findLowBit(0x10) == 4);
CHECK(LB_findLowBit((NINT)0x80000000U) == 31);
CHECK((uint32_t)LB_RotateLeft((NINT)0x12345678U, 8) == 0x34567812U);
CHECK((uint32_t)LB_RotateRight((NINT)0x12345678U, 8) == 0x78123456U);
CHECK((uint32_t)LB_RotateLeft((NINT)0x12345678U, 0) == 0x12345678U);
CHECK((uint32_t)LB_RotateRight((NINT)0x12345678U, 32) == 0x12345678U);
return 0;
}

View File

@@ -0,0 +1,9 @@
add_executable(test_nwcore_bitmap
test_nwcore_bitmap.c)
target_compile_features(test_nwcore_bitmap PRIVATE c_std_99)
target_include_directories(test_nwcore_bitmap PRIVATE
"${CMAKE_SOURCE_DIR}/include/core")
target_link_libraries(test_nwcore_bitmap PRIVATE mars_nwe::core)
add_test(NAME nwcore_bitmap COMMAND test_nwcore_bitmap)

View File

@@ -0,0 +1,48 @@
#include "bitmap.h"
#include <stdio.h>
#define CHECK(expr) \
do { \
if (!(expr)) { \
fprintf(stderr, "CHECK failed at %s:%d: %s\n", __FILE__, __LINE__, #expr); \
return 1; \
} \
} while (0)
int main(void)
{
BitMap_s map;
SNINT start;
CHECK(newBitMap(&map, 20) == &map);
CHECK(getMaxBits(&map) == 20);
CHECK(countBits(&map) == 20);
CHECK(testABit(&map, 0));
CHECK(testABit(&map, 19));
start = findBits(&map, 4);
CHECK(start == 0);
CHECK(countBits(&map) == 16);
CHECK(!testABit(&map, 0));
CHECK(!testABit(&map, 3));
CHECK(testABit(&map, 4));
setAbit(&map, 1);
CHECK(testABit(&map, 1));
clearAbit(&map, 1);
CHECK(!testABit(&map, 1));
clearBits(&map, 8, 4);
CHECK(!testABit(&map, 8));
CHECK(!testABit(&map, 11));
setBits(&map, 8, 2);
CHECK(testABit(&map, 8));
CHECK(testABit(&map, 9));
CHECK(!testABit(&map, 10));
start = findBits(&map, 4);
CHECK(start == 4);
freeBitMap(&map);
return 0;
}

View File

@@ -0,0 +1,9 @@
add_executable(test_nwcore_crc
test_nwcore_crc.c)
target_compile_features(test_nwcore_crc PRIVATE c_std_99)
target_include_directories(test_nwcore_crc PRIVATE
"${CMAKE_SOURCE_DIR}/include/core")
target_link_libraries(test_nwcore_crc PRIVATE mars_nwe::core)
add_test(NAME nwcore_crc COMMAND test_nwcore_crc)

View File

@@ -0,0 +1,31 @@
#include "crc.h"
#include <stdint.h>
#include <stdio.h>
#define CHECK(expr) \
do { \
if (!(expr)) { \
fprintf(stderr, "CHECK failed at %s:%d: %s\n", __FILE__, __LINE__, #expr); \
return 1; \
} \
} while (0)
int main(void)
{
BYTE input[] = "123456789";
char mixed[] = "Mars-NWE";
char lower[] = "mars-nwe";
crc_t running;
CHECK((uint32_t)crc(input, 9) == 0xcbf43926U);
running = updateCRC((crc_t)~0L, input, 4);
running = updateCRC(running, input + 4, 5);
CHECK((uint32_t)~running == 0xcbf43926U);
CHECK(hashLowerString(mixed) == hashLowerString(lower));
CHECK(hashString(mixed) != hashLowerString(mixed));
CHECK(lowerStringCRC(mixed) == lowerStringCRC(lower));
return 0;
}

View File

@@ -0,0 +1,9 @@
add_executable(test_nwcore_utf8
test_nwcore_utf8.c)
target_compile_features(test_nwcore_utf8 PRIVATE c_std_99)
target_include_directories(test_nwcore_utf8 PRIVATE
"${CMAKE_SOURCE_DIR}/include/core")
target_link_libraries(test_nwcore_utf8 PRIVATE mars_nwe::core)
add_test(NAME nwcore_utf8 COMMAND test_nwcore_utf8)

View File

@@ -0,0 +1,43 @@
#include "xUnicode.h"
#include <stdio.h>
#include <string.h>
#define CHECK(expr) \
do { \
if (!(expr)) { \
fprintf(stderr, "CHECK failed at %s:%d: %s\n", __FILE__, __LINE__, #expr); \
return 1; \
} \
} while (0)
int main(void)
{
utf8_t ascii[] = "Mars";
utf8_t utf8_word[] = { 'M', 0xc3, 0xa4, 'r', 'z', 0 };
unicode_t unicode[16];
utf8_t out[16];
NINT n;
n = utf2uni(ascii, unicode, sizeof(unicode));
CHECK(n == 4);
CHECK(unicode[0] == 'M');
CHECK(unicode[3] == 's');
CHECK(unicode[4] == 0);
n = uni2utf(unicode, out, sizeof(out));
CHECK(n == 4);
CHECK(strcmp((char *)out, "Mars") == 0);
n = utf2uni(utf8_word, unicode, sizeof(unicode));
CHECK(n == 4);
CHECK(unicode[0] == 'M');
CHECK(unicode[1] == 0x00e4);
CHECK(unicode[2] == 'r');
CHECK(unicode[3] == 'z');
n = uni2utf(unicode, out, sizeof(out));
CHECK(n == 5);
CHECK(memcmp(out, utf8_word, 6) == 0);
return 0;
}

View File

@@ -0,0 +1,9 @@
add_executable(test_nwcore_xctype
test_nwcore_xctype.c)
target_compile_features(test_nwcore_xctype PRIVATE c_std_99)
target_include_directories(test_nwcore_xctype PRIVATE
"${CMAKE_SOURCE_DIR}/include/core")
target_link_libraries(test_nwcore_xctype PRIVATE mars_nwe::core)
add_test(NAME nwcore_xctype COMMAND test_nwcore_xctype)

View File

@@ -0,0 +1,33 @@
#include "xCtype.h"
#include <stdio.h>
#define CHECK(expr) \
do { \
if (!(expr)) { \
fprintf(stderr, "CHECK failed at %s:%d: %s\n", __FILE__, __LINE__, #expr); \
return 1; \
} \
} while (0)
int main(void)
{
CHECK(LB_tolower('A') == 'a');
CHECK(LB_tolower('z') == 'z');
CHECK(LB_toupper('a') == 'A');
CHECK(LB_toupper('Z') == 'Z');
CHECK(LB_isalpha('A'));
CHECK(LB_isalpha('z'));
CHECK(LB_isdigit('7'));
CHECK(LB_isxdigit('f'));
CHECK(LB_isxdigit('F'));
CHECK(LB_isspace(' '));
CHECK(LB_isspace('\n'));
CHECK(LB_ispunct('.'));
CHECK(LB_isprint('~'));
CHECK(!LB_isprint('\n'));
CHECK(LB_isascii(0x7f));
CHECK(!LB_isascii(0x80));
return 0;
}

View File

@@ -0,0 +1,9 @@
add_executable(test_nwcore_xstring
test_nwcore_xstring.c)
target_compile_features(test_nwcore_xstring PRIVATE c_std_99)
target_include_directories(test_nwcore_xstring PRIVATE
"${CMAKE_SOURCE_DIR}/include/core")
target_link_libraries(test_nwcore_xstring PRIVATE mars_nwe::core)
add_test(NAME nwcore_xstring COMMAND test_nwcore_xstring)

View File

@@ -0,0 +1,39 @@
#include "xString.h"
#include <stdio.h>
#include <string.h>
#define CHECK(expr) \
do { \
if (!(expr)) { \
fprintf(stderr, "CHECK failed at %s:%d: %s\n", __FILE__, __LINE__, #expr); \
return 1; \
} \
} while (0)
int main(void)
{
char buffer[32];
char overlap[16] = "abcdef";
CHECK(LB_stricmp("Mars", "mArS") == 0);
CHECK(LB_strnicmp("NetWare", "net", 3) == 0);
CHECK(LB_memicmp("AbCd", "aBcD", 4) == 0);
CHECK(LB_strmcpy(buffer, "abcdef", 4) == buffer);
CHECK(strcmp(buffer, "abc") == 0);
strcpy(buffer, "Mars");
CHECK(LB_strlwr(buffer) == buffer);
CHECK(strcmp(buffer, "mars") == 0);
CHECK(LB_strupr(buffer) == buffer);
CHECK(strcmp(buffer, "MARS") == 0);
CHECK(LB_strrev(buffer) == buffer);
CHECK(strcmp(buffer, "SRAM") == 0);
CHECK(LB_strset(buffer, 'x') == buffer);
CHECK(strcmp(buffer, "xxxx") == 0);
CHECK(LB_memmove(overlap + 2, overlap, 4) == overlap + 2);
CHECK(memcmp(overlap, "ababcd", 6) == 0);
return 0;
}