diff options
author | Donald Sharp <sharpd@cumulusnetworks.com> | 2019-09-25 02:40:08 +0200 |
---|---|---|
committer | Donald Sharp <sharpd@cumulusnetworks.com> | 2019-09-25 15:26:24 +0200 |
commit | 0f9f74baeb97f437d7acf7feda0f400d50943c4c (patch) | |
tree | de20395258870f3baa322acce995f8fbab74687d /ospf6d/ospf6_lsdb.c | |
parent | isisd: circuit is derefed in every code path (diff) | |
download | frr-0f9f74baeb97f437d7acf7feda0f400d50943c4c.tar.xz frr-0f9f74baeb97f437d7acf7feda0f400d50943c4c.zip |
ospf6d: Prevent use after free
the for (ALL_LSDB...) macro was iterating over lsa,
when lsa had just been freed in these functions.
Remove the macro and make the adjustments saving lsa_next
before the free.
Signed-off-by: Donald Sharp <sharpd@cumulusnetworks.com>
Diffstat (limited to 'ospf6d/ospf6_lsdb.c')
-rw-r--r-- | ospf6d/ospf6_lsdb.c | 15 |
1 files changed, 11 insertions, 4 deletions
diff --git a/ospf6d/ospf6_lsdb.c b/ospf6d/ospf6_lsdb.c index b551dbdfa..0a9f1c6f7 100644 --- a/ospf6d/ospf6_lsdb.c +++ b/ospf6d/ospf6_lsdb.c @@ -298,13 +298,17 @@ struct ospf6_lsa *ospf6_lsdb_next(const struct route_node *iterend, void ospf6_lsdb_remove_all(struct ospf6_lsdb *lsdb) { - struct ospf6_lsa *lsa; + struct ospf6_lsa *lsa, *lsa_next; + const struct route_node *iterend; if (lsdb == NULL) return; - for (ALL_LSDB(lsdb, lsa)) + for (iterend = ospf6_lsdb_head(lsdb, 0, 0, 0, &lsa); lsa; + lsa = lsa_next) { + lsa_next = ospf6_lsdb_next(iterend, lsa); ospf6_lsdb_remove(lsa, lsdb); + } } void ospf6_lsdb_lsa_unlock(struct ospf6_lsa *lsa) @@ -319,9 +323,12 @@ void ospf6_lsdb_lsa_unlock(struct ospf6_lsa *lsa) int ospf6_lsdb_maxage_remover(struct ospf6_lsdb *lsdb) { int reschedule = 0; - struct ospf6_lsa *lsa; + struct ospf6_lsa *lsa, *lsa_next; + const struct route_node *iterend; - for (ALL_LSDB(lsdb, lsa)) { + for (iterend = ospf6_lsdb_head(lsdb, 0, 0, 0, &lsa); lsa; + lsa = lsa_next) { + lsa_next = ospf6_lsdb_next(iterend, lsa); if (!OSPF6_LSA_IS_MAXAGE(lsa)) continue; if (lsa->retrans_count != 0) { |