void fr_pair_delete_by_child_num(VALUE_PAIR **head, fr_dict_attr_t const *parent,
unsigned int attr, int8_t tag);
+VALUE_PAIR *fr_pair_add_by_da(TALLOC_CTX *ctx, VALUE_PAIR **list,
+ fr_dict_attr_t const *da, int8_t tag);
+
VALUE_PAIR *fr_pair_update_by_da(TALLOC_CTX *ctx, VALUE_PAIR **list,
fr_dict_attr_t const *da, int8_t tag,
bool skip_if_exists);
#define pair_make_reply(_a, _b, _c) fr_pair_make(request->reply, &request->reply->vps, _a, _b, _c)
#define pair_make_config(_a, _b, _c) fr_pair_make(request, &request->control, _a, _b, _c)
+/** Allocate a VALUE_PAIR in the request list
+ *
+ * @param[in] _da #fr_dict_attr_t of the pair to be found or allocated.
+ * @param[in] _tag tag of the attribute to be found or allocated.
+ */
+#define pair_add_request(_da, _tag) fr_pair_add_by_da(request->packet, &request->packet->vps, _da, _tag)
+
+/** Allocate a VALUE_PAIR in the reply list
+ *
+ * @param[in] _da #fr_dict_attr_t of the pair to be found or allocated.
+ * @param[in] _tag tag of the attribute to be found or allocated.
+ */
+#define pair_add_reply(_da, _tag) fr_pair_add_by_da(request->reply, &request->reply->vps, _da, _tag)
+
+/** Allocate a VALUE_PAIR in the control list
+ *
+ * @param[in] _da #fr_dict_attr_t of the pair to be found or allocated.
+ * @param[in] _tag tag of the attribute to be found or allocated.
+ */
+#define pair_add_control(_da, _tag) fr_pair_add_by_da(request, &request->control, _da, _tag)
+
/** Return or allocate a VALUE_PAIR in the request list
*
- * @param[in] _da #fr_dict_attr_t of the pair to be found or allocated.
- * @param[in] _tag tag of the attribute to be found or allocated.
+ * @param[in] _da #fr_dict_attr_t of the pair to be found or allocated.
+ * @param[in] _tag tag of the attribute to be found or allocated.
*/
#define pair_update_request(_da, _tag) fr_pair_update_by_da(request->packet, &request->packet->vps, _da, _tag, false)
/** Return or allocate a VALUE_PAIR in the reply list
*
- * @param[in] _da #fr_dict_attr_t of the pair to be found or allocated.
- * @param[in] _tag tag of the attribute to be found or allocated.
+ * @param[in] _da #fr_dict_attr_t of the pair to be found or allocated.
+ * @param[in] _tag tag of the attribute to be found or allocated.
*/
#define pair_update_reply(_da, _tag) fr_pair_update_by_da(request->reply, &request->reply->vps, _da, _tag, false)
/** Return or allocate a VALUE_PAIR in the control list
*
- * @param[in] _da #fr_dict_attr_t of the pair to be found or allocated.
- * @param[in] _tag tag of the attribute to be found or allocated.
+ * @param[in] _da #fr_dict_attr_t of the pair to be found or allocated.
+ * @param[in] _tag tag of the attribute to be found or allocated.
*/
#define pair_update_control(_da, _tag) fr_pair_update_by_da(request, &request->control, _da, _tag, false)
return NULL;
}
+/** Create a new VALUE_PAIR
+ *
+ * @param[in] ctx to allocate new #VALUE_PAIR in.
+ * @param[in,out] list in search and insert into it.
+ * @param[in] da of attribute to update.
+ * @param[in] tag of attribute to update.
+ * @return
+ * - 0 on success.
+ * - -1 on failure.
+ */
+VALUE_PAIR *fr_pair_add_by_da(TALLOC_CTX *ctx, VALUE_PAIR **list,
+ fr_dict_attr_t const *da, int8_t tag)
+{
+ vp_cursor_t cursor;
+ VALUE_PAIR *vp;
+
+ (void)fr_pair_cursor_init(&cursor, list);
+ vp = fr_pair_afrom_da(ctx, da);
+ if (!vp) return NULL;
+ vp->tag = tag;
+
+ fr_pair_cursor_prepend(&cursor, vp);
+
+ return vp;
+}
+
/** Create a new VALUE_PAIR or replaces the value of the head pair in the specified list
*
* If skip_if_exists is true, will return NULL if a pair matching the specified #fr_dict_attr_t
fr_dict_attr_t const *da, int8_t tag,
bool skip_if_exists)
{
- vp_cursor_t cursor;
- VALUE_PAIR *vp;
+ vp_cursor_t cursor;
+ VALUE_PAIR *vp;
(void)fr_pair_cursor_init(&cursor, list);
vp = fr_pair_cursor_next_by_da(&cursor, da, tag);