diff options
| author | Donatas Abraitis <donatas@opensourcerouting.org> | 2023-05-18 10:24:41 +0300 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2023-05-18 10:24:41 +0300 |
| commit | a8bc67a989a203d2fb51748eb73bb02dbe706f6f (patch) | |
| tree | f3340122ade587c91b421069e2bfbe2005deb934 /lib | |
| parent | c374605ecb4a33005a0ee826b62c3a7ae27fc695 (diff) | |
| parent | accafb6b787d1c92d54104f6eba03c1e7217e513 (diff) | |
Merge pull request #13369 from samanvithab/bgpd_fix
lib : fix duplicate prefix list delete
Diffstat (limited to 'lib')
| -rw-r--r-- | lib/plist.c | 39 |
1 files changed, 33 insertions, 6 deletions
diff --git a/lib/plist.c b/lib/plist.c index e286a32f92..d8ce83d219 100644 --- a/lib/plist.c +++ b/lib/plist.c @@ -336,6 +336,22 @@ prefix_list_entry_lookup(struct prefix_list *plist, struct prefix *prefix, return NULL; } +static bool +prefix_list_entry_lookup_prefix(struct prefix_list *plist, + struct prefix_list_entry *plist_entry) +{ + struct prefix_list_entry *pentry = NULL; + + for (pentry = plist->head; pentry; pentry = pentry->next) { + if (pentry == plist_entry) + continue; + if (prefix_same(&pentry->prefix, &plist_entry->prefix)) + return true; + } + + return false; +} + static void trie_walk_affected(size_t validbits, struct pltrie_table *table, uint8_t byte, struct prefix_list_entry *object, void (*fn)(struct prefix_list_entry *object, @@ -404,12 +420,16 @@ static void prefix_list_trie_del(struct prefix_list *plist, void prefix_list_entry_delete(struct prefix_list *plist, - struct prefix_list_entry *pentry, - int update_list) + struct prefix_list_entry *pentry, int update_list) { + bool duplicate = false; + if (plist == NULL || pentry == NULL) return; + if (prefix_list_entry_lookup_prefix(plist, pentry)) + duplicate = true; + prefix_list_trie_del(plist, pentry); if (pentry->prev) @@ -421,8 +441,10 @@ void prefix_list_entry_delete(struct prefix_list *plist, else plist->tail = pentry->prev; - route_map_notify_pentry_dependencies(plist->name, pentry, - RMAP_EVENT_PLIST_DELETED); + if (!duplicate) + route_map_notify_pentry_dependencies(plist->name, pentry, + RMAP_EVENT_PLIST_DELETED); + prefix_list_entry_free(pentry); plist->count--; @@ -557,11 +579,15 @@ static void prefix_list_entry_add(struct prefix_list *plist, void prefix_list_entry_update_start(struct prefix_list_entry *ple) { struct prefix_list *pl = ple->pl; + bool duplicate = false; /* Not installed, nothing to do. */ if (!ple->installed) return; + if (prefix_list_entry_lookup_prefix(pl, ple)) + duplicate = true; + prefix_list_trie_del(pl, ple); /* List manipulation: shameless copy from `prefix_list_entry_delete`. */ @@ -574,8 +600,9 @@ void prefix_list_entry_update_start(struct prefix_list_entry *ple) else pl->tail = ple->prev; - route_map_notify_pentry_dependencies(pl->name, ple, - RMAP_EVENT_PLIST_DELETED); + if (!duplicate) + route_map_notify_pentry_dependencies(pl->name, ple, + RMAP_EVENT_PLIST_DELETED); pl->count--; route_map_notify_dependencies(pl->name, RMAP_EVENT_PLIST_DELETED); |
