]> git.ipfire.org Git - thirdparty/bird.git/commitdiff
Merge commit '00b139bd' into thread-merge-2.16
authorMaria Matejka <mq@ucw.cz>
Thu, 28 Nov 2024 08:09:00 +0000 (09:09 +0100)
committerMaria Matejka <mq@ucw.cz>
Thu, 28 Nov 2024 08:28:34 +0000 (09:28 +0100)
1  2 
sysdep/linux/netlink.c

index ea79a1aa70faf42c19ad98bed3b73bd6702c6a53,533cc26860b96d4a7a73a984c24bc0b93c59cadf..9e275152daeb96d9d8e93d74af557d58748b47ff
@@@ -1593,8 -1465,24 +1593,24 @@@ done
  }
  
  static inline int
- nl_allow_replace(struct krt_proto *p, rte *new)
 -nl_allow_replace(struct krt_proto *p, rte *new, rte *old)
++nl_allow_replace(struct krt_proto *p, const rte *new, const rte *old)
  {
 -    uint new_metric = ea_get_int(new->attrs->eattrs, EA_KRT_METRIC, 0);
 -    uint old_metric = ea_get_int(old->attrs->eattrs, EA_KRT_METRIC, 0);
+   /*
+    * In kernel routing tables, (net, metric) is the primary key. Therefore, we
+    * can use NL_OP_REPLACE only if the new and and the old route have the same
+    * kernel metric, otherwise the replace would just add the new route while
+    * keep the old one.
+    */
+   if ((p->af != AF_MPLS) && (KRT_CF->sys.metric == 0))
+   {
++    uint new_metric = ea_get_int(new->attrs, &ea_krt_metric, 0);
++    uint old_metric = ea_get_int(old->attrs, &ea_krt_metric, 0);
+     if (new_metric != old_metric)
+       return 0;
+   }
    /*
     * We use NL_OP_REPLACE for IPv4, it has an issue with not checking for
     * matching rtm_protocol, but that is OK when dedicated priority is used.