diff options
author | Marco Varlese <marco.varlese@suse.com> | 2018-02-06 13:48:30 +0100 |
---|---|---|
committer | Florin Coras <florin.coras@gmail.com> | 2018-02-06 17:44:23 +0000 |
commit | df5a99cef13ff6a22c195091be45152dc65f5d71 (patch) | |
tree | 229afaffac54a30e0c318c0e5d35c440dd364a5b /src/vnet/sctp/sctp.c | |
parent | e060ed1e1891f0fdf88b53865eccded38728f44c (diff) |
SCTP: handling of heartbeating and max-retransmits
This patch address the need to send/receive heartbeats between peers.
At the same time, the number of unacked heartbeats is tracked and when
the peer requests to send DATA to the remote-peer the value of unacked
heartbeats needs to be checked against the maximum value allowed for
retransmissions. If the unacked heartbeats value is higher then the
remote-peer is considered unreachable and the connetion needs to be
shutdown.
Change-Id: I2b1a21c26775e734dbe82486f40982ed5702dc63
Signed-off-by: Marco Varlese <marco.varlese@suse.com>
Diffstat (limited to 'src/vnet/sctp/sctp.c')
-rw-r--r-- | src/vnet/sctp/sctp.c | 49 |
1 files changed, 29 insertions, 20 deletions
diff --git a/src/vnet/sctp/sctp.c b/src/vnet/sctp/sctp.c index f8cd21c63ec..61c0252b1ba 100644 --- a/src/vnet/sctp/sctp.c +++ b/src/vnet/sctp/sctp.c @@ -606,33 +606,43 @@ sctp_expired_timers_cb (u32 conn_index, u32 timer_id) /* note: the connection may have already disappeared */ if (PREDICT_FALSE (sctp_conn == 0)) return; - ASSERT (sctp_conn->state == SCTP_STATE_COOKIE_ECHOED); + + SCTP_DBG ("%s expired", sctp_timer_to_string (timer_id)); switch (timer_id) { + case SCTP_TIMER_T1_INIT: + case SCTP_TIMER_T1_COOKIE: + case SCTP_TIMER_T2_SHUTDOWN: + case SCTP_TIMER_T3_RXTX: + clib_smp_atomic_add (&sctp_conn->sub_conn[conn_index].unacknowledged_hb, + 1); + sctp_timer_reset (sctp_conn, conn_index, timer_id); + break; case SCTP_TIMER_T4_HEARTBEAT: - { - clib_warning ("Heartbeat timeout"); - break; - } + sctp_timer_reset (sctp_conn, conn_index, timer_id); + goto heartbeat; } - /* Start cleanup. App wasn't notified yet so use delete notify as - * opposed to delete to cleanup session layer state. */ - stream_session_delete_notify (&sctp_conn-> - sub_conn[MAIN_SCTP_SUB_CONN_IDX].connection); - sctp_connection_timers_reset (sctp_conn); + if (sctp_conn->sub_conn[conn_index].unacknowledged_hb > + SCTP_ASSOCIATION_MAX_RETRANS) + { + // The remote-peer is considered to be unreachable hence shutting down - sctp_connection_cleanup (sctp_conn); -} + /* Start cleanup. App wasn't notified yet so use delete notify as + * opposed to delete to cleanup session layer state. */ + stream_session_delete_notify (&sctp_conn->sub_conn + [MAIN_SCTP_SUB_CONN_IDX].connection); -/* *INDENT OFF* */ -static sctp_timer_expiration_handler - * sctp_timer_expiration_handlers[SCTP_N_TIMERS] = { - sctp_expired_timers_cb -}; + sctp_connection_timers_reset (sctp_conn); -/* *INDENT ON* */ + sctp_connection_cleanup (sctp_conn); + } + return; + +heartbeat: + sctp_send_heartbeat (sctp_conn); +} static void sctp_expired_timers_dispatch (u32 * expired_timers) @@ -649,8 +659,7 @@ sctp_expired_timers_dispatch (u32 * expired_timers) SCTP_DBG ("Expired timer ID: %u", timer_id); /* Handle expiration */ - (*sctp_timer_expiration_handlers[timer_id]) (connection_index, - timer_id); + sctp_expired_timers_cb (connection_index, timer_id); } } |