]> git.ipfire.org Git - thirdparty/freeradius-server.git/commitdiff
Add useful utility functions
authorArran Cudbard-Bell <a.cudbardb@freeradius.org>
Fri, 17 Jun 2022 21:38:20 +0000 (16:38 -0500)
committerArran Cudbard-Bell <a.cudbardb@freeradius.org>
Sat, 18 Jun 2022 02:04:52 +0000 (21:04 -0500)
src/lib/server/cf_util.c
src/lib/server/cf_util.h

index 2d487280dea5b71cb7d2934881e15d0aa7d7a384..25d92d30e4be72a55b1ff0fc5adbc00dc634a1d6 100644 (file)
@@ -1351,7 +1351,7 @@ static void _pair_count(int *count, CONF_SECTION const *cs)
  * @param[in] cs to search for items in.
  * @return The number of pairs nested within section.
  */
-int cf_pair_count(CONF_SECTION const *cs)
+unsigned int cf_pair_count_descendents(CONF_SECTION const *cs)
 {
        int count = 0;
 
@@ -1360,6 +1360,59 @@ int cf_pair_count(CONF_SECTION const *cs)
        return count;
 }
 
+/** Count the number of times an attribute occurs in a parent section
+ *
+ * @param[in] cs       to search for items in.
+ * @param[in] attr     to search for.
+ * @return The number of pairs of that attribute type.
+ */
+unsigned int cf_pair_count(CONF_SECTION const *cs, char const *attr)
+{
+       size_t          i;
+       CONF_PAIR       *cp = NULL;
+
+       for (i = 0; (cp = cf_pair_find_next(cs, cp, attr)); i++);
+
+       return i;
+}
+
+/** Concatenate the values of any pairs with name attr
+ *
+ * @param[out] out     where to write the concatenated values.
+ * @param[in] cs       to search in.
+ * @param[in] attr     to search for.
+ * @param[in] sep      to use to separate values
+ * @return
+ *      - Length of the data written to out on success.
+ *     - < 0 on failure.  Number of additional bytes required in buffer.
+ */
+fr_slen_t cf_pair_values_concat(fr_sbuff_t *out, CONF_SECTION const *cs, char const *attr, char const *sep)
+{
+       fr_sbuff_t              our_out = FR_SBUFF(out);
+       CONF_PAIR               *cp;
+       fr_slen_t               slen = 0;
+       fr_sbuff_escape_rules_t e_rules = {
+                                       .name = __FUNCTION__,
+                                       .chr = '\\'
+                               };
+
+       if (sep) e_rules.subs[(uint8_t)*sep] = *sep;
+
+       for (cp = cf_pair_find(cs, attr); cp;) {
+               slen = fr_sbuff_in_escape(&our_out, cf_pair_value(cp),
+                                         strlen(cf_pair_value(cp)), &e_rules);
+               if (slen < 0) return slen;
+
+               cp = cf_pair_find_next(cs, cp, attr);
+               if (cp && sep) {
+                       slen = fr_sbuff_in_strcpy(&our_out, sep);
+                       if (slen < 0) return slen;
+               }
+       }
+
+       return fr_sbuff_set(out, &our_out);
+}
+
 /** Return the attr of a #CONF_PAIR
  *
  * Return the LHS value of a pair (the attribute).
index 76b71d72601b90dcbee6b6a06be99e5ff7334a32..65425552fcb3273851937b94827af5cafae89dac 100644 (file)
@@ -172,17 +172,28 @@ fr_token_t        cf_section_argv_quote(CONF_SECTION const *cs, int argc);
  */
 CONF_PAIR      *cf_pair_alloc(CONF_SECTION *parent, char const *attr, char const *value,
                               fr_token_t op, fr_token_t lhs_type, fr_token_t rhs_type);
+
 CONF_PAIR      *cf_pair_dup(CONF_SECTION *parent, CONF_PAIR *cp);
+
 int            cf_pair_replace(CONF_SECTION *cs, CONF_PAIR *cp, char const *value);
+
 void           cf_pair_mark_parsed(CONF_PAIR *cp);
 
 bool           cf_pair_is_parsed(CONF_PAIR *cp);
 
 CONF_PAIR      *cf_pair_next(CONF_SECTION const *cs, CONF_PAIR const *prev);
+
 CONF_PAIR      *cf_pair_find(CONF_SECTION const *cs, char const *name);
+
 CONF_PAIR      *cf_pair_find_next(CONF_SECTION const *cs, CONF_PAIR const *prev, char const *name);
+
 CONF_PAIR      *cf_pair_find_in_parent(CONF_SECTION const *cs, char const *attr);
-int            cf_pair_count(CONF_SECTION const *cs);
+
+unsigned int   cf_pair_count_descendents(CONF_SECTION const *cs);
+
+unsigned int   cf_pair_count(CONF_SECTION const *cs, char const *attr);
+
+fr_slen_t      cf_pair_values_concat(fr_sbuff_t *sbuff, CONF_SECTION const *cs, char const *attr, char const *sep);
 
 /** @hidecallergraph */
 char const     *cf_pair_attr(CONF_PAIR const *pair);