From d756f9e66589707f33e28cec1c54f604ffedf7ac Mon Sep 17 00:00:00 2001 From: Kate F Date: Mon, 1 Jul 2024 12:42:08 +0100 Subject: [PATCH] Sort endids written out by fsm_endid_get(). This is for caller convenience, I keep calling qsort for various reasons whenever I call this function, for example to use memcmp on ids. But the final motivation here was that I wanted to memcmp a const-qualified pointer to an id set stored elsewhere, and I can't do that without allocating for a local copy. And that seems silly when we can just qsort here. --- include/fsm/fsm.h | 3 +-- src/libfsm/endids.c | 4 ++- src/libfsm/minimise.c | 12 --------- src/libfsm/minimise_test_oracle.c | 3 +-- src/libfsm/print/api.c | 15 ----------- src/libfsm/print/fsm.c | 15 ----------- tests/capture/capture4.c | 2 +- tests/endids/endids0.c | 7 +----- tests/endids/endids0_many_endids.c | 13 ++-------- tests/endids/endids1_determinise.c | 7 +----- .../endids/endids1_determinise_and_minimise.c | 7 +----- tests/endids/endids2_union.c | 12 ++------- tests/endids/endids2_union_many_endids.c | 16 ++---------- tests/endids/endids4.c | 12 +-------- tests/endids/endids5.c | 11 +------- tests/endids/endids6.c | 25 +++---------------- tests/endids/endids7.c | 16 ++---------- tests/endids/endids7_with_duplicates.c | 16 ++---------- tests/endids/endids8.c | 10 +------- tests/endids/endids9.c | 9 +------ tests/endids/endids_utils.h | 3 --- tests/endids/utils.c | 11 -------- tests/gen/gtest.c | 2 +- tests/re_strings/testutil.c | 8 +++--- 24 files changed, 33 insertions(+), 206 deletions(-) diff --git a/include/fsm/fsm.h b/include/fsm/fsm.h index 269ee5c87..de5de136e 100644 --- a/include/fsm/fsm.h +++ b/include/fsm/fsm.h @@ -222,8 +222,7 @@ fsm_endid_set(struct fsm *fsm, fsm_state_t end_state, fsm_end_id_t id); * id_buf is expected to have enough cells (according to id_buf_count) * to store all the end IDs. You can find this with fsm_endid_count(). * - * The end IDs in the buffer may appear in any order, - * but will not have duplicates. + * The end IDs in the buffer are sorted and do not have duplicates. * * A state with no end IDs set is considered equivalent to a state * that has the empty set, this API does not distinguish these cases. diff --git a/src/libfsm/endids.c b/src/libfsm/endids.c index 66860e88a..c86277865 100644 --- a/src/libfsm/endids.c +++ b/src/libfsm/endids.c @@ -734,7 +734,9 @@ fsm_endid_get(const struct fsm *fsm, fsm_state_t end_state, ids[id_i] = b->ids->ids[id_i]; } - /* todo: could sort them here, if it matters. */ + /* sorting for caller convenience */ + qsort(ids, count, sizeof *ids, cmp_endids); + return 1; } else { /* collision */ #if LOG_ENDIDS > 4 diff --git a/src/libfsm/minimise.c b/src/libfsm/minimise.c index 8100e22da..d520b39fa 100644 --- a/src/libfsm/minimise.c +++ b/src/libfsm/minimise.c @@ -939,14 +939,6 @@ split_ecs_by_end_metadata(struct min_env *env, const struct fsm *fsm) return res; } -static int -cmp_end_ids(const void *pa, const void *pb) -{ - const fsm_end_id_t a = *(fsm_end_id_t *)pa; - const fsm_end_id_t b = *(fsm_end_id_t *)pb; - return a < b ? -1 : a > b ? 1 : 0; -} - static int collect_end_ids(const struct fsm *fsm, fsm_state_t s, struct end_metadata_end *e) @@ -965,10 +957,6 @@ collect_end_ids(const struct fsm *fsm, fsm_state_t s, int res = fsm_endid_get(fsm, s, e->count, e->ids); assert(res == 1); - /* sort, to make comparison easier later */ - qsort(e->ids, e->count, - sizeof(e->ids[0]), cmp_end_ids); - #if LOG_ECS fprintf(stderr, "%d:", s); for (size_t i = 0; i < written; i++) { diff --git a/src/libfsm/minimise_test_oracle.c b/src/libfsm/minimise_test_oracle.c index 6cd1848c4..d2cfa404d 100644 --- a/src/libfsm/minimise_test_oracle.c +++ b/src/libfsm/minimise_test_oracle.c @@ -186,8 +186,7 @@ fsm_minimise_test_oracle(const struct fsm *fsm) continue; } - int eres = fsm_endid_get(fsm, i, - count_a, ids_a); + int eres = fsm_endid_get(fsm, i, count_a, ids_a); assert(eres == 1); bool found = false; diff --git a/src/libfsm/print/api.c b/src/libfsm/print/api.c index 7a0a9ffa5..f25a1d97a 100644 --- a/src/libfsm/print/api.c +++ b/src/libfsm/print/api.c @@ -27,19 +27,6 @@ #include #include -/* TODO: centralise */ -static int -comp_end_id(const void *a, const void *b) -{ - assert(a != NULL); - assert(b != NULL); - - if (* (fsm_end_id_t *) a < * (fsm_end_id_t *) b) { return -1; } - if (* (fsm_end_id_t *) a > * (fsm_end_id_t *) b) { return +1; } - - return 0; -} - static int rangeclass(unsigned char x, unsigned char y) { @@ -161,8 +148,6 @@ fsm_print_api(FILE *f, const struct fsm *fsm_orig) res = fsm_endid_get(fsm, end, count, ids); assert(res == 1); - qsort(ids, count, sizeof *ids, comp_end_id); - fprintf(f, "\tif (fsm_isend(fsm, s[%u])) {\n", end); for (size_t id = 0; id < count; id++) { fprintf(f, "\t\tif (!fsm_endid_set(fsm, s[%u], %zu)) { return 0; }\n", end, id); diff --git a/src/libfsm/print/fsm.c b/src/libfsm/print/fsm.c index 46bc428ff..a3cb471cf 100644 --- a/src/libfsm/print/fsm.c +++ b/src/libfsm/print/fsm.c @@ -24,19 +24,6 @@ #include #include -/* TODO: centralise */ -static int -comp_end_id(const void *a, const void *b) -{ - assert(a != NULL); - assert(b != NULL); - - if (* (fsm_end_id_t *) a < * (fsm_end_id_t *) b) { return -1; } - if (* (fsm_end_id_t *) a > * (fsm_end_id_t *) b) { return +1; } - - return 0; -} - /* TODO: centralise */ static int findany(const struct fsm *fsm, fsm_state_t state, fsm_state_t *a) @@ -325,8 +312,6 @@ fsm_print_fsm(FILE *f, const struct fsm *fsm) } if (count > 0) { - qsort(ids, count, sizeof *ids, comp_end_id); - fprintf(f, " = ["); for (size_t id = 0; id < count; id++) { diff --git a/tests/capture/capture4.c b/tests/capture/capture4.c index 313086c97..5ba8c941c 100644 --- a/tests/capture/capture4.c +++ b/tests/capture/capture4.c @@ -223,7 +223,7 @@ check(const struct fsm *fsm, const char *string, int gres; fsm_end_id_t ids[2]; - gres = fsm_endid_get(fsm, end, 2, ids); + gres = fsm_endid_get(fsm, end, fsm_endid_count(fsm, end), ids); if (gres != 1) { assert(!"fsm_getendids failed"); } diff --git a/tests/endids/endids0.c b/tests/endids/endids0.c index c9117c0b0..1f5e6f9b6 100644 --- a/tests/endids/endids0.c +++ b/tests/endids/endids0.c @@ -48,12 +48,7 @@ int main(void) assert( fsm_endid_count(fsm, state_ind) == 1); - ret = fsm_endid_get( - fsm, - state_ind, - 1, - &id); - + ret = fsm_endid_get(fsm, state_ind, 1, &id); assert(ret == 1); assert(id == 1); diff --git a/tests/endids/endids0_many_endids.c b/tests/endids/endids0_many_endids.c index 0af45112b..86a66063c 100644 --- a/tests/endids/endids0_many_endids.c +++ b/tests/endids/endids0_many_endids.c @@ -100,20 +100,14 @@ int main(void) assert(ret == 1); - /* sort endids and compare */ - qsort(&endids[0], - sizeof endids / sizeof endids[0], sizeof endids[0], - cmp_endids); - for (i=0; i < fsm_endid_count(fsm, state_ind); i++) { + for (i=0; i < sizeof all_ids / sizeof all_ids[0]; i++) { assert(endids[i] == sorted_all_ids[i]); } -#if 0 /* endids should be sorted */ - for (i=0; i < nwritten; i++) { + for (i=0; i < sizeof all_ids / sizeof all_ids[0]; i++) { assert(endids[i] == sorted_all_ids[i]); } -#endif /* 0 */ nend++; } @@ -160,9 +154,6 @@ int main(void) assert( ids[0] == matches[i].endid ); #endif /* 0 */ - /* sort endids and compare */ - qsort(&ids[0], count, sizeof ids[0], cmp_endids); - for (j=0; j < count; j++) { assert(ids[j] == sorted_all_ids[j]); } diff --git a/tests/endids/endids1_determinise.c b/tests/endids/endids1_determinise.c index 3860aefca..472807eed 100644 --- a/tests/endids/endids1_determinise.c +++ b/tests/endids/endids1_determinise.c @@ -44,12 +44,7 @@ int main(void) assert( fsm_endid_count(fsm, state_ind) == 1); - ret = fsm_endid_get( - fsm, - state_ind, - 1, - &endid); - + ret = fsm_endid_get(fsm, state_ind, 1, &endid); assert(ret == 1); assert( endid == 1 ); } diff --git a/tests/endids/endids1_determinise_and_minimise.c b/tests/endids/endids1_determinise_and_minimise.c index bb0711905..a2feafb18 100644 --- a/tests/endids/endids1_determinise_and_minimise.c +++ b/tests/endids/endids1_determinise_and_minimise.c @@ -49,12 +49,7 @@ int main(void) assert(fsm_endid_count(fsm, state_ind) == 1); - ret = fsm_endid_get( - fsm, - state_ind, - 1, - &endid); - + ret = fsm_endid_get(fsm, state_ind, 1, &endid); assert(ret == 1); assert( endid == 1 ); } diff --git a/tests/endids/endids2_union.c b/tests/endids/endids2_union.c index c990e7c95..0d6182437 100644 --- a/tests/endids/endids2_union.c +++ b/tests/endids/endids2_union.c @@ -60,15 +60,9 @@ int main(void) count = fsm_endid_count(comb, state_ind); // fprintf(stderr, "state %u, count = %zu\n", state_ind, count); + assert(count > 0 && count <= 2); - assert( count > 0 && count <= 2); - - ret = fsm_endid_get( - comb, - state_ind, - 2, - &endids[0]); - + ret = fsm_endid_get( comb, state_ind, count, &endids[0]); assert(ret == 1); if (count == 1) { @@ -158,8 +152,6 @@ int main(void) assert( count == matches[i].count ); - qsort(&ids[0], count, sizeof ids[0], cmp_endids); - for (j=0; j < count; j++) { assert( ids[j] == matches[i].endid[j] ); } diff --git a/tests/endids/endids2_union_many_endids.c b/tests/endids/endids2_union_many_endids.c index deafcff1e..a573f1921 100644 --- a/tests/endids/endids2_union_many_endids.c +++ b/tests/endids/endids2_union_many_endids.c @@ -189,15 +189,9 @@ int main(void) memset(&ids[0], 0, sizeof ids); count = fsm_endid_count(fsm, state_ind); - assert(count > 0 && count <= sizeof ids/sizeof ids[0]); - ret = fsm_endid_get( - fsm, - state_ind, - sizeof ids/sizeof ids[0], - &ids[0]); - + ret = fsm_endid_get(fsm, state_ind, count, &ids[0]); assert(ret == 1); memset(&tested_pattern[0], 0, sizeof tested_pattern); @@ -253,15 +247,9 @@ int main(void) memset(&ids[0], 0, sizeof ids); count = fsm_endid_count(fsm, state_ind); - assert(count <= NUM_ENDIDS_TOTAL); - ret = fsm_endid_get( - fsm, - state_ind, - sizeof ids/sizeof ids[0], - &ids[0]); - + ret = fsm_endid_get(fsm, state_ind, count, &ids[0]); assert(ret == 1); } } diff --git a/tests/endids/endids4.c b/tests/endids/endids4.c index 80afbcc39..a4530c93b 100644 --- a/tests/endids/endids4.c +++ b/tests/endids/endids4.c @@ -71,20 +71,12 @@ int main(void) int ret; count = fsm_endid_count(comb, state_ind); - printf("state %u count = %zu\n", state_ind, count); - assert(count == 2); - ret = fsm_endid_get( - comb, - state_ind, - 2, - &endids[0]); - + ret = fsm_endid_get(comb, state_ind, count, &endids[0]); assert(ret == 1); - qsort(&endids[0], count, sizeof endids[0], cmp_endids); assert(endids[0] == 1 && endids[1] == 2); } } @@ -149,8 +141,6 @@ int main(void) assert( count == matches[i].count ); - qsort(&ids[0], count, sizeof ids[0], cmp_endids); - for (j=0; j < count; j++) { assert( ids[j] == matches[i].endid[j] ); } diff --git a/tests/endids/endids5.c b/tests/endids/endids5.c index d6a713843..50030ea0d 100644 --- a/tests/endids/endids5.c +++ b/tests/endids/endids5.c @@ -72,17 +72,10 @@ int main(void) int ret; count = fsm_endid_count(comb, state_ind); - printf("state %u count = %zu\n", state_ind, count); - assert(count == 1); - ret = fsm_endid_get( - comb, - state_ind, - 2, - &endids[0]); - + ret = fsm_endid_get(comb, state_ind, count, &endids[0]); assert(ret == 1); assert(endids[0] == 1); @@ -153,8 +146,6 @@ int main(void) assert( count == matches[i].count ); - qsort(&ids[0], count, sizeof ids[0], cmp_endids); - for (j=0; j < count; j++) { assert( ids[j] == matches[i].endid[j] ); } diff --git a/tests/endids/endids6.c b/tests/endids/endids6.c index 34b261118..e237c2881 100644 --- a/tests/endids/endids6.c +++ b/tests/endids/endids6.c @@ -96,15 +96,9 @@ int main(void) int ret; count = fsm_endid_count(fsm, state_ind); + assert(count > 0 && count <= 2); - assert( count > 0 && count <= 2); - - ret = fsm_endid_get( - fsm, - state_ind, - sizeof ids / sizeof ids[0], - &ids[0]); - + ret = fsm_endid_get(fsm, state_ind, count, &ids[0]); assert(ret == 1); info[ninfo].state = state_ind; @@ -114,7 +108,6 @@ int main(void) assert(ids[0] == 1 || ids[0] == 2); info[ninfo].ids[0] = ids[0]; } else if (count == 2) { - qsort(&ids[0], count, sizeof ids[0], cmp_endids); assert(ids[0] == 1 && ids[1] == 2); info[ninfo].ids[0] = ids[0]; info[ninfo].ids[1] = ids[1]; @@ -139,22 +132,12 @@ int main(void) assert( state_ind == info[info_ind].state ); count = fsm_endid_count(fsm, state_ind); - assert(count > 0 && count <= 2); + assert(count == info[info_ind].count); - assert( count == info[info_ind].count ); - ret = fsm_endid_get( - fsm, - state_ind, - sizeof ids / sizeof ids[0], - &ids[0]); - + ret = fsm_endid_get(fsm, state_ind, count, &ids[0]); assert(ret == 1); - if (count > 1) { - qsort(&ids[0], count, sizeof ids[0], cmp_endids); - } - for (ind=0; ind < count; ind++) { fsm_end_id_t expected = info[info_ind].ids[ind]; switch (info[info_ind].ids[ind]) { diff --git a/tests/endids/endids7.c b/tests/endids/endids7.c index 6508308eb..3021be830 100644 --- a/tests/endids/endids7.c +++ b/tests/endids/endids7.c @@ -108,15 +108,9 @@ int main(void) int ret; count = fsm_endid_count(fsm, state_ind); - assert( count > 0 && count <= 2); - ret = fsm_endid_get( - fsm, - state_ind, - sizeof ids / sizeof ids[0], - &ids[0]); - + ret = fsm_endid_get(fsm, state_ind, count, &ids[0]); assert(ret == 1); info[ninfo].state = state_ind; @@ -126,7 +120,6 @@ int main(void) assert(ids[0] == 1 || ids[0] == 2); info[ninfo].ids[0] = ids[0]; } else if (count == 2) { - qsort(&ids[0], count, sizeof ids[0], cmp_endids); assert(ids[0] == 1 && ids[1] == 2); info[ninfo].ids[0] = ids[0]; info[ninfo].ids[1] = ids[1]; @@ -152,14 +145,9 @@ int main(void) assert( state_ind == info[info_ind].state ); count = fsm_endid_count(fsm, state_ind); - assert(count == 1); - ret = fsm_endid_get( - fsm, - state_ind, - 1, - &id); + ret = fsm_endid_get(fsm, state_ind, 1, &id); assert(ret == 1); if (info[info_ind].count == 2) { diff --git a/tests/endids/endids7_with_duplicates.c b/tests/endids/endids7_with_duplicates.c index 6b01d5f15..939c4b306 100644 --- a/tests/endids/endids7_with_duplicates.c +++ b/tests/endids/endids7_with_duplicates.c @@ -112,15 +112,9 @@ int main(void) int ret; count = fsm_endid_count(fsm, state_ind); - assert( count > 0 && count <= 2); - ret = fsm_endid_get( - fsm, - state_ind, - sizeof ids / sizeof ids[0], - &ids[0]); - + ret = fsm_endid_get(fsm, state_ind, count, &ids[0]); assert(ret == 1); info[ninfo].state = state_ind; @@ -130,7 +124,6 @@ int main(void) assert(ids[0] == 1 || ids[0] == 2); info[ninfo].ids[0] = ids[0]; } else if (count == 2) { - qsort(&ids[0], count, sizeof ids[0], cmp_endids); assert(ids[0] == 1 && ids[1] == 2); info[ninfo].ids[0] = ids[0]; info[ninfo].ids[1] = ids[1]; @@ -156,14 +149,9 @@ int main(void) assert( state_ind == info[info_ind].state ); count = fsm_endid_count(fsm, state_ind); - assert(count == 1); - ret = fsm_endid_get( - fsm, - state_ind, - 1, - &endid); + ret = fsm_endid_get( fsm, state_ind, 1, &endid); assert(ret == 1); if (info[info_ind].count == 2) { diff --git a/tests/endids/endids8.c b/tests/endids/endids8.c index 86a2b28c8..12b36fae0 100644 --- a/tests/endids/endids8.c +++ b/tests/endids/endids8.c @@ -77,20 +77,12 @@ int main(void) int ret; count = fsm_endid_count(comb, state_ind); - printf("state %u count = %zu\n", state_ind, count); - assert(count == 3); - ret = fsm_endid_get( - comb, - state_ind, - sizeof ids / sizeof ids[0], - &ids[0]); - + ret = fsm_endid_get(comb, state_ind, count, &ids[0]); assert(ret == 1); - qsort(&ids[0], count, sizeof ids[0], cmp_endids); assert(ids[0] == 1 && ids[1] == 2 && ids[2] == 4); } } diff --git a/tests/endids/endids9.c b/tests/endids/endids9.c index 33a872155..519399973 100644 --- a/tests/endids/endids9.c +++ b/tests/endids/endids9.c @@ -76,15 +76,9 @@ int main(void) int ret; count = fsm_endid_count(fsm, state_ind); - assert( count > 0 && count <= 2); - ret = fsm_endid_get( - fsm, - state_ind, - sizeof ids / sizeof ids[0], - &ids[0]); - + ret = fsm_endid_get(fsm, state_ind, count, &ids[0]); assert(ret == 1); info[ninfo].state = state_ind; @@ -94,7 +88,6 @@ int main(void) assert(ids[0] == 11 || ids[0] == 12); info[ninfo].ids[0] = ids[0]; } else if (count == 2) { - qsort(&ids[0], count, sizeof ids[0], cmp_endids); assert(ids[0] == 11 && ids[1] == 12); info[ninfo].ids[0] = ids[0]; info[ninfo].ids[1] = ids[1]; diff --git a/tests/endids/endids_utils.h b/tests/endids/endids_utils.h index f1aaefb5d..e2aad628a 100644 --- a/tests/endids/endids_utils.h +++ b/tests/endids/endids_utils.h @@ -7,8 +7,5 @@ int match_string(const struct fsm *fsm, const char *s, fsm_state_t *end_ptr, fsm_end_id_t **endids_ptr, size_t *num_endids_ptr); -int -cmp_endids(const void *pa, const void *pb); - #endif /* ENDIDS_UTILS_H */ diff --git a/tests/endids/utils.c b/tests/endids/utils.c index 882df92c4..28d65a1dd 100644 --- a/tests/endids/utils.c +++ b/tests/endids/utils.c @@ -47,14 +47,3 @@ match_string(const struct fsm *fsm, const char *s, fsm_state_t *end_ptr, fsm_end return ret; } -int -cmp_endids(const void *pa, const void *pb) { - const fsm_end_id_t *a = pa; - const fsm_end_id_t *b = pb; - - if (*a < *b) { return -1; } - if (*a > *b) { return 1; } - return 0; -} - - diff --git a/tests/gen/gtest.c b/tests/gen/gtest.c index 124c8be1b..ae4e94eed 100644 --- a/tests/gen/gtest.c +++ b/tests/gen/gtest.c @@ -60,7 +60,7 @@ gtest_matches_cb(const struct fsm *fsm, #define ID_BUF_COUNT 1 fsm_end_id_t ids[ID_BUF_COUNT]; int gres = fsm_endid_get(fsm, - end_state, ID_BUF_COUNT, ids); + end_state, fsm_endid_count(fsm, end_state), ids); if (gres != 1) { fprintf(stderr, diff --git a/tests/re_strings/testutil.c b/tests/re_strings/testutil.c index 50cc21be0..66afa1a38 100644 --- a/tests/re_strings/testutil.c +++ b/tests/re_strings/testutil.c @@ -47,11 +47,13 @@ run_test(const char **strings) const int res = fsm_exec(fsm, fsm_sgetc, string, &end, NULL); assert(res > 0); /* match */ - int eres = fsm_endid_get(fsm, end, - MAX_INPUTS, ids); + size_t count = fsm_endid_count(fsm, end); + assert(count <= MAX_INPUTS); + + int eres = fsm_endid_get(fsm, end, count, ids); assert(eres == 1); bool found = false; - for (size_t i = 0; i < fsm_endid_count(fsm, end); i++) { + for (size_t i = 0; i < count; i++) { if (ids[i] == id) { found = true; break;