transport: cleanup 33/17333/6
authorFlorin Coras <fcoras@cisco.com>
Tue, 5 Feb 2019 23:51:15 +0000 (15:51 -0800)
committerDamjan Marion <dmarion@me.com>
Wed, 6 Feb 2019 16:56:39 +0000 (16:56 +0000)
- move transport specific types to transport_types
- add transport wrapper functions for interaction with transport
protocol vfts

Change-Id: I93f70d884585fc2f41c4a605e310c80e8a8972f2
Signed-off-by: Florin Coras <fcoras@cisco.com>
19 files changed:
src/vnet/CMakeLists.txt
src/vnet/sctp/sctp.c
src/vnet/sctp/sctp_output.c
src/vnet/session/application.h
src/vnet/session/session.c
src/vnet/session/session.h
src/vnet/session/session_api.c
src/vnet/session/session_lookup.c
src/vnet/session/session_lookup.h
src/vnet/session/session_node.c
src/vnet/session/session_types.h
src/vnet/session/transport.c
src/vnet/session/transport.h
src/vnet/session/transport_interface.h [deleted file]
src/vnet/session/transport_types.h [new file with mode: 0644]
src/vnet/tcp/tcp.c
src/vnet/tcp/tcp_output.c
src/vnet/tls/tls.c
src/vnet/udp/udp.c

index 72da325..6c1eae8 100644 (file)
@@ -1054,7 +1054,7 @@ list(APPEND VNET_HEADERS
   session/session_lookup.h
   session/application.h
   session/transport.h
-  session/transport_interface.h
+  session/transport_types.h
   session/application_interface.h
   session/application_namespace.h
   session/session_debug.h
index 86aef88..d0e28c5 100644 (file)
@@ -943,9 +943,9 @@ sctp_update_time (f64 now, u8 thread_index)
 /* *INDENT OFF* */
 const static transport_proto_vft_t sctp_proto = {
   .enable = sctp_enable_disable,
-  .bind = sctp_session_bind,
-  .unbind = sctp_session_unbind,
-  .open = sctp_session_open,
+  .start_listen = sctp_session_bind,
+  .stop_listen = sctp_session_unbind,
+  .connect = sctp_session_open,
   .close = sctp_session_close,
   .cleanup = sctp_session_cleanup,
   .push_header = sctp_push_header,
index 17b28a8..8fea714 100644 (file)
@@ -264,7 +264,7 @@ sctp_reuse_buffer (vlib_main_t * vm, vlib_buffer_t * b)
   vnet_buffer (b)->sctp.subconn_idx = MAX_SCTP_CONNECTIONS;
 
   /* Leave enough space for headers */
-  return vlib_buffer_make_headroom (b, MAX_HDRS_LEN);
+  return vlib_buffer_make_headroom (b, TRANSPORT_MAX_HDRS_LEN);
 }
 
 always_inline void *
@@ -277,7 +277,7 @@ sctp_init_buffer (vlib_main_t * vm, vlib_buffer_t * b)
   vnet_buffer (b)->sctp.subconn_idx = MAX_SCTP_CONNECTIONS;
   VLIB_BUFFER_TRACE_TRAJECTORY_INIT (b);
   /* Leave enough space for headers */
-  return vlib_buffer_make_headroom (b, MAX_HDRS_LEN);
+  return vlib_buffer_make_headroom (b, TRANSPORT_MAX_HDRS_LEN);
 }
 
 always_inline int
index f0c0a0d..e5bb00e 100644 (file)
@@ -16,7 +16,7 @@
 #ifndef SRC_VNET_SESSION_APPLICATION_H_
 #define SRC_VNET_SESSION_APPLICATION_H_
 
-#include <vnet/session/session.h>
+#include <vnet/session/session_types.h>
 #include <vnet/session/segment_manager.h>
 #include <vnet/session/application_namespace.h>
 
index 7b1c754..6833a93 100644 (file)
 #include <vnet/session/session.h>
 #include <vnet/session/session_debug.h>
 #include <vnet/session/application.h>
-#include <vlibmemory/api.h>
 #include <vnet/dpo/load_balance.h>
 #include <vnet/fib/ip4_fib.h>
 
 session_manager_main_t session_manager_main;
-extern transport_proto_vft_t *tp_vfts;
 
 static inline int
 session_send_evt_to_thread (void *data, void *args, u32 thread_index,
@@ -752,14 +750,13 @@ static void
 session_switch_pool (void *cb_args)
 {
   session_switch_pool_args_t *args = (session_switch_pool_args_t *) cb_args;
-  transport_proto_t tp;
   session_t *s;
   ASSERT (args->thread_index == vlib_get_thread_index ());
   s = session_get (args->session_index, args->thread_index);
   s->tx_fifo->master_session_index = args->new_session_index;
   s->tx_fifo->master_thread_index = args->new_thread_index;
-  tp = session_get_transport_proto (s);
-  tp_vfts[tp].cleanup (s->connection_index, s->thread_index);
+  transport_cleanup (session_get_transport_proto (s), s->connection_index,
+                    s->thread_index);
   session_free (s);
   clib_mem_free (cb_args);
 }
@@ -989,14 +986,14 @@ session_open_cl (u32 app_wrk_index, session_endpoint_t * rmt, u32 opaque)
   int rv;
 
   tep = session_endpoint_to_transport_cfg (rmt);
-  rv = tp_vfts[rmt->transport_proto].open (tep);
+  rv = transport_connect (rmt->transport_proto, tep);
   if (rv < 0)
     {
       SESSION_DBG ("Transport failed to open connection.");
       return VNET_API_ERROR_SESSION_CONNECT;
     }
 
-  tc = tp_vfts[rmt->transport_proto].get_half_open ((u32) rv);
+  tc = transport_get_half_open (rmt->transport_proto, (u32) rv);
 
   /* For dgram type of service, allocate session and fifos now.
    */
@@ -1024,14 +1021,14 @@ session_open_vc (u32 app_wrk_index, session_endpoint_t * rmt, u32 opaque)
   int rv;
 
   tep = session_endpoint_to_transport_cfg (rmt);
-  rv = tp_vfts[rmt->transport_proto].open (tep);
+  rv = transport_connect (rmt->transport_proto, tep);
   if (rv < 0)
     {
       SESSION_DBG ("Transport failed to open connection.");
       return VNET_API_ERROR_SESSION_CONNECT;
     }
 
-  tc = tp_vfts[rmt->transport_proto].get_half_open ((u32) rv);
+  tc = transport_get_half_open (rmt->transport_proto, (u32) rv);
 
   /* If transport offers a stream service, only allocate session once the
    * connection has been established.
@@ -1059,7 +1056,7 @@ session_open_app (u32 app_wrk_index, session_endpoint_t * rmt, u32 opaque)
   sep->app_wrk_index = app_wrk_index;
   sep->opaque = opaque;
 
-  return tp_vfts[rmt->transport_proto].open (tep_cfg);
+  return transport_connect (rmt->transport_proto, tep_cfg);
 }
 
 typedef int (*session_open_service_fn) (u32, session_endpoint_t *, u32);
@@ -1088,7 +1085,8 @@ static session_open_service_fn session_open_srv_fns[TRANSPORT_N_SERVICES] = {
 int
 session_open (u32 app_wrk_index, session_endpoint_t * rmt, u32 opaque)
 {
-  transport_service_type_t tst = tp_vfts[rmt->transport_proto].service_type;
+  transport_service_type_t tst;
+  tst = transport_protocol_service_type (rmt->transport_proto);
   return session_open_srv_fns[tst] (app_wrk_index, rmt, opaque);
 }
 
@@ -1110,7 +1108,7 @@ session_listen (session_t * ls, session_endpoint_cfg_t * sep)
   /* Transport bind/listen */
   tep = session_endpoint_to_transport (sep);
   s_index = ls->session_index;
-  tc_index = tp_vfts[sep->transport_proto].bind (s_index, tep);
+  tc_index = transport_start_listen (sep->transport_proto, s_index, tep);
 
   if (tc_index == (u32) ~ 0)
     return -1;
@@ -1120,7 +1118,7 @@ session_listen (session_t * ls, session_endpoint_cfg_t * sep)
   ls->connection_index = tc_index;
 
   /* Add to the main lookup table after transport was initialized */
-  tc = tp_vfts[sep->transport_proto].get_listener (tc_index);
+  tc = transport_get_listener (sep->transport_proto, tc_index);
   session_lookup_add_connection (tc, s_index);
   return 0;
 }
@@ -1135,21 +1133,16 @@ session_stop_listen (session_t * s)
 {
   transport_proto_t tp = session_get_transport_proto (s);
   transport_connection_t *tc;
+
   if (s->session_state != SESSION_STATE_LISTENING)
-    {
-      clib_warning ("not a listening session");
-      return -1;
-    }
+    return -1;
 
-  tc = tp_vfts[tp].get_listener (s->connection_index);
+  tc = transport_get_listener (tp, s->connection_index);
   if (!tc)
-    {
-      clib_warning ("no transport");
-      return VNET_API_ERROR_ADDRESS_NOT_IN_USE;
-    }
+    return VNET_API_ERROR_ADDRESS_NOT_IN_USE;
 
   session_lookup_del_connection (tc);
-  tp_vfts[tp].unbind (s->connection_index);
+  transport_stop_listen (tp, s->connection_index);
   return 0;
 }
 
@@ -1210,8 +1203,8 @@ session_transport_close (session_t * s)
   else
     s->session_state = SESSION_STATE_CLOSED;
 
-  tp_vfts[session_get_transport_proto (s)].close (s->connection_index,
-                                                 s->thread_index);
+  transport_close (session_get_transport_proto (s), s->connection_index,
+                  s->thread_index);
 }
 
 /**
@@ -1228,8 +1221,8 @@ session_transport_cleanup (session_t * s)
 
   /* Delete from main lookup table before we axe the the transport */
   session_lookup_del_session (s);
-  tp_vfts[session_get_transport_proto (s)].cleanup (s->connection_index,
-                                                   s->thread_index);
+  transport_cleanup (session_get_transport_proto (s), s->connection_index,
+                    s->thread_index);
   /* Since we called cleanup, no delete notification will come. So, make
    * sure the session is properly freed. */
   session_free_w_fifos (s);
index 68d8276..c622e4e 100644 (file)
 
 #include <vnet/session/session_types.h>
 #include <vnet/session/session_lookup.h>
-#include <vnet/session/transport_interface.h>
 #include <vnet/session/session_debug.h>
 #include <vnet/session/segment_manager.h>
 #include <svm/message_queue.h>
 
 #define SESSION_PROXY_LISTENER_INDEX ((u8)~0 - 1)
 
-/* TODO decide how much since we have pre-data as well */
-#define MAX_HDRS_LEN    100    /* Max number of bytes for headers */
-
 typedef enum
 {
   FIFO_EVENT_APP_RX,
@@ -298,21 +294,6 @@ extern vlib_node_registration_t session_queue_process_node;
 #define SESSION_Q_PROCESS_FLUSH_FRAMES 1
 #define SESSION_Q_PROCESS_STOP         2
 
-/*
- * Session manager function
- */
-always_inline session_manager_main_t *
-vnet_get_session_manager_main ()
-{
-  return &session_manager_main;
-}
-
-always_inline session_manager_worker_t *
-session_manager_get_worker (u32 thread_index)
-{
-  return &session_manager_main.wrk[thread_index];
-}
-
 always_inline u8
 stream_session_is_valid (u32 si, u8 thread_index)
 {
@@ -437,53 +418,6 @@ session_get_from_handle_safe (u64 handle)
     }
 }
 
-always_inline u32
-transport_max_rx_enqueue (transport_connection_t * tc)
-{
-  session_t *s = session_get (tc->s_index, tc->thread_index);
-  return svm_fifo_max_enqueue (s->rx_fifo);
-}
-
-always_inline u32
-transport_max_tx_dequeue (transport_connection_t * tc)
-{
-  session_t *s = session_get (tc->s_index, tc->thread_index);
-  return svm_fifo_max_dequeue (s->tx_fifo);
-}
-
-always_inline u32
-transport_rx_fifo_size (transport_connection_t * tc)
-{
-  session_t *s = session_get (tc->s_index, tc->thread_index);
-  return s->rx_fifo->nitems;
-}
-
-always_inline u32
-transport_tx_fifo_size (transport_connection_t * tc)
-{
-  session_t *s = session_get (tc->s_index, tc->thread_index);
-  return s->tx_fifo->nitems;
-}
-
-always_inline u8
-transport_rx_fifo_has_ooo_data (transport_connection_t * tc)
-{
-  session_t *s = session_get (tc->c_index, tc->thread_index);
-  return svm_fifo_has_ooo_data (s->rx_fifo);
-}
-
-always_inline f64
-transport_dispatch_period (u32 thread_index)
-{
-  return session_manager_main.wrk[thread_index].dispatch_period;
-}
-
-always_inline f64
-transport_time_now (u32 thread_index)
-{
-  return session_manager_main.wrk[thread_index].last_vlib_time;
-}
-
 always_inline u32
 session_get_index (session_t * s)
 {
@@ -511,14 +445,34 @@ session_clone_safe (u32 session_index, u32 thread_index)
   return new_s;
 }
 
+int session_open (u32 app_index, session_endpoint_t * tep, u32 opaque);
+int session_listen (session_t * s, session_endpoint_cfg_t * sep);
+int session_stop_listen (session_t * s);
+void session_close (session_t * s);
+void session_transport_close (session_t * s);
+void session_transport_cleanup (session_t * s);
+int session_send_io_evt_to_thread (svm_fifo_t * f,
+                                  session_evt_type_t evt_type);
+int session_dequeue_notify (session_t * s);
+int session_send_io_evt_to_thread_custom (void *data, u32 thread_index,
+                                         session_evt_type_t evt_type);
+void session_send_rpc_evt_to_thread (u32 thread_index, void *fp,
+                                    void *rpc_args);
 transport_connection_t *session_get_transport (session_t * s);
 
-u32 session_tx_fifo_max_dequeue (transport_connection_t * tc);
 
-int
-session_enqueue_stream_connection (transport_connection_t * tc,
-                                  vlib_buffer_t * b, u32 offset,
-                                  u8 queue_event, u8 is_in_order);
+u8 *format_stream_session (u8 * s, va_list * args);
+uword unformat_stream_session (unformat_input_t * input, va_list * args);
+uword unformat_transport_connection (unformat_input_t * input,
+                                    va_list * args);
+
+/*
+ * Interface to transport protos
+ */
+
+int session_enqueue_stream_connection (transport_connection_t * tc,
+                                      vlib_buffer_t * b, u32 offset,
+                                      u8 queue_event, u8 is_in_order);
 int session_enqueue_dgram_connection (session_t * s,
                                      session_dgram_hdr_t * hdr,
                                      vlib_buffer_t * b, u8 proto,
@@ -531,7 +485,6 @@ int session_stream_connect_notify (transport_connection_t * tc, u8 is_fail);
 int session_dgram_connect_notify (transport_connection_t * tc,
                                  u32 old_thread_index,
                                  session_t ** new_session);
-int session_dequeue_notify (session_t * s);
 void stream_session_init_fifos_pointers (transport_connection_t * tc,
                                         u32 rx_pointer, u32 tx_pointer);
 
@@ -542,30 +495,58 @@ void session_transport_closed_notify (transport_connection_t * tc);
 void session_transport_reset_notify (transport_connection_t * tc);
 int stream_session_accept (transport_connection_t * tc, u32 listener_index,
                           u8 notify);
-int session_open (u32 app_index, session_endpoint_t * tep, u32 opaque);
-int session_listen (session_t * s, session_endpoint_cfg_t * sep);
-int session_stop_listen (session_t * s);
-void session_close (session_t * s);
-void session_transport_close (session_t * s);
-void session_transport_cleanup (session_t * s);
-int session_send_io_evt_to_thread (svm_fifo_t * f,
-                                  session_evt_type_t evt_type);
-int session_send_io_evt_to_thread_custom (void *data, u32 thread_index,
-                                         session_evt_type_t evt_type);
-void session_send_rpc_evt_to_thread (u32 thread_index, void *fp,
-                                    void *rpc_args);
-
-ssvm_private_t *session_manager_get_evt_q_segment (void);
-
-u8 *format_stream_session (u8 * s, va_list * args);
-uword unformat_stream_session (unformat_input_t * input, va_list * args);
-uword unformat_transport_connection (unformat_input_t * input,
-                                    va_list * args);
-
+u32 session_tx_fifo_max_dequeue (transport_connection_t * tc);
 void session_register_transport (transport_proto_t transport_proto,
                                 const transport_proto_vft_t * vft, u8 is_ip4,
                                 u32 output_node);
 
+always_inline u32
+transport_max_rx_enqueue (transport_connection_t * tc)
+{
+  session_t *s = session_get (tc->s_index, tc->thread_index);
+  return svm_fifo_max_enqueue (s->rx_fifo);
+}
+
+always_inline u32
+transport_max_tx_dequeue (transport_connection_t * tc)
+{
+  session_t *s = session_get (tc->s_index, tc->thread_index);
+  return svm_fifo_max_dequeue (s->tx_fifo);
+}
+
+always_inline u32
+transport_rx_fifo_size (transport_connection_t * tc)
+{
+  session_t *s = session_get (tc->s_index, tc->thread_index);
+  return s->rx_fifo->nitems;
+}
+
+always_inline u32
+transport_tx_fifo_size (transport_connection_t * tc)
+{
+  session_t *s = session_get (tc->s_index, tc->thread_index);
+  return s->tx_fifo->nitems;
+}
+
+always_inline u8
+transport_rx_fifo_has_ooo_data (transport_connection_t * tc)
+{
+  session_t *s = session_get (tc->c_index, tc->thread_index);
+  return svm_fifo_has_ooo_data (s->rx_fifo);
+}
+
+always_inline f64
+transport_dispatch_period (u32 thread_index)
+{
+  return session_manager_main.wrk[thread_index].dispatch_period;
+}
+
+always_inline f64
+transport_time_now (u32 thread_index)
+{
+  return session_manager_main.wrk[thread_index].last_vlib_time;
+}
+
 always_inline void
 transport_add_tx_event (transport_connection_t * tc)
 {
@@ -575,16 +556,9 @@ transport_add_tx_event (transport_connection_t * tc)
   session_send_io_evt_to_thread (s->tx_fifo, FIFO_EVENT_APP_TX);
 }
 
-clib_error_t *vnet_session_enable_disable (vlib_main_t * vm, u8 is_en);
-
-always_inline svm_msg_q_t *
-session_manager_get_vpp_event_queue (u32 thread_index)
-{
-  return session_manager_main.wrk[thread_index].vpp_event_queue;
-}
-
-int session_manager_flush_enqueue_events (u8 proto, u32 thread_index);
-int session_manager_flush_all_enqueue_events (u8 transport_proto);
+/*
+ * Listen sessions
+ */
 
 always_inline u64
 listen_session_get_handle (session_t * s)
@@ -634,7 +608,27 @@ int
 listen_session_get_local_session_endpoint (session_t * listener,
                                           session_endpoint_t * sep);
 
-void session_flush_frames_main_thread (vlib_main_t * vm);
+/*
+ * Session manager functions
+ */
+
+always_inline session_manager_main_t *
+vnet_get_session_manager_main ()
+{
+  return &session_manager_main;
+}
+
+always_inline session_manager_worker_t *
+session_manager_get_worker (u32 thread_index)
+{
+  return &session_manager_main.wrk[thread_index];
+}
+
+always_inline svm_msg_q_t *
+session_manager_get_vpp_event_queue (u32 thread_index)
+{
+  return session_manager_main.wrk[thread_index].vpp_event_queue;
+}
 
 always_inline u8
 session_manager_is_enabled ()
@@ -648,7 +642,12 @@ do {                                                                       \
       return clib_error_return(0, "session layer is not enabled");     \
 } while (0)
 
+int session_manager_flush_enqueue_events (u8 proto, u32 thread_index);
+int session_manager_flush_all_enqueue_events (u8 transport_proto);
+void session_flush_frames_main_thread (vlib_main_t * vm);
+ssvm_private_t *session_manager_get_evt_q_segment (void);
 void session_node_enable_disable (u8 is_en);
+clib_error_t *vnet_session_enable_disable (vlib_main_t * vm, u8 is_en);
 
 #endif /* __included_session_h__ */
 
index bd80936..8196f4c 100755 (executable)
@@ -201,7 +201,6 @@ static int
 send_session_accept_callback (session_t * s)
 {
   app_worker_t *server_wrk = app_worker_get (s->app_wrk_index);
-  transport_proto_vft_t *tp_vft;
   vl_api_accept_session_t *mp;
   vl_api_registration_t *reg;
   transport_connection_t *tc;
@@ -241,8 +240,8 @@ send_session_accept_callback (session_t * s)
       vpp_queue = session_manager_get_vpp_event_queue (s->thread_index);
       mp->vpp_event_queue_address = pointer_to_uword (vpp_queue);
       mp->handle = session_handle (s);
-      tp_vft = transport_protocol_get_vft (session_get_transport_proto (s));
-      tc = tp_vft->get_connection (s->connection_index, s->thread_index);
+      tc = transport_get_connection (session_get_transport_proto (s),
+                                    s->connection_index, s->thread_index);
       mp->port = tc->rmt_port;
       mp->is_ip4 = tc->is_ip4;
       clib_memcpy_fast (&mp->ip, &tc->rmt_ip, sizeof (tc->rmt_ip));
@@ -420,7 +419,6 @@ mq_send_session_accepted_cb (session_t * s)
   app_worker_t *app_wrk = app_worker_get (s->app_wrk_index);
   svm_msg_q_msg_t _msg, *msg = &_msg;
   svm_msg_q_t *vpp_queue, *app_mq;
-  transport_proto_vft_t *tp_vft;
   transport_connection_t *tc;
   session_t *listener;
   session_accepted_msg_t *mp;
@@ -457,8 +455,8 @@ mq_send_session_accepted_cb (session_t * s)
       vpp_queue = session_manager_get_vpp_event_queue (s->thread_index);
       mp->vpp_event_queue_address = pointer_to_uword (vpp_queue);
       mp->handle = session_handle (s);
-      tp_vft = transport_protocol_get_vft (session_get_transport_proto (s));
-      tc = tp_vft->get_connection (s->connection_index, s->thread_index);
+      tc = transport_get_connection (session_get_transport_proto (s),
+                                    s->connection_index, s->thread_index);
       mp->port = tc->rmt_port;
       mp->is_ip4 = tc->is_ip4;
       clib_memcpy_fast (&mp->ip, &tc->rmt_ip, sizeof (tc->rmt_ip));
index 33fcb42..f267a4c 100644 (file)
 #include <vnet/session/session.h>
 #include <vnet/session/application.h>
 
-/**
- * External vector of per transport virtual functions table
- */
-extern transport_proto_vft_t *tp_vfts;
-
 /**
  * Network namespace index (i.e., fib index) to session lookup table. We
  * should have one per network protocol type but for now we only support IP4/6
@@ -340,9 +335,9 @@ session_lookup_del_connection (transport_connection_t * tc)
 int
 session_lookup_del_session (session_t * s)
 {
-  transport_proto_t tp = session_get_transport_proto (s);
   transport_connection_t *ts;
-  ts = tp_vfts[tp].get_connection (s->connection_index, s->thread_index);
+  ts = transport_get_connection (session_get_transport_proto (s),
+                                s->connection_index, s->thread_index);
   return session_lookup_del_connection (ts);
 }
 
@@ -812,12 +807,10 @@ session_lookup_half_open_handle (transport_connection_t * tc)
 transport_connection_t *
 session_lookup_half_open_connection (u64 handle, u8 proto, u8 is_ip4)
 {
-  u32 sst;
-
   if (handle != HALF_OPEN_LOOKUP_INVALID_VALUE)
     {
-      sst = session_type_from_proto_and_ip (proto, is_ip4);
-      return tp_vfts[sst].get_half_open (handle & 0xFFFFFFFF);
+      u32 sst = session_type_from_proto_and_ip (proto, is_ip4);
+      return transport_get_half_open (sst, handle & 0xFFFFFFFF);
     }
   return 0;
 }
@@ -877,8 +870,8 @@ session_lookup_connection_wt4 (u32 fib_index, ip4_address_t * lcl,
          return 0;
        }
       s = session_get (kv4.value & 0xFFFFFFFFULL, thread_index);
-      return tp_vfts[proto].get_connection (s->connection_index,
-                                           thread_index);
+      return transport_get_connection (proto, s->connection_index,
+                                      thread_index);
     }
 
   /*
@@ -886,7 +879,7 @@ session_lookup_connection_wt4 (u32 fib_index, ip4_address_t * lcl,
    */
   rv = clib_bihash_search_inline_16_8 (&st->v4_half_open_hash, &kv4);
   if (rv == 0)
-    return tp_vfts[proto].get_half_open (kv4.value & 0xFFFFFFFF);
+    return transport_get_half_open (proto, kv4.value & 0xFFFFFFFF);
 
   /*
    * Check the session rules table
@@ -902,7 +895,7 @@ session_lookup_connection_wt4 (u32 fib_index, ip4_address_t * lcl,
        }
       if ((s = session_lookup_action_to_session (action_index,
                                                 FIB_PROTOCOL_IP4, proto)))
-       return tp_vfts[proto].get_listener (s->connection_index);
+       return transport_get_listener (proto, s->connection_index);
       return 0;
     }
 
@@ -911,7 +904,7 @@ session_lookup_connection_wt4 (u32 fib_index, ip4_address_t * lcl,
    */
   s = session_lookup_listener4_i (st, lcl, lcl_port, proto, 1);
   if (s)
-    return tp_vfts[proto].get_listener (s->connection_index);
+    return transport_get_listener (proto, s->connection_index);
 
   return 0;
 }
@@ -954,8 +947,8 @@ session_lookup_connection4 (u32 fib_index, ip4_address_t * lcl,
   if (rv == 0)
     {
       s = session_get_from_handle (kv4.value);
-      return tp_vfts[proto].get_connection (s->connection_index,
-                                           s->thread_index);
+      return transport_get_connection (proto, s->connection_index,
+                                      s->thread_index);
     }
 
   /*
@@ -963,7 +956,7 @@ session_lookup_connection4 (u32 fib_index, ip4_address_t * lcl,
    */
   rv = clib_bihash_search_inline_16_8 (&st->v4_half_open_hash, &kv4);
   if (rv == 0)
-    return tp_vfts[proto].get_half_open (kv4.value & 0xFFFFFFFF);
+    return transport_get_half_open (proto, kv4.value & 0xFFFFFFFF);
 
   /*
    * Check the session rules table
@@ -976,7 +969,7 @@ session_lookup_connection4 (u32 fib_index, ip4_address_t * lcl,
        return 0;
       if ((s = session_lookup_action_to_session (action_index,
                                                 FIB_PROTOCOL_IP4, proto)))
-       return tp_vfts[proto].get_listener (s->connection_index);
+       return transport_get_listener (proto, s->connection_index);
       return 0;
     }
 
@@ -985,7 +978,7 @@ session_lookup_connection4 (u32 fib_index, ip4_address_t * lcl,
    */
   s = session_lookup_listener4_i (st, lcl, lcl_port, proto, 1);
   if (s)
-    return tp_vfts[proto].get_listener (s->connection_index);
+    return transport_get_listener (proto, s->connection_index);
 
   return 0;
 }
@@ -1099,14 +1092,14 @@ session_lookup_connection_wt6 (u32 fib_index, ip6_address_t * lcl,
          return 0;
        }
       s = session_get (kv6.value & 0xFFFFFFFFULL, thread_index);
-      return tp_vfts[proto].get_connection (s->connection_index,
-                                           thread_index);
+      return transport_get_connection (proto, s->connection_index,
+                                      thread_index);
     }
 
   /* Try half-open connections */
   rv = clib_bihash_search_inline_48_8 (&st->v6_half_open_hash, &kv6);
   if (rv == 0)
-    return tp_vfts[proto].get_half_open (kv6.value & 0xFFFFFFFF);
+    return transport_get_half_open (proto, kv6.value & 0xFFFFFFFF);
 
   /* Check the session rules table */
   action_index = session_rules_table_lookup6 (&st->session_rules[proto], lcl,
@@ -1120,14 +1113,14 @@ session_lookup_connection_wt6 (u32 fib_index, ip6_address_t * lcl,
        }
       if ((s = session_lookup_action_to_session (action_index,
                                                 FIB_PROTOCOL_IP6, proto)))
-       return tp_vfts[proto].get_listener (s->connection_index);
+       return transport_get_listener (proto, s->connection_index);
       return 0;
     }
 
   /* If nothing is found, check if any listener is available */
   s = session_lookup_listener6_i (st, lcl, lcl_port, proto, 1);
   if (s)
-    return tp_vfts[proto].get_listener (s->connection_index);
+    return transport_get_listener (proto, s->connection_index);
 
   return 0;
 }
@@ -1168,14 +1161,14 @@ session_lookup_connection6 (u32 fib_index, ip6_address_t * lcl,
   if (rv == 0)
     {
       s = session_get_from_handle (kv6.value);
-      return tp_vfts[proto].get_connection (s->connection_index,
-                                           s->thread_index);
+      return transport_get_connection (proto, s->connection_index,
+                                      s->thread_index);
     }
 
   /* Try half-open connections */
   rv = clib_bihash_search_inline_48_8 (&st->v6_half_open_hash, &kv6);
   if (rv == 0)
-    return tp_vfts[proto].get_half_open (kv6.value & 0xFFFFFFFF);
+    return transport_get_half_open (proto, kv6.value & 0xFFFFFFFF);
 
   /* Check the session rules table */
   action_index = session_rules_table_lookup6 (&st->session_rules[proto], lcl,
@@ -1186,14 +1179,14 @@ session_lookup_connection6 (u32 fib_index, ip6_address_t * lcl,
        return 0;
       if ((s = session_lookup_action_to_session (action_index,
                                                 FIB_PROTOCOL_IP6, proto)))
-       return tp_vfts[proto].get_listener (s->connection_index);
+       return transport_get_listener (proto, s->connection_index);
       return 0;
     }
 
   /* If nothing is found, check if any listener is available */
   s = session_lookup_listener6_i (st, lcl, lcl_port, proto, 1);
   if (s)
-    return tp_vfts[proto].get_listener (s->connection_index);
+    return transport_get_listener (proto, s->connection_index);
 
   return 0;
 }
index 5efb1f4..995d2aa 100644 (file)
@@ -18,7 +18,6 @@
 
 #include <vnet/session/session_table.h>
 #include <vnet/session/session_types.h>
-#include <vnet/session/transport.h>
 #include <vnet/session/application_namespace.h>
 
 #define HALF_OPEN_LOOKUP_INVALID_VALUE ((u64)~0)
index fa33ad3..286bd7b 100644 (file)
@@ -447,7 +447,7 @@ session_tx_fill_buffer (vlib_main_t * vm, session_tx_context_t * ctx,
   b->flags = VNET_BUFFER_F_LOCALLY_ORIGINATED;
   b->current_data = 0;
 
-  data0 = vlib_buffer_make_headroom (b, MAX_HDRS_LEN);
+  data0 = vlib_buffer_make_headroom (b, TRANSPORT_MAX_HDRS_LEN);
   len_to_deq = clib_min (ctx->left_to_snd, ctx->deq_per_first_buf);
 
   if (peek_data)
@@ -606,12 +606,13 @@ session_tx_set_dequeue_params (vlib_main_t * vm, session_tx_context_t * ctx,
     }
 
   n_bytes_per_buf = VLIB_BUFFER_DATA_SIZE;
-  ASSERT (n_bytes_per_buf > MAX_HDRS_LEN);
-  n_bytes_per_seg = MAX_HDRS_LEN + ctx->snd_mss;
+  ASSERT (n_bytes_per_buf > TRANSPORT_MAX_HDRS_LEN);
+  n_bytes_per_seg = TRANSPORT_MAX_HDRS_LEN + ctx->snd_mss;
   ctx->n_bufs_per_seg = ceil ((f64) n_bytes_per_seg / n_bytes_per_buf);
   ctx->deq_per_buf = clib_min (ctx->snd_mss, n_bytes_per_buf);
   ctx->deq_per_first_buf = clib_min (ctx->snd_mss,
-                                    n_bytes_per_buf - MAX_HDRS_LEN);
+                                    n_bytes_per_buf -
+                                    TRANSPORT_MAX_HDRS_LEN);
 }
 
 always_inline int
index b334c3c..286f4c4 100644 (file)
@@ -17,7 +17,7 @@
 #define SRC_VNET_SESSION_SESSION_TYPES_H_
 
 #include <svm/svm_fifo.h>
-#include <vnet/session/transport.h>
+#include <vnet/session/transport_types.h>
 
 #define SESSION_LOCAL_HANDLE_PREFIX 0x7FFFFFFF
 
index df5282c..2c4efe1 100644 (file)
@@ -13,7 +13,7 @@
  * limitations under the License.
  */
 
-#include <vnet/session/transport_interface.h>
+#include <vnet/session/transport.h>
 #include <vnet/session/session.h>
 #include <vnet/fib/fib.h>
 
@@ -271,17 +271,35 @@ transport_protocol_tx_fn_type (transport_proto_t tp)
   return tp_vfts[tp].tx_type;
 }
 
-transport_connection_t *
-transport_get_connection (transport_proto_t tp, u32 conn_index,
-                         u8 thread_index)
+void
+transport_cleanup (transport_proto_t tp, u32 conn_index, u8 thread_index)
+{
+  tp_vfts[tp].cleanup (conn_index, thread_index);
+}
+
+int
+transport_connect (transport_proto_t tp, transport_endpoint_cfg_t * tep)
+{
+  return tp_vfts[tp].connect (tep);
+}
+
+void
+transport_close (transport_proto_t tp, u32 conn_index, u8 thread_index)
 {
-  return tp_vfts[tp].get_connection (conn_index, thread_index);
+  tp_vfts[tp].close (conn_index, thread_index);
 }
 
-transport_connection_t *
-transport_get_listener (transport_proto_t tp, u32 conn_index)
+u32
+transport_start_listen (transport_proto_t tp, u32 session_index,
+                       transport_endpoint_t * tep)
+{
+  return tp_vfts[tp].start_listen (session_index, tep);
+}
+
+u32
+transport_stop_listen (transport_proto_t tp, u32 conn_index)
 {
-  return tp_vfts[tp].get_listener (conn_index);
+  return tp_vfts[tp].stop_listen (conn_index);
 }
 
 u8
index a82dc3d..8500e9d 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 Cisco and/or its affiliates.
+ * Copyright (c) 2017-2019 Cisco and/or its affiliates.
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
  * You may obtain a copy of the License at:
  * limitations under the License.
  */
 
-#ifndef VNET_VNET_URI_TRANSPORT_H_
-#define VNET_VNET_URI_TRANSPORT_H_
+#ifndef SRC_VNET_SESSION_TRANSPORT_H_
+#define SRC_VNET_SESSION_TRANSPORT_H_
 
 #include <vnet/vnet.h>
-#include <vnet/ip/ip.h>
-#include <vnet/tcp/tcp_debug.h>
+#include <vnet/session/transport_types.h>
 
-typedef enum transport_dequeue_type_
+/*
+ * Transport protocol virtual function table
+ */
+/* *INDENT-OFF* */
+typedef struct _transport_proto_vft
 {
-  TRANSPORT_TX_PEEK,           /**< reliable transport protos */
-  TRANSPORT_TX_DEQUEUE,                /**< unreliable transport protos */
-  TRANSPORT_TX_INTERNAL,       /**< apps acting as transports */
-  TRANSPORT_TX_DGRAM,          /**< datagram mode */
-  TRANSPORT_TX_N_FNS
-} transport_tx_fn_type_t;
-
-typedef enum transport_service_type_
+  /*
+   * Setup
+   */
+  u32 (*start_listen) (u32 session_index, transport_endpoint_t * lcl);
+  u32 (*stop_listen) (u32 conn_index);
+  int (*connect) (transport_endpoint_cfg_t * rmt);
+  void (*close) (u32 conn_index, u32 thread_index);
+  void (*cleanup) (u32 conn_index, u32 thread_index);
+  clib_error_t *(*enable) (vlib_main_t * vm, u8 is_en);
+
+  /*
+   * Transmission
+   */
+
+  u32 (*push_header) (transport_connection_t * tconn, vlib_buffer_t * b);
+  u16 (*send_mss) (transport_connection_t * tc);
+  u32 (*send_space) (transport_connection_t * tc);
+  u32 (*tx_fifo_offset) (transport_connection_t * tc);
+  void (*update_time) (f64 time_now, u8 thread_index);
+  void (*flush_data) (transport_connection_t *tconn);
+
+  /*
+   * Connection retrieval
+   */
+  transport_connection_t *(*get_connection) (u32 conn_idx, u32 thread_idx);
+  transport_connection_t *(*get_listener) (u32 conn_index);
+  transport_connection_t *(*get_half_open) (u32 conn_index);
+
+  /*
+   * Format
+   */
+  u8 *(*format_connection) (u8 * s, va_list * args);
+  u8 *(*format_listener) (u8 * s, va_list * args);
+  u8 *(*format_half_open) (u8 * s, va_list * args);
+
+  /*
+   * Properties
+   */
+  transport_tx_fn_type_t tx_type;
+  transport_service_type_t service_type;
+} transport_proto_vft_t;
+/* *INDENT-ON* */
+
+extern transport_proto_vft_t *tp_vfts;
+
+#define transport_proto_foreach(VAR, BODY)                     \
+do {                                                           \
+    for (VAR = 0; VAR < vec_len (tp_vfts); VAR++)              \
+      if (tp_vfts[VAR].push_header != 0)                       \
+       do { BODY; } while (0);                                 \
+} while (0)
+
+int transport_connect (transport_proto_t tp, transport_endpoint_cfg_t * tep);
+void transport_close (transport_proto_t tp, u32 conn_index, u8 thread_index);
+u32 transport_start_listen (transport_proto_t tp, u32 session_index,
+                           transport_endpoint_t * tep);
+u32 transport_stop_listen (transport_proto_t tp, u32 conn_index);
+void transport_cleanup (transport_proto_t tp, u32 conn_index,
+                       u8 thread_index);
+
+static inline transport_connection_t *
+transport_get_connection (transport_proto_t tp, u32 conn_index,
+                         u8 thread_index)
 {
-  TRANSPORT_SERVICE_VC,                /**< virtual circuit service */
-  TRANSPORT_SERVICE_CL,                /**< connectionless service */
-  TRANSPORT_SERVICE_APP,       /**< app transport service */
-  TRANSPORT_N_SERVICES
-} transport_service_type_t;
+  return tp_vfts[tp].get_connection (conn_index, thread_index);
+}
 
-typedef struct _transport_stats
+static inline transport_connection_t *
+transport_get_listener (transport_proto_t tp, u32 conn_index)
 {
-  u64 tx_bytes;
-} transport_stats_t;
+  return tp_vfts[tp].get_listener (conn_index);
+}
 
-typedef struct _spacer
+static inline transport_connection_t *
+transport_get_half_open (transport_proto_t tp, u32 conn_index)
 {
-  u64 bucket;
-  u32 max_burst_size;
-  f32 tokens_per_period;
-  u64 last_update;
-} spacer_t;
+  return tp_vfts[tp].get_half_open (conn_index);
+}
 
-/*
- * Protocol independent transport properties associated to a session
- */
-typedef struct _transport_connection
-{
-  /** Connection ID */
-  union
-  {
-    /*
-     * Network connection ID tuple
-     */
-    struct
-    {
-      ip46_address_t rmt_ip;   /**< Remote IP */
-      ip46_address_t lcl_ip;   /**< Local IP */
-      u16 rmt_port;            /**< Remote port */
-      u16 lcl_port;            /**< Local port */
-      u8 is_ip4;               /**< Flag if IP4 connection */
-      u8 proto;                        /**< Protocol id */
-      u32 fib_index;           /**< Network namespace */
-    };
-    /*
-     * Opaque connection ID
-     */
-    u8 opaque_conn_id[42];
-  };
-
-  u32 s_index;                 /**< Parent session index */
-  u32 c_index;                 /**< Connection index in transport pool */
-  u32 thread_index;            /**< Worker-thread index */
-
-  /*fib_node_index_t rmt_fei;
-     dpo_id_t rmt_dpo; */
-
-  u8 flags;                    /**< Transport specific flags */
-  transport_stats_t stats;     /**< Transport connection stats */
-  spacer_t pacer;              /**< Simple transport pacer */
+void transport_register_protocol (transport_proto_t transport_proto,
+                                 const transport_proto_vft_t * vft,
+                                 fib_protocol_t fib_proto, u32 output_node);
+transport_proto_vft_t *transport_protocol_get_vft (transport_proto_t tp);
+void transport_update_time (f64 time_now, u8 thread_index);
 
+int transport_alloc_local_port (u8 proto, ip46_address_t * ip);
+int transport_alloc_local_endpoint (u8 proto, transport_endpoint_cfg_t * rmt,
+                                   ip46_address_t * lcl_addr,
+                                   u16 * lcl_port);
+void transport_endpoint_cleanup (u8 proto, ip46_address_t * lcl_ip, u16 port);
+void transport_enable_disable (vlib_main_t * vm, u8 is_en);
+void transport_init (void);
+
+always_inline u32
+transport_elog_track_index (transport_connection_t * tc)
+{
 #if TRANSPORT_DEBUG
-  elog_track_t elog_track;     /**< Event logging */
-  u32 cc_stat_tstamp;          /**< CC stats timestamp */
+  return tc->elog_track.track_index_plus_one - 1;
+#else
+  return ~0;
 #endif
+}
 
-  /** Macros for 'derived classes' where base is named "connection" */
-#define c_lcl_ip connection.lcl_ip
-#define c_rmt_ip connection.rmt_ip
-#define c_lcl_ip4 connection.lcl_ip.ip4
-#define c_rmt_ip4 connection.rmt_ip.ip4
-#define c_lcl_ip6 connection.lcl_ip.ip6
-#define c_rmt_ip6 connection.rmt_ip.ip6
-#define c_lcl_port connection.lcl_port
-#define c_rmt_port connection.rmt_port
-#define c_proto connection.proto
-#define c_fib_index connection.fib_index
-#define c_s_index connection.s_index
-#define c_c_index connection.c_index
-#define c_is_ip4 connection.is_ip4
-#define c_thread_index connection.thread_index
-#define c_elog_track connection.elog_track
-#define c_cc_stat_tstamp connection.cc_stat_tstamp
-#define c_rmt_fei connection.rmt_fei
-#define c_rmt_dpo connection.rmt_dpo
-#define c_opaque_id connection.opaque_conn_id
-#define c_stats connection.stats
-#define c_pacer connection.pacer
-#define c_flags connection.flags
-} transport_connection_t;
-
-#define TRANSPORT_CONNECTION_F_IS_TX_PACED     1 << 0
-
-typedef enum _transport_proto
-{
-  TRANSPORT_PROTO_TCP,
-  TRANSPORT_PROTO_UDP,
-  TRANSPORT_PROTO_SCTP,
-  TRANSPORT_PROTO_NONE,
-  TRANSPORT_PROTO_TLS,
-  TRANSPORT_PROTO_UDPC,
-  TRANSPORT_N_PROTO
-} transport_proto_t;
-
-u8 *format_transport_proto (u8 * s, va_list * args);
-u8 *format_transport_proto_short (u8 * s, va_list * args);
-u8 *format_transport_connection (u8 * s, va_list * args);
-u8 *format_transport_listen_connection (u8 * s, va_list * args);
-u8 *format_transport_half_open_connection (u8 * s, va_list * args);
-
-uword unformat_transport_proto (unformat_input_t * input, va_list * args);
-
-#define foreach_transport_endpoint_fields                              \
-  _(ip46_address_t, ip) /**< ip address in net order */                        \
-  _(u16, port)         /**< port in net order */                       \
-  _(u8, is_ip4)                /**< set if ip4 */                              \
-  _(u32, sw_if_index)  /**< interface endpoint is associated with  */  \
-  _(u32, fib_index)    /**< fib table endpoint is associated with */   \
-
-typedef struct transport_endpoint_
-{
-#define _(type, name) type name;
-  foreach_transport_endpoint_fields
-#undef _
-} transport_endpoint_t;
+void transport_connection_tx_pacer_reset (transport_connection_t * tc,
+                                         u32 rate_bytes_per_sec,
+                                         u32 initial_bucket, u64 time_now);
+/**
+ * Initialize tx pacer for connection
+ *
+ * @param tc                           transport connection
+ * @param rate_bytes_per_second                initial byte rate
+ * @param burst_bytes                  initial burst size in bytes
+ */
+void transport_connection_tx_pacer_init (transport_connection_t * tc,
+                                        u32 rate_bytes_per_sec,
+                                        u32 initial_bucket);
 
-#define foreach_transport_endpoint_cfg_fields                          \
-  foreach_transport_endpoint_fields                                    \
-  _(transport_endpoint_t, peer)                                                \
+/**
+ * Update tx pacer pacing rate
+ *
+ * @param tc                   transport connection
+ * @param bytes_per_sec                new pacing rate
+ */
+void transport_connection_tx_pacer_update (transport_connection_t * tc,
+                                          u64 bytes_per_sec);
 
-typedef struct transport_endpoint_pair_
-{
-#define _(type, name) type name;
-  foreach_transport_endpoint_cfg_fields
-#undef _
-} transport_endpoint_cfg_t;
+/**
+ * Get maximum tx burst allowed for transport connection
+ *
+ * @param tc           transport connection
+ * @param time_now     current cpu time as returned by @ref clib_cpu_time_now
+ * @param mss          transport's mss
+ */
+u32 transport_connection_snd_space (transport_connection_t * tc,
+                                   u64 time_now, u16 mss);
 
-typedef clib_bihash_24_8_t transport_endpoint_table_t;
+u32 transport_connection_tx_pacer_burst (transport_connection_t * tc,
+                                        u64 time_now);
 
-#define ENDPOINT_INVALID_INDEX ((u32)~0)
+/**
+ * Initialize period for tx pacers
+ *
+ * Defines a unit of time with respect to number of cpu cycles that is to
+ * be used by all tx pacers.
+ */
+void transport_init_tx_pacers_period (void);
 
+/**
+ * Check if transport connection is paced
+ */
 always_inline u8
-transport_connection_fib_proto (transport_connection_t * tc)
+transport_connection_is_tx_paced (transport_connection_t * tc)
 {
-  return tc->is_ip4 ? FIB_PROTOCOL_IP4 : FIB_PROTOCOL_IP6;
+  return (tc->flags & TRANSPORT_CONNECTION_F_IS_TX_PACED);
 }
 
-always_inline u8
-transport_endpoint_fib_proto (transport_endpoint_t * tep)
-{
-  return tep->is_ip4 ? FIB_PROTOCOL_IP4 : FIB_PROTOCOL_IP6;
-}
+u8 *format_transport_pacer (u8 * s, va_list * args);
 
-int transport_alloc_local_port (u8 proto, ip46_address_t * ip);
-int transport_alloc_local_endpoint (u8 proto, transport_endpoint_cfg_t * rmt,
-                                   ip46_address_t * lcl_addr,
-                                   u16 * lcl_port);
-void transport_endpoint_cleanup (u8 proto, ip46_address_t * lcl_ip, u16 port);
-u8 transport_protocol_is_cl (transport_proto_t tp);
-transport_service_type_t transport_protocol_service_type (transport_proto_t);
-transport_tx_fn_type_t transport_protocol_tx_fn_type (transport_proto_t tp);
-void transport_init (void);
+/**
+ * Update tx byte stats for transport connection
+ *
+ * If tx pacing is enabled, this also updates pacer bucket to account for the
+ * amount of bytes that have been sent.
+ *
+ * @param tc           transport connection
+ * @param pkts         packets recently sent
+ * @param bytes                bytes recently sent
+ */
+void transport_connection_update_tx_stats (transport_connection_t * tc,
+                                          u32 bytes);
+
+void
+transport_connection_tx_pacer_update_bytes (transport_connection_t * tc,
+                                           u32 bytes);
 
-#endif /* VNET_VNET_URI_TRANSPORT_H_ */
+#endif /* SRC_VNET_SESSION_TRANSPORT_H_ */
 
 /*
  * fd.io coding-style-patch-verification: ON
diff --git a/src/vnet/session/transport_interface.h b/src/vnet/session/transport_interface.h
deleted file mode 100644 (file)
index 1230486..0000000
+++ /dev/null
@@ -1,182 +0,0 @@
-/*
- * Copyright (c) 2017-2019 Cisco and/or its affiliates.
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef SRC_VNET_SESSION_TRANSPORT_INTERFACE_H_
-#define SRC_VNET_SESSION_TRANSPORT_INTERFACE_H_
-
-#include <vnet/vnet.h>
-#include <vnet/session/transport.h>
-
-/*
- * Transport protocol virtual function table
- */
-/* *INDENT-OFF* */
-typedef struct _transport_proto_vft
-{
-  /*
-   * Setup
-   */
-  u32 (*bind) (u32 session_index, transport_endpoint_t * lcl);
-  u32 (*unbind) (u32);
-  int (*open) (transport_endpoint_cfg_t * rmt);
-  void (*close) (u32 conn_index, u32 thread_index);
-  void (*cleanup) (u32 conn_index, u32 thread_index);
-  clib_error_t *(*enable) (vlib_main_t * vm, u8 is_en);
-
-  /*
-   * Transmission
-   */
-
-  u32 (*push_header) (transport_connection_t * tconn, vlib_buffer_t * b);
-  u16 (*send_mss) (transport_connection_t * tc);
-  u32 (*send_space) (transport_connection_t * tc);
-  u32 (*tx_fifo_offset) (transport_connection_t * tc);
-  void (*update_time) (f64 time_now, u8 thread_index);
-  void (*flush_data) (transport_connection_t *tconn);
-
-  /*
-   * Connection retrieval
-   */
-  transport_connection_t *(*get_connection) (u32 conn_idx, u32 thread_idx);
-  transport_connection_t *(*get_listener) (u32 conn_index);
-  transport_connection_t *(*get_half_open) (u32 conn_index);
-
-  /*
-   * Format
-   */
-  u8 *(*format_connection) (u8 * s, va_list * args);
-  u8 *(*format_listener) (u8 * s, va_list * args);
-  u8 *(*format_half_open) (u8 * s, va_list * args);
-
-  /*
-   * Properties
-   */
-  transport_tx_fn_type_t tx_type;
-  transport_service_type_t service_type;
-} transport_proto_vft_t;
-/* *INDENT-ON* */
-
-extern transport_proto_vft_t *tp_vfts;
-
-#define transport_proto_foreach(VAR, BODY)                     \
-do {                                                           \
-    for (VAR = 0; VAR < vec_len (tp_vfts); VAR++)              \
-      if (tp_vfts[VAR].push_header != 0)                       \
-       do { BODY; } while (0);                                 \
-} while (0)
-
-void transport_register_protocol (transport_proto_t transport_proto,
-                                 const transport_proto_vft_t * vft,
-                                 fib_protocol_t fib_proto, u32 output_node);
-transport_proto_vft_t *transport_protocol_get_vft (transport_proto_t tp);
-void transport_update_time (f64 time_now, u8 thread_index);
-transport_connection_t *transport_get_connection (transport_proto_t tp,
-                                                 u32 conn_index,
-                                                 u8 thread_index);
-transport_connection_t *transport_get_listener (transport_proto_t tp,
-                                               u32 conn_index);
-void transport_enable_disable (vlib_main_t * vm, u8 is_en);
-
-always_inline u32
-transport_elog_track_index (transport_connection_t * tc)
-{
-#if TRANSPORT_DEBUG
-  return tc->elog_track.track_index_plus_one - 1;
-#else
-  return ~0;
-#endif
-}
-
-void transport_connection_tx_pacer_reset (transport_connection_t * tc,
-                                         u32 rate_bytes_per_sec,
-                                         u32 initial_bucket, u64 time_now);
-/**
- * Initialize tx pacer for connection
- *
- * @param tc                           transport connection
- * @param rate_bytes_per_second                initial byte rate
- * @param burst_bytes                  initial burst size in bytes
- */
-void transport_connection_tx_pacer_init (transport_connection_t * tc,
-                                        u32 rate_bytes_per_sec,
-                                        u32 initial_bucket);
-
-/**
- * Update tx pacer pacing rate
- *
- * @param tc                   transport connection
- * @param bytes_per_sec                new pacing rate
- */
-void transport_connection_tx_pacer_update (transport_connection_t * tc,
-                                          u64 bytes_per_sec);
-
-/**
- * Get maximum tx burst allowed for transport connection
- *
- * @param tc           transport connection
- * @param time_now     current cpu time as returned by @ref clib_cpu_time_now
- * @param mss          transport's mss
- */
-u32 transport_connection_snd_space (transport_connection_t * tc,
-                                   u64 time_now, u16 mss);
-
-u32 transport_connection_tx_pacer_burst (transport_connection_t * tc,
-                                        u64 time_now);
-
-/**
- * Initialize period for tx pacers
- *
- * Defines a unit of time with respect to number of cpu cycles that is to
- * be used by all tx pacers.
- */
-void transport_init_tx_pacers_period (void);
-
-/**
- * Check if transport connection is paced
- */
-always_inline u8
-transport_connection_is_tx_paced (transport_connection_t * tc)
-{
-  return (tc->flags & TRANSPORT_CONNECTION_F_IS_TX_PACED);
-}
-
-u8 *format_transport_pacer (u8 * s, va_list * args);
-
-/**
- * Update tx byte stats for transport connection
- *
- * If tx pacing is enabled, this also updates pacer bucket to account for the
- * amount of bytes that have been sent.
- *
- * @param tc           transport connection
- * @param pkts         packets recently sent
- * @param bytes                bytes recently sent
- */
-void transport_connection_update_tx_stats (transport_connection_t * tc,
-                                          u32 bytes);
-
-void
-transport_connection_tx_pacer_update_bytes (transport_connection_t * tc,
-                                           u32 bytes);
-
-#endif /* SRC_VNET_SESSION_TRANSPORT_INTERFACE_H_ */
-
-/*
- * fd.io coding-style-patch-verification: ON
- *
- * Local Variables:
- * eval: (c-set-style "gnu")
- * End:
- */
diff --git a/src/vnet/session/transport_types.h b/src/vnet/session/transport_types.h
new file mode 100644 (file)
index 0000000..d309c58
--- /dev/null
@@ -0,0 +1,197 @@
+/*
+ * Copyright (c) 2016-2019 Cisco and/or its affiliates.
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef VNET_VNET_URI_TRANSPORT_TYPES_H_
+#define VNET_VNET_URI_TRANSPORT_TYPES_H_
+
+#include <vnet/vnet.h>
+#include <vnet/ip/ip.h>
+#include <vnet/tcp/tcp_debug.h>
+
+#define TRANSPORT_MAX_HDRS_LEN    100  /* Max number of bytes for headers */
+
+typedef enum transport_dequeue_type_
+{
+  TRANSPORT_TX_PEEK,           /**< reliable transport protos */
+  TRANSPORT_TX_DEQUEUE,                /**< unreliable transport protos */
+  TRANSPORT_TX_INTERNAL,       /**< apps acting as transports */
+  TRANSPORT_TX_DGRAM,          /**< datagram mode */
+  TRANSPORT_TX_N_FNS
+} transport_tx_fn_type_t;
+
+typedef enum transport_service_type_
+{
+  TRANSPORT_SERVICE_VC,                /**< virtual circuit service */
+  TRANSPORT_SERVICE_CL,                /**< connectionless service */
+  TRANSPORT_SERVICE_APP,       /**< app transport service */
+  TRANSPORT_N_SERVICES
+} transport_service_type_t;
+
+typedef struct _transport_stats
+{
+  u64 tx_bytes;
+} transport_stats_t;
+
+typedef struct _spacer
+{
+  u64 bucket;
+  u32 max_burst_size;
+  f32 tokens_per_period;
+  u64 last_update;
+} spacer_t;
+
+/*
+ * Protocol independent transport properties associated to a session
+ */
+typedef struct _transport_connection
+{
+  /** Connection ID */
+  union
+  {
+    /*
+     * Network connection ID tuple
+     */
+    struct
+    {
+      ip46_address_t rmt_ip;   /**< Remote IP */
+      ip46_address_t lcl_ip;   /**< Local IP */
+      u16 rmt_port;            /**< Remote port */
+      u16 lcl_port;            /**< Local port */
+      u8 is_ip4;               /**< Flag if IP4 connection */
+      u8 proto;                        /**< Protocol id */
+      u32 fib_index;           /**< Network namespace */
+    };
+    /*
+     * Opaque connection ID
+     */
+    u8 opaque_conn_id[42];
+  };
+
+  u32 s_index;                 /**< Parent session index */
+  u32 c_index;                 /**< Connection index in transport pool */
+  u32 thread_index;            /**< Worker-thread index */
+
+  /*fib_node_index_t rmt_fei;
+     dpo_id_t rmt_dpo; */
+
+  u8 flags;                    /**< Transport specific flags */
+  transport_stats_t stats;     /**< Transport connection stats */
+  spacer_t pacer;              /**< Simple transport pacer */
+
+#if TRANSPORT_DEBUG
+  elog_track_t elog_track;     /**< Event logging */
+  u32 cc_stat_tstamp;          /**< CC stats timestamp */
+#endif
+
+  /** Macros for 'derived classes' where base is named "connection" */
+#define c_lcl_ip connection.lcl_ip
+#define c_rmt_ip connection.rmt_ip
+#define c_lcl_ip4 connection.lcl_ip.ip4
+#define c_rmt_ip4 connection.rmt_ip.ip4
+#define c_lcl_ip6 connection.lcl_ip.ip6
+#define c_rmt_ip6 connection.rmt_ip.ip6
+#define c_lcl_port connection.lcl_port
+#define c_rmt_port connection.rmt_port
+#define c_proto connection.proto
+#define c_fib_index connection.fib_index
+#define c_s_index connection.s_index
+#define c_c_index connection.c_index
+#define c_is_ip4 connection.is_ip4
+#define c_thread_index connection.thread_index
+#define c_elog_track connection.elog_track
+#define c_cc_stat_tstamp connection.cc_stat_tstamp
+#define c_rmt_fei connection.rmt_fei
+#define c_rmt_dpo connection.rmt_dpo
+#define c_opaque_id connection.opaque_conn_id
+#define c_stats connection.stats
+#define c_pacer connection.pacer
+#define c_flags connection.flags
+} transport_connection_t;
+
+#define TRANSPORT_CONNECTION_F_IS_TX_PACED     1 << 0
+
+typedef enum _transport_proto
+{
+  TRANSPORT_PROTO_TCP,
+  TRANSPORT_PROTO_UDP,
+  TRANSPORT_PROTO_SCTP,
+  TRANSPORT_PROTO_NONE,
+  TRANSPORT_PROTO_TLS,
+  TRANSPORT_PROTO_UDPC,
+  TRANSPORT_N_PROTO
+} transport_proto_t;
+
+u8 *format_transport_proto (u8 * s, va_list * args);
+u8 *format_transport_proto_short (u8 * s, va_list * args);
+u8 *format_transport_connection (u8 * s, va_list * args);
+u8 *format_transport_listen_connection (u8 * s, va_list * args);
+u8 *format_transport_half_open_connection (u8 * s, va_list * args);
+
+uword unformat_transport_proto (unformat_input_t * input, va_list * args);
+
+#define foreach_transport_endpoint_fields                              \
+  _(ip46_address_t, ip) /**< ip address in net order */                        \
+  _(u16, port)         /**< port in net order */                       \
+  _(u8, is_ip4)                /**< set if ip4 */                              \
+  _(u32, sw_if_index)  /**< interface endpoint is associated with  */  \
+  _(u32, fib_index)    /**< fib table endpoint is associated with */   \
+
+typedef struct transport_endpoint_
+{
+#define _(type, name) type name;
+  foreach_transport_endpoint_fields
+#undef _
+} transport_endpoint_t;
+
+#define foreach_transport_endpoint_cfg_fields                          \
+  foreach_transport_endpoint_fields                                    \
+  _(transport_endpoint_t, peer)                                                \
+
+typedef struct transport_endpoint_pair_
+{
+#define _(type, name) type name;
+  foreach_transport_endpoint_cfg_fields
+#undef _
+} transport_endpoint_cfg_t;
+
+typedef clib_bihash_24_8_t transport_endpoint_table_t;
+
+#define ENDPOINT_INVALID_INDEX ((u32)~0)
+
+always_inline u8
+transport_connection_fib_proto (transport_connection_t * tc)
+{
+  return tc->is_ip4 ? FIB_PROTOCOL_IP4 : FIB_PROTOCOL_IP6;
+}
+
+always_inline u8
+transport_endpoint_fib_proto (transport_endpoint_t * tep)
+{
+  return tep->is_ip4 ? FIB_PROTOCOL_IP4 : FIB_PROTOCOL_IP6;
+}
+
+u8 transport_protocol_is_cl (transport_proto_t tp);
+transport_service_type_t transport_protocol_service_type (transport_proto_t);
+transport_tx_fn_type_t transport_protocol_tx_fn_type (transport_proto_t tp);
+
+#endif /* VNET_VNET_URI_TRANSPORT_TYPES_H_ */
+
+/*
+ * fd.io coding-style-patch-verification: ON
+ *
+ * Local Variables:
+ * eval: (c-set-style "gnu")
+ * End:
+ */
index 99b015b..5fdeec6 100644 (file)
@@ -1173,13 +1173,13 @@ tcp_session_flush_data (transport_connection_t * tconn)
 /* *INDENT-OFF* */
 const static transport_proto_vft_t tcp_proto = {
   .enable = vnet_tcp_enable_disable,
-  .bind = tcp_session_bind,
-  .unbind = tcp_session_unbind,
+  .start_listen = tcp_session_bind,
+  .stop_listen = tcp_session_unbind,
   .push_header = tcp_session_push_header,
   .get_connection = tcp_session_get_transport,
   .get_listener = tcp_session_get_listener,
   .get_half_open = tcp_half_open_session_get_transport,
-  .open = tcp_session_open,
+  .connect = tcp_session_open,
   .close = tcp_session_close,
   .cleanup = tcp_session_cleanup,
   .send_mss = tcp_session_send_mss,
index 9032a97..96ffd2c 100644 (file)
@@ -14,7 +14,6 @@
  */
 
 #include <vnet/tcp/tcp.h>
-#include <vnet/lisp-cp/packets.h>
 #include <math.h>
 
 vlib_node_registration_t tcp4_output_node;
@@ -477,7 +476,7 @@ tcp_reuse_buffer (vlib_main_t * vm, vlib_buffer_t * b)
   vnet_buffer (b)->tcp.flags = 0;
 
   /* Leave enough space for headers */
-  return vlib_buffer_make_headroom (b, MAX_HDRS_LEN);
+  return vlib_buffer_make_headroom (b, TRANSPORT_MAX_HDRS_LEN);
 }
 
 static void *
@@ -490,7 +489,7 @@ tcp_init_buffer (vlib_main_t * vm, vlib_buffer_t * b)
   vnet_buffer (b)->tcp.flags = 0;
   VLIB_BUFFER_TRACE_TRAJECTORY_INIT (b);
   /* Leave enough space for headers */
-  return vlib_buffer_make_headroom (b, MAX_HDRS_LEN);
+  return vlib_buffer_make_headroom (b, TRANSPORT_MAX_HDRS_LEN);
 }
 
 /**
@@ -1290,7 +1289,7 @@ tcp_prepare_segment (tcp_worker_ctx_t * wrk, tcp_connection_t * tc,
   int n_bytes = 0;
   u8 *data;
 
-  seg_size = max_deq_bytes + MAX_HDRS_LEN;
+  seg_size = max_deq_bytes + TRANSPORT_MAX_HDRS_LEN;
 
   /*
    * Prepare options
@@ -1339,7 +1338,8 @@ tcp_prepare_segment (tcp_worker_ctx_t * wrk, tcp_connection_t * tc,
       *b = vlib_get_buffer (vm, wrk->tx_buffers[--n_bufs]);
       data = tcp_init_buffer (vm, *b);
       n_bytes = stream_session_peek_bytes (&tc->connection, data, offset,
-                                          bytes_per_buffer - MAX_HDRS_LEN);
+                                          bytes_per_buffer -
+                                          TRANSPORT_MAX_HDRS_LEN);
       b[0]->current_length = n_bytes;
       b[0]->flags |= VLIB_BUFFER_TOTAL_LENGTH_VALID;
       b[0]->total_length_not_including_first_buffer = 0;
@@ -1710,9 +1710,10 @@ tcp_timer_persist_handler (u32 index)
 
   tcp_validate_txf_size (tc, offset);
   tc->snd_opts_len = tcp_make_options (tc, &tc->snd_opts, tc->state);
-  max_snd_bytes = clib_min (tc->snd_mss, tm->bytes_per_buffer - MAX_HDRS_LEN);
-  n_bytes = stream_session_peek_bytes (&tc->connection, data, offset,
-                                      max_snd_bytes);
+  max_snd_bytes =
+    clib_min (tc->snd_mss, tm->bytes_per_buffer - TRANSPORT_MAX_HDRS_LEN);
+  n_bytes =
+    stream_session_peek_bytes (&tc->connection, data, offset, max_snd_bytes);
   b->current_length = n_bytes;
   ASSERT (n_bytes != 0 && (tcp_timer_is_active (tc, TCP_TIMER_RETRANSMIT)
                           || tc->snd_nxt == tc->snd_una_max
index 3f21e6e..ed12378 100644 (file)
@@ -739,12 +739,12 @@ format_tls_half_open (u8 * s, va_list * args)
 
 /* *INDENT-OFF* */
 const static transport_proto_vft_t tls_proto = {
-  .open = tls_connect,
+  .connect = tls_connect,
   .close = tls_disconnect,
-  .bind = tls_start_listen,
+  .start_listen = tls_start_listen,
+  .stop_listen = tls_stop_listen,
   .get_connection = tls_connection_get,
   .get_listener = tls_listener_get,
-  .unbind = tls_stop_listen,
   .tx_type = TRANSPORT_TX_INTERNAL,
   .service_type = TRANSPORT_SERVICE_APP,
   .format_connection = format_tls_connection,
index 7674ef2..694cffa 100644 (file)
@@ -318,9 +318,9 @@ udp_session_get_half_open (u32 conn_index)
 
 /* *INDENT-OFF* */
 const static transport_proto_vft_t udp_proto = {
-  .bind = udp_session_bind,
-  .open = udp_open_connection,
-  .unbind = udp_session_unbind,
+  .start_listen = udp_session_bind,
+  .connect = udp_open_connection,
+  .stop_listen = udp_session_unbind,
   .push_header = udp_push_header,
   .get_connection = udp_session_get,
   .get_listener = udp_session_get_listener,
@@ -362,9 +362,9 @@ udpc_connection_listen (u32 session_index, transport_endpoint_t * lcl)
 
 /* *INDENT-OFF* */
 const static transport_proto_vft_t udpc_proto = {
-  .bind = udpc_connection_listen,
-  .open = udpc_connection_open,
-  .unbind = udp_session_unbind,
+  .start_listen = udpc_connection_listen,
+  .stop_listen = udp_session_unbind,
+  .connect = udpc_connection_open,
   .push_header = udp_push_header,
   .get_connection = udp_session_get,
   .get_listener = udp_session_get_listener,