]> git.ipfire.org Git - thirdparty/freeradius-server.git/commitdiff
Hack in default list selection when parsing in list_as_attr mode
authorArran Cudbard-Bell <a.cudbardb@freeradius.org>
Wed, 8 Dec 2021 19:01:07 +0000 (14:01 -0500)
committerArran Cudbard-Bell <a.cudbardb@freeradius.org>
Wed, 8 Dec 2021 19:57:59 +0000 (14:57 -0500)
src/lib/server/tmpl_dcursor.c
src/lib/server/tmpl_tokenize.c

index b9f9abcc0e395f087438192d8b61fed62b29c5fb..393306c55a9ae15a2feedd63c5de36b80e40ab2c 100644 (file)
@@ -367,16 +367,18 @@ fr_pair_t *tmpl_dcursor_init(int *err, TALLOC_CTX *ctx, tmpl_dcursor_ctx_t *cc,
        /*
         *      Get the right list in the specified context
         */
-       list_head = tmpl_list_head(request, tmpl_list(vpt));
-       if (!list_head) {
-               if (err) {
-                       *err = -2;
+       if (!vpt->rules.list_as_attr) {
+               list_head = tmpl_list_head(request, tmpl_list(vpt));
+               if (!list_head) {
                        fr_strerror_printf("List \"%s\" not available in this context",
                                           fr_table_str_by_value(pair_list_table, tmpl_list(vpt), "<INVALID>"));
+                       goto error;
                }
-               goto error;
+               list_ctx = tmpl_list_ctx(request, tmpl_list(vpt));
+       } else {
+               list_head = &request->pair_root->vp_group;
+               list_ctx = request->pair_root;
        }
-       list_ctx = tmpl_list_ctx(request, tmpl_list(vpt));
 
        /*
         *      Initialise the temporary cursor context
@@ -511,16 +513,21 @@ int tmpl_extents_find(TALLOC_CTX *ctx,
                }
        }
 
-       /*
-        *      Get the right list in the specified context
-        */
-       list_head = tmpl_list_head(request, tmpl_list(vpt));
-       if (!list_head) {
-               fr_strerror_printf("List \"%s\" not available in this context",
-                                  fr_table_str_by_value(pair_list_table, tmpl_list(vpt), "<INVALID>"));
-               return -2;
+       if (!vpt->rules.list_as_attr) {
+               /*
+                *      Get the right list in the specified context
+                */
+               list_head = tmpl_list_head(request, tmpl_list(vpt));
+               if (!list_head) {
+                       fr_strerror_printf("List \"%s\" not available in this context",
+                                          fr_table_str_by_value(pair_list_table, tmpl_list(vpt), "<INVALID>"));
+                       return -2;
+               }
+               list_ctx = tmpl_list_ctx(request, tmpl_list(vpt));
+       } else {
+               list_head = &request->pair_root->vp_group;
+               list_ctx = request->pair_root;
        }
-       list_ctx = tmpl_list_ctx(request, tmpl_list(vpt));
 
        /*
         *      If it's a list, just return the list head
index 9b10002fec227c818ef7ac78ca153327982c1e1a..59396ffa8c4daf69f2ed9ba4d45b4267f0357786 100644 (file)
@@ -1956,6 +1956,56 @@ ssize_t tmpl_afrom_attr_substr(TALLOC_CTX *ctx, tmpl_attr_error_t *err,
                 *      later.
                 */
                if (tmpl_is_attr(vpt) && is_raw) tmpl_attr_to_raw(vpt);
+
+               /*
+                *      Check to see what the first attribute reference
+                *      was.  If it wasn't a known list group attribute
+                *      and we're parsing in list_as_attr mode, then
+                *      we need to add in a default list.
+                */
+               if (t_rules->list_as_attr) {
+                       tmpl_attr_t *ar;
+
+                       ar = fr_dlist_head(&vpt->data.attribute.ar);
+                       fr_assert(ar != NULL);
+
+                       if ((ar->ar_type != TMPL_ATTR_TYPE_NORMAL) ||
+                           ((ar->ar_da != request_attr_request) &&
+                            (ar->ar_da != request_attr_reply) &&
+                            (ar->ar_da != request_attr_control) &&
+                            (ar->ar_da != request_attr_state))) {
+                               MEM(ar = talloc(vpt, tmpl_attr_t));
+                               *ar = (tmpl_attr_t){
+                                       .ar_type = TMPL_ATTR_TYPE_NORMAL,
+                                       .ar_parent = fr_dict_root(fr_dict_internal())
+                               };
+
+                               switch (t_rules->list_def) {
+                               default:
+                               case PAIR_LIST_REQUEST:
+                                       ar->ar_da = request_attr_request;
+                                       break;
+
+                               case PAIR_LIST_REPLY:
+                                       ar->ar_da = request_attr_reply;
+                                       break;
+
+                               case PAIR_LIST_CONTROL:
+                                       ar->ar_da = request_attr_control;
+                                       break;
+
+                               case PAIR_LIST_STATE:
+                                       ar->ar_da = request_attr_state;
+                                       break;
+                               }
+
+                               /*
+                                *      Prepend the list ref so it gets evaluated
+                                *      first.
+                                */
+                               fr_dlist_insert_head(&vpt->data.attribute.ar, ar);
+                       }
+               }
        }
 
        /*