summaryrefslogtreecommitdiff
path: root/proto
diff options
context:
space:
mode:
authorOndrej Zajicek (work) <santiago@crfreenet.org>2019-02-03 17:31:27 +0100
committerOndrej Zajicek (work) <santiago@crfreenet.org>2019-02-03 17:31:27 +0100
commit16605f2fdad730b8bb570e17192dc5f45cf15d3f (patch)
treed463373e209fd4cacdd621e56527ada6d3664a14 /proto
parent9c94583a3ded3b2792bd08d88beb10100a82d7b4 (diff)
OSPF: Reject duplicate DBDES packets after dead interval
Master may free last DBDES packet immediately. Slave must wait dead interval before freeing last DBDES packet and then reject duplicate DBDES packets with SeqNumberMismatch.
Diffstat (limited to 'proto')
-rw-r--r--proto/ospf/dbdes.c13
-rw-r--r--proto/ospf/neighbor.c6
-rw-r--r--proto/ospf/ospf.h1
3 files changed, 20 insertions, 0 deletions
diff --git a/proto/ospf/dbdes.c b/proto/ospf/dbdes.c
index 4d3bbe8c..a1559782 100644
--- a/proto/ospf/dbdes.c
+++ b/proto/ospf/dbdes.c
@@ -238,6 +238,14 @@ ospf_rxmt_dbdes(struct ospf_proto *p, struct ospf_neighbor *n)
ospf_do_send_dbdes(p, n);
}
+void
+ospf_reset_ldd(struct ospf_proto *p UNUSED, struct ospf_neighbor *n)
+{
+ mb_free(n->ldd_buffer);
+ n->ldd_buffer = NULL;
+ n->ldd_bsize = 0;
+}
+
static int
ospf_process_dbdes(struct ospf_proto *p, struct ospf_packet *pkt, struct ospf_neighbor *n)
{
@@ -434,6 +442,7 @@ ospf_receive_dbdes(struct ospf_packet *pkt, struct ospf_iface *ifa,
if (!(n->myimms & DBDES_M) && !(n->imms & DBDES_M))
{
tm_stop(n->dbdes_timer);
+ ospf_reset_ldd(p, n);
ospf_neigh_sm(n, INM_EXDONE);
break;
}
@@ -457,7 +466,11 @@ ospf_receive_dbdes(struct ospf_packet *pkt, struct ospf_iface *ifa,
ospf_send_dbdes(p, n);
if (!(n->myimms & DBDES_M) && !(n->imms & DBDES_M))
+ {
+ /* Use dbdes timer to postpone freeing of Last DBDES packet buffer */
+ tm_start(n->dbdes_timer, n->ifa->deadint S);
ospf_neigh_sm(n, INM_EXDONE);
+ }
}
break;
diff --git a/proto/ospf/neighbor.c b/proto/ospf/neighbor.c
index 54d643c6..c143b130 100644
--- a/proto/ospf/neighbor.c
+++ b/proto/ospf/neighbor.c
@@ -608,6 +608,12 @@ dbdes_timer_hook(timer *t)
if ((n->state == NEIGHBOR_EXCHANGE) && (n->myimms & DBDES_MS))
ospf_rxmt_dbdes(p, n);
+
+ if ((n->state > NEIGHBOR_LOADING) && !(n->myimms & DBDES_MS))
+ {
+ ospf_reset_ldd(p, n);
+ tm_stop(n->dbdes_timer);
+ }
}
static void
diff --git a/proto/ospf/ospf.h b/proto/ospf/ospf.h
index 23289ccd..d3f12738 100644
--- a/proto/ospf/ospf.h
+++ b/proto/ospf/ospf.h
@@ -1041,6 +1041,7 @@ uint ospf_hello3_options(struct ospf_packet *pkt);
/* dbdes.c */
void ospf_send_dbdes(struct ospf_proto *p, struct ospf_neighbor *n);
void ospf_rxmt_dbdes(struct ospf_proto *p, struct ospf_neighbor *n);
+void ospf_reset_ldd(struct ospf_proto *p, struct ospf_neighbor *n);
void ospf_receive_dbdes(struct ospf_packet *pkt, struct ospf_iface *ifa, struct ospf_neighbor *n);
uint ospf_dbdes3_options(struct ospf_packet *pkt);