From: Alan T. DeKok Date: Fri, 12 Nov 2021 20:56:40 +0000 (-0500) Subject: rearrange / rename API, and add fr_edit_list_replace() X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=7e45a52fd57dd4549e1092dcdc2dcec28c216975;p=thirdparty%2Ffreeradius-server.git rearrange / rename API, and add fr_edit_list_replace() --- diff --git a/src/lib/util/edit.c b/src/lib/util/edit.c index 038020af51..d226ba58c1 100644 --- a/src/lib/util/edit.c +++ b/src/lib/util/edit.c @@ -162,7 +162,8 @@ static int edit_record(fr_edit_list_t *el, fr_edit_op_t op, fr_pair_t *vp, fr_pa { fr_edit_t *e; - if (!el) return 0; + fr_assert(el != NULL); + fr_assert(vp != NULL); /* * Search for previous edits. @@ -339,21 +340,81 @@ static int edit_record(fr_edit_list_t *el, fr_edit_op_t op, fr_pair_t *vp, fr_pa return 0; } -int fr_edit_list_insert(fr_edit_list_t *el, fr_pair_t *vp, fr_pair_list_t *list, fr_pair_t *prev) + +/** Insert a new VP after an existing one. + * + * This function mirrors fr_pair_insert_after(). + * + * After this function returns, the new VP has been inserted into the + * list. + */ +int fr_edit_list_insert_after(fr_edit_list_t *el, fr_pair_list_t *list, fr_pair_t *pos, fr_pair_t *vp) { - return edit_record(el, FR_EDIT_INSERT, vp, list, prev); + if (!el) return 0; + + return edit_record(el, FR_EDIT_INSERT, vp, list, pos); } -int fr_edit_list_delete(fr_edit_list_t *el, fr_pair_t *vp, fr_pair_list_t *list) + +/** Delete a VP + * + * This function mirrors fr_pair_delete() + * + * After this function returns, the VP has been removed from the list. + */ +int fr_edit_list_delete(fr_edit_list_t *el, fr_pair_list_t *list, fr_pair_t *vp) { return edit_record(el, FR_EDIT_DELETE, vp, list, NULL); } -int fr_edit_list_record(fr_edit_list_t *el, fr_pair_t *vp) +/** Record the value of a leaf #fr_value_box_t + * + * After this function returns, it's safe to edit the pair. + */ +int fr_edit_list_record_value(fr_edit_list_t *el, fr_pair_t *vp) { + if (!el) return 0; + + if (!fr_type_is_leaf(vp->vp_type)) return -1; + return edit_record(el, FR_EDIT_VALUE, vp, NULL, NULL); } +/** Replace a pair with another one. + * + * This function mirrors fr_pair_replace(). + * + * After this function returns, the new VP has replaced the old one, + * and the new one can be edited. + */ +int fr_edit_list_replace(fr_edit_list_t *el, fr_pair_list_t *list, fr_pair_t *to_replace, fr_pair_t *vp) +{ + if (!el) return 0; + + if (to_replace->da != vp->da) return -1; + + if (edit_record(el, FR_EDIT_INSERT, vp, list, to_replace) < 0) return -1; + + /* + * If deleting the old entry fails, then the new entry + * above MUST be the last member of the edit list. If + * it's not the last member, then it means that it + * already existed in the list (either VP list of edit + * list). The edit_record() function checks for that, + * and errors if so. + */ + if (edit_record(el, FR_EDIT_DELETE, to_replace, list, NULL) < 0) { + fr_edit_t *e = fr_dlist_pop_tail(&el->list); + + fr_assert(e != NULL); + fr_assert(e->vp == vp); + talloc_free(e); + return -1; + } + + return 0; +} + /** Finalize the edits when we destroy the edit list. * diff --git a/src/lib/util/edit.h b/src/lib/util/edit.h index 13d3e1ba4b..5d1902a115 100644 --- a/src/lib/util/edit.h +++ b/src/lib/util/edit.h @@ -37,11 +37,13 @@ fr_edit_list_t *fr_edit_list_alloc(TALLOC_CTX *ctx); void fr_edit_list_abort(fr_edit_list_t *el); -int fr_edit_list_insert(fr_edit_list_t *el, fr_pair_t *vp, fr_pair_list_t *list, fr_pair_t *prev); +int fr_edit_list_insert_after(fr_edit_list_t *el, fr_pair_list_t *list, fr_pair_t *pos, fr_pair_t *vp) CC_HINT(nonnull(2,4)); -int fr_edit_list_delete(fr_edit_list_t *el, fr_pair_t *vp, fr_pair_list_t *list); +int fr_edit_list_delete(fr_edit_list_t *el, fr_pair_list_t *list, fr_pair_t *vp) CC_HINT(nonnull(2,3)); -int fr_edit_list_record(fr_edit_list_t *el, fr_pair_t *vp); +int fr_edit_list_record_value(fr_edit_list_t *el, fr_pair_t *vp) CC_HINT(nonnull(2)); + +int fr_edit_list_replace(fr_edit_list_t *el, fr_pair_list_t *list, fr_pair_t *to_replace, fr_pair_t *vp) CC_HINT(nonnull(2,3,4)); #ifdef __cplusplus } diff --git a/src/lib/util/edit_tests.c b/src/lib/util/edit_tests.c index 1eb8753a76..3965162520 100644 --- a/src/lib/util/edit_tests.c +++ b/src/lib/util/edit_tests.c @@ -132,7 +132,7 @@ static void test_pair_delete_head(void) el = fr_edit_list_alloc(NULL); fr_assert(el != NULL); - rcode = fr_edit_list_delete(el, vp, &local_pairs); + rcode = fr_edit_list_delete(el, &local_pairs, vp); TEST_CHECK(rcode == 0); talloc_free(el); @@ -165,7 +165,7 @@ static void test_pair_delete_head_abort(void) el = fr_edit_list_alloc(NULL); fr_assert(el != NULL); - rcode = fr_edit_list_delete(el, vp, &local_pairs); + rcode = fr_edit_list_delete(el, &local_pairs, vp); TEST_CHECK(rcode == 0); count = fr_pair_list_len(&local_pairs); @@ -201,7 +201,7 @@ static void test_pair_delete_middle(void) el = fr_edit_list_alloc(NULL); fr_assert(el != NULL); - rcode = fr_edit_list_delete(el, vp, &local_pairs); + rcode = fr_edit_list_delete(el, &local_pairs, vp); TEST_CHECK(rcode == 0); talloc_free(el); @@ -240,7 +240,7 @@ static void test_pair_delete_middle_abort(void) el = fr_edit_list_alloc(NULL); fr_assert(el != NULL); - rcode = fr_edit_list_delete(el, middle, &local_pairs); + rcode = fr_edit_list_delete(el, &local_pairs, middle); TEST_CHECK(rcode == 0); count = fr_pair_list_len(&local_pairs); @@ -282,13 +282,13 @@ static void test_pair_delete_multiple(void) el = fr_edit_list_alloc(NULL); fr_assert(el != NULL); - rcode = fr_edit_list_delete(el, vp, &local_pairs); /* middle */ + rcode = fr_edit_list_delete(el, &local_pairs, vp); /* middle */ TEST_CHECK(rcode == 0); vp = fr_pair_list_tail(&local_pairs); fr_assert(vp != NULL); - rcode = fr_edit_list_delete(el, vp, &local_pairs); /* tail */ + rcode = fr_edit_list_delete(el, &local_pairs, vp); /* tail */ TEST_CHECK(rcode == 0); talloc_free(el); @@ -325,13 +325,13 @@ static void test_pair_delete_multiple_abort(void) el = fr_edit_list_alloc(NULL); fr_assert(el != NULL); - rcode = fr_edit_list_delete(el, vp, &local_pairs); /* middle */ + rcode = fr_edit_list_delete(el, &local_pairs, vp); /* middle */ TEST_CHECK(rcode == 0); vp = fr_pair_list_tail(&local_pairs); fr_assert(vp != NULL); - rcode = fr_edit_list_delete(el, vp, &local_pairs); /* tail */ + rcode = fr_edit_list_delete(el, &local_pairs, vp); /* tail */ TEST_CHECK(rcode == 0); count = fr_pair_list_len(&local_pairs); @@ -372,7 +372,7 @@ static void test_pair_edit_value(void) el = fr_edit_list_alloc(NULL); fr_assert(el != NULL); - rcode = fr_edit_list_record(el, vp); + rcode = fr_edit_list_record_value(el, vp); TEST_CHECK(rcode == 0); TEST_CHECK(vp->vp_uint32 == 0); @@ -406,7 +406,7 @@ static void test_pair_edit_value_abort(void) el = fr_edit_list_alloc(NULL); fr_assert(el != NULL); - rcode = fr_edit_list_record(el, vp); + rcode = fr_edit_list_record_value(el, vp); TEST_CHECK(rcode == 0); TEST_CHECK(vp->vp_uint32 == 0);