]> git.ipfire.org Git - thirdparty/freeradius-server.git/commitdiff
allow DEFINE for STRUCT
authorAlan T. DeKok <aland@freeradius.org>
Fri, 17 Feb 2023 14:00:56 +0000 (09:00 -0500)
committerAlan T. DeKok <aland@freeradius.org>
Fri, 17 Feb 2023 14:32:22 +0000 (09:32 -0500)
src/lib/util/dict_tokenize.c
src/lib/util/dict_util.c

index a7c2156ae3c9b6a1f115bcadb9a0da1444419b0d..0f4ae6c404cce081ca9ebb82b71386c21d44cb10 100644 (file)
@@ -1032,8 +1032,8 @@ static int dict_read_process_define(dict_tokenize_ctx_t *ctx, char **argv, int a
        }
 
        /*
-        *      Since there is no number, the attribute MUST be
-        *      internal, and cannot be encoded as a number.
+        *      Since there is no number, the attribute cannot be
+        *      encoded as a number.
         */
        memcpy(&flags, base_flags, sizeof(flags));
        flags.name_only = true;
@@ -1044,7 +1044,6 @@ static int dict_read_process_define(dict_tokenize_ctx_t *ctx, char **argv, int a
         *      Certain structural types MUST have numbers.
         */
        switch (type) {
-       case FR_TYPE_STRUCT:
        case FR_TYPE_VSA:
        case FR_TYPE_VENDOR:
                fr_strerror_printf("DEFINE cannot be used for type '%s'", argv[1]);
@@ -1098,7 +1097,16 @@ static int dict_read_process_define(dict_tokenize_ctx_t *ctx, char **argv, int a
 
        if (dict_process_ref(ctx, parent, da, ref) < 0) return -1;
 
-       memcpy(&ctx->value_attr, &da, sizeof(da));
+       /*
+        *      Adding an attribute of type 'struct' is an implicit
+        *      BEGIN-STRUCT.
+        */
+       if (type == FR_TYPE_STRUCT) {
+               if (dict_gctx_push(ctx, da) < 0) return -1;
+               ctx->value_attr = NULL;
+       } else {
+               memcpy(&ctx->value_attr, &da, sizeof(da));
+       }
 
        return 0;
 }
index a0182fecf19b95ecdec5d163f07a1f46bac9f91c..4ef9e8ca5c5ede285bdd590b75f4d0181b7e1b0f 100644 (file)
@@ -1080,7 +1080,7 @@ int dict_attr_child_add(fr_dict_attr_t *parent, fr_dict_attr_t *child)
         *      The parent has children by name only, not by number.  Don't even bother trying to track
         *      numbers.
         */
-       if (parent->flags.name_only) return 0;
+       if (parent->flags.name_only && (parent->type != FR_TYPE_STRUCT)) return 0;
 
        /*
         *      We only allocate the pointer array *if* the parent has children.