diff options
Diffstat (limited to 'tests')
31 files changed, 2065 insertions, 2065 deletions
diff --git a/tests/api_args_test.c b/tests/api_args_test.c index 6c7dfc7..309ee6e 100644 --- a/tests/api_args_test.c +++ b/tests/api_args_test.c @@ -4,7 +4,7 @@ #include <string.h> /* A feed that returns false must not move the cursor or change a cell. */ -static void expect_unchanged(struct term *t, int x, int y, uint32_t cp) +static void expect_unchanged(struct wsap_vtcore *t, int x, int y, uint32_t cp) { assert(tt_cursor_x(t) == x); assert(tt_cursor_y(t) == y); @@ -13,117 +13,117 @@ static void expect_unchanged(struct term *t, int x, int y, uint32_t cp) static void test_feed_unknown_flag(void) { - struct term *t = tt_new(10, 3); + struct wsap_vtcore *t = tt_new(10, 3); assert(t); - assert(term_feed(t, "abc", 3, 0)); + assert(wsap_vtcore_feed(t, "abc", 3, 0)); expect_unchanged(t, 3, 0, 'a'); - assert(!term_feed(t, "xy", 2, 1u << 1)); + assert(!wsap_vtcore_feed(t, "xy", 2, 1u << 1)); expect_unchanged(t, 3, 0, 'a'); - assert(!term_feed(t, "xy", 2, TERM_FEED_ONLCR | (1u << 4))); + assert(!wsap_vtcore_feed(t, "xy", 2, WSAP_VTCORE_FEED_ONLCR | (1u << 4))); expect_unchanged(t, 3, 0, 'a'); - assert(!term_feed(t, "xy", 2, 1u << 31)); + assert(!wsap_vtcore_feed(t, "xy", 2, 1u << 31)); expect_unchanged(t, 3, 0, 'a'); /* Unknown bits are rejected even when there are no bytes. */ - assert(!term_feed(t, "", 0, 1u << 1)); + assert(!wsap_vtcore_feed(t, "", 0, 1u << 1)); - assert(term_feed(t, "\nz", 2, TERM_FEED_ONLCR)); + assert(wsap_vtcore_feed(t, "\nz", 2, WSAP_VTCORE_FEED_ONLCR)); assert(tt_cursor_x(t) == 1); assert(tt_cursor_y(t) == 1); - term_free(t); + wsap_vtcore_free(t); } static void test_feed_null_buffer(void) { - struct term *t = tt_new(10, 3); + struct wsap_vtcore *t = tt_new(10, 3); assert(t); - assert(term_feed(t, "abc", 3, 0)); + assert(wsap_vtcore_feed(t, "abc", 3, 0)); - assert(!term_feed(t, NULL, 1, 0)); + assert(!wsap_vtcore_feed(t, NULL, 1, 0)); expect_unchanged(t, 3, 0, 'a'); - assert(!term_feed(t, NULL, 4096, TERM_FEED_ONLCR)); + assert(!wsap_vtcore_feed(t, NULL, 4096, WSAP_VTCORE_FEED_ONLCR)); expect_unchanged(t, 3, 0, 'a'); /* A zero length is a no-op, so a NULL buffer is fine. */ - assert(term_feed(t, NULL, 0, 0)); - assert(term_feed(t, "", 0, TERM_FEED_ONLCR)); + assert(wsap_vtcore_feed(t, NULL, 0, 0)); + assert(wsap_vtcore_feed(t, "", 0, WSAP_VTCORE_FEED_ONLCR)); expect_unchanged(t, 3, 0, 'a'); - assert(!term_feed(NULL, "a", 1, 0)); - assert(!term_feed(NULL, NULL, 0, 0)); - term_free(t); + assert(!wsap_vtcore_feed(NULL, "a", 1, 0)); + assert(!wsap_vtcore_feed(NULL, NULL, 0, 0)); + wsap_vtcore_free(t); } static void test_new_rejects_bad_options(void) { - struct term_options opt; + struct wsap_vtcore_options opt; memset(&opt, 0, sizeof(opt)); opt.size.x = -1; - assert(!term_new(&opt)); + assert(!wsap_vtcore_new(&opt)); memset(&opt, 0, sizeof(opt)); opt.size.y = -1; - assert(!term_new(&opt)); + assert(!wsap_vtcore_new(&opt)); memset(&opt, 0, sizeof(opt)); - opt.size.x = TERM_MAX_COLS + 1; - assert(!term_new(&opt)); + opt.size.x = WSAP_VTCORE_MAX_COLS + 1; + assert(!wsap_vtcore_new(&opt)); memset(&opt, 0, sizeof(opt)); opt.scrollback = -1; - assert(!term_new(&opt)); + assert(!wsap_vtcore_new(&opt)); memset(&opt, 0, sizeof(opt)); - opt.scrollback = TERM_SCROLLBACK_MAX + 1; - assert(!term_new(&opt)); + opt.scrollback = WSAP_VTCORE_SCROLLBACK_MAX + 1; + assert(!wsap_vtcore_new(&opt)); memset(&opt, 0, sizeof(opt)); - opt.scrollback = TERM_SCROLLBACK_MAX; - struct term *max = term_new(&opt); + opt.scrollback = WSAP_VTCORE_SCROLLBACK_MAX; + struct wsap_vtcore *max = wsap_vtcore_new(&opt); assert(max); - term_free(max); + wsap_vtcore_free(max); memset(&opt, 0, sizeof(opt)); - opt.cursor_style = (enum term_cursor_style)3; - assert(!term_new(&opt)); + opt.cursor_style = (enum wsap_vtcore_cursor_style)3; + assert(!wsap_vtcore_new(&opt)); memset(&opt, 0, sizeof(opt)); - opt.cursor_style = (enum term_cursor_style)-1; - assert(!term_new(&opt)); + opt.cursor_style = (enum wsap_vtcore_cursor_style)-1; + assert(!wsap_vtcore_new(&opt)); } static void test_new_accepts_defaults(void) { - struct term_options opt; + struct wsap_vtcore_options opt; memset(&opt, 0, sizeof(opt)); - struct term *t = term_new(&opt); + struct wsap_vtcore *t = wsap_vtcore_new(&opt); assert(t); assert(tt_cols(t) == 80); assert(tt_rows(t) == 24); - assert(term_cursor(t).style == TERM_CURSOR_BLOCK); - term_free(t); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BLOCK); + wsap_vtcore_free(t); memset(&opt, 0, sizeof(opt)); - opt.size.x = TERM_MAX_COLS; + opt.size.x = WSAP_VTCORE_MAX_COLS; opt.size.y = 1; - opt.cursor_style = TERM_CURSOR_BAR; - t = term_new(&opt); + opt.cursor_style = WSAP_VTCORE_CURSOR_BAR; + t = wsap_vtcore_new(&opt); assert(t); - assert(tt_cols(t) == TERM_MAX_COLS); + assert(tt_cols(t) == WSAP_VTCORE_MAX_COLS); assert(tt_rows(t) == 1); - assert(term_cursor(t).style == TERM_CURSOR_BAR); - term_free(t); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BAR); + wsap_vtcore_free(t); } static void test_resize_rejects_too_wide(void) { - struct term *t = tt_new(10, 3); + struct wsap_vtcore *t = tt_new(10, 3); assert(t); - assert(term_feed(t, "abc", 3, 0)); + assert(wsap_vtcore_feed(t, "abc", 3, 0)); - assert(!tt_resize(t, TERM_MAX_COLS + 1, 3)); + assert(!tt_resize(t, WSAP_VTCORE_MAX_COLS + 1, 3)); assert(tt_cols(t) == 10); assert(tt_rows(t) == 3); expect_unchanged(t, 3, 0, 'a'); @@ -133,10 +133,10 @@ static void test_resize_rejects_too_wide(void) assert(tt_cols(t) == 10); assert(tt_rows(t) == 3); - assert(tt_resize(t, TERM_MAX_COLS, 3)); - assert(tt_cols(t) == TERM_MAX_COLS); + assert(tt_resize(t, WSAP_VTCORE_MAX_COLS, 3)); + assert(tt_cols(t) == WSAP_VTCORE_MAX_COLS); assert(tt_rows(t) == 3); - term_free(t); + wsap_vtcore_free(t); } int main(void) diff --git a/tests/correctness_probe.c b/tests/correctness_probe.c index 9ac74ca..47548a3 100644 --- a/tests/correctness_probe.c +++ b/tests/correctness_probe.c @@ -27,60 +27,60 @@ void *__wrap_realloc(void *ptr, size_t size) int main(void) { bool failed = false; - struct term_options options = { .size = { 8, 3 }, .scrollback = 5 }; - struct term *t = term_new(&options); - struct term_snapshot *s = term_snapshot_new(); - assert(t && s && term_snapshot_update(s, t)); + struct wsap_vtcore_options options = { .size = { 8, 3 }, .scrollback = 5 }; + struct wsap_vtcore *t = wsap_vtcore_new(&options); + struct wsap_vtcore_snapshot *s = wsap_vtcore_snapshot_new(); + assert(t && s && wsap_vtcore_snapshot_update(s, t)); const char accented[] = "e\xcc\x81"; - term_feed(t, accented, sizeof(accented) - 1, 0); + wsap_vtcore_feed(t, accented, sizeof(accented) - 1, 0); fail_realloc = 1; - bool ok = term_snapshot_update(s, t); + bool ok = wsap_vtcore_snapshot_update(s, t); uint32_t cps[16]; printf("snapshot arena allocation failure: update=%d size=%dx%d (expected false and the previous 8x3 view)\n", - ok, term_snapshot_view(s)->size.x, term_snapshot_view(s)->size.y); - failed |= ok || term_snapshot_view(s)->size.x != 8 || term_snapshot_view(s)->size.y != 3; - assert(term_snapshot_update(s, t)); - int n = term_snapshot_cluster(s, term_snapshot_row(s, 0)[0].text, cps, 16); + ok, wsap_vtcore_snapshot_view(s)->size.x, wsap_vtcore_snapshot_view(s)->size.y); + failed |= ok || wsap_vtcore_snapshot_view(s)->size.x != 8 || wsap_vtcore_snapshot_view(s)->size.y != 3; + assert(wsap_vtcore_snapshot_update(s, t)); + int n = wsap_vtcore_snapshot_cluster(s, wsap_vtcore_snapshot_row(s, 0)[0].text, cps, 16); printf("retry after allocation recovers: cluster_length=%d (expected 2)\n", n); failed |= n != 2 || cps[0] != 'e' || cps[1] != 0x301; - term_snapshot_free(s); - term_free(t); + wsap_vtcore_snapshot_free(s); + wsap_vtcore_free(t); options.size.y = 24; - t = term_new(&options); - s = term_snapshot_new(); + t = wsap_vtcore_new(&options); + s = wsap_vtcore_snapshot_new(); assert(t && s); const char line[] = "e\xcc\x81\r\n"; for (int i = 1; i <= 10000; i++) { - term_feed(t, line, sizeof(line) - 1, 0); - assert(term_snapshot_update(s, t)); + wsap_vtcore_feed(t, line, sizeof(line) - 1, 0); + assert(wsap_vtcore_snapshot_update(s, t)); if (i == 1000 || i == 10000) printf("after %d lines: arena_words=%u dead_words=%u history_rows=%d\n", - i, s->arena_len, s->arena_dead, term_history_rows(t)); + i, s->arena_len, s->arena_dead, wsap_vtcore_history_rows(t)); } - failed |= s->arena_len >= 8192 || term_history_rows(t) != 5; - term_snapshot_free(s); - term_free(t); + failed |= s->arena_len >= 8192 || wsap_vtcore_history_rows(t) != 5; + wsap_vtcore_snapshot_free(s); + wsap_vtcore_free(t); - options.size = (struct term_vector2i){ 8, 4 }; - t = term_new(&options); - s = term_snapshot_new(); + options.size = (struct wsap_vtcore_vector2i){ 8, 4 }; + t = wsap_vtcore_new(&options); + s = wsap_vtcore_snapshot_new(); assert(t && s); const char rows[] = "A\r\nB\r\nC\r\nD"; - term_feed(t, rows, sizeof(rows) - 1, 0); - assert(term_snapshot_update(s, t)); + wsap_vtcore_feed(t, rows, sizeof(rows) - 1, 0); + assert(wsap_vtcore_snapshot_update(s, t)); printf("before failed height shrink: top=%c cursor_y=%d history=%d\n", - (char)term_snapshot_row(s, 0)[0].text, term_cursor(t).pos.y, term_history_rows(t)); + (char)wsap_vtcore_snapshot_row(s, 0)[0].text, wsap_vtcore_cursor(t).pos.y, wsap_vtcore_history_rows(t)); fail_resize_calloc = 1; - ok = term_resize(t, (struct term_vector2i){ 8, 2 }); + ok = wsap_vtcore_resize(t, (struct wsap_vtcore_vector2i){ 8, 2 }); assert(!fail_resize_calloc); - assert(term_snapshot_update(s, t)); + assert(wsap_vtcore_snapshot_update(s, t)); printf("after failed height shrink: resize=%d height=%d top=%c cursor_y=%d history=%d\n", - ok, term_size(t).y, (char)term_snapshot_row(s, 0)[0].text, - term_cursor(t).pos.y, term_history_rows(t)); - failed |= ok || term_size(t).y != 4 || term_snapshot_row(s, 0)[0].text != 'A' || - term_cursor(t).pos.y != 3 || term_history_rows(t) != 0; - term_snapshot_free(s); - term_free(t); + ok, wsap_vtcore_size(t).y, (char)wsap_vtcore_snapshot_row(s, 0)[0].text, + wsap_vtcore_cursor(t).pos.y, wsap_vtcore_history_rows(t)); + failed |= ok || wsap_vtcore_size(t).y != 4 || wsap_vtcore_snapshot_row(s, 0)[0].text != 'A' || + wsap_vtcore_cursor(t).pos.y != 3 || wsap_vtcore_history_rows(t) != 0; + wsap_vtcore_snapshot_free(s); + wsap_vtcore_free(t); return failed ? 1 : 0; } diff --git a/tests/cross_test.sh b/tests/cross_test.sh index 6c0efa2..bc46a8e 100644 --- a/tests/cross_test.sh +++ b/tests/cross_test.sh @@ -1,8 +1,8 @@ #!/usr/bin/env bash -# The term core compiles as strict C11 for the platforms a host may embed +# The core compiles as strict C11 for the platforms a host may embed # it on. zig cc supplies the cross compilers. The aarch64 targets build the # NEON paths, and windows-gnu builds the Windows path of compat.h. The -# amalgamation, one term.c, compiles the same way. +# amalgamation, one wsap_vtcore.c, compiles the same way. set -euo pipefail root=${1:-$(dirname "$0")/..} cd "$root/src" @@ -15,10 +15,10 @@ status=0 for target in aarch64-linux-gnu x86_64-macos aarch64-macos x86_64-windows-gnu; do for src in *.c osc/*.c; do zig cc -target "$target" -std=c11 -O2 -Wall -Wextra -Wpedantic -Werror \ - -I. -I../include/term -c "$src" -o "$out/obj.o" || { echo "$target: $src fails" >&2; status=1; } + -I. -I../include/wsap_vtcore -c "$src" -o "$out/obj.o" || { echo "$target: $src fails" >&2; status=1; } done zig cc -target "$target" -std=c11 -O2 -Wall -Wextra -Wpedantic -Werror \ - -c "$out/amalgamation/term.c" -o "$out/obj.o" || + -c "$out/amalgamation/wsap_vtcore.c" -o "$out/obj.o" || { echo "$target: the amalgamation fails" >&2; status=1; } done exit $status diff --git a/tests/dcs_test.c b/tests/dcs_test.c index d9455be..c76b73b 100644 --- a/tests/dcs_test.c +++ b/tests/dcs_test.c @@ -14,11 +14,11 @@ static void respond(void *ud, const char *data, size_t len) response[len] = 0; response_len = len; } -static void write_seq(struct term *t, const char *s) +static void write_seq(struct wsap_vtcore *t, const char *s) { for (; *s; s++) tt_write(t, s, 1); } -static const char *row_text(struct term *t, int r, char *buf) +static const char *row_text(struct wsap_vtcore *t, int r, char *buf) { int n = 0; for (int c = 0; c < tt_cols(t); c++) @@ -27,18 +27,18 @@ static const char *row_text(struct term *t, int r, char *buf) buf[n] = 0; return buf; } -static bool row_is(struct term *t, int r, const char *want) +static bool row_is(struct wsap_vtcore *t, int r, const char *want) { - char got[TERM_MAX_COLS + 1]; + char got[WSAP_VTCORE_MAX_COLS + 1]; if (strcmp(row_text(t, r, got), want)) { fprintf(stderr, "row %d: got \"%s\" want \"%s\"\n", r, got, want); return false; } return true; } -static struct term *new_term(int cols, int rows) +static struct wsap_vtcore *new_term(int cols, int rows) { - struct term *t = tt_new_opts(cols, rows, &(struct term_callbacks){ .reply = respond }); + struct wsap_vtcore *t = tt_new_opts(cols, rows, &(struct wsap_vtcore_callbacks){ .reply = respond }); assert(t); response_len = 0; response[0] = 0; @@ -66,7 +66,7 @@ static void hex_encode(char *out, const char *s) *out = 0; } -static void assert_rqss(struct term *t, const char *spec, const char *payload) +static void assert_rqss(struct wsap_vtcore *t, const char *spec, const char *payload) { char req[128], want[256]; snprintf(req, sizeof(req), "\033P$q%s\033\\", spec); @@ -75,7 +75,7 @@ static void assert_rqss(struct term *t, const char *spec, const char *payload) write_seq(t, req); expect_response(want); } -static void assert_rqss_invalid(struct term *t, const char *spec) +static void assert_rqss_invalid(struct wsap_vtcore *t, const char *spec) { char req[128]; snprintf(req, sizeof(req), "\033P$q%s\033\\", spec); @@ -86,55 +86,55 @@ static void assert_rqss_invalid(struct term *t, const char *spec) static void test_decrqss_sgr(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); assert_rqss(t, "m", "m"); write_seq(t, "\033[1;31m"); assert_rqss(t, "m", "0;1;31m"); - term_free(t); + wsap_vtcore_free(t); t = new_term(80, 24); write_seq(t, "\033[4:3m"); assert_rqss(t, "m", "0;4:3m"); - term_free(t); + wsap_vtcore_free(t); t = new_term(80, 24); write_seq(t, "\033[38;2;10;20;30m"); assert_rqss(t, "m", "0;38:2:10:20:30m"); - term_free(t); + wsap_vtcore_free(t); } static void test_decrqss_margins_and_page(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); assert_rqss(t, "r", "1;24r"); assert_rqss(t, "t", "24t"); assert_rqss(t, "$|", "80$|"); assert_rqss(t, "*|", "24*|"); write_seq(t, "\033[3;10r"); assert_rqss(t, "r", "3;10r"); - term_free(t); + wsap_vtcore_free(t); t = new_term(80, 24); assert_rqss(t, "s", "1;80s"); write_seq(t, "\033[?69h\033[5;20s"); assert_rqss(t, "s", "5;20s"); - term_free(t); + wsap_vtcore_free(t); } static void test_decrqss_cursor_style(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); assert_rqss(t, " q", "1 q"); write_seq(t, "\033[5 q"); assert_rqss(t, " q", "5 q"); write_seq(t, "\033[4 q"); assert_rqss(t, " q", "4 q"); - term_free(t); + wsap_vtcore_free(t); } static void test_decrqss_misc(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); assert_rqss(t, "\"p", "64;1\"p"); assert_rqss(t, "\"q", "0\"q"); assert_rqss(t, "$}", "0$}"); @@ -142,12 +142,12 @@ static void test_decrqss_misc(void) assert_rqss(t, "*x", "0*x"); write_seq(t, "\033[2*x"); assert_rqss(t, "*x", "2*x"); - term_free(t); + wsap_vtcore_free(t); } static void test_decrqss_invalid(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); static const char *bad[] = { "){", ",|", ",}", ">0f", ">0m", ">0t", "z", "ABC", }; @@ -157,10 +157,10 @@ static void test_decrqss_invalid(void) response_len = 0; write_seq(t, "\033P$x\033\\"); expect_no_response(); - term_free(t); + wsap_vtcore_free(t); } -static void assert_tcap(struct term *t, const char *name, const char *value) +static void assert_tcap(struct wsap_vtcore *t, const char *name, const char *value) { char hn[128], hv[512], req[256], want[1024]; hex_encode(hn, name); @@ -174,10 +174,10 @@ static void assert_tcap(struct term *t, const char *name, const char *value) static void test_xtgettcap(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); assert_tcap(t, "kind", "\033[1;2B"); - assert_tcap(t, "TN", "term"); - assert_tcap(t, "name", "term"); + assert_tcap(t, "TN", "wsap_vtcore"); + assert_tcap(t, "name", "wsap_vtcore"); assert_tcap(t, "Co", "16777216"); assert_tcap(t, "colors", "16777216"); assert_tcap(t, "RGB", "8/8/8"); @@ -216,12 +216,12 @@ static void test_xtgettcap(void) assert_tcap(t, "kri", "\033[1;2A"); assert_tcap(t, "kxIN", "\033[I"); assert_tcap(t, "kxOUT", "\033[O"); - term_free(t); + wsap_vtcore_free(t); } static void test_xtgettcap_multi(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); char hk[16], htn[16], hb[16], hv[32], req[256], want[1024]; hex_encode(hk, "kind"); hex_encode(htn, "TN"); @@ -230,7 +230,7 @@ static void test_xtgettcap_multi(void) snprintf(req, sizeof(req), "\033P+q%s;%s\033\\", hk, htn); snprintf(want, sizeof(want), "\033P1+r%s=%s;%s=%s\033\\", - hk, hv, htn, "7465726d"); + hk, hv, htn, "777361705f7674636f7265"); response_len = 0; write_seq(t, req); expect_response(want); @@ -247,12 +247,12 @@ static void test_xtgettcap_multi(void) response_len = 0; write_seq(t, req); expect_response(want); - term_free(t); + wsap_vtcore_free(t); } static void test_xtgettcap_malformed(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); static const char *bad[] = {"6b696", "zz", "6g", "6b69 6e"}; for (size_t i = 0; i < sizeof(bad) / sizeof(bad[0]); i++) { char req[128]; @@ -264,12 +264,12 @@ static void test_xtgettcap_malformed(void) assert(response[response_len - 2] == '\033'); assert(response[response_len - 1] == '\\'); } - term_free(t); + wsap_vtcore_free(t); } static void test_xtsettcap(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); char hn[32]; hex_encode(hn, "myterm"); char req[128]; @@ -278,12 +278,12 @@ static void test_xtsettcap(void) write_seq(t, req); expect_no_response(); assert_tcap(t, "TN", "myterm"); - term_free(t); + wsap_vtcore_free(t); } static void test_xtgetxres(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); char hn[64], req[128], want[256]; hex_encode(hn, "allowTcapOps"); snprintf(req, sizeof(req), "\033P+Q%s\033\\", hn); @@ -291,40 +291,40 @@ static void test_xtgetxres(void) response_len = 0; write_seq(t, req); expect_response(want); - term_free(t); + wsap_vtcore_free(t); } static void test_decrsps_cir(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); write_seq(t, "\033P1$t3;5;1;I;@;H;00;@;BBBB\033\\"); assert(tt_cursor_y(t) == 2 && tt_cursor_x(t) == 4); write_seq(t, "Z"); - const struct term_cell *cell = tt_cell(t, 4, 2); + const struct wsap_vtcore_cell *cell = tt_cell(t, 4, 2); assert(cell->text == 'Z'); - assert(cell->attrs & TERM_ATTR_BOLD); - assert(cell->fg == TERM_COLOR_BG); - term_free(t); + assert(cell->attrs & WSAP_VTCORE_ATTR_BOLD); + assert(cell->fg == WSAP_VTCORE_COLOR_BG); + wsap_vtcore_free(t); t = new_term(80, 24); write_seq(t, "\033P1$t3;5;1;@;@;H;00;@;BBBB\033\\"); write_seq(t, "\033[1;80Hab"); assert(tt_cell(t, 79, 0)->text == 'a'); assert(tt_cell(t, 0, 1)->text == 'b'); - term_free(t); + wsap_vtcore_free(t); t = new_term(80, 24); write_seq(t, "\033[5;15r"); write_seq(t, "\033P1$t3;5;1;@;@;I;00;@;BBBB\033\\"); write_seq(t, "\033[1;1H"); assert(tt_cursor_y(t) == 4 && tt_cursor_x(t) == 0); - term_free(t); + wsap_vtcore_free(t); } static void test_decrsps_tabsr(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); write_seq(t, "\033P2$t4/10\033\\"); write_seq(t, "\033[1;1H"); write_seq(t, "\t"); @@ -333,26 +333,26 @@ static void test_decrsps_tabsr(void) assert(tt_cursor_x(t) == 9); write_seq(t, "\t"); assert(tt_cursor_x(t) == 79); - term_free(t); + wsap_vtcore_free(t); } static void test_synchronized_output(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); write_seq(t, "\033P=1s\033\\"); - assert(term_modes(t).synchronized); + assert(wsap_vtcore_modes(t).synchronized); write_seq(t, "\033P=2s\033\\"); - assert(!term_modes(t).synchronized); + assert(!wsap_vtcore_modes(t).synchronized); write_seq(t, "\033P=10s\033\\"); - assert(!term_modes(t).synchronized); + assert(!wsap_vtcore_modes(t).synchronized); write_seq(t, "\033P=1;s\033\\"); - assert(term_modes(t).synchronized); + assert(wsap_vtcore_modes(t).synchronized); write_seq(t, "\033P=xs\033\\"); - assert(term_modes(t).synchronized); + assert(wsap_vtcore_modes(t).synchronized); write_seq(t, "\033P=2;s\033\\"); - assert(!term_modes(t).synchronized); - term_free(t); + assert(!wsap_vtcore_modes(t).synchronized); + wsap_vtcore_free(t); } static void test_ignored_dcs(void) @@ -367,36 +367,36 @@ static void test_ignored_dcs(void) "\033P?~junk\033\\", }; for (size_t i = 0; i < sizeof(seqs) / sizeof(seqs[0]); i++) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); write_seq(t, "A"); write_seq(t, seqs[i]); write_seq(t, "B"); assert(row_is(t, 0, "AB")); assert(tt_cursor_x(t) == 2 && tt_cursor_y(t) == 0); expect_no_response(); - term_free(t); + wsap_vtcore_free(t); } } static void test_xtversion(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); response_len = 0; write_seq(t, "\033[>0q"); - expect_response("\033P>|term\033\\"); - term_free(t); + expect_response("\033P>|wsap_vtcore\033\\"); + wsap_vtcore_free(t); } -/* term_options.name feeds XTVERSION and the TN and name capabilities. */ +/* wsap_vtcore_options.name feeds XTVERSION and the TN and name capabilities. */ static void test_host_name(void) { - struct term_options opt = { + struct wsap_vtcore_options opt = { .size = { .x = 80, .y = 24 }, .scrollback = TEST_SCROLLBACK, .name = "myterm", .callbacks = { .reply = respond }, }; - struct term *t = term_new(&opt); + struct wsap_vtcore *t = wsap_vtcore_new(&opt); assert(t); response_len = 0; write_seq(t, "\033[>0q"); @@ -412,28 +412,28 @@ static void test_host_name(void) response_len = 0; write_seq(t, "\033[>0q"); expect_response("\033P>|myterm\033\\"); - term_free(t); + wsap_vtcore_free(t); /* NULL and "" both select the default. */ opt.name = ""; - t = term_new(&opt); + t = wsap_vtcore_new(&opt); assert(t); response_len = 0; write_seq(t, "\033[>0q"); - expect_response("\033P>|term\033\\"); - term_free(t); + expect_response("\033P>|wsap_vtcore\033\\"); + wsap_vtcore_free(t); opt.name = NULL; - t = term_new(&opt); + t = wsap_vtcore_new(&opt); assert(t); response_len = 0; write_seq(t, "\033[>0q"); - expect_response("\033P>|term\033\\"); - term_free(t); + expect_response("\033P>|wsap_vtcore\033\\"); + wsap_vtcore_free(t); } static void test_bel_terminator(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); response_len = 0; write_seq(t, "\033P+q6b696e64\007"); expect_response("\033P1+r6b696e64=1b5b313b3242\033\\"); @@ -441,7 +441,7 @@ static void test_bel_terminator(void) response_len = 0; write_seq(t, "\033P$qm\007"); expect_response("\033P1$rm\033\\"); - term_free(t); + wsap_vtcore_free(t); } /* A query far past the old 256-byte DCS buffer is answered in full, @@ -464,7 +464,7 @@ static void test_dcs_long_query(void) snprintf(want + wn, sizeof(want) - (size_t)wn, "\033\\"); assert(strlen(req) > 256); - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); write_seq(t, req); expect_response(want); response_len = 0; @@ -472,26 +472,26 @@ static void test_dcs_long_query(void) expect_response(want); write_seq(t, "X"); assert(row_is(t, 0, "X")); - term_free(t); + wsap_vtcore_free(t); } static void test_dcs_abort_c0(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); response_len = 0; write_seq(t, "\033P+q6b69\nX"); expect_no_response(); assert(row_is(t, 1, "X")); - term_free(t); + wsap_vtcore_free(t); } static void test_dcs_abort_esc(void) { - struct term *t = new_term(80, 24); + struct wsap_vtcore *t = new_term(80, 24); response_len = 0; write_seq(t, "\033P$qm\033[5n"); expect_response("\033[0n"); - term_free(t); + wsap_vtcore_free(t); } int main(void) diff --git a/tests/extern/README.md b/tests/extern/README.md index 2a52e29..e1aa03d 100644 --- a/tests/extern/README.md +++ b/tests/extern/README.md @@ -27,7 +27,7 @@ Kitty parser test suite against it via a Python compatibility layer. - `kitty_parser.py` — Pure-Python VT parser that emits Kitty-style callback events while feeding every byte to the C terminal via `screen.write()`. Maintains state across calls for split-write (threading) tests. -- `screen.py` — `ctypes` wrapper around `libterm.so` providing the Kitty +- `screen.py` — `ctypes` wrapper around the bridge `libkitty_bridge.so` providing the Kitty `Screen`, `Cursor`, `Line`, `CellCursor`, and `Callbacks` API. - `fast_data_types.py` — Pure-Python replacements for Kitty's C-extension helpers (base64, UTF-8 decode, constants). diff --git a/tests/extern/kitty/.gitignore b/tests/extern/kitty/.gitignore index 79a6f1c..42be567 100644 --- a/tests/extern/kitty/.gitignore +++ b/tests/extern/kitty/.gitignore @@ -1,2 +1,2 @@ __pycache__/ -libterm.so +libkitty_bridge.so diff --git a/tests/extern/kitty/screen.py b/tests/extern/kitty/screen.py index a3336d8..1b66234 100644 --- a/tests/extern/kitty/screen.py +++ b/tests/extern/kitty/screen.py @@ -1,9 +1,9 @@ """ctypes wrapper providing the Kitty ``Screen`` API on top of our C terminal. -The shared library ``libterm.so`` is loaded via :mod:`ctypes`. Python calls -only the ``kitty_*`` functions of ``screen_bridge.c``, which wrap the public -API (declared in ``src/term/term.h``). Python classes on top of them match the -subset of Kitty's test API used by ``parser.py``. +The bridge library ``libkitty_bridge.so`` is loaded via :mod:`ctypes`. Python +calls only the ``kitty_*`` functions of ``screen_bridge.c``, which wrap the +public API (declared in ``include/wsap_vtcore/wsap_vtcore.h``). Python classes +on top of them match the subset of Kitty's test API used by ``parser.py``. """ import ctypes @@ -15,7 +15,7 @@ import os _lib = ctypes.CDLL(os.environ.get('WSAP_KITTY_LIB', os.path.join(os.path.dirname(__file__), 'libkitty_bridge.so'))) -# struct term_cell { uint32_t text, fg, bg; uint16_t attrs; uint8_t width, reserved; } +# struct wsap_vtcore_cell { uint32_t text, fg, bg; uint16_t attrs; uint8_t width, reserved; } class TermCell(ctypes.Structure): _fields_ = [ ('text', ctypes.c_uint32), @@ -65,19 +65,19 @@ for _name, _type in { # Constants # --------------------------------------------------------------------------- -TERM_DEFAULT_FG = 0xFFFFFFFF -TERM_DEFAULT_BG = 0xFF1E1E2E +WSAP_VTCORE_DEFAULT_FG = 0xFFFFFFFF +WSAP_VTCORE_DEFAULT_BG = 0xFF1E1E2E -# Cell attributes (must match enum term_attr in term.h) -TERM_ATTR_BOLD = 1 << 0 -TERM_ATTR_ITALIC = 1 << 1 -TERM_ATTR_FAINT = 1 << 10 -TERM_ATTR_STRIKE = 1 << 3 -TERM_ATTR_OVERLINE = 1 << 4 -TERM_ATTR_LINK = 1 << 15 -TERM_ATTR_EMOJI = 1 << 5 -TERM_ATTR_TEXT = 1 << 6 -TERM_UNDERLINE_FLAGS = (1 << 2, 1 << 11, 1 << 12, 1 << 13, 1 << 14) +# Cell attributes (must match enum wsap_vtcore_attr in wsap_vtcore.h) +WSAP_VTCORE_ATTR_BOLD = 1 << 0 +WSAP_VTCORE_ATTR_ITALIC = 1 << 1 +WSAP_VTCORE_ATTR_FAINT = 1 << 10 +WSAP_VTCORE_ATTR_STRIKE = 1 << 3 +WSAP_VTCORE_ATTR_OVERLINE = 1 << 4 +WSAP_VTCORE_ATTR_LINK = 1 << 15 +WSAP_VTCORE_ATTR_EMOJI = 1 << 5 +WSAP_VTCORE_ATTR_TEXT = 1 << 6 +WSAP_VTCORE_UNDERLINE_FLAGS = (1 << 2, 1 << 11, 1 << 12, 1 << 13, 1 << 14) # The longest grapheme cluster that a cell's text is read with. _CLUSTER_CAP = 32 @@ -105,7 +105,7 @@ _lib.kitty_screen_cell_is_tab.argtypes = [ctypes.c_void_p, ctypes.c_int, ctypes. _lib.kitty_screen_cell_is_tab.restype = ctypes.c_bool # ANSI color table from escape.c — used for reverse-mapping to Kitty indices. -# Must match the built-in default palette in src/term/palette.c. +# Must match the built-in default palette in src/palette.c. _ANSI_COLORS = [ 0xFF585B70, 0xFFCC6666, 0xFFB5BD68, 0xFFF0C674, 0xFF81A2BE, 0xFFB294BB, 0xFF8ABEB7, 0xFFC5C8C6, @@ -135,7 +135,7 @@ def _build_color_table(): _COLOR_TO_KITTY = _build_color_table() -TERM_COLOR_REF = 0x01000000 +WSAP_VTCORE_COLOR_REF = 0x01000000 def _convert_color(color): @@ -149,10 +149,10 @@ def _convert_color(color): index<<8|1 = indexed (0-255) r<<24|g<<16|b<<8|2 = RGB """ - if (color >> 24) == (TERM_COLOR_REF >> 24): + if (color >> 24) == (WSAP_VTCORE_COLOR_REF >> 24): slot = color & 0x1FF return 0 if slot >= 0x100 else (slot << 8) | 1 - if color == TERM_DEFAULT_FG or color == TERM_DEFAULT_BG: + if color == WSAP_VTCORE_DEFAULT_FG or color == WSAP_VTCORE_DEFAULT_BG: return 0 kitty = _COLOR_TO_KITTY.get(color) if kitty is not None: @@ -251,15 +251,15 @@ class CellCursor: @property def bold(self): - return bool(self._cell.attrs & TERM_ATTR_BOLD) + return bool(self._cell.attrs & WSAP_VTCORE_ATTR_BOLD) @property def italic(self): - return bool(self._cell.attrs & TERM_ATTR_ITALIC) + return bool(self._cell.attrs & WSAP_VTCORE_ATTR_ITALIC) @property def dim(self): - return bool(self._cell.attrs & TERM_ATTR_FAINT) + return bool(self._cell.attrs & WSAP_VTCORE_ATTR_FAINT) @property def reverse(self): @@ -269,13 +269,13 @@ class CellCursor: @property def strikethrough(self): - return bool(self._cell.attrs & TERM_ATTR_STRIKE) + return bool(self._cell.attrs & WSAP_VTCORE_ATTR_STRIKE) @property def decoration(self): - # enum term_underline uses Kitty's numbers: 0=none, 1=straight, + # enum wsap_vtcore_underline uses Kitty's numbers: 0=none, 1=straight, # 2=double, 3=curly, 4=dotted, 5=dashed. - return next((i for i, flag in enumerate(TERM_UNDERLINE_FLAGS, 1) + return next((i for i, flag in enumerate(WSAP_VTCORE_UNDERLINE_FLAGS, 1) if self._cell.attrs & flag), 0) @property diff --git a/tests/extern/kitty/screen_bridge.c b/tests/extern/kitty/screen_bridge.c index 50f86a7..c307c1a 100644 --- a/tests/extern/kitty/screen_bridge.c +++ b/tests/extern/kitty/screen_bridge.c @@ -1,87 +1,87 @@ /* Test-only entry points for the Kitty screen wrapper in screen.py. * Python calls only these functions, so it needs no struct layouts other - * than the public struct term_cell. The kitty_screen_* accessors read - * properties that term.h does not expose. They compile against the current + * than the public struct wsap_vtcore_cell. The kitty_screen_* accessors read + * properties that wsap_vtcore.h does not expose. They compile against the current * terminal layout rather than duplicating byte offsets in Python. */ #include "internal.h" #include "screen.h" typedef void (*kitty_reply_fn)(void *ud, const char *bytes, size_t len); -struct term *kitty_term_new(int cols, int rows, kitty_reply_fn reply, void *ud) +struct wsap_vtcore *kitty_term_new(int cols, int rows, kitty_reply_fn reply, void *ud) { - return term_new(&(struct term_options){ + return wsap_vtcore_new(&(struct wsap_vtcore_options){ .size = { .x = cols, .y = rows }, .callbacks = { .ud = ud, .reply = reply }, }); } /* One snapshot serves every cell read. */ -static struct term_snapshot *snap; +static struct wsap_vtcore_snapshot *snap; -void kitty_term_free(struct term *t) +void kitty_term_free(struct wsap_vtcore *t) { /* A new terminal can get the address of the freed one. The snapshot * would then keep its rows, so it goes away too. */ - term_snapshot_free(snap); + wsap_vtcore_snapshot_free(snap); snap = NULL; - term_free(t); + wsap_vtcore_free(t); } -void kitty_term_write(struct term *t, const char *bytes, size_t len) +void kitty_term_write(struct wsap_vtcore *t, const char *bytes, size_t len) { - term_feed(t, bytes, len, 0); + wsap_vtcore_feed(t, bytes, len, 0); } -bool kitty_term_resize(struct term *t, int cols, int rows) +bool kitty_term_resize(struct wsap_vtcore *t, int cols, int rows) { - return term_resize(t, (struct term_vector2i){ .x = cols, .y = rows }); + return wsap_vtcore_resize(t, (struct wsap_vtcore_vector2i){ .x = cols, .y = rows }); } -int kitty_term_cols(struct term *t) { return term_size(t).x; } -int kitty_term_rows(struct term *t) { return term_size(t).y; } -int kitty_term_cursor_x(struct term *t) { return term_cursor(t).pos.x; } -int kitty_term_cursor_y(struct term *t) { return term_cursor(t).pos.y; } -int kitty_term_cursor_style(struct term *t) { return (int)term_cursor(t).style; } -bool kitty_term_cursor_blink(struct term *t) { return term_cursor(t).blink; } -bool kitty_term_application_cursor(struct term *t) { return term_modes(t).app_cursor; } +int kitty_term_cols(struct wsap_vtcore *t) { return wsap_vtcore_size(t).x; } +int kitty_term_rows(struct wsap_vtcore *t) { return wsap_vtcore_size(t).y; } +int kitty_term_cursor_x(struct wsap_vtcore *t) { return wsap_vtcore_cursor(t).pos.x; } +int kitty_term_cursor_y(struct wsap_vtcore *t) { return wsap_vtcore_cursor(t).pos.y; } +int kitty_term_cursor_style(struct wsap_vtcore *t) { return (int)wsap_vtcore_cursor(t).style; } +bool kitty_term_cursor_blink(struct wsap_vtcore *t) { return wsap_vtcore_cursor(t).blink; } +bool kitty_term_application_cursor(struct wsap_vtcore *t) { return wsap_vtcore_modes(t).app_cursor; } /* Update the snapshot from the live screen, as a renderer reads it. * Returns NULL when the cell is out of range or memory runs out. */ -static struct term_snapshot *cell_snapshot(struct term *t, int col, int row) +static struct wsap_vtcore_snapshot *cell_snapshot(struct wsap_vtcore *t, int col, int row) { - struct term_vector2i size = term_size(t); + struct wsap_vtcore_vector2i size = wsap_vtcore_size(t); if (col < 0 || col >= size.x || row < 0 || row >= size.y) return NULL; if (!snap) - snap = term_snapshot_new(); - term_scroll_to(t, 0); - if (!snap || !term_snapshot_update(snap, t)) + snap = wsap_vtcore_snapshot_new(); + wsap_vtcore_scroll_to(t, 0); + if (!snap || !wsap_vtcore_snapshot_update(snap, t)) return NULL; return snap; } -bool kitty_term_cell(struct term *t, int col, int row, struct term_cell *out) +bool kitty_term_cell(struct wsap_vtcore *t, int col, int row, struct wsap_vtcore_cell *out) { - struct term_snapshot *s = cell_snapshot(t, col, row); + struct wsap_vtcore_snapshot *s = cell_snapshot(t, col, row); if (!s) return false; - *out = term_snapshot_row(s, row)[col]; + *out = wsap_vtcore_snapshot_row(s, row)[col]; return true; } /* The code points of a cell's text: one, or a whole grapheme cluster. * Returns the number of code points and writes at most cap of them. */ -int kitty_term_cell_text(struct term *t, int col, int row, uint32_t *cps, int cap) +int kitty_term_cell_text(struct wsap_vtcore *t, int col, int row, uint32_t *cps, int cap) { - struct term_snapshot *s = cell_snapshot(t, col, row); + struct wsap_vtcore_snapshot *s = cell_snapshot(t, col, row); if (!s) return 0; - return term_snapshot_cluster(s, term_snapshot_row(s, row)[col].text, cps, cap); + return wsap_vtcore_snapshot_cluster(s, wsap_vtcore_snapshot_row(s, row)[col].text, cps, cap); } #define PROPERTY(type, name) \ - type kitty_screen_##name(struct term *t) { return t->name; } + type kitty_screen_##name(struct wsap_vtcore *t) { return t->name; } PROPERTY(int, scroll_top) PROPERTY(int, scroll_bottom) @@ -94,20 +94,20 @@ PROPERTY(bool, strike) PROPERTY(bool, inverse) PROPERTY(uint8_t, underline) -int kitty_screen_row_length(struct term *t, int row) +int kitty_screen_row_length(struct wsap_vtcore *t, int row) { if (!t || row < 0 || row >= t->rows) return 0; - const struct srow *r = term_row(t, row); + const struct srow *r = wsap_vtcore_row(t, row); return r ? (int)r->len : 0; } /* A tab stores a marker cell that a snapshot shows as a blank. Kitty keeps * the tab in its line text, so the wrapper asks for the marker. */ -bool kitty_screen_cell_is_tab(struct term *t, int col, int row) +bool kitty_screen_cell_is_tab(struct wsap_vtcore *t, int col, int row) { if (col < 0 || col >= t->cols || row < 0 || row >= t->rows) return false; - term_scroll_to(t, 0); - const struct cell *cells = term_screen_view_row(t, row); + wsap_vtcore_scroll_to(t, 0); + const struct cell *cells = wsap_vtcore_screen_view_row(t, row); return cells && cells[col].c == '\t'; } diff --git a/tests/gstore_test.c b/tests/gstore_test.c index ea582f3..1ffeaad 100644 --- a/tests/gstore_test.c +++ b/tests/gstore_test.c @@ -10,8 +10,8 @@ */ #include "gstore.h" #include "internal.h" -#include "term/term.h" -#include "term/unicode/utf8.h" +#include "wsap_vtcore/wsap_vtcore.h" +#include "wsap_vtcore/unicode/utf8.h" #include <assert.h> #include <stdio.h> @@ -20,151 +20,151 @@ static void test_direct_unit(void) { - struct gstore *g = term_gstore_new(NULL); + struct gstore *g = wsap_vtcore_gstore_new(NULL); assert(g != NULL); - assert(term_gstore_count(g) == 0); + assert(wsap_vtcore_gstore_count(g) == 0); /* Single code point returns the code point itself. */ uint32_t single = 'A'; - assert(term_gstore_intern(g, &single, 1) == 'A'); - assert(term_gstore_count(g) == 0); + assert(wsap_vtcore_gstore_intern(g, &single, 1) == 'A'); + assert(wsap_vtcore_gstore_count(g) == 0); /* Cluster returns a handle. */ uint32_t c1[2] = { 'e', 0x0301 }; - uint32_t h1 = term_gstore_intern(g, c1, 2); - assert(term_grapheme_is_handle(h1)); - assert(term_gstore_count(g) == 1); + uint32_t h1 = wsap_vtcore_gstore_intern(g, c1, 2); + assert(wsap_vtcore_grapheme_is_handle(h1)); + assert(wsap_vtcore_gstore_count(g) == 1); /* Identical cluster deduplicates to the same handle. */ - uint32_t h1_dup = term_gstore_intern(g, c1, 2); + uint32_t h1_dup = wsap_vtcore_gstore_intern(g, c1, 2); assert(h1_dup == h1); - assert(term_gstore_count(g) == 1); + assert(wsap_vtcore_gstore_count(g) == 1); /* Different cluster gets a distinct handle. */ uint32_t c2[2] = { 'a', 0x0300 }; - uint32_t h2 = term_gstore_intern(g, c2, 2); - assert(term_grapheme_is_handle(h2)); + uint32_t h2 = wsap_vtcore_gstore_intern(g, c2, 2); + assert(wsap_vtcore_grapheme_is_handle(h2)); assert(h2 != h1); - assert(term_gstore_count(g) == 2); + assert(wsap_vtcore_gstore_count(g) == 2); /* Expand both handles. */ - uint32_t out[TERM_GRAPHEME_MAX_LEN] = {0}; - int n = term_gstore_expand(g, h1, out, TERM_GRAPHEME_MAX_LEN); + uint32_t out[WSAP_VTCORE_GRAPHEME_MAX_LEN] = {0}; + int n = wsap_vtcore_gstore_expand(g, h1, out, WSAP_VTCORE_GRAPHEME_MAX_LEN); assert(n == 2); assert(out[0] == 'e' && out[1] == 0x0301); - n = term_gstore_expand(g, h2, out, TERM_GRAPHEME_MAX_LEN); + n = wsap_vtcore_gstore_expand(g, h2, out, WSAP_VTCORE_GRAPHEME_MAX_LEN); assert(n == 2); assert(out[0] == 'a' && out[1] == 0x0300); /* Sweep with h1 marked and h2 unmarked. */ - term_gstore_mark(g, h1); - term_gstore_sweep(g, NULL); - assert(term_gstore_count(g) == 1); + wsap_vtcore_gstore_mark(g, h1); + wsap_vtcore_gstore_sweep(g, NULL); + assert(wsap_vtcore_gstore_count(g) == 1); /* h1 is still valid. */ - n = term_gstore_expand(g, h1, out, TERM_GRAPHEME_MAX_LEN); + n = wsap_vtcore_gstore_expand(g, h1, out, WSAP_VTCORE_GRAPHEME_MAX_LEN); assert(n == 2); assert(out[0] == 'e' && out[1] == 0x0301); /* h2 was reclaimed. */ - n = term_gstore_expand(g, h2, out, TERM_GRAPHEME_MAX_LEN); + n = wsap_vtcore_gstore_expand(g, h2, out, WSAP_VTCORE_GRAPHEME_MAX_LEN); assert(n == 1 && out[0] == 0xFFFD); /* New cluster can reuse the reclaimed slot. */ uint32_t c3[3] = { 'o', 0x0308, 0x0301 }; - uint32_t h3 = term_gstore_intern(g, c3, 3); - assert(term_grapheme_is_handle(h3)); - assert(term_gstore_count(g) == 2); - n = term_gstore_expand(g, h3, out, TERM_GRAPHEME_MAX_LEN); + uint32_t h3 = wsap_vtcore_gstore_intern(g, c3, 3); + assert(wsap_vtcore_grapheme_is_handle(h3)); + assert(wsap_vtcore_gstore_count(g) == 2); + n = wsap_vtcore_gstore_expand(g, h3, out, WSAP_VTCORE_GRAPHEME_MAX_LEN); assert(n == 3); assert(out[0] == 'o' && out[1] == 0x0308 && out[2] == 0x0301); - term_gstore_free(g); + wsap_vtcore_gstore_free(g); } static void test_two_terminals_isolation(void) { - struct term_options opt = { .size = { .x = 20, .y = 4 } }; - struct term *t1 = term_new(&opt); - struct term *t2 = term_new(&opt); + struct wsap_vtcore_options opt = { .size = { .x = 20, .y = 4 } }; + struct wsap_vtcore *t1 = wsap_vtcore_new(&opt); + struct wsap_vtcore *t2 = wsap_vtcore_new(&opt); assert(t1 && t2); const char *cluster_text = "e\xcc\x81"; /* 'e' with acute */ - term_feed(t1, cluster_text, strlen(cluster_text), 0); - term_feed(t2, cluster_text, strlen(cluster_text), 0); + wsap_vtcore_feed(t1, cluster_text, strlen(cluster_text), 0); + wsap_vtcore_feed(t2, cluster_text, strlen(cluster_text), 0); /* Free terminal 1. */ - term_free(t1); + wsap_vtcore_free(t1); /* Terminal 2 must still expand its cluster correctly. */ - struct term_snapshot *snap = term_snapshot_new(); + struct wsap_vtcore_snapshot *snap = wsap_vtcore_snapshot_new(); assert(snap); - assert(term_snapshot_update(snap, t2)); + assert(wsap_vtcore_snapshot_update(snap, t2)); - const struct term_cell *row = term_snapshot_row(snap, 0); - assert(row[0].text & TERM_TEXT_CLUSTER); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(snap, 0); + assert(row[0].text & WSAP_VTCORE_TEXT_CLUSTER); - uint32_t cps[TERM_GRAPHEME_MAX_LEN] = {0}; - int n = term_snapshot_cluster(snap, row[0].text, cps, TERM_GRAPHEME_MAX_LEN); + uint32_t cps[WSAP_VTCORE_GRAPHEME_MAX_LEN] = {0}; + int n = wsap_vtcore_snapshot_cluster(snap, row[0].text, cps, WSAP_VTCORE_GRAPHEME_MAX_LEN); assert(n == 2); assert(cps[0] == 'e' && cps[1] == 0x0301); - term_snapshot_free(snap); - term_free(t2); + wsap_vtcore_snapshot_free(snap); + wsap_vtcore_free(t2); } static void test_screen_clusters_survive_sweep(void) { - struct term_options opt = { .size = { .x = 40, .y = 10 }, .scrollback = 10 }; - struct term *t = term_new(&opt); + struct wsap_vtcore_options opt = { .size = { .x = 40, .y = 10 }, .scrollback = 10 }; + struct wsap_vtcore *t = wsap_vtcore_new(&opt); assert(t); /* Write 5 clusters on the top row. */ - term_feed(t, "a\xcc\x80" "b\xcc\x81" "c\xcc\x82" "d\xcc\x83" "e\xcc\x84", 15, 0); + wsap_vtcore_feed(t, "a\xcc\x80" "b\xcc\x81" "c\xcc\x82" "d\xcc\x83" "e\xcc\x84", 15, 0); /* Write ephemeral clusters on row 1, then overwrite them. */ for (int i = 0; i < 50; i++) { - term_feed(t, "\033[2;1H\033[2K", 8, 0); + wsap_vtcore_feed(t, "\033[2;1H\033[2K", 8, 0); char buf[32]; int len = snprintf(buf, sizeof(buf), "z\xcc\x80\xcc\x81%d", i); - term_feed(t, buf, (size_t)len, 0); + wsap_vtcore_feed(t, buf, (size_t)len, 0); } - term_feed(t, "\033[2;1H\033[2K", 8, 0); + wsap_vtcore_feed(t, "\033[2;1H\033[2K", 8, 0); /* Explicit sweep. The clusters on row 0 are on screen and must survive. */ - term_gstore_sweep(t->gstore, t); + wsap_vtcore_gstore_sweep(t->gstore, t); - struct term_snapshot *snap = term_snapshot_new(); + struct wsap_vtcore_snapshot *snap = wsap_vtcore_snapshot_new(); assert(snap); - assert(term_snapshot_update(snap, t)); + assert(wsap_vtcore_snapshot_update(snap, t)); /* Row 0 of screen has "a\xcc\x80...". */ - const struct term_cell *row = term_snapshot_row(snap, 0); - assert(row[0].text & TERM_TEXT_CLUSTER); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(snap, 0); + assert(row[0].text & WSAP_VTCORE_TEXT_CLUSTER); - uint32_t cps[TERM_GRAPHEME_MAX_LEN] = {0}; - int n = term_snapshot_cluster(snap, row[0].text, cps, TERM_GRAPHEME_MAX_LEN); + uint32_t cps[WSAP_VTCORE_GRAPHEME_MAX_LEN] = {0}; + int n = wsap_vtcore_snapshot_cluster(snap, row[0].text, cps, WSAP_VTCORE_GRAPHEME_MAX_LEN); assert(n == 2); assert(cps[0] == 'a' && cps[1] == 0x0300); - n = term_snapshot_cluster(snap, row[1].text, cps, TERM_GRAPHEME_MAX_LEN); + n = wsap_vtcore_snapshot_cluster(snap, row[1].text, cps, WSAP_VTCORE_GRAPHEME_MAX_LEN); assert(n == 2); assert(cps[0] == 'b' && cps[1] == 0x0301); - n = term_snapshot_cluster(snap, row[2].text, cps, TERM_GRAPHEME_MAX_LEN); + n = wsap_vtcore_snapshot_cluster(snap, row[2].text, cps, WSAP_VTCORE_GRAPHEME_MAX_LEN); assert(n == 2); assert(cps[0] == 'c' && cps[1] == 0x0302); - term_snapshot_free(snap); - term_free(t); + wsap_vtcore_snapshot_free(snap); + wsap_vtcore_free(t); } static void test_more_than_65536_clusters(void) { /* Bounded history so old lines scroll out. */ - struct term_options opt = { .size = { .x = 80, .y = 24 }, .scrollback = 10 }; - struct term *t = term_new(&opt); + struct wsap_vtcore_options opt = { .size = { .x = 80, .y = 24 }, .scrollback = 10 }; + struct wsap_vtcore *t = wsap_vtcore_new(&opt); assert(t); /* @@ -183,37 +183,37 @@ static void test_more_than_65536_clusters(void) size_t len = 0; buf[len++] = base; - len += (size_t)term_utf8_encode(cp1, buf + len); - len += (size_t)term_utf8_encode(cp2, buf + len); + len += (size_t)wsap_vtcore_utf8_encode(cp1, buf + len); + len += (size_t)wsap_vtcore_utf8_encode(cp2, buf + len); buf[len++] = '\r'; buf[len++] = '\n'; - term_feed(t, buf, len, 0); + wsap_vtcore_feed(t, buf, len, 0); total++; } assert(total >= 65536); /* Verify the latest cluster on screen reads back correctly. */ - struct term_snapshot *snap = term_snapshot_new(); + struct wsap_vtcore_snapshot *snap = wsap_vtcore_snapshot_new(); assert(snap); - assert(term_snapshot_update(snap, t)); + assert(wsap_vtcore_snapshot_update(snap, t)); - struct term_cursor c = term_cursor(t); + struct wsap_vtcore_cursor c = wsap_vtcore_cursor(t); int y = c.pos.y > 0 ? c.pos.y - 1 : 0; - const struct term_cell *row = term_snapshot_row(snap, y); - assert(row[0].text & TERM_TEXT_CLUSTER); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(snap, y); + assert(row[0].text & WSAP_VTCORE_TEXT_CLUSTER); - uint32_t cps[TERM_GRAPHEME_MAX_LEN] = {0}; - int n = term_snapshot_cluster(snap, row[0].text, cps, TERM_GRAPHEME_MAX_LEN); + uint32_t cps[WSAP_VTCORE_GRAPHEME_MAX_LEN] = {0}; + int n = wsap_vtcore_snapshot_cluster(snap, row[0].text, cps, WSAP_VTCORE_GRAPHEME_MAX_LEN); assert(n == 3); /* Live cluster count must be small (only bounded screen and history). */ - uint32_t count = term_gstore_count(t->gstore); + uint32_t count = wsap_vtcore_gstore_count(t->gstore); assert(count < 2000); - term_snapshot_free(snap); - term_free(t); + wsap_vtcore_snapshot_free(snap); + wsap_vtcore_free(t); } int main(void) diff --git a/tests/header_test.sh b/tests/header_test.sh index 9fd1041..299a950 100644 --- a/tests/header_test.sh +++ b/tests/header_test.sh @@ -1,6 +1,6 @@ #!/usr/bin/env bash -# A host includes <term/term.h> and nothing else. The package puts only the -# parent of term/ on the include path. The headers compile alone as strict +# A host includes <wsap_vtcore/wsap_vtcore.h> and nothing else. The package puts only the +# parent of wsap_vtcore/ on the include path. The headers compile alone as strict # C11 and as C++. set -euo pipefail cd "${1:-$(dirname "$0")/..}" @@ -22,18 +22,18 @@ check() { fi } -check term.h <<'EOF' -#include <term/term.h> +check wsap_vtcore.h <<'EOF' +#include <wsap_vtcore/wsap_vtcore.h> EOF # Apple headers define wide before a host includes the Unicode API. check "unicode/width.h: conflicts with host types" <<'EOF' typedef struct wide { int value; } wide; -#include <term/unicode/width.h> +#include <wsap_vtcore/unicode/width.h> EOF -# A host that uses the names the Unicode API had before the term_ and -# TERM_ prefixes. The API must not clash with them in either order. +# A host that uses the names the Unicode API had before the wsap_vtcore_ and +# WSAP_VTCORE_ prefixes. The API must not clash with them in either order. check "unicode API: host names declared first" <<'EOF' int unicode_width(int); static int in_ranges; @@ -45,9 +45,9 @@ struct unicode_range { int lo; }; #define IN_TABLE 1 #define UNICODE_DATA_VERSION "host" #define UTF_8_H -#include <term/unicode/utf8.h> -#include <term/unicode/width.h> -#include <term/unicode/grapheme.h> +#include <wsap_vtcore/unicode/utf8.h> +#include <wsap_vtcore/unicode/width.h> +#include <wsap_vtcore/unicode/grapheme.h> int host_use(void) { return in_ranges + zero_width + utf8d + unicode_width(1) + UTF8_ACCEPT + GRAPHEME_MAX_LEN; @@ -55,9 +55,9 @@ int host_use(void) EOF check "unicode API: host names declared after" <<'EOF' -#include <term/unicode/utf8.h> -#include <term/unicode/width.h> -#include <term/unicode/grapheme.h> +#include <wsap_vtcore/unicode/utf8.h> +#include <wsap_vtcore/unicode/width.h> +#include <wsap_vtcore/unicode/grapheme.h> int unicode_width(int); static int in_ranges; #define UTF8_ACCEPT 7 diff --git a/tests/helpers/term_api.h b/tests/helpers/term_api.h index f2d6a5d..17a29ae 100644 --- a/tests/helpers/term_api.h +++ b/tests/helpers/term_api.h @@ -7,7 +7,7 @@ * terminal shows. */ -#include "term/term.h" +#include "wsap_vtcore/wsap_vtcore.h" #include <stdbool.h> #include <stddef.h> @@ -17,149 +17,149 @@ /* The history size the tests assume. */ #define TEST_SCROLLBACK 4096 -static inline struct term *tt_new_opts(int cols, int rows, const struct term_callbacks *cb) +static inline struct wsap_vtcore *tt_new_opts(int cols, int rows, const struct wsap_vtcore_callbacks *cb) { - struct term_options opt = { + struct wsap_vtcore_options opt = { .size = { .x = cols, .y = rows }, .scrollback = TEST_SCROLLBACK, }; if (cb) opt.callbacks = *cb; - return term_new(&opt); + return wsap_vtcore_new(&opt); } -static inline struct term *tt_new(int cols, int rows) +static inline struct wsap_vtcore *tt_new(int cols, int rows) { return tt_new_opts(cols, rows, NULL); } -static inline void tt_write(struct term *t, const char *s, size_t len) +static inline void tt_write(struct wsap_vtcore *t, const char *s, size_t len) { - term_feed(t, s, len, 0); + wsap_vtcore_feed(t, s, len, 0); } -static inline void tt_puts(struct term *t, const char *s) +static inline void tt_puts(struct wsap_vtcore *t, const char *s) { - term_feed(t, s, strlen(s), 0); + wsap_vtcore_feed(t, s, strlen(s), 0); } -static inline int tt_cols(const struct term *t) { return term_size(t).x; } -static inline int tt_rows(const struct term *t) { return term_size(t).y; } -static inline int tt_cursor_x(const struct term *t) { return term_cursor(t).pos.x; } -static inline int tt_cursor_y(const struct term *t) { return term_cursor(t).pos.y; } -static inline int tt_history(const struct term *t) { return term_scrollback(t).total; } -static inline int tt_view_offset(const struct term *t) { return term_scrollback(t).offset; } +static inline int tt_cols(const struct wsap_vtcore *t) { return wsap_vtcore_size(t).x; } +static inline int tt_rows(const struct wsap_vtcore *t) { return wsap_vtcore_size(t).y; } +static inline int tt_cursor_x(const struct wsap_vtcore *t) { return wsap_vtcore_cursor(t).pos.x; } +static inline int tt_cursor_y(const struct wsap_vtcore *t) { return wsap_vtcore_cursor(t).pos.y; } +static inline int tt_history(const struct wsap_vtcore *t) { return wsap_vtcore_scrollback(t).total; } +static inline int tt_view_offset(const struct wsap_vtcore *t) { return wsap_vtcore_scrollback(t).offset; } /* One snapshot serves every read. It follows whichever terminal a test * reads last. */ -static struct term_snapshot *tt_snapshot_for(struct term *t) +static struct wsap_vtcore_snapshot *tt_snapshot_for(struct wsap_vtcore *t) { - static struct term_snapshot *snap; + static struct wsap_vtcore_snapshot *snap; if (!snap) - snap = term_snapshot_new(); - term_snapshot_update(snap, t); + snap = wsap_vtcore_snapshot_new(); + wsap_vtcore_snapshot_update(snap, t); return snap; } -static const struct term_cell tt_blank_cell = { - .text = ' ', .fg = TERM_COLOR_FG, .bg = TERM_COLOR_BG, .width = 1, +static const struct wsap_vtcore_cell tt_blank_cell = { + .text = ' ', .fg = WSAP_VTCORE_COLOR_FG, .bg = WSAP_VTCORE_COLOR_BG, .width = 1, }; /* A cell of the viewport. Out-of-range columns read as a blank cell. */ -static inline const struct term_cell *tt_view_cell(struct term *t, int col, int row) +static inline const struct wsap_vtcore_cell *tt_view_cell(struct wsap_vtcore *t, int col, int row) { - struct term_snapshot *s = tt_snapshot_for(t); - const struct term_cell *cells = term_snapshot_row(s, row); + struct wsap_vtcore_snapshot *s = tt_snapshot_for(t); + const struct wsap_vtcore_cell *cells = wsap_vtcore_snapshot_row(s, row); if (!cells) return NULL; - if (col < 0 || col >= term_snapshot_view(s)->size.x) + if (col < 0 || col >= wsap_vtcore_snapshot_view(s)->size.x) return &tt_blank_cell; return &cells[col]; } /* A cell of the live screen, whatever the viewport shows. */ -static inline const struct term_cell *tt_cell(struct term *t, int col, int row) +static inline const struct wsap_vtcore_cell *tt_cell(struct wsap_vtcore *t, int col, int row) { int offset = tt_view_offset(t); if (offset) - term_scroll_to(t, 0); - const struct term_cell *cell = tt_view_cell(t, col, row); + wsap_vtcore_scroll_to(t, 0); + const struct wsap_vtcore_cell *cell = tt_view_cell(t, col, row); if (offset) - term_scroll_to(t, offset); + wsap_vtcore_scroll_to(t, offset); return cell; } /* The code points of a cell's text: one, or a whole cluster. The snapshot * that the last read used must still describe the terminal. */ -static inline int tt_cell_cps(struct term *t, const struct term_cell *cell, +static inline int tt_cell_cps(struct wsap_vtcore *t, const struct wsap_vtcore_cell *cell, uint32_t *cps, int cap) { - return term_snapshot_cluster(tt_snapshot_for(t), cell->text, cps, cap); + return wsap_vtcore_snapshot_cluster(tt_snapshot_for(t), cell->text, cps, cap); } /* The first code point of a cell's text. */ -static inline uint32_t tt_cell_cp(struct term *t, const struct term_cell *cell) +static inline uint32_t tt_cell_cp(struct wsap_vtcore *t, const struct wsap_vtcore_cell *cell) { uint32_t cp = 0; - if (!(cell->text & TERM_TEXT_CLUSTER)) + if (!(cell->text & WSAP_VTCORE_TEXT_CLUSTER)) return cell->text; tt_cell_cps(t, cell, &cp, 1); return cp; } -static inline bool tt_is_cluster(const struct term_cell *cell) +static inline bool tt_is_cluster(const struct wsap_vtcore_cell *cell) { - return (cell->text & TERM_TEXT_CLUSTER) != 0; + return (cell->text & WSAP_VTCORE_TEXT_CLUSTER) != 0; } /* The selected columns [begin, end) of a viewport row. */ -static inline struct term_span tt_row_selection(struct term *t, int row) +static inline struct wsap_vtcore_span tt_row_selection(struct wsap_vtcore *t, int row) { - return term_snapshot_row_selection(tt_snapshot_for(t), row); + return wsap_vtcore_snapshot_row_selection(tt_snapshot_for(t), row); } -static inline bool tt_selected(struct term *t, int col, int row) +static inline bool tt_selected(struct wsap_vtcore *t, int col, int row) { - struct term_span span = tt_row_selection(t, row); + struct wsap_vtcore_span span = tt_row_selection(t, row); return col >= span.begin && col < span.end; } /* Select from one viewport cell to another, both inclusive. */ -static inline void tt_select(struct term *t, int x1, int y1, int x2, int y2) +static inline void tt_select(struct wsap_vtcore *t, int x1, int y1, int x2, int y2) { bool forward = y1 < y2 || (y1 == y2 && x1 <= x2); - struct term_vector2i a = { .x = x1, .y = y1 }, b = { .x = x2, .y = y2 }; - term_select_start(t, forward ? a : b, false, TERM_SELECT_CELL); - term_select_extend(t, forward ? b : a, true); + struct wsap_vtcore_vector2i a = { .x = x1, .y = y1 }, b = { .x = x2, .y = y2 }; + wsap_vtcore_select_start(t, forward ? a : b, false, WSAP_VTCORE_SELECT_CELL); + wsap_vtcore_select_extend(t, forward ? b : a, true); } /* The helpers below return new strings. The caller frees them. */ /* NULL when nothing is selected. */ -static inline char *tt_selection_text(const struct term *t) +static inline char *tt_selection_text(const struct wsap_vtcore *t) { - return term_selection_text(t); + return wsap_vtcore_selection_text(t); } -static inline char *tt_history_text(struct term *t, int max_rows) +static inline char *tt_history_text(struct wsap_vtcore *t, int max_rows) { - return term_history_text(t, max_rows); + return wsap_vtcore_history_text(t, max_rows); } /* NULL when there is no link. */ -static inline char *tt_link_at(struct term *t, int col, int row) +static inline char *tt_link_at(struct wsap_vtcore *t, int col, int row) { - return term_link_at(t, (struct term_vector2i){ .x = col, .y = row }); + return wsap_vtcore_link_at(t, (struct wsap_vtcore_vector2i){ .x = col, .y = row }); } -static inline bool tt_resize(struct term *t, int cols, int rows) +static inline bool tt_resize(struct wsap_vtcore *t, int cols, int rows) { - return term_resize(t, (struct term_vector2i){ .x = cols, .y = rows }); + return wsap_vtcore_resize(t, (struct wsap_vtcore_vector2i){ .x = cols, .y = rows }); } /* The ARGB value of a color in the terminal's current palette. */ -static inline uint32_t tt_color(struct term *t, term_color c) +static inline uint32_t tt_color(struct wsap_vtcore *t, wsap_vtcore_color c) { - return term_view_color(term_snapshot_view(tt_snapshot_for(t)), c); + return wsap_vtcore_view_color(wsap_vtcore_snapshot_view(tt_snapshot_for(t)), c); } #endif diff --git a/tests/hist_test.c b/tests/hist_test.c index 691ae3c..1cf807c 100644 --- a/tests/hist_test.c +++ b/tests/hist_test.c @@ -1,6 +1,6 @@ #include "hist.h" #include "hist_view.h" -#include "term/unicode/grapheme.h" +#include "wsap_vtcore/unicode/grapheme.h" #include <assert.h> #include <limits.h> @@ -15,70 +15,70 @@ static uint64_t lines(const struct hist *h) static struct cell dc(uint32_t c) { - return (struct cell){ .c = c, .fg = TERM_COLOR_FG, .bg = TERM_COLOR_BG }; + return (struct cell){ .c = c, .fg = WSAP_VTCORE_COLOR_FG, .bg = WSAP_VTCORE_COLOR_BG }; } static void test_init_free(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); assert(lines(&h) == 0); assert(hist_first_id(&h) == 0); assert(!hist_is_open(&h)); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } static void test_ascii_roundtrip(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); const char *msg = "Hello, world!"; - term_hist_push_ascii(&h, msg, (int)strlen(msg), NULL, false); + wsap_vtcore_hist_push_ascii(&h, msg, (int)strlen(msg), NULL, false); assert(lines(&h) == 1); - assert(term_hist_line_rows(&h, 0, 80) == 1); - assert(term_hist_line_rows(&h, 0, 5) == 3); + assert(wsap_vtcore_hist_line_rows(&h, 0, 80) == 1); + assert(wsap_vtcore_hist_line_rows(&h, 0, 5) == 3); struct cell out[80]; - int n = term_hist_decode_segment(&h, 0, 0, 80, out, NULL); + int n = wsap_vtcore_hist_decode_segment(&h, 0, 0, 80, out, NULL); assert(n == (int)strlen(msg)); for (int i = 0; i < n; i++) { assert(out[i].c == (uint32_t)msg[i]); - assert(out[i].fg == TERM_COLOR_FG); - assert(out[i].bg == TERM_COLOR_BG); + assert(out[i].fg == WSAP_VTCORE_COLOR_FG); + assert(out[i].bg == WSAP_VTCORE_COLOR_BG); assert(out[i].flags == 0); } - assert(term_hist_decode_segment(&h, 0, 0, 5, out, NULL) == 5); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 5, out, NULL) == 5); assert(out[0].c == 'H' && out[4].c == 'o'); - assert(term_hist_decode_segment(&h, 0, 1, 5, out, NULL) == 5); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 1, 5, out, NULL) == 5); assert(out[0].c == ',' && out[4].c == 'r'); - assert(term_hist_decode_segment(&h, 0, 2, 5, out, NULL) == 3); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 2, 5, out, NULL) == 3); assert(out[0].c == 'l' && out[2].c == '!'); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } static void test_attributes_roundtrip(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); struct cell row[10]; for (int i = 0; i < 10; i++) { row[i] = (struct cell){ .c = 'A' + i, - .fg = term_color_rgb(i * 10, i * 20, i * 25), - .bg = term_color_rgb(255 - i * 10, 0, 0), + .fg = wsap_vtcore_color_rgb(i * 10, i * 20, i * 25), + .bg = wsap_vtcore_color_rgb(255 - i * 10, 0, 0), .flags = (i % 2 == 0) ? CELL_BOLD : CELL_ITALIC, .pad = (uint16_t)(100 + i), }; } - term_hist_push_row(&h, row, 10, false, NULL); + wsap_vtcore_hist_push_row(&h, row, 10, false, NULL); assert(lines(&h) == 1); struct cell out[10]; - assert(term_hist_decode_segment(&h, 0, 0, 10, out, NULL) == 10); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 10, out, NULL) == 10); for (int i = 0; i < 10; i++) { assert(out[i].c == row[i].c); assert(out[i].fg == row[i].fg); @@ -86,252 +86,252 @@ static void test_attributes_roundtrip(void) assert(out[i].flags == row[i].flags); assert(out[i].pad == row[i].pad); } - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } static void test_wide_and_wrap(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); struct cell row[4] = { dc('A'), dc(0x4e16), dc(' '), dc('B') }; row[1].flags = CELL_WIDE; row[2].flags = CELL_TRAIL; - term_hist_push_row(&h, row, 4, false, NULL); + wsap_vtcore_hist_push_row(&h, row, 4, false, NULL); - assert(term_hist_line_rows(&h, 0, 4) == 1); + assert(wsap_vtcore_hist_line_rows(&h, 0, 4) == 1); /* Width 2: 'A' and a pad, then the wide cell, then 'B'. */ - assert(term_hist_line_rows(&h, 0, 2) == 3); + assert(wsap_vtcore_hist_line_rows(&h, 0, 2) == 3); struct cell out[4]; - assert(term_hist_decode_segment(&h, 0, 0, 2, out, NULL) == 2); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 2, out, NULL) == 2); assert(out[0].c == 'A'); assert(out[1].flags & CELL_WRAP_PAD); - assert(term_hist_decode_segment(&h, 0, 1, 2, out, NULL) == 2); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 1, 2, out, NULL) == 2); assert(out[0].c == 0x4e16 && (out[0].flags & CELL_WIDE)); assert(out[1].flags & CELL_TRAIL); - assert(term_hist_decode_segment(&h, 0, 2, 2, out, NULL) == 1); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 2, 2, out, NULL) == 1); assert(out[0].c == 'B'); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } static void test_clusters_roundtrip(void) { - struct gstore *g = term_gstore_new(NULL); + struct gstore *g = wsap_vtcore_gstore_new(NULL); assert(g); uint32_t cps[3] = { 'e', 0x0301, 0x0300 }; - uint32_t handle = term_gstore_intern(g, cps, 3); + uint32_t handle = wsap_vtcore_gstore_intern(g, cps, 3); struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); struct cell row[2] = { dc(handle), dc('X') }; - term_hist_push_row(&h, row, 2, false, g); + wsap_vtcore_hist_push_row(&h, row, 2, false, g); struct cell out[2]; - assert(term_hist_decode_segment(&h, 0, 0, 2, out, g) == 2); - assert(term_grapheme_is_handle(out[0].c)); - uint32_t got[TERM_GRAPHEME_MAX_LEN]; - assert(term_gstore_expand(g, out[0].c, got, TERM_GRAPHEME_MAX_LEN) == 3); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 2, out, g) == 2); + assert(wsap_vtcore_grapheme_is_handle(out[0].c)); + uint32_t got[WSAP_VTCORE_GRAPHEME_MAX_LEN]; + assert(wsap_vtcore_gstore_expand(g, out[0].c, got, WSAP_VTCORE_GRAPHEME_MAX_LEN) == 3); assert(got[0] == cps[0] && got[1] == cps[1] && got[2] == cps[2]); assert(out[1].c == 'X'); - term_hist_free(&h); - term_gstore_free(g); + wsap_vtcore_hist_free(&h); + wsap_vtcore_gstore_free(g); } static void test_open_lines_and_pop(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); struct cell part1[3] = { dc('1'), dc('2'), dc('3') }; - term_hist_push_row(&h, part1, 3, true, NULL); + wsap_vtcore_hist_push_row(&h, part1, 3, true, NULL); assert(lines(&h) == 1 && hist_is_open(&h)); struct cell part2[2] = { dc('4'), dc('5') }; - term_hist_push_row(&h, part2, 2, false, NULL); + wsap_vtcore_hist_push_row(&h, part2, 2, false, NULL); assert(lines(&h) == 1 && !hist_is_open(&h)); struct cell out[5]; - assert(term_hist_decode_segment(&h, 0, 0, 10, out, NULL) == 5); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 10, out, NULL) == 5); for (int i = 0; i < 5; i++) assert(out[i].c == (uint32_t)('1' + i)); struct cell popped[2]; - assert(term_hist_pop_tail_cells(&h, 2, popped, NULL) == 2); + assert(wsap_vtcore_hist_pop_tail_cells(&h, 2, popped, NULL) == 2); assert(popped[0].c == '4' && popped[1].c == '5'); - assert(term_hist_decode_segment(&h, 0, 0, 10, out, NULL) == 3); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 10, out, NULL) == 3); assert(out[0].c == '1' && out[2].c == '3'); /* Pop from an open line with a pen. */ - term_hist_close_open_line(&h); + wsap_vtcore_hist_close_open_line(&h); struct cell color[2] = { { .c = 'A', .fg = 0xff0000, .bg = 0x00ff00, .flags = CELL_BOLD }, { .c = 'B', .fg = 0xff0000, .bg = 0x00ff00, .flags = CELL_BOLD }, }; - term_hist_push_row(&h, color, 2, true, NULL); + wsap_vtcore_hist_push_row(&h, color, 2, true, NULL); assert(lines(&h) == 2); struct cell pop_color[1]; - assert(term_hist_pop_tail_cells(&h, 1, pop_color, NULL) == 1); + assert(wsap_vtcore_hist_pop_tail_cells(&h, 1, pop_color, NULL) == 1); assert(pop_color[0].c == 'B' && pop_color[0].fg == 0xff0000 && pop_color[0].bg == 0x00ff00); assert(pop_color[0].flags & CELL_BOLD); - assert(term_hist_decode_segment(&h, 1, 0, 10, out, NULL) == 1); + assert(wsap_vtcore_hist_decode_segment(&h, 1, 0, 10, out, NULL) == 1); assert(out[0].c == 'A' && out[0].fg == 0xff0000 && (out[0].flags & CELL_BOLD)); /* Popping a whole line returns its cells and removes it. */ struct cell all[4]; - assert(term_hist_pop_line(&h, all, 4, NULL) == 1); + assert(wsap_vtcore_hist_pop_line(&h, all, 4, NULL) == 1); assert(all[0].c == 'A'); assert(lines(&h) == 1 && !hist_is_open(&h)); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } static void test_open_line_joins(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); struct cell line1[2] = { dc('X'), dc('Y') }; - term_hist_push_row(&h, line1, 2, true, NULL); - term_hist_close_open_line(&h); + wsap_vtcore_hist_push_row(&h, line1, 2, true, NULL); + wsap_vtcore_hist_close_open_line(&h); struct cell line2[2] = { dc('Z'), dc('W') }; - term_hist_push_row(&h, line2, 2, false, NULL); + wsap_vtcore_hist_push_row(&h, line2, 2, false, NULL); assert(lines(&h) == 2); struct cell out[16]; - assert(term_hist_decode_segment(&h, 0, 0, 10, out, NULL) == 2); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 10, out, NULL) == 2); assert(out[0].c == 'X' && out[1].c == 'Y'); - assert(term_hist_decode_segment(&h, 1, 0, 10, out, NULL) == 2); + assert(wsap_vtcore_hist_decode_segment(&h, 1, 0, 10, out, NULL) == 2); assert(out[0].c == 'Z' && out[1].c == 'W'); /* ASCII joins a wide open line. */ - struct cell wide[2] = { { .c = 0x4e2d, .fg = 0x123456, .bg = TERM_COLOR_BG, .flags = CELL_WIDE }, - { .c = 0, .fg = 0x123456, .bg = TERM_COLOR_BG, .flags = CELL_TRAIL } }; - term_hist_push_row(&h, wide, 2, true, NULL); - term_hist_push_ascii(&h, "hello", 5, NULL, false); + struct cell wide[2] = { { .c = 0x4e2d, .fg = 0x123456, .bg = WSAP_VTCORE_COLOR_BG, .flags = CELL_WIDE }, + { .c = 0, .fg = 0x123456, .bg = WSAP_VTCORE_COLOR_BG, .flags = CELL_TRAIL } }; + wsap_vtcore_hist_push_row(&h, wide, 2, true, NULL); + wsap_vtcore_hist_push_ascii(&h, "hello", 5, NULL, false); assert(lines(&h) == 3); - assert(term_hist_decode_segment(&h, 2, 0, 10, out, NULL) == 7); + assert(wsap_vtcore_hist_decode_segment(&h, 2, 0, 10, out, NULL) == 7); assert(out[0].c == 0x4e2d && out[0].fg == 0x123456); - assert(out[2].c == 'h' && out[2].fg == TERM_COLOR_FG); - term_hist_free(&h); + assert(out[2].c == 'h' && out[2].fg == WSAP_VTCORE_COLOR_FG); + wsap_vtcore_hist_free(&h); } static void test_eviction(void) { struct hist h; - assert(term_hist_init(&h, 5, 64 * 1024 * 2)); + assert(wsap_vtcore_hist_init(&h, 5, 64 * 1024 * 2)); for (int i = 0; i < 10; i++) { char buf[16]; snprintf(buf, sizeof(buf), "line%d", i); - term_hist_push_ascii(&h, buf, (int)strlen(buf), NULL, false); + wsap_vtcore_hist_push_ascii(&h, buf, (int)strlen(buf), NULL, false); } assert(lines(&h) == 5); assert(hist_first_id(&h) == 5 && hist_end_id(&h) == 10); struct cell out[16]; - assert(term_hist_decode_segment(&h, 5, 0, 16, out, NULL) == 5); + assert(wsap_vtcore_hist_decode_segment(&h, 5, 0, 16, out, NULL) == 5); assert(out[0].c == 'l' && out[4].c == '5'); - assert(term_hist_decode_segment(&h, 9, 0, 16, out, NULL) == 5); + assert(wsap_vtcore_hist_decode_segment(&h, 9, 0, 16, out, NULL) == 5); assert(out[4].c == '9'); - assert(term_hist_decode_segment(&h, 4, 0, 16, out, NULL) == 0); - term_hist_free(&h); + assert(wsap_vtcore_hist_decode_segment(&h, 4, 0, 16, out, NULL) == 0); + wsap_vtcore_hist_free(&h); } static void test_emoji_and_text_presentation(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); struct cell row[3] = { dc(0x2764), dc(' '), dc(0x2600) }; row[0].flags = CELL_WIDE | CELL_EMOJI; row[1].flags = CELL_TRAIL; row[2].flags = CELL_TEXT; - term_hist_push_row(&h, row, 3, false, NULL); + wsap_vtcore_hist_push_row(&h, row, 3, false, NULL); struct cell out[3]; - assert(term_hist_decode_segment(&h, 0, 0, 10, out, NULL) == 3); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 10, out, NULL) == 3); assert(out[0].c == 0x2764 && (out[0].flags & CELL_WIDE) && (out[0].flags & CELL_EMOJI)); assert(out[1].flags & CELL_TRAIL); assert(out[2].c == 0x2600 && (out[2].flags & CELL_TEXT)); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } static void test_width_one(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); - term_hist_push_ascii(&h, "ABC", 3, NULL, false); - assert(term_hist_line_rows(&h, 0, 1) == 3); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); + wsap_vtcore_hist_push_ascii(&h, "ABC", 3, NULL, false); + assert(wsap_vtcore_hist_line_rows(&h, 0, 1) == 3); struct cell out[2]; - assert(term_hist_decode_segment(&h, 0, 0, 1, out, NULL) == 1 && out[0].c == 'A'); - assert(term_hist_decode_segment(&h, 0, 1, 1, out, NULL) == 1 && out[0].c == 'B'); - assert(term_hist_decode_segment(&h, 0, 2, 1, out, NULL) == 1 && out[0].c == 'C'); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 1, out, NULL) == 1 && out[0].c == 'A'); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 1, 1, out, NULL) == 1 && out[0].c == 'B'); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 2, 1, out, NULL) == 1 && out[0].c == 'C'); struct cell wide[2] = { dc(0x4e16), dc(' ') }; wide[0].flags = CELL_WIDE; wide[1].flags = CELL_TRAIL; - term_hist_push_row(&h, wide, 2, false, NULL); - assert(term_hist_line_rows(&h, 1, 1) == 1); - assert(term_hist_decode_segment(&h, 1, 0, 1, out, NULL) == 1); + wsap_vtcore_hist_push_row(&h, wide, 2, false, NULL); + assert(wsap_vtcore_hist_line_rows(&h, 1, 1) == 1); + assert(wsap_vtcore_hist_decode_segment(&h, 1, 0, 1, out, NULL) == 1); assert(out[0].c == 0x4e16 && (out[0].flags & CELL_WIDE)); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } static void test_blank_lines(void) { struct hist h; - assert(term_hist_init(&h, 10, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 10, 64 * 1024 * 4)); const char *first = "First line on page 0"; - term_hist_push_ascii(&h, first, (int)strlen(first), NULL, false); - term_hist_push_blank(&h, 10); + wsap_vtcore_hist_push_ascii(&h, first, (int)strlen(first), NULL, false); + wsap_vtcore_hist_push_blank(&h, 10); assert(lines(&h) == 10); assert(hist_first_id(&h) == 1); for (int i = 0; i < 20; i++) { char buf[32]; snprintf(buf, sizeof(buf), "line %d", i); - term_hist_push_ascii(&h, buf, (int)strlen(buf), NULL, false); + wsap_vtcore_hist_push_ascii(&h, buf, (int)strlen(buf), NULL, false); } struct cell out[32]; - assert(term_hist_decode_segment(&h, hist_end_id(&h) - 1, 0, 32, out, NULL) == 7); + assert(wsap_vtcore_hist_decode_segment(&h, hist_end_id(&h) - 1, 0, 32, out, NULL) == 7); assert(out[5].c == '1' && out[6].c == '9'); /* A blank row closes an open line and adds no line. */ - term_hist_push_ascii(&h, "open", 4, NULL, true); + wsap_vtcore_hist_push_ascii(&h, "open", 4, NULL, true); uint64_t before = hist_end_id(&h); - term_hist_push_blank(&h, 1); + wsap_vtcore_hist_push_blank(&h, 1); assert(!hist_is_open(&h) && hist_end_id(&h) == before); /* More blank rows than the limit keep the id count going. */ - term_hist_push_blank(&h, 1000); + wsap_vtcore_hist_push_blank(&h, 1000); assert(lines(&h) == 10 && hist_end_id(&h) == before + 1000); - term_hist_push_blank(&h, 5); + wsap_vtcore_hist_push_blank(&h, 5); assert(lines(&h) == 10 && hist_end_id(&h) == before + 1005); - assert(term_hist_decode_segment(&h, hist_end_id(&h) - 1, 0, 32, out, NULL) == 0); - assert(term_hist_line_rows(&h, hist_end_id(&h) - 1, 32) == 1); - term_hist_free(&h); + assert(wsap_vtcore_hist_decode_segment(&h, hist_end_id(&h) - 1, 0, 32, out, NULL) == 0); + assert(wsap_vtcore_hist_line_rows(&h, hist_end_id(&h) - 1, 32) == 1); + wsap_vtcore_hist_free(&h); } static void test_open_line_attrs_continuation(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); struct cell r1[5], r2[10]; for (int i = 0; i < 5; i++) - r1[i] = (struct cell){ .c = '1' + i, .fg = term_color_rgb(255, 0, 0), .bg = TERM_COLOR_BG }; + r1[i] = (struct cell){ .c = '1' + i, .fg = wsap_vtcore_color_rgb(255, 0, 0), .bg = WSAP_VTCORE_COLOR_BG }; for (int i = 0; i < 10; i++) - r2[i] = (struct cell){ .c = 'a' + i, .fg = i < 5 ? term_color_rgb(255, 0, 0) : term_color_rgb(0, 0, 255), - .bg = TERM_COLOR_BG }; - term_hist_push_row(&h, r1, 5, true, NULL); - term_hist_push_row(&h, r2, 10, false, NULL); + r2[i] = (struct cell){ .c = 'a' + i, .fg = i < 5 ? wsap_vtcore_color_rgb(255, 0, 0) : wsap_vtcore_color_rgb(0, 0, 255), + .bg = WSAP_VTCORE_COLOR_BG }; + wsap_vtcore_hist_push_row(&h, r1, 5, true, NULL); + wsap_vtcore_hist_push_row(&h, r2, 10, false, NULL); assert(lines(&h) == 1); struct cell out[15]; - assert(term_hist_decode_segment(&h, 0, 0, 15, out, NULL) == 15); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 15, out, NULL) == 15); for (int i = 0; i < 10; i++) - assert(out[i].fg == term_color_rgb(255, 0, 0)); + assert(out[i].fg == wsap_vtcore_color_rgb(255, 0, 0)); for (int i = 10; i < 15; i++) - assert(out[i].fg == term_color_rgb(0, 0, 255)); - term_hist_free(&h); + assert(out[i].fg == wsap_vtcore_color_rgb(0, 0, 255)); + wsap_vtcore_hist_free(&h); } static void mark_link(void *ud, uint16_t link) @@ -342,76 +342,76 @@ static void mark_link(void *ud, uint16_t link) static void test_hyperlinks(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); struct pen_attr pen = pen_attr_default(); pen.link = 42; - term_hist_push_ascii(&h, "Link text", 9, &pen, false); + wsap_vtcore_hist_push_ascii(&h, "Link text", 9, &pen, false); struct cell row[2] = { dc('a'), dc('b') }; row[1].pad = 7; row[1].flags = CELL_LINK; - term_hist_push_row(&h, row, 2, true, NULL); + wsap_vtcore_hist_push_row(&h, row, 2, true, NULL); struct cell out[16]; - assert(term_hist_decode_segment(&h, 0, 0, 16, out, NULL) == 9); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 16, out, NULL) == 9); for (int i = 0; i < 9; i++) assert(out[i].pad == 42); int marks[64] = { 0 }; - term_hist_mark_links(&h, mark_link, marks); + wsap_vtcore_hist_mark_links(&h, mark_link, marks); assert(marks[42] && marks[7]); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } static void test_long_lines(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); /* A line past the part limit keeps one id. */ char chunk[1024]; memset(chunk, 'X', sizeof(chunk)); for (int i = 0; i < 64; i++) - term_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, true); - term_hist_push_ascii(&h, chunk, 100, NULL, false); + wsap_vtcore_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, true); + wsap_vtcore_hist_push_ascii(&h, chunk, 100, NULL, false); assert(lines(&h) == 1); - assert(term_hist_line_cells(&h, 0) == 65636); - assert(term_hist_line_rows(&h, 0, 1000) == 66); + assert(wsap_vtcore_hist_line_cells(&h, 0) == 65636); + assert(wsap_vtcore_hist_line_rows(&h, 0, 1000) == 66); struct cell out[1000]; - assert(term_hist_decode_segment(&h, 0, 64, 1000, out, NULL) == 1000); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 64, 1000, out, NULL) == 1000); for (int i = 0; i < 1000; i++) assert(out[i].c == 'X'); - assert(term_hist_decode_segment(&h, 0, 65, 1000, out, NULL) == 636); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 65, 1000, out, NULL) == 636); memset(chunk, 'Y', sizeof(chunk)); for (int i = 0; i < 64; i++) - term_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, true); - term_hist_push_ascii(&h, chunk, 100, NULL, false); - term_hist_push_ascii(&h, "tail", 4, NULL, false); + wsap_vtcore_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, true); + wsap_vtcore_hist_push_ascii(&h, chunk, 100, NULL, false); + wsap_vtcore_hist_push_ascii(&h, "tail", 4, NULL, false); assert(lines(&h) == 3); - assert(term_hist_line_rows(&h, 1, 1000) == 66); - assert(term_hist_decode_segment(&h, 1, 0, 1000, out, NULL) == 1000 && out[0].c == 'Y'); - assert(term_hist_decode_segment(&h, 2, 0, 1000, out, NULL) == 4 && out[0].c == 't'); - assert(term_hist_rows(&h, 1000) == 133); + assert(wsap_vtcore_hist_line_rows(&h, 1, 1000) == 66); + assert(wsap_vtcore_hist_decode_segment(&h, 1, 0, 1000, out, NULL) == 1000 && out[0].c == 'Y'); + assert(wsap_vtcore_hist_decode_segment(&h, 2, 0, 1000, out, NULL) == 4 && out[0].c == 't'); + assert(wsap_vtcore_hist_rows(&h, 1000) == 133); /* One long ASCII push splits into parts but reads back whole. */ - term_hist_free(&h); - assert(term_hist_init(&h, 100, 64 * 1024 * 8)); + wsap_vtcore_hist_free(&h); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 8)); int big_len = 150000; char *big = malloc((size_t)big_len); assert(big); for (int i = 0; i < big_len; i++) big[i] = (char)('A' + (i % 26)); - term_hist_push_ascii(&h, big, big_len, NULL, false); + wsap_vtcore_hist_push_ascii(&h, big, big_len, NULL, false); assert(lines(&h) == 1); - assert(term_hist_line_rows(&h, 0, 1000) == 150); + assert(wsap_vtcore_hist_line_rows(&h, 0, 1000) == 150); for (int s = 0; s < 150; s++) { - assert(term_hist_decode_segment(&h, 0, s, 1000, out, NULL) == 1000); + assert(wsap_vtcore_hist_decode_segment(&h, 0, s, 1000, out, NULL) == 1000); for (int x = 0; x < 1000; x++) assert(out[x].c == (uint32_t)big[s * 1000 + x]); } free(big); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } static void test_page_limits(void) @@ -420,143 +420,143 @@ static void test_page_limits(void) struct cell out[1000]; /* One page: old lines leave to make room. */ - assert(term_hist_init(&h, 10000, HIST_PAGE_SIZE)); + assert(wsap_vtcore_hist_init(&h, 10000, HIST_PAGE_SIZE)); char line64[64]; memset(line64, 'M', sizeof(line64)); for (int i = 0; i < 1200; i++) - term_hist_push_ascii(&h, line64, sizeof(line64), NULL, false); + wsap_vtcore_hist_push_ascii(&h, line64, sizeof(line64), NULL, false); assert(lines(&h) > 0 && lines(&h) < 1200); - assert(term_hist_decode_segment(&h, hist_end_id(&h) - 1, 0, 64, out, NULL) == 64); + assert(wsap_vtcore_hist_decode_segment(&h, hist_end_id(&h) - 1, 0, 64, out, NULL) == 64); assert(out[0].c == 'M'); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); /* A line limit of one keeps the long line as one line. */ - assert(term_hist_init(&h, 1, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 1, 64 * 1024 * 4)); char chunk[1024]; memset(chunk, 'Z', sizeof(chunk)); for (int i = 0; i < 65; i++) - term_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, true); + wsap_vtcore_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, true); assert(lines(&h) == 1 && hist_is_open(&h)); - term_hist_push_ascii(&h, "new", 3, NULL, false); - term_hist_push_ascii(&h, "next", 4, NULL, false); + wsap_vtcore_hist_push_ascii(&h, "new", 3, NULL, false); + wsap_vtcore_hist_push_ascii(&h, "next", 4, NULL, false); assert(lines(&h) == 1); - assert(term_hist_decode_segment(&h, hist_first_id(&h), 0, 10, out, NULL) == 4); - term_hist_free(&h); + assert(wsap_vtcore_hist_decode_segment(&h, hist_first_id(&h), 0, 10, out, NULL) == 4); + wsap_vtcore_hist_free(&h); /* A line longer than the arena drops its head but keeps its id. */ - assert(term_hist_init(&h, 10, HIST_PAGE_SIZE)); - term_hist_push_ascii(&h, "PREFIX", 6, NULL, true); + assert(wsap_vtcore_hist_init(&h, 10, HIST_PAGE_SIZE)); + wsap_vtcore_hist_push_ascii(&h, "PREFIX", 6, NULL, true); for (int i = 0; i < 100; i++) - term_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, true); - term_hist_close_open_line(&h); + wsap_vtcore_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, true); + wsap_vtcore_hist_close_open_line(&h); assert(lines(&h) == 1 && hist_first_id(&h) == 0); - assert(term_hist_line_cells(&h, 0) > 0 && term_hist_line_cells(&h, 0) < 100 * 1024); - assert(term_hist_decode_segment(&h, 0, 0, 6, out, NULL) == 6 && out[0].c == 'Z'); - term_hist_free(&h); + assert(wsap_vtcore_hist_line_cells(&h, 0) > 0 && wsap_vtcore_hist_line_cells(&h, 0) < 100 * 1024); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 6, out, NULL) == 6 && out[0].c == 'Z'); + wsap_vtcore_hist_free(&h); /* A small open line moves to a new page instead of splitting. */ - assert(term_hist_init(&h, 10, HIST_PAGE_SIZE)); + assert(wsap_vtcore_hist_init(&h, 10, HIST_PAGE_SIZE)); for (int i = 0; i < 60; i++) - term_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, false); - term_hist_push_ascii(&h, "PREFIX", 6, NULL, true); + wsap_vtcore_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, false); + wsap_vtcore_hist_push_ascii(&h, "PREFIX", 6, NULL, true); for (int i = 0; i < 10; i++) - term_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, true); - term_hist_close_open_line(&h); + wsap_vtcore_hist_push_ascii(&h, chunk, sizeof(chunk), NULL, true); + wsap_vtcore_hist_close_open_line(&h); uint64_t id = hist_end_id(&h) - 1; - assert(term_hist_decode_segment(&h, id, 0, 6, out, NULL) == 6); + assert(wsap_vtcore_hist_decode_segment(&h, id, 0, 6, out, NULL) == 6); assert(out[0].c == 'P' && out[5].c == 'X'); - assert(term_hist_line_rows(&h, id, 1000) == 11); - term_hist_free(&h); + assert(wsap_vtcore_hist_line_rows(&h, id, 1000) == 11); + wsap_vtcore_hist_free(&h); } static void test_nul_and_wide_pop(void) { struct hist h; struct cell out[8]; - assert(term_hist_init(&h, 10, 64 * 1024)); + assert(wsap_vtcore_hist_init(&h, 10, 64 * 1024)); struct cell nul_row[4] = { dc('A'), dc(0), dc('B'), dc('C') }; - term_hist_push_row(&h, nul_row, 4, false, NULL); - assert(term_hist_decode_segment(&h, 0, 0, 4, out, NULL) == 4); + wsap_vtcore_hist_push_row(&h, nul_row, 4, false, NULL); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 4, out, NULL) == 4); assert(out[0].c == 'A' && out[1].c == ' ' && out[2].c == 'B' && out[3].c == 'C'); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); /* A pop does not split a wide cell. */ - assert(term_hist_init(&h, 10, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 10, 64 * 1024 * 4)); struct cell wide[4] = { dc('A'), dc(0x4E2D), dc(0), dc('B') }; wide[1].flags = CELL_WIDE; wide[2].flags = CELL_TRAIL; - term_hist_push_row(&h, wide, 4, true, NULL); + wsap_vtcore_hist_push_row(&h, wide, 4, true, NULL); struct cell popped[2]; - assert(term_hist_pop_tail_cells(&h, 2, popped, NULL) == 1); + assert(wsap_vtcore_hist_pop_tail_cells(&h, 2, popped, NULL) == 1); assert(popped[0].c == 'B'); - assert(term_hist_decode_segment(&h, 0, 0, 4, out, NULL) == 3); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 4, out, NULL) == 3); assert(out[0].c == 'A' && out[1].c == 0x4E2D && (out[2].flags & CELL_TRAIL)); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } static void test_default_prefix_attributes(void) { struct hist h; - assert(term_hist_init(&h, 100, 64 * 1024 * 4)); + assert(wsap_vtcore_hist_init(&h, 100, 64 * 1024 * 4)); struct cell row[8]; for (int i = 0; i < 8; i++) { row[i] = dc('a' + i); if (i >= 4) { - row[i].fg = term_color_rgb(10, 20, 30); - row[i].bg = term_color_rgb(40, 50, 60); + row[i].fg = wsap_vtcore_color_rgb(10, 20, 30); + row[i].bg = wsap_vtcore_color_rgb(40, 50, 60); row[i].flags = CELL_BOLD; } } - term_hist_push_row(&h, row, 8, false, NULL); + wsap_vtcore_hist_push_row(&h, row, 8, false, NULL); struct cell out[8]; - assert(term_hist_decode_segment(&h, 0, 0, 8, out, NULL) == 8); + assert(wsap_vtcore_hist_decode_segment(&h, 0, 0, 8, out, NULL) == 8); for (int i = 0; i < 8; i++) { assert(out[i].c == (uint32_t)('a' + i)); assert(out[i].fg == row[i].fg && out[i].bg == row[i].bg && out[i].flags == row[i].flags); } struct pen_attr colored = pen_attr_default(); - colored.fg = term_color_rgb(200, 100, 50); - term_hist_push_ascii(&h, "0123", 4, NULL, true); - term_hist_push_ascii(&h, "4567", 4, &colored, false); - assert(term_hist_decode_segment(&h, 1, 0, 8, out, NULL) == 8); + colored.fg = wsap_vtcore_color_rgb(200, 100, 50); + wsap_vtcore_hist_push_ascii(&h, "0123", 4, NULL, true); + wsap_vtcore_hist_push_ascii(&h, "4567", 4, &colored, false); + assert(wsap_vtcore_hist_decode_segment(&h, 1, 0, 8, out, NULL) == 8); for (int i = 0; i < 8; i++) - assert(out[i].fg == (i < 4 ? TERM_COLOR_FG : term_color_rgb(200, 100, 50))); - term_hist_free(&h); + assert(out[i].fg == (i < 4 ? WSAP_VTCORE_COLOR_FG : wsap_vtcore_color_rgb(200, 100, 50))); + wsap_vtcore_hist_free(&h); } static void test_utf8_and_disabled(void) { struct hist h; - assert(term_hist_init(&h, 2, 64 * 1024 * 2)); - term_hist_push_ascii(&h, "first", 5, NULL, false); + assert(wsap_vtcore_hist_init(&h, 2, 64 * 1024 * 2)); + wsap_vtcore_hist_push_ascii(&h, "first", 5, NULL, false); struct cell p1[2] = { dc('A'), dc('B') }; struct cell p2[2] = { dc(0x00e9), dc('C') }; - term_hist_push_row(&h, p1, 2, true, NULL); - term_hist_push_row(&h, p2, 2, false, NULL); + wsap_vtcore_hist_push_row(&h, p1, 2, true, NULL); + wsap_vtcore_hist_push_row(&h, p2, 2, false, NULL); assert(lines(&h) == 2 && hist_first_id(&h) == 0); struct cell out[8]; - assert(term_hist_decode_segment(&h, 1, 0, 8, out, NULL) == 4); + assert(wsap_vtcore_hist_decode_segment(&h, 1, 0, 8, out, NULL) == 4); assert(out[0].c == 'A' && out[1].c == 'B' && out[2].c == 0x00e9 && out[3].c == 'C'); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); - assert(term_hist_init(&h, 0, 0)); - term_hist_push_ascii(&h, "ignored", 7, NULL, false); - term_hist_push_row(&h, p1, 2, false, NULL); - term_hist_push_blank(&h, 3); + assert(wsap_vtcore_hist_init(&h, 0, 0)); + wsap_vtcore_hist_push_ascii(&h, "ignored", 7, NULL, false); + wsap_vtcore_hist_push_row(&h, p1, 2, false, NULL); + wsap_vtcore_hist_push_blank(&h, 3); assert(lines(&h) == 0); - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } /* Random rows of every kind, pushed and compared with a plain copy. */ static void test_fuzz_rows(void) { enum { LIMIT = 40, COLS = 24, ITER = 4000 }; - struct gstore *g = term_gstore_new(NULL); + struct gstore *g = wsap_vtcore_gstore_new(NULL); uint32_t cps[2] = { 'a', 0x0301 }; - uint32_t cluster = term_gstore_intern(g, cps, 2); + uint32_t cluster = wsap_vtcore_gstore_intern(g, cps, 2); struct hist h; - assert(term_hist_init(&h, LIMIT, 64 * 1024 * 2)); + assert(wsap_vtcore_hist_init(&h, LIMIT, 64 * 1024 * 2)); static struct cell ref[LIMIT + 1][COLS * 8]; static int ref_len[LIMIT + 1]; @@ -574,7 +574,7 @@ static void test_fuzz_rows(void) unsigned k = (state >> 16) % 10; struct cell c = dc('a' + (state >> 20) % 26); if (k == 1) - c.fg = term_color_index((int)(state >> 24) % 16); + c.fg = wsap_vtcore_color_index((int)(state >> 24) % 16); if (k == 2) c.flags = CELL_BOLD; if (k == 3) @@ -603,7 +603,7 @@ static void test_fuzz_rows(void) memcpy(&ref[slot][ref_len[slot]], row, (size_t)n * sizeof(row[0])); ref_len[slot] += n; } - term_hist_push_row(&h, row, n, wrapped, g); + wsap_vtcore_hist_push_row(&h, row, n, wrapped, g); open = wrapped; assert(hist_first_id(&h) == ref_first && hist_end_id(&h) == ref_end); } @@ -612,10 +612,10 @@ static void test_fuzz_rows(void) for (uint64_t id = ref_first; id < ref_end; id++) { int slot = (int)(id % (LIMIT + 1)); int want = ref_len[slot]; - assert((int)term_hist_line_cells(&h, id) == want); + assert((int)wsap_vtcore_hist_line_cells(&h, id) == want); if (!want) continue; - assert(term_hist_decode_segment(&h, id, 0, COLS * 8, out, g) == want); + assert(wsap_vtcore_hist_decode_segment(&h, id, 0, COLS * 8, out, g) == want); for (int x = 0; x < want; x++) { const struct cell *a = &ref[slot][x], *b = &out[x]; if (a->flags & CELL_TRAIL) { @@ -623,87 +623,87 @@ static void test_fuzz_rows(void) continue; } assert(a->fg == b->fg && a->flags == b->flags); - if (term_grapheme_is_handle(a->c)) { - uint32_t got[TERM_GRAPHEME_MAX_LEN]; - assert(term_gstore_expand(g, b->c, got, TERM_GRAPHEME_MAX_LEN) == 2 && got[1] == 0x0301); + if (wsap_vtcore_grapheme_is_handle(a->c)) { + uint32_t got[WSAP_VTCORE_GRAPHEME_MAX_LEN]; + assert(wsap_vtcore_gstore_expand(g, b->c, got, WSAP_VTCORE_GRAPHEME_MAX_LEN) == 2 && got[1] == 0x0301); } else { assert(a->c == b->c); } } } - term_hist_free(&h); - term_gstore_free(g); + wsap_vtcore_hist_free(&h); + wsap_vtcore_gstore_free(g); } static void test_large_wide_count(void) { struct hist h; struct hist_view view = {0}; - assert(term_hist_init(&h, 600, 4 * HIST_PAGE_SIZE)); + assert(wsap_vtcore_hist_init(&h, 600, 4 * HIST_PAGE_SIZE)); struct cell row[4] = { dc('A'), dc(0x65e5), dc(0), dc('B') }; row[1].flags = CELL_WIDE; row[2].flags = CELL_TRAIL; for (int i = 0; i < 400; i++) - term_hist_push_row(&h, row, 4, true, NULL); - term_hist_close_open_line(&h); - uint64_t exact = term_hist_rows(&h, 3); - term_hist_prepare_rows(&h, 3); - assert(term_hist_estimated_rows(&h, 3) < exact); - assert(term_hist_view_sync(&view, &h, 3)); - term_hist_view_scroll_to(&view, &h, 3, (struct line_pos){0}, INT_MAX); - term_hist_view_refine(&view, &h, 3, 3); + wsap_vtcore_hist_push_row(&h, row, 4, true, NULL); + wsap_vtcore_hist_close_open_line(&h); + uint64_t exact = wsap_vtcore_hist_rows(&h, 3); + wsap_vtcore_hist_prepare_rows(&h, 3); + assert(wsap_vtcore_hist_estimated_rows(&h, 3) < exact); + assert(wsap_vtcore_hist_view_sync(&view, &h, 3)); + wsap_vtcore_hist_view_scroll_to(&view, &h, 3, (struct line_pos){0}, INT_MAX); + wsap_vtcore_hist_view_refine(&view, &h, 3, 3); assert(exact > 254); - assert(term_hist_estimated_rows(&h, 3) == exact); + assert(wsap_vtcore_hist_estimated_rows(&h, 3) == exact); for (int i = 0; i < 300; i++) - term_hist_push_ascii(&h, "x", 1, NULL, false); - assert(term_hist_estimated_rows(&h, 3) == exact + 300); - assert(term_hist_view_sync(&view, &h, 3)); + wsap_vtcore_hist_push_ascii(&h, "x", 1, NULL, false); + assert(wsap_vtcore_hist_estimated_rows(&h, 3) == exact + 300); + assert(wsap_vtcore_hist_view_sync(&view, &h, 3)); for (int i = 0; i < 300; i++) - term_hist_push_ascii(&h, "x", 1, NULL, false); - assert(term_hist_estimated_rows(&h, 3) == 600); - term_hist_view_free(&view); - term_hist_free(&h); + wsap_vtcore_hist_push_ascii(&h, "x", 1, NULL, false); + assert(wsap_vtcore_hist_estimated_rows(&h, 3) == 600); + wsap_vtcore_hist_view_free(&view); + wsap_vtcore_hist_free(&h); } static void test_view_after_prefix_eviction(void) { struct hist h; struct hist_view view = {0}; - assert(term_hist_init(&h, 10, 2 * HIST_PAGE_SIZE)); + assert(wsap_vtcore_hist_init(&h, 10, 2 * HIST_PAGE_SIZE)); char bytes[1000]; for (int i = 0; i < 100; i++) { memset(bytes, 'A' + i % 26, sizeof(bytes)); - term_hist_push_ascii(&h, bytes, sizeof(bytes), NULL, true); + wsap_vtcore_hist_push_ascii(&h, bytes, sizeof(bytes), NULL, true); } - term_hist_view_scroll_to(&view, &h, 1000, (struct line_pos){0}, 10); + wsap_vtcore_hist_view_scroll_to(&view, &h, 1000, (struct line_pos){0}, 10); struct hist_view_pos pos; struct cell before[1000], after[1000]; - assert(term_hist_view_row_pos(&view, &h, 1000, 3, (struct line_pos){0}, 0, &pos)); - assert(term_hist_decode_segment(&h, pos.id, pos.seg, 1000, before, NULL) == 1000); + assert(wsap_vtcore_hist_view_row_pos(&view, &h, 1000, 3, (struct line_pos){0}, 0, &pos)); + assert(wsap_vtcore_hist_decode_segment(&h, pos.id, pos.seg, 1000, before, NULL) == 1000); for (int i = 100; i < 140; i++) { memset(bytes, 'A' + i % 26, sizeof(bytes)); - term_hist_push_ascii(&h, bytes, sizeof(bytes), NULL, true); - term_hist_view_note_push(&view, &h, 1000); + wsap_vtcore_hist_push_ascii(&h, bytes, sizeof(bytes), NULL, true); + wsap_vtcore_hist_view_note_push(&view, &h, 1000); } - assert(term_hist_line_cells(&h, 0) < 140000); - assert(term_hist_view_row_pos(&view, &h, 1000, 3, (struct line_pos){0}, 0, &pos)); - assert(term_hist_decode_segment(&h, pos.id, pos.seg, 1000, after, NULL) == 1000); + assert(wsap_vtcore_hist_line_cells(&h, 0) < 140000); + assert(wsap_vtcore_hist_view_row_pos(&view, &h, 1000, 3, (struct line_pos){0}, 0, &pos)); + assert(wsap_vtcore_hist_decode_segment(&h, pos.id, pos.seg, 1000, after, NULL) == 1000); for (int i = 0; i < 1000; i++) assert(before[i].c == after[i].c); - term_hist_view_rewrap(&view, &h, 500); - assert(term_hist_view_row_pos(&view, &h, 500, 3, (struct line_pos){0}, 0, &pos)); - assert(term_hist_decode_segment(&h, pos.id, pos.seg, 500, after, NULL) == 500); + wsap_vtcore_hist_view_rewrap(&view, &h, 500); + assert(wsap_vtcore_hist_view_row_pos(&view, &h, 500, 3, (struct line_pos){0}, 0, &pos)); + assert(wsap_vtcore_hist_decode_segment(&h, pos.id, pos.seg, 500, after, NULL) == 500); for (int i = 0; i < 500; i++) assert(before[i].c == after[i].c); - term_hist_view_free(&view); - term_hist_free(&h); + wsap_vtcore_hist_view_free(&view); + wsap_vtcore_hist_free(&h); } static void test_short_lines_after_eviction(void) { struct hist h; - assert(term_hist_init(&h, 64, 64 * 1024 * 4)); - term_hist_prepare_rows(&h, 80); + assert(wsap_vtcore_hist_init(&h, 64, 64 * 1024 * 4)); + wsap_vtcore_hist_prepare_rows(&h, 80); const char text[] = "abc\n\nx\npqrs\n\nz\n"; const int offsets[] = {0, 4, 5, 7, 12, 13}; const int lengths[] = {3, 0, 1, 4, 0, 1}; @@ -713,20 +713,20 @@ static void test_short_lines_after_eviction(void) .ptr = text + offsets[i], .len = (uint16_t)lengths[i], }; for (int pass = 0; pass < 20000; pass++) - term_hist_push_ascii_lines(&h, batch, 6, NULL); + wsap_vtcore_hist_push_ascii_lines(&h, batch, 6, NULL); assert(lines(&h) == 64); - assert(term_hist_rows(&h, 80) == 64); + assert(wsap_vtcore_hist_rows(&h, 80) == 64); for (uint64_t id = hist_first_id(&h); id < hist_end_id(&h); id++) { int k = (int)(id % 6); struct cell out[80]; - assert(term_hist_decode_segment(&h, id, 0, 80, out, NULL) == lengths[k]); + assert(wsap_vtcore_hist_decode_segment(&h, id, 0, 80, out, NULL) == lengths[k]); for (int x = 0; x < lengths[k]; x++) { assert(out[x].c == (uint32_t)text[offsets[k] + x]); - assert(out[x].fg == TERM_COLOR_FG); - assert(out[x].bg == TERM_COLOR_BG); + assert(out[x].fg == WSAP_VTCORE_COLOR_FG); + assert(out[x].bg == WSAP_VTCORE_COLOR_BG); } } - term_hist_free(&h); + wsap_vtcore_hist_free(&h); } int main(void) diff --git a/tests/history_text_test.c b/tests/history_text_test.c index 88ca6aa..4ede890 100644 --- a/tests/history_text_test.c +++ b/tests/history_text_test.c @@ -1,4 +1,4 @@ -#include "term/term.h" +#include "wsap_vtcore/wsap_vtcore.h" #include "term_api.h" #include <assert.h> @@ -8,9 +8,9 @@ #include <stdlib.h> #include <string.h> -static struct term *new_term(int cols) +static struct wsap_vtcore *new_term(int cols) { - struct term *term = term_new(&(struct term_options){ + struct wsap_vtcore *term = wsap_vtcore_new(&(struct wsap_vtcore_options){ .size = { .x = cols, .y = 2 }, .scrollback = 100, }); @@ -18,12 +18,12 @@ static struct term *new_term(int cols) return term; } -static void feed(struct term *term, const char *text) +static void feed(struct wsap_vtcore *term, const char *text) { - term_feed(term, text, strlen(text), 0); + wsap_vtcore_feed(term, text, strlen(text), 0); } -static void expect_history(struct term *term, int rows, const char *expected) +static void expect_history(struct wsap_vtcore *term, int rows, const char *expected) { char *text = tt_history_text(term, rows); assert(text); @@ -36,13 +36,13 @@ static void expect_history(struct term *term, int rows, const char *expected) static void unicode_and_selection(void) { - struct term *term = new_term(16); + struct wsap_vtcore *term = new_term(16); expect_history(term, 100, ""); feed(term, "é👩💻界\r\nnext\r\nlast"); expect_history(term, 100, "é👩💻界\n"); expect_history(term, 0, ""); - term_select_start(term, (struct term_vector2i){0}, false, TERM_SELECT_CELL); - term_select_extend(term, (struct term_vector2i){ .x = 4 }, false); + wsap_vtcore_select_start(term, (struct wsap_vtcore_vector2i){0}, false, WSAP_VTCORE_SELECT_CELL); + wsap_vtcore_select_extend(term, (struct wsap_vtcore_vector2i){ .x = 4 }, false); char *before = tt_selection_text(term); assert(before); expect_history(term, 100, "é👩💻界\n"); @@ -54,41 +54,41 @@ static void unicode_and_selection(void) expect_history(term, 100, ""); feed(term, "\033[?1049l"); expect_history(term, 100, "é👩💻界\n"); - term_free(term); + wsap_vtcore_free(term); } static void limits_and_scrolled_view(void) { - struct term *term = new_term(8); + struct wsap_vtcore *term = new_term(8); feed(term, "one\r\ntwo\r\nthree\r\nfour\r\nfive"); expect_history(term, 100, "one\ntwo\nthree\n"); expect_history(term, 2, "two\nthree\n"); - term_scroll(term, 2); + wsap_vtcore_scroll(term, 2); expect_history(term, 100, "one\n"); - term_scroll(term, 100); + wsap_vtcore_scroll(term, 100); expect_history(term, 100, ""); - term_scroll_to(term, 0); - assert(term_resize(term, (struct term_vector2i){ .x = 12, .y = 2 })); + wsap_vtcore_scroll_to(term, 0); + assert(wsap_vtcore_resize(term, (struct wsap_vtcore_vector2i){ .x = 12, .y = 2 })); expect_history(term, 100, "one\ntwo\nthree\n"); - term_free(term); + wsap_vtcore_free(term); } static void wrapped_rows(void) { - struct term *term = new_term(4); + struct wsap_vtcore *term = new_term(4); feed(term, "abcdefghi\r\nx\r\ny"); expect_history(term, 100, "abcdefghi\n"); expect_history(term, 2, "efghi\n"); - term_free(term); + wsap_vtcore_free(term); term = new_term(4); feed(term, "abcdefghijklm"); expect_history(term, 100, "abcdefgh"); - term_free(term); + wsap_vtcore_free(term); } struct writer { - struct term *term; + struct wsap_vtcore *term; _Atomic bool done; }; @@ -106,7 +106,7 @@ static void *write_history(void *userdata) static void concurrent_history(void) { - struct term *term = new_term(16); + struct wsap_vtcore *term = new_term(16); struct writer writer = { .term = term }; pthread_t thread; assert(pthread_create(&thread, NULL, write_history, &writer) == 0); @@ -121,7 +121,7 @@ static void concurrent_history(void) free(text); } while (!atomic_load(&writer.done)); assert(pthread_join(thread, NULL) == 0); - term_free(term); + wsap_vtcore_free(term); } int main(void) diff --git a/tests/input_test.c b/tests/input_test.c index e3a6b8b..59223d2 100644 --- a/tests/input_test.c +++ b/tests/input_test.c @@ -1,29 +1,29 @@ -#include "term/term.h" +#include "wsap_vtcore/wsap_vtcore.h" #include <assert.h> #include <stdio.h> #include <stdlib.h> #include <string.h> -static struct term_keyboard_state st; -static struct term_modes m; +static struct wsap_vtcore_keyboard_state st; +static struct wsap_vtcore_modes m; static char out[128]; static size_t out_len; static void mode(unsigned kitty_flags) { - st = (struct term_keyboard_state){0}; - m = (struct term_modes){ .keyboard = kitty_flags, .grid = { .x = 80, .y = 24 } }; + st = (struct wsap_vtcore_keyboard_state){0}; + m = (struct wsap_vtcore_modes){ .keyboard = kitty_flags, .grid = { .x = 80, .y = 24 } }; } -static void enc(struct term_key_event ev) +static void enc(struct wsap_vtcore_key_event ev) { - if (!ev.action) ev.action = TERM_KEY_PRESS; - term_keyboard_update(&st, &ev); - struct term_input_result r = - term_input_encode_key(&st, &ev, &m, out, sizeof(out)); + if (!ev.action) ev.action = WSAP_VTCORE_KEY_PRESS; + wsap_vtcore_keyboard_update(&st, &ev); + struct wsap_vtcore_input_result r = + wsap_vtcore_input_encode_key(&st, &ev, &m, out, sizeof(out)); out_len = r.len; } -#define K(...) enc((struct term_key_event){ __VA_ARGS__ }) +#define K(...) enc((struct wsap_vtcore_key_event){ __VA_ARGS__ }) static void typed(uint32_t cp, unsigned mods) { @@ -31,16 +31,16 @@ static void typed(uint32_t cp, unsigned mods) } static bool consumed; -static void enc_mouse(struct term_mouse_event ev) +static void enc_mouse(struct wsap_vtcore_mouse_event ev) { if (ev.pixel.x == 0 && ev.pixel.y == 0) ev.pixel = ev.pos; - struct term_input_result r = - term_input_encode_mouse(&ev, &m, out, sizeof(out)); + struct wsap_vtcore_input_result r = + wsap_vtcore_input_encode_mouse(&ev, &m, out, sizeof(out)); out_len = r.len; - consumed = r.status != TERM_INPUT_UNHANDLED; + consumed = r.status != WSAP_VTCORE_INPUT_UNHANDLED; } -#define MOUSE(x_, y_, ...) enc_mouse((struct term_mouse_event){ .pos = { .x = (x_), .y = (y_) }, __VA_ARGS__ }) +#define MOUSE(x_, y_, ...) enc_mouse((struct wsap_vtcore_mouse_event){ .pos = { .x = (x_), .y = (y_) }, __VA_ARGS__ }) static void expect_at(const char *s, int line) { @@ -55,343 +55,343 @@ static void expect_at(const char *s, int line) int main(void) { mode(0); - K(.key = TERM_KEY_UP); expect("\033[A"); - K(.key = TERM_KEY_HOME); expect("\033[H"); - K(.key = TERM_KEY_DELETE); expect("\033[3~"); - K(.key = TERM_KEY_PAGE_UP); expect("\033[5~"); - K(.key = TERM_KEY_F1); expect("\033OP"); - K(.key = TERM_KEY_F5); expect("\033[15~"); - K(.key = TERM_KEY_F12); expect("\033[24~"); - K(.key = TERM_KEY_RETURN); expect("\r"); - K(.key = TERM_KEY_ESCAPE); expect("\033"); - K(.key = TERM_KEY_TAB); expect("\t"); - K(.key = TERM_KEY_TAB, .mods = TERM_MOD_SHIFT); expect("\033[Z"); - K(.key = TERM_KEY_BACKSPACE); expect("\177"); - K(.key = TERM_KEY_RIGHT, .mods = TERM_MOD_CTRL); expect("\033[1;5C"); - K(.key = TERM_KEY_F5, .mods = TERM_MOD_SHIFT); expect("\033[15;2~"); - K(.key = TERM_KEY_DELETE, .mods = TERM_MOD_CTRL); expect("\033[3;5~"); + K(.key = WSAP_VTCORE_KEY_UP); expect("\033[A"); + K(.key = WSAP_VTCORE_KEY_HOME); expect("\033[H"); + K(.key = WSAP_VTCORE_KEY_DELETE); expect("\033[3~"); + K(.key = WSAP_VTCORE_KEY_PAGE_UP); expect("\033[5~"); + K(.key = WSAP_VTCORE_KEY_F1); expect("\033OP"); + K(.key = WSAP_VTCORE_KEY_F5); expect("\033[15~"); + K(.key = WSAP_VTCORE_KEY_F12); expect("\033[24~"); + K(.key = WSAP_VTCORE_KEY_RETURN); expect("\r"); + K(.key = WSAP_VTCORE_KEY_ESCAPE); expect("\033"); + K(.key = WSAP_VTCORE_KEY_TAB); expect("\t"); + K(.key = WSAP_VTCORE_KEY_TAB, .mods = WSAP_VTCORE_MOD_SHIFT); expect("\033[Z"); + K(.key = WSAP_VTCORE_KEY_BACKSPACE); expect("\177"); + K(.key = WSAP_VTCORE_KEY_RIGHT, .mods = WSAP_VTCORE_MOD_CTRL); expect("\033[1;5C"); + K(.key = WSAP_VTCORE_KEY_F5, .mods = WSAP_VTCORE_MOD_SHIFT); expect("\033[15;2~"); + K(.key = WSAP_VTCORE_KEY_DELETE, .mods = WSAP_VTCORE_MOD_CTRL); expect("\033[3;5~"); m.backarrow_bs = true; - K(.key = TERM_KEY_BACKSPACE); expect("\010"); + K(.key = WSAP_VTCORE_KEY_BACKSPACE); expect("\010"); m.backarrow_bs = false; m.app_cursor = true; - K(.key = TERM_KEY_UP); expect("\033OA"); - K(.key = TERM_KEY_END); expect("\033OF"); + K(.key = WSAP_VTCORE_KEY_UP); expect("\033OA"); + K(.key = WSAP_VTCORE_KEY_END); expect("\033OF"); - K(.key = TERM_KEY_UP, .mods = TERM_MOD_CTRL); expect("\033[1;5A"); + K(.key = WSAP_VTCORE_KEY_UP, .mods = WSAP_VTCORE_MOD_CTRL); expect("\033[1;5A"); m.app_cursor = false; typed('a', 0); expect("a"); typed(0x00E9, 0); expect("\xc3\xa9"); K(.codepoint = 'a', .shifted = 'A', .base = 'a', .text = 'A', - .mods = TERM_MOD_SHIFT); expect("A"); - K(.action = TERM_KEY_RELEASE, .codepoint = 'a', .text = 'a'); expect(""); + .mods = WSAP_VTCORE_MOD_SHIFT); expect("A"); + K(.action = WSAP_VTCORE_KEY_RELEASE, .codepoint = 'a', .text = 'a'); expect(""); - typed('c', TERM_MOD_CTRL); expect("\003"); - typed('a', TERM_MOD_CTRL); expect("\001"); - typed('\\', TERM_MOD_CTRL); expect("\034"); - typed(' ', TERM_MOD_CTRL); assert(out_len == 1 && out[0] == 0); + typed('c', WSAP_VTCORE_MOD_CTRL); expect("\003"); + typed('a', WSAP_VTCORE_MOD_CTRL); expect("\001"); + typed('\\', WSAP_VTCORE_MOD_CTRL); expect("\034"); + typed(' ', WSAP_VTCORE_MOD_CTRL); assert(out_len == 1 && out[0] == 0); K(.codepoint = '2', .shifted = '@', .base = '2', .text = '@', - .mods = TERM_MOD_CTRL | TERM_MOD_SHIFT); + .mods = WSAP_VTCORE_MOD_CTRL | WSAP_VTCORE_MOD_SHIFT); assert(out_len == 1 && out[0] == 0); - typed('b', TERM_MOD_ALT); expect("\033b"); - typed('b', TERM_MOD_ALT | TERM_MOD_CTRL); expect("\033\002"); - K(.key = TERM_KEY_BACKSPACE, .mods = TERM_MOD_ALT); expect("\033\177"); - K(.key = TERM_KEY_RETURN, .mods = TERM_MOD_ALT); expect("\033\r"); - K(.key = TERM_KEY_TAB, .mods = TERM_MOD_ALT); expect("\033\t"); - K(.key = TERM_KEY_TAB, .mods = TERM_MOD_ALT | TERM_MOD_SHIFT); expect("\033[Z"); - K(.key = TERM_KEY_ESCAPE, .mods = TERM_MOD_ALT); expect("\033"); + typed('b', WSAP_VTCORE_MOD_ALT); expect("\033b"); + typed('b', WSAP_VTCORE_MOD_ALT | WSAP_VTCORE_MOD_CTRL); expect("\033\002"); + K(.key = WSAP_VTCORE_KEY_BACKSPACE, .mods = WSAP_VTCORE_MOD_ALT); expect("\033\177"); + K(.key = WSAP_VTCORE_KEY_RETURN, .mods = WSAP_VTCORE_MOD_ALT); expect("\033\r"); + K(.key = WSAP_VTCORE_KEY_TAB, .mods = WSAP_VTCORE_MOD_ALT); expect("\033\t"); + K(.key = WSAP_VTCORE_KEY_TAB, .mods = WSAP_VTCORE_MOD_ALT | WSAP_VTCORE_MOD_SHIFT); expect("\033[Z"); + K(.key = WSAP_VTCORE_KEY_ESCAPE, .mods = WSAP_VTCORE_MOD_ALT); expect("\033"); - K(.key = TERM_KEY_LEFT, .mods = TERM_MOD_ALT); expect("\033[1;3D"); + K(.key = WSAP_VTCORE_KEY_LEFT, .mods = WSAP_VTCORE_MOD_ALT); expect("\033[1;3D"); { char b_null[16]; - struct term_input_result r = term_input_encode_key( + struct wsap_vtcore_input_result r = wsap_vtcore_input_encode_key( NULL, - &(struct term_key_event){ .key = TERM_KEY_UP, .action = TERM_KEY_PRESS }, - &(struct term_modes){0}, + &(struct wsap_vtcore_key_event){ .key = WSAP_VTCORE_KEY_UP, .action = WSAP_VTCORE_KEY_PRESS }, + &(struct wsap_vtcore_modes){0}, b_null, sizeof(b_null)); - assert(r.status == TERM_INPUT_BYTES && r.len == 3 && !memcmp(b_null, "\033[A", 3)); + assert(r.status == WSAP_VTCORE_INPUT_BYTES && r.len == 3 && !memcmp(b_null, "\033[A", 3)); } K(.codepoint = 'b', .base = 'b', .text = 0x222B, .text_deferred = true); expect(""); - K(.key = TERM_KEY_KP_DELETE, .keypad = TERM_KEY_KP_DECIMAL); expect("\033[3~"); - K(.key = TERM_KEY_KP_ENTER, .keypad = TERM_KEY_KP_ENTER); expect("\r"); - K(.key = TERM_KEY_KP_LEFT, .keypad = TERM_KEY_KP_4); expect("\033[D"); + K(.key = WSAP_VTCORE_KEY_KP_DELETE, .keypad = WSAP_VTCORE_KEY_KP_DECIMAL); expect("\033[3~"); + K(.key = WSAP_VTCORE_KEY_KP_ENTER, .keypad = WSAP_VTCORE_KEY_KP_ENTER); expect("\r"); + K(.key = WSAP_VTCORE_KEY_KP_LEFT, .keypad = WSAP_VTCORE_KEY_KP_4); expect("\033[D"); m.app_keypad = true; - K(.key = TERM_KEY_KP_END, .keypad = TERM_KEY_KP_1); expect("\033Oq"); - K(.key = TERM_KEY_KP_ENTER, .keypad = TERM_KEY_KP_ENTER); expect("\033OM"); - K(.key = TERM_KEY_KP_ADD, .keypad = TERM_KEY_KP_ADD); expect("\033Ok"); + K(.key = WSAP_VTCORE_KEY_KP_END, .keypad = WSAP_VTCORE_KEY_KP_1); expect("\033Oq"); + K(.key = WSAP_VTCORE_KEY_KP_ENTER, .keypad = WSAP_VTCORE_KEY_KP_ENTER); expect("\033OM"); + K(.key = WSAP_VTCORE_KEY_KP_ADD, .keypad = WSAP_VTCORE_KEY_KP_ADD); expect("\033Ok"); m.app_keypad = false; mode(1); - K(.key = TERM_KEY_ESCAPE); expect("\033[27u"); - K(.key = TERM_KEY_DELETE); expect("\033[3~"); - K(.key = TERM_KEY_F3); expect("\033[13~"); - K(.key = TERM_KEY_KP_ENTER, .keypad = TERM_KEY_KP_ENTER); expect("\033[57414u"); - typed('i', TERM_MOD_CTRL); expect("\033[105;5u"); - K(.key = TERM_KEY_RETURN, .mods = TERM_MOD_CTRL); expect("\033[13;5u"); + K(.key = WSAP_VTCORE_KEY_ESCAPE); expect("\033[27u"); + K(.key = WSAP_VTCORE_KEY_DELETE); expect("\033[3~"); + K(.key = WSAP_VTCORE_KEY_F3); expect("\033[13~"); + K(.key = WSAP_VTCORE_KEY_KP_ENTER, .keypad = WSAP_VTCORE_KEY_KP_ENTER); expect("\033[57414u"); + typed('i', WSAP_VTCORE_MOD_CTRL); expect("\033[105;5u"); + K(.key = WSAP_VTCORE_KEY_RETURN, .mods = WSAP_VTCORE_MOD_CTRL); expect("\033[13;5u"); typed('a', 0); expect("a"); - K(.key = TERM_KEY_RETURN); expect("\r"); + K(.key = WSAP_VTCORE_KEY_RETURN); expect("\r"); - K(.key = TERM_KEY_UP, .action = TERM_KEY_RELEASE); expect(""); - K(.key = TERM_KEY_LSHIFT); expect(""); + K(.key = WSAP_VTCORE_KEY_UP, .action = WSAP_VTCORE_KEY_RELEASE); expect(""); + K(.key = WSAP_VTCORE_KEY_LSHIFT); expect(""); mode(1 | 4); K(.codepoint = 'a', .shifted = 'A', .base = 'a', .text = 'A', - .mods = TERM_MOD_CTRL | TERM_MOD_SHIFT); expect("\033[97:65;6u"); + .mods = WSAP_VTCORE_MOD_CTRL | WSAP_VTCORE_MOD_SHIFT); expect("\033[97:65;6u"); mode(1 | 2 | 8); - K(.key = TERM_KEY_ESCAPE); expect("\033[27;1u"); - K(.key = TERM_KEY_ESCAPE, .action = TERM_KEY_REPEAT); expect("\033[27;1:2u"); - K(.key = TERM_KEY_ESCAPE, .action = TERM_KEY_RELEASE); expect("\033[27;1:3u"); - K(.key = TERM_KEY_UP, .action = TERM_KEY_REPEAT); expect("\033[1;1:2A"); + K(.key = WSAP_VTCORE_KEY_ESCAPE); expect("\033[27;1u"); + K(.key = WSAP_VTCORE_KEY_ESCAPE, .action = WSAP_VTCORE_KEY_REPEAT); expect("\033[27;1:2u"); + K(.key = WSAP_VTCORE_KEY_ESCAPE, .action = WSAP_VTCORE_KEY_RELEASE); expect("\033[27;1:3u"); + K(.key = WSAP_VTCORE_KEY_UP, .action = WSAP_VTCORE_KEY_REPEAT); expect("\033[1;1:2A"); mode(31); K(.codepoint = 1092, .base = 'a', .text = 1092); expect("\033[1092::97;1;1092u"); K(.codepoint = 'a', .shifted = 'A', .base = 'a', .text = 'A', - .mods = TERM_MOD_SHIFT); expect("\033[97:65;2;65u"); + .mods = WSAP_VTCORE_MOD_SHIFT); expect("\033[97:65;2;65u"); - K(.action = TERM_KEY_RELEASE, .codepoint = 'a', .base = 'a', .text = 'a'); + K(.action = WSAP_VTCORE_KEY_RELEASE, .codepoint = 'a', .base = 'a', .text = 'a'); expect("\033[97;1:3u"); mode(1 | 2 | 8); - K(.key = TERM_KEY_LSHIFT, .mods = TERM_MOD_SHIFT); expect("\033[57441;2u"); - K(.key = TERM_KEY_RSHIFT, .mods = TERM_MOD_SHIFT); expect("\033[57447;2u"); - K(.key = TERM_KEY_LSHIFT, .action = TERM_KEY_RELEASE, .mods = TERM_MOD_SHIFT); + K(.key = WSAP_VTCORE_KEY_LSHIFT, .mods = WSAP_VTCORE_MOD_SHIFT); expect("\033[57441;2u"); + K(.key = WSAP_VTCORE_KEY_RSHIFT, .mods = WSAP_VTCORE_MOD_SHIFT); expect("\033[57447;2u"); + K(.key = WSAP_VTCORE_KEY_LSHIFT, .action = WSAP_VTCORE_KEY_RELEASE, .mods = WSAP_VTCORE_MOD_SHIFT); expect("\033[57441;2:3u"); - K(.key = TERM_KEY_RSHIFT, .action = TERM_KEY_RELEASE, .mods = TERM_MOD_SHIFT); + K(.key = WSAP_VTCORE_KEY_RSHIFT, .action = WSAP_VTCORE_KEY_RELEASE, .mods = WSAP_VTCORE_MOD_SHIFT); expect("\033[57447;1:3u"); - K(.key = TERM_KEY_ISO_LEVEL3_SHIFT); expect("\033[57453;1u"); - K(.key = TERM_KEY_ISO_LEVEL5_SHIFT); expect("\033[57454;1u"); - K(.key = TERM_KEY_CAPS_LOCK); expect("\033[57358;65u"); + K(.key = WSAP_VTCORE_KEY_ISO_LEVEL3_SHIFT); expect("\033[57453;1u"); + K(.key = WSAP_VTCORE_KEY_ISO_LEVEL5_SHIFT); expect("\033[57454;1u"); + K(.key = WSAP_VTCORE_KEY_CAPS_LOCK); expect("\033[57358;65u"); mode(1 | 2 | 4); - K(.key = TERM_KEY_CAPS_LOCK); expect(""); - K(.key = TERM_KEY_CAPS_LOCK, .action = TERM_KEY_RELEASE); expect(""); + K(.key = WSAP_VTCORE_KEY_CAPS_LOCK); expect(""); + K(.key = WSAP_VTCORE_KEY_CAPS_LOCK, .action = WSAP_VTCORE_KEY_RELEASE); expect(""); mode(1 | 2 | 4 | 8); - K(.key = TERM_KEY_CAPS_LOCK); expect("\033[57358;65u"); - K(.key = TERM_KEY_CAPS_LOCK, .action = TERM_KEY_RELEASE, - .mods = TERM_MOD_CAPS); expect("\033[57358;65:3u"); + K(.key = WSAP_VTCORE_KEY_CAPS_LOCK); expect("\033[57358;65u"); + K(.key = WSAP_VTCORE_KEY_CAPS_LOCK, .action = WSAP_VTCORE_KEY_RELEASE, + .mods = WSAP_VTCORE_MOD_CAPS); expect("\033[57358;65:3u"); mode(1); - K(.key = TERM_KEY_LEFT, .mods = TERM_MOD_NUM); expect("\033[1;129D"); - K(.key = TERM_KEY_LEFT); expect("\033[D"); - K(.key = TERM_KEY_F1, .mods = TERM_MOD_CAPS); expect("\033[1;65P"); - K(.codepoint = 'a', .base = 'a', .mods = TERM_MOD_CTRL | TERM_MOD_CAPS); + K(.key = WSAP_VTCORE_KEY_LEFT, .mods = WSAP_VTCORE_MOD_NUM); expect("\033[1;129D"); + K(.key = WSAP_VTCORE_KEY_LEFT); expect("\033[D"); + K(.key = WSAP_VTCORE_KEY_F1, .mods = WSAP_VTCORE_MOD_CAPS); expect("\033[1;65P"); + K(.codepoint = 'a', .base = 'a', .mods = WSAP_VTCORE_MOD_CTRL | WSAP_VTCORE_MOD_CAPS); expect("\033[97;69u"); - K(.codepoint = 'a', .base = 'a', .mods = TERM_MOD_CTRL); + K(.codepoint = 'a', .base = 'a', .mods = WSAP_VTCORE_MOD_CTRL); expect("\033[97;5u"); - K(.codepoint = 'a', .base = 'a', .text = 'A', .mods = TERM_MOD_CAPS); + K(.codepoint = 'a', .base = 'a', .text = 'A', .mods = WSAP_VTCORE_MOD_CAPS); expect("A"); - K(.key = TERM_KEY_RETURN, .mods = TERM_MOD_CAPS); expect("\r"); + K(.key = WSAP_VTCORE_KEY_RETURN, .mods = WSAP_VTCORE_MOD_CAPS); expect("\r"); mode(1 | 8); - K(.codepoint = 'a', .base = 'a', .text = 'A', .mods = TERM_MOD_CAPS); + K(.codepoint = 'a', .base = 'a', .text = 'A', .mods = WSAP_VTCORE_MOD_CAPS); expect("\033[97;65u"); - K(.key = TERM_KEY_RETURN, .mods = TERM_MOD_CAPS); expect("\033[13;65u"); + K(.key = WSAP_VTCORE_KEY_RETURN, .mods = WSAP_VTCORE_MOD_CAPS); expect("\033[13;65u"); mode(0); - K(.key = TERM_KEY_LEFT, .mods = TERM_MOD_NUM); expect("\033[D"); - K(.key = TERM_KEY_F1, .mods = TERM_MOD_CAPS); expect("\033OP"); - K(.codepoint = 'a', .base = 'a', .mods = TERM_MOD_CTRL | TERM_MOD_CAPS); + K(.key = WSAP_VTCORE_KEY_LEFT, .mods = WSAP_VTCORE_MOD_NUM); expect("\033[D"); + K(.key = WSAP_VTCORE_KEY_F1, .mods = WSAP_VTCORE_MOD_CAPS); expect("\033OP"); + K(.codepoint = 'a', .base = 'a', .mods = WSAP_VTCORE_MOD_CTRL | WSAP_VTCORE_MOD_CAPS); expect("\001"); mode(0); - MOUSE(2, 1, .kind = TERM_MOUSE_PRESS); + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_PRESS); assert(out_len == 0 && !consumed); - m.mouse = TERM_MOUSE_NORMAL; - MOUSE(2, 1, .kind = TERM_MOUSE_PRESS); expect("\033[M\040\043\042"); - MOUSE(2, 1, .kind = TERM_MOUSE_RELEASE); expect("\033[M\043\043\042"); - MOUSE(2, 1, .kind = TERM_MOUSE_MOTION); expect(""); + m.mouse = WSAP_VTCORE_MOUSE_NORMAL; + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_PRESS); expect("\033[M\040\043\042"); + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_RELEASE); expect("\033[M\043\043\042"); + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_MOTION); expect(""); - MOUSE(2, 1, .mods = TERM_MOD_SHIFT); + MOUSE(2, 1, .mods = WSAP_VTCORE_MOD_SHIFT); assert(out_len == 0 && !consumed); - MOUSE(200, 99, .kind = TERM_MOUSE_PRESS); + MOUSE(200, 99, .kind = WSAP_VTCORE_MOUSE_PRESS); assert(out_len == 0 && consumed); - m.mouse_encoding = TERM_MOUSE_ENC_SGR; - MOUSE(2, 1, .kind = TERM_MOUSE_PRESS); expect("\033[<0;3;2M"); - MOUSE(2, 1, .kind = TERM_MOUSE_RELEASE); expect("\033[<0;3;2m"); - MOUSE(2, 1, .mods = TERM_MOD_CTRL); expect("\033[<16;3;2M"); - MOUSE(2, 1, .button = TERM_MOUSE_WHEEL_UP); expect("\033[<64;3;2M"); - m.mouse_encoding = TERM_MOUSE_ENC_SGR_PIXELS; + m.mouse_encoding = WSAP_VTCORE_MOUSE_ENC_SGR; + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_PRESS); expect("\033[<0;3;2M"); + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_RELEASE); expect("\033[<0;3;2m"); + MOUSE(2, 1, .mods = WSAP_VTCORE_MOD_CTRL); expect("\033[<16;3;2M"); + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_WHEEL_UP); expect("\033[<64;3;2M"); + m.mouse_encoding = WSAP_VTCORE_MOUSE_ENC_SGR_PIXELS; MOUSE(2, 1, .pixel = { .x = 25, .y = 17 }); expect("\033[<0;26;18M"); - m.mouse_encoding = TERM_MOUSE_ENC_URXVT; - MOUSE(2, 1, .kind = TERM_MOUSE_PRESS); expect("\033[32;3;2M"); - m.mouse_encoding = TERM_MOUSE_ENC_X10; + m.mouse_encoding = WSAP_VTCORE_MOUSE_ENC_URXVT; + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_PRESS); expect("\033[32;3;2M"); + m.mouse_encoding = WSAP_VTCORE_MOUSE_ENC_X10; - m.mouse = TERM_MOUSE_BUTTON; - MOUSE(2, 1, .kind = TERM_MOUSE_MOTION, .button = TERM_MOUSE_BUTTON_NONE); expect(""); - MOUSE(2, 1, .kind = TERM_MOUSE_MOTION, .button = TERM_MOUSE_BUTTON_PRIMARY); + m.mouse = WSAP_VTCORE_MOUSE_BUTTON; + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_MOTION, .button = WSAP_VTCORE_MOUSE_BUTTON_NONE); expect(""); + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_MOTION, .button = WSAP_VTCORE_MOUSE_BUTTON_PRIMARY); expect("\033[M\100\043\042"); - m.mouse_encoding = TERM_MOUSE_ENC_SGR; - MOUSE(2, 1, .kind = TERM_MOUSE_MOTION, .button = TERM_MOUSE_BUTTON_NONE); expect(""); - MOUSE(2, 1, .kind = TERM_MOUSE_MOTION, .button = TERM_MOUSE_BUTTON_PRIMARY, .mods = TERM_MOD_CTRL); + m.mouse_encoding = WSAP_VTCORE_MOUSE_ENC_SGR; + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_MOTION, .button = WSAP_VTCORE_MOUSE_BUTTON_NONE); expect(""); + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_MOTION, .button = WSAP_VTCORE_MOUSE_BUTTON_PRIMARY, .mods = WSAP_VTCORE_MOD_CTRL); expect("\033[<48;3;2M"); - m.mouse = TERM_MOUSE_ANY; - MOUSE(2, 1, .kind = TERM_MOUSE_MOTION, .button = TERM_MOUSE_BUTTON_NONE); expect("\033[<35;3;2M"); - m.mouse_encoding = TERM_MOUSE_ENC_X10; - MOUSE(2, 1, .button = TERM_MOUSE_WHEEL_UP); expect("\033[M\140\043\042"); + m.mouse = WSAP_VTCORE_MOUSE_ANY; + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_MOTION, .button = WSAP_VTCORE_MOUSE_BUTTON_NONE); expect("\033[<35;3;2M"); + m.mouse_encoding = WSAP_VTCORE_MOUSE_ENC_X10; + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_WHEEL_UP); expect("\033[M\140\043\042"); - m.mouse = TERM_MOUSE_X10; - MOUSE(2, 1, .kind = TERM_MOUSE_PRESS); expect("\033[M\040\043\042"); - MOUSE(2, 1, .kind = TERM_MOUSE_RELEASE); expect(""); + m.mouse = WSAP_VTCORE_MOUSE_X10; + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_PRESS); expect("\033[M\040\043\042"); + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_RELEASE); expect(""); { - struct term_keyboard_state s2 = {0}; - struct term_modes m2 = { .keyboard = 1 | 2 | 8, .grid = { .x = 80, .y = 24 } }; + struct wsap_vtcore_keyboard_state s2 = {0}; + struct wsap_vtcore_modes m2 = { .keyboard = 1 | 2 | 8, .grid = { .x = 80, .y = 24 } }; char b2[64]; - struct term_key_event sh = { - .key = TERM_KEY_LSHIFT, .action = TERM_KEY_PRESS, - .mods = TERM_MOD_SHIFT, + struct wsap_vtcore_key_event sh = { + .key = WSAP_VTCORE_KEY_LSHIFT, .action = WSAP_VTCORE_KEY_PRESS, + .mods = WSAP_VTCORE_MOD_SHIFT, }; - term_keyboard_update(&s2, &sh); - struct term_key_event rsh = { - .key = TERM_KEY_RSHIFT, .action = TERM_KEY_PRESS, - .mods = TERM_MOD_SHIFT, + wsap_vtcore_keyboard_update(&s2, &sh); + struct wsap_vtcore_key_event rsh = { + .key = WSAP_VTCORE_KEY_RSHIFT, .action = WSAP_VTCORE_KEY_PRESS, + .mods = WSAP_VTCORE_MOD_SHIFT, }; - term_keyboard_update(&s2, &rsh); + wsap_vtcore_keyboard_update(&s2, &rsh); - struct term_key_event rel = { - .key = TERM_KEY_LSHIFT, .action = TERM_KEY_RELEASE, - .mods = TERM_MOD_SHIFT, + struct wsap_vtcore_key_event rel = { + .key = WSAP_VTCORE_KEY_LSHIFT, .action = WSAP_VTCORE_KEY_RELEASE, + .mods = WSAP_VTCORE_MOD_SHIFT, }; - term_keyboard_update(&s2, &rel); - struct term_input_result r = - term_input_encode_key(&s2, &rel, &m2, b2, sizeof(b2)); - assert(r.status == TERM_INPUT_BYTES); + wsap_vtcore_keyboard_update(&s2, &rel); + struct wsap_vtcore_input_result r = + wsap_vtcore_input_encode_key(&s2, &rel, &m2, b2, sizeof(b2)); + assert(r.status == WSAP_VTCORE_INPUT_BYTES); assert(!memcmp(b2, "\033[57441;2:3u", r.len)); - struct term_key_event rrel = { - .key = TERM_KEY_RSHIFT, .action = TERM_KEY_RELEASE, - .mods = TERM_MOD_SHIFT, + struct wsap_vtcore_key_event rrel = { + .key = WSAP_VTCORE_KEY_RSHIFT, .action = WSAP_VTCORE_KEY_RELEASE, + .mods = WSAP_VTCORE_MOD_SHIFT, }; - term_keyboard_update(&s2, &rrel); - r = term_input_encode_key(&s2, &rrel, &m2, b2, sizeof(b2)); + wsap_vtcore_keyboard_update(&s2, &rrel); + r = wsap_vtcore_input_encode_key(&s2, &rrel, &m2, b2, sizeof(b2)); assert(!memcmp(b2, "\033[57447;1:3u", r.len)); } { char tiny[4]; - struct term_input_result r = term_input_encode_key( + struct wsap_vtcore_input_result r = wsap_vtcore_input_encode_key( &st, - &(struct term_key_event){ - .key = TERM_KEY_DELETE, .action = TERM_KEY_PRESS, - .mods = TERM_MOD_CTRL | TERM_MOD_ALT | TERM_MOD_SHIFT, + &(struct wsap_vtcore_key_event){ + .key = WSAP_VTCORE_KEY_DELETE, .action = WSAP_VTCORE_KEY_PRESS, + .mods = WSAP_VTCORE_MOD_CTRL | WSAP_VTCORE_MOD_ALT | WSAP_VTCORE_MOD_SHIFT, }, - &(struct term_modes){ .grid = { .x = 80, .y = 24 } }, + &(struct wsap_vtcore_modes){ .grid = { .x = 80, .y = 24 } }, tiny, sizeof(tiny)); - assert(r.status == TERM_INPUT_BUFFER_FULL && r.len == 0); + assert(r.status == WSAP_VTCORE_INPUT_BUFFER_FULL && r.len == 0); } { - struct term_keyboard_state s5 = {0}; - struct term_key_event bad = { - .key = UINT16_MAX, .action = TERM_KEY_PRESS, + struct wsap_vtcore_keyboard_state s5 = {0}; + struct wsap_vtcore_key_event bad = { + .key = UINT16_MAX, .action = WSAP_VTCORE_KEY_PRESS, }; - term_keyboard_update(&s5, &bad); - assert(!term_keyboard_key_down(&s5, TERM_KEY_LSHIFT)); - struct term_input_result r = - term_input_encode_key(&s5, &bad, &m, out, sizeof(out)); - assert(r.status == TERM_INPUT_UNHANDLED && r.len == 0); - - struct term_key_event bad_kp = { - .key = TERM_KEY_KP_1, .keypad = UINT16_MAX, - .action = TERM_KEY_PRESS, + wsap_vtcore_keyboard_update(&s5, &bad); + assert(!wsap_vtcore_keyboard_key_down(&s5, WSAP_VTCORE_KEY_LSHIFT)); + struct wsap_vtcore_input_result r = + wsap_vtcore_input_encode_key(&s5, &bad, &m, out, sizeof(out)); + assert(r.status == WSAP_VTCORE_INPUT_UNHANDLED && r.len == 0); + + struct wsap_vtcore_key_event bad_kp = { + .key = WSAP_VTCORE_KEY_KP_1, .keypad = UINT16_MAX, + .action = WSAP_VTCORE_KEY_PRESS, }; m.app_keypad = true; - r = term_input_encode_key(&s5, &bad_kp, &m, out, sizeof(out)); + r = wsap_vtcore_input_encode_key(&s5, &bad_kp, &m, out, sizeof(out)); assert(r.len == 0); m.app_keypad = false; } { - struct term_key_event deferred = { - .action = TERM_KEY_PRESS, .codepoint = 'a', .text = 'a', + struct wsap_vtcore_key_event deferred = { + .action = WSAP_VTCORE_KEY_PRESS, .codepoint = 'a', .text = 'a', .text_deferred = true, }; - struct term_input_result r = term_input_encode_key( - &st, &deferred, &(struct term_modes){0}, out, sizeof(out)); - assert(r.status == TERM_INPUT_UNHANDLED && r.len == 0); - struct term_modes kitty = { .keyboard = TERM_KEYBOARD_ALL_KEYS }; - r = term_input_encode_key(&st, &deferred, &kitty, out, sizeof(out)); - assert(r.status == TERM_INPUT_BYTES && r.len == strlen("\033[97u")); + struct wsap_vtcore_input_result r = wsap_vtcore_input_encode_key( + &st, &deferred, &(struct wsap_vtcore_modes){0}, out, sizeof(out)); + assert(r.status == WSAP_VTCORE_INPUT_UNHANDLED && r.len == 0); + struct wsap_vtcore_modes kitty = { .keyboard = WSAP_VTCORE_KEYBOARD_ALL_KEYS }; + r = wsap_vtcore_input_encode_key(&st, &deferred, &kitty, out, sizeof(out)); + assert(r.status == WSAP_VTCORE_INPUT_BYTES && r.len == strlen("\033[97u")); assert(!memcmp(out, "\033[97u", r.len)); - deferred.action = TERM_KEY_RELEASE; - r = term_input_encode_key(&st, &deferred, &kitty, out, sizeof(out)); - assert(r.status == TERM_INPUT_CONSUMED && r.len == 0); + deferred.action = WSAP_VTCORE_KEY_RELEASE; + r = wsap_vtcore_input_encode_key(&st, &deferred, &kitty, out, sizeof(out)); + assert(r.status == WSAP_VTCORE_INPUT_CONSUMED && r.len == 0); } - m.mouse = TERM_MOUSE_ANY; - m.mouse_encoding = TERM_MOUSE_ENC_SGR; - MOUSE(2, 1, .button = TERM_MOUSE_BUTTON_EXTRA_1); expect("\033[<128;3;2M"); - MOUSE(2, 1, .button = TERM_MOUSE_BUTTON_EXTRA_2); expect("\033[<129;3;2M"); - MOUSE(2, 1, .button = TERM_MOUSE_BUTTON_EXTRA_3); expect("\033[<130;3;2M"); - MOUSE(2, 1, .button = TERM_MOUSE_BUTTON_EXTRA_4); expect("\033[<131;3;2M"); - MOUSE(2, 1, .button = TERM_MOUSE_WHEEL_LEFT); expect("\033[<66;3;2M"); - MOUSE(2, 1, .button = TERM_MOUSE_WHEEL_RIGHT); expect("\033[<67;3;2M"); + m.mouse = WSAP_VTCORE_MOUSE_ANY; + m.mouse_encoding = WSAP_VTCORE_MOUSE_ENC_SGR; + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_BUTTON_EXTRA_1); expect("\033[<128;3;2M"); + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_BUTTON_EXTRA_2); expect("\033[<129;3;2M"); + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_BUTTON_EXTRA_3); expect("\033[<130;3;2M"); + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_BUTTON_EXTRA_4); expect("\033[<131;3;2M"); + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_WHEEL_LEFT); expect("\033[<66;3;2M"); + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_WHEEL_RIGHT); expect("\033[<67;3;2M"); /* Ensure Alt modifier does not collide with extra buttons */ - MOUSE(2, 1, .button = TERM_MOUSE_BUTTON_PRIMARY, .mods = TERM_MOD_ALT); expect("\033[<8;3;2M"); - MOUSE(2, 1, .button = TERM_MOUSE_BUTTON_EXTRA_1, .mods = TERM_MOD_ALT); expect("\033[<136;3;2M"); - MOUSE(2, 1, .button = TERM_MOUSE_BUTTON_MIDDLE, .mods = TERM_MOD_ALT); expect("\033[<9;3;2M"); - MOUSE(2, 1, .button = TERM_MOUSE_BUTTON_EXTRA_2, .mods = TERM_MOD_ALT); expect("\033[<137;3;2M"); - MOUSE(2, 1, .kind = TERM_MOUSE_RELEASE, .button = TERM_MOUSE_BUTTON_EXTRA_1); expect("\033[<128;3;2m"); + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_BUTTON_PRIMARY, .mods = WSAP_VTCORE_MOD_ALT); expect("\033[<8;3;2M"); + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_BUTTON_EXTRA_1, .mods = WSAP_VTCORE_MOD_ALT); expect("\033[<136;3;2M"); + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_BUTTON_MIDDLE, .mods = WSAP_VTCORE_MOD_ALT); expect("\033[<9;3;2M"); + MOUSE(2, 1, .button = WSAP_VTCORE_MOUSE_BUTTON_EXTRA_2, .mods = WSAP_VTCORE_MOD_ALT); expect("\033[<137;3;2M"); + MOUSE(2, 1, .kind = WSAP_VTCORE_MOUSE_RELEASE, .button = WSAP_VTCORE_MOUSE_BUTTON_EXTRA_1); expect("\033[<128;3;2m"); { /* A host sizes the paste buffer from the text alone. */ static const char text[] = "ls\r\n\033[31m\u202erm\x7f\t\xe4\xb8\xad"; static const char want[] = "\033[200~ls\r[31mrm\t\xe4\xb8\xad\033[201~"; - char buf[sizeof(text) - 1 + TERM_PASTE_EXTRA]; - struct term_modes bracketed = { .bracketed_paste = true }; - struct term_input_result r = - term_input_encode_paste(&bracketed, text, sizeof(text) - 1, buf, sizeof(buf)); - assert(r.status == TERM_INPUT_BYTES && r.len == sizeof(want) - 1); + char buf[sizeof(text) - 1 + WSAP_VTCORE_PASTE_EXTRA]; + struct wsap_vtcore_modes bracketed = { .bracketed_paste = true }; + struct wsap_vtcore_input_result r = + wsap_vtcore_input_encode_paste(&bracketed, text, sizeof(text) - 1, buf, sizeof(buf)); + assert(r.status == WSAP_VTCORE_INPUT_BYTES && r.len == sizeof(want) - 1); assert(!memcmp(buf, want, r.len)); - r = term_input_encode_paste(&bracketed, text, sizeof(text) - 1, buf, r.len - 1); - assert(r.status == TERM_INPUT_BUFFER_FULL && r.len == 0); + r = wsap_vtcore_input_encode_paste(&bracketed, text, sizeof(text) - 1, buf, r.len - 1); + assert(r.status == WSAP_VTCORE_INPUT_BUFFER_FULL && r.len == 0); - r = term_input_encode_paste(&bracketed, "\033\a\u2066", 5, buf, sizeof(buf)); - assert(r.status == TERM_INPUT_CONSUMED && r.len == 0); + r = wsap_vtcore_input_encode_paste(&bracketed, "\033\a\u2066", 5, buf, sizeof(buf)); + assert(r.status == WSAP_VTCORE_INPUT_CONSUMED && r.len == 0); - struct term_modes plain = {0}; - r = term_input_encode_paste(&plain, "a\nb", 3, buf, 3); - assert(r.status == TERM_INPUT_BYTES && r.len == 3 && !memcmp(buf, "a\rb", 3)); + struct wsap_vtcore_modes plain = {0}; + r = wsap_vtcore_input_encode_paste(&plain, "a\nb", 3, buf, 3); + assert(r.status == WSAP_VTCORE_INPUT_BYTES && r.len == 3 && !memcmp(buf, "a\rb", 3)); } { - mode(TERM_KEYBOARD_ALL_KEYS | TERM_KEYBOARD_EVENT_TYPES); - K(.key = TERM_KEY_NUM_LOCK); expect("\033[57360;129u"); - K(.key = TERM_KEY_NUM_LOCK, .action = TERM_KEY_REPEAT, - .mods = TERM_MOD_NUM); expect("\033[57360;129:2u"); - K(.key = TERM_KEY_NUM_LOCK, .action = TERM_KEY_RELEASE, - .mods = TERM_MOD_NUM); expect("\033[57360;129:3u"); - K(.key = TERM_KEY_NUM_LOCK, .mods = TERM_MOD_NUM); expect("\033[57360;1u"); - K(.key = TERM_KEY_SCROLL_LOCK); expect("\033[57359;1u"); + mode(WSAP_VTCORE_KEYBOARD_ALL_KEYS | WSAP_VTCORE_KEYBOARD_EVENT_TYPES); + K(.key = WSAP_VTCORE_KEY_NUM_LOCK); expect("\033[57360;129u"); + K(.key = WSAP_VTCORE_KEY_NUM_LOCK, .action = WSAP_VTCORE_KEY_REPEAT, + .mods = WSAP_VTCORE_MOD_NUM); expect("\033[57360;129:2u"); + K(.key = WSAP_VTCORE_KEY_NUM_LOCK, .action = WSAP_VTCORE_KEY_RELEASE, + .mods = WSAP_VTCORE_MOD_NUM); expect("\033[57360;129:3u"); + K(.key = WSAP_VTCORE_KEY_NUM_LOCK, .mods = WSAP_VTCORE_MOD_NUM); expect("\033[57360;1u"); + K(.key = WSAP_VTCORE_KEY_SCROLL_LOCK); expect("\033[57359;1u"); } { /* UTF-8 writes must report overflow without crossing the capacity. */ - struct term_key_event key = { .action = TERM_KEY_PRESS, .text = 0x4e2d }; - struct term_mouse_event mouse = { - .kind = TERM_MOUSE_PRESS, .button = TERM_MOUSE_BUTTON_PRIMARY, + struct wsap_vtcore_key_event key = { .action = WSAP_VTCORE_KEY_PRESS, .text = 0x4e2d }; + struct wsap_vtcore_mouse_event mouse = { + .kind = WSAP_VTCORE_MOUSE_PRESS, .button = WSAP_VTCORE_MOUSE_BUTTON_PRIMARY, .pos = { .x = 190, .y = 95 }, }; - struct term_modes modes = { - .mouse = TERM_MOUSE_ANY, .mouse_encoding = TERM_MOUSE_ENC_UTF8, + struct wsap_vtcore_modes modes = { + .mouse = WSAP_VTCORE_MOUSE_ANY, .mouse_encoding = WSAP_VTCORE_MOUSE_ENC_UTF8, .grid = { .x = 256, .y = 128 }, }; static const char *const want[] = { "\xe4\xb8\xad", "\033[M \xc3\x9f\xc2\x80" }; @@ -400,14 +400,14 @@ int main(void) size_t len = strlen(want[which]); for (size_t cap = 0; cap <= len + 1; cap++) { memset(buf, '!', sizeof(buf)); - struct term_input_result r = which == 0 - ? term_input_encode_key(NULL, &key, &modes, buf, cap) - : term_input_encode_mouse(&mouse, &modes, buf, cap); + struct wsap_vtcore_input_result r = which == 0 + ? wsap_vtcore_input_encode_key(NULL, &key, &modes, buf, cap) + : wsap_vtcore_input_encode_mouse(&mouse, &modes, buf, cap); assert(buf[cap] == '!'); if (cap < len) { - assert(r.status == TERM_INPUT_BUFFER_FULL && r.len == 0); + assert(r.status == WSAP_VTCORE_INPUT_BUFFER_FULL && r.len == 0); } else { - assert(r.status == TERM_INPUT_BYTES && r.len == len); + assert(r.status == WSAP_VTCORE_INPUT_BYTES && r.len == len); assert(!memcmp(buf, want[which], len)); } } diff --git a/tests/meson.build b/tests/meson.build index 4fda075..c0a0cd0 100644 --- a/tests/meson.build +++ b/tests/meson.build @@ -13,7 +13,7 @@ test_env.set('DYLD_INSERT_LIBRARIES', '') test_env.set('NM', find_program('nm', native: true).full_path()) # [name, sources, dependencies, suites] -term_tests = [ +wsap_vtcore_tests = [ ['unicode-test', files('unicode/unicode_test.c'), [], []], ['term-input-test', files('input_test.c'), [], []], ['term-test', files('term_test.c'), [thread_dep], ['isa']], @@ -34,14 +34,14 @@ term_tests = [ ] test_helpers_inc = include_directories('helpers') -term_test_exes = {} -foreach entry : term_tests +wsap_vtcore_test_exes = {} +foreach entry : wsap_vtcore_tests exe = executable(entry[0], entry[1], c_args: test_c_args, include_directories: test_helpers_inc, - dependencies: [term_internal_dep] + entry[2], + dependencies: [wsap_vtcore_internal_dep] + entry[2], ) - term_test_exes += {entry[0]: exe} + wsap_vtcore_test_exes += {entry[0]: exe} test(entry[0], exe, args: entry[0] == 'write-fuzz-test' ? [get_option('write_fuzz_seeds').to_string()] : [], env: test_env, @@ -56,40 +56,40 @@ if host_machine.cpu_family() == 'x86_64' and cc.get_argument_syntax() == 'gcc' a cc.get_define('__AVX2__', args: get_option('arch_flag') != '' ? [get_option('arch_flag')] : []) == '' foreach level : ['base', 'avx2'] level_env = test_env - level_env.set('TERM_HEADLESS_ISA', level) + level_env.set('WSAP_VTCORE_ISA', level) foreach name : ['term-test', 'spec-test', 'model-test', 'view-test', 'term-input-test', 'hist-test', 'history-text-test'] - test(name + '-' + level, term_test_exes[name], env: level_env, + test(name + '-' + level, wsap_vtcore_test_exes[name], env: level_env, suite: ['unit', 'isa'], timeout: 180) endforeach endforeach endif -# The amalgamation is the core as one term.c, the way a host builds it. The -# tests that use only term.h run again against it. -term_amalgamation = custom_target( +# The amalgamation is the core as one wsap_vtcore.c, the way a host builds +# it. The tests that use only wsap_vtcore.h run again against it. +wsap_vtcore_amalgamation = custom_target( 'term-amalgamation', - output: ['term.c', 'term.h'], + output: ['wsap_vtcore.c', 'wsap_vtcore.h'], depfile: 'term-amalgamation.d', command: [python, files('../tools/amalgamate.py'), meson.project_source_root(), '@OUTDIR@', '@DEPFILE@'], ) -term_amalgamation_lib = static_library( +wsap_vtcore_amalgamation_lib = static_library( 'term-amalgamation', - term_amalgamation[0], + wsap_vtcore_amalgamation[0], dependencies: [m_dep, thread_dep], override_options: ['c_std=c11', 'warning_level=3', 'werror=true'], build_by_default: false, ) -foreach entry : term_tests +foreach entry : wsap_vtcore_tests if entry[0] in ['term-test', 'spec-test', 'view-test', 'dcs-test', 'osc-test', 'history-text-test', 'term-input-test', 'model-test', 'model-row-test', 'resize-property-test', 'api-args-test'] test(entry[0] + '-amalgamation', executable(entry[0] + '-amalgamation', entry[1], c_args: test_c_args, - include_directories: [term_inc, test_helpers_inc], - link_with: term_amalgamation_lib, + include_directories: [wsap_vtcore_inc, test_helpers_inc], + link_with: wsap_vtcore_amalgamation_lib, dependencies: [m_dep, thread_dep] + entry[2], build_by_default: false), env: test_env, suite: ['unit', 'amalgamation'], timeout: 180) @@ -97,9 +97,9 @@ foreach entry : term_tests endforeach test('term-symbols-test', bash, - args: [files('symbols_test.sh'), term_lib.get_static_lib(), - meson.project_source_root() / 'include' / 'term', - term_lib.get_shared_lib()], + args: [files('symbols_test.sh'), wsap_vtcore_lib.get_static_lib(), + meson.project_source_root() / 'include' / 'wsap_vtcore', + wsap_vtcore_lib.get_shared_lib()], env: test_env, suite: 'unit', ) @@ -111,7 +111,7 @@ if cc.has_link_argument('-Wl,--wrap=realloc') and cc.has_link_argument('-Wl,--wr snapshot_failure_test = executable('snapshot-failure-test', 'snapshot_failure_test.c', c_args: test_c_args, link_args: ['-Wl,--wrap=realloc', '-Wl,--wrap=malloc'], - dependencies: [term_internal_dep], + dependencies: [wsap_vtcore_internal_dep], ) test('snapshot-failure-test', snapshot_failure_test, env: test_env, @@ -122,8 +122,8 @@ endif # The project version comes in as a define, so the header macros cannot # drift from meson.build. version_test = executable('version-test', 'version_test.c', - c_args: test_c_args + ['-DTERM_TEST_PROJECT_VERSION="@0@"'.format(meson.project_version())], - dependencies: [term_internal_dep], + c_args: test_c_args + ['-DWSAP_VTCORE_TEST_PROJECT_VERSION="@0@"'.format(meson.project_version())], + dependencies: [wsap_vtcore_internal_dep], ) test('version-test', version_test, env: test_env, @@ -141,10 +141,10 @@ kitty_tests = get_option('kitty').require( host_machine.system() == 'linux' and get_option('b_sanitize') == 'none', error_message: 'The Kitty tests need an unsanitized Linux build', ) -term_kitty_tests = kitty_tests.allowed() -if term_kitty_tests +wsap_vtcore_kitty_tests = kitty_tests.allowed() +if wsap_vtcore_kitty_tests kitty_bridge = shared_library('kitty_bridge', 'extern/kitty/screen_bridge.c', - dependencies: term_internal_dep, + dependencies: wsap_vtcore_internal_dep, ) kitty_env = environment() kitty_env.set('WSAP_KITTY_LIB', kitty_bridge.full_path()) diff --git a/tests/model.c b/tests/model.c index 6c9f288..bd8c6c7 100644 --- a/tests/model.c +++ b/tests/model.c @@ -13,7 +13,7 @@ * current terminal, and the macro names the phase that removes it. */ #include "model.h" -#include "term/unicode/unicode.h" +#include "wsap_vtcore/unicode/unicode.h" #include <limits.h> #include <stdarg.h> @@ -31,10 +31,10 @@ #define STR_KEEP 1024 struct cell { - uint32_t cp[TERM_GRAPHEME_MAX_LEN]; + uint32_t cp[WSAP_VTCORE_GRAPHEME_MAX_LEN]; uint8_t n, width; uint16_t attrs; - term_color fg, bg; + wsap_vtcore_color fg, bg; bool pad; /* the blank that a wide glyph left at a row end */ }; @@ -50,8 +50,8 @@ struct row { }; struct pen { - term_color fg, bg, ul; - uint16_t attrs; /* TERM_ATTR_* style bits and the underline style */ + wsap_vtcore_color fg, bg, ul; + uint16_t attrs; /* WSAP_VTCORE_ATTR_* style bits and the underline style */ bool inverse; }; @@ -99,7 +99,7 @@ struct model { bool tabs[MAX_TABS]; struct keyboard keyboard[2]; /* The last printed glyph, for REP and cluster joins. */ - uint32_t last[TERM_GRAPHEME_MAX_LEN]; + uint32_t last[WSAP_VTCORE_GRAPHEME_MAX_LEN]; int last_n; int prompt; /* screen row of the last OSC 133;A, or -1 */ unsigned flags; @@ -124,14 +124,14 @@ struct model { /* ---- cells and rows ---- */ -static struct cell blank(term_color fg, term_color bg) +static struct cell blank(wsap_vtcore_color fg, wsap_vtcore_color bg) { return (struct cell){ .cp = { ' ' }, .n = 1, .width = 1, .fg = fg, .bg = bg }; } static struct cell default_blank(void) { - return blank(TERM_COLOR_FG, TERM_COLOR_BG); + return blank(WSAP_VTCORE_COLOR_FG, WSAP_VTCORE_COLOR_BG); } static struct row *row_new(int cols) @@ -154,12 +154,12 @@ static void row_cut(struct row *r, int n, int cols) static bool pristine(const struct model *m) { - return m->pen.fg == TERM_COLOR_FG && m->pen.bg == TERM_COLOR_BG; + return m->pen.fg == WSAP_VTCORE_COLOR_FG && m->pen.bg == WSAP_VTCORE_COLOR_BG; } static bool is_ri(uint32_t cp) { - return cp - 0x1F1E6u <= 0x19u && term_grapheme_regional_indicator(cp); + return cp - 0x1F1E6u <= 0x19u && wsap_vtcore_grapheme_regional_indicator(cp); } /* ---- replies ---- */ @@ -185,7 +185,7 @@ static void __attribute__((format(printf, 2, 3))) reply(struct model *m, const c static int history_limit(int requested) { - return requested == 0 ? TERM_SCROLLBACK_DEFAULT : requested < 0 ? 0 : requested; + return requested == 0 ? WSAP_VTCORE_SCROLLBACK_DEFAULT : requested < 0 ? 0 : requested; } static void hist_reflow_tail(struct model *m); @@ -229,7 +229,7 @@ static void hist_push(struct model *m, struct row *r) hist_reflow_tail(m); } -static void term_hist_clear(struct model *m) +static void wsap_vtcore_hist_clear(struct model *m) { for (int i = 0; i < m->hist_len; i++) free(m->hist[i]); m->hist_len = 0; @@ -355,7 +355,7 @@ static int last_text_row(const struct model *m) static void erase_display(struct model *m, int mode) { if (mode == 3) { - term_hist_clear(m); + wsap_vtcore_hist_clear(m); return; } if (mode == 2) { @@ -418,17 +418,17 @@ static void fill_gap(struct row *r, int x) static uint16_t presentation(const uint32_t *cps, int n) { - bool pictographic = term_unicode_extended_pictographic(cps[0]); + bool pictographic = wsap_vtcore_unicode_extended_pictographic(cps[0]); bool emoji = false; for (int i = 1; i < n; i++) { - if (cps[i] == 0xFE0F) return TERM_ATTR_EMOJI; - if (cps[i] == 0xFE0E) return TERM_ATTR_TEXT; - if (cps[i] == 0x20E3 || term_grapheme_regional_indicator(cps[i]) || - (pictographic && (cps[i] == 0x200D || term_grapheme_emoji_modifier(cps[i]) || + if (cps[i] == 0xFE0F) return WSAP_VTCORE_ATTR_EMOJI; + if (cps[i] == 0xFE0E) return WSAP_VTCORE_ATTR_TEXT; + if (cps[i] == 0x20E3 || wsap_vtcore_grapheme_regional_indicator(cps[i]) || + (pictographic && (cps[i] == 0x200D || wsap_vtcore_grapheme_emoji_modifier(cps[i]) || (cps[i] >= 0xE0020 && cps[i] <= 0xE007F)))) emoji = true; } - return emoji ? TERM_ATTR_EMOJI : 0; + return emoji ? WSAP_VTCORE_ATTR_EMOJI : 0; } static void wrap_to_next_row(struct model *m) @@ -443,10 +443,10 @@ static void wrap_to_next_row(struct model *m) static void put_glyph(struct model *m, const uint32_t *cps, int n, uint16_t attrs) { if (n > 1) - attrs = (uint16_t)((attrs & ~(TERM_ATTR_EMOJI | TERM_ATTR_TEXT)) | presentation(cps, n)); - int width = term_unicode_width(cps[0]) == 2 ? 2 : 1; - if (attrs & TERM_ATTR_EMOJI) width = 2; - if (attrs & TERM_ATTR_TEXT) width = 1; + attrs = (uint16_t)((attrs & ~(WSAP_VTCORE_ATTR_EMOJI | WSAP_VTCORE_ATTR_TEXT)) | presentation(cps, n)); + int width = wsap_vtcore_unicode_width(cps[0]) == 2 ? 2 : 1; + if (attrs & WSAP_VTCORE_ATTR_EMOJI) width = 2; + if (attrs & WSAP_VTCORE_ATTR_TEXT) width = 1; if (m->pending) wrap_to_next_row(m); int right = m->cols - 1; struct row *r = m->scr[m->y]; @@ -496,14 +496,14 @@ static void put_glyph(struct model *m, const uint32_t *cps, int n, uint16_t attr static bool joins(uint32_t cp, int width) { if (cp < 0x300) return false; - return width == 0 || term_grapheme_emoji_modifier(cp) || - (width == 1 && term_unicode_spacing_mark(cp)); + return width == 0 || wsap_vtcore_grapheme_emoji_modifier(cp) || + (width == 1 && wsap_vtcore_unicode_spacing_mark(cp)); } static bool cluster_joins(const uint32_t *cps, int n, uint32_t cp, int width) { if (joins(cp, width)) return true; - if (cps[n - 1] == 0x200D) return term_unicode_extended_pictographic(cp); + if (cps[n - 1] == 0x200D) return wsap_vtcore_unicode_extended_pictographic(cp); return n == 1 && is_ri(cp) && is_ri(cps[0]); } @@ -528,10 +528,10 @@ static bool extend_cluster(struct model *m, uint32_t cp, int width) return joins(cp, width); if (!cluster_joins(prev->cp, prev->n, cp, width)) return false; - if (prev->n >= TERM_GRAPHEME_MAX_LEN) + if (prev->n >= WSAP_VTCORE_GRAPHEME_MAX_LEN) return true; struct cell old = *prev; - uint32_t cps[TERM_GRAPHEME_MAX_LEN]; + uint32_t cps[WSAP_VTCORE_GRAPHEME_MAX_LEN]; memcpy(cps, old.cp, (size_t)old.n * sizeof(*cps)); cps[old.n] = cp; int n = old.n + 1; @@ -542,7 +542,7 @@ static bool extend_cluster(struct model *m, uint32_t cp, int width) m->pending = false; memcpy(m->last, cps, (size_t)n * sizeof(*cps)); m->last_n = n; - put_glyph(m, cps, n, (uint16_t)(old.attrs & ~(TERM_ATTR_EMOJI | TERM_ATTR_TEXT))); + put_glyph(m, cps, n, (uint16_t)(old.attrs & ~(WSAP_VTCORE_ATTR_EMOJI | WSAP_VTCORE_ATTR_TEXT))); r = m->scr[m->y]; x = m->pending ? m->cols - 1 : m->x - 1; if (x > 0 && r->c[x].width == 0) x--; @@ -591,7 +591,7 @@ static void print_cp(struct model *m, uint32_t cp) emit(m, cp); return; } - int width = term_unicode_width(cp); + int width = wsap_vtcore_unicode_width(cp); if (!extend_cluster(m, cp, width)) emit(m, cp); } @@ -655,7 +655,7 @@ static void restore_cursor(struct model *m, const struct saved *s) static struct saved initial_saved(void) { return (struct saved){ - .pen = { .fg = TERM_COLOR_FG, .bg = TERM_COLOR_BG }, + .pen = { .fg = WSAP_VTCORE_COLOR_FG, .bg = WSAP_VTCORE_COLOR_BG }, .g = { 'B', 'B' }, }; } @@ -723,28 +723,28 @@ static void insert_chars(struct model *m, int n) static void pen_reset(struct pen *p) { - *p = (struct pen){ .fg = TERM_COLOR_FG, .bg = TERM_COLOR_BG }; + *p = (struct pen){ .fg = WSAP_VTCORE_COLOR_FG, .bg = WSAP_VTCORE_COLOR_BG }; } static void set_underline(uint16_t *attrs, int style) { static const uint16_t flags[] = { - 0, TERM_ATTR_UNDERLINE, TERM_ATTR_DOUBLE_UNDERLINE, - TERM_ATTR_CURLY_UNDERLINE, TERM_ATTR_DOTTED_UNDERLINE, TERM_ATTR_DASHED_UNDERLINE, + 0, WSAP_VTCORE_ATTR_UNDERLINE, WSAP_VTCORE_ATTR_DOUBLE_UNDERLINE, + WSAP_VTCORE_ATTR_CURLY_UNDERLINE, WSAP_VTCORE_ATTR_DOTTED_UNDERLINE, WSAP_VTCORE_ATTR_DASHED_UNDERLINE, }; if ((unsigned)style > 5) style = 1; - *attrs = (uint16_t)((*attrs & ~TERM_ATTR_UNDERLINE_MASK) | flags[style]); + *attrs = (uint16_t)((*attrs & ~WSAP_VTCORE_ATTR_UNDERLINE_MASK) | flags[style]); } /* 38, 48, and 58. Returns the parameters it used after the first. */ -static int extended_color(const struct model *m, int i, term_color *color, bool *ok) +static int extended_color(const struct model *m, int i, wsap_vtcore_color *color, bool *ok) { *ok = false; if (i + 1 >= m->nparam) return 0; if (i + 2 < m->nparam && m->param[i + 1] == 5) { int index = m->param[i + 2]; if (index >= 0 && index <= 255) { - *color = term_color_index(index); + *color = wsap_vtcore_color_index(index); *ok = true; } return 2; @@ -756,7 +756,7 @@ static int extended_color(const struct model *m, int i, term_color *color, bool colon++; int skip = colon >= 4 ? 1 : 0; if (i + 4 + skip >= m->nparam) return 0; - *color = term_color_rgb((uint8_t)m->param[i + 2 + skip], (uint8_t)m->param[i + 3 + skip], + *color = wsap_vtcore_color_rgb((uint8_t)m->param[i + 2 + skip], (uint8_t)m->param[i + 3 + skip], (uint8_t)m->param[i + 4 + skip]); *ok = true; return 4 + skip; @@ -771,13 +771,13 @@ static void sgr(struct model *m) } for (int i = 0; i < m->nparam; i++) { int v = m->param[i]; - term_color color; + wsap_vtcore_color color; bool ok; switch (v) { case 0: pen_reset(p); break; - case 1: p->attrs |= TERM_ATTR_BOLD; break; - case 2: p->attrs |= TERM_ATTR_FAINT; break; - case 3: p->attrs |= TERM_ATTR_ITALIC; break; + case 1: p->attrs |= WSAP_VTCORE_ATTR_BOLD; break; + case 2: p->attrs |= WSAP_VTCORE_ATTR_FAINT; break; + case 3: p->attrs |= WSAP_VTCORE_ATTR_ITALIC; break; case 4: { int style = 1; if (i + 1 < m->nparam && (m->sub & (1u << (i + 1)))) @@ -786,26 +786,26 @@ static void sgr(struct model *m) break; } case 7: p->inverse = true; break; - case 9: p->attrs |= TERM_ATTR_STRIKE; break; + case 9: p->attrs |= WSAP_VTCORE_ATTR_STRIKE; break; case 21: set_underline(&p->attrs, 2); break; - case 22: p->attrs &= (uint16_t)~(TERM_ATTR_BOLD | TERM_ATTR_FAINT); break; - case 23: p->attrs &= (uint16_t)~TERM_ATTR_ITALIC; break; + case 22: p->attrs &= (uint16_t)~(WSAP_VTCORE_ATTR_BOLD | WSAP_VTCORE_ATTR_FAINT); break; + case 23: p->attrs &= (uint16_t)~WSAP_VTCORE_ATTR_ITALIC; break; case 24: set_underline(&p->attrs, 0); break; case 27: p->inverse = false; break; - case 29: p->attrs &= (uint16_t)~TERM_ATTR_STRIKE; break; + case 29: p->attrs &= (uint16_t)~WSAP_VTCORE_ATTR_STRIKE; break; case 38: i += extended_color(m, i, &color, &ok); if (ok) p->fg = color; break; - case 39: p->fg = TERM_COLOR_FG; break; + case 39: p->fg = WSAP_VTCORE_COLOR_FG; break; case 48: i += extended_color(m, i, &color, &ok); if (ok) p->bg = color; break; - case 49: p->bg = TERM_COLOR_BG; break; - case 53: p->attrs |= TERM_ATTR_OVERLINE; break; - case 55: p->attrs &= (uint16_t)~TERM_ATTR_OVERLINE; break; + case 49: p->bg = WSAP_VTCORE_COLOR_BG; break; + case 53: p->attrs |= WSAP_VTCORE_ATTR_OVERLINE; break; + case 55: p->attrs &= (uint16_t)~WSAP_VTCORE_ATTR_OVERLINE; break; case 58: i += extended_color(m, i, &color, &ok); if (ok) p->ul = color; break; case 59: p->ul = 0; break; default: - if (v >= 30 && v <= 37) p->fg = term_color_index(v - 30); - else if (v >= 40 && v <= 47) p->bg = term_color_index(v - 40); - else if (v >= 90 && v <= 97) p->fg = term_color_index(v - 90 + 8); - else if (v >= 100 && v <= 107) p->bg = term_color_index(v - 100 + 8); + if (v >= 30 && v <= 37) p->fg = wsap_vtcore_color_index(v - 30); + else if (v >= 40 && v <= 47) p->bg = wsap_vtcore_color_index(v - 40); + else if (v >= 90 && v <= 97) p->fg = wsap_vtcore_color_index(v - 90 + 8); + else if (v >= 100 && v <= 107) p->bg = wsap_vtcore_color_index(v - 100 + 8); break; } } @@ -818,27 +818,27 @@ static void sgr_report(const struct model *m, char *out, size_t cap) size_t n = 0; out[0] = 0; #define ADD(...) do { int k = snprintf(out + n, cap - n, __VA_ARGS__); if (k > 0) n += (size_t)k; } while (0) - int ul = term_attr_underline(p->attrs); - if (!(p->attrs & (TERM_ATTR_BOLD | TERM_ATTR_FAINT | TERM_ATTR_ITALIC | TERM_ATTR_STRIKE | - TERM_ATTR_OVERLINE | TERM_ATTR_UNDERLINE_MASK)) && - !p->inverse && p->fg == TERM_COLOR_FG && p->bg == TERM_COLOR_BG && !p->ul) + int ul = wsap_vtcore_attr_underline(p->attrs); + if (!(p->attrs & (WSAP_VTCORE_ATTR_BOLD | WSAP_VTCORE_ATTR_FAINT | WSAP_VTCORE_ATTR_ITALIC | WSAP_VTCORE_ATTR_STRIKE | + WSAP_VTCORE_ATTR_OVERLINE | WSAP_VTCORE_ATTR_UNDERLINE_MASK)) && + !p->inverse && p->fg == WSAP_VTCORE_COLOR_FG && p->bg == WSAP_VTCORE_COLOR_BG && !p->ul) return; ADD("0"); - if (p->attrs & TERM_ATTR_BOLD) ADD(";1"); - if (p->attrs & TERM_ATTR_FAINT) ADD(";2"); - if (p->attrs & TERM_ATTR_ITALIC) ADD(";3"); + if (p->attrs & WSAP_VTCORE_ATTR_BOLD) ADD(";1"); + if (p->attrs & WSAP_VTCORE_ATTR_FAINT) ADD(";2"); + if (p->attrs & WSAP_VTCORE_ATTR_ITALIC) ADD(";3"); if (ul == 1) ADD(";4"); else if (ul) ADD(";4:%d", ul); if (p->inverse) ADD(";7"); - if (p->attrs & TERM_ATTR_STRIKE) ADD(";9"); - if (p->attrs & TERM_ATTR_OVERLINE) ADD(";53"); - const term_color colors[3] = { p->fg, p->bg, p->ul }; - const bool set[3] = { p->fg != TERM_COLOR_FG, p->bg != TERM_COLOR_BG, p->ul != 0 }; + if (p->attrs & WSAP_VTCORE_ATTR_STRIKE) ADD(";9"); + if (p->attrs & WSAP_VTCORE_ATTR_OVERLINE) ADD(";53"); + const wsap_vtcore_color colors[3] = { p->fg, p->bg, p->ul }; + const bool set[3] = { p->fg != WSAP_VTCORE_COLOR_FG, p->bg != WSAP_VTCORE_COLOR_BG, p->ul != 0 }; for (int k = 0; k < 3; k++) { if (!set[k]) continue; int base = 30 + 10 * k; - term_color c = colors[k]; - if (term_color_is_slot(c) && (c & 0x1FFu) < 256) { + wsap_vtcore_color c = colors[k]; + if (wsap_vtcore_color_is_slot(c) && (c & 0x1FFu) < 256) { int i = (int)(c & 0xFFu); if (i < 16 && k < 2) ADD(";%d", i < 8 ? base + i : base + 60 + i - 8); else ADD(";%d:5:%d", base + 8, i); @@ -856,24 +856,24 @@ static void sgr_report(const struct model *m, char *out, size_t cap) static void cara_cell(struct model *m, struct cell *c) { if (m->nparam <= 4) { - c->fg = TERM_COLOR_FG; - c->bg = TERM_COLOR_BG; - c->attrs &= TERM_ATTR_EMOJI | TERM_ATTR_TEXT | TERM_ATTR_LINK; + c->fg = WSAP_VTCORE_COLOR_FG; + c->bg = WSAP_VTCORE_COLOR_BG; + c->attrs &= WSAP_VTCORE_ATTR_EMOJI | WSAP_VTCORE_ATTR_TEXT | WSAP_VTCORE_ATTR_LINK; return; } for (int i = 4; i < m->nparam; i++) { int v = m->param[i]; - term_color color; + wsap_vtcore_color color; bool ok; switch (v) { case 0: - c->fg = TERM_COLOR_FG; - c->bg = TERM_COLOR_BG; - c->attrs &= TERM_ATTR_EMOJI | TERM_ATTR_TEXT | TERM_ATTR_LINK; + c->fg = WSAP_VTCORE_COLOR_FG; + c->bg = WSAP_VTCORE_COLOR_BG; + c->attrs &= WSAP_VTCORE_ATTR_EMOJI | WSAP_VTCORE_ATTR_TEXT | WSAP_VTCORE_ATTR_LINK; break; - case 1: c->attrs |= TERM_ATTR_BOLD; break; - case 2: c->attrs |= TERM_ATTR_FAINT; break; - case 3: c->attrs |= TERM_ATTR_ITALIC; break; + case 1: c->attrs |= WSAP_VTCORE_ATTR_BOLD; break; + case 2: c->attrs |= WSAP_VTCORE_ATTR_FAINT; break; + case 3: c->attrs |= WSAP_VTCORE_ATTR_ITALIC; break; case 4: { int style = 1; if (i + 1 < m->nparam && (m->sub & (1u << (i + 1)))) @@ -881,25 +881,25 @@ static void cara_cell(struct model *m, struct cell *c) set_underline(&c->attrs, style); break; } - case 7: { term_color t = c->fg; c->fg = c->bg; c->bg = t; break; } - case 9: c->attrs |= TERM_ATTR_STRIKE; break; + case 7: { wsap_vtcore_color t = c->fg; c->fg = c->bg; c->bg = t; break; } + case 9: c->attrs |= WSAP_VTCORE_ATTR_STRIKE; break; case 21: set_underline(&c->attrs, 2); break; - case 22: c->attrs &= (uint16_t)~(TERM_ATTR_BOLD | TERM_ATTR_FAINT); break; - case 23: c->attrs &= (uint16_t)~TERM_ATTR_ITALIC; break; + case 22: c->attrs &= (uint16_t)~(WSAP_VTCORE_ATTR_BOLD | WSAP_VTCORE_ATTR_FAINT); break; + case 23: c->attrs &= (uint16_t)~WSAP_VTCORE_ATTR_ITALIC; break; case 24: set_underline(&c->attrs, 0); break; - case 29: c->attrs &= (uint16_t)~TERM_ATTR_STRIKE; break; + case 29: c->attrs &= (uint16_t)~WSAP_VTCORE_ATTR_STRIKE; break; case 38: i += extended_color(m, i, &color, &ok); if (ok) c->fg = color; break; - case 39: c->fg = TERM_COLOR_FG; break; + case 39: c->fg = WSAP_VTCORE_COLOR_FG; break; case 48: i += extended_color(m, i, &color, &ok); if (ok) c->bg = color; break; - case 49: c->bg = TERM_COLOR_BG; break; - case 53: c->attrs |= TERM_ATTR_OVERLINE; break; - case 55: c->attrs &= (uint16_t)~TERM_ATTR_OVERLINE; break; + case 49: c->bg = WSAP_VTCORE_COLOR_BG; break; + case 53: c->attrs |= WSAP_VTCORE_ATTR_OVERLINE; break; + case 55: c->attrs &= (uint16_t)~WSAP_VTCORE_ATTR_OVERLINE; break; case 58: i += extended_color(m, i, &color, &ok); break; default: - if (v >= 30 && v <= 37) c->fg = term_color_index(v - 30); - else if (v >= 40 && v <= 47) c->bg = term_color_index(v - 40); - else if (v >= 90 && v <= 97) c->fg = term_color_index(v - 90 + 8); - else if (v >= 100 && v <= 107) c->bg = term_color_index(v - 100 + 8); + if (v >= 30 && v <= 37) c->fg = wsap_vtcore_color_index(v - 30); + else if (v >= 40 && v <= 47) c->bg = wsap_vtcore_color_index(v - 40); + else if (v >= 90 && v <= 97) c->fg = wsap_vtcore_color_index(v - 90 + 8); + else if (v >= 100 && v <= 107) c->bg = wsap_vtcore_color_index(v - 100 + 8); break; } } @@ -1187,7 +1187,7 @@ static void reflow(struct model *m, int cols, int rows) } m->cols = cols; - term_hist_clear(m); + wsap_vtcore_hist_clear(m); for (int i = start - history; i < start; i++) { hist_push(m, r.out[i]); r.out[i] = NULL; @@ -1291,7 +1291,7 @@ static void resize_plain(struct model *m, int cols, int rows) static bool resize(struct model *m, int cols, int rows) { - if (cols > TERM_MAX_COLS) return false; + if (cols > WSAP_VTCORE_MAX_COLS) return false; if (cols == m->cols && rows == m->rows) return true; if (cols > MAX_TABS) return false; m->top = 0; @@ -1352,7 +1352,7 @@ static void soft_reset(struct model *m) m->bracketed = false; m->autowrap = m->visible = true; m->blink = true; - m->style = TERM_CURSOR_BLOCK; + m->style = WSAP_VTCORE_CURSOR_BLOCK; m->top = 0; m->bottom = m->rows - 1; m->decsace = 0; @@ -1630,11 +1630,11 @@ static void csi_dispatch(struct model *m, unsigned char final) } else if (!m->prefix && m->inter == ' ') { int ps = m->nparam ? m->param[0] : 0; if (ps == 0) { - m->style = TERM_CURSOR_BLOCK; + m->style = WSAP_VTCORE_CURSOR_BLOCK; m->blink = true; } else if (ps <= 6) { - m->style = ps < 3 ? TERM_CURSOR_BLOCK : ps < 5 ? TERM_CURSOR_UNDERLINE - : TERM_CURSOR_BAR; + m->style = ps < 3 ? WSAP_VTCORE_CURSOR_BLOCK : ps < 5 ? WSAP_VTCORE_CURSOR_UNDERLINE + : WSAP_VTCORE_CURSOR_BAR; m->blink = ps & 1; } } @@ -1676,8 +1676,8 @@ static void dcs_finish(struct model *m) size_t n = len - 2; char body[256]; if (n == 2 && !memcmp(spec, " q", 2)) { - int shape = m->style == TERM_CURSOR_BLOCK ? (m->blink ? 1 : 2) - : m->style == TERM_CURSOR_UNDERLINE ? (m->blink ? 3 : 4) + int shape = m->style == WSAP_VTCORE_CURSOR_BLOCK ? (m->blink ? 1 : 2) + : m->style == WSAP_VTCORE_CURSOR_UNDERLINE ? (m->blink ? 3 : 4) : (m->blink ? 5 : 6); reply(m, "\033P1$r%d q\033\\", shape); } else if (n == 1 && spec[0] == 'm') { @@ -1779,7 +1779,7 @@ static void control(struct model *m, unsigned char c) case 0x1b: m->state = ESC; break; case '\n': case 0x0b: case 0x0c: m->pending = false; - if (m->lnm || (m->flags & TERM_FEED_ONLCR)) m->x = 0; + if (m->lnm || (m->flags & WSAP_VTCORE_FEED_ONLCR)) m->x = 0; line_feed(m); break; case '\r': m->pending = false; m->x = 0; break; @@ -1972,17 +1972,17 @@ static void feed_byte(struct model *m, unsigned char c) /* ---- public ---- */ -struct model *model_new(struct term_vector2i size, int history, const char *name) +struct model *model_new(struct wsap_vtcore_vector2i size, int history, const char *name) { struct model *m = calloc(1, sizeof(*m)); if (!m) abort(); - snprintf(m->name, sizeof(m->name), "%s", name && *name ? name : "term"); + snprintf(m->name, sizeof(m->name), "%s", name && *name ? name : "wsap_vtcore"); m->cols = size.x < 1 ? 80 : size.x; m->rows = size.y < 1 ? 24 : size.y; m->limit = history_limit(history); m->scr = rows_new(m->rows, m->cols); m->autowrap = m->visible = m->blink = true; - m->style = TERM_CURSOR_BLOCK; + m->style = WSAP_VTCORE_CURSOR_BLOCK; m->bottom = m->rows - 1; m->g[0] = m->g[1] = 'B'; m->saved = initial_saved(); @@ -1998,7 +1998,7 @@ void model_free(struct model *m) if (!m) return; free_rows(m->scr, m->rows); free_rows(m->normal, m->normal_rows); - term_hist_clear(m); + wsap_vtcore_hist_clear(m); free(m->hist); free(m->reply); for (int i = 0; i < m->out_cap; i++) free(m->out[i]); @@ -2012,15 +2012,15 @@ void model_feed(struct model *m, const char *s, size_t len, unsigned flags) for (size_t i = 0; i < len; i++) feed_byte(m, (unsigned char)s[i]); } -bool model_resize(struct model *m, struct term_vector2i size) +bool model_resize(struct model *m, struct wsap_vtcore_vector2i size) { if (size.x < 1 || size.y < 1) return false; return resize(m, size.x, size.y); } -struct term_vector2i model_size(const struct model *m) +struct wsap_vtcore_vector2i model_size(const struct model *m) { - return (struct term_vector2i){ .x = m->cols, .y = m->rows }; + return (struct wsap_vtcore_vector2i){ .x = m->cols, .y = m->rows }; } int model_history(const struct model *m) @@ -2071,22 +2071,22 @@ const struct model_cell *model_row(const struct model *m, int row) return mm->out[row]; } -struct term_cursor model_cursor(const struct model *m) +struct wsap_vtcore_cursor model_cursor(const struct model *m) { - return (struct term_cursor){ + return (struct wsap_vtcore_cursor){ .pos = { .x = m->x, .y = m->y }, - .style = (enum term_cursor_style)m->style, + .style = (enum wsap_vtcore_cursor_style)m->style, .visible = m->visible, .blink = m->blink, }; } -struct term_modes model_modes(const struct model *m) +struct wsap_vtcore_modes model_modes(const struct model *m) { - return (struct term_modes){ + return (struct wsap_vtcore_modes){ .keyboard = m->keyboard[m->alternate].flags, - .mouse = (enum term_mouse)m->mouse, - .mouse_encoding = (enum term_mouse_encoding)m->mouse_enc, + .mouse = (enum wsap_vtcore_mouse)m->mouse, + .mouse_encoding = (enum wsap_vtcore_mouse_encoding)m->mouse_enc, .app_cursor = m->app_cursor, .app_keypad = m->app_keypad, .backarrow_bs = m->backarrow, diff --git a/tests/model.h b/tests/model.h index ca2bf96..be250ef 100644 --- a/tests/model.h +++ b/tests/model.h @@ -3,7 +3,7 @@ /* * A slow reference model of the terminal. It defines correct behavior for - * the input that tests/term/fuzz_gen.h makes. model.c names its sources: + * the input that tests/fuzz_gen.h makes. model.c names its sources: * xterm and ECMA-48 for controls, Unicode for UTF-8, and this terminal's * own design where xterm has no rule (reflow, history, clusters). * @@ -11,39 +11,39 @@ * the public API only. */ -#include "term/term.h" -#include "term/unicode/grapheme.h" +#include "wsap_vtcore/wsap_vtcore.h" +#include "wsap_vtcore/unicode/grapheme.h" #include <stdbool.h> #include <stddef.h> #include <stdint.h> struct model_cell { - uint32_t cp[TERM_GRAPHEME_MAX_LEN]; + uint32_t cp[WSAP_VTCORE_GRAPHEME_MAX_LEN]; uint8_t n; /* code points; 0 for the right half of a wide cell */ uint8_t width; /* 1, 2 for a wide cell, 0 for its right half */ - uint16_t attrs; /* TERM_ATTR_* */ - term_color fg, bg; + uint16_t attrs; /* WSAP_VTCORE_ATTR_* */ + wsap_vtcore_color fg, bg; }; struct model; -/* history is the history limit, as in term_options.scrollback. name is - * as in term_options.name. */ -struct model *model_new(struct term_vector2i size, int history, const char *name); +/* history is the history limit, as in wsap_vtcore_options.scrollback. name is + * as in wsap_vtcore_options.name. */ +struct model *model_new(struct wsap_vtcore_vector2i size, int history, const char *name); void model_free(struct model *m); void model_feed(struct model *m, const char *s, size_t len, unsigned flags); -bool model_resize(struct model *m, struct term_vector2i size); +bool model_resize(struct model *m, struct wsap_vtcore_vector2i size); -struct term_vector2i model_size(const struct model *m); +struct wsap_vtcore_vector2i model_size(const struct model *m); /* History rows. The alternate screen shows no history, so it reports 0. */ int model_history(const struct model *m); /* Row 0 is the oldest history row. Row model_history() is the top screen * row. Return NULL for an invalid row. Different rows can be read together. * A feed or resize ends the lifetime of returned row data. */ const struct model_cell *model_row(const struct model *m, int row); -struct term_cursor model_cursor(const struct model *m); -struct term_modes model_modes(const struct model *m); +struct wsap_vtcore_cursor model_cursor(const struct model *m); +struct wsap_vtcore_modes model_modes(const struct model *m); /* Replies since the last model_take_replies(). */ const char *model_replies(const struct model *m, size_t *len); void model_take_replies(struct model *m); diff --git a/tests/model_row_test.c b/tests/model_row_test.c index ad4ac2c..e204e1f 100644 --- a/tests/model_row_test.c +++ b/tests/model_row_test.c @@ -5,7 +5,7 @@ int main(void) { - struct model *m = model_new((struct term_vector2i){ .x = 10, .y = 3 }, 10, NULL); + struct model *m = model_new((struct wsap_vtcore_vector2i){ .x = 10, .y = 3 }, 10, NULL); model_feed(m, "A\r\nB\r\nC\r\nD", strlen("A\r\nB\r\nC\r\nD"), 0); assert(model_history(m) == 1); assert(model_row(m, -1) == NULL); @@ -21,7 +21,7 @@ int main(void) model_feed(m, "E", 1, 0); assert(model_row(m, 3)[1].cp[0] == 'E'); - assert(model_resize(m, (struct term_vector2i){ .x = 12, .y = 3 })); + assert(model_resize(m, (struct wsap_vtcore_vector2i){ .x = 12, .y = 3 })); assert(model_row(m, 3)[0].cp[0] == 'D'); assert(model_row(m, 3)[1].cp[0] == 'E'); model_free(m); diff --git a/tests/model_test.c b/tests/model_test.c index d3988c6..4f58914 100644 --- a/tests/model_test.c +++ b/tests/model_test.c @@ -17,7 +17,7 @@ */ #include "model.h" #include "fuzz_gen.h" -#include "term/term.h" +#include "wsap_vtcore/wsap_vtcore.h" #include <stdio.h> #include <limits.h> @@ -33,11 +33,11 @@ struct event { char *bytes; /* NULL for a resize */ size_t len; unsigned flags; - struct term_vector2i size; + struct wsap_vtcore_vector2i size; }; struct script { - struct term_vector2i size; + struct wsap_vtcore_vector2i size; int history; struct event *ev; int n, cap; @@ -107,10 +107,10 @@ static char glyph(uint32_t cp) } /* Print every retained row of both, side by side. */ -static void dump_all(struct model *m, struct term *t, struct term_snapshot *snap, FILE *log) +static void dump_all(struct model *m, struct wsap_vtcore *t, struct wsap_vtcore_snapshot *snap, FILE *log) { - int total = term_scrollback(t).total, mtotal = model_history(m); - struct term_vector2i size = term_size(t), msize = model_size(m); + int total = wsap_vtcore_scrollback(t).total, mtotal = model_history(m); + struct wsap_vtcore_vector2i size = wsap_vtcore_size(t), msize = model_size(m); int rows = total + size.y > mtotal + msize.y ? total + size.y : mtotal + msize.y; fprintf(log, " term (history %d)%*s model (history %d)\n", total, size.x > 8 ? size.x - 8 : 0, "", mtotal); @@ -118,12 +118,12 @@ static void dump_all(struct model *m, struct term *t, struct term_snapshot *snap fprintf(log, " %3d |", r); if (r < total + size.y) { int offset = r < total ? total - r : 0; - term_scroll_to(t, offset); - term_snapshot_update(snap, t); - const struct term_cell *row = term_snapshot_row(snap, r < total ? 0 : r - total); + wsap_vtcore_scroll_to(t, offset); + wsap_vtcore_snapshot_update(snap, t); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(snap, r < total ? 0 : r - total); for (int x = 0; x < size.x; x++) { - uint32_t cp[TERM_GRAPHEME_MAX_LEN] = {0}; - if (row[x].text) term_snapshot_cluster(snap, row[x].text, cp, TERM_GRAPHEME_MAX_LEN); + uint32_t cp[WSAP_VTCORE_GRAPHEME_MAX_LEN] = {0}; + if (row[x].text) wsap_vtcore_snapshot_cluster(snap, row[x].text, cp, WSAP_VTCORE_GRAPHEME_MAX_LEN); fputc(glyph(cp[0]), log); } } else { @@ -136,14 +136,14 @@ static void dump_all(struct model *m, struct term *t, struct term_snapshot *snap } fprintf(log, "|\n"); } - term_scroll_to(t, 0); - struct term_cursor c = term_cursor(t), mc = model_cursor(m); + wsap_vtcore_scroll_to(t, 0); + struct wsap_vtcore_cursor c = wsap_vtcore_cursor(t), mc = model_cursor(m); fprintf(log, " cursor term %d,%d model %d,%d\n", c.pos.x, c.pos.y, mc.pos.x, mc.pos.y); } /* Returns NULL when the terminal matches the model, else a description. * Details go to log when it is not NULL. */ -static const char *compare(struct model *m, struct term *t, struct term_snapshot *snap, +static const char *compare(struct model *m, struct wsap_vtcore *t, struct wsap_vtcore_snapshot *snap, struct replies *got, char *why, size_t cap, FILE *log) { size_t want_len; @@ -159,12 +159,12 @@ static const char *compare(struct model *m, struct term *t, struct term_snapshot snprintf(why, cap, "replies differ"); return why; } - struct term_vector2i size = term_size(t), msize = model_size(m); + struct wsap_vtcore_vector2i size = wsap_vtcore_size(t), msize = model_size(m); if (size.x != msize.x || size.y != msize.y) { snprintf(why, cap, "size %dx%d, model %dx%d", size.x, size.y, msize.x, msize.y); return why; } - struct term_cursor c = term_cursor(t), mc = model_cursor(m); + struct wsap_vtcore_cursor c = wsap_vtcore_cursor(t), mc = model_cursor(m); if (c.pos.x != mc.pos.x || c.pos.y != mc.pos.y || c.style != mc.style || c.visible != mc.visible || c.blink != mc.blink) { snprintf(why, cap, "cursor %d,%d style %d visible %d blink %d; model %d,%d %d %d %d", @@ -172,7 +172,7 @@ static const char *compare(struct model *m, struct term *t, struct term_snapshot mc.pos.x, mc.pos.y, mc.style, mc.visible, mc.blink); return why; } - struct term_modes md = term_modes(t), mm = model_modes(m); + struct wsap_vtcore_modes md = wsap_vtcore_modes(t), mm = model_modes(m); if (md.keyboard != mm.keyboard || md.mouse != mm.mouse || md.mouse_encoding != mm.mouse_encoding || md.app_cursor != mm.app_cursor || md.app_keypad != mm.app_keypad || md.backarrow_bs != mm.backarrow_bs || @@ -186,24 +186,24 @@ static const char *compare(struct model *m, struct term *t, struct term_snapshot } /* Visit each retained row. Wide-line totals can start as estimates. */ int total = model_history(m); - term_scroll_to(t, 0); - term_scroll(t, INT_MAX); + wsap_vtcore_scroll_to(t, 0); + wsap_vtcore_scroll(t, INT_MAX); for (int offset = total;; offset = offset > size.y ? offset - size.y : 0) { if (!offset) - term_scroll_to(t, 0); - if (!term_snapshot_update(snap, t)) { + wsap_vtcore_scroll_to(t, 0); + if (!wsap_vtcore_snapshot_update(snap, t)) { snprintf(why, cap, "snapshot update failed"); return why; } for (int y = 0; y < size.y; y++) { - const struct term_cell *row = term_snapshot_row(snap, y); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(snap, y); int retained = total - offset + y; const struct model_cell *want_row = model_row(m, retained); for (int x = 0; x < size.x; x++) { const struct model_cell *e = &want_row[x]; - uint32_t cps[TERM_GRAPHEME_MAX_LEN] = {0}; - int n = row[x].text ? term_snapshot_cluster(snap, row[x].text, cps, - TERM_GRAPHEME_MAX_LEN) : 0; + uint32_t cps[WSAP_VTCORE_GRAPHEME_MAX_LEN] = {0}; + int n = row[x].text ? wsap_vtcore_snapshot_cluster(snap, row[x].text, cps, + WSAP_VTCORE_GRAPHEME_MAX_LEN) : 0; if (n == e->n && row[x].width == e->width && row[x].attrs == e->attrs && row[x].fg == e->fg && row[x].bg == e->bg && !memcmp(cps, e->cp, (size_t)n * sizeof(*cps))) @@ -211,9 +211,9 @@ static const char *compare(struct model *m, struct term *t, struct term_snapshot if (log) { fprintf(log, "retained row %d (offset %d):\n term: ", retained, offset); for (int k = 0; k < size.x; k++) { - uint32_t cp[TERM_GRAPHEME_MAX_LEN] = {0}; + uint32_t cp[WSAP_VTCORE_GRAPHEME_MAX_LEN] = {0}; if (row[k].text) - term_snapshot_cluster(snap, row[k].text, cp, TERM_GRAPHEME_MAX_LEN); + wsap_vtcore_snapshot_cluster(snap, row[k].text, cp, WSAP_VTCORE_GRAPHEME_MAX_LEN); fputc(glyph(cp[0]), log); } fprintf(log, "\n model: "); @@ -228,19 +228,19 @@ static const char *compare(struct model *m, struct term *t, struct term_snapshot "model U+%04X (%u cps) w%u attrs %#x fg %#x bg %#x", x, y, cps[0], n, row[x].width, row[x].attrs, row[x].fg, row[x].bg, e->cp[0], e->n, e->width, e->attrs, e->fg, e->bg); - term_scroll_to(t, 0); + wsap_vtcore_scroll_to(t, 0); return why; } } if (!offset) break; - term_scroll(t, -(offset > size.y ? size.y : offset)); + wsap_vtcore_scroll(t, -(offset > size.y ? size.y : offset)); } - int observed_total = term_scrollback(t).total; + int observed_total = wsap_vtcore_scrollback(t).total; if (observed_total != total) { snprintf(why, cap, "visited history %d rows, model %d", observed_total, total); return why; } - term_scroll_to(t, 0); + wsap_vtcore_scroll_to(t, 0); return NULL; } @@ -251,13 +251,13 @@ static int run(const struct script *s, enum chunking chunks, uint64_t chunk_seed char *why, size_t cap, bool verbose) { struct replies got = {0}; - struct term_options opt = { + struct wsap_vtcore_options opt = { .size = s->size, .scrollback = s->history, .callbacks = { .ud = &got, .reply = on_reply }, }; - struct term *t = term_new(&opt); + struct wsap_vtcore *t = wsap_vtcore_new(&opt); struct model *m = model_new(s->size, s->history, NULL); - struct term_snapshot *snap = term_snapshot_new(); + struct wsap_vtcore_snapshot *snap = wsap_vtcore_snapshot_new(); if (!t || !snap) abort(); uint64_t saved_rng = rng; rng = chunk_seed | 1; @@ -270,12 +270,12 @@ static int run(const struct script *s, enum chunking chunks, uint64_t chunk_seed size_t n = chunks == CHUNK_WHOLE ? e->len - k : chunks == CHUNK_BYTES ? 1 : 1 + (size_t)rn((int)(e->len - k)); - term_feed(t, e->bytes + k, n, e->flags); + wsap_vtcore_feed(t, e->bytes + k, n, e->flags); k += n; } } else { bool a = model_resize(m, e->size); - bool b = term_resize(t, e->size); + bool b = wsap_vtcore_resize(t, e->size); if (a != b) { snprintf(why, cap, "resize result differs"); bad = i; @@ -291,9 +291,9 @@ static int run(const struct script *s, enum chunking chunks, uint64_t chunk_seed } rng = saved_rng; free(got.s); - term_snapshot_free(snap); + wsap_vtcore_snapshot_free(snap); model_free(m); - term_free(t); + wsap_vtcore_free(t); return bad; } @@ -378,7 +378,7 @@ static int fixed_cases(void) { 8, 3, 5, "abcdefgh\033[3;4H\033[31;1m\0337\033[0m\033[H\0338X" }, { 6, 2, 5, "abcdef\xe3\x80z\xed\xa0\x80\x80" }, }; - static const struct term_vector2i sizes[] = { + static const struct wsap_vtcore_vector2i sizes[] = { { .x = 5, .y = 3 }, { .x = 16, .y = 4 }, { .x = 7, .y = 3 }, { .x = 20, .y = 5 }, { .x = 1, .y = 2 }, { .x = 3, .y = 6 }, }; @@ -419,16 +419,16 @@ int main(int argc, char **argv) .size = { .x = 4 + rn(37), .y = 2 + rn(11) }, .history = limits[rn(4)], }; - struct term_vector2i size = s.size; + struct wsap_vtcore_vector2i size = s.size; for (int step = 0; step < 4; step++) { blen = 0; gen(10 + rn(30), size.x, size.y); put(probe); - unsigned flags = rn(5) == 0 ? TERM_FEED_ONLCR : 0; + unsigned flags = rn(5) == 0 ? WSAP_VTCORE_FEED_ONLCR : 0; script_add(&s, (struct event){ .bytes = dup_bytes(buf, blen), .len = blen, .flags = flags }); if (rn(4) == 0) { - size = (struct term_vector2i){ .x = 1 + rn(44), .y = 1 + rn(14) }; + size = (struct wsap_vtcore_vector2i){ .x = 1 + rn(44), .y = 1 + rn(14) }; script_add(&s, (struct event){ .size = size }); } } diff --git a/tests/osc_test.c b/tests/osc_test.c index 9d08157..66c6303 100644 --- a/tests/osc_test.c +++ b/tests/osc_test.c @@ -1,17 +1,17 @@ #include "term_api.h" -#include "term/unicode/unicode.h" +#include "wsap_vtcore/unicode/unicode.h" #include <assert.h> #include <stdbool.h> #include <stdio.h> #include <stdlib.h> #include <string.h> -static void write_seq(struct term *t, const char *s) +static void write_seq(struct wsap_vtcore *t, const char *s) { for (; *s; s++) tt_write(t, s, 1); } -static void write_buf(struct term *t, const char *s, size_t len) +static void write_buf(struct wsap_vtcore *t, const char *s, size_t len) { tt_write(t, s, len); } @@ -55,9 +55,9 @@ static void capture_notify(void *ud, const char *t_, const char *b) notify_count++; } -static struct term *osc_test_term(void) +static struct wsap_vtcore *osc_test_term(void) { - struct term *t = tt_new_opts(80, 24, &(struct term_callbacks){ + struct wsap_vtcore *t = tt_new_opts(80, 24, &(struct wsap_vtcore_callbacks){ .reply = capture_reply, .title = capture_title, .clipboard = capture_clip, @@ -69,7 +69,7 @@ static struct term *osc_test_term(void) /* Check the OSC 8 link or the detected URL at a viewport cell. NULL means * no link. */ -static void assert_link(struct term *t, int col, int row, const char *want) +static void assert_link(struct wsap_vtcore *t, int col, int row, const char *want) { char *url = tt_link_at(t, col, row); if (want) @@ -79,13 +79,13 @@ static void assert_link(struct term *t, int col, int row, const char *want) free(url); } -static uint32_t cursor_color(struct term *t) +static uint32_t cursor_color(struct wsap_vtcore *t) { - return term_snapshot_view(tt_snapshot_for(t))->palette[TERM_PALETTE_CURSOR]; + return wsap_vtcore_snapshot_view(tt_snapshot_for(t))->palette[WSAP_VTCORE_PALETTE_CURSOR]; } /* Send a color query and check the reply. */ -static void assert_query(struct term *t, const char *query, const char *want) +static void assert_query(struct wsap_vtcore *t, const char *query, const char *want) { reply[0] = 0; write_seq(t, query); @@ -104,16 +104,16 @@ static void reset_captures(void) notify_count = 0; } -/* The notification default is term_options.name. A DCS +p does not change it. */ +/* The notification default is wsap_vtcore_options.name. A DCS +p does not change it. */ static void test_host_name_notify(void) { - struct term_options opt = { + struct wsap_vtcore_options opt = { .size = { .x = 80, .y = 24 }, .scrollback = TEST_SCROLLBACK, .name = "myterm", .callbacks = { .notify = capture_notify }, }; - struct term *t = term_new(&opt); + struct wsap_vtcore *t = wsap_vtcore_new(&opt); assert(t); reset_captures(); write_seq(t, "\033]9;hello\007"); @@ -130,12 +130,12 @@ static void test_host_name_notify(void) write_seq(t, "\033]777;notify;Title;Body\007"); assert(notify_count == 2); assert(!strcmp(notify_title, "Title")); - term_free(t); + wsap_vtcore_free(t); } static void test_osc52(void) { - struct term *t = osc_test_term(); + struct wsap_vtcore *t = osc_test_term(); reset_captures(); write_seq(t, "\033]52;c;aGVsbG8=\007"); assert(clip_count == 1 && !strcmp(clip_sel, "c")); @@ -180,7 +180,7 @@ static void test_osc52(void) write_seq(t, "\033]52;s;AAH9\007"); assert(clip_count == 1 && !strcmp(clip_sel, "s") && clip_len == 3); assert(clip_data[0] == 0 && clip_data[1] == 1 && clip_data[2] == (char)0xfd); - term_free(t); + wsap_vtcore_free(t); } /* An SGR reset must not drop an open link. @@ -191,44 +191,44 @@ static void test_osc52(void) * path runs. */ static void test_sgr_reset_keeps_link(void) { - struct term *t = osc_test_term(); + struct wsap_vtcore *t = osc_test_term(); reset_captures(); static const char seq[] = "\033]8;;https://reset.dev\033\\\033[0mX"; write_buf(t, seq, sizeof(seq) - 1); - assert(tt_cell(t, 0, 0)->attrs & TERM_ATTR_LINK); + assert(tt_cell(t, 0, 0)->attrs & WSAP_VTCORE_ATTR_LINK); assert_link(t, 0, 0, "https://reset.dev"); /* The same reset in its own write, which takes the normal parser. */ static const char seq2[] = "\033]8;;https://second.dev\033\\\033[0m"; write_buf(t, seq2, sizeof(seq2) - 1); write_buf(t, "Y", 1); - assert(tt_cell(t, 1, 0)->attrs & TERM_ATTR_LINK); + assert(tt_cell(t, 1, 0)->attrs & WSAP_VTCORE_ATTR_LINK); assert_link(t, 1, 0, "https://second.dev"); - term_free(t); + wsap_vtcore_free(t); } static void test_osc8(void) { - struct term *t = osc_test_term(); + struct wsap_vtcore *t = osc_test_term(); reset_captures(); write_seq(t, "\033]8;;https://example.com\033\\link text\033]8;;\033\\after"); for (int c = 0; c < 9; c++) { - assert(tt_cell(t, c, 0)->attrs & TERM_ATTR_LINK); + assert(tt_cell(t, c, 0)->attrs & WSAP_VTCORE_ATTR_LINK); assert_link(t, c, 0, "https://example.com"); } for (int c = 9; c < 14; c++) { - assert(!(tt_cell(t, c, 0)->attrs & TERM_ATTR_LINK)); + assert(!(tt_cell(t, c, 0)->attrs & WSAP_VTCORE_ATTR_LINK)); assert_link(t, c, 0, NULL); } /* Each cell keeps the URI of its own link. */ write_seq(t, "\033[2;1H\033]8;;https://other.org\033\\bbb\033]8;;\033\\"); write_seq(t, "\033[3;1H\033]8;;https://example.com\033\\ccc\033]8;;\033\\"); - assert(tt_cell(t, 0, 1)->attrs & TERM_ATTR_LINK); - assert(tt_cell(t, 0, 2)->attrs & TERM_ATTR_LINK); + assert(tt_cell(t, 0, 1)->attrs & WSAP_VTCORE_ATTR_LINK); + assert(tt_cell(t, 0, 2)->attrs & WSAP_VTCORE_ATTR_LINK); assert_link(t, 0, 1, "https://other.org"); assert_link(t, 2, 1, "https://other.org"); assert_link(t, 0, 2, "https://example.com"); @@ -236,31 +236,31 @@ static void test_osc8(void) /* An erase removes the link. */ write_seq(t, "\033[4;1H\033]8;;https://gone.io\033\\zzz\033]8;;\033\\"); - assert(tt_cell(t, 0, 3)->attrs & TERM_ATTR_LINK); + assert(tt_cell(t, 0, 3)->attrs & WSAP_VTCORE_ATTR_LINK); write_seq(t, "\033[4;1H\033[K"); - assert(!(tt_cell(t, 0, 3)->attrs & TERM_ATTR_LINK)); + assert(!(tt_cell(t, 0, 3)->attrs & WSAP_VTCORE_ATTR_LINK)); assert_link(t, 0, 3, NULL); write_seq(t, "\033[5;1H\033]8;x\033\\nop\033]8;xyz\033\\qq"); - assert(!(tt_cell(t, 0, 4)->attrs & TERM_ATTR_LINK)); + assert(!(tt_cell(t, 0, 4)->attrs & WSAP_VTCORE_ATTR_LINK)); assert_link(t, 0, 4, NULL); - assert(!(tt_cell(t, 4, 4)->attrs & TERM_ATTR_LINK)); + assert(!(tt_cell(t, 4, 4)->attrs & WSAP_VTCORE_ATTR_LINK)); write_seq(t, "\033]8;;https://stay.net\033\\\033]8;bogus\033\\ST\033]8;;\033\\"); - assert(tt_cell(t, 5, 4)->attrs & TERM_ATTR_LINK); + assert(tt_cell(t, 5, 4)->attrs & WSAP_VTCORE_ATTR_LINK); assert_link(t, 5, 4, "https://stay.net"); write_seq(t, "\033[6;1H\033]8;id=grp;https://params.dev\007p1\033]8;;\007"); - assert(tt_cell(t, 0, 5)->attrs & TERM_ATTR_LINK); + assert(tt_cell(t, 0, 5)->attrs & WSAP_VTCORE_ATTR_LINK); assert_link(t, 0, 5, "https://params.dev"); /* A link stays on its cells when they scroll into the history. */ for (int i = 0; i < 30; i++) write_buf(t, "filler\r\n", 8); assert(tt_history(t) > 0); - term_scroll(t, tt_history(t)); - assert(tt_view_cell(t, 0, 0)->attrs & TERM_ATTR_LINK); + wsap_vtcore_scroll(t, tt_history(t)); + assert(tt_view_cell(t, 0, 0)->attrs & WSAP_VTCORE_ATTR_LINK); assert_link(t, 0, 0, "https://example.com"); - term_scroll_to(t, 0); + wsap_vtcore_scroll_to(t, 0); write_seq(t, "\033[7;1H"); for (int i = 0; i < 8300; i++) { @@ -279,46 +279,46 @@ static void test_osc8(void) write_seq(t, "\033[1;1H\033]8;;https://altscreen.test\033\\ALT\033]8;;\033\\"); assert_link(t, 0, 0, "https://altscreen.test"); write_seq(t, "\033[?1049l"); - term_scroll(t, tt_history(t)); + wsap_vtcore_scroll(t, tt_history(t)); assert_link(t, 0, 0, "https://example.com"); - term_scroll_to(t, 0); + wsap_vtcore_scroll_to(t, 0); write_seq(t, "\033[8;1HSee file:///home/user/code/file.c#L10-L20 for info"); assert_link(t, 10, 7, "file:///home/user/code/file.c#L10-L20"); - term_free(t); + wsap_vtcore_free(t); } -static bool text_is(char *(*get)(const struct term *), - const struct term *t, const char *want) +static bool text_is(char *(*get)(const struct wsap_vtcore *), + const struct wsap_vtcore *t, const char *want) { char *text = get(t); bool same = text && !strcmp(text, want); - term_text_free(text); + wsap_vtcore_text_free(text); return same; } static void test_osc_misc(void) { - struct term *t = osc_test_term(); + struct wsap_vtcore *t = osc_test_term(); reset_captures(); write_seq(t, "\033]7;file://host/home/user/proj\007"); - assert(text_is(term_cwd, t, "/home/user/proj")); + assert(text_is(wsap_vtcore_cwd, t, "/home/user/proj")); write_seq(t, "\033]7;file:///a%20b\033\\"); - assert(text_is(term_cwd, t, "/a b")); + assert(text_is(wsap_vtcore_cwd, t, "/a b")); const char *bulk = "\033]7;file://h/bulk%20dir\007"; write_buf(t, bulk, strlen(bulk)); - assert(text_is(term_cwd, t, "/bulk dir")); + assert(text_is(wsap_vtcore_cwd, t, "/bulk dir")); write_seq(t, "\033]7;https://x/y\007"); write_seq(t, "\033]7;notauri\007"); - assert(text_is(term_cwd, t, "/bulk dir")); + assert(text_is(wsap_vtcore_cwd, t, "/bulk dir")); write_seq(t, "\033]9;hello there\033\\"); assert(notify_count == 1); - assert(!strcmp(notify_title, "term")); + assert(!strcmp(notify_title, "wsap_vtcore")); assert(!strcmp(notify_body, "hello there")); write_seq(t, "\033]9;4;3;50\007"); assert(notify_count == 1); @@ -331,43 +331,43 @@ static void test_osc_misc(void) assert(notify_count == 2); write_seq(t, "\033]22;pointer\033\\"); - assert(text_is(term_pointer_shape, t, "pointer")); + assert(text_is(wsap_vtcore_pointer_shape, t, "pointer")); write_seq(t, "\033]22;text\007"); - assert(text_is(term_pointer_shape, t, "text")); + assert(text_is(wsap_vtcore_pointer_shape, t, "text")); write_seq(t, "\033]22;\033\\"); - assert(!term_pointer_shape(t)); + assert(!wsap_vtcore_pointer_shape(t)); - term_free(t); + wsap_vtcore_free(t); } /* OSC 4, 10, 11, and 12 change the colors of one terminal. The reset codes * restore the colors of its theme. */ static void test_osc_colors(void) { - struct term_theme theme; - term_theme_default(&theme); - struct term *t = osc_test_term(); - struct term *other = osc_test_term(); + struct wsap_vtcore_theme theme; + wsap_vtcore_theme_default(&theme); + struct wsap_vtcore *t = osc_test_term(); + struct wsap_vtcore *other = osc_test_term(); reset_captures(); /* tt_new starts with the built-in theme. */ - assert(tt_color(t, TERM_COLOR_FG) == 0xFFFFFFFFu && theme.fg == 0xFFFFFFFFu); - assert(tt_color(t, TERM_COLOR_BG) == 0xFF1E1E2Eu && theme.bg == 0xFF1E1E2Eu); + assert(tt_color(t, WSAP_VTCORE_COLOR_FG) == 0xFFFFFFFFu && theme.fg == 0xFFFFFFFFu); + assert(tt_color(t, WSAP_VTCORE_COLOR_BG) == 0xFF1E1E2Eu && theme.bg == 0xFF1E1E2Eu); assert(cursor_color(t) == 0xFF89B4FAu && theme.cursor == 0xFF89B4FAu); assert_query(t, "\033]10;?\007", "\033]10;rgb:ffff/ffff/ffff\033\\"); write_seq(t, "\033]10;#ff0000\007"); - assert(tt_color(t, TERM_COLOR_FG) == 0xFFFF0000u); + assert(tt_color(t, WSAP_VTCORE_COLOR_FG) == 0xFFFF0000u); assert_query(t, "\033]10;?\007", "\033]10;rgb:ffff/0000/0000\033\\"); write_seq(t, "\033]110\007"); - assert(tt_color(t, TERM_COLOR_FG) == theme.fg); + assert(tt_color(t, WSAP_VTCORE_COLOR_FG) == theme.fg); assert_query(t, "\033]10;?\033\\", "\033]10;rgb:ffff/ffff/ffff\033\\"); write_seq(t, "\033]11;#00ff00\033\\"); - assert(tt_color(t, TERM_COLOR_BG) == 0xFF00FF00u); + assert(tt_color(t, WSAP_VTCORE_COLOR_BG) == 0xFF00FF00u); assert_query(t, "\033]11;?\007", "\033]11;rgb:0000/ffff/0000\033\\"); write_seq(t, "\033]111\007"); - assert(tt_color(t, TERM_COLOR_BG) == theme.bg); + assert(tt_color(t, WSAP_VTCORE_COLOR_BG) == theme.bg); assert_query(t, "\033]11;?\007", "\033]11;rgb:1e1e/1e1e/2e2e\033\\"); write_seq(t, "\033]12;#0000ff\007"); @@ -377,35 +377,35 @@ static void test_osc_colors(void) assert(cursor_color(t) == theme.cursor); assert_query(t, "\033]12;?\007", "\033]12;rgb:8989/b4b4/fafa\033\\"); - uint32_t ansi5 = tt_color(t, term_color_index(5)); + uint32_t ansi5 = tt_color(t, wsap_vtcore_color_index(5)); assert(ansi5 == theme.ansi[5]); write_seq(t, "\033]4;5;#ff0000\007"); - assert(tt_color(t, term_color_index(5)) == 0xFFFF0000u); - assert(tt_color(t, term_color_index(4)) == theme.ansi[4]); + assert(tt_color(t, wsap_vtcore_color_index(5)) == 0xFFFF0000u); + assert(tt_color(t, wsap_vtcore_color_index(4)) == theme.ansi[4]); /* A color change in one terminal does not change another terminal. */ write_seq(t, "\033]10;#123456\007"); - assert(tt_color(other, term_color_index(5)) == theme.ansi[5]); - assert(tt_color(other, TERM_COLOR_FG) == theme.fg); + assert(tt_color(other, wsap_vtcore_color_index(5)) == theme.ansi[5]); + assert(tt_color(other, WSAP_VTCORE_COLOR_FG) == theme.fg); assert_query(other, "\033]10;?\007", "\033]10;rgb:ffff/ffff/ffff\033\\"); - assert(tt_color(t, TERM_COLOR_FG) == 0xFF123456u); + assert(tt_color(t, WSAP_VTCORE_COLOR_FG) == 0xFF123456u); write_seq(t, "\033]104;5\007"); - assert(tt_color(t, term_color_index(5)) == ansi5); + assert(tt_color(t, wsap_vtcore_color_index(5)) == ansi5); write_seq(t, "\033]4;1;#010203;2;#040506\007"); - assert(tt_color(t, term_color_index(1)) == 0xFF010203u); - assert(tt_color(t, term_color_index(2)) == 0xFF040506u); + assert(tt_color(t, wsap_vtcore_color_index(1)) == 0xFF010203u); + assert(tt_color(t, wsap_vtcore_color_index(2)) == 0xFF040506u); write_seq(t, "\033]104\007"); - assert(tt_color(t, term_color_index(1)) == theme.ansi[1]); - assert(tt_color(t, term_color_index(2)) == theme.ansi[2]); + assert(tt_color(t, wsap_vtcore_color_index(1)) == theme.ansi[1]); + assert(tt_color(t, wsap_vtcore_color_index(2)) == theme.ansi[2]); - term_free(other); - term_free(t); + wsap_vtcore_free(other); + wsap_vtcore_free(t); } static void test_osc_legacy_titles(void) { - struct term *t = osc_test_term(); + struct wsap_vtcore *t = osc_test_term(); reset_captures(); write_seq(t, "\033]legacy title\007"); @@ -415,61 +415,61 @@ static void test_osc_legacy_titles(void) write_seq(t, "\033]2adjacent\033\\"); assert(!strcmp(title, "adjacent")); - term_free(t); + wsap_vtcore_free(t); } static void test_palette_and_theme(void) { uint32_t c; /* Hex formats */ - assert(term_color_parse("#f00", &c) && c == 0xFFFF0000u); - assert(term_color_parse("#00ff00", &c) && c == 0xFF00FF00u); - assert(term_color_parse(" #0000ff \t", &c) && c == 0xFF0000FFu); - assert(term_color_parse("123456", &c) && c == 0xFF123456u); - assert(term_color_parse("abc", &c) && c == 0xFFAABBCCu); - assert(term_color_parse("#123456789abc", &c) && c == 0xFF12569au); - assert(term_color_parse("#123456789", &c) && c == 0xFF124578u); - assert(!term_color_parse("#12g456789", &c)); - assert(!term_color_parse("#123456789abg", &c)); + assert(wsap_vtcore_color_parse("#f00", &c) && c == 0xFFFF0000u); + assert(wsap_vtcore_color_parse("#00ff00", &c) && c == 0xFF00FF00u); + assert(wsap_vtcore_color_parse(" #0000ff \t", &c) && c == 0xFF0000FFu); + assert(wsap_vtcore_color_parse("123456", &c) && c == 0xFF123456u); + assert(wsap_vtcore_color_parse("abc", &c) && c == 0xFFAABBCCu); + assert(wsap_vtcore_color_parse("#123456789abc", &c) && c == 0xFF12569au); + assert(wsap_vtcore_color_parse("#123456789", &c) && c == 0xFF124578u); + assert(!wsap_vtcore_color_parse("#12g456789", &c)); + assert(!wsap_vtcore_color_parse("#123456789abg", &c)); /* rgb: / rgbi: */ - assert(term_color_parse("rgb:ff/80/00", &c) && c == 0xFFFF8000u); - assert(term_color_parse("rgb:f/123/4567", &c) && c == 0xFFFF1245u); - assert(!term_color_parse("rgb:fffff/0/0", &c)); - assert(term_color_parse("rgbi:1.0/0.0/0.5", &c) && c == 0xFFFF0080u); - assert(term_color_parse("rgbi:.25/.5/.75", &c)); + assert(wsap_vtcore_color_parse("rgb:ff/80/00", &c) && c == 0xFFFF8000u); + assert(wsap_vtcore_color_parse("rgb:f/123/4567", &c) && c == 0xFFFF1245u); + assert(!wsap_vtcore_color_parse("rgb:fffff/0/0", &c)); + assert(wsap_vtcore_color_parse("rgbi:1.0/0.0/0.5", &c) && c == 0xFFFF0080u); + assert(wsap_vtcore_color_parse("rgbi:.25/.5/.75", &c)); /* Errors */ - assert(!term_color_parse(NULL, &c)); - assert(!term_color_parse("#ff", &c)); - assert(!term_color_parse("", &c)); - assert(!term_color_parse("rgb:ff/80", &c)); - assert(!term_color_parse("rgb:ff/80/00/11", &c)); - assert(!term_color_parse("rgbi:2.0/0/0", &c)); - assert(!term_color_parse("rgbi:./0/0", &c)); + assert(!wsap_vtcore_color_parse(NULL, &c)); + assert(!wsap_vtcore_color_parse("#ff", &c)); + assert(!wsap_vtcore_color_parse("", &c)); + assert(!wsap_vtcore_color_parse("rgb:ff/80", &c)); + assert(!wsap_vtcore_color_parse("rgb:ff/80/00/11", &c)); + assert(!wsap_vtcore_color_parse("rgbi:2.0/0/0", &c)); + assert(!wsap_vtcore_color_parse("rgbi:./0/0", &c)); /* Theme APIs */ - struct term_theme theme; - term_theme_default(&theme); - assert(term_theme_set_key(&theme, "foreground", "#112233") && theme.fg == 0xFF112233u); - assert(term_theme_set_key(&theme, "foreground", "") && theme.fg == 0xFFFFFFFFu); - assert(term_theme_set_key(&theme, "background", "#445566") && theme.bg == 0xFF445566u); - assert(term_theme_set_key(&theme, "background", "") && theme.bg == 0xFF1E1E2Eu); - assert(term_theme_set_key(&theme, "color0", "#010203") && theme.ansi[0] == 0xFF010203u); - assert(term_theme_set_key(&theme, "color15", "#fafbfc") && theme.ansi[15] == 0xFFFAFBFCu); - assert(term_theme_set_key(&theme, "color0", "") && theme.ansi[0] == 0xFF585B70u); - assert(!term_theme_set_key(&theme, "color16", "#000000")); - assert(!term_theme_set_key(&theme, "color01", "#000000")); - assert(!term_theme_set_key(&theme, "color", "#000000")); - assert(!term_theme_set_key(&theme, "color1x", "#000000")); - assert(!term_theme_set_key(&theme, "color100000000000000000000", "#000000")); - assert(!term_theme_set_key(&theme, "invalid", "#000000")); - assert(!term_theme_set_key(NULL, "foreground", "#000000")); - assert(!term_theme_set_key(&theme, NULL, "#000000")); - assert(!term_theme_set_key(&theme, "foreground", NULL)); - - struct term_theme hc; - term_theme_high_contrast(&hc); + struct wsap_vtcore_theme theme; + wsap_vtcore_theme_default(&theme); + assert(wsap_vtcore_theme_set_key(&theme, "foreground", "#112233") && theme.fg == 0xFF112233u); + assert(wsap_vtcore_theme_set_key(&theme, "foreground", "") && theme.fg == 0xFFFFFFFFu); + assert(wsap_vtcore_theme_set_key(&theme, "background", "#445566") && theme.bg == 0xFF445566u); + assert(wsap_vtcore_theme_set_key(&theme, "background", "") && theme.bg == 0xFF1E1E2Eu); + assert(wsap_vtcore_theme_set_key(&theme, "color0", "#010203") && theme.ansi[0] == 0xFF010203u); + assert(wsap_vtcore_theme_set_key(&theme, "color15", "#fafbfc") && theme.ansi[15] == 0xFFFAFBFCu); + assert(wsap_vtcore_theme_set_key(&theme, "color0", "") && theme.ansi[0] == 0xFF585B70u); + assert(!wsap_vtcore_theme_set_key(&theme, "color16", "#000000")); + assert(!wsap_vtcore_theme_set_key(&theme, "color01", "#000000")); + assert(!wsap_vtcore_theme_set_key(&theme, "color", "#000000")); + assert(!wsap_vtcore_theme_set_key(&theme, "color1x", "#000000")); + assert(!wsap_vtcore_theme_set_key(&theme, "color100000000000000000000", "#000000")); + assert(!wsap_vtcore_theme_set_key(&theme, "invalid", "#000000")); + assert(!wsap_vtcore_theme_set_key(NULL, "foreground", "#000000")); + assert(!wsap_vtcore_theme_set_key(&theme, NULL, "#000000")); + assert(!wsap_vtcore_theme_set_key(&theme, "foreground", NULL)); + + struct wsap_vtcore_theme hc; + wsap_vtcore_theme_high_contrast(&hc); assert(hc.bg == 0xFF000000u && hc.fg == 0xFFFFFFFFu); } diff --git a/tests/resize_failure_test.c b/tests/resize_failure_test.c index fbfa38d..0074f56 100644 --- a/tests/resize_failure_test.c +++ b/tests/resize_failure_test.c @@ -52,7 +52,7 @@ int main(void) puts("resize failure test skipped under sanitizer"); return 0; #else - struct term *term = tt_new(10, 2); + struct wsap_vtcore *term = tt_new(10, 2); assert(term); tt_write(term, "abc", 3); @@ -79,7 +79,7 @@ int main(void) assert(tt_cols(term) == 20); assert(tt_rows(term) == 2); assert(tt_cell(term, 0, 0)->text == '1'); - term_free(term); + wsap_vtcore_free(term); term = tt_new(10, 3); assert(term); @@ -96,7 +96,7 @@ int main(void) assert(tt_cell(term, 4, 0)->text == 'e'); assert(tt_cell(term, 5, 0)->text != 'f'); assert(tt_cell(term, 0, 1)->text == 'f'); - term_free(term); + wsap_vtcore_free(term); term = tt_new(10, 2); assert(term); @@ -106,12 +106,12 @@ int main(void) assert(!fail_next_calloc); /* A failed alternate-screen allocation keeps the normal screen active. */ - assert(!term_modes(term).alternate); + assert(!wsap_vtcore_modes(term).alternate); assert(tt_cell(term, 0, 0)->text == 'n'); assert(tt_cell(term, 5, 0)->text == 'l'); tt_write(term, "\033[?1049l", 8); assert(tt_cell(term, 0, 0)->text == 'n'); - term_free(term); + wsap_vtcore_free(term); /* A reflow that cannot grow its row buffers fails before it changes the * history, so the old geometry and text survive the failed resize. The @@ -144,7 +144,7 @@ int main(void) resized = tt_resize(term, 10, 40); assert(resized); assert(tt_cols(term) == 10); - term_free(term); + wsap_vtcore_free(term); /* A failed same-width height shrink must not scroll rows into history or * move the cursor. The same resize must succeed when allocation recovers. */ @@ -174,14 +174,14 @@ int main(void) assert(tt_cell(term, 0, 1)->text == 'D'); assert(tt_cursor_y(term) == 1); assert(tt_history(term) == 2); - term_free(term); + wsap_vtcore_free(term); /* The alternate screen uses the same allocation-before-scroll path. */ term = tt_new(8, 4); assert(term); tt_write(term, "\033[?1049h", 8); tt_write(term, four_rows, sizeof four_rows - 1); - assert(term_modes(term).alternate); + assert(wsap_vtcore_modes(term).alternate); assert(tt_cursor_y(term) == 3); fail_next_calloc = true; resized = tt_resize(term, 8, 2); @@ -195,7 +195,7 @@ int main(void) assert(tt_rows(term) == 2 && tt_cursor_y(term) == 1); assert(tt_cell(term, 0, 0)->text == 'C'); assert(tt_cell(term, 0, 1)->text == 'D'); - term_free(term); + wsap_vtcore_free(term); puts("lazy screen allocation failures preserve observable terminal state"); return 0; diff --git a/tests/resize_property_test.c b/tests/resize_property_test.c index 360e640..91b487f 100644 --- a/tests/resize_property_test.c +++ b/tests/resize_property_test.c @@ -1,4 +1,4 @@ -#include "term/term.h" +#include "wsap_vtcore/wsap_vtcore.h" #include "term_api.h" #include <stdint.h> @@ -18,15 +18,15 @@ static unsigned random_below(unsigned limit) /* Select from the oldest retained row to the end of the live screen. * Selection text joins wrapped rows and trims blank cells on other rows. */ -static char *logical_text(struct term *t) +static char *logical_text(struct wsap_vtcore *t) { - struct term_vector2i size = term_size(t); - term_scroll_to(t, term_scrollback(t).total); - term_select_start(t, (struct term_vector2i){ .x = 0, .y = 0 }, false, TERM_SELECT_CELL); - term_scroll_to(t, 0); - term_select_extend(t, (struct term_vector2i){ .x = size.x - 1, .y = size.y - 1 }, true); + struct wsap_vtcore_vector2i size = wsap_vtcore_size(t); + wsap_vtcore_scroll_to(t, wsap_vtcore_scrollback(t).total); + wsap_vtcore_select_start(t, (struct wsap_vtcore_vector2i){ .x = 0, .y = 0 }, false, WSAP_VTCORE_SELECT_CELL); + wsap_vtcore_scroll_to(t, 0); + wsap_vtcore_select_extend(t, (struct wsap_vtcore_vector2i){ .x = size.x - 1, .y = size.y - 1 }, true); char *text = tt_selection_text(t); - term_select_clear(t); + wsap_vtcore_select_clear(t); if (!text) return NULL; size_t out = 0; for (size_t i = 0; text[i]; i++) { @@ -40,76 +40,76 @@ static char *logical_text(struct term *t) return text; } -static uint32_t cell_at(struct term *t, struct term_snapshot *s, int x, int y) +static uint32_t cell_at(struct wsap_vtcore *t, struct wsap_vtcore_snapshot *s, int x, int y) { - if (!term_snapshot_update(s, t)) return 0; - return term_snapshot_row(s, y)[x].text; + if (!wsap_vtcore_snapshot_update(s, t)) return 0; + return wsap_vtcore_snapshot_row(s, y)[x].text; } /* A height change that pulls rows back from history moves the saved * cursor with its row. DECRC then prints next to the saved text. */ -static int saved_cursor_follows_history(struct term_snapshot *s) +static int saved_cursor_follows_history(struct wsap_vtcore_snapshot *s) { static const struct { int cols, rows, grow_cols, grow_rows; } cases[] = { { 8, 3, 8, 5 }, /* same width: rows come back from history */ { 8, 3, 10, 5 }, /* new width: reflow */ }; for (size_t i = 0; i < sizeof(cases) / sizeof(cases[0]); i++) { - struct term_options opt = { + struct wsap_vtcore_options opt = { .size = { .x = cases[i].cols, .y = cases[i].rows }, .scrollback = 10, }; - struct term *t = term_new(&opt); + struct wsap_vtcore *t = wsap_vtcore_new(&opt); if (!t) return 1; const char *text = "l1\r\nl2\r\nl3\r\nl4\r\nab\0337\033[1;1H"; - term_feed(t, text, strlen(text), 0); - struct term_vector2i size = { .x = cases[i].grow_cols, .y = cases[i].grow_rows }; - if (!term_resize(t, size)) return 1; - term_feed(t, "\0338X", 3, 0); - struct term_cursor c = term_cursor(t); + wsap_vtcore_feed(t, text, strlen(text), 0); + struct wsap_vtcore_vector2i size = { .x = cases[i].grow_cols, .y = cases[i].grow_rows }; + if (!wsap_vtcore_resize(t, size)) return 1; + wsap_vtcore_feed(t, "\0338X", 3, 0); + struct wsap_vtcore_cursor c = wsap_vtcore_cursor(t); int y = c.pos.y; if (cell_at(t, s, 0, y) != 'a' || cell_at(t, s, 1, y) != 'b' || cell_at(t, s, 2, y) != 'X') { fprintf(stderr, "case %zu: DECRC after a resize lost the saved row\n", i); return 1; } - term_free(t); + wsap_vtcore_free(t); } return 0; } /* Narrowing a full screen with the cursor at the top wraps more rows than * the ring holds. The cursor row must survive and stay on screen. */ -static int narrow_resize_keeps_cursor_row(struct term_snapshot *s) +static int narrow_resize_keeps_cursor_row(struct wsap_vtcore_snapshot *s) { - struct term_options opt = { .size = { .x = 40, .y = 12 }, .scrollback = 5 }; - struct term *t = term_new(&opt); + struct wsap_vtcore_options opt = { .size = { .x = 40, .y = 12 }, .scrollback = 5 }; + struct wsap_vtcore *t = wsap_vtcore_new(&opt); if (!t) return 1; for (int y = 0; y < 12; y++) { char line[64]; memset(line, 'a' + y, 40); line[40] = 0; - term_feed(t, line, 40, 0); + wsap_vtcore_feed(t, line, 40, 0); } - term_feed(t, "\033[1;1H", 6, 0); - if (!term_resize(t, (struct term_vector2i){ .x = 1, .y = 12 })) return 1; - struct term_cursor c = term_cursor(t); + wsap_vtcore_feed(t, "\033[1;1H", 6, 0); + if (!wsap_vtcore_resize(t, (struct wsap_vtcore_vector2i){ .x = 1, .y = 12 })) return 1; + struct wsap_vtcore_cursor c = wsap_vtcore_cursor(t); if (c.pos.x != 0 || c.pos.y != 0 || cell_at(t, s, 0, 0) != 'a') { fprintf(stderr, "narrow resize: cursor %d,%d, cell %x\n", c.pos.x, c.pos.y, cell_at(t, s, 0, 0)); return 1; } - term_feed(t, "Z", 1, 0); + wsap_vtcore_feed(t, "Z", 1, 0); if (cell_at(t, s, 0, 0) != 'Z') return 1; - term_free(t); + wsap_vtcore_free(t); return 0; } int main(int argc, char **argv) { - struct term_snapshot *snap = term_snapshot_new(); + struct wsap_vtcore_snapshot *snap = wsap_vtcore_snapshot_new(); if (!snap || saved_cursor_follows_history(snap) || narrow_resize_keeps_cursor_row(snap)) return 1; - term_snapshot_free(snap); + wsap_vtcore_snapshot_free(snap); int seeds = argc > 1 ? atoi(argv[1]) : 100; static const char *word[] = { @@ -117,28 +117,28 @@ int main(int argc, char **argv) }; for (int seed = 1; seed <= seeds; seed++) { state = 0x9e3779b97f4a7c15ull * (uint64_t)seed; - struct term_options opt = { + struct wsap_vtcore_options opt = { .size = { .x = 40, .y = 12 }, .scrollback = 4096, }; - struct term *t = term_new(&opt); + struct wsap_vtcore *t = wsap_vtcore_new(&opt); if (!t) return 1; for (int line = 0; line < 16; line++) { int words = 1 + (int)random_below(4); for (int i = 0; i < words; i++) { const char *s = word[random_below(sizeof(word) / sizeof(word[0]))]; - term_feed(t, s, strlen(s), 0); + wsap_vtcore_feed(t, s, strlen(s), 0); } - if (line != 15) term_feed(t, "\r\n", 2, 0); + if (line != 15) wsap_vtcore_feed(t, "\r\n", 2, 0); } char *before = logical_text(t); if (!before) return 1; for (int step = 0; step < 20; step++) { - struct term_vector2i size = { + struct wsap_vtcore_vector2i size = { .x = 1 + (int)random_below(200), .y = 1 + (int)random_below(60), }; - if (!term_resize(t, size)) return 1; + if (!wsap_vtcore_resize(t, size)) return 1; char *after = logical_text(t); if (!after) return 1; if (strcmp(before, after)) { @@ -150,7 +150,7 @@ int main(int argc, char **argv) free(after); } free(before); - term_free(t); + wsap_vtcore_free(t); } return 0; } diff --git a/tests/snapshot_failure_test.c b/tests/snapshot_failure_test.c index 7d4b139..bf4b694 100644 --- a/tests/snapshot_failure_test.c +++ b/tests/snapshot_failure_test.c @@ -1,4 +1,4 @@ -#include "term/term.h" +#include "wsap_vtcore/wsap_vtcore.h" #include <assert.h> #include <stdbool.h> @@ -49,18 +49,18 @@ void *__wrap_realloc(void *p, size_t size) /* A copy of everything a renderer can read from a snapshot. */ struct frame { - struct term_view view; - uint32_t palette[TERM_PALETTE_SIZE]; + struct wsap_vtcore_view view; + uint32_t palette[WSAP_VTCORE_PALETTE_SIZE]; int cols, rows; - struct term_cell *cells; /* rows * cols */ + struct wsap_vtcore_cell *cells; /* rows * cols */ uint32_t *cps; /* per cell: count, then code points */ uint64_t *keys; /* per row */ - struct term_span *sel; /* per row */ + struct wsap_vtcore_span *sel; /* per row */ }; -static void frame_capture(const struct term_snapshot *s, struct frame *f) +static void frame_capture(const struct wsap_vtcore_snapshot *s, struct frame *f) { - const struct term_view *v = term_snapshot_view(s); + const struct wsap_vtcore_view *v = wsap_vtcore_snapshot_view(s); f->view = *v; memcpy(f->palette, v->palette, sizeof(f->palette)); f->cols = v->size.x; @@ -72,17 +72,17 @@ static void frame_capture(const struct term_snapshot *s, struct frame *f) f->sel = calloc((size_t)f->rows + 1, sizeof(*f->sel)); assert(f->cells && f->cps && f->keys && f->sel); for (int y = 0; y < f->rows; y++) { - const struct term_cell *row = term_snapshot_row(s, y); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(s, y); assert(row); - f->keys[y] = term_snapshot_row_key(s, y); - f->sel[y] = term_snapshot_row_selection(s, y); + f->keys[y] = wsap_vtcore_snapshot_row_key(s, y); + f->sel[y] = wsap_vtcore_snapshot_row_selection(s, y); for (int x = 0; x < f->cols; x++) { size_t i = (size_t)y * f->cols + x; f->cells[i] = row[x]; uint32_t *cps = f->cps + i * CPS_SLOT; cps[0] = 0; - if (row[x].text & TERM_TEXT_CLUSTER) - cps[0] = (uint32_t)term_snapshot_cluster(s, row[x].text, cps + 1, CPS_MAX); + if (row[x].text & WSAP_VTCORE_TEXT_CLUSTER) + cps[0] = (uint32_t)wsap_vtcore_snapshot_cluster(s, row[x].text, cps + 1, CPS_MAX); } } } @@ -97,7 +97,7 @@ static void frame_free(struct frame *f) static bool same_view(const struct frame *a, const struct frame *b) { - const struct term_view *x = &a->view, *y = &b->view; + const struct wsap_vtcore_view *x = &a->view, *y = &b->view; return x->size.x == y->size.x && x->size.y == y->size.y && x->cursor.pos.x == y->cursor.pos.x && x->cursor.pos.y == y->cursor.pos.y && x->cursor.style == y->cursor.style && x->cursor.visible == y->cursor.visible && @@ -125,7 +125,7 @@ static bool frame_same(const struct frame *a, const struct frame *b) * between an incremental snapshot and a fresh one. */ static bool frame_shows_same(const struct frame *a, const struct frame *b) { - const struct term_view *x = &a->view, *y = &b->view; + const struct wsap_vtcore_view *x = &a->view, *y = &b->view; if (a->cols != b->cols || a->rows != b->rows || x->cursor.pos.x != y->cursor.pos.x || x->cursor.pos.y != y->cursor.pos.y || x->cursor.visible != y->cursor.visible || x->scroll_offset != y->scroll_offset || x->reverse_video != y->reverse_video || @@ -136,11 +136,11 @@ static bool frame_shows_same(const struct frame *a, const struct frame *b) return false; for (int c = 0; c < a->cols; c++) { size_t i = (size_t)r * a->cols + c; - const struct term_cell *p = &a->cells[i], *q = &b->cells[i]; + const struct wsap_vtcore_cell *p = &a->cells[i], *q = &b->cells[i]; const uint32_t *cp = a->cps + i * CPS_SLOT, *cq = b->cps + i * CPS_SLOT; if (p->fg != q->fg || p->bg != q->bg || p->attrs != q->attrs || p->width != q->width) return false; - if (p->text & TERM_TEXT_CLUSTER) { + if (p->text & WSAP_VTCORE_TEXT_CLUSTER) { if (cp[0] != cq[0] || memcmp(cp + 1, cq + 1, cp[0] * sizeof(*cp)) != 0) return false; } else if (p->text != q->text) { @@ -154,13 +154,13 @@ static bool frame_shows_same(const struct frame *a, const struct frame *b) /* One update with the k-th allocation failing, from the state the caller * built. A failed update must leave s as it was, and the retry must succeed. * Returns true when an allocation was failed. */ -static bool update_failing_at(struct term_snapshot *s, struct term *t, int k) +static bool update_failing_at(struct wsap_vtcore_snapshot *s, struct wsap_vtcore *t, int k) { struct frame before, after; frame_capture(s, &before); alloc_was_failed = false; alloc_countdown = k; - bool ok = term_snapshot_update(s, t); + bool ok = wsap_vtcore_snapshot_update(s, t); alloc_countdown = -1; bool injected = alloc_was_failed; if (!ok) { @@ -168,7 +168,7 @@ static bool update_failing_at(struct term_snapshot *s, struct term *t, int k) frame_capture(s, &after); assert(frame_same(&before, &after)); frame_free(&after); - assert(term_snapshot_update(s, t)); + assert(wsap_vtcore_snapshot_update(s, t)); } frame_free(&before); return injected; @@ -191,7 +191,7 @@ static int sweep(bool (*attempt)(int k)) * an update succeeds. Every failed attempt must leave s as it was. Progress * from earlier attempts stays, so this covers the later steps of a long run * rather than each site from one start. Returns the number of failures. */ -static int update_each_failure(struct term_snapshot *s, struct term *t) +static int update_each_failure(struct wsap_vtcore_snapshot *s, struct wsap_vtcore *t) { struct frame before, after; frame_capture(s, &before); @@ -201,7 +201,7 @@ static int update_each_failure(struct term_snapshot *s, struct term *t) assert(k < 1000); alloc_was_failed = false; alloc_countdown = k; - ok = term_snapshot_update(s, t); + ok = wsap_vtcore_snapshot_update(s, t); alloc_countdown = -1; if (ok) break; @@ -216,53 +216,53 @@ static int update_each_failure(struct term_snapshot *s, struct term *t) } /* A renderer sees the same picture as a fresh capture of t. */ -static void expect_matches_fresh(struct term *t, const struct term_snapshot *s) +static void expect_matches_fresh(struct wsap_vtcore *t, const struct wsap_vtcore_snapshot *s) { - struct term_snapshot *fresh = term_snapshot_new(); - assert(fresh && term_snapshot_update(fresh, t)); + struct wsap_vtcore_snapshot *fresh = wsap_vtcore_snapshot_new(); + assert(fresh && wsap_vtcore_snapshot_update(fresh, t)); struct frame a, b; frame_capture(s, &a); frame_capture(fresh, &b); assert(frame_shows_same(&a, &b)); frame_free(&a); frame_free(&b); - term_snapshot_free(fresh); + wsap_vtcore_snapshot_free(fresh); } /* A US flag and a ZWJ family: two regional indicators, and five code points. */ static const char flag_us[] = "\xf0\x9f\x87\xba\xf0\x9f\x87\xb8"; static const char family[] = "\xf0\x9f\x91\xa8\xe2\x80\x8d\xf0\x9f\x91\xa9\xe2\x80\x8d\xf0\x9f\x91\xa7"; -static uint32_t cluster_cps(const struct term_snapshot *s, const struct term_cell *cell, +static uint32_t cluster_cps(const struct wsap_vtcore_snapshot *s, const struct wsap_vtcore_cell *cell, uint32_t *cps, int cap) { - return (uint32_t)term_snapshot_cluster(s, cell->text, cps, cap); + return (uint32_t)wsap_vtcore_snapshot_cluster(s, cell->text, cps, cap); } /* A new terminal and an empty snapshot. The first update grows every buffer * and the arena, so each allocation site in the update is hit. */ static bool first_update_at(int k) { - struct term_options options = { .size = { 8, 3 }, .scrollback = 5 }; - struct term *t = term_new(&options); - struct term_snapshot *s = term_snapshot_new(); + struct wsap_vtcore_options options = { .size = { 8, 3 }, .scrollback = 5 }; + struct wsap_vtcore *t = wsap_vtcore_new(&options); + struct wsap_vtcore_snapshot *s = wsap_vtcore_snapshot_new(); assert(t && s); const char accented[] = "e\xcc\x81 "; - term_feed(t, accented, sizeof(accented) - 1, 0); - term_feed(t, flag_us, sizeof(flag_us) - 1, 0); + wsap_vtcore_feed(t, accented, sizeof(accented) - 1, 0); + wsap_vtcore_feed(t, flag_us, sizeof(flag_us) - 1, 0); bool injected = update_failing_at(s, t, k); - const struct term_cell *row = term_snapshot_row(s, 0); - assert(row && (row[0].text & TERM_TEXT_CLUSTER)); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(s, 0); + assert(row && (row[0].text & WSAP_VTCORE_TEXT_CLUSTER)); uint32_t cps[8]; assert(cluster_cps(s, &row[0], cps, 8) == 2 && cps[0] == 'e' && cps[1] == 0x301); assert(cluster_cps(s, &row[2], cps, 8) == 2 && cps[0] == 0x1F1FA && cps[1] == 0x1F1F8); expect_matches_fresh(t, s); - term_snapshot_free(s); - term_free(t); + wsap_vtcore_snapshot_free(s); + wsap_vtcore_free(t); return injected; } @@ -270,60 +270,60 @@ static bool first_update_at(int k) * 256 words, so the arena growth is one of the failing sites. */ static bool full_cluster_screen_at(int k) { - struct term_options options = { .size = { 32, 16 }, .scrollback = 5 }; - struct term *t = term_new(&options); - struct term_snapshot *s = term_snapshot_new(); + struct wsap_vtcore_options options = { .size = { 32, 16 }, .scrollback = 5 }; + struct wsap_vtcore *t = wsap_vtcore_new(&options); + struct wsap_vtcore_snapshot *s = wsap_vtcore_snapshot_new(); assert(t && s); for (int y = 0; y < 16; y++) { for (int i = 0; i < 16; i++) { if (y % 2) - term_feed(t, flag_us, sizeof(flag_us) - 1, 0); + wsap_vtcore_feed(t, flag_us, sizeof(flag_us) - 1, 0); else - term_feed(t, family, sizeof(family) - 1, 0); + wsap_vtcore_feed(t, family, sizeof(family) - 1, 0); } if (y < 15) - term_feed(t, "\r\n", 2, 0); + wsap_vtcore_feed(t, "\r\n", 2, 0); } bool injected = update_failing_at(s, t, k); uint32_t cps[8]; - const struct term_cell *row = term_snapshot_row(s, 0); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(s, 0); assert(cluster_cps(s, &row[0], cps, 8) == 5 && cps[0] == 0x1F468 && cps[1] == 0x200D); - row = term_snapshot_row(s, 1); + row = wsap_vtcore_snapshot_row(s, 1); assert(cluster_cps(s, &row[0], cps, 8) == 2 && cps[0] == 0x1F1FA); expect_matches_fresh(t, s); - term_snapshot_free(s); - term_free(t); + wsap_vtcore_snapshot_free(s); + wsap_vtcore_free(t); return injected; } /* The screen grows, so cells, keys, row clusters, and selection all reserve. */ static bool resize_at(int k) { - struct term_options options = { .size = { 8, 3 }, .scrollback = 5 }; - struct term *t = term_new(&options); - struct term_snapshot *s = term_snapshot_new(); + struct wsap_vtcore_options options = { .size = { 8, 3 }, .scrollback = 5 }; + struct wsap_vtcore *t = wsap_vtcore_new(&options); + struct wsap_vtcore_snapshot *s = wsap_vtcore_snapshot_new(); assert(t && s); - term_feed(t, "old", 3, 0); - assert(term_snapshot_update(s, t)); + wsap_vtcore_feed(t, "old", 3, 0); + assert(wsap_vtcore_snapshot_update(s, t)); - assert(term_resize(t, (struct term_vector2i){ 32, 16 })); - term_feed(t, "\x1b[H\x1b[2J", 7, 0); - term_feed(t, family, sizeof(family) - 1, 0); + assert(wsap_vtcore_resize(t, (struct wsap_vtcore_vector2i){ 32, 16 })); + wsap_vtcore_feed(t, "\x1b[H\x1b[2J", 7, 0); + wsap_vtcore_feed(t, family, sizeof(family) - 1, 0); bool injected = update_failing_at(s, t, k); - assert(term_snapshot_view(s)->size.x == 32 && term_snapshot_view(s)->size.y == 16); + assert(wsap_vtcore_snapshot_view(s)->size.x == 32 && wsap_vtcore_snapshot_view(s)->size.y == 16); uint32_t cps[8]; - const struct term_cell *row = term_snapshot_row(s, 0); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(s, 0); assert(cluster_cps(s, &row[0], cps, 8) == 5 && cps[0] == 0x1F468); expect_matches_fresh(t, s); - term_snapshot_free(s); - term_free(t); + wsap_vtcore_snapshot_free(s); + wsap_vtcore_free(t); return injected; } @@ -331,124 +331,124 @@ static bool resize_at(int k) * row list, off the stack. */ static bool tall_screen_at(int k) { - struct term_options options = { .size = { 8, 300 }, .scrollback = 5 }; - struct term *t = term_new(&options); - struct term_snapshot *s = term_snapshot_new(); + struct wsap_vtcore_options options = { .size = { 8, 300 }, .scrollback = 5 }; + struct wsap_vtcore *t = wsap_vtcore_new(&options); + struct wsap_vtcore_snapshot *s = wsap_vtcore_snapshot_new(); assert(t && s); for (int y = 0; y < 299; y++) - term_feed(t, "\r\n", 2, 0); - term_feed(t, "e\xcc\x81yes", 5, 0); - assert(term_select_start(t, (struct term_vector2i){ .x = 0, .y = 299 }, false, - TERM_SELECT_CELL)); - assert(term_select_extend(t, (struct term_vector2i){ .x = 3, .y = 299 }, true)); + wsap_vtcore_feed(t, "\r\n", 2, 0); + wsap_vtcore_feed(t, "e\xcc\x81yes", 5, 0); + assert(wsap_vtcore_select_start(t, (struct wsap_vtcore_vector2i){ .x = 0, .y = 299 }, false, + WSAP_VTCORE_SELECT_CELL)); + assert(wsap_vtcore_select_extend(t, (struct wsap_vtcore_vector2i){ .x = 3, .y = 299 }, true)); bool injected = update_failing_at(s, t, k); - assert(term_snapshot_view(s)->size.y == 300); - const struct term_cell *row = term_snapshot_row(s, 299); + assert(wsap_vtcore_snapshot_view(s)->size.y == 300); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(s, 299); uint32_t cps[4]; assert(cluster_cps(s, &row[0], cps, 4) == 2 && cps[0] == 'e' && cps[1] == 0x301); - struct term_span span = term_snapshot_row_selection(s, 299); + struct wsap_vtcore_span span = wsap_vtcore_snapshot_row_selection(s, 299); assert(span.begin == 0 && span.end == 4); expect_matches_fresh(t, s); - term_snapshot_free(s); - term_free(t); + wsap_vtcore_snapshot_free(s); + wsap_vtcore_free(t); return injected; } /* Without failures, the selection of a tall screen reaches the last row. */ static void tall_selection_is_kept(void) { - struct term_options options = { .size = { 8, 300 }, .scrollback = 5 }; - struct term *t = term_new(&options); - struct term_snapshot *s = term_snapshot_new(); + struct wsap_vtcore_options options = { .size = { 8, 300 }, .scrollback = 5 }; + struct wsap_vtcore *t = wsap_vtcore_new(&options); + struct wsap_vtcore_snapshot *s = wsap_vtcore_snapshot_new(); assert(t && s); for (int y = 0; y < 299; y++) - term_feed(t, "\r\n", 2, 0); - term_feed(t, "e\xcc\x81yes", 5, 0); - term_select_start(t, (struct term_vector2i){ .x = 0, .y = 299 }, false, TERM_SELECT_CELL); - term_select_extend(t, (struct term_vector2i){ .x = 3, .y = 299 }, true); + wsap_vtcore_feed(t, "\r\n", 2, 0); + wsap_vtcore_feed(t, "e\xcc\x81yes", 5, 0); + wsap_vtcore_select_start(t, (struct wsap_vtcore_vector2i){ .x = 0, .y = 299 }, false, WSAP_VTCORE_SELECT_CELL); + wsap_vtcore_select_extend(t, (struct wsap_vtcore_vector2i){ .x = 3, .y = 299 }, true); - assert(term_snapshot_update(s, t)); - struct term_span span = term_snapshot_row_selection(s, 299); + assert(wsap_vtcore_snapshot_update(s, t)); + struct wsap_vtcore_span span = wsap_vtcore_snapshot_row_selection(s, 299); assert(span.begin == 0 && span.end == 4); expect_matches_fresh(t, s); - term_snapshot_free(s); - term_free(t); + wsap_vtcore_snapshot_free(s); + wsap_vtcore_free(t); } /* On a screen taller than 256 rows, selecting needs memory. When none is * left, the call fails and the selection stays as it was. */ static void tall_selection_fails_cleanly(void) { - struct term_options options = { .size = { 8, 300 }, .scrollback = 5 }; - struct term *t = term_new(&options); + struct wsap_vtcore_options options = { .size = { 8, 300 }, .scrollback = 5 }; + struct wsap_vtcore *t = wsap_vtcore_new(&options); assert(t); for (int y = 0; y < 299; y++) - term_feed(t, "\r\n", 2, 0); - term_feed(t, "yes", 3, 0); - assert(term_select_start(t, (struct term_vector2i){ .x = 0, .y = 299 }, false, - TERM_SELECT_CELL)); - assert(term_select_extend(t, (struct term_vector2i){ .x = 1, .y = 299 }, true)); - char *before = term_selection_text(t); + wsap_vtcore_feed(t, "\r\n", 2, 0); + wsap_vtcore_feed(t, "yes", 3, 0); + assert(wsap_vtcore_select_start(t, (struct wsap_vtcore_vector2i){ .x = 0, .y = 299 }, false, + WSAP_VTCORE_SELECT_CELL)); + assert(wsap_vtcore_select_extend(t, (struct wsap_vtcore_vector2i){ .x = 1, .y = 299 }, true)); + char *before = wsap_vtcore_selection_text(t); assert(before && !strcmp(before, "ye")); alloc_was_failed = false; alloc_countdown = 0; - assert(!term_select_extend(t, (struct term_vector2i){ .x = 2, .y = 299 }, true)); + assert(!wsap_vtcore_select_extend(t, (struct wsap_vtcore_vector2i){ .x = 2, .y = 299 }, true)); alloc_countdown = -1; assert(alloc_was_failed); alloc_was_failed = false; alloc_countdown = 0; - assert(!term_select_start(t, (struct term_vector2i){ .x = 2, .y = 299 }, false, - TERM_SELECT_WORD)); + assert(!wsap_vtcore_select_start(t, (struct wsap_vtcore_vector2i){ .x = 2, .y = 299 }, false, + WSAP_VTCORE_SELECT_WORD)); alloc_countdown = -1; assert(alloc_was_failed); - char *after = term_selection_text(t); + char *after = wsap_vtcore_selection_text(t); assert(after && !strcmp(after, before)); - term_text_free(before); - term_text_free(after); + wsap_vtcore_text_free(before); + wsap_vtcore_text_free(after); - assert(term_select_extend(t, (struct term_vector2i){ .x = 2, .y = 299 }, true)); - char *grown = term_selection_text(t); + assert(wsap_vtcore_select_extend(t, (struct wsap_vtcore_vector2i){ .x = 2, .y = 299 }, true)); + char *grown = wsap_vtcore_selection_text(t); assert(grown && !strcmp(grown, "yes")); - term_text_free(grown); - term_free(t); + wsap_vtcore_text_free(grown); + wsap_vtcore_free(t); } /* Scroll with clusters in most lines. Each step fails every allocation in * turn, then retries, and must match a fresh capture. */ static void scrolling_fails_cleanly(void) { - struct term_options options = { .size = { 8, 3 }, .scrollback = 5 }; - struct term *t = term_new(&options); - struct term_snapshot *s = term_snapshot_new(); + struct wsap_vtcore_options options = { .size = { 8, 3 }, .scrollback = 5 }; + struct wsap_vtcore *t = wsap_vtcore_new(&options); + struct wsap_vtcore_snapshot *s = wsap_vtcore_snapshot_new(); assert(t && s); int failures = 0; for (int i = 0; i < 300; i++) { - term_feed(t, "e\xcc\x81", 3, 0); + wsap_vtcore_feed(t, "e\xcc\x81", 3, 0); if (i % 3 == 0) - term_feed(t, flag_us, sizeof(flag_us) - 1, 0); + wsap_vtcore_feed(t, flag_us, sizeof(flag_us) - 1, 0); if (i % 5 == 0) - term_feed(t, family, sizeof(family) - 1, 0); - term_feed(t, "\r\n", 2, 0); + wsap_vtcore_feed(t, family, sizeof(family) - 1, 0); + wsap_vtcore_feed(t, "\r\n", 2, 0); if (i == 150) - term_select_start(t, (struct term_vector2i){ .x = 0, .y = 1 }, false, TERM_SELECT_CELL); + wsap_vtcore_select_start(t, (struct wsap_vtcore_vector2i){ .x = 0, .y = 1 }, false, WSAP_VTCORE_SELECT_CELL); if (i == 151) - term_select_extend(t, (struct term_vector2i){ .x = 4, .y = 2 }, true); + wsap_vtcore_select_extend(t, (struct wsap_vtcore_vector2i){ .x = 4, .y = 2 }, true); failures += update_each_failure(s, t); expect_matches_fresh(t, s); } assert(failures > 0); - assert(term_history_rows(t) == 5); + assert(wsap_vtcore_history_rows(t) == 5); - term_snapshot_free(s); - term_free(t); + wsap_vtcore_snapshot_free(s); + wsap_vtcore_free(t); } int main(void) diff --git a/tests/snapshot_scroll_arena_test.c b/tests/snapshot_scroll_arena_test.c index 7da6507..8e20aae 100644 --- a/tests/snapshot_scroll_arena_test.c +++ b/tests/snapshot_scroll_arena_test.c @@ -7,23 +7,23 @@ int main(void) { - struct term_options options = { .size = { 8, 24 }, .scrollback = 5 }; - struct term *t = term_new(&options); - struct term_snapshot *s = term_snapshot_new(); - assert(t && s && term_snapshot_update(s, t)); + struct wsap_vtcore_options options = { .size = { 8, 24 }, .scrollback = 5 }; + struct wsap_vtcore *t = wsap_vtcore_new(&options); + struct wsap_vtcore_snapshot *s = wsap_vtcore_snapshot_new(); + assert(t && s && wsap_vtcore_snapshot_update(s, t)); const char line[] = "e\xcc\x81\r\n"; for (int i = 0; i < 10000; i++) { - term_feed(t, line, sizeof(line) - 1, 0); - assert(term_snapshot_update(s, t)); + wsap_vtcore_feed(t, line, sizeof(line) - 1, 0); + assert(wsap_vtcore_snapshot_update(s, t)); } /* A fixed viewport holds fewer than 24 * 8 cluster records at once. * Dead records are compacted before they can dominate this arena. */ - assert(term_history_rows(t) == 5); + assert(wsap_vtcore_history_rows(t) == 5); assert(s->arena_len < 8192); - term_snapshot_free(s); - term_free(t); + wsap_vtcore_snapshot_free(s); + wsap_vtcore_free(t); return 0; } diff --git a/tests/spec_test.c b/tests/spec_test.c index 202f9ba..56e974c 100644 --- a/tests/spec_test.c +++ b/tests/spec_test.c @@ -6,7 +6,7 @@ * Rows read as text: '#' is U+FFFD, '?' is any other code point outside * ASCII or a cluster, '_' is the right half of a wide glyph. */ -#include "term/term.h" +#include "wsap_vtcore/wsap_vtcore.h" #include <stdio.h> #include <stdlib.h> @@ -21,7 +21,7 @@ struct spec { * the history check; reply NULL skips the reply check. */ int attr_x, attr_y; uint16_t attrs; - term_color fg, bg; + wsap_vtcore_color fg, bg; int history; const char *reply; }; @@ -31,8 +31,8 @@ struct spec { #define NO_EXTRA .attr_x = -1, .history = -1 #define CASE(name_, input_, a, b, c, x_, y_) \ { .name = name_, .input = input_, .cols = 8, .rows = 3, ROWS3(a, b, c), AT(x_, y_), NO_EXTRA } -#define RED (TERM_COLOR_SLOT | 1) -#define BLUE (TERM_COLOR_SLOT | 4) +#define RED (WSAP_VTCORE_COLOR_SLOT | 1) +#define BLUE (WSAP_VTCORE_COLOR_SLOT | 4) static const struct spec cases[] = { /* Printing and C0 controls. */ @@ -174,56 +174,56 @@ static const struct spec cases[] = { .name = "SGR", .input = "\033[1;3;4;9;53;38;5;123;48;2;1;2;3mX", .cols = 8, .rows = 3, ROWS3("X", "", ""), AT(1, 0), .attr_x = 0, .attr_y = 0, - .attrs = TERM_ATTR_BOLD | TERM_ATTR_ITALIC | TERM_ATTR_STRIKE | - TERM_ATTR_OVERLINE | TERM_ATTR_UNDERLINE, - .fg = TERM_COLOR_SLOT | 123, .bg = 0xff010203u, .history = -1, + .attrs = WSAP_VTCORE_ATTR_BOLD | WSAP_VTCORE_ATTR_ITALIC | WSAP_VTCORE_ATTR_STRIKE | + WSAP_VTCORE_ATTR_OVERLINE | WSAP_VTCORE_ATTR_UNDERLINE, + .fg = WSAP_VTCORE_COLOR_SLOT | 123, .bg = 0xff010203u, .history = -1, }, { .name = "SGR colon RGB with a color space", .input = "\033[38:2::1:2:3mX", .cols = 8, .rows = 3, ROWS3("X", "", ""), AT(1, 0), - .attr_x = 0, .attr_y = 0, .fg = 0xff010203u, .bg = TERM_COLOR_BG, .history = -1, + .attr_x = 0, .attr_y = 0, .fg = 0xff010203u, .bg = WSAP_VTCORE_COLOR_BG, .history = -1, }, { /* 48:2:: takes the next three fields as RGB; the trailing 0 resets. */ .name = "SGR colon form is not two semicolon colors", .input = "\033[48:2::::38;2;;;mX", .cols = 8, .rows = 3, ROWS3("X", "", ""), AT(1, 0), - .attr_x = 0, .attr_y = 0, .fg = TERM_COLOR_FG, .bg = TERM_COLOR_BG, .history = -1, + .attr_x = 0, .attr_y = 0, .fg = WSAP_VTCORE_COLOR_FG, .bg = WSAP_VTCORE_COLOR_BG, .history = -1, }, { .name = "restore restores the pen", .input = "\033[31m\0337\033[m\0338X", .cols = 8, .rows = 3, ROWS3("X", "", ""), AT(1, 0), - .attr_x = 0, .attr_y = 0, .fg = RED, .bg = TERM_COLOR_BG, .history = -1, + .attr_x = 0, .attr_y = 0, .fg = RED, .bg = WSAP_VTCORE_COLOR_BG, .history = -1, }, { .name = "SCORC restores the pen", .input = "\033[1m\033[s\033[m\033[uX", .cols = 8, .rows = 3, ROWS3("X", "", ""), AT(1, 0), - .attr_x = 0, .attr_y = 0, .attrs = TERM_ATTR_BOLD, - .fg = TERM_COLOR_FG, .bg = TERM_COLOR_BG, .history = -1, + .attr_x = 0, .attr_y = 0, .attrs = WSAP_VTCORE_ATTR_BOLD, + .fg = WSAP_VTCORE_COLOR_FG, .bg = WSAP_VTCORE_COLOR_BG, .history = -1, }, { .name = "restore without save resets the pen", .input = "\033[31m\0338X", .cols = 8, .rows = 3, ROWS3("X", "", ""), AT(1, 0), - .attr_x = 0, .attr_y = 0, .fg = TERM_COLOR_FG, .bg = TERM_COLOR_BG, .history = -1, + .attr_x = 0, .attr_y = 0, .fg = WSAP_VTCORE_COLOR_FG, .bg = WSAP_VTCORE_COLOR_BG, .history = -1, }, { /* A rectangle edge on the right half of a wide glyph changes both * halves. */ .name = "DECCARA on half a wide glyph", .input = "a中b\033[1;3;1;3;1$r", .cols = 8, .rows = 3, ROWS3("a?_b", "", ""), AT(4, 0), - .attr_x = 1, .attr_y = 0, .attrs = TERM_ATTR_BOLD, - .fg = TERM_COLOR_FG, .bg = TERM_COLOR_BG, .history = -1, + .attr_x = 1, .attr_y = 0, .attrs = WSAP_VTCORE_ATTR_BOLD, + .fg = WSAP_VTCORE_COLOR_FG, .bg = WSAP_VTCORE_COLOR_BG, .history = -1, }, { .name = "erase uses the pen background", .input = "ab\033[41m\033[1;1H\033[X", .cols = 8, .rows = 3, ROWS3(" b", "", ""), AT(0, 0), - .attr_x = 0, .attr_y = 0, .fg = TERM_COLOR_FG, .bg = TERM_COLOR_SLOT | 1, .history = -1, + .attr_x = 0, .attr_y = 0, .fg = WSAP_VTCORE_COLOR_FG, .bg = WSAP_VTCORE_COLOR_SLOT | 1, .history = -1, }, { .name = "full-screen scroll BCE", .input = "abc\033[44m\r\n\r\n\r\n", .cols = 8, .rows = 3, ROWS3("", "", ""), AT(0, 2), .attr_x = 0, .attr_y = 2, - .fg = TERM_COLOR_FG, .bg = BLUE, .history = -1, + .fg = WSAP_VTCORE_COLOR_FG, .bg = BLUE, .history = -1, }, /* Replies. */ @@ -268,41 +268,41 @@ static void on_reply(void *ud, const char *bytes, size_t len) } } -static char cell_char(const struct term_snapshot *s, const struct term_cell *c) +static char cell_char(const struct wsap_vtcore_snapshot *s, const struct wsap_vtcore_cell *c) { if (c->width == 0) return '_'; uint32_t cps[4] = {0}; - int n = term_snapshot_cluster(s, c->text, cps, 4); + int n = wsap_vtcore_snapshot_cluster(s, c->text, cps, 4); if (n != 1) return '?'; if (cps[0] == 0xFFFD) return '#'; return cps[0] >= 0x20 && cps[0] < 0x7f ? (char)cps[0] : '?'; } -static int run(const struct spec *c, struct term_snapshot *s, bool bytes) +static int run(const struct spec *c, struct wsap_vtcore_snapshot *s, bool bytes) { struct replies got = {0}; - struct term_options opt = { + struct wsap_vtcore_options opt = { .size = { .x = c->cols, .y = c->rows }, .scrollback = 100, .callbacks = { .ud = &got, .reply = on_reply }, }; - struct term *t = term_new(&opt); + struct wsap_vtcore *t = wsap_vtcore_new(&opt); if (!t) return 1; size_t len = strlen(c->input); if (bytes) - for (size_t i = 0; i < len; i++) term_feed(t, c->input + i, 1, 0); + for (size_t i = 0; i < len; i++) wsap_vtcore_feed(t, c->input + i, 1, 0); else - term_feed(t, c->input, len, 0); + wsap_vtcore_feed(t, c->input, len, 0); const char *mode = bytes ? "byte by byte" : "whole"; int bad = 0; - struct term_cursor cursor = term_cursor(t); + struct wsap_vtcore_cursor cursor = wsap_vtcore_cursor(t); if (cursor.pos.x != c->x || cursor.pos.y != c->y) { fprintf(stderr, "%s (%s): cursor %d,%d; expected %d,%d\n", c->name, mode, cursor.pos.x, cursor.pos.y, c->x, c->y); bad = 1; } - if (!term_snapshot_update(s, t)) return 1; + if (!wsap_vtcore_snapshot_update(s, t)) return 1; for (int y = 0; y < c->rows && y < 4; y++) { - const struct term_cell *row = term_snapshot_row(s, y); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(s, y); char text[64]; int n = 0; for (int x = 0; x < c->cols && n < 63; x++) text[n++] = cell_char(s, &row[x]); @@ -316,66 +316,66 @@ static int run(const struct spec *c, struct term_snapshot *s, bool bytes) } } if (c->attr_x >= 0) { - const struct term_cell *cell = &term_snapshot_row(s, c->attr_y)[c->attr_x]; + const struct wsap_vtcore_cell *cell = &wsap_vtcore_snapshot_row(s, c->attr_y)[c->attr_x]; if (cell->attrs != c->attrs || cell->fg != c->fg || cell->bg != c->bg) { fprintf(stderr, "%s (%s): attributes %x fg %x bg %x; expected %x %x %x\n", c->name, mode, cell->attrs, cell->fg, cell->bg, c->attrs, c->fg, c->bg); bad = 1; } } - if (c->history >= 0 && term_scrollback(t).total != c->history) { + if (c->history >= 0 && wsap_vtcore_scrollback(t).total != c->history) { fprintf(stderr, "%s (%s): history %d; expected %d\n", c->name, mode, - term_scrollback(t).total, c->history); + wsap_vtcore_scrollback(t).total, c->history); bad = 1; } if (c->reply && (got.len != strlen(c->reply) || memcmp(got.s, c->reply, got.len))) { fprintf(stderr, "%s (%s): reply differs\n", c->name, mode); bad = 1; } - term_free(t); + wsap_vtcore_free(t); return bad; } int main(void) { - struct term_snapshot *s = term_snapshot_new(); + struct wsap_vtcore_snapshot *s = wsap_vtcore_snapshot_new(); if (!s) return 1; int failed = 0; for (size_t i = 0; i < sizeof(cases) / sizeof(cases[0]); i++) failed += run(&cases[i], s, false) | run(&cases[i], s, true); /* ONLCR is a feed option. A plain line feed keeps the column. */ - struct term_options opt = { .size = { .x = 8, .y = 2 } }; - struct term *t = term_new(&opt); + struct wsap_vtcore_options opt = { .size = { .x = 8, .y = 2 } }; + struct wsap_vtcore *t = wsap_vtcore_new(&opt); if (!t) return 1; - term_feed(t, "ab\nZ", 4, TERM_FEED_ONLCR); - if (term_cursor(t).pos.x != 1 || term_cursor(t).pos.y != 1) { + wsap_vtcore_feed(t, "ab\nZ", 4, WSAP_VTCORE_FEED_ONLCR); + if (wsap_vtcore_cursor(t).pos.x != 1 || wsap_vtcore_cursor(t).pos.y != 1) { fprintf(stderr, "ONLCR: line feed did not return to column zero\n"); failed++; } - term_free(t); + wsap_vtcore_free(t); /* A long stream can skip old rows. A bare CR must keep the last rows. */ - opt.size = (struct term_vector2i){ .x = 8, .y = 3 }; + opt.size = (struct wsap_vtcore_vector2i){ .x = 8, .y = 3 }; opt.scrollback = 5; - t = term_new(&opt); + t = wsap_vtcore_new(&opt); if (!t) return 1; char *stream = malloc(13000u * 9u + 8u); if (!stream) return 1; for (int i = 0; i < 13000; i++) memcpy(stream + (size_t)i * 9, "1234567\r\n", 9); memcpy(stream + 13000u * 9u, "broken\rY", 8); - term_feed(t, stream, 13000u * 9u + 8u, 0); + wsap_vtcore_feed(t, stream, 13000u * 9u + 8u, 0); free(stream); - if (term_scrollback(t).total != 5) { + if (wsap_vtcore_scrollback(t).total != 5) { fprintf(stderr, "long stream: history count differs\n"); failed++; } for (int offset = 5;; offset = offset > 3 ? offset - 3 : 0) { - term_scroll_to(t, offset); - if (!term_snapshot_update(s, t)) return 1; + wsap_vtcore_scroll_to(t, offset); + if (!wsap_vtcore_snapshot_update(s, t)) return 1; for (int y = 0; y < 3; y++) { const char *want = offset == 0 && y == 2 ? "Yroken" : "1234567"; - const struct term_cell *row = term_snapshot_row(s, y); + const struct wsap_vtcore_cell *row = wsap_vtcore_snapshot_row(s, y); for (int x = 0; x < 8; x++) { uint32_t cp = x < (int)strlen(want) ? (unsigned char)want[x] : ' '; if (row[x].text != cp) { @@ -388,8 +388,8 @@ int main(void) } if (!offset) break; } - term_free(t); - term_snapshot_free(s); + wsap_vtcore_free(t); + wsap_vtcore_snapshot_free(s); if (failed) fprintf(stderr, "%d spec failures\n", failed); return failed != 0; } diff --git a/tests/symbols_test.sh b/tests/symbols_test.sh index 0343eb0..d787b72 100644 --- a/tests/symbols_test.sh +++ b/tests/symbols_test.sh @@ -1,12 +1,12 @@ #!/usr/bin/env bash -# Every global symbol of the term library starts with term_. A host links +# Every global symbol of the library starts with wsap_vtcore_. A host links # the library next to its own code, so a bare name such as palette_init can -# collide with a host symbol. Every function that term.h declares is also +# collide with a host symbol. Every function that wsap_vtcore.h declares is also # defined, so the library cannot leave one out. A shared build exports -# exactly the functions of term.h. +# exactly the functions of wsap_vtcore.h. set -euo pipefail lib=$1 -src=${2:-$(dirname "$0")/../include/term} +src=${2:-$(dirname "$0")/../include/wsap_vtcore} nm=${NM:-nm} defined_args=(-g --defined-only -P) @@ -21,14 +21,14 @@ defined=$(awk 'NF >= 2 && $2 ~ /^[A-Z]$/ && $2 != "U" { print $1 }' <<<"$syms" | grep -v '^_*odr_asan\.' | sed 's/^_//' | sort -u) status=0 -bad=$(grep -v '^term_' <<<"$defined" || true) +bad=$(grep -v '^wsap_vtcore_' <<<"$defined" || true) if [[ -n $bad ]]; then - echo "$lib: global symbols without the term_ prefix:" >&2 + echo "$lib: global symbols without the wsap_vtcore_ prefix:" >&2 echo "$bad" >&2 status=1 fi -declared=$("${CC:-cc}" -std=c11 -E -P -I"$src" "$src/term.h" | python3 -c ' +declared=$("${CC:-cc}" -std=c11 -E -P -I"$src" "$src/wsap_vtcore.h" | python3 -c ' import re, sys text = re.sub(r"\s+", " ", sys.stdin.read()) depth, flat = 0, [] @@ -42,18 +42,18 @@ for ch in text: for stmt in "".join(flat).split(";"): if "static" in stmt or "typedef" in stmt: continue - m = re.search(r"\b(term_\w+)\s*\(", stmt) + m = re.search(r"\b(wsap_vtcore_\w+)\s*\(", stmt) if m: print(m.group(1)) ' | sort -u) missing=$(comm -23 <(echo "$declared") <(echo "$defined")) if [[ -n $missing ]]; then - echo "$lib: functions declared in term.h but not defined:" >&2 + echo "$lib: functions declared in wsap_vtcore.h but not defined:" >&2 echo "$missing" >&2 status=1 fi -# The shared library exports term.h and nothing else. +# The shared library exports wsap_vtcore.h and nothing else. shared=${3:-} if [[ -n $shared ]]; then exported=$("$nm" "${exported_args[@]}" "$shared" | awk '$2 ~ /^[TDBRVW]$/ { print $1 }' | @@ -61,8 +61,8 @@ if [[ -n $shared ]]; then extra=$(comm -13 <(echo "$declared") <(echo "$exported")) absent=$(comm -23 <(echo "$declared") <(echo "$exported")) if [[ -n $extra || -n $absent ]]; then - echo "$shared: exports differ from term.h" >&2 - [[ -n $extra ]] && echo "not in term.h: $extra" >&2 + echo "$shared: exports differ from wsap_vtcore.h" >&2 + [[ -n $extra ]] && echo "not in wsap_vtcore.h: $extra" >&2 [[ -n $absent ]] && echo "not exported: $absent" >&2 status=1 fi diff --git a/tests/term_test.c b/tests/term_test.c index 235e9df..0e7d986 100644 --- a/tests/term_test.c +++ b/tests/term_test.c @@ -1,6 +1,6 @@ #include "term_api.h" -#include "term/unicode/unicode.h" -#include "term/unicode/utf8.h" +#include "wsap_vtcore/unicode/unicode.h" +#include "wsap_vtcore/unicode/utf8.h" #include <assert.h> #include <limits.h> #include <pthread.h> @@ -27,21 +27,21 @@ static void capture_title(void *ud, const char *s) (void)ud; snprintf(title, sizeof(title), "%s", s); } -static const struct term_callbacks reply_cb = { .reply = respond }; -static const struct term_callbacks title_cb = { .reply = respond, .title = capture_title }; +static const struct wsap_vtcore_callbacks reply_cb = { .reply = respond }; +static const struct wsap_vtcore_callbacks title_cb = { .reply = respond, .title = capture_title }; -static void write_seq(struct term *t, const char *s) +static void write_seq(struct wsap_vtcore *t, const char *s) { for (; *s; s++) tt_write(t, s, 1); } -static void feed_seq(struct term *t, const char *s, unsigned flags) +static void feed_seq(struct wsap_vtcore *t, const char *s, unsigned flags) { - for (; *s; s++) term_feed(t, s, 1, flags); + for (; *s; s++) wsap_vtcore_feed(t, s, 1, flags); } -static const char *row_text(struct term *t, int r, char *buf) +static const char *row_text(struct wsap_vtcore *t, int r, char *buf) { - const struct term_cell *cells = term_snapshot_row(tt_snapshot_for(t), r); + const struct wsap_vtcore_cell *cells = wsap_vtcore_snapshot_row(tt_snapshot_for(t), r); int n = 0; for (int c = 0; c < tt_cols(t); c++) { uint32_t cp = tt_cell_cp(t, &cells[c]); @@ -52,7 +52,7 @@ static const char *row_text(struct term *t, int r, char *buf) buf[n] = 0; return buf; } -static bool row_eq(struct term *t, int r, const char *want) +static bool row_eq(struct wsap_vtcore *t, int r, const char *want) { char *got = malloc((size_t)tt_cols(t) + 1); assert(got); @@ -60,7 +60,7 @@ static bool row_eq(struct term *t, int r, const char *want) free(got); return equal; } -static bool row_is(struct term *t, int r, const char *want) +static bool row_is(struct wsap_vtcore *t, int r, const char *want) { char *got = malloc((size_t)tt_cols(t) + 1); assert(got); @@ -71,7 +71,7 @@ static bool row_is(struct term *t, int r, const char *want) return equal; } -static void write_both(struct term *whole, struct term *bytes, const char *s) +static void write_both(struct wsap_vtcore *whole, struct wsap_vtcore *bytes, const char *s) { tt_write(whole, s, strlen(s)); write_seq(bytes, s); @@ -79,10 +79,10 @@ static void write_both(struct term *whole, struct term *bytes, const char *s) /* The view version of s after it copies t. A renderer redraws when the * version changes. */ -static uint64_t view_version(struct term_snapshot *s, struct term *t) +static uint64_t view_version(struct wsap_vtcore_snapshot *s, struct wsap_vtcore *t) { - term_snapshot_update(s, t); - return term_snapshot_view(s)->version; + wsap_vtcore_snapshot_update(s, t); + return wsap_vtcore_snapshot_view(s)->version; } /* @@ -102,12 +102,12 @@ static void test_skipped_cells_read_blank(void) /* row_text() reads U+2026 as '?'. */ static const char *const want[] = { "ab cd ef", "a?b c", "ab cd" }; for (size_t k = 0; k < sizeof(lines) / sizeof(lines[0]); k++) { - struct term *whole = tt_new(20, 4); - struct term *bytes = tt_new(20, 4); + struct wsap_vtcore *whole = tt_new(20, 4); + struct wsap_vtcore *bytes = tt_new(20, 4); for (int i = 0; i < 12; i++) write_both(whole, bytes, "XXXXXXXXXXXXXXXXXXXX\r\n"); write_both(whole, bytes, lines[k]); - for (struct term *t = whole; t; t = t == whole ? bytes : NULL) { + for (struct wsap_vtcore *t = whole; t; t = t == whole ? bytes : NULL) { char *got = malloc((size_t)tt_cols(t) + 1); assert(got); row_text(t, 3, got); @@ -118,39 +118,39 @@ static void test_skipped_cells_read_blank(void) } free(got); } - term_free(whole); - term_free(bytes); + wsap_vtcore_free(whole); + wsap_vtcore_free(bytes); } - struct term *whole = tt_new(20, 4); - struct term *bytes = tt_new(20, 4); + struct wsap_vtcore *whole = tt_new(20, 4); + struct wsap_vtcore *bytes = tt_new(20, 4); write_both(whole, bytes, "abcdefgh\r\033[2C\033[K\033[2CZ"); assert(row_is(whole, 0, "ab Z")); assert(row_is(bytes, 0, "ab Z")); - term_free(whole); - term_free(bytes); + wsap_vtcore_free(whole); + wsap_vtcore_free(bytes); } /* Compare the first rows of both viewports cell by cell. Each terminal gets * its own snapshot. A cluster has a different handle in each snapshot, so * the test compares its code points. */ -static void assert_same_rows(struct term *a, struct term *b, int rows) +static void assert_same_rows(struct wsap_vtcore *a, struct wsap_vtcore *b, int rows) { - struct term_snapshot *sa = term_snapshot_new(); - struct term_snapshot *sb = term_snapshot_new(); - bool copied = sa && sb && term_snapshot_update(sa, a) && term_snapshot_update(sb, b); + struct wsap_vtcore_snapshot *sa = wsap_vtcore_snapshot_new(); + struct wsap_vtcore_snapshot *sb = wsap_vtcore_snapshot_new(); + bool copied = sa && sb && wsap_vtcore_snapshot_update(sa, a) && wsap_vtcore_snapshot_update(sb, b); assert(copied); - int cols = term_snapshot_view(sa)->size.x; - assert(cols == term_snapshot_view(sb)->size.x); + int cols = wsap_vtcore_snapshot_view(sa)->size.x; + assert(cols == wsap_vtcore_snapshot_view(sb)->size.x); for (int y = 0; y < rows; y++) { - const struct term_cell *ra = term_snapshot_row(sa, y); - const struct term_cell *rb = term_snapshot_row(sb, y); + const struct wsap_vtcore_cell *ra = wsap_vtcore_snapshot_row(sa, y); + const struct wsap_vtcore_cell *rb = wsap_vtcore_snapshot_row(sb, y); assert(ra && rb); for (int x = 0; x < cols; x++) { - const struct term_cell *ac = &ra[x], *bc = &rb[x]; + const struct wsap_vtcore_cell *ac = &ra[x], *bc = &rb[x]; uint32_t acp[32], bcp[32]; - int an = term_snapshot_cluster(sa, ac->text, acp, 32); - int bn = term_snapshot_cluster(sb, bc->text, bcp, 32); + int an = wsap_vtcore_snapshot_cluster(sa, ac->text, acp, 32); + int bn = wsap_vtcore_snapshot_cluster(sb, bc->text, bcp, 32); bool same = an == bn && an <= 32 && !memcmp(acp, bcp, (size_t)an * sizeof(*acp)) && ac->fg == bc->fg && ac->bg == bc->bg && @@ -164,16 +164,16 @@ static void assert_same_rows(struct term *a, struct term *b, int rows) } } } - term_snapshot_free(sa); - term_snapshot_free(sb); + wsap_vtcore_snapshot_free(sa); + wsap_vtcore_snapshot_free(sb); } -static void assert_same_screen(struct term *a, struct term *b) +static void assert_same_screen(struct wsap_vtcore *a, struct wsap_vtcore *b) { assert(tt_cursor_x(a) == tt_cursor_x(b)); assert(tt_cursor_y(a) == tt_cursor_y(b)); assert(tt_history(a) == tt_history(b)); - assert(term_modes(a).synchronized == term_modes(b).synchronized); + assert(wsap_vtcore_modes(a).synchronized == wsap_vtcore_modes(b).synchronized); assert(tt_rows(a) == tt_rows(b)); assert_same_rows(a, b, tt_rows(a)); } @@ -187,24 +187,24 @@ static void test_read_boundaries(void) "\033[?1049halt\033[?1049lZ" "\033]11;?\007\033Pignored\033\\" "\xf0\x9f\x98\x80\xc3XQ©️界\033[2G\033[P"; - struct term *expected = tt_new(16, 4); + struct wsap_vtcore *expected = tt_new(16, 4); tt_write(expected, input, sizeof(input) - 1); for (size_t split = 0; split < sizeof(input); split++) { - struct term *actual = tt_new(16, 4); + struct wsap_vtcore *actual = tt_new(16, 4); tt_write(actual, input, split); tt_write(actual, input + split, sizeof(input) - 1 - split); assert_same_screen(actual, expected); - term_free(actual); + wsap_vtcore_free(actual); } /* The byte that ends an unfinished sequence is not lost. */ - struct term *t = tt_new(16, 4); + struct wsap_vtcore *t = tt_new(16, 4); write_seq(t, "\xc3XQ"); assert(tt_cell_cp(t, tt_cell(t, 0, 0)) == 0xFFFD); assert(tt_cell_cp(t, tt_cell(t, 1, 0)) == 'X'); assert(tt_cell_cp(t, tt_cell(t, 2, 0)) == 'Q'); - term_free(t); - term_free(expected); + wsap_vtcore_free(t); + wsap_vtcore_free(expected); } static void test_ascii_controls(void) @@ -218,8 +218,8 @@ static void test_ascii_controls(void) memcpy(input + 29, separators[c], n); memset(input + 29 + n, 'b', 173); input[202 + n] = '\0'; - struct term *bulk = tt_new(120, 6); - struct term *bytes = tt_new(120, 6); + struct wsap_vtcore *bulk = tt_new(120, 6); + struct wsap_vtcore *bytes = tt_new(120, 6); const char *setup = bottom ? "\033[6;1H\033[1;3;4;38;2;12;34;56m" : "\033[1;3;4;38;2;12;34;56m"; write_seq(bulk, setup); @@ -227,18 +227,18 @@ static void test_ascii_controls(void) tt_write(bulk, input, strlen(input)); write_seq(bytes, input); assert_same_screen(bulk, bytes); - term_scroll(bulk, 6); - term_scroll(bytes, 6); + wsap_vtcore_scroll(bulk, 6); + wsap_vtcore_scroll(bytes, 6); assert_same_screen(bulk, bytes); - term_free(bulk); - term_free(bytes); + wsap_vtcore_free(bulk); + wsap_vtcore_free(bytes); } } } static void test_esc_control_strings_and_designators(void) { - struct term *t = tt_new(32, 2); + struct wsap_vtcore *t = tt_new(32, 2); assert(t); write_seq(t, "A\033_payload ignored\033\\B"); @@ -253,13 +253,13 @@ static void test_esc_control_strings_and_designators(void) write_seq(t, "\033.Am\033*0n"); assert(row_is(t, 0, "ABCDxyz%qxmn")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(8, 2); write_seq(t, "A\033_ignored\033DB"); assert(row_is(t, 0, "A")); assert(row_is(t, 1, " B")); - term_free(t); + wsap_vtcore_free(t); } static void test_random_read_boundaries(void) @@ -277,11 +277,11 @@ static void test_random_read_boundaries(void) input[i] = (char)(random >> 16); } memcpy(input + 400, embedded, sizeof(embedded) - 1); - struct term *whole = tt_new(32, 8); + struct wsap_vtcore *whole = tt_new(32, 8); tt_write(whole, input, sizeof(input)); for (size_t c = 0; c < sizeof(chunks) / sizeof(chunks[0]); c++) { - struct term *a = tt_new(32, 8); - struct term *b = tt_new(32, 8); + struct wsap_vtcore *a = tt_new(32, 8); + struct wsap_vtcore *b = tt_new(32, 8); for (size_t block = 0; block < sizeof(input); block += 128) { tt_write(a, input + block, 128); for (size_t i = block; i < block + 128;) { @@ -298,14 +298,14 @@ static void test_random_read_boundaries(void) assert_same_screen(a, b); int history = tt_history(a); for (int i = 0; i < history; i += 8) { - term_scroll(a, 8); - term_scroll(b, 8); + wsap_vtcore_scroll(a, 8); + wsap_vtcore_scroll(b, 8); assert_same_screen(a, b); } - term_free(a); - term_free(b); + wsap_vtcore_free(a); + wsap_vtcore_free(b); } - term_free(whole); + wsap_vtcore_free(whole); } } @@ -330,13 +330,13 @@ static void test_csi_recovery(void) for (size_t c = 0; c < sizeof(cases) / sizeof(cases[0]); c++) { size_t len = strlen(cases[c].input); for (size_t split = 0; split <= len; split++) { - struct term *t = tt_new(20, 4); + struct wsap_vtcore *t = tt_new(20, 4); tt_write(t, cases[c].input, split); tt_write(t, cases[c].input + split, len - split); assert(row_is(t, 0, cases[c].first)); assert(row_is(t, 1, cases[c].second)); - for (int x = 0; x < 20; x++) assert(tt_cell(t, x, 0)->fg == TERM_COLOR_FG); - term_free(t); + for (int x = 0; x < 20; x++) assert(tt_cell(t, x, 0)->fg == WSAP_VTCORE_COLOR_FG); + wsap_vtcore_free(t); } } } @@ -353,31 +353,31 @@ static void test_csi_byte_boundaries(void) static const char suffix[] = "mX\033[6n\033[?25l\033[?25h\033[0mY"; memcpy(input + n, suffix, sizeof(suffix) - 1); n += sizeof(suffix) - 1; - struct term *whole = tt_new_opts(20, 4, &reply_cb); + struct wsap_vtcore *whole = tt_new_opts(20, 4, &reply_cb); response_len = 0; tt_write(whole, input, n); char expected_response[64]; size_t expected_len = response_len; memcpy(expected_response, response, expected_len); for (size_t split = 0; split <= strlen(prefixes[p]) + 2; split++) { - struct term *parts = tt_new_opts(20, 4, &reply_cb); + struct wsap_vtcore *parts = tt_new_opts(20, 4, &reply_cb); response_len = 0; tt_write(parts, input, split); tt_write(parts, input + split, n - split); assert_same_screen(whole, parts); - assert(term_cursor(whole).visible == term_cursor(parts).visible); + assert(wsap_vtcore_cursor(whole).visible == wsap_vtcore_cursor(parts).visible); assert(response_len == expected_len); assert(!memcmp(response, expected_response, expected_len)); - term_free(parts); + wsap_vtcore_free(parts); } - term_free(whole); + wsap_vtcore_free(whole); } } } static void test_parameter_limits(void) { - struct term *t = tt_new(10, 4); + struct wsap_vtcore *t = tt_new(10, 4); write_seq(t, "\033[2;4r\033[?6h\033[999999999999999999999;1H"); assert(tt_cursor_y(t) == 3 && tt_cursor_x(t) == 0); write_seq(t, "\033[?6l\033[r"); @@ -387,26 +387,26 @@ static void test_parameter_limits(void) write_seq(t, "\033[999999999999999999999A\033[999999999999999999999D"); assert(tt_cursor_y(t) == 0 && tt_cursor_x(t) == 0); write_seq(t, "\033[38;5;999999999999999999999mX"); - assert(tt_cell(t, 0, 0)->fg == TERM_COLOR_FG); + assert(tt_cell(t, 0, 0)->fg == WSAP_VTCORE_COLOR_FG); /* A renderer sees the cursor move to another row. */ - struct term_snapshot *snap = term_snapshot_new(); + struct wsap_vtcore_snapshot *snap = wsap_vtcore_snapshot_new(); uint64_t version = view_version(snap, t); write_seq(t, "\033[3d"); assert(tt_cursor_y(t) == 2 && view_version(snap, t) != version); - term_snapshot_free(snap); + wsap_vtcore_snapshot_free(snap); write_seq(t, "\033[4;8H\0337"); tt_resize(t, 5, 2); write_seq(t, "\0338Z"); assert(tt_cursor_y(t) == 1 && tt_cursor_x(t) == 3); assert(tt_cell(t, 2, 1)->text == 'Z'); - term_free(t); + wsap_vtcore_free(t); } static void test_unterminated_control_strings_do_not_swallow_text(void) { - struct term *t = tt_new(20, 4); + struct wsap_vtcore *t = tt_new(20, 4); assert(t); write_seq(t, "A\033]0;random bytes\tgit\r\nstatus"); @@ -417,7 +417,7 @@ static void test_unterminated_control_strings_do_not_swallow_text(void) assert(row_is(t, 1, "status branch")); assert(row_is(t, 2, "next")); - term_free(t); + wsap_vtcore_free(t); char overlong[1200]; for (int intro = 0; intro < 2; intro++) { @@ -425,35 +425,35 @@ static void test_unterminated_control_strings_do_not_swallow_text(void) memset(overlong + n, 'T', 1024); overlong[n + 1024] = '\0'; - struct term *u = tt_new(20, 4); + struct wsap_vtcore *u = tt_new(20, 4); write_seq(u, overlong); write_seq(u, "\r\n[sudo] password:"); assert(row_is(u, 0, "")); assert(row_is(u, 1, "[sudo] password:")); - term_free(u); + wsap_vtcore_free(u); - struct term *d = tt_new(20, 4); + struct wsap_vtcore *d = tt_new(20, 4); write_seq(d, overlong); write_seq(d, "\033\\after"); assert(row_is(d, 0, "after")); - term_free(d); + wsap_vtcore_free(d); } } static void test_c0_controls_after_esc_are_executed(void) { - struct term *t = tt_new(20, 4); + struct wsap_vtcore *t = tt_new(20, 4); assert(t); write_seq(t, "A\033\tB"); assert(row_is(t, 0, "A B")); - term_free(t); + wsap_vtcore_free(t); } static void test_resize_reflow(void) { - struct term *t = tt_new(8, 4); + struct wsap_vtcore *t = tt_new(8, 4); write_seq(t, "abcdefghijkl"); tt_resize(t, 16, 4); assert(row_is(t, 0, "abcdefghijkl") && row_is(t, 1, "")); @@ -469,16 +469,16 @@ static void test_resize_reflow(void) free(text); tt_resize(t, 20, 4); assert(row_is(t, 0, "abcdefghijklM")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(6, 6); write_seq(t, "\033[31mab cdef\033[m\r\nnext"); - term_color red = tt_cell(t, 0, 0)->fg; + wsap_vtcore_color red = tt_cell(t, 0, 0)->fg; tt_resize(t, 12, 6); assert(row_is(t, 0, "ab cdef") && row_is(t, 1, "next")); assert(tt_cell(t, 7, 0)->fg == red); - assert(tt_cell(t, 0, 1)->fg == TERM_COLOR_FG); - term_free(t); + assert(tt_cell(t, 0, 1)->fg == WSAP_VTCORE_COLOR_FG); + wsap_vtcore_free(t); t = tt_new(4, 2); write_seq(t, "abcdefghijkl"); @@ -493,7 +493,7 @@ static void test_resize_reflow(void) assert(row_is(t, 0, "ijkl") && row_is(t, 1, "M")); tt_resize(t, 20, 2); assert(row_is(t, 0, "abcdefghijklM")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(4, 3); write_seq(t, "abcd"); @@ -503,7 +503,7 @@ static void test_resize_reflow(void) tt_resize(t, 5, 3); write_seq(t, "F"); assert(row_is(t, 0, "abcdE") && row_is(t, 1, "F")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(4, 4); write_seq(t, "abcdefghijkl\033[?1049h12345678"); @@ -513,14 +513,14 @@ static void test_resize_reflow(void) write_seq(t, "\033[?1049lM"); assert(row_is(t, 0, "abcdefghijklM")); assert(tt_cursor_y(t) == 0 && tt_cursor_x(t) == 13); - term_free(t); + wsap_vtcore_free(t); t = tt_new(4, 2); write_seq(t, "abcd"); tt_resize(t, 4, 3); write_seq(t, "E"); assert(row_is(t, 0, "abcd") && row_is(t, 1, "E")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(80, 4); for (int i = 0; i < 1000; i++) write_seq(t, "abcdefgh"); @@ -532,22 +532,22 @@ static void test_resize_reflow(void) assert(tt_cursor_x(t) < 80 && tt_cursor_y(t) < 4); write_seq(t, "Z"); assert(tt_cell(t, 0, 3)->text == 'Z'); - term_free(t); + wsap_vtcore_free(t); } static void test_resize_exposes_blank_rows(void) { - struct term *t = tt_new(20, 2); + struct wsap_vtcore *t = tt_new(20, 2); write_seq(t, "kept"); for (int pass = 0; pass < 2; pass++) { tt_resize(t, 20, 6); assert(row_is(t, 0, "kept")); for (int y = 2; y < 6; y++) { for (int x = 0; x < 20; x++) { - const struct term_cell *cell = tt_cell(t, x, y); - assert(cell->text == ' ' && cell->fg == TERM_COLOR_FG); - assert(cell->bg == TERM_COLOR_BG && cell->attrs == 0 && cell->width == 1); + const struct wsap_vtcore_cell *cell = tt_cell(t, x, y); + assert(cell->text == ' ' && cell->fg == WSAP_VTCORE_COLOR_FG); + assert(cell->bg == WSAP_VTCORE_COLOR_BG && cell->attrs == 0 && cell->width == 1); } } write_seq(t, "\033[6;1H\tfile/"); @@ -555,12 +555,12 @@ static void test_resize_exposes_blank_rows(void) write_seq(t, "\033[1;1H"); tt_resize(t, 20, 2); } - term_free(t); + wsap_vtcore_free(t); } static void test_prompt_resize(void) { - struct term *t = tt_new(80, 6); + struct wsap_vtcore *t = tt_new(80, 6); const char *prompt = "~/Documents/GitHub/clernen_pi main> "; write_seq(t, "\033]133;A;click_events=1\033\\"); write_seq(t, prompt); @@ -596,7 +596,7 @@ static void test_prompt_resize(void) tt_resize(t, 20, 6); assert(row_is(t, 0, "~/Documents/GitHub/c")); assert(row_is(t, 1, "lernen_pi main>")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(20, 6); write_seq(t, "abcdefghijklmnop\r\n\033]133;A\007prompt> input\033]133;B\007"); @@ -605,12 +605,12 @@ static void test_prompt_resize(void) assert(row_is(t, 2, "prompt>")); tt_resize(t, 30, 6); assert(row_is(t, 0, "abcdefghijklmnop") && row_is(t, 1, "prompt>")); - term_free(t); + wsap_vtcore_free(t); } static void test_cursor_line_motion(void) { - struct term *t = tt_new(80, 9); + struct wsap_vtcore *t = tt_new(80, 9); assert(t); const char *lines = "one\r\ntwo\r\nthree\r\nfour\r\nfive\r\nsix\r\nseven\r\n"; tt_write(t, lines, strlen(lines)); @@ -619,12 +619,12 @@ static void test_cursor_line_motion(void) assert(row_is(t, 1, "two revised")); assert(row_is(t, 3, "four revised")); assert(row_is(t, 0, "one revised")); - term_free(t); + wsap_vtcore_free(t); } static void test_relative_cursor_motion(void) { - struct term *t = tt_new(10, 5); + struct wsap_vtcore *t = tt_new(10, 5); assert(t); const char *text = "0123456789\r\nabcdefghij\r\nklmnopqrst"; tt_write(t, text, strlen(text)); @@ -634,7 +634,7 @@ static void test_relative_cursor_motion(void) assert(tt_cell(t, 5, 2)->text == 'Y'); assert(tt_cell(t, 6, 3)->text == 'Z'); assert(tt_cell(t, 7, 1)->text == 'W'); - term_free(t); + wsap_vtcore_free(t); } static void test_top_region_scrollback(void) @@ -651,7 +651,7 @@ static void test_top_region_scrollback(void) {"\033[99S", 4}, }; for (size_t i = 0; i < sizeof(cases) / sizeof(cases[0]); i++) { - struct term *t = tt_new(12, 6); + struct wsap_vtcore *t = tt_new(12, 6); write_seq(t, "one\r\ntwo\r\nthree\r\nfour\r\nPROMPT\r\nSTATUS"); write_seq(t, "\033[1;4r\033[4;1H"); write_seq(t, cases[i].scroll); @@ -660,15 +660,15 @@ static void test_top_region_scrollback(void) cases[i].lines == 2 ? "three" : "")); assert(row_is(t, 3, "")); assert(row_is(t, 4, "PROMPT") && row_is(t, 5, "STATUS")); - term_scroll(t, cases[i].lines); + wsap_vtcore_scroll(t, cases[i].lines); assert(tt_view_offset(t) == cases[i].lines); assert(row_is(t, 0, "one") && row_is(t, 1, "two")); - term_free(t); + wsap_vtcore_free(t); } /* Retain the same history as a full screen after the ring wraps. */ - struct term *t = tt_new(12, 6); - struct term *reference = tt_new(12, 4); + struct wsap_vtcore *t = tt_new(12, 6); + struct wsap_vtcore *reference = tt_new(12, 4); const char *footer = "\033[5;1H\033[31mPROMPT\r\nSTATUS\033[m\033[1;4r"; tt_write(t, footer, strlen(footer)); for (int i = 0; i < 2 * TEST_SCROLLBACK; i++) { @@ -682,19 +682,19 @@ static void test_top_region_scrollback(void) assert(tt_cursor_y(t) == tt_cursor_y(reference)); assert(row_is(t, 4, "PROMPT") && row_is(t, 5, "STATUS")); assert(tt_cell(t, 0, 4)->fg == tt_cell(t, 0, 5)->fg); - assert(tt_cell(t, 0, 4)->fg != TERM_COLOR_FG); + assert(tt_cell(t, 0, 4)->fg != WSAP_VTCORE_COLOR_FG); for (int i = 0; i <= tt_history(reference); i++) { assert_same_rows(t, reference, tt_rows(reference)); - term_scroll(t, 1); - term_scroll(reference, 1); + wsap_vtcore_scroll(t, 1); + wsap_vtcore_scroll(reference, 1); } - term_free(t); - term_free(reference); + wsap_vtcore_free(t); + wsap_vtcore_free(reference); } static void test_editor_scrolling(void) { - struct term *t = tt_new(80, 24); + struct wsap_vtcore *t = tt_new(80, 24); write_seq(t, "\033[?1049hTITLE"); for (int i = 1; i <= 20; i++) { char line[64]; @@ -711,7 +711,7 @@ static void test_editor_scrolling(void) assert(row_is(t, 22, "HELP") && row_is(t, 23, "FOOTER")); assert(tt_cursor_x(t) == 0 && tt_cursor_y(t) == 3); assert(tt_history(t) == 0); - term_free(t); + wsap_vtcore_free(t); t = tt_new(12, 6); write_seq(t, "old\r\nHEAD\r\nA\r\nB\r\nC\r\nD\r\nFOOT"); @@ -736,7 +736,7 @@ static void test_editor_scrolling(void) for (int r = 1; r <= 4; r++) { assert(row_is(t, r, "")); assert(tt_cell(t, 0, r)->bg == tt_cell(t, 11, r)->bg); - assert(tt_cell(t, 0, r)->bg != TERM_COLOR_BG); + assert(tt_cell(t, 0, r)->bg != WSAP_VTCORE_COLOR_BG); } assert(tt_history(t) == 1); @@ -746,117 +746,117 @@ static void test_editor_scrolling(void) tt_resize(t, 12, 4); write_seq(t, "\033[4;1H\033[2Kend\n"); assert(tt_cursor_y(t) == 3 && row_is(t, 2, "end")); - term_free(t); + wsap_vtcore_free(t); } static bool pending_decsca_decsed_decsel(void) { - struct term *d = tt_new(20, 3); + struct wsap_vtcore *d = tt_new(20, 3); write_seq(d, "\033[H" "AB" "\033[1\"q" "CD" "\033[0\"q" "EF"); write_seq(d, "\033[?2J"); bool ok = row_eq(d, 0, " CD"); - term_free(d); + wsap_vtcore_free(d); - struct term *l = tt_new(20, 3); + struct wsap_vtcore *l = tt_new(20, 3); write_seq(l, "\033[H" "GH" "\033[1\"q" "IJ" "\033[0\"q" "KL"); write_seq(l, "\033[H\033[?0K"); ok = ok && row_eq(l, 0, " IJ"); - term_free(l); + wsap_vtcore_free(l); return ok; } static bool pending_decfra_decera(void) { - struct term *f = tt_new(20, 3); + struct wsap_vtcore *f = tt_new(20, 3); write_seq(f, "\033[88;1;2;2;4$x"); bool ok = row_eq(f, 0, " XXX") && row_eq(f, 1, " XXX"); - term_free(f); + wsap_vtcore_free(f); - struct term *e = tt_new(20, 3); + struct wsap_vtcore *e = tt_new(20, 3); write_seq(e, "\033[Habcde\r\nfghij"); write_seq(e, "\033[1;2;2;3$z"); ok = ok && row_eq(e, 0, "a de") && row_eq(e, 1, "f ij"); - term_free(e); + wsap_vtcore_free(e); return ok; } static bool pending_deccra(void) { - struct term *t = tt_new(20, 3); + struct wsap_vtcore *t = tt_new(20, 3); write_seq(t, "\033[HAB\r\nCD"); write_seq(t, "\033[1;1;2;2;1;1;5;1$v"); bool ok = row_eq(t, 0, "AB AB") && row_eq(t, 1, "CD CD"); - term_free(t); + wsap_vtcore_free(t); return ok; } static bool pending_decrara(void) { - struct term *t = tt_new(20, 3); + struct wsap_vtcore *t = tt_new(20, 3); write_seq(t, "\033[H\033[1mAB\033[mCD"); write_seq(t, "\033[1;1;1;4;1$t"); - bool ok = !(tt_cell(t, 0, 0)->attrs & TERM_ATTR_BOLD) && - (tt_cell(t, 2, 0)->attrs & TERM_ATTR_BOLD); - term_free(t); + bool ok = !(tt_cell(t, 0, 0)->attrs & WSAP_VTCORE_ATTR_BOLD) && + (tt_cell(t, 2, 0)->attrs & WSAP_VTCORE_ATTR_BOLD); + wsap_vtcore_free(t); return ok; } static bool pending_decsera(void) { - struct term *t = tt_new(20, 3); + struct wsap_vtcore *t = tt_new(20, 3); write_seq(t, "\033[H\033[0\"qAB\033[1\"qCD"); write_seq(t, "\033[1;1;1;4${"); bool ok = row_eq(t, 0, " CD"); - term_free(t); + wsap_vtcore_free(t); return ok; } static bool pending_deccolm(void) { - struct term *t = tt_new(80, 4); + struct wsap_vtcore *t = tt_new(80, 4); write_seq(t, "\033[?40h" "keep" "\033[?3h"); bool ok = tt_cols(t) == 132 && row_eq(t, 0, "") && tt_cursor_x(t) == 0 && tt_cursor_y(t) == 0; write_seq(t, "\033[?3l"); ok = ok && tt_cols(t) == 80; - term_free(t); + wsap_vtcore_free(t); return ok; } static bool pending_decic_decdc(void) { - struct term *i = tt_new(10, 2); + struct wsap_vtcore *i = tt_new(10, 2); write_seq(i, "\033[Habcdef\033[H\033[2'}"); bool ok = row_eq(i, 0, " abcdef"); - term_free(i); + wsap_vtcore_free(i); - struct term *d = tt_new(10, 2); + struct wsap_vtcore *d = tt_new(10, 2); write_seq(d, "\033[Habcdef\033[H\033[2'~"); ok = ok && row_eq(d, 0, "cdef"); - term_free(d); + wsap_vtcore_free(d); return ok; } static bool pending_sl_sr(void) { - struct term *l = tt_new(10, 2); + struct wsap_vtcore *l = tt_new(10, 2); write_seq(l, "\033[Habcdef\033[2 @"); bool ok = row_eq(l, 0, "cdef"); - term_free(l); + wsap_vtcore_free(l); - struct term *r = tt_new(10, 2); + struct wsap_vtcore *r = tt_new(10, 2); write_seq(r, "\033[Habcdef\033[2 A"); ok = ok && row_eq(r, 0, " abcdef"); - term_free(r); + wsap_vtcore_free(r); return ok; } static bool pending_sixel(void) { - struct term *t = tt_new(20, 6); + struct wsap_vtcore *t = tt_new(20, 6); write_seq(t, "\033[H\033Pq#0;2;100;100;100#0~~~~\033\\"); bool ok = tt_cursor_y(t) > 0; - term_free(t); + wsap_vtcore_free(t); return ok; } @@ -888,7 +888,7 @@ static void test_unimplemented_da_features(void) static void test_device_attributes(void) { - struct term *t = tt_new_opts(80, 24, &reply_cb); + struct wsap_vtcore *t = tt_new_opts(80, 24, &reply_cb); write_seq(t, "\033[c"); assert(!strcmp(response, "\033[?62;22c")); @@ -903,10 +903,10 @@ static void test_device_attributes(void) write_seq(t, "\033[=c"); assert(response_len == 0); - term_free(t); + wsap_vtcore_free(t); } -static void expect_flags(struct term *t, const char *commands, const char *reply) +static void expect_flags(struct wsap_vtcore *t, const char *commands, const char *reply) { write_seq(t, commands); write_seq(t, "\033[?u"); @@ -914,12 +914,12 @@ static void expect_flags(struct term *t, const char *commands, const char *reply } static void test_keyboard_negotiation(void) { - struct term *t = tt_new_opts(80, 24, &reply_cb); - assert(!term_modes(t).app_cursor); + struct wsap_vtcore *t = tt_new_opts(80, 24, &reply_cb); + assert(!wsap_vtcore_modes(t).app_cursor); write_seq(t, "\033[?1h"); - assert(term_modes(t).app_cursor); + assert(wsap_vtcore_modes(t).app_cursor); write_seq(t, "\033[?1l"); - assert(!term_modes(t).app_cursor); + assert(!wsap_vtcore_modes(t).app_cursor); expect_flags(t, "", "\033[?0u"); expect_flags(t, "\033[=1u", "\033[?1u"); expect_flags(t, "\033[>3u\033[>31u", "\033[?31u"); @@ -943,10 +943,10 @@ static void test_keyboard_negotiation(void) expect_flags(t, "\033[<2147483647u", "\033[?0u"); write_seq(t, "hello"); assert(row_is(t, 0, "hello")); - term_free(t); + wsap_vtcore_free(t); } -static void expect_selection(struct term *t, int x1, int y1, int x2, int y2, const char *want) +static void expect_selection(struct wsap_vtcore *t, int x1, int y1, int x2, int y2, const char *want) { tt_select(t, x1, y1, x2, y2); char *text = tt_selection_text(t); @@ -958,7 +958,7 @@ static void expect_selection(struct term *t, int x1, int y1, int x2, int y2, con static void test_wide_characters(void) { - struct term *t = tt_new(8, 4); + struct wsap_vtcore *t = tt_new(8, 4); write_seq(t, "A😀界B"); assert(tt_cursor_x(t) == 6); assert(tt_cell(t, 1, 0)->text == 0x1f600 && tt_cell(t, 3, 0)->text == 0x754c); @@ -974,7 +974,7 @@ static void test_wide_characters(void) write_seq(t, "\033[4;1H😀\r \033[4;1H😀\033[4;2H\033[38;2;1;2;3mX"); assert(row_is(t, 3, " X")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(5, 8); write_seq(t, "abcd😀Z"); @@ -991,7 +991,7 @@ static void test_wide_characters(void) tt_resize(t, 12, 8); expect_selection(t, 0, 0, 11, 0, "abcd😀Z"); assert(tt_cursor_x(t) == 7); - term_free(t); + wsap_vtcore_free(t); t = tt_new(4, 3); write_seq(t, "abc©️)"); @@ -1002,16 +1002,16 @@ static void test_wide_characters(void) expect_selection(t, 0, 0, 3, 0, "😀︎x"); write_seq(t, "\033[2J\033[H\033[?7labc😀"); assert(tt_cursor_y(t) == 0 && tt_cursor_x(t) == 3); - term_free(t); + wsap_vtcore_free(t); t = tt_new(4, 2); write_seq(t, "😀😀界界AB"); - term_scroll(t, 1); + wsap_vtcore_scroll(t, 1); expect_selection(t, 0, 0, 3, 1, "😀😀界界"); - term_scroll_to(t, 0); + wsap_vtcore_scroll_to(t, 0); tt_resize(t, 10, 2); expect_selection(t, 0, 0, 9, 0, "😀😀界界AB"); - term_free(t); + wsap_vtcore_free(t); } static void test_wide_runs(void) @@ -1029,15 +1029,15 @@ static void test_wide_runs(void) for (size_t k = 0; k < sizeof(runs) / sizeof(*runs); k++) { char text[512]; snprintf(text, sizeof(text), "\033[999;1H%s", runs[k]); - struct term *bulk = tt_new(120, 6); - struct term *split = tt_new(120, 6); + struct wsap_vtcore *bulk = tt_new(120, 6); + struct wsap_vtcore *split = tt_new(120, 6); tt_write(bulk, text, strlen(text)); write_seq(split, text); assert_same_screen(bulk, split); expect_selection(bulk, 0, 5, 119, 5, runs[k]); - term_free(bulk); - term_free(split); + wsap_vtcore_free(bulk); + wsap_vtcore_free(split); } } @@ -1055,8 +1055,8 @@ static void test_invalid_utf8_runs(void) } memcpy(input + n, "END", 3); n += 3; - struct term *bulk = tt_new(120, 4); - struct term *split = tt_new(120, 4); + struct wsap_vtcore *bulk = tt_new(120, 4); + struct wsap_vtcore *split = tt_new(120, 4); write_seq(bulk, "\033[4;1H\n"); write_seq(split, "\033[4;1H\n"); tt_write(bulk, input, n); @@ -1067,15 +1067,15 @@ static void test_invalid_utf8_runs(void) for (int c = 0; c < 3; c++) assert(tt_cell_cp(bulk, tt_cell(bulk, 96 + c, 3)) == (uint32_t)"END"[c]); assert_same_screen(bulk, split); - term_free(bulk); - term_free(split); + wsap_vtcore_free(bulk); + wsap_vtcore_free(split); } } static void test_recycled_scrollback_blanks(void) { for (int mode = 0; mode < 3; mode++) { - struct term *t = tt_new(32, 3); + struct wsap_vtcore *t = tt_new(32, 3); write_seq(t, "\033[3;1H"); const char *line = mode == 2 ? "abcdefghijklmnopqrstuvwxyz\r\033[S" : "abcdefghijklmnopqrstuvwxyz\r\n"; @@ -1085,7 +1085,7 @@ static void test_recycled_scrollback_blanks(void) } write_seq(t, "\tfile/"); assert(row_is(t, 2, " file/")); - term_free(t); + wsap_vtcore_free(t); } } @@ -1093,26 +1093,26 @@ static void test_recycled_scrollback_blanks(void) * scroll that cannot move leaves the frame alone. */ static void test_scroll_view_clamps_extreme_deltas(void) { - struct term *t = tt_new(20, 3); + struct wsap_vtcore *t = tt_new(20, 3); for (int i = 0; i < 10; i++) write_seq(t, "line\r\n"); int max = tt_history(t); assert(max > 1); - struct term_snapshot *snap = term_snapshot_new(); - term_scroll(t, 1); - term_scroll(t, INT_MAX); + struct wsap_vtcore_snapshot *snap = wsap_vtcore_snapshot_new(); + wsap_vtcore_scroll(t, 1); + wsap_vtcore_scroll(t, INT_MAX); assert(tt_view_offset(t) == max); uint64_t version = view_version(snap, t); - term_scroll(t, 1); + wsap_vtcore_scroll(t, 1); assert(view_version(snap, t) == version); - term_scroll(t, -1); - term_scroll(t, INT_MIN); + wsap_vtcore_scroll(t, -1); + wsap_vtcore_scroll(t, INT_MIN); assert(tt_view_offset(t) == 0); version = view_version(snap, t); - term_scroll(t, -1); + wsap_vtcore_scroll(t, -1); assert(view_version(snap, t) == version); - term_snapshot_free(snap); - term_free(t); + wsap_vtcore_snapshot_free(snap); + wsap_vtcore_free(t); } static void test_batched_recycled_lines(void) @@ -1125,8 +1125,8 @@ static void test_batched_recycled_lines(void) "short\r\nx\r\nyz\r\npartial\r", }; for (size_t k = 0; k < sizeof(endings) / sizeof(endings[0]); k++) { - struct term *bulk = tt_new(32, 3); - struct term *bytes = tt_new(32, 3); + struct wsap_vtcore *bulk = tt_new(32, 3); + struct wsap_vtcore *bytes = tt_new(32, 3); const char *old = "\033[31;44mabcdefghijklmnopqrst界界界\r\n"; for (int i = 0; i < TEST_SCROLLBACK + 10; i++) { tt_write(bulk, old, strlen(old)); @@ -1139,12 +1139,12 @@ static void test_batched_recycled_lines(void) assert_same_screen(bulk, bytes); for (int i = 0; i < tt_history(bulk); i += 3) { - term_scroll(bulk, 3); - term_scroll(bytes, 3); + wsap_vtcore_scroll(bulk, 3); + wsap_vtcore_scroll(bytes, 3); assert_same_screen(bulk, bytes); } - term_free(bulk); - term_free(bytes); + wsap_vtcore_free(bulk); + wsap_vtcore_free(bytes); } } @@ -1158,20 +1158,20 @@ static void test_full_width_line_endings(void) "aa\r\nbb\r\ncc\r\nd中d\r\nef", }; for (size_t k = 0; k < sizeof(feeds) / sizeof(feeds[0]); k++) { - struct term *bulk = tt_new(4, 3); - struct term *bytes = tt_new(4, 3); + struct wsap_vtcore *bulk = tt_new(4, 3); + struct wsap_vtcore *bytes = tt_new(4, 3); tt_write(bulk, feeds[k], strlen(feeds[k])); write_seq(bytes, feeds[k]); assert_same_screen(bulk, bytes); - term_free(bulk); - term_free(bytes); + wsap_vtcore_free(bulk); + wsap_vtcore_free(bytes); } - struct term *t = tt_new(4, 3); + struct wsap_vtcore *t = tt_new(4, 3); tt_write(t, feeds[0], strlen(feeds[0])); assert(tt_history(t) == 3); assert(row_is(t, 0, "dddd") && row_is(t, 1, "eeee") && row_is(t, 2, "ffff")); - term_free(t); + wsap_vtcore_free(t); } /* CRLFs at every mask boundary, followed by complete or interrupted lines. */ @@ -1189,18 +1189,18 @@ static void test_batched_line_masks(void) memcpy(input + offset, tails[k], strlen(tails[k])); memset(input + n, 'z', 128); n += 128; - struct term *bulk = tt_new(80, 3), *bytes = tt_new(80, 3); + struct wsap_vtcore *bulk = tt_new(80, 3), *bytes = tt_new(80, 3); /* A nondefault pen exercises the queued bulk path, not streaming. */ write_both(bulk, bytes, "\033[3;1H\033[31m"); tt_write(bulk, input, n); for (size_t i = 0; i < n; i++) tt_write(bytes, input + i, 1); write_both(bulk, bytes, "\033[b"); assert_same_screen(bulk, bytes); - term_scroll_to(bulk, INT_MAX); - term_scroll_to(bytes, INT_MAX); + wsap_vtcore_scroll_to(bulk, INT_MAX); + wsap_vtcore_scroll_to(bytes, INT_MAX); assert_same_screen(bulk, bytes); - term_free(bulk); - term_free(bytes); + wsap_vtcore_free(bulk); + wsap_vtcore_free(bytes); } } } @@ -1217,7 +1217,7 @@ static void test_batched_line_masks(void) */ static void test_bulk_line_flood(void) { - static const struct term_vector2i geoms[] = { + static const struct wsap_vtcore_vector2i geoms[] = { {.x = 80, .y = 24}, {.x = 27, .y = 8}, {.x = 10, .y = 5}, {.x = 120, .y = 80}, }; for (size_t g = 0; g < 2 * sizeof(geoms) / sizeof(geoms[0]); g++) { @@ -1246,28 +1246,28 @@ static void test_bulk_line_flood(void) buf[n++] = pick == 26 ? '\n' : (char)('a' + pick); } - struct term *bulk = tt_new(cols, rows); - struct term *stream = tt_new(cols, rows); - struct term *bytes = tt_new(cols, rows); - unsigned flags = g % 2 != 0 ? TERM_FEED_ONLCR : 0; + struct wsap_vtcore *bulk = tt_new(cols, rows); + struct wsap_vtcore *stream = tt_new(cols, rows); + struct wsap_vtcore *bytes = tt_new(cols, rows); + unsigned flags = g % 2 != 0 ? WSAP_VTCORE_FEED_ONLCR : 0; for (size_t i = 0; i < n; i += 65536) - term_feed(bulk, buf + i, n - i < 65536 ? n - i : 65536, flags); + wsap_vtcore_feed(bulk, buf + i, n - i < 65536 ? n - i : 65536, flags); /* One large write has enough newlines to discard old output. */ - term_feed(stream, buf, n, flags); - for (size_t i = 0; i < n; i++) term_feed(bytes, buf + i, 1, flags); + wsap_vtcore_feed(stream, buf, n, flags); + for (size_t i = 0; i < n; i++) wsap_vtcore_feed(bytes, buf + i, 1, flags); assert_same_screen(bulk, bytes); assert_same_screen(stream, bytes); for (int i = 0; i < tt_history(bulk); i += 7) { - term_scroll(bulk, 7); - term_scroll(stream, 7); - term_scroll(bytes, 7); + wsap_vtcore_scroll(bulk, 7); + wsap_vtcore_scroll(stream, 7); + wsap_vtcore_scroll(bytes, 7); assert_same_screen(bulk, bytes); assert_same_screen(stream, bytes); } - term_free(bulk); - term_free(stream); - term_free(bytes); + wsap_vtcore_free(bulk); + wsap_vtcore_free(stream); + wsap_vtcore_free(bytes); free(buf); } } @@ -1289,29 +1289,29 @@ static void test_ascii_flood_edits(void) "\033[?1049hALT\033[?1049l\033[6;1Htail\n"; for (size_t w = 0; w < sizeof(widths) / sizeof(widths[0]); w++) { for (size_t chunk = 4096; chunk <= sizeof(input); chunk *= 16) { - struct term *bulk = tt_new(widths[w], 6); - struct term *bytes = tt_new(widths[w], 6); + struct wsap_vtcore *bulk = tt_new(widths[w], 6); + struct wsap_vtcore *bytes = tt_new(widths[w], 6); for (size_t i = 0; i < sizeof(input); i += chunk) - term_feed(bulk, input + i, chunk, TERM_FEED_ONLCR); + wsap_vtcore_feed(bulk, input + i, chunk, WSAP_VTCORE_FEED_ONLCR); for (size_t i = 0; i < sizeof(input); i++) - term_feed(bytes, input + i, 1, TERM_FEED_ONLCR); + wsap_vtcore_feed(bytes, input + i, 1, WSAP_VTCORE_FEED_ONLCR); assert_same_screen(bulk, bytes); - term_feed(bulk, edit, sizeof(edit) - 1, TERM_FEED_ONLCR); + wsap_vtcore_feed(bulk, edit, sizeof(edit) - 1, WSAP_VTCORE_FEED_ONLCR); for (size_t i = 0; i < sizeof(edit) - 1; i++) - term_feed(bytes, edit + i, 1, TERM_FEED_ONLCR); + wsap_vtcore_feed(bytes, edit + i, 1, WSAP_VTCORE_FEED_ONLCR); assert_same_screen(bulk, bytes); for (int i = 0; i < tt_history(bulk); i += 6) { - term_scroll(bulk, 6); - term_scroll(bytes, 6); + wsap_vtcore_scroll(bulk, 6); + wsap_vtcore_scroll(bytes, 6); assert_same_screen(bulk, bytes); } - term_scroll_to(bulk, 0); - term_scroll_to(bytes, 0); + wsap_vtcore_scroll_to(bulk, 0); + wsap_vtcore_scroll_to(bytes, 0); assert(tt_resize(bulk, widths[w] + 3, 7)); assert(tt_resize(bytes, widths[w] + 3, 7)); assert_same_screen(bulk, bytes); - term_free(bulk); - term_free(bytes); + wsap_vtcore_free(bulk); + wsap_vtcore_free(bytes); } } } @@ -1327,8 +1327,8 @@ static void test_margin_linefeed_bursts(void) }; for (size_t k = 0; k < sizeof(bursts) / sizeof(bursts[0]); k++) { for (int mode = 0; mode < 3; mode++) { - struct term *bulk = tt_new(8, 8); - struct term *bytes = tt_new(8, 8); + struct wsap_vtcore *bulk = tt_new(8, 8); + struct wsap_vtcore *bytes = tt_new(8, 8); const char *setup = "\033[1;1Htop\033[2;1Ha\033[3;1Hb\033[4;1Hc" "\033[5;1Hd\033[6;1He\033[7;1Hf\033[8;1Hfoot" "\033[2;7r\033[7;3H"; @@ -1338,22 +1338,22 @@ static void test_margin_linefeed_bursts(void) write_seq(bulk, "\033[20h"); write_seq(bytes, "\033[20h"); } - unsigned flags = mode == 2 ? TERM_FEED_ONLCR : 0; - term_feed(bulk, bursts[k], strlen(bursts[k]), flags); + unsigned flags = mode == 2 ? WSAP_VTCORE_FEED_ONLCR : 0; + wsap_vtcore_feed(bulk, bursts[k], strlen(bursts[k]), flags); feed_seq(bytes, bursts[k], flags); assert_same_screen(bulk, bytes); assert(row_is(bulk, 0, "top")); assert(row_is(bulk, 7, "foot")); - term_free(bulk); - term_free(bytes); + wsap_vtcore_free(bulk); + wsap_vtcore_free(bytes); } } } static void test_alt_linefeed_burst_after_resize(void) { - struct term *bulk = tt_new(8, 5); - struct term *bytes = tt_new(8, 5); + struct wsap_vtcore *bulk = tt_new(8, 5); + struct wsap_vtcore *bytes = tt_new(8, 5); const char *setup = "\033[?1049h\033[5;1H\n\n\n\n"; tt_write(bulk, setup, strlen(setup)); write_seq(bytes, setup); @@ -1366,8 +1366,8 @@ static void test_alt_linefeed_burst_after_resize(void) tt_resize(bulk, 12, 4); tt_resize(bytes, 12, 4); assert_same_screen(bulk, bytes); - term_free(bulk); - term_free(bytes); + wsap_vtcore_free(bulk); + wsap_vtcore_free(bytes); } /* @@ -1380,24 +1380,24 @@ static void test_alt_resize_keeps_row_order(void) const char *setup = "\033[?1049h\033[5;1H\n\n\n" "\033[1;1HA\033[2;1HB\033[3;1HC\033[4;1HD\033[5;1HE"; - struct term *grow = tt_new(20, 5); + struct wsap_vtcore *grow = tt_new(20, 5); write_seq(grow, setup); tt_resize(grow, 20, 8); assert(row_is(grow, 0, "A") && row_is(grow, 4, "E")); assert(row_is(grow, 5, "") && row_is(grow, 7, "")); - term_free(grow); + wsap_vtcore_free(grow); /* The cursor is on the last row, so shrinking scrolls A and B off. */ - struct term *shrink = tt_new(20, 5); + struct wsap_vtcore *shrink = tt_new(20, 5); write_seq(shrink, setup); tt_resize(shrink, 20, 3); assert(row_is(shrink, 0, "C") && row_is(shrink, 2, "E")); - term_free(shrink); + wsap_vtcore_free(shrink); } static void test_alt_shrink_then_flood(void) { - struct term *t = tt_new(80, 40); + struct wsap_vtcore *t = tt_new(80, 40); tt_write(t, "\033[?1049h\033[40;1H", 16); for (int i = 0; i < 35; i++) tt_write(t, "x\n", 2); @@ -1409,36 +1409,36 @@ static void test_alt_shrink_then_flood(void) tt_write(t, line, (size_t)len); } assert(row_is(t, 8, "line 5999") && row_is(t, 0, "line 5991")); - term_free(t); + wsap_vtcore_free(t); } /* Regression: ED 3 on the alternate screen kept the history count, so the * normal screen came back with blank history rows. */ static void test_alt_erase_scrollback(void) { - struct term *t = tt_new(20, 5); + struct wsap_vtcore *t = tt_new(20, 5); for (int i = 0; i < 30; i++) tt_write(t, "line\r\n", 6); assert(tt_history(t) > 0); write_seq(t, "\033[?1049h\033[3J\033[?1049l"); assert(tt_history(t) == 0); - term_free(t); + wsap_vtcore_free(t); } /* Regression: a snapshot knew its terminal by address. A new terminal that * reused a freed one's memory then showed the old terminal's rows. */ static void test_snapshot_follows_new_terminal(void) { - struct term_snapshot *s = term_snapshot_new(); + struct wsap_vtcore_snapshot *s = wsap_vtcore_snapshot_new(); for (int i = 0; i < 8; i++) { - struct term *t = tt_new(10, 2); + struct wsap_vtcore *t = tt_new(10, 2); char text[2] = { (char)('a' + i), 0 }; tt_puts(t, text); - assert(term_snapshot_update(s, t)); - assert(term_snapshot_row(s, 0)[0].text == (uint32_t)text[0]); - term_free(t); + assert(wsap_vtcore_snapshot_update(s, t)); + assert(wsap_vtcore_snapshot_row(s, 0)[0].text == (uint32_t)text[0]); + wsap_vtcore_free(t); } - term_snapshot_free(s); + wsap_vtcore_snapshot_free(s); } /* The getters take a NULL snapshot and an out-of-range row like a NULL @@ -1446,48 +1446,48 @@ static void test_snapshot_follows_new_terminal(void) static void test_snapshot_null_and_range(void) { uint32_t cps[4] = { 0xAAAA, 0xAAAA, 0xAAAA, 0xAAAA }; - assert(term_snapshot_view(NULL) == NULL); - assert(term_snapshot_row(NULL, 0) == NULL); - assert(term_snapshot_row_key(NULL, 0) == 0); - struct term_span none = term_snapshot_row_selection(NULL, 0); + assert(wsap_vtcore_snapshot_view(NULL) == NULL); + assert(wsap_vtcore_snapshot_row(NULL, 0) == NULL); + assert(wsap_vtcore_snapshot_row_key(NULL, 0) == 0); + struct wsap_vtcore_span none = wsap_vtcore_snapshot_row_selection(NULL, 0); assert(none.begin == 0 && none.end == 0); - assert(term_snapshot_cluster(NULL, 'a', cps, 4) == 0); - assert(term_snapshot_cluster(NULL, TERM_TEXT_CLUSTER, cps, 4) == 0); + assert(wsap_vtcore_snapshot_cluster(NULL, 'a', cps, 4) == 0); + assert(wsap_vtcore_snapshot_cluster(NULL, WSAP_VTCORE_TEXT_CLUSTER, cps, 4) == 0); assert(cps[0] == 0xAAAA); - struct term *t = tt_new(4, 2); + struct wsap_vtcore *t = tt_new(4, 2); tt_write(t, "e\xcc\x81", 3); - struct term_snapshot *s = term_snapshot_new(); - assert(term_snapshot_update(s, t)); + struct wsap_vtcore_snapshot *s = wsap_vtcore_snapshot_new(); + assert(wsap_vtcore_snapshot_update(s, t)); - const struct term_view *view = term_snapshot_view(s); + const struct wsap_vtcore_view *view = wsap_vtcore_snapshot_view(s); const uint32_t *palette = view->palette; - assert(term_snapshot_update(s, t)); - assert(term_snapshot_view(s) == view && view->palette == palette); - - assert(term_snapshot_row(s, -1) == NULL); - assert(term_snapshot_row(s, 2) == NULL); - assert(term_snapshot_row_key(s, -1) == 0); - assert(term_snapshot_row_key(s, 2) == 0); - struct term_span off = term_snapshot_row_selection(s, 2); + assert(wsap_vtcore_snapshot_update(s, t)); + assert(wsap_vtcore_snapshot_view(s) == view && view->palette == palette); + + assert(wsap_vtcore_snapshot_row(s, -1) == NULL); + assert(wsap_vtcore_snapshot_row(s, 2) == NULL); + assert(wsap_vtcore_snapshot_row_key(s, -1) == 0); + assert(wsap_vtcore_snapshot_row_key(s, 2) == 0); + struct wsap_vtcore_span off = wsap_vtcore_snapshot_row_selection(s, 2); assert(off.begin == 0 && off.end == 0); /* A cluster cell gives its count with no buffer, and with cap 0 it * writes nothing. */ - uint32_t text = term_snapshot_row(s, 0)[0].text; - assert(text & TERM_TEXT_CLUSTER); - assert(term_snapshot_cluster(s, text, NULL, 0) == 2); - assert(term_snapshot_cluster(s, text, cps, 0) == 2); + uint32_t text = wsap_vtcore_snapshot_row(s, 0)[0].text; + assert(text & WSAP_VTCORE_TEXT_CLUSTER); + assert(wsap_vtcore_snapshot_cluster(s, text, NULL, 0) == 2); + assert(wsap_vtcore_snapshot_cluster(s, text, cps, 0) == 2); assert(cps[0] == 0xAAAA); - assert(term_snapshot_cluster(s, text, NULL, 4) == 2); + assert(wsap_vtcore_snapshot_cluster(s, text, NULL, 4) == 2); /* A plain code point is one code point, and cap 0 writes nothing. */ - assert(term_snapshot_cluster(s, 'a', NULL, 0) == 1); - assert(term_snapshot_cluster(s, 'a', cps, 0) == 1); + assert(wsap_vtcore_snapshot_cluster(s, 'a', NULL, 0) == 1); + assert(wsap_vtcore_snapshot_cluster(s, 'a', cps, 0) == 1); assert(cps[0] == 0xAAAA); - assert(term_snapshot_cluster(s, 'a', cps, 4) == 1 && cps[0] == 'a'); + assert(wsap_vtcore_snapshot_cluster(s, 'a', cps, 4) == 1 && cps[0] == 'a'); - term_snapshot_free(s); - term_free(t); + wsap_vtcore_snapshot_free(s); + wsap_vtcore_free(t); } static void test_string_payloads(void) @@ -1508,7 +1508,7 @@ static void test_string_payloads(void) for (size_t c = 0; c < 3; c++) { title[0] = 0; response_len = 0; - struct term *t = tt_new_opts(80, 4, &title_cb); + struct wsap_vtcore *t = tt_new_opts(80, 4, &title_cb); for (size_t i = 0; i < n;) { size_t take = n - i < chunks[c] ? n - i : chunks[c]; tt_write(t, input + i, take); @@ -1528,14 +1528,14 @@ static void test_string_payloads(void) assert(title[0] == 0); } } - term_free(t); + wsap_vtcore_free(t); } } } } } -/* term_new() refuses a name that a DCS reply could echo unsafely. */ +/* wsap_vtcore_new() refuses a name that a DCS reply could echo unsafely. */ static void test_host_name_rejected(void) { static const char *const bad[] = { @@ -1549,40 +1549,40 @@ static void test_host_name_rejected(void) fits[63] = 0; for (size_t i = 0; i < sizeof(bad) / sizeof(bad[0]); i++) { - struct term_options opt = { .size = { .x = 10, .y = 3 }, .name = bad[i] }; - assert(!term_new(&opt)); + struct wsap_vtcore_options opt = { .size = { .x = 10, .y = 3 }, .name = bad[i] }; + assert(!wsap_vtcore_new(&opt)); } - struct term_options opt = { .size = { .x = 10, .y = 3 }, .name = longest }; - assert(!term_new(&opt)); + struct wsap_vtcore_options opt = { .size = { .x = 10, .y = 3 }, .name = longest }; + assert(!wsap_vtcore_new(&opt)); opt.name = fits; - struct term *t = term_new(&opt); + struct wsap_vtcore *t = wsap_vtcore_new(&opt); assert(t); - term_free(t); + wsap_vtcore_free(t); } static void test_newline_policy_survives_reset(void) { static const char *const resets[] = { "\033c", "\033[!p", "\033[20l" }; for (size_t i = 0; i < sizeof(resets) / sizeof(resets[0]); i++) { - struct term *t = tt_new(20, 6); - term_feed(t, "a\n", 2, TERM_FEED_ONLCR); + struct wsap_vtcore *t = tt_new(20, 6); + wsap_vtcore_feed(t, "a\n", 2, WSAP_VTCORE_FEED_ONLCR); assert(tt_cursor_x(t) == 0); write_seq(t, resets[i]); - term_feed(t, "b\nc", 3, TERM_FEED_ONLCR); + wsap_vtcore_feed(t, "b\nc", 3, WSAP_VTCORE_FEED_ONLCR); assert(tt_cursor_x(t) == 1); assert(row_is(t, tt_cursor_y(t), "c")); - term_free(t); + wsap_vtcore_free(t); } } static void test_lnm_mode_alone_is_not_sticky(void) { - struct term *t = tt_new(20, 6); + struct wsap_vtcore *t = tt_new(20, 6); write_seq(t, "\033[20h\033c"); tt_write(t, "b\nc", 3); assert(tt_cursor_x(t) == 2); - term_free(t); + wsap_vtcore_free(t); } /* A C0 control ends an unfinished UTF-8 sequence, which prints U+FFFD. A @@ -1591,13 +1591,13 @@ static void test_c0_ends_utf8_sequence(void) { static const char input[] = "\xc3\n\xa9z"; for (size_t split = 0; split < sizeof(input) - 1; split++) { - struct term *t = tt_new(20, 4); + struct wsap_vtcore *t = tt_new(20, 4); tt_write(t, input, split); tt_write(t, input + split, sizeof(input) - 1 - split); assert(tt_cell_cp(t, tt_cell(t, 0, 0)) == 0xFFFD); assert(tt_cell_cp(t, tt_cell(t, 1, 1)) == 0xFFFD); assert(tt_cell_cp(t, tt_cell(t, 2, 1)) == 'z'); - term_free(t); + wsap_vtcore_free(t); } } @@ -1611,8 +1611,8 @@ static void test_bulk_rows_survive_edits(void) for (size_t i = 0; i < sizeof(flood); i++) flood[i] = (char)('a' + (i * 7 + i / COLS) % 26); - struct term *bulk = tt_new(COLS, ROWS); - struct term *bytes = tt_new(COLS, ROWS); + struct wsap_vtcore *bulk = tt_new(COLS, ROWS); + struct wsap_vtcore *bytes = tt_new(COLS, ROWS); write_seq(bulk, "\033[1;4;38;2;9;8;7;48;2;1;2;3m"); write_seq(bytes, "\033[1;4;38;2;9;8;7;48;2;1;2;3m"); tt_write(bulk, flood, sizeof(flood)); @@ -1637,24 +1637,24 @@ static void test_bulk_rows_survive_edits(void) write_seq(bytes, "\033[?1049hALT\033[?1049l"); assert_same_screen(bulk, bytes); for (int i = 0; i < 3; i++) { - term_scroll(bulk, 100); - term_scroll(bytes, 100); + wsap_vtcore_scroll(bulk, 100); + wsap_vtcore_scroll(bytes, 100); assert_same_screen(bulk, bytes); } - term_scroll_to(bulk, 0); - term_scroll_to(bytes, 0); + wsap_vtcore_scroll_to(bulk, 0); + wsap_vtcore_scroll_to(bytes, 0); /* Selection text reads rows straight from history. */ - term_scroll(bulk, 50); - term_scroll(bytes, 50); + wsap_vtcore_scroll(bulk, 50); + wsap_vtcore_scroll(bytes, 50); tt_select(bulk, 0, 0, COLS - 1, 2); tt_select(bytes, 0, 0, COLS - 1, 2); char *a = tt_selection_text(bulk), *b = tt_selection_text(bytes); assert(a && b && !strcmp(a, b) && strlen(a) >= COLS); free(a); free(b); - term_scroll_to(bulk, 0); - term_scroll_to(bytes, 0); + wsap_vtcore_scroll_to(bulk, 0); + wsap_vtcore_scroll_to(bytes, 0); /* Reflow narrower and wider keeps history identical. */ tt_resize(bulk, 29, ROWS); @@ -1663,27 +1663,27 @@ static void test_bulk_rows_survive_edits(void) tt_resize(bulk, 61, ROWS + 2); tt_resize(bytes, 61, ROWS + 2); assert_same_screen(bulk, bytes); - term_scroll(bulk, 20); - term_scroll(bytes, 20); + wsap_vtcore_scroll(bulk, 20); + wsap_vtcore_scroll(bytes, 20); assert_same_screen(bulk, bytes); - term_free(bulk); - term_free(bytes); + wsap_vtcore_free(bulk); + wsap_vtcore_free(bytes); } static void test_erase_keeps_used_rows(void) { for (int row = 0; row < 40; row++) { - struct term *t = tt_new(20, 40); + struct wsap_vtcore *t = tt_new(20, 40); char seq[64]; int len = snprintf(seq, sizeof(seq), "\033[%d;1Hsaved\033[2J", row + 1); tt_write(t, seq, (size_t)len); assert(tt_history(t) == row + 1); for (int y = 0; y < 40; y++) assert(row_eq(t, y, "")); - term_scroll(t, 1); + wsap_vtcore_scroll(t, 1); assert(row_eq(t, 0, "saved")); - term_free(t); + wsap_vtcore_free(t); } } @@ -1691,20 +1691,20 @@ static void test_blank_rows(void) { /* ED 2 pushes used rows to scrollback; the erased screen reads as * default-color blanks through every accessor. */ - struct term *t = tt_new(10, 4); + struct wsap_vtcore *t = tt_new(10, 4); write_seq(t, "one\r\ntwo\r\nthree"); write_seq(t, "\033[2J"); assert(tt_history(t) == 3); for (int y = 0; y < 4; y++) for (int x = 0; x < 10; x++) { - const struct term_cell *c = tt_view_cell(t, x, y); - assert(c->text == ' ' && c->fg == TERM_COLOR_FG && - c->bg == TERM_COLOR_BG); + const struct wsap_vtcore_cell *c = tt_view_cell(t, x, y); + assert(c->text == ' ' && c->fg == WSAP_VTCORE_COLOR_FG && + c->bg == WSAP_VTCORE_COLOR_BG); assert(tt_cell(t, x, y)->text == ' '); } - term_scroll(t, 3); + wsap_vtcore_scroll(t, 3); assert(row_is(t, 0, "one") && row_is(t, 1, "two") && row_is(t, 2, "three")); - term_scroll_to(t, 0); + wsap_vtcore_scroll_to(t, 0); /* A scrolled-in blank row reads as blanks, then accepts new text. */ write_seq(t, "\033[4;1Hlast\r\n\r\n\r\n"); @@ -1712,7 +1712,7 @@ static void test_blank_rows(void) assert(tt_view_cell(t, x, 3)->text == ' '); write_seq(t, "\033[4;6Hhi"); assert(row_is(t, 3, " hi")); - term_free(t); + wsap_vtcore_free(t); /* A spaces-only row does not extend ED 2 history. */ t = tt_new(10, 6); @@ -1720,23 +1720,23 @@ static void test_blank_rows(void) assert(tt_history(t) == 0); write_seq(t, "\033[2J"); assert(tt_history(t) == 1); - term_scroll(t, 1); + wsap_vtcore_scroll(t, 1); assert(row_is(t, 0, "top")); - term_scroll_to(t, 0); + wsap_vtcore_scroll_to(t, 0); /* Blank rows survive a resize and still read as blanks. */ tt_resize(t, 20, 6); for (int x = 0; x < 20; x++) assert(tt_cell(t, x, 5)->text == ' ' && - tt_cell(t, x, 5)->bg == TERM_COLOR_BG); - term_free(t); + tt_cell(t, x, 5)->bg == WSAP_VTCORE_COLOR_BG); + wsap_vtcore_free(t); /* Erasing a blank row with a color still produces a colored row. */ t = tt_new(10, 4); write_seq(t, "\033[2J\033[41m\033[2K"); - assert(tt_cell(t, 0, 0)->bg != TERM_COLOR_BG); + assert(tt_cell(t, 0, 0)->bg != WSAP_VTCORE_COLOR_BG); assert(tt_cell(t, 9, 0)->bg == tt_cell(t, 0, 0)->bg); - term_free(t); + wsap_vtcore_free(t); } static void test_csi_text_chunks(void) @@ -1757,26 +1757,26 @@ static void test_csi_text_chunks(void) for (size_t c = 0; c < sizeof(cases) / sizeof(cases[0]); c++) { const char *seq = cases[c]; size_t len = strlen(seq); - struct term *expected = tt_new(20, 40); + struct wsap_vtcore *expected = tt_new(20, 40); write_seq(expected, seq); for (size_t split = 0; split <= len; split++) { - struct term *actual = tt_new(20, 40); + struct wsap_vtcore *actual = tt_new(20, 40); tt_write(actual, seq, split); tt_write(actual, seq + split, len - split); assert(tt_cursor_x(actual) == tt_cursor_x(expected)); assert(tt_cursor_y(actual) == tt_cursor_y(expected)); assert(tt_history(actual) == tt_history(expected)); int history = tt_history(expected); - term_scroll(actual, history); - term_scroll(expected, history); + wsap_vtcore_scroll(actual, history); + wsap_vtcore_scroll(expected, history); for (int page = 0; page <= history; page++) { assert_same_rows(actual, expected, 40); - term_scroll(actual, -1); - term_scroll(expected, -1); + wsap_vtcore_scroll(actual, -1); + wsap_vtcore_scroll(expected, -1); } - term_free(actual); + wsap_vtcore_free(actual); } - term_free(expected); + wsap_vtcore_free(expected); } } @@ -1785,7 +1785,7 @@ static void test_csi_text_chunks(void) * keep their text. */ static void test_grow_past_reservation(void) { - struct term *t = tt_new(40, 10); + struct wsap_vtcore *t = tt_new(40, 10); for (int i = 0; i < 30; i++) { char line[32]; int len = snprintf(line, sizeof(line), "hist %02d\r\n", i); @@ -1821,20 +1821,20 @@ static void test_grow_past_reservation(void) tt_write(t, "\033[?1049l", 8); bool found = false; - term_scroll(t, tt_history(t)); + wsap_vtcore_scroll(t, tt_history(t)); for (int y = 0; y < tt_rows(t) && !found; y++) found = row_eq(t, y, "hist 00"); assert(found); - term_scroll(t, -tt_history(t)); + wsap_vtcore_scroll(t, -tt_history(t)); bool last = false; for (int y = 0; y < tt_rows(t) && !last; y++) last = row_eq(t, y, "fill 0999"); assert(last); - term_free(t); + wsap_vtcore_free(t); } struct concurrent_worker_args { - struct term *t; + struct wsap_vtcore *t; _Atomic bool done; }; @@ -1853,7 +1853,7 @@ static void *concurrent_feed_worker(void *arg) size_t len = strlen(concurrent_stream); for (int i = 0; i < 2000; i++) { - term_feed(w->t, concurrent_stream, len, 0); + wsap_vtcore_feed(w->t, concurrent_stream, len, 0); } atomic_store(&w->done, true); return NULL; @@ -1861,11 +1861,11 @@ static void *concurrent_feed_worker(void *arg) static void test_concurrent_feed_and_snapshot(void) { - struct term_options opt = { + struct wsap_vtcore_options opt = { .size = { .x = 80, .y = 24 }, .scrollback = 1000, }; - struct term *t = term_new(&opt); + struct wsap_vtcore *t = wsap_vtcore_new(&opt); assert(t != NULL); struct concurrent_worker_args w = { .t = t, .done = false }; @@ -1873,43 +1873,43 @@ static void test_concurrent_feed_and_snapshot(void) int err = pthread_create(&th, NULL, concurrent_feed_worker, &w); assert(err == 0); - struct term_snapshot *snap = term_snapshot_new(); + struct wsap_vtcore_snapshot *snap = wsap_vtcore_snapshot_new(); assert(snap != NULL); while (!atomic_load(&w.done)) { - bool ok = term_snapshot_update(snap, t); + bool ok = wsap_vtcore_snapshot_update(snap, t); assert(ok); - struct term_vector2i sz = term_size(t); + struct wsap_vtcore_vector2i sz = wsap_vtcore_size(t); assert(sz.x > 0 && sz.y > 0); - term_scroll(t, 2); - term_scroll_to(t, 0); - struct term_modes m = term_modes(t); + wsap_vtcore_scroll(t, 2); + wsap_vtcore_scroll_to(t, 0); + struct wsap_vtcore_modes m = wsap_vtcore_modes(t); (void)m; - struct term_cursor c = term_cursor(t); + struct wsap_vtcore_cursor c = wsap_vtcore_cursor(t); (void)c; /* Every reader is safe while another thread feeds. */ - term_select_start(t, (struct term_vector2i){ .x = 0, .y = 0 }, false, TERM_SELECT_WORD); - term_select_extend(t, (struct term_vector2i){ .x = 40, .y = 10 }, false); - (void)term_has_selection(t); - term_text_free(term_selection_text(t)); - term_text_free(term_link_at(t, (struct term_vector2i){ .x = 1, .y = 1 })); - term_text_free(term_cwd(t)); - term_text_free(term_pointer_shape(t)); - (void)term_history_rows(t); - term_text_free(term_history_text(t, 5)); - struct term_scrollback sb = term_scrollback(t); + wsap_vtcore_select_start(t, (struct wsap_vtcore_vector2i){ .x = 0, .y = 0 }, false, WSAP_VTCORE_SELECT_WORD); + wsap_vtcore_select_extend(t, (struct wsap_vtcore_vector2i){ .x = 40, .y = 10 }, false); + (void)wsap_vtcore_has_selection(t); + wsap_vtcore_text_free(wsap_vtcore_selection_text(t)); + wsap_vtcore_text_free(wsap_vtcore_link_at(t, (struct wsap_vtcore_vector2i){ .x = 1, .y = 1 })); + wsap_vtcore_text_free(wsap_vtcore_cwd(t)); + wsap_vtcore_text_free(wsap_vtcore_pointer_shape(t)); + (void)wsap_vtcore_history_rows(t); + wsap_vtcore_text_free(wsap_vtcore_history_text(t, 5)); + struct wsap_vtcore_scrollback sb = wsap_vtcore_scrollback(t); assert(sb.offset >= 0 && sb.total >= 0); } pthread_join(th, NULL); - bool ok = term_snapshot_update(snap, t); + bool ok = wsap_vtcore_snapshot_update(snap, t); assert(ok); /* The reader changed only the view and the selection. The screen and * the history must match a terminal that got the same bytes on one * thread. */ - struct term *ref = term_new(&opt); + struct wsap_vtcore *ref = wsap_vtcore_new(&opt); assert(ref != NULL); for (int i = 0; i < 2000; i++) tt_write(ref, concurrent_stream, strlen(concurrent_stream)); @@ -1926,65 +1926,65 @@ static void test_concurrent_feed_and_snapshot(void) } free(got); free(want); - char *text = term_history_text(t, 1000); - char *text_ref = term_history_text(ref, 1000); + char *text = wsap_vtcore_history_text(t, 1000); + char *text_ref = wsap_vtcore_history_text(ref, 1000); assert(text && text_ref && !strcmp(text, text_ref)); - term_text_free(text); - term_text_free(text_ref); + wsap_vtcore_text_free(text); + wsap_vtcore_text_free(text_ref); - term_free(ref); - term_snapshot_free(snap); - term_free(t); + wsap_vtcore_free(ref); + wsap_vtcore_snapshot_free(snap); + wsap_vtcore_free(t); } static void test_reserved_options_must_be_zero(void) { - struct term_options opt = { .size = { .x = 10, .y = 2 } }; - struct term *t = term_new(&opt); + struct wsap_vtcore_options opt = { .size = { .x = 10, .y = 2 } }; + struct wsap_vtcore *t = wsap_vtcore_new(&opt); assert(t != NULL); - term_free(t); + wsap_vtcore_free(t); size_t words = sizeof(opt.reserved) / sizeof(opt.reserved[0]); for (size_t i = 0; i < words; i++) { opt.reserved[i] = 1; - assert(term_new(&opt) == NULL); + assert(wsap_vtcore_new(&opt) == NULL); opt.reserved[i] = 0; } opt.reserved[words - 1] = 0x80000000u; - assert(term_new(&opt) == NULL); + assert(wsap_vtcore_new(&opt) == NULL); opt.reserved[words - 1] = 0; - t = term_new(&opt); + t = wsap_vtcore_new(&opt); assert(t != NULL); - term_free(t); + wsap_vtcore_free(t); } struct lock_probe { - struct term *t; + struct wsap_vtcore *t; _Atomic bool entered; }; static void *lock_probe_worker(void *arg) { struct lock_probe *p = arg; - term_lock(p->t); + wsap_vtcore_lock(p->t); atomic_store(&p->entered, true); - term_unlock(p->t); + wsap_vtcore_unlock(p->t); return NULL; } -/* term_lock() nests on the owning thread. Another thread waits until the - * last term_unlock(). */ +/* wsap_vtcore_lock() nests on the owning thread. Another thread waits until the + * last wsap_vtcore_unlock(). */ static void test_lock_reentrant_across_threads(void) { - struct term *t = term_new(&(struct term_options){ + struct wsap_vtcore *t = wsap_vtcore_new(&(struct wsap_vtcore_options){ .size = { .x = 80, .y = 24 }, }); assert(t != NULL); - term_lock(t); - term_lock(t); + wsap_vtcore_lock(t); + wsap_vtcore_lock(t); assert(tt_cols(t) == 80); - term_unlock(t); + wsap_vtcore_unlock(t); struct lock_probe p = { .t = t, .entered = false }; pthread_t th; @@ -1992,11 +1992,11 @@ static void test_lock_reentrant_across_threads(void) for (int i = 0; i < 1000; i++) sched_yield(); assert(!atomic_load(&p.entered)); - term_unlock(t); + wsap_vtcore_unlock(t); assert(pthread_join(th, NULL) == 0); assert(atomic_load(&p.entered)); - term_free(t); + wsap_vtcore_free(t); } int main(void) @@ -2032,21 +2032,21 @@ int main(void) test_bulk_rows_survive_edits(); test_host_name_rejected(); - assert(!strcmp(TERM_UNICODE_DATA_VERSION, "18.0.0")); - assert(!strcmp(term_unicode_version(), TERM_UNICODE_DATA_VERSION)); - assert(term_unicode_width('A') == 1); - assert(term_unicode_width(0x0301) == 0); - assert(term_unicode_width(0x754C) == 2); - assert(term_unicode_width(0x1FAE0) == 2); - assert(term_unicode_emoji_presentation(0x1FAE0)); - assert(term_unicode_width(0x1FAEB) == 2); - assert(term_unicode_emoji_presentation(0x1FAEB)); + assert(!strcmp(WSAP_VTCORE_UNICODE_DATA_VERSION, "18.0.0")); + assert(!strcmp(wsap_vtcore_unicode_version(), WSAP_VTCORE_UNICODE_DATA_VERSION)); + assert(wsap_vtcore_unicode_width('A') == 1); + assert(wsap_vtcore_unicode_width(0x0301) == 0); + assert(wsap_vtcore_unicode_width(0x754C) == 2); + assert(wsap_vtcore_unicode_width(0x1FAE0) == 2); + assert(wsap_vtcore_unicode_emoji_presentation(0x1FAE0)); + assert(wsap_vtcore_unicode_width(0x1FAEB) == 2); + assert(wsap_vtcore_unicode_emoji_presentation(0x1FAEB)); { /* A Jamo Extended-B vowel draws inside its leading consonant. */ - struct term *t = term_new(&(struct term_options){ .size = { .x = 10, .y = 2 } }); - term_feed(t, "\xe1\x84\x80\xed\x9e\xb0", 6, 0); - assert(term_cursor(t).pos.x == 2); - term_free(t); + struct wsap_vtcore *t = wsap_vtcore_new(&(struct wsap_vtcore_options){ .size = { .x = 10, .y = 2 } }); + wsap_vtcore_feed(t, "\xe1\x84\x80\xed\x9e\xb0", 6, 0); + assert(wsap_vtcore_cursor(t).pos.x == 2); + wsap_vtcore_free(t); } test_wide_characters(); @@ -2069,7 +2069,7 @@ int main(void) test_parameter_limits(); test_unterminated_control_strings_do_not_swallow_text(); test_c0_controls_after_esc_are_executed(); - struct term *t = tt_new_opts(10, 4, &reply_cb); + struct wsap_vtcore *t = tt_new_opts(10, 4, &reply_cb); write_seq(t, "\033(Babc\r\nD"); assert(tt_cell(t, 0, 0)->text == 'a'); assert(tt_cell(t, 0, 1)->text == 'D'); @@ -2133,7 +2133,7 @@ int main(void) write_seq(t, "\033[?6;69l"); write_seq(t, "\033[?1;5;1004;2026h\033[!p"); - struct term_modes modes = term_modes(t); + struct wsap_vtcore_modes modes = wsap_vtcore_modes(t); assert(!modes.app_cursor && !modes.focus_events); assert(!modes.synchronized && !modes.reverse_video); write_seq(t, "kept\033c"); @@ -2147,28 +2147,28 @@ int main(void) assert(tt_cell(t, 0, 0)->text == 'A'); write_seq(t, "\033[2;4H\033[2J"); assert(tt_cursor_x(t) == 3 && tt_cursor_y(t) == 1); - assert(term_modes(t).mouse == TERM_MOUSE_OFF); + assert(wsap_vtcore_modes(t).mouse == WSAP_VTCORE_MOUSE_OFF); write_seq(t, "\033[?1000;1006h"); - assert(term_modes(t).mouse == TERM_MOUSE_NORMAL); - assert(term_modes(t).mouse_encoding == TERM_MOUSE_ENC_SGR); + assert(wsap_vtcore_modes(t).mouse == WSAP_VTCORE_MOUSE_NORMAL); + assert(wsap_vtcore_modes(t).mouse_encoding == WSAP_VTCORE_MOUSE_ENC_SGR); write_seq(t, "\033[?1002h"); - assert(term_modes(t).mouse == TERM_MOUSE_BUTTON); - assert(term_modes(t).mouse_encoding == TERM_MOUSE_ENC_SGR); + assert(wsap_vtcore_modes(t).mouse == WSAP_VTCORE_MOUSE_BUTTON); + assert(wsap_vtcore_modes(t).mouse_encoding == WSAP_VTCORE_MOUSE_ENC_SGR); write_seq(t, "\033[?1003h"); - assert(term_modes(t).mouse == TERM_MOUSE_ANY); + assert(wsap_vtcore_modes(t).mouse == WSAP_VTCORE_MOUSE_ANY); write_seq(t, "\033[?1006l"); - assert(term_modes(t).mouse_encoding == TERM_MOUSE_ENC_X10); + assert(wsap_vtcore_modes(t).mouse_encoding == WSAP_VTCORE_MOUSE_ENC_X10); write_seq(t, "\033[?1015h"); - assert(term_modes(t).mouse_encoding == TERM_MOUSE_ENC_URXVT); + assert(wsap_vtcore_modes(t).mouse_encoding == WSAP_VTCORE_MOUSE_ENC_URXVT); write_seq(t, "\033[?1016h"); - assert(term_modes(t).mouse_encoding == TERM_MOUSE_ENC_SGR_PIXELS); + assert(wsap_vtcore_modes(t).mouse_encoding == WSAP_VTCORE_MOUSE_ENC_SGR_PIXELS); write_seq(t, "\033[?1004h"); - term_focus(t, false); + wsap_vtcore_focus(t, false); assert(!strcmp(response, "\033[O")); - term_focus(t, true); + wsap_vtcore_focus(t, true); assert(!strcmp(response, "\033[I")); write_seq(t, "\033[?1003l"); - assert(term_modes(t).mouse == TERM_MOUSE_OFF); + assert(wsap_vtcore_modes(t).mouse == WSAP_VTCORE_MOUSE_OFF); response_len = 0; write_seq(t, "\033]10;?\007"); assert(!strcmp(response, "\033]10;rgb:ffff/ffff/ffff\033\\")); @@ -2176,7 +2176,7 @@ int main(void) assert(!strcmp(response, "\033P0+r696e646e\033\\")); write_seq(t, "\033P+q6b696e64\033\\"); assert(!strcmp(response, "\033P1+r6b696e64=1b5b313b3242\033\\")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(40, 4); write_seq(t, "hello 世界 \r\nsecond line\r\nhttps://example.com/path."); tt_select(t, 9, 0, 0, 0); @@ -2194,13 +2194,13 @@ int main(void) free(text); assert(!tt_link_at(t, 10, 1)); write_seq(t, "\033[?2004h"); - assert(term_modes(t).bracketed_paste); + assert(wsap_vtcore_modes(t).bracketed_paste); text = tt_selection_text(t); assert(text && !strcmp(text, "hello 世界\nsecond")); free(text); write_seq(t, "\033[?2004l\r\nlast\r\n"); - assert(!term_modes(t).bracketed_paste); - term_scroll(t, 1); + assert(!wsap_vtcore_modes(t).bracketed_paste); + wsap_vtcore_scroll(t, 1); tt_select(t, 0, 0, 9, 0); text = tt_selection_text(t); assert(text && !strcmp(text, "hello 世界")); @@ -2209,7 +2209,7 @@ int main(void) text = tt_selection_text(t); assert(text && !strcmp(text, "hello 世界")); free(text); - term_free(t); + wsap_vtcore_free(t); t = tt_new(40, 4); write_seq(t, "\033[31;44mA\033[>4;0mB\033[>4;1m\033[31mC"); assert(tt_cell(t, 0, 0)->fg == tt_cell(t, 1, 0)->fg); @@ -2218,49 +2218,49 @@ int main(void) assert(tt_cell(t, 0, 0)->bg == tt_cell(t, 2, 0)->bg); assert(tt_cursor_x(t) == 3 && tt_cursor_y(t) == 0); write_seq(t, "\033[0mD"); - assert(tt_cell(t, 3, 0)->fg == TERM_COLOR_FG); - assert(tt_cell(t, 3, 0)->bg == TERM_COLOR_BG); - term_free(t); + assert(tt_cell(t, 3, 0)->fg == WSAP_VTCORE_COLOR_FG); + assert(tt_cell(t, 3, 0)->bg == WSAP_VTCORE_COLOR_BG); + wsap_vtcore_free(t); t = tt_new(10, 4); write_seq(t, "ABCDEFGHIJ\r\n\r\n\r\n\r\n"); - term_scroll(t, 1); + wsap_vtcore_scroll(t, 1); assert(tt_view_cell(t, 0, 0)->text == 'A'); assert(tt_view_cell(t, 9, 0)->text == 'J'); - term_scroll_to(t, 0); + wsap_vtcore_scroll_to(t, 0); for (int i = 0; i < TEST_SCROLLBACK; i++) write_seq(t, "xy\r\n"); - term_scroll(t, 1); + wsap_vtcore_scroll(t, 1); assert(tt_view_cell(t, 0, 0)->text == 'x'); for (int c = 2; c < 10; c++) { assert(tt_view_cell(t, c, 0)->text == ' '); - assert(tt_view_cell(t, c, 0)->bg == TERM_COLOR_BG); + assert(tt_view_cell(t, c, 0)->bg == WSAP_VTCORE_COLOR_BG); } - term_free(t); + wsap_vtcore_free(t); t = tt_new(10, 4); write_seq(t, "\033[41m\033[2K"); - term_color erased_bg = tt_cell(t, 0, 0)->bg; - assert(erased_bg != TERM_COLOR_BG); + wsap_vtcore_color erased_bg = tt_cell(t, 0, 0)->bg; + assert(erased_bg != WSAP_VTCORE_COLOR_BG); assert(tt_cell(t, 9, 0)->bg == erased_bg); write_seq(t, "\033[m\n\n\n\n"); - term_scroll(t, 1); + wsap_vtcore_scroll(t, 1); assert(tt_view_cell(t, 9, 0)->bg == erased_bg); - assert(tt_view_cell(t, 10, 0)->bg == TERM_COLOR_BG); - term_free(t); + assert(tt_view_cell(t, 10, 0)->bg == WSAP_VTCORE_COLOR_BG); + wsap_vtcore_free(t); t = tt_new(10, 4); write_seq(t, "\033[Hnormal"); write_seq(t, "\033[?1049h"); for (int c = 0; c < 10; c++) { assert(tt_cell(t, c, 0)->text == ' '); - assert(tt_cell(t, c, 0)->bg == TERM_COLOR_BG); + assert(tt_cell(t, c, 0)->bg == WSAP_VTCORE_COLOR_BG); } write_seq(t, "\033[Halt\n\033[2J"); write_seq(t, "\033[?1049l"); assert(tt_cell(t, 0, 0)->text == 'n' && tt_cell(t, 5, 0)->text == 'l'); - term_free(t); + wsap_vtcore_free(t); t = tt_new(20, 8); write_seq(t, "one\r\ntwo\r\nthree\r\nfour\r\nfive\r\n$ "); @@ -2268,9 +2268,9 @@ int main(void) tt_resize(t, 20, 3); assert(tt_cursor_y(t) == 2 && tt_history(t) == 3); assert(row_is(t, 0, "four") && row_is(t, 1, "five") && row_is(t, 2, "$")); - term_scroll(t, 3); + wsap_vtcore_scroll(t, 3); assert(row_is(t, 0, "one") && row_is(t, 1, "two") && row_is(t, 2, "three")); - term_scroll_to(t, 0); + wsap_vtcore_scroll_to(t, 0); tt_resize(t, 20, 8); assert(tt_cursor_y(t) == 5 && tt_history(t) == 0); assert(row_is(t, 0, "one") && row_is(t, 2, "three") && row_is(t, 5, "$")); @@ -2279,7 +2279,7 @@ int main(void) tt_resize(t, 20, 6); assert(tt_cursor_y(t) == 5 && tt_history(t) == 0); assert(row_is(t, 0, "one") && row_is(t, 5, "$")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(20, 6); write_seq(t, "a\r\nb\r\nc\r\nd\r\ne\r\n"); @@ -2291,7 +2291,7 @@ int main(void) assert(tt_history(t) == before); write_seq(t, "\033[?1049l"); assert(row_is(t, 0, "a") && row_is(t, 4, "e")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(40, 6); write_seq(t, "\033[?1049h\033[1;38Hxy"); @@ -2300,7 +2300,7 @@ int main(void) assert(tt_cursor_x(t) < tt_cols(t)); write_seq(t, "Q"); assert(tt_cell(t, tt_cursor_x(t) - 1, tt_cursor_y(t))->text == 'Q'); - term_free(t); + wsap_vtcore_free(t); t = tt_new(8, 4); write_seq(t, "abcdefghijkl"); @@ -2313,7 +2313,7 @@ int main(void) text = tt_selection_text(t); assert(text && !strcmp(text, "abcd\nefgh")); free(text); - term_free(t); + wsap_vtcore_free(t); t = tt_new(10, 4); write_seq(t, "abcdef"); @@ -2326,7 +2326,7 @@ int main(void) write_seq(t, "\033[10P"); assert(row_is(t, 0, "ab")); assert(tt_cursor_x(t) == 2 && tt_cursor_y(t) == 0); - term_free(t); + wsap_vtcore_free(t); t = tt_new(8, 4); write_seq(t, "abcdef"); @@ -2335,87 +2335,87 @@ int main(void) assert(tt_cursor_x(t) == 2 && tt_cursor_y(t) == 0); write_seq(t, "\033[2@"); assert(row_is(t, 0, "ab cde")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(10, 4); - assert(term_cursor(t).style == TERM_CURSOR_BLOCK); - assert(term_cursor(t).blink == true); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BLOCK); + assert(wsap_vtcore_cursor(t).blink == true); write_seq(t, "\033[2 q"); - assert(term_cursor(t).style == TERM_CURSOR_BLOCK); - assert(term_cursor(t).blink == false); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BLOCK); + assert(wsap_vtcore_cursor(t).blink == false); write_seq(t, "\033[3 q"); - assert(term_cursor(t).style == TERM_CURSOR_UNDERLINE); - assert(term_cursor(t).blink == true); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_UNDERLINE); + assert(wsap_vtcore_cursor(t).blink == true); write_seq(t, "\033[4 q"); - assert(term_cursor(t).style == TERM_CURSOR_UNDERLINE); - assert(term_cursor(t).blink == false); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_UNDERLINE); + assert(wsap_vtcore_cursor(t).blink == false); write_seq(t, "\033[5 q"); - assert(term_cursor(t).style == TERM_CURSOR_BAR); - assert(term_cursor(t).blink == true); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BAR); + assert(wsap_vtcore_cursor(t).blink == true); write_seq(t, "\033[6 q"); - assert(term_cursor(t).style == TERM_CURSOR_BAR); - assert(term_cursor(t).blink == false); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BAR); + assert(wsap_vtcore_cursor(t).blink == false); write_seq(t, "\033[0 q"); - assert(term_cursor(t).style == TERM_CURSOR_BLOCK); - assert(term_cursor(t).blink == true); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BLOCK); + assert(wsap_vtcore_cursor(t).blink == true); write_seq(t, "\033[5 q"); write_seq(t, "\033[ q"); - assert(term_cursor(t).style == TERM_CURSOR_BLOCK); - assert(term_cursor(t).blink == true); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BLOCK); + assert(wsap_vtcore_cursor(t).blink == true); write_seq(t, "\033[6 q"); - assert(term_cursor(t).style == TERM_CURSOR_BAR && !term_cursor(t).blink); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BAR && !wsap_vtcore_cursor(t).blink); write_seq(t, "\033[?1049h"); write_seq(t, "\033[3 q"); - assert(term_cursor(t).style == TERM_CURSOR_UNDERLINE && term_cursor(t).blink); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_UNDERLINE && wsap_vtcore_cursor(t).blink); write_seq(t, "\033[?1049l"); - assert(term_cursor(t).style == TERM_CURSOR_BAR && !term_cursor(t).blink); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BAR && !wsap_vtcore_cursor(t).blink); - term_set_cursor_default(t, TERM_CURSOR_UNDERLINE, true); + wsap_vtcore_set_cursor_default(t, WSAP_VTCORE_CURSOR_UNDERLINE, true); write_seq(t, "\033[5 q"); - assert(term_cursor(t).style == TERM_CURSOR_BAR && term_cursor(t).blink); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BAR && wsap_vtcore_cursor(t).blink); write_seq(t, "\033[0 q"); - assert(term_cursor(t).style == TERM_CURSOR_UNDERLINE && !term_cursor(t).blink); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_UNDERLINE && !wsap_vtcore_cursor(t).blink); write_seq(t, "\033[2 q"); - assert(term_cursor(t).style == TERM_CURSOR_BLOCK && !term_cursor(t).blink); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BLOCK && !wsap_vtcore_cursor(t).blink); write_seq(t, "\033[ q"); - assert(term_cursor(t).style == TERM_CURSOR_UNDERLINE && !term_cursor(t).blink); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_UNDERLINE && !wsap_vtcore_cursor(t).blink); write_seq(t, "\033[1 q"); - assert(term_cursor(t).style == TERM_CURSOR_BLOCK && term_cursor(t).blink); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_BLOCK && wsap_vtcore_cursor(t).blink); write_seq(t, "\033[!p"); - assert(term_cursor(t).style == TERM_CURSOR_UNDERLINE && !term_cursor(t).blink); - term_free(t); + assert(wsap_vtcore_cursor(t).style == WSAP_VTCORE_CURSOR_UNDERLINE && !wsap_vtcore_cursor(t).blink); + wsap_vtcore_free(t); t = tt_new(20, 4); write_seq(t, "\033[1;2;3;4;9;53mA\033[21mB\033[4:2mC\033[22;24mD\033[0mE"); - const uint16_t styles = TERM_ATTR_BOLD | TERM_ATTR_FAINT | TERM_ATTR_ITALIC | - TERM_ATTR_STRIKE | TERM_ATTR_OVERLINE; + const uint16_t styles = WSAP_VTCORE_ATTR_BOLD | WSAP_VTCORE_ATTR_FAINT | WSAP_VTCORE_ATTR_ITALIC | + WSAP_VTCORE_ATTR_STRIKE | WSAP_VTCORE_ATTR_OVERLINE; assert((tt_cell(t, 0, 0)->attrs & styles) == styles); - assert(term_attr_underline(tt_cell(t, 0, 0)->attrs) == TERM_UNDERLINE_SINGLE); - assert(term_attr_underline(tt_cell(t, 1, 0)->attrs) == TERM_UNDERLINE_DOUBLE); - assert(term_attr_underline(tt_cell(t, 2, 0)->attrs) == TERM_UNDERLINE_DOUBLE); - assert(!(tt_cell(t, 3, 0)->attrs & (TERM_ATTR_BOLD | TERM_ATTR_FAINT))); - assert(term_attr_underline(tt_cell(t, 3, 0)->attrs) == TERM_UNDERLINE_NONE); + assert(wsap_vtcore_attr_underline(tt_cell(t, 0, 0)->attrs) == WSAP_VTCORE_UNDERLINE_SINGLE); + assert(wsap_vtcore_attr_underline(tt_cell(t, 1, 0)->attrs) == WSAP_VTCORE_UNDERLINE_DOUBLE); + assert(wsap_vtcore_attr_underline(tt_cell(t, 2, 0)->attrs) == WSAP_VTCORE_UNDERLINE_DOUBLE); + assert(!(tt_cell(t, 3, 0)->attrs & (WSAP_VTCORE_ATTR_BOLD | WSAP_VTCORE_ATTR_FAINT))); + assert(wsap_vtcore_attr_underline(tt_cell(t, 3, 0)->attrs) == WSAP_VTCORE_UNDERLINE_NONE); assert(tt_cell(t, 4, 0)->attrs == 0); - term_free(t); + wsap_vtcore_free(t); t = tt_new(20, 4); write_seq(t, "\033[30mA\033[0;1;30mB\033[0;90mC"); assert(tt_cell(t, 0, 0)->fg == tt_cell(t, 1, 0)->fg); assert(tt_cell(t, 1, 0)->fg != tt_cell(t, 2, 0)->fg); - assert(!(tt_cell(t, 0, 0)->attrs & TERM_ATTR_BOLD)); - assert(tt_cell(t, 1, 0)->attrs & TERM_ATTR_BOLD); - term_free(t); + assert(!(tt_cell(t, 0, 0)->attrs & WSAP_VTCORE_ATTR_BOLD)); + assert(tt_cell(t, 1, 0)->attrs & WSAP_VTCORE_ATTR_BOLD); + wsap_vtcore_free(t); const char *colon_rgb = "\033[48;2;145;2;34m\033[38;2;12;34;56mA" "\033[38:2::12:34:56mB\033[;mC"; @@ -2428,16 +2428,16 @@ int main(void) assert(tt_cell(t, x, 0)->fg == 0xFF0C2238); assert(tt_cell(t, x, 0)->bg == 0xFF910222); } - assert(tt_cell(t, 2, 0)->fg == TERM_COLOR_FG); - assert(tt_cell(t, 2, 0)->bg == TERM_COLOR_BG); - term_free(t); + assert(tt_cell(t, 2, 0)->fg == WSAP_VTCORE_COLOR_FG); + assert(tt_cell(t, 2, 0)->bg == WSAP_VTCORE_COLOR_BG); + wsap_vtcore_free(t); } t = tt_new(20, 4); write_seq(t, "\033[38;2;246;226;183;49mX"); assert(tt_cell(t, 0, 0)->fg == 0xFFF6E2B7); - assert(tt_cell(t, 0, 0)->bg == TERM_COLOR_BG); - term_free(t); + assert(tt_cell(t, 0, 0)->bg == WSAP_VTCORE_COLOR_BG); + wsap_vtcore_free(t); t = tt_new(20, 4); const char *clusters = "(\xc2\xa9\xef\xb8\x8f)\xe2\x98\xba\xef\xb8\x8e" @@ -2445,17 +2445,17 @@ int main(void) write_seq(t, clusters); assert(tt_cursor_x(t) == 7); - assert((tt_cell(t, 1, 0)->attrs & TERM_ATTR_EMOJI) && tt_cell(t, 1, 0)->width == 2); + assert((tt_cell(t, 1, 0)->attrs & WSAP_VTCORE_ATTR_EMOJI) && tt_cell(t, 1, 0)->width == 2); assert(tt_cell(t, 2, 0)->width == 0); - assert((tt_cell(t, 4, 0)->attrs & TERM_ATTR_TEXT) && tt_cell(t, 4, 0)->width == 1); - assert((tt_cell(t, 5, 0)->attrs & TERM_ATTR_EMOJI) && tt_cell(t, 5, 0)->width == 2); + assert((tt_cell(t, 4, 0)->attrs & WSAP_VTCORE_ATTR_TEXT) && tt_cell(t, 4, 0)->width == 1); + assert((tt_cell(t, 5, 0)->attrs & WSAP_VTCORE_ATTR_EMOJI) && tt_cell(t, 5, 0)->width == 2); assert(tt_cell(t, 6, 0)->width == 0); tt_select(t, 0, 0, 6, 0); text = tt_selection_text(t); assert(text && !strcmp(text, clusters)); free(text); - term_free(t); + wsap_vtcore_free(t); /* BS with a pending wrap clears the wrap and moves left from the last * column, as in xterm and the VT100. */ @@ -2471,11 +2471,11 @@ int main(void) write_seq(t, "\b \b"); assert(row_is(t, 0, "123 5")); assert(tt_cursor_x(t) == 3 && tt_cursor_y(t) == 0); - term_free(t); + wsap_vtcore_free(t); /* A renderer sees each cursor move within the row. */ t = tt_new(10, 2); - struct term_snapshot *snap = term_snapshot_new(); + struct wsap_vtcore_snapshot *snap = wsap_vtcore_snapshot_new(); write_seq(t, "abc"); uint64_t version = view_version(snap, t); write_seq(t, "\b"); @@ -2486,14 +2486,14 @@ int main(void) version = view_version(snap, t); write_seq(t, "\t"); assert(tt_cursor_x(t) == 8 && view_version(snap, t) != version); - term_snapshot_free(snap); - term_free(t); + wsap_vtcore_snapshot_free(snap); + wsap_vtcore_free(t); t = tt_new(20, 2); tt_write(t, "hello world", 11); assert(row_is(t, 0, "hello world")); assert(tt_cursor_x(t) == 11 && tt_cursor_y(t) == 0); - term_free(t); + wsap_vtcore_free(t); title[0] = 0; t = tt_new_opts(10, 4, &title_cb); @@ -2503,18 +2503,18 @@ int main(void) assert(!strcmp(title, "Second Title")); write_seq(t, "\033]1;Icon Name\007"); assert(!strcmp(title, "Icon Name")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(20, 4); write_seq(t, "$ /mnt/work"); const char *round_trip = "\033[?1049h\033[?1049l"; tt_write(t, round_trip, strlen(round_trip)); assert(row_is(t, 0, "$ /mnt/work")); - term_free(t); + wsap_vtcore_free(t); /* A renderer sees both switches between the screens. */ t = tt_new(20, 4); - snap = term_snapshot_new(); + snap = wsap_vtcore_snapshot_new(); write_seq(t, "$ /mnt/work"); version = view_version(snap, t); write_seq(t, "\033[?1049h"); @@ -2523,22 +2523,22 @@ int main(void) write_seq(t, "\033[?1049l"); assert(view_version(snap, t) != version); assert(row_is(t, 0, "$ /mnt/work")); - term_snapshot_free(snap); - term_free(t); + wsap_vtcore_snapshot_free(snap); + wsap_vtcore_free(t); t = tt_new(20, 4); write_seq(t, "output"); write_seq(t, "\r\033[K../"); assert(row_is(t, 0, "../")); - term_free(t); + wsap_vtcore_free(t); t = tt_new(80, 24); - assert(!term_modes(t).alternate); + assert(!wsap_vtcore_modes(t).alternate); write_seq(t, "\033[?1049h"); - assert(term_modes(t).alternate); + assert(wsap_vtcore_modes(t).alternate); write_seq(t, "\033[?1049l"); - assert(!term_modes(t).alternate); - term_free(t); + assert(!wsap_vtcore_modes(t).alternate); + wsap_vtcore_free(t); const char *color_runs[] = { "\033[1;1H\033[48;2;10;20;30m\033[38;2;200;210;220ma" @@ -2560,9 +2560,9 @@ int main(void) assert(tt_cell(t, 1, 0)->fg == 0xffe6f0fa); assert(tt_cell(t, 1, 0)->bg == 0xff646e78); for (int col = 2; col < 100; col++) - assert(tt_cell(t, col, 0)->bg == TERM_COLOR_BG); + assert(tt_cell(t, col, 0)->bg == WSAP_VTCORE_COLOR_BG); assert(row_is(t, 1, "")); - term_free(t); + wsap_vtcore_free(t); } } diff --git a/tests/unicode/unicode_test.c b/tests/unicode/unicode_test.c index e3cf5a7..dd6534b 100644 --- a/tests/unicode/unicode_test.c +++ b/tests/unicode/unicode_test.c @@ -1,4 +1,4 @@ -#include "term/unicode/utf8.h" +#include "wsap_vtcore/unicode/utf8.h" #include <assert.h> #include <stdio.h> #include <string.h> @@ -16,17 +16,17 @@ static void test_utf8_decode_one(void) for (size_t i = 0; i < sizeof(valid) / sizeof(*valid); i++) { uint32_t cp = 0xdeadbeef; for (int n = 0; n < valid[i].len; n++) { - int r = term_utf8_decode_one(valid[i].bytes, n, &cp); + int r = wsap_vtcore_utf8_decode_one(valid[i].bytes, n, &cp); assert(r == 0); assert(cp == 0xdeadbeef); } - int r = term_utf8_decode_one(valid[i].bytes, valid[i].len, &cp); + int r = wsap_vtcore_utf8_decode_one(valid[i].bytes, valid[i].len, &cp); assert(r == valid[i].len); assert(cp == valid[i].cp); char followed[8]; memcpy(followed, valid[i].bytes, valid[i].len); memcpy(followed + valid[i].len, "next", 4); - r = term_utf8_decode_one(followed, valid[i].len + 4, &cp); + r = wsap_vtcore_utf8_decode_one(followed, valid[i].len + 4, &cp); assert(r == valid[i].len); assert(cp == valid[i].cp); } @@ -38,7 +38,7 @@ static void test_utf8_decode_one(void) }; for (size_t i = 0; i < sizeof(invalid) / sizeof(*invalid); i++) { uint32_t cp = 0xdeadbeef; - int r = term_utf8_decode_one(invalid[i], strlen(invalid[i]), &cp); + int r = wsap_vtcore_utf8_decode_one(invalid[i], strlen(invalid[i]), &cp); assert(r == 0); assert(cp == 0xdeadbeef); } @@ -48,24 +48,24 @@ static void test_scalar_roundtrips(void) { for (uint32_t cp = 0; cp <= 0x10ffff; cp++) { if (cp >= 0xd800 && cp <= 0xdfff) continue; - char bytes[TERM_UTF8_MAX_BYTES]; - int len = term_utf8_encode(cp, bytes); - uint32_t scalar = 0, streamed = 0, state = TERM_UTF8_ACCEPT; - int r = term_utf8_decode_one(bytes, (size_t)len, &scalar); + char bytes[WSAP_VTCORE_UTF8_MAX_BYTES]; + int len = wsap_vtcore_utf8_encode(cp, bytes); + uint32_t scalar = 0, streamed = 0, state = WSAP_VTCORE_UTF8_ACCEPT; + int r = wsap_vtcore_utf8_decode_one(bytes, (size_t)len, &scalar); assert(r == len); assert(scalar == cp); for (int i = 0; i < len; i++) { - term_utf8_decode(&state, &streamed, (unsigned char)bytes[i]); - if (i + 1 < len) assert(state != TERM_UTF8_ACCEPT && state != TERM_UTF8_REJECT); + wsap_vtcore_utf8_decode(&state, &streamed, (unsigned char)bytes[i]); + if (i + 1 < len) assert(state != WSAP_VTCORE_UTF8_ACCEPT && state != WSAP_VTCORE_UTF8_REJECT); } - assert(state == TERM_UTF8_ACCEPT && streamed == cp); + assert(state == WSAP_VTCORE_UTF8_ACCEPT && streamed == cp); } static const uint32_t invalid[] = {0xd800, 0xdfff, 0x110000, UINT32_MAX}; for (size_t i = 0; i < sizeof(invalid) / sizeof(*invalid); i++) { - char bytes[TERM_UTF8_MAX_BYTES]; - int len = term_utf8_encode(invalid[i], bytes); + char bytes[WSAP_VTCORE_UTF8_MAX_BYTES]; + int len = wsap_vtcore_utf8_encode(invalid[i], bytes); uint32_t cp = 0; - int r = term_utf8_decode_one(bytes, len, &cp); + int r = wsap_vtcore_utf8_decode_one(bytes, len, &cp); assert(len == 3 && r == len && cp == 0xfffd); } } @@ -74,26 +74,26 @@ static void test_utf8_sanitize(void) { char dst[64]; - term_utf8_sanitize(dst, sizeof(dst), "hello \xe2\x82\xac\xf0\x9f\x98\x80"); + wsap_vtcore_utf8_sanitize(dst, sizeof(dst), "hello \xe2\x82\xac\xf0\x9f\x98\x80"); assert(!strcmp(dst, "hello \xe2\x82\xac\xf0\x9f\x98\x80")); - term_utf8_sanitize(dst, sizeof(dst), "a\xff\x80" "b\xed\xa0\x80" "c\xe2\x82"); + wsap_vtcore_utf8_sanitize(dst, sizeof(dst), "a\xff\x80" "b\xed\xa0\x80" "c\xe2\x82"); assert(!strcmp(dst, "abc")); - term_utf8_sanitize(dst, sizeof(dst), ""); + wsap_vtcore_utf8_sanitize(dst, sizeof(dst), ""); assert(!strcmp(dst, "")); - term_utf8_sanitize(dst, sizeof(dst), "\xff\xfe"); + wsap_vtcore_utf8_sanitize(dst, sizeof(dst), "\xff\xfe"); assert(!strcmp(dst, "")); - term_utf8_sanitize(dst, 6, "ab\xe2\x82\xac" "cd"); + wsap_vtcore_utf8_sanitize(dst, 6, "ab\xe2\x82\xac" "cd"); assert(!strcmp(dst, "ab\xe2\x82\xac")); - term_utf8_sanitize(dst, 5, "ab\xe2\x82\xac" "cd"); + wsap_vtcore_utf8_sanitize(dst, 5, "ab\xe2\x82\xac" "cd"); assert(!strcmp(dst, "abcd")); memset(dst, 'x', sizeof(dst)); - term_utf8_sanitize(dst, 4, "abcdef"); + wsap_vtcore_utf8_sanitize(dst, 4, "abcdef"); assert(!strcmp(dst, "abc")); memset(dst, 'x', sizeof(dst)); - term_utf8_sanitize(dst, 0, "abc"); + wsap_vtcore_utf8_sanitize(dst, 0, "abc"); assert(dst[0] == 'x'); } @@ -101,30 +101,30 @@ static void test_utf8_sanitize(void) * stays unused. */ static void test_ground_invalid_subparts(void) { - uint32_t state = TERM_UTF8_ACCEPT, codep = 0, cp = 0xdead; - int n = term_utf8_decode_ground(&state, &codep, "\xe2\x80\x1b\xac", 4, &cp); + uint32_t state = WSAP_VTCORE_UTF8_ACCEPT, codep = 0, cp = 0xdead; + int n = wsap_vtcore_utf8_decode_ground(&state, &codep, "\xe2\x80\x1b\xac", 4, &cp); assert(n == 2); assert(cp == 0xFFFD); - assert(state == TERM_UTF8_ACCEPT); - n = term_utf8_decode_ground(&state, &codep, "\xac", 1, &cp); + assert(state == WSAP_VTCORE_UTF8_ACCEPT); + n = wsap_vtcore_utf8_decode_ground(&state, &codep, "\xac", 1, &cp); assert(n == 1); assert(cp == 0xFFFD); - assert(state == TERM_UTF8_ACCEPT); - n = term_utf8_decode_ground(&state, &codep, "\xe2\x82z", 3, &cp); + assert(state == WSAP_VTCORE_UTF8_ACCEPT); + n = wsap_vtcore_utf8_decode_ground(&state, &codep, "\xe2\x82z", 3, &cp); assert(n == 2); assert(cp == 0xFFFD); - assert(state == TERM_UTF8_ACCEPT); - n = term_utf8_decode_ground(&state, &codep, "\xe2\x82", 2, &cp); + assert(state == WSAP_VTCORE_UTF8_ACCEPT); + n = wsap_vtcore_utf8_decode_ground(&state, &codep, "\xe2\x82", 2, &cp); assert(n == 2); assert(cp == 0); - assert(state != TERM_UTF8_ACCEPT); + assert(state != WSAP_VTCORE_UTF8_ACCEPT); - state = TERM_UTF8_ACCEPT; + state = WSAP_VTCORE_UTF8_ACCEPT; codep = 0; - n = term_utf8_decode_ground(&state, &codep, "\xe2\x82\xac", 3, &cp); + n = wsap_vtcore_utf8_decode_ground(&state, &codep, "\xe2\x82\xac", 3, &cp); assert(n == 3); assert(cp == 0x20ac); - assert(state == TERM_UTF8_ACCEPT); + assert(state == WSAP_VTCORE_UTF8_ACCEPT); } int main(void) diff --git a/tests/version_test.c b/tests/version_test.c index 0eb889e..9893e2f 100644 --- a/tests/version_test.c +++ b/tests/version_test.c @@ -1,27 +1,27 @@ -#include "term/term.h" +#include "wsap_vtcore/wsap_vtcore.h" #include <assert.h> #include <stdio.h> #include <string.h> /* The project version from meson.build. The build defines it. */ -#ifndef TERM_TEST_PROJECT_VERSION -#error "define TERM_TEST_PROJECT_VERSION as the project version, such as \"0.1.0\"" +#ifndef WSAP_VTCORE_TEST_PROJECT_VERSION +#error "define WSAP_VTCORE_TEST_PROJECT_VERSION as the project version, such as \"0.1.0\"" #endif int main(void) { char text[32]; snprintf(text, sizeof(text), "%d.%d.%d", - TERM_VERSION_MAJOR, TERM_VERSION_MINOR, TERM_VERSION_PATCH); - assert(!strcmp(text, TERM_TEST_PROJECT_VERSION)); + WSAP_VTCORE_VERSION_MAJOR, WSAP_VTCORE_VERSION_MINOR, WSAP_VTCORE_VERSION_PATCH); + assert(!strcmp(text, WSAP_VTCORE_TEST_PROJECT_VERSION)); int major, minor, patch; - assert(sscanf(TERM_TEST_PROJECT_VERSION, "%d.%d.%d", &major, &minor, &patch) == 3); - assert(TERM_VERSION_CODE == TERM_VERSION(major, minor, patch)); - assert(term_version() == TERM_VERSION_CODE); + assert(sscanf(WSAP_VTCORE_TEST_PROJECT_VERSION, "%d.%d.%d", &major, &minor, &patch) == 3); + assert(WSAP_VTCORE_VERSION_CODE == WSAP_VTCORE_VERSION(major, minor, patch)); + assert(wsap_vtcore_version() == WSAP_VTCORE_VERSION_CODE); - assert(TERM_VERSION(0, 2, 0) > TERM_VERSION(0, 1, 255)); - assert(TERM_VERSION(1, 0, 0) > TERM_VERSION(0, 255, 255)); + assert(WSAP_VTCORE_VERSION(0, 2, 0) > WSAP_VTCORE_VERSION(0, 1, 255)); + assert(WSAP_VTCORE_VERSION(1, 0, 0) > WSAP_VTCORE_VERSION(0, 255, 255)); return 0; } diff --git a/tests/view_test.c b/tests/view_test.c index 5e17450..02eeede 100644 --- a/tests/view_test.c +++ b/tests/view_test.c @@ -16,9 +16,9 @@ #define VIEW_TEXT_CAP 256 /* The text of a view row, trailing blanks cut. */ -static void view_row_text(struct term *t, int row, char *buf, size_t cap) +static void view_row_text(struct wsap_vtcore *t, int row, char *buf, size_t cap) { - const struct term_cell *cells = term_snapshot_row(tt_snapshot_for(t), row); + const struct wsap_vtcore_cell *cells = wsap_vtcore_snapshot_row(tt_snapshot_for(t), row); size_t n = 0; for (int c = 0; c < tt_cols(t) && n + 1 < cap; c++) { uint32_t cp = tt_cell_cp(t, &cells[c]); @@ -29,7 +29,7 @@ static void view_row_text(struct term *t, int row, char *buf, size_t cap) buf[n] = 0; } -static bool view_row_is(struct term *t, int row, const char *want) +static bool view_row_is(struct wsap_vtcore *t, int row, const char *want) { char got[VIEW_TEXT_CAP]; view_row_text(t, row, got, sizeof(got)); @@ -38,7 +38,7 @@ static bool view_row_is(struct term *t, int row, const char *want) /* Every view row holds the text of the same row in want. A view row that * resolves to no row at all fails the text compare. */ -static void assert_view_rows_equal(struct term *t, struct term *want) +static void assert_view_rows_equal(struct wsap_vtcore *t, struct wsap_vtcore *want) { for (int row = 0; row < tt_rows(t); row++) { char got[VIEW_TEXT_CAP], expect[VIEW_TEXT_CAP]; @@ -51,30 +51,30 @@ static void assert_view_rows_equal(struct term *t, struct term *want) /* The view offset, in range, and the same as the snapshot reports. The two * must come from one field: a second copy of the offset is what let the * scrollbar and the rows disagree. */ -static void assert_offset_agrees(struct term *t) +static void assert_offset_agrees(struct wsap_vtcore *t) { - const struct term_view *v = term_snapshot_view(tt_snapshot_for(t)); - struct term_scrollback sb = term_scrollback(t); + const struct wsap_vtcore_view *v = wsap_vtcore_snapshot_view(tt_snapshot_for(t)); + struct wsap_vtcore_scrollback sb = wsap_vtcore_scrollback(t); assert(sb.offset == v->scroll_offset); assert(sb.offset >= 0); assert(sb.offset <= sb.total); } /* A terminal whose history is small enough to fill. */ -static struct term *small_history_term(int cols, int rows, int scrollback) +static struct wsap_vtcore *small_history_term(int cols, int rows, int scrollback) { - struct term_options opt = { + struct wsap_vtcore_options opt = { .size = { .x = cols, .y = rows }, .scrollback = scrollback, }; - struct term *t = term_new(&opt); + struct wsap_vtcore *t = wsap_vtcore_new(&opt); assert(t); return t; } /* Fill the history with count lines of "Lnn" and leave the cursor on the * last screen row. */ -static void feed_lines(struct term *t, const char *tag, int count) +static void feed_lines(struct wsap_vtcore *t, const char *tag, int count) { char line[64]; for (int i = 0; i < count; i++) { @@ -87,12 +87,12 @@ static void feed_lines(struct term *t, const char *tag, int count) * on the same text. */ static void view_holds_text_while_output_arrives(void) { - struct term *t = tt_new(12, 5); - struct term *reference = tt_new(12, 5); + struct wsap_vtcore *t = tt_new(12, 5); + struct wsap_vtcore *reference = tt_new(12, 5); feed_lines(t, "L", 15); feed_lines(reference, "L", 15); - term_scroll(t, 2); - term_scroll(reference, 2); + wsap_vtcore_scroll(t, 2); + wsap_vtcore_scroll(reference, 2); assert(tt_view_offset(t) == 2); assert_view_rows_equal(t, reference); @@ -101,8 +101,8 @@ static void view_holds_text_while_output_arrives(void) assert_offset_agrees(t); /* Nothing was evicted, so the view still shows the rows it showed. */ assert_view_rows_equal(t, reference); - term_free(t); - term_free(reference); + wsap_vtcore_free(t); + wsap_vtcore_free(reference); } /* A view that sits at the top of the history keeps the oldest text there @@ -111,12 +111,12 @@ static void view_holds_text_while_output_arrives(void) static void view_at_the_top_keeps_the_oldest_text(void) { const int scrollback = 20; - struct term *t = small_history_term(12, 5, scrollback); - struct term *reference = small_history_term(12, 5, scrollback); + struct wsap_vtcore *t = small_history_term(12, 5, scrollback); + struct wsap_vtcore *reference = small_history_term(12, 5, scrollback); feed_lines(t, "L", 12); feed_lines(reference, "L", 12); - term_scroll_to(t, INT_MAX); - term_scroll_to(reference, INT_MAX); + wsap_vtcore_scroll_to(t, INT_MAX); + wsap_vtcore_scroll_to(reference, INT_MAX); int total = tt_history(t); assert(total > 0 && total + tt_rows(t) <= scrollback); assert(tt_view_offset(t) == total); @@ -131,8 +131,8 @@ static void view_at_the_top_keeps_the_oldest_text(void) assert(tt_view_offset(t) == total + 3); assert(view_row_is(t, 0, "L00")); assert_view_rows_equal(t, reference); - term_free(t); - term_free(reference); + wsap_vtcore_free(t); + wsap_vtcore_free(reference); } /* Output larger than the history evicts the rows the view was anchored to. @@ -141,11 +141,11 @@ static void view_at_the_top_keeps_the_oldest_text(void) static void view_survives_output_larger_than_history(void) { const int scrollback = 20; - struct term *t = small_history_term(12, 5, scrollback); - struct term *reference = small_history_term(12, 5, scrollback); + struct wsap_vtcore *t = small_history_term(12, 5, scrollback); + struct wsap_vtcore *reference = small_history_term(12, 5, scrollback); feed_lines(t, "L", 15); feed_lines(reference, "L", 15); - term_scroll(t, 3); + wsap_vtcore_scroll(t, 3); feed_lines(t, "M", 40); feed_lines(reference, "M", 40); @@ -155,12 +155,12 @@ static void view_survives_output_larger_than_history(void) assert(tt_view_offset(t) > 0); /* The top of the history is where the view ends up. */ - term_scroll(reference, INT_MAX); + wsap_vtcore_scroll(reference, INT_MAX); assert(tt_view_offset(reference) == tt_history(reference)); assert(tt_view_offset(t) == tt_history(t)); assert_view_rows_equal(t, reference); - term_free(t); - term_free(reference); + wsap_vtcore_free(t); + wsap_vtcore_free(reference); } /* An eviction can drop a line that wraps to more rows than the push adds. @@ -169,16 +169,16 @@ static void view_survives_output_larger_than_history(void) static void view_survives_eviction_of_a_wrapped_line(void) { const int scrollback = 20; - struct term *t = small_history_term(12, 5, scrollback); - struct term *reference = small_history_term(12, 5, scrollback); + struct wsap_vtcore *t = small_history_term(12, 5, scrollback); + struct wsap_vtcore *reference = small_history_term(12, 5, scrollback); /* The oldest line wraps to three rows. */ const char *wrapped = "0123456789012345678901234\r\n"; tt_puts(t, wrapped); tt_puts(reference, wrapped); feed_lines(t, "s", 22); feed_lines(reference, "s", 22); - term_scroll_to(t, INT_MAX); - term_scroll_to(reference, INT_MAX); + wsap_vtcore_scroll_to(t, INT_MAX); + wsap_vtcore_scroll_to(reference, INT_MAX); assert_offset_agrees(t); /* The next line evicts the wrapped one: three rows go, one arrives. */ @@ -189,11 +189,11 @@ static void view_survives_eviction_of_a_wrapped_line(void) assert(tt_view_offset(t) <= tt_history(t)); } /* The view sits on the oldest text the terminal still keeps. */ - term_scroll_to(reference, INT_MAX); + wsap_vtcore_scroll_to(reference, INT_MAX); assert(tt_view_offset(t) == tt_view_offset(reference)); assert_view_rows_equal(t, reference); - term_free(t); - term_free(reference); + wsap_vtcore_free(t); + wsap_vtcore_free(reference); } /* A resize keeps the same retained text at the top of the view. */ @@ -203,21 +203,21 @@ static void view_keeps_anchor_on_resize(void) int cols, rows; } sizes[] = { { 12, 6 }, { 20, 5 }, { 6, 5 } }; for (size_t i = 0; i < sizeof(sizes) / sizeof(sizes[0]); i++) { - struct term *t = tt_new(12, 5); - struct term *reference = tt_new(12, 5); + struct wsap_vtcore *t = tt_new(12, 5); + struct wsap_vtcore *reference = tt_new(12, 5); feed_lines(t, "L", 15); feed_lines(reference, "L", 15); - term_scroll(t, 3); + wsap_vtcore_scroll(t, 3); assert(tt_view_offset(t) == 3); assert(tt_resize(t, sizes[i].cols, sizes[i].rows)); assert(tt_resize(reference, sizes[i].cols, sizes[i].rows)); assert_offset_agrees(t); assert(tt_view_offset(t) > 0); assert(view_row_is(t, 0, "L08")); - term_scroll_to(t, 0); + wsap_vtcore_scroll_to(t, 0); assert_view_rows_equal(t, reference); - term_free(t); - term_free(reference); + wsap_vtcore_free(t); + wsap_vtcore_free(reference); } } @@ -225,9 +225,9 @@ static void view_keeps_anchor_on_resize(void) * back at its own bottom. */ static void view_follows_the_alternate_screen(void) { - struct term *t = tt_new(12, 5); + struct wsap_vtcore *t = tt_new(12, 5); feed_lines(t, "L", 15); - term_scroll(t, 3); + wsap_vtcore_scroll(t, 3); assert(tt_view_offset(t) == 3); tt_puts(t, "\033[?1049hALT"); @@ -239,66 +239,66 @@ static void view_follows_the_alternate_screen(void) assert_offset_agrees(t); assert(tt_view_offset(t) == 0); assert(view_row_is(t, 0, "L11")); - term_free(t); + wsap_vtcore_free(t); } /* The view offset has one owner. Every operation that moves or clears the * view leaves the public offset and the snapshot offset equal. */ static void view_offset_has_one_owner(void) { - struct term *t = tt_new(12, 5); + struct wsap_vtcore *t = tt_new(12, 5); feed_lines(t, "L", 15); assert_offset_agrees(t); - term_scroll(t, 3); + wsap_vtcore_scroll(t, 3); assert_offset_agrees(t); - term_scroll_to(t, INT_MAX); + wsap_vtcore_scroll_to(t, INT_MAX); assert_offset_agrees(t); assert(tt_view_offset(t) == tt_history(t)); - term_scroll(t, INT_MIN); + wsap_vtcore_scroll(t, INT_MIN); assert_offset_agrees(t); assert(tt_view_offset(t) == 0); - term_free(t); + wsap_vtcore_free(t); } /* ED2 and ED3 return the view to the live screen. RIS keeps the offset, as * it did before the view had an anchor of its own. */ static void view_returns_to_bottom_on_erase(void) { - struct term *t = tt_new(12, 5); + struct wsap_vtcore *t = tt_new(12, 5); feed_lines(t, "L", 15); - term_scroll(t, 3); + wsap_vtcore_scroll(t, 3); assert(tt_view_offset(t) == 3); tt_puts(t, "\033[2J"); assert_offset_agrees(t); assert(tt_view_offset(t) == 0); - term_scroll(t, 2); + wsap_vtcore_scroll(t, 2); assert(tt_view_offset(t) == 2); tt_puts(t, "\033[3J"); assert_offset_agrees(t); assert(tt_view_offset(t) == 0); assert(tt_history(t) == 0); - term_free(t); + wsap_vtcore_free(t); t = tt_new(12, 5); feed_lines(t, "L", 15); - term_scroll(t, 3); + wsap_vtcore_scroll(t, 3); int before = tt_view_offset(t); tt_puts(t, "\033c"); assert_offset_agrees(t); assert(tt_view_offset(t) == before); - term_free(t); + wsap_vtcore_free(t); } /* Rewrap keeps the cell that selected the anchored segment in view. */ static void wrapped_anchor_survives_resize(void) { - struct term *t = tt_new(10, 3); + struct wsap_vtcore *t = tt_new(10, 3); tt_puts(t, "abcdefghijKLMNOPQRSTuvwxyz\r\n"); feed_lines(t, "L", 10); - term_scroll_to(t, INT_MAX); - term_scroll(t, -1); + wsap_vtcore_scroll_to(t, INT_MAX); + wsap_vtcore_scroll(t, -1); assert(view_row_is(t, 0, "KLMNOPQRST")); tt_select(t, 0, 0, 2, 0); char *selected = tt_selection_text(t); @@ -317,17 +317,17 @@ static void wrapped_anchor_survives_resize(void) assert(tt_resize(t, 6, 3)); assert(view_row_is(t, 0, "ghijKL")); assert_offset_agrees(t); - term_free(t); + wsap_vtcore_free(t); } /* A wide glyph leaves a wrap pad. That pad does not move the anchor. */ static void wide_anchor_survives_resize(void) { - struct term *t = tt_new(5, 3); + struct wsap_vtcore *t = tt_new(5, 3); tt_puts(t, "abcd日本語XYZ\r\n"); feed_lines(t, "L", 10); - term_scroll_to(t, INT_MAX); - term_scroll(t, -1); + wsap_vtcore_scroll_to(t, INT_MAX); + wsap_vtcore_scroll(t, -1); assert(tt_cell_cp(t, tt_view_cell(t, 0, 0)) == 0x65e5); assert(tt_resize(t, 3, 3)); assert_offset_agrees(t); @@ -337,14 +337,14 @@ static void wide_anchor_survives_resize(void) assert(tt_cell_cp(t, tt_view_cell(t, 0, 0)) == 'a'); assert(tt_resize(t, 3, 3)); assert(tt_cell_cp(t, tt_view_cell(t, 1, 0)) == 0x65e5); - term_free(t); + wsap_vtcore_free(t); } /* Incremental and new snapshots must show the same retained rows. */ static void snapshots_agree_after_eviction_and_rewrap(void) { - struct term *t = small_history_term(11, 5, 23); - struct term_snapshot *persistent = term_snapshot_new(); + struct wsap_vtcore *t = small_history_term(11, 5, 23); + struct wsap_vtcore_snapshot *persistent = wsap_vtcore_snapshot_new(); assert(persistent); for (int n = 0; n < 120; n++) { char line[120]; @@ -353,67 +353,67 @@ static void snapshots_agree_after_eviction_and_rewrap(void) if (n % 13 == 0) assert(tt_resize(t, 6 + n % 17, 5)); int total = tt_history(t); - term_scroll_to(t, n % (total + 1)); - assert(term_snapshot_update(persistent, t)); - struct term_snapshot *fresh = term_snapshot_new(); - assert(fresh && term_snapshot_update(fresh, t)); - struct term_vector2i size = term_size(t); + wsap_vtcore_scroll_to(t, n % (total + 1)); + assert(wsap_vtcore_snapshot_update(persistent, t)); + struct wsap_vtcore_snapshot *fresh = wsap_vtcore_snapshot_new(); + assert(fresh && wsap_vtcore_snapshot_update(fresh, t)); + struct wsap_vtcore_vector2i size = wsap_vtcore_size(t); for (int y = 0; y < size.y; y++) { - const struct term_cell *a = term_snapshot_row(persistent, y); - const struct term_cell *b = term_snapshot_row(fresh, y); + const struct wsap_vtcore_cell *a = wsap_vtcore_snapshot_row(persistent, y); + const struct wsap_vtcore_cell *b = wsap_vtcore_snapshot_row(fresh, y); for (int x = 0; x < size.x; x++) { assert(a[x].fg == b[x].fg && a[x].bg == b[x].bg); assert(a[x].width == b[x].width && a[x].attrs == b[x].attrs); uint32_t acp[32], bcp[32]; - int an = term_snapshot_cluster(persistent, a[x].text, acp, 32); - int bn = term_snapshot_cluster(fresh, b[x].text, bcp, 32); + int an = wsap_vtcore_snapshot_cluster(persistent, a[x].text, acp, 32); + int bn = wsap_vtcore_snapshot_cluster(fresh, b[x].text, bcp, 32); assert(an == bn); if (an) assert(!memcmp(acp, bcp, (size_t)an * sizeof(*acp))); else assert(a[x].text == b[x].text); } - assert(term_snapshot_row_key(persistent, y) == term_snapshot_row_key(fresh, y)); + assert(wsap_vtcore_snapshot_row_key(persistent, y) == wsap_vtcore_snapshot_row_key(fresh, y)); } assert_offset_agrees(t); - term_snapshot_free(fresh); + wsap_vtcore_snapshot_free(fresh); } - term_snapshot_free(persistent); - term_free(t); + wsap_vtcore_snapshot_free(persistent); + wsap_vtcore_free(t); } static void snapshots_agree_after_prefix_eviction(void) { - struct term *t = tt_new(1000, 3); + struct wsap_vtcore *t = tt_new(1000, 3); char line[1000]; for (int i = 0; i < 9500; i++) { memset(line, 'A' + i % 26, sizeof(line)); tt_write(t, line, sizeof(line)); } tt_write(t, "\r\n", 2); - term_scroll(t, INT_MAX); - struct term_snapshot *persistent = term_snapshot_new(); - assert(persistent && term_snapshot_update(persistent, t)); - uint64_t old_key = term_snapshot_row_key(persistent, 0); + wsap_vtcore_scroll(t, INT_MAX); + struct wsap_vtcore_snapshot *persistent = wsap_vtcore_snapshot_new(); + assert(persistent && wsap_vtcore_snapshot_update(persistent, t)); + uint64_t old_key = wsap_vtcore_snapshot_row_key(persistent, 0); memset(line, 'z', sizeof(line)); for (int i = 0; i < 1200; i++) { tt_write(t, line, sizeof(line)); tt_write(t, "\r\n", 2); } - assert(term_snapshot_update(persistent, t)); - assert(term_snapshot_row_key(persistent, 0) != old_key); - struct term_snapshot *fresh = term_snapshot_new(); - assert(fresh && term_snapshot_update(fresh, t)); + assert(wsap_vtcore_snapshot_update(persistent, t)); + assert(wsap_vtcore_snapshot_row_key(persistent, 0) != old_key); + struct wsap_vtcore_snapshot *fresh = wsap_vtcore_snapshot_new(); + assert(fresh && wsap_vtcore_snapshot_update(fresh, t)); for (int y = 0; y < 3; y++) { - const struct term_cell *a = term_snapshot_row(persistent, y); - const struct term_cell *b = term_snapshot_row(fresh, y); + const struct wsap_vtcore_cell *a = wsap_vtcore_snapshot_row(persistent, y); + const struct wsap_vtcore_cell *b = wsap_vtcore_snapshot_row(fresh, y); for (int x = 0; x < 1000; x++) assert(a[x].text == b[x].text && a[x].fg == b[x].fg && a[x].bg == b[x].bg); - assert(term_snapshot_row_key(persistent, y) == term_snapshot_row_key(fresh, y)); + assert(wsap_vtcore_snapshot_row_key(persistent, y) == wsap_vtcore_snapshot_row_key(fresh, y)); } - term_snapshot_free(fresh); - term_snapshot_free(persistent); - term_free(t); + wsap_vtcore_snapshot_free(fresh); + wsap_vtcore_snapshot_free(persistent); + wsap_vtcore_free(t); } /* A line that needs more than one storage part stays scannable. Every @@ -422,8 +422,8 @@ static void snapshots_agree_after_prefix_eviction(void) static void view_scrolls_a_line_that_needs_several_parts(void) { const int cols = 40, rows = 6, cells = 2000000; - struct term_options opt = { .size = { .x = cols, .y = rows }, .scrollback = 60000 }; - struct term *t = term_new(&opt); + struct wsap_vtcore_options opt = { .size = { .x = cols, .y = rows }, .scrollback = 60000 }; + struct wsap_vtcore *t = wsap_vtcore_new(&opt); assert(t); char *big = malloc((size_t)cells); assert(big); @@ -436,23 +436,23 @@ static void view_scrolls_a_line_that_needs_several_parts(void) /* The rows still on the screen are not history rows. */ int total = tt_history(t); assert(total == cells / cols - (rows - 1)); - struct term_snapshot *snap = term_snapshot_new(); + struct wsap_vtcore_snapshot *snap = wsap_vtcore_snapshot_new(); assert(snap); for (int off = 1; off <= total; off += 5) { - term_scroll_to(t, off); + wsap_vtcore_scroll_to(t, off); assert(tt_view_offset(t) == off); - assert(term_snapshot_update(snap, t)); + assert(wsap_vtcore_snapshot_update(snap, t)); for (int y = 0; y < rows; y++) { int row = total - off + y; if (row >= total) continue; - const struct term_cell *line = term_snapshot_row(snap, y); + const struct wsap_vtcore_cell *line = wsap_vtcore_snapshot_row(snap, y); for (int x = 0; x < cols; x++) assert(line[x].text == (uint32_t)('0' + (row * cols + x) % 10)); } } - term_snapshot_free(snap); - term_free(t); + wsap_vtcore_snapshot_free(snap); + wsap_vtcore_free(t); } int main(void) diff --git a/tests/write_fuzz_test.c b/tests/write_fuzz_test.c index 8c1475a..d415c5e 100644 --- a/tests/write_fuzz_test.c +++ b/tests/write_fuzz_test.c @@ -1,5 +1,5 @@ /* - * Differential fuzz test for term_feed. Each seed makes random terminal + * Differential fuzz test for wsap_vtcore_feed. Each seed makes random terminal * output: text, controls, CSI and ESC sequences, raw bytes, and resizes. * One terminal gets the output in a few large writes; the bulk fast paths * handle it. A second terminal gets it one byte at a time; the generic @@ -17,18 +17,18 @@ /* Each terminal has its own snapshot, so cells of both stay readable at * the same time. */ -static struct term_snapshot *snap_bulk, *snap_bytes; +static struct wsap_vtcore_snapshot *snap_bulk, *snap_bytes; /* The code points of a cell's text. A cluster has handles that differ * between snapshots, so the test compares its code points. */ -static int cell_text(const struct term_snapshot *s, const struct term_cell *cell, +static int cell_text(const struct wsap_vtcore_snapshot *s, const struct wsap_vtcore_cell *cell, uint32_t *cps, int cap) { - int n = term_snapshot_cluster(s, cell->text, cps, cap); + int n = wsap_vtcore_snapshot_cluster(s, cell->text, cps, cap); return n < cap ? n : cap; } -static bool same_cell(const struct term_cell *a, const struct term_cell *b) +static bool same_cell(const struct wsap_vtcore_cell *a, const struct wsap_vtcore_cell *b) { if (a->fg != b->fg || a->bg != b->bg || a->attrs != b->attrs || a->width != b->width) return false; @@ -38,24 +38,24 @@ static bool same_cell(const struct term_cell *a, const struct term_cell *b) return na == nb && memcmp(ta, tb, (size_t)na * sizeof(ta[0])) == 0; } -static void assert_same(struct term *bulk, struct term *bytes, int seed, int step) +static void assert_same(struct wsap_vtcore *bulk, struct wsap_vtcore *bytes, int seed, int step) { int cols = tt_cols(bulk), rows = tt_rows(bulk); int history = tt_history(bulk); bool same = tt_cursor_x(bulk) == tt_cursor_x(bytes) && tt_cursor_y(bulk) == tt_cursor_y(bytes) && history == tt_history(bytes); - term_scroll(bulk, history); - term_scroll(bytes, history); + wsap_vtcore_scroll(bulk, history); + wsap_vtcore_scroll(bytes, history); for (int page = 0; same && page <= history; page += rows) { - bool copied = term_snapshot_update(snap_bulk, bulk); - copied &= term_snapshot_update(snap_bytes, bytes); + bool copied = wsap_vtcore_snapshot_update(snap_bulk, bulk); + copied &= wsap_vtcore_snapshot_update(snap_bytes, bytes); assert(copied); for (int y = 0; same && y < rows; y++) { - const struct term_cell *ra = term_snapshot_row(snap_bulk, y); - const struct term_cell *rb = term_snapshot_row(snap_bytes, y); + const struct wsap_vtcore_cell *ra = wsap_vtcore_snapshot_row(snap_bulk, y); + const struct wsap_vtcore_cell *rb = wsap_vtcore_snapshot_row(snap_bytes, y); for (int x = 0; x < cols; x++) { - const struct term_cell *a = &ra[x], *b = &rb[x]; + const struct wsap_vtcore_cell *a = &ra[x], *b = &rb[x]; if (!same_cell(a, b)) { fprintf(stderr, "seed %d step %d: page %d row %d col %d: " "bulk %x/%x/%x/%x/%u, bytes %x/%x/%x/%x/%u\n", @@ -66,11 +66,11 @@ static void assert_same(struct term *bulk, struct term *bytes, int seed, int ste } } } - term_scroll(bulk, -rows); - term_scroll(bytes, -rows); + wsap_vtcore_scroll(bulk, -rows); + wsap_vtcore_scroll(bytes, -rows); } - term_scroll_to(bulk, 0); - term_scroll_to(bytes, 0); + wsap_vtcore_scroll_to(bulk, 0); + wsap_vtcore_scroll_to(bytes, 0); if (!same) fprintf(stderr, "seed %d step %d: cursor %d,%d vs %d,%d, history %d vs %d\n", seed, step, tt_cursor_x(bulk), tt_cursor_y(bulk), @@ -85,12 +85,12 @@ int main(int argc, char **argv) for (int seed = 1; seed <= seeds; seed++) { rng = 0x9e3779b97f4a7c15ull * (uint64_t)seed; int cols = 4 + rn(30), rows = 2 + rn(10); - struct term *bulk = tt_new(cols, rows); - struct term *bytes = tt_new(cols, rows); + struct wsap_vtcore *bulk = tt_new(cols, rows); + struct wsap_vtcore *bytes = tt_new(cols, rows); /* A new terminal can get the address of a freed one, so each seed * uses new snapshots. */ - snap_bulk = term_snapshot_new(); - snap_bytes = term_snapshot_new(); + snap_bulk = wsap_vtcore_snapshot_new(); + snap_bytes = wsap_vtcore_snapshot_new(); assert(bulk && bytes && snap_bulk && snap_bytes); for (int step = 0; step < 6; step++) { blen = 0; @@ -110,10 +110,10 @@ int main(int argc, char **argv) assert_same(bulk, bytes, seed, step); } } - term_snapshot_free(snap_bulk); - term_snapshot_free(snap_bytes); - term_free(bulk); - term_free(bytes); + wsap_vtcore_snapshot_free(snap_bulk); + wsap_vtcore_snapshot_free(snap_bytes); + wsap_vtcore_free(bulk); + wsap_vtcore_free(bytes); } return 0; } |
