diff --git a/nest/iface.h b/nest/iface.h index 6e8c8448..87ad86cf 100644 --- a/nest/iface.h +++ b/nest/iface.h @@ -160,7 +160,7 @@ neighbor *neigh_find(struct proto *p, ip_addr a, struct iface *ifa, uint flags); void neigh_dump(neighbor *); void neigh_dump_all(void); -void neigh_prune(void); +void neigh_prune(struct proto *p); void neigh_if_up(struct iface *); void neigh_if_down(struct iface *); void neigh_if_link(struct iface *); diff --git a/nest/neighbor.c b/nest/neighbor.c index e4d42b4d..7b951366 100644 --- a/nest/neighbor.c +++ b/nest/neighbor.c @@ -61,6 +61,7 @@ static slab *neigh_slab; static list neigh_hash_table[NEIGH_HASH_SIZE], sticky_neigh_list; static void neigh_do_notify(void *); static void neigh_do_notify_main(void *); +static void neigh_free(neighbor *n); static inline uint neigh_hash(struct proto *p, ip_addr a, struct iface *i) @@ -372,6 +373,9 @@ neigh_do_notify(void *data) if (n->proto->proto_state != PS_STOP) n->proto->neigh_notify(n); + + if ((n->scope < 0) && !(n->flags & NEF_STICKY)) + neigh_free(n); } static void @@ -402,7 +406,7 @@ neigh_down(neighbor *n) neigh_notify(n); } -static inline void +static void neigh_free(neighbor *n) { ASSERT_DIE(birdloop_inside(n->proto->loop)); @@ -480,12 +484,6 @@ neigh_update(neighbor *n, struct iface *iface) if (n->scope >= 0) neigh_down(n); - if ((n->scope < 0) && !(n->flags & NEF_STICKY)) - { - neigh_free(n); - return; - } - if (scope >= 0) neigh_up(n, iface, ifa, scope); } @@ -630,7 +628,7 @@ neigh_prune_one(neighbor *n) * is shut down to get rid of all its heritage. */ void -neigh_prune(void) +neigh_prune(struct proto *p) { neighbor *n; node *m; @@ -641,7 +639,8 @@ neigh_prune(void) DBG("Pruning neighbors\n"); for(i=0; iproto == p) + neigh_prune_one(n); IFACE_UNLOCK; } diff --git a/nest/proto.c b/nest/proto.c index 1e7f5560..3ba8ac5c 100644 --- a/nest/proto.c +++ b/nest/proto.c @@ -2434,7 +2434,7 @@ static void proto_do_down(struct proto *p) { p->down_code = 0; - neigh_prune(); + neigh_prune(p); /* Shutdown is finished in the protocol event */ if (proto_is_done(p))