From: Renato Westphal Date: Fri, 10 May 2019 11:42:07 +0000 (-0300) Subject: Merge pull request #4295 from donaldsharp/topotest_if X-Git-Tag: frr-7.2~397 X-Git-Url: https://git.proxmox.com/?a=commitdiff_plain;h=e777abf3a1ed41f18e479969288a06cef73df425;hp=c9d72a0b7f2f28ac33368675f70d55428099e831;p=mirror_frr.git Merge pull request #4295 from donaldsharp/topotest_if topotests: ifindex values are not guaranteed to be the same --- diff --git a/.gitignore b/.gitignore index 7a1378d58..df2b0a6bf 100644 --- a/.gitignore +++ b/.gitignore @@ -88,5 +88,6 @@ GSYMS GRTAGS GPATH compile_commands.json +.ccls-cache .dirstamp refix diff --git a/bgpd/bgpd.c b/bgpd/bgpd.c index b2925cd51..6183bbd47 100644 --- a/bgpd/bgpd.c +++ b/bgpd/bgpd.c @@ -6186,8 +6186,15 @@ int peer_route_map_set(struct peer *peer, afi_t afi, safi_t safi, int direct, /* Set configuration on peer. */ filter = &peer->filter[afi][safi]; - if (filter->map[direct].name) + if (filter->map[direct].name) { + /* If the neighbor is configured with the same route-map + * again then, ignore the duplicate configuration. + */ + if (strcmp(filter->map[direct].name, name) == 0) + return 0; + XFREE(MTYPE_BGP_FILTER_NAME, filter->map[direct].name); + } route_map_counter_decrement(filter->map[direct].map); filter->map[direct].name = XSTRDUP(MTYPE_BGP_FILTER_NAME, name); filter->map[direct].map = route_map; diff --git a/doc/developer/lists.rst b/doc/developer/lists.rst index 6d60420b2..987b3b7f4 100644 --- a/doc/developer/lists.rst +++ b/doc/developer/lists.rst @@ -119,6 +119,8 @@ The common setup pattern will look like this: .. code-block:: c + #include + PREDECL_XXX(Z) struct item { int otherdata; @@ -159,26 +161,26 @@ Common iteration macros The following iteration macros work across all data structures: -.. c:function:: for_each(Z, head, item) +.. c:function:: for_each(Z, &head, item) Equivalent to: .. code-block:: c - for (item = Z_first(head); item; item = Z_next(head, item)) + for (item = Z_first(&head); item; item = Z_next(&head, item)) Note that this will fail if the list is modified while being iterated over. -.. c:function:: for_each_safe(Z, head, item) +.. c:function:: for_each_safe(Z, &head, item) Same as the previous, but the next element is pre-loaded into a "hidden" variable (named ``Z_safe``.) Equivalent to: .. code-block:: c - for (item = Z_first(head); item; item = next) { - next = Z_next_safe(head, item); + for (item = Z_first(&head); item; item = next) { + next = Z_next_safe(&head, item); ... } @@ -189,7 +191,7 @@ The following iteration macros work across all data structures: tables is resized while iterating. This will cause items to be skipped or iterated over twice. -.. c:function:: for_each_from(Z, head, item, from) +.. c:function:: for_each_from(Z, &head, item, from) Iterates over the list, starting at item ``from``. This variant is "safe" as in the previous macro. Equivalent to: @@ -197,7 +199,7 @@ The following iteration macros work across all data structures: .. code-block:: c for (item = from; item; item = from) { - from = Z_next_safe(head, item); + from = Z_next_safe(&head, item); ... } diff --git a/doc/user/basic.rst b/doc/user/basic.rst index 8fbea29ee..f55b1b9d7 100644 --- a/doc/user/basic.rst +++ b/doc/user/basic.rst @@ -287,8 +287,8 @@ Terminal Mode Commands Write current configuration to configuration file. -.. index:: configure terminal -.. clicmd:: configure terminal +.. index:: configure [terminal] +.. clicmd:: configure [terminal] Change to configuration mode. This command is the first step to configuration. diff --git a/doc/user/bgp.rst b/doc/user/bgp.rst index 35e42d95c..d663b4fc1 100644 --- a/doc/user/bgp.rst +++ b/doc/user/bgp.rst @@ -942,14 +942,18 @@ Configuring Peers .. index:: [no] neighbor PEER maximum-prefix NUMBER .. clicmd:: [no] neighbor PEER maximum-prefix NUMBER -.. index:: [no] neighbor PEER local-as AS-NUMBER no-prepend -.. clicmd:: [no] neighbor PEER local-as AS-NUMBER no-prepend - -.. index:: [no] neighbor PEER local-as AS-NUMBER no-prepend replace-as -.. clicmd:: [no] neighbor PEER local-as AS-NUMBER no-prepend replace-as - -.. index:: [no] neighbor PEER local-as AS-NUMBER -.. clicmd:: [no] neighbor PEER local-as AS-NUMBER + Sets a maximum number of prefixes we can receive from a given peer. If this + number is exceeded, the BGP session will be destroyed. + + In practice, it is generally preferable to use a prefix-list to limit what + prefixes are received from the peer instead of using this knob. Tearing down + the BGP session when a limit is exceeded is far more destructive than merely + rejecting undesired prefixes. The prefix-list method is also much more + granular and offers much smarter matching criterion than number of received + prefixes, making it more suited to implementing policy. + +.. index:: [no] neighbor PEER local-as AS-NUMBER [no-prepend] [replace-as] +.. clicmd:: [no] neighbor PEER local-as AS-NUMBER [no-prepend] [replace-as] Specify an alternate AS for this BGP process when interacting with the specified peer. With no modifiers, the specified local-as is prepended to diff --git a/doc/user/static.rst b/doc/user/static.rst index 1705b6379..09bdc9cbe 100644 --- a/doc/user/static.rst +++ b/doc/user/static.rst @@ -123,7 +123,7 @@ but this time, the route command will apply to the VRF. .. code-block:: frr # case with VRF - configure terminal + configure vrf r1-cust1 ip route 10.0.0.0/24 10.0.0.2 exit-vrf diff --git a/lib/command.c b/lib/command.c index b3ef02800..d6fd1fa56 100644 --- a/lib/command.c +++ b/lib/command.c @@ -1386,7 +1386,7 @@ int config_from_file(struct vty *vty, FILE *fp, unsigned int *line_num) /* Configuration from terminal */ DEFUN (config_terminal, config_terminal_cmd, - "configure terminal", + "configure [terminal]", "Configuration from vty interface\n" "Configuration terminal\n") { diff --git a/lib/prefix.c b/lib/prefix.c index 6b9196921..d2a4c3a43 100644 --- a/lib/prefix.c +++ b/lib/prefix.c @@ -1543,7 +1543,7 @@ char *prefix_mac2str(const struct ethaddr *mac, char *buf, int size) return ptr; } -unsigned prefix_hash_key(void *pp) +unsigned prefix_hash_key(const void *pp) { struct prefix copy; diff --git a/lib/prefix.h b/lib/prefix.h index d3c387e10..d57b43dac 100644 --- a/lib/prefix.h +++ b/lib/prefix.h @@ -466,7 +466,7 @@ extern int is_zero_mac(struct ethaddr *mac); extern int prefix_str2mac(const char *str, struct ethaddr *mac); extern char *prefix_mac2str(const struct ethaddr *mac, char *buf, int size); -extern unsigned prefix_hash_key(void *pp); +extern unsigned prefix_hash_key(const void *pp); extern int str_to_esi(const char *str, esi_t *esi); extern char *esi_to_str(const esi_t *esi, char *buf, int size); diff --git a/lib/routemap.c b/lib/routemap.c index 4898a8d0f..e9c8d9c4c 100644 --- a/lib/routemap.c +++ b/lib/routemap.c @@ -1308,6 +1308,16 @@ int route_map_add_match(struct route_map_index *index, const char *match_name, for (rule = index->match_list.head; rule; rule = next) { next = rule->next; if (rule->cmd == cmd) { + /* If the configured route-map match rule is exactly + * the same as the existing configuration then, + * ignore the duplicate configuration. + */ + if (strcmp(match_arg, rule->rule_str) == 0) { + if (cmd->func_free) + (*cmd->func_free)(compile); + return RMAP_COMPILE_SUCCESS; + } + route_map_rule_delete(&index->match_list, rule); replaced = 1; } @@ -2803,6 +2813,13 @@ DEFUN (rmap_call, assert(index); + /* If "call" is invoked with the same route-map name as + * the one previously configured then, ignore the duplicate + * configuration. + */ + if (index->nextrm && (strcmp(index->nextrm, rmap) == 0)) + return CMD_SUCCESS; + if (index->nextrm) { route_map_upd8_dependency(RMAP_EVENT_CALL_DELETED, index->nextrm, index->map->name); diff --git a/lib/table.c b/lib/table.c index edba7f193..2d42e2d55 100644 --- a/lib/table.c +++ b/lib/table.c @@ -33,12 +33,14 @@ DEFINE_MTYPE(LIB, ROUTE_NODE, "Route node") static void route_table_free(struct route_table *); -static bool route_table_hash_cmp(const void *a, const void *b) +static int route_table_hash_cmp(const void *a, const void *b) { const struct prefix *pa = a, *pb = b; - return prefix_cmp(pa, pb) == 0; + return prefix_cmp(pa, pb); } +DECLARE_HASH(rn_hash_node, struct route_node, nodehash, route_table_hash_cmp, + prefix_hash_key) /* * route_table_init_with_delegate */ @@ -49,8 +51,7 @@ route_table_init_with_delegate(route_table_delegate_t *delegate) rt = XCALLOC(MTYPE_ROUTE_TABLE, sizeof(struct route_table)); rt->delegate = delegate; - rt->hash = hash_create(prefix_hash_key, route_table_hash_cmp, - "route table hash"); + rn_hash_node_init(&rt->hash); return rt; } @@ -69,15 +70,14 @@ static struct route_node *route_node_new(struct route_table *table) static struct route_node *route_node_set(struct route_table *table, const struct prefix *prefix) { - struct route_node *node, *inserted; + struct route_node *node; node = route_node_new(table); prefix_copy(&node->p, prefix); node->table = table; - inserted = hash_get(node->table->hash, node, hash_alloc_intern); - assert(inserted == node); + rn_hash_node_add(&node->table->hash, node); return node; } @@ -99,9 +99,6 @@ static void route_table_free(struct route_table *rt) if (rt == NULL) return; - hash_clean(rt->hash, NULL); - hash_free(rt->hash); - node = rt->top; /* Bulk deletion of nodes remaining in this table. This function is not @@ -123,6 +120,7 @@ static void route_table_free(struct route_table *rt) tmp_node->table->count--; tmp_node->lock = 0; /* to cause assert if unlocked after this */ + rn_hash_node_del(&rt->hash, tmp_node); route_node_free(rt, tmp_node); if (node != NULL) { @@ -137,6 +135,7 @@ static void route_table_free(struct route_table *rt) assert(rt->count == 0); + rn_hash_node_fini(&rt->hash); XFREE(MTYPE_ROUTE_TABLE, rt); return; } @@ -257,7 +256,7 @@ struct route_node *route_node_lookup(const struct route_table *table, prefix_copy(&p, pu.p); apply_mask(&p); - node = hash_get(table->hash, (void *)&p, NULL); + node = rn_hash_node_find(&table->hash, (void *)&p); return (node && node->info) ? route_lock_node(node) : NULL; } @@ -270,7 +269,7 @@ struct route_node *route_node_lookup_maynull(const struct route_table *table, prefix_copy(&p, pu.p); apply_mask(&p); - node = hash_get(table->hash, (void *)&p, NULL); + node = rn_hash_node_find(&table->hash, (void *)&p); return node ? route_lock_node(node) : NULL; } @@ -282,12 +281,11 @@ struct route_node *route_node_get(struct route_table *const table, struct route_node *new; struct route_node *node; struct route_node *match; - struct route_node *inserted; uint16_t prefixlen = p->prefixlen; const uint8_t *prefix = &p->u.prefix; apply_mask((struct prefix *)p); - node = hash_get(table->hash, (void *)p, NULL); + node = rn_hash_node_find(&table->hash, (void *)p); if (node && node->info) return route_lock_node(node); @@ -314,8 +312,7 @@ struct route_node *route_node_get(struct route_table *const table, new->p.family = p->family; new->table = table; set_link(new, node); - inserted = hash_get(node->table->hash, new, hash_alloc_intern); - assert(inserted == new); + rn_hash_node_add(&table->hash, new); if (match) set_link(match, new); @@ -367,7 +364,7 @@ void route_node_delete(struct route_node *node) node->table->count--; - hash_release(node->table->hash, node); + rn_hash_node_del(&node->table->hash, node); /* WARNING: FRAGILE CODE! * route_node_free may have the side effect of free'ing the entire diff --git a/lib/table.h b/lib/table.h index ce578e795..3e3fb658a 100644 --- a/lib/table.h +++ b/lib/table.h @@ -25,6 +25,7 @@ #include "memory.h" #include "hash.h" #include "prefix.h" +#include "typesafe.h" #ifdef __cplusplus extern "C" { @@ -59,10 +60,12 @@ struct route_table_delegate_t_ { route_table_destroy_node_func_t destroy_node; }; +PREDECL_HASH(rn_hash_node) + /* Routing table top structure. */ struct route_table { struct route_node *top; - struct hash *hash; + struct rn_hash_node_head hash; /* * Delegate that performs certain functions for this table. @@ -129,6 +132,7 @@ struct route_table { /* Lock of this radix */ \ unsigned int table_rdonly(lock); \ \ + struct rn_hash_node_item nodehash; \ /* Each node of route. */ \ void *info; \ diff --git a/lib/typesafe.h b/lib/typesafe.h index bbf3ce8f1..94002da59 100644 --- a/lib/typesafe.h +++ b/lib/typesafe.h @@ -275,7 +275,7 @@ macro_pure size_t prefix ## _count(struct prefix##_head *h) \ #define DECLARE_SORTLIST_UNIQ(prefix, type, field, cmpfn) \ _DECLARE_SORTLIST(prefix, type, field, cmpfn, cmpfn) \ \ -macro_inline type *prefix ## _find(struct prefix##_head *h, const type *item) \ +macro_inline type *prefix ## _find(const struct prefix##_head *h, const type *item) \ { \ struct ssort_item *sitem = h->sh.first; \ int cmpval = 0; \ @@ -383,7 +383,7 @@ macro_inline type *prefix ## _add(struct prefix##_head *h, type *item) \ *np = &item->field.hi; \ return NULL; \ } \ -macro_inline type *prefix ## _find(struct prefix##_head *h, const type *item) \ +macro_inline type *prefix ## _find(const struct prefix##_head *h, const type *item) \ { \ if (!h->hh.tabshift) \ return NULL; \ @@ -576,7 +576,7 @@ macro_inline int prefix ## __cmp(const struct sskip_item *a, \ return cmpfn(container_of(a, type, field.si), \ container_of(b, type, field.si)); \ } \ -macro_inline type *prefix ## _find(struct prefix##_head *h, const type *item) \ +macro_inline type *prefix ## _find(const struct prefix##_head *h, const type *item) \ { \ struct sskip_item *sitem = typesafe_skiplist_find(&h->sh, \ &item->field.si, &prefix ## __cmp); \ diff --git a/pimd/pim_upstream.c b/pimd/pim_upstream.c index b708e86a2..d829d0134 100644 --- a/pimd/pim_upstream.c +++ b/pimd/pim_upstream.c @@ -1181,8 +1181,16 @@ struct pim_upstream *pim_upstream_keep_alive_timer_proc( "kat expired on %s[%s]; remove stream reference", up->sg_str, pim->vrf->name); PIM_UPSTREAM_FLAG_UNSET_SRC_STREAM(up->flags); - up = pim_upstream_del(pim, up, __PRETTY_FUNCTION__); - } else if (PIM_UPSTREAM_FLAG_TEST_SRC_LHR(up->flags)) { + + /* Return if upstream entry got deleted.*/ + if (!pim_upstream_del(pim, up, __PRETTY_FUNCTION__)) + return NULL; + } + /* upstream reference would have been added to track the local + * membership if it is LHR. We have to clear it when KAT expires. + * Otherwise would result in stale entry with uncleared ref count. + */ + if (PIM_UPSTREAM_FLAG_TEST_SRC_LHR(up->flags)) { struct pim_upstream *parent = up->parent; PIM_UPSTREAM_FLAG_UNSET_SRC_LHR(up->flags); diff --git a/tools/checkpatch.pl b/tools/checkpatch.pl index 77e6e9a33..1b48d10a0 100755 --- a/tools/checkpatch.pl +++ b/tools/checkpatch.pl @@ -6347,6 +6347,35 @@ sub process { "Please, only use 32 bit atomics.\n" . $herecurr); } +# check for use of strcpy() + if ($line =~ /\bstrcpy\s*\(.*\)/) { + ERROR("STRCPY", + "strcpy() is error-prone; please use strlcpy()" . $herecurr); + } + +# check for use of strncpy() + if ($line =~ /\bstrncpy\s*\(.*\)/) { + WARN("STRNCPY", + "strncpy() is error-prone; please use strlcpy() if possible, or memcpy()" . $herecurr); + } + +# check for use of strcat() + if ($line =~ /\bstrcat\s*\(.*\)/) { + ERROR("STRCAT", + "strcat() is error-prone; please use strlcat() if possible" . $herecurr); + } + +# check for use of strncat() + if ($line =~ /\bstrncat\s*\(.*\)/) { + WARN("STRNCAT", + "strncat() is error-prone; please use strlcat() if possible" . $herecurr); + } + +# check for use of bzero() + if ($line =~ /\bbzero\s*\(.*\)/) { + ERROR("BZERO", + "bzero() is deprecated; use memset()" . $herecurr); + } } # If we have no input at all, then there is nothing to report on diff --git a/vtysh/vtysh.c b/vtysh/vtysh.c index eff1e996e..24effa704 100644 --- a/vtysh/vtysh.c +++ b/vtysh/vtysh.c @@ -502,7 +502,7 @@ static int vtysh_execute_func(const char *line, int pager) vtysh_execute("exit"); } else if (tried) { vtysh_execute("end"); - vtysh_execute("configure terminal"); + vtysh_execute("configure"); } } /* @@ -540,7 +540,7 @@ static int vtysh_execute_func(const char *line, int pager) if (pager && strncmp(line, "exit", 4)) vty_open_pager(vty); - if (!strcmp(cmd->string, "configure terminal")) { + if (!strcmp(cmd->string, "configure")) { for (i = 0; i < array_size(vtysh_client); i++) { cmd_stat = vtysh_client_execute( &vtysh_client[i], line); @@ -674,7 +674,7 @@ int vtysh_mark_file(const char *filename) vty->node = CONFIG_NODE; vtysh_execute_no_pager("enable"); - vtysh_execute_no_pager("configure terminal"); + vtysh_execute_no_pager("configure"); vty_buf_copy = XCALLOC(MTYPE_VTYSH_CMD, VTY_BUFSIZ); while (fgets(vty->buf, VTY_BUFSIZ, confp)) { @@ -1744,7 +1744,7 @@ DEFUNSH(VTYSH_REALLYALL, vtysh_disable, vtysh_disable_cmd, "disable", } DEFUNSH(VTYSH_REALLYALL, vtysh_config_terminal, vtysh_config_terminal_cmd, - "configure terminal", + "configure [terminal]", "Configuration from vty interface\n" "Configuration terminal\n") { @@ -1786,7 +1786,7 @@ static int vtysh_exit(struct vty *vty) case BFD_NODE: case RPKI_NODE: vtysh_execute("end"); - vtysh_execute("configure terminal"); + vtysh_execute("configure"); vty->node = CONFIG_NODE; break; case BGP_VPNV4_NODE: diff --git a/zebra/rib.h b/zebra/rib.h index e26831e1a..8a59cea6d 100644 --- a/zebra/rib.h +++ b/zebra/rib.h @@ -24,6 +24,7 @@ #include "zebra.h" #include "hook.h" +#include "typesafe.h" #include "linklist.h" #include "prefix.h" #include "table.h" @@ -39,13 +40,52 @@ extern "C" { #endif +typedef enum { RNH_NEXTHOP_TYPE, RNH_IMPORT_CHECK_TYPE } rnh_type_t; + +PREDECL_LIST(rnh_list) + +/* Nexthop structure. */ +struct rnh { + uint8_t flags; + +#define ZEBRA_NHT_CONNECTED 0x1 +#define ZEBRA_NHT_DELETED 0x2 +#define ZEBRA_NHT_EXACT_MATCH 0x4 + + /* VRF identifier. */ + vrf_id_t vrf_id; + + afi_t afi; + + rnh_type_t type; + + uint32_t seqno; + + struct route_entry *state; + struct prefix resolved_route; + struct list *client_list; + + /* pseudowires dependent on this nh */ + struct list *zebra_pseudowire_list; + + struct route_node *node; + + /* + * if this has been filtered for the client + */ + int filtered[ZEBRA_ROUTE_MAX]; + + struct rnh_list_item rnh_list_item; +}; + #define DISTANCE_INFINITY 255 #define ZEBRA_KERNEL_TABLE_MAX 252 /* support for no more than this rt tables */ +PREDECL_LIST(re_list) + struct route_entry { /* Link list. */ - struct route_entry *next; - struct route_entry *prev; + struct re_list_item next; /* Nexthop structure */ struct nexthop_group ng; @@ -135,7 +175,7 @@ typedef struct rib_dest_t_ { /* * Doubly-linked list of routes for this prefix. */ - struct route_entry *routes; + struct re_list_head routes; struct route_entry *selected_fib; @@ -151,7 +191,7 @@ typedef struct rib_dest_t_ { * the data plane we will run evaluate_rnh * on these prefixes. */ - struct list *nht; + struct rnh_list_head nht; /* * Linkage to put dest on the FPM processing queue. @@ -160,6 +200,9 @@ typedef struct rib_dest_t_ { } rib_dest_t; +DECLARE_LIST(rnh_list, struct rnh, rnh_list_item); +DECLARE_LIST(re_list, struct route_entry, next); + #define RIB_ROUTE_QUEUED(x) (1 << (x)) // If MQ_SIZE is modified this value needs to be updated. #define RIB_ROUTE_ANY_QUEUED 0x1F @@ -187,14 +230,16 @@ typedef struct rib_dest_t_ { * Macro to iterate over each route for a destination (prefix). */ #define RE_DEST_FOREACH_ROUTE(dest, re) \ - for ((re) = (dest) ? (dest)->routes : NULL; (re); (re) = (re)->next) + for ((re) = (dest) ? re_list_first(&((dest)->routes)) : NULL; (re); \ + (re) = re_list_next(&((dest)->routes), (re))) /* * Same as above, but allows the current node to be unlinked. */ #define RE_DEST_FOREACH_ROUTE_SAFE(dest, re, next) \ - for ((re) = (dest) ? (dest)->routes : NULL; \ - (re) && ((next) = (re)->next, 1); (re) = (next)) + for ((re) = (dest) ? re_list_first(&((dest)->routes)) : NULL; \ + (re) && ((next) = re_list_next(&((dest)->routes), (re)), 1); \ + (re) = (next)) #define RNODE_FOREACH_RE(rn, re) \ RE_DEST_FOREACH_ROUTE (rib_dest_from_rnode(rn), re) @@ -406,7 +451,7 @@ static inline struct route_entry *rnode_to_ribs(struct route_node *rn) if (!dest) return NULL; - return dest->routes; + return re_list_first(&dest->routes); } /* diff --git a/zebra/zebra_rib.c b/zebra/zebra_rib.c index 2945a5ef9..3623852af 100644 --- a/zebra/zebra_rib.c +++ b/zebra/zebra_rib.c @@ -1174,7 +1174,7 @@ static void rib_uninstall(struct route_node *rn, struct route_entry *re) */ static int rib_can_delete_dest(rib_dest_t *dest) { - if (dest->routes) { + if (re_list_first(&dest->routes)) { return 0; } @@ -1202,7 +1202,6 @@ static int rib_can_delete_dest(rib_dest_t *dest) void zebra_rib_evaluate_rn_nexthops(struct route_node *rn, uint32_t seq) { rib_dest_t *dest = rib_dest_from_rnode(rn); - struct listnode *node, *nnode; struct rnh *rnh; /* @@ -1234,7 +1233,7 @@ void zebra_rib_evaluate_rn_nexthops(struct route_node *rn, uint32_t seq) * nht resolution and as such we need to call the * nexthop tracking evaluation code */ - for (ALL_LIST_ELEMENTS(dest->nht, node, nnode, rnh)) { + for_each (rnh_list, &dest->nht, rnh) { struct zebra_vrf *zvrf = zebra_vrf_lookup_by_id(rnh->vrf_id); struct prefix *p = &rnh->node->p; @@ -1310,7 +1309,7 @@ int rib_gc_dest(struct route_node *rn) zebra_rib_evaluate_rn_nexthops(rn, zebra_router_get_next_sequence()); dest->rnode = NULL; - list_delete(&dest->nht); + rnh_list_fini(&dest->nht); XFREE(MTYPE_RIB_DEST, dest); rn->info = NULL; @@ -2355,7 +2354,7 @@ rib_dest_t *zebra_rib_create_dest(struct route_node *rn) rib_dest_t *dest; dest = XCALLOC(MTYPE_RIB_DEST, sizeof(rib_dest_t)); - dest->nht = list_new(); + rnh_list_init(&dest->nht); route_lock_node(rn); /* rn route table reference */ rn->info = dest; dest->rnode = rn; @@ -2403,7 +2402,6 @@ rib_dest_t *zebra_rib_create_dest(struct route_node *rn) /* Add RE to head of the route node. */ static void rib_link(struct route_node *rn, struct route_entry *re, int process) { - struct route_entry *head; rib_dest_t *dest; afi_t afi; const char *rmap_name; @@ -2418,12 +2416,7 @@ static void rib_link(struct route_node *rn, struct route_entry *re, int process) dest = zebra_rib_create_dest(rn); } - head = dest->routes; - if (head) { - head->prev = re; - } - re->next = head; - dest->routes = re; + re_list_add_head(&dest->routes, re); afi = (rn->p.family == AF_INET) ? AFI_IP @@ -2473,14 +2466,7 @@ void rib_unlink(struct route_node *rn, struct route_entry *re) dest = rib_dest_from_rnode(rn); - if (re->next) - re->next->prev = re->prev; - - if (re->prev) - re->prev->next = re->next; - else { - dest->routes = re->next; - } + re_list_del(&dest->routes, re); if (dest->selected_fib == re) dest->selected_fib = NULL; diff --git a/zebra/zebra_rnh.c b/zebra/zebra_rnh.c index 220a8006d..2917d0e7a 100644 --- a/zebra/zebra_rnh.c +++ b/zebra/zebra_rnh.c @@ -119,7 +119,7 @@ static void zebra_rnh_remove_from_routing_table(struct rnh *rnh) } dest = rib_dest_from_rnode(rn); - listnode_delete(dest->nht, rnh); + rnh_list_del(&dest->nht, rnh); route_unlock_node(rn); } @@ -145,7 +145,7 @@ static void zebra_rnh_store_in_routing_table(struct rnh *rnh) } dest = rib_dest_from_rnode(rn); - listnode_add(dest->nht, rnh); + rnh_list_add_tail(&dest->nht, rnh); route_unlock_node(rn); } @@ -251,7 +251,7 @@ void zebra_free_rnh(struct rnh *rnh) route_unlock_node(rern); dest = rib_dest_from_rnode(rern); - listnode_delete(dest->nht, rnh); + rnh_list_del(&dest->nht, rnh); } } free_state(rnh->vrf_id, rnh->state, rnh->node); diff --git a/zebra/zebra_rnh.h b/zebra/zebra_rnh.h index 9cd9116ee..95a394118 100644 --- a/zebra/zebra_rnh.h +++ b/zebra/zebra_rnh.h @@ -29,40 +29,6 @@ extern "C" { #endif -typedef enum { RNH_NEXTHOP_TYPE, RNH_IMPORT_CHECK_TYPE } rnh_type_t; - -/* Nexthop structure. */ -struct rnh { - uint8_t flags; - -#define ZEBRA_NHT_CONNECTED 0x1 -#define ZEBRA_NHT_DELETED 0x2 -#define ZEBRA_NHT_EXACT_MATCH 0x4 - - /* VRF identifier. */ - vrf_id_t vrf_id; - - afi_t afi; - - rnh_type_t type; - - uint32_t seqno; - - struct route_entry *state; - struct prefix resolved_route; - struct list *client_list; - - /* pseudowires dependent on this nh */ - struct list *zebra_pseudowire_list; - - struct route_node *node; - - /* - * if this has been filtered for the client - */ - int filtered[ZEBRA_ROUTE_MAX]; -}; - extern int zebra_rnh_ip_default_route; extern int zebra_rnh_ipv6_default_route; diff --git a/zebra/zebra_vrf.c b/zebra/zebra_vrf.c index 315d5b490..5a18534ac 100644 --- a/zebra/zebra_vrf.c +++ b/zebra/zebra_vrf.c @@ -355,7 +355,7 @@ void zebra_rtable_node_cleanup(struct route_table *table, if (node->info) { rib_dest_t *dest = node->info; - list_delete(&dest->nht); + rnh_list_fini(&dest->nht); XFREE(MTYPE_RIB_DEST, node->info); } }