summaryrefslogtreecommitdiffstats
path: root/src/vnet/tcp
diff options
context:
space:
mode:
authorPierre Pfister <ppfister@cisco.com>2017-09-20 08:48:36 +0200
committerDave Wallace <dwallacelf@gmail.com>2017-09-20 13:43:36 +0000
commit7fe51f3e3e80ed6ffe989df1c6963527166afc25 (patch)
tree4b007227cfb4949066901cbaca6a1158e235303a /src/vnet/tcp
parent440751b91804947a7c9b533570531cac79629016 (diff)
tcp: add option to punt traffic
Until now, if the stack didn't find a connection for a packet, it sent back a reset. With the punt option enabled, packets are now enqueued to error-punt where they can be handed off to the host os. Change-Id: I12dea8694b8bd24c92b0d601412928aa7b8046cb Signed-off-by: Florin Coras <fcoras@cisco.com> Signed-off-by: Pierre Pfister <ppfister@cisco.com>
Diffstat (limited to 'src/vnet/tcp')
-rw-r--r--src/vnet/tcp/tcp.c33
-rw-r--r--src/vnet/tcp/tcp.h5
-rw-r--r--src/vnet/tcp/tcp_error.def3
-rw-r--r--src/vnet/tcp/tcp_input.c22
4 files changed, 57 insertions, 6 deletions
diff --git a/src/vnet/tcp/tcp.c b/src/vnet/tcp/tcp.c
index f779428fbaf..f457ef7e536 100644
--- a/src/vnet/tcp/tcp.c
+++ b/src/vnet/tcp/tcp.c
@@ -1398,6 +1398,16 @@ vnet_tcp_enable_disable (vlib_main_t * vm, u8 is_en)
return 0;
}
+void
+tcp_punt_unknown (vlib_main_t * vm, u8 is_ip4, u8 is_add)
+{
+ tcp_main_t *tm = &tcp_main;
+ if (is_ip4)
+ tm->punt_unknown4 = is_add;
+ else
+ tm->punt_unknown6 = is_add;
+}
+
clib_error_t *
tcp_init (vlib_main_t * vm)
{
@@ -1893,6 +1903,29 @@ VLIB_CLI_COMMAND (tcp_replay_scoreboard_command, static) =
};
/* *INDENT-ON* */
+static clib_error_t *
+show_tcp_punt_fn (vlib_main_t * vm, unformat_input_t * input,
+ vlib_cli_command_t * cmd_arg)
+{
+ tcp_main_t *tm = vnet_get_tcp_main ();
+ if (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
+ return clib_error_return (0, "unknown input `%U'", format_unformat_error,
+ input);
+ vlib_cli_output (vm, "IPv4 TCP punt: %s",
+ tm->punt_unknown4 ? "enabled" : "disabled");
+ vlib_cli_output (vm, "IPv6 TCP punt: %s",
+ tm->punt_unknown6 ? "enabled" : "disabled");
+ return 0;
+}
+/* *INDENT-OFF* */
+VLIB_CLI_COMMAND (show_tcp_punt_command, static) =
+{
+ .path = "show tcp punt",
+ .short_help = "show tcp punt",
+ .function = show_tcp_punt_fn,
+};
+/* *INDENT-ON* */
+
/*
* fd.io coding-style-patch-verification: ON
*
diff --git a/src/vnet/tcp/tcp.h b/src/vnet/tcp/tcp.h
index bb8091af84f..259dbca1519 100644
--- a/src/vnet/tcp/tcp.h
+++ b/src/vnet/tcp/tcp.h
@@ -417,6 +417,9 @@ typedef struct _tcp_main
/** vlib buffer size */
u32 bytes_per_buffer;
+
+ u8 punt_unknown4;
+ u8 punt_unknown6;
} tcp_main_t;
extern tcp_main_t tcp_main;
@@ -441,6 +444,8 @@ tcp_buffer_hdr (vlib_buffer_t * b)
clib_error_t *vnet_tcp_enable_disable (vlib_main_t * vm, u8 is_en);
+void tcp_punt_unknown (vlib_main_t * vm, u8 is_ip4, u8 is_add);
+
always_inline tcp_connection_t *
tcp_connection_get (u32 conn_index, u32 thread_index)
{
diff --git a/src/vnet/tcp/tcp_error.def b/src/vnet/tcp/tcp_error.def
index 08922315c99..a179717ff13 100644
--- a/src/vnet/tcp/tcp_error.def
+++ b/src/vnet/tcp/tcp_error.def
@@ -39,4 +39,5 @@ tcp_error (RST_SENT, "Resets sent")
tcp_error (INVALID_CONNECTION, "Invalid connection")
tcp_error (NO_WND, "No window")
tcp_error (CONNECTION_CLOSED, "Connection closed")
-tcp_error (CREATE_EXISTS, "Connection already exists") \ No newline at end of file
+tcp_error (CREATE_EXISTS, "Connection already exists")
+tcp_error (PUNT, "Packets punted") \ No newline at end of file
diff --git a/src/vnet/tcp/tcp_input.c b/src/vnet/tcp/tcp_input.c
index 64a07070ec2..bd57eca3223 100644
--- a/src/vnet/tcp/tcp_input.c
+++ b/src/vnet/tcp/tcp_input.c
@@ -2869,6 +2869,7 @@ typedef enum _tcp_input_next
TCP_INPUT_NEXT_SYN_SENT,
TCP_INPUT_NEXT_ESTABLISHED,
TCP_INPUT_NEXT_RESET,
+ TCP_INPUT_NEXT_PUNT,
TCP_INPUT_N_NEXT
} tcp_input_next_t;
@@ -2878,7 +2879,8 @@ typedef enum _tcp_input_next
_ (RCV_PROCESS, "tcp4-rcv-process") \
_ (SYN_SENT, "tcp4-syn-sent") \
_ (ESTABLISHED, "tcp4-established") \
- _ (RESET, "tcp4-reset")
+ _ (RESET, "tcp4-reset") \
+ _ (PUNT, "error-punt")
#define foreach_tcp6_input_next \
_ (DROP, "error-drop") \
@@ -2886,7 +2888,8 @@ typedef enum _tcp_input_next
_ (RCV_PROCESS, "tcp6-rcv-process") \
_ (SYN_SENT, "tcp6-syn-sent") \
_ (ESTABLISHED, "tcp6-established") \
- _ (RESET, "tcp6-reset")
+ _ (RESET, "tcp6-reset") \
+ _ (PUNT, "error-punt")
#define filter_flags (TCP_FLAG_SYN|TCP_FLAG_ACK|TCP_FLAG_RST|TCP_FLAG_FIN)
@@ -3010,9 +3013,18 @@ tcp46_input_inline (vlib_main_t * vm, vlib_node_runtime_t * node,
}
else
{
- /* Send reset */
- next0 = TCP_INPUT_NEXT_RESET;
- error0 = TCP_ERROR_NO_LISTENER;
+ if ((is_ip4 && tm->punt_unknown4) ||
+ (!is_ip4 && tm->punt_unknown6))
+ {
+ next0 = TCP_INPUT_NEXT_PUNT;
+ error0 = TCP_ERROR_PUNT;
+ }
+ else
+ {
+ /* Send reset */
+ next0 = TCP_INPUT_NEXT_RESET;
+ error0 = TCP_ERROR_NO_LISTENER;
+ }
}
done: