diff options
author | Florin Coras <fcoras@cisco.com> | 2017-09-28 23:49:42 -0400 |
---|---|---|
committer | Damjan Marion <dmarion.lists@gmail.com> | 2017-10-03 11:05:55 +0000 |
commit | a096f2d182537cb292241af4cc842d21e5369617 (patch) | |
tree | c4002e227655714b9b5c8e4c3029261ca5907198 /src/vnet/tcp/tcp.c | |
parent | b4d3c96f89bb832203092dcc94eeaa11a906594c (diff) |
tcp: updates to connection closing procedure (VPP-996)
- add separate TIME_WAIT time constant
- fix output node for TIME_WAIT acks
- ensure snd_nxt is snd_una_max after retransmitting fin
- debugging improvements
Change-Id: Ic947153346979853f2526824b229126e47aead86
Signed-off-by: Florin Coras <fcoras@cisco.com>
Diffstat (limited to 'src/vnet/tcp/tcp.c')
-rw-r--r-- | src/vnet/tcp/tcp.c | 37 |
1 files changed, 34 insertions, 3 deletions
diff --git a/src/vnet/tcp/tcp.c b/src/vnet/tcp/tcp.c index 38a21dbbdd6..2a705d01b4c 100644 --- a/src/vnet/tcp/tcp.c +++ b/src/vnet/tcp/tcp.c @@ -314,19 +314,22 @@ tcp_connection_close (tcp_connection_t * tc) tc->state = TCP_STATE_FIN_WAIT_1; break; case TCP_STATE_CLOSE_WAIT: + tcp_connection_timers_reset (tc); tcp_send_fin (tc); tc->state = TCP_STATE_LAST_ACK; + tcp_timer_update (tc, TCP_TIMER_WAITCLOSE, TCP_2MSL_TIME); break; case TCP_STATE_FIN_WAIT_1: + tcp_timer_update (tc, TCP_TIMER_WAITCLOSE, TCP_2MSL_TIME); break; default: - clib_warning ("state: %u", tc->state); + TCP_DBG ("state: %u", tc->state); } TCP_EVT_DBG (TCP_EVT_STATE_CHANGE, tc); /* If in CLOSED and WAITCLOSE timer is not set, delete connection now */ - if (tc->timers[TCP_TIMER_WAITCLOSE] == TCP_TIMER_HANDLE_INVALID + if (!tcp_timer_is_active (tc, TCP_TIMER_WAITCLOSE) && tc->state == TCP_STATE_CLOSED) tcp_connection_del (tc); } @@ -344,6 +347,7 @@ tcp_session_cleanup (u32 conn_index, u32 thread_index) { tcp_connection_t *tc; tc = tcp_connection_get (conn_index, thread_index); + tcp_connection_timers_reset (tc); /* Wait for the session tx events to clear */ tc->state = TCP_STATE_CLOSED; @@ -748,6 +752,31 @@ format_tcp_state (u8 * s, va_list * args) return s; } +const char *tcp_connection_flags_str[] = { +#define _(sym, str) str, + foreach_tcp_connection_flag +#undef _ +}; + +u8 * +format_tcp_connection_flags (u8 * s, va_list * args) +{ + tcp_connection_t *tc = va_arg (*args, tcp_connection_t *); + int i, last = -1; + + for (i = 0; i < TCP_CONN_N_FLAG_BITS; i++) + if (tc->flags & (1 << i)) + last = i; + for (i = 0; i < last; i++) + { + if (tc->flags & (1 << i)) + s = format (s, "%s, ", tcp_connection_flags_str[i]); + } + if (last >= 0) + s = format (s, "%s", tcp_connection_flags_str[last]); + return s; +} + const char *tcp_conn_timers[] = { #define _(sym, str) str, foreach_tcp_timer @@ -796,6 +825,8 @@ u8 * format_tcp_vars (u8 * s, va_list * args) { tcp_connection_t *tc = va_arg (*args, tcp_connection_t *); + s = format (s, " flags: %U timers: %U\n", format_tcp_connection_flags, tc, + format_tcp_timers, tc); s = format (s, " snd_una %u snd_nxt %u snd_una_max %u", tc->snd_una - tc->iss, tc->snd_nxt - tc->iss, tc->snd_una_max - tc->iss); @@ -866,7 +897,7 @@ format_tcp_connection (u8 * s, va_list * args) { s = format (s, "%-15U", format_tcp_state, tc->state); if (verbose > 1) - s = format (s, " %U\n%U", format_tcp_timers, tc, format_tcp_vars, tc); + s = format (s, "\n%U", format_tcp_vars, tc); } return s; |