]> git.ipfire.org Git - thirdparty/bird.git/commitdiff
Merge commit 'a5a6de58' into thread-next
authorMaria Matejka <mq@ucw.cz>
Tue, 24 Oct 2023 08:39:52 +0000 (10:39 +0200)
committerMaria Matejka <mq@ucw.cz>
Tue, 24 Oct 2023 08:39:52 +0000 (10:39 +0200)
Conflicts:
      filter/config.Y
      filter/data.h
      filter/data.c

1  2 
filter/config.Y
filter/data.c
filter/data.h
filter/f-inst.c

diff --cc filter/config.Y
index 53884bb7b51430896a8e4c52ea3bb17f818be1a6,9141f964dbdb0258ca52474552e302eba7ebb1ef..194e312db8c653540f2404f287cb5287b83ea73e
@@@ -201,33 -191,33 +201,33 @@@ f_new_lc_item(u32 f1, u32 t1, u32 f2, u
  }
  
  static inline struct f_inst *
 -f_const_empty(struct f_dynamic_attr dyn)
 +f_generate_empty(const struct symbol *sym)
  {
 -  struct f_val empty;
 -
 -  switch (dyn.type) {
 -    case EAF_TYPE_AS_PATH:
 -    case EAF_TYPE_INT_SET:
 -    case EAF_TYPE_EC_SET:
 -    case EAF_TYPE_LC_SET:
 -      empty = (struct f_val) {
 -      .type = dyn.f_type,
 -      .val.ad = &null_adata,
 -      };
 -      break;
 -    default:
 -      cf_error("Can't empty that attribute");
 -  }
 +  if (sym->class != SYM_ATTRIBUTE)
 +    cf_error("Can't empty %s: not an attribute", sym->name);
  
 -  return f_new_inst(FI_CONSTANT, empty);
 +  const struct ea_class *def = sym->attribute;
-   const struct f_val *empty = f_get_empty(def->type);
-   if (!empty)
++  const struct f_val empty = f_get_empty(def->type);
++  if (empty.type == T_VOID)
 +    cf_error("Can't empty attribute %s", def->name);
 +
-   return f_new_inst(FI_EA_SET, f_new_inst(FI_CONSTANT, *empty), def);
++  return f_new_inst(FI_EA_SET, f_new_inst(FI_CONSTANT, empty), def);
  }
  
 -#define f_dummy_dynattr(_type, _f_type)       ((struct f_dynamic_attr) { .type = _type, .f_type = _f_type, })
 +static inline struct f_inst *
 +f_implicit_roa_check(struct rtable_config *tab)
 +{
 +  const struct ea_class *def = ea_class_find("bgp_path");
 +  if (!def)
 +    cf_error("Fatal: Couldn't find BGP path attribute definition.");
 +
 +  struct f_static_attr fsa = f_new_static_attr(T_NET, SA_NET, 1);
  
 -#define f_const_empty_path            f_const_empty(f_dummy_dynattr(EAF_TYPE_AS_PATH, T_PATH))
 -#define f_const_empty_clist           f_const_empty(f_dummy_dynattr(EAF_TYPE_INT_SET, T_CLIST))
 -#define f_const_empty_eclist          f_const_empty(f_dummy_dynattr(EAF_TYPE_EC_SET, T_ECLIST))
 -#define f_const_empty_lclist          f_const_empty(f_dummy_dynattr(EAF_TYPE_LC_SET, T_LCLIST))
 +  return f_new_inst(FI_ROA_CHECK,
 +          f_new_inst(FI_RTA_GET, fsa),
 +          f_new_inst(FI_AS_PATH_LAST, f_new_inst(FI_EA_GET, def)),
 +          tab);
 +}
  
  /*
   * Remove all new lines and doubled whitespaces
@@@ -875,10 -860,10 +875,10 @@@ term
   | dynamic_attr '.' RESET{ }
  */
  
-  | '+' EMPTY '+' { $$ = f_new_inst(FI_CONSTANT, f_const_empty_path); }
-  | '-' EMPTY '-' { $$ = f_new_inst(FI_CONSTANT, f_const_empty_clist); }
-  | '-' '-' EMPTY '-' '-' { $$ = f_new_inst(FI_CONSTANT, f_const_empty_eclist); }
-  | '-' '-' '-' EMPTY '-' '-' '-' { $$ = f_new_inst(FI_CONSTANT, f_const_empty_lclist); }
 - | '+' EMPTY '+' { $$ = f_const_empty_path; }
 - | '-' EMPTY '-' { $$ = f_const_empty_clist; }
 - | '-' '-' EMPTY '-' '-' { $$ = f_const_empty_eclist; }
 - | '-' '-' '-' EMPTY '-' '-' '-' { $$ = f_const_empty_lclist; }
++ | '+' EMPTY '+' { $$ = f_new_inst(FI_CONSTANT, f_get_empty(T_PATH)); }
++ | '-' EMPTY '-' { $$ = f_new_inst(FI_CONSTANT, f_get_empty(T_CLIST)); }
++ | '-' '-' EMPTY '-' '-' { $$ = f_new_inst(FI_CONSTANT, f_get_empty(T_ECLIST)); }
++ | '-' '-' '-' EMPTY '-' '-' '-' { $$ = f_new_inst(FI_CONSTANT, f_get_empty(T_LCLIST)); }
   | PREPEND '(' term ',' term ')' { $$ = f_new_inst(FI_PATH_PREPEND, $3, $5); }
   | ADD '(' term ',' term ')' { $$ = f_new_inst(FI_CLIST_ADD, $3, $5); }
   | DELETE '(' term ',' term ')' { $$ = f_new_inst(FI_CLIST_DEL, $3, $5); }
diff --cc filter/data.c
Simple merge
diff --cc filter/data.h
index b5db4aecf1cb106f15409202ba530548a61c1921,f341b8b37f9d30ee979f5aa3590b79f43e5f1c89..cecb7bd5e10e930fdb9056ffe09891a984085fd6
@@@ -242,18 -316,8 +242,23 @@@ undef_value(struct f_val v
      (v.val.ad == &null_adata);
  }
  
- extern const struct f_val f_const_empty_path, f_const_empty_clist, f_const_empty_eclist, f_const_empty_lclist, f_const_empty_prefix_set;
- static inline const struct f_val *f_get_empty(btype t)
+ extern const struct f_val f_const_empty_prefix_set;
++static inline struct f_val f_get_empty(btype t)
 +{
 +  switch (t) {
-     case T_PATH:      return &f_const_empty_path;
-     case T_CLIST:     return &f_const_empty_clist;
-     case T_ECLIST:    return &f_const_empty_eclist;
-     case T_LCLIST:    return &f_const_empty_lclist;
-     default:          return NULL;
++    case T_PATH:
++    case T_CLIST:
++    case T_ECLIST:
++    case T_LCLIST:
++      return (struct f_val) {
++      .type = t,
++      .val.ad = &null_adata,
++      };
++    default:
++      return (struct f_val) { .type = T_VOID };
 +  }
 +}
  
 -enum filter_return f_eval(const struct f_line *expr, struct linpool *tmp_pool, struct f_val *pres);
 +enum filter_return f_eval(const struct f_line *expr, struct f_val *pres);
  
  #endif
diff --cc filter/f-inst.c
index bc5477a359ffc2000e1f6641012e35a95ffcb7ed,b63fc1f48b1d33d6c6abaacb8fbb6d9675bf192a..de5314fc33649a851214d46b30bede5570878b7c
    INST(FI_EA_GET, 0, 1) {     /* Access to extended attributes */
      DYNAMIC_ATTR;
      ACCESS_RTE;
 -    ACCESS_EATTRS;
 -    RESULT_TYPE(da.f_type);
 +    RESULT_TYPE(da->type);
      {
-       const struct f_val *empty;
 -      eattr *e = ea_find(*fs->eattrs, da.ea_code);
++      struct f_val empty;
 +      const eattr *e = ea_find(fs->rte->attrs, da->id);
  
 -      if (!e) {
 -      /* A special case: undefined as_path looks like empty as_path */
 -      if (da.type == EAF_TYPE_AS_PATH) {
 -        RESULT_(T_PATH, ad, &null_adata);
 -        break;
 -      }
 -
 -      /* The same special case for int_set */
 -      if (da.type == EAF_TYPE_INT_SET) {
 -        RESULT_(T_CLIST, ad, &null_adata);
 -        break;
 -      }
 -
 -      /* The same special case for ec_set */
 -      if (da.type == EAF_TYPE_EC_SET) {
 -        RESULT_(T_ECLIST, ad, &null_adata);
 -        break;
 -      }
 +      if (e)
 +      {
 +      ASSERT_DIE(e->type == da->type);
  
 -      /* The same special case for lc_set */
 -      if (da.type == EAF_TYPE_LC_SET) {
 -        RESULT_(T_LCLIST, ad, &null_adata);
 -        break;
 +      switch (e->type) {
 +        case T_IP:
 +          RESULT_(T_IP, ip, *((const ip_addr *) e->u.ptr->data));
 +          break;
 +        default:
 +          RESULT_VAL([[(struct f_val) {
 +              .type = e->type,
 +              .val.bval = e->u,
 +              }]]);
        }
 -
 -      /* Undefined value */
 -      RESULT_VOID;
 -      break;
 -      }
 -
 -      switch (e->type & EAF_TYPE_MASK) {
 -      case EAF_TYPE_INT:
 -      RESULT_(da.f_type, i, e->u.data);
 -      break;
 -      case EAF_TYPE_ROUTER_ID:
 -      RESULT_(T_QUAD, i, e->u.data);
 -      break;
 -      case EAF_TYPE_OPAQUE:
 -      RESULT_(T_ENUM_EMPTY, i, 0);
 -      break;
 -      case EAF_TYPE_IP_ADDRESS:
 -      RESULT_(T_IP, ip, *((ip_addr *) e->u.ptr->data));
 -      break;
 -      case EAF_TYPE_AS_PATH:
 -      RESULT_(T_PATH, ad, e->u.ptr);
 -      break;
 -      case EAF_TYPE_BITFIELD:
 -      RESULT_(T_BOOL, i, !!(e->u.data & (1u << da.bit)));
 -      break;
 -      case EAF_TYPE_INT_SET:
 -      RESULT_(T_CLIST, ad, e->u.ptr);
 -      break;
 -      case EAF_TYPE_EC_SET:
 -      RESULT_(T_ECLIST, ad, e->u.ptr);
 -      break;
 -      case EAF_TYPE_LC_SET:
 -      RESULT_(T_LCLIST, ad, e->u.ptr);
 -      break;
 -      default:
 -      bug("Unknown dynamic attribute type");
        }
-       else if (empty = f_get_empty(da->type))
-       RESULT_VAL(*empty);
++      else if ((empty = f_get_empty(da->type)).type != T_VOID)
++      RESULT_VAL(empty);
 +      else
 +      RESULT_VOID;
      }
    }