cnat: maglev fixes 51/31551/2
authorNathan Skrzypczak <nathan.skrzypczak@gmail.com>
Fri, 5 Mar 2021 16:16:40 +0000 (17:16 +0100)
committerDamjan Marion <dmarion@me.com>
Mon, 15 Mar 2021 17:36:23 +0000 (17:36 +0000)
This fixes cnat_feature node LB
- use siblings instead of direct next_nodes
- only do the lookup if we have NO_NAT
- fix behavior in v6

Type: fix

Change-Id: Ie80c9912946bf55c30eadeb51340f4aec9bb297e
Signed-off-by: Nathan Skrzypczak <nathan.skrzypczak@gmail.com>
src/plugins/cnat/cnat_node_feature.c
src/plugins/cnat/cnat_translation.h
src/plugins/cnat/cnat_types.c
src/plugins/cnat/cnat_types.h

index 4585fcb..f9b6fa2 100644 (file)
@@ -126,19 +126,19 @@ cnat_input_feature_fn (vlib_main_t *vm, vlib_node_runtime_t *node,
        clib_host_to_net_u16 (trk0->ct_ep[VLIB_TX].ce_port);
       session->value.cs_port[VLIB_RX] = udp0->src_port;
 
-      const dpo_id_t *dpo0;
-      const load_balance_t *lb1;
-      fib_entry_t *fib_entry;
-      fib_entry = fib_entry_get (trk0->ct_fei);
-
-      lb1 = load_balance_get (fib_entry->fe_lb /*[fct] */.dpoi_index);
-      dpo0 = load_balance_get_bucket_i (lb1, 0);
+      if (trk0->ct_flags & CNAT_TRK_FLAG_NO_NAT)
+       {
+         const dpo_id_t *dpo0;
+         const load_balance_t *lb1;
 
-      session->value.dpoi_next_node = dpo0->dpoi_next_node;
-      session->value.cs_lbi = dpo0->dpoi_index;
+         lb1 = load_balance_get (trk0->ct_dpo.dpoi_index);
+         /* Assume backend has exactly one item in LB */
+         dpo0 = load_balance_get_bucket_i (lb1, 0);
 
-      if (trk0->ct_flags & CNAT_TRK_FLAG_NO_NAT)
-       session->value.flags |= CNAT_SESSION_FLAG_NO_NAT;
+         session->value.dpoi_next_node = dpo0->dpoi_next_node;
+         session->value.cs_lbi = dpo0->dpoi_index;
+         session->value.flags = CNAT_SESSION_FLAG_NO_NAT;
+       }
 
       /* refcnt session in current client */
       cnat_client_cnt_session (cc);
@@ -146,11 +146,13 @@ cnat_input_feature_fn (vlib_main_t *vm, vlib_node_runtime_t *node,
       trace_flags |= CNAT_TRACE_SESSION_CREATED;
     }
 
-  next0 = session->value.dpoi_next_node;
-  vnet_buffer (b)->ip.adj_index[VLIB_TX] = session->value.cs_lbi;
-
   if (session->value.flags & CNAT_SESSION_FLAG_NO_NAT)
-    goto trace;
+    {
+      /* If we don't translate, directly do the lookup & bypass arc */
+      next0 = session->value.dpoi_next_node;
+      vnet_buffer (b)->ip.adj_index[VLIB_TX] = session->value.cs_lbi;
+      goto trace;
+    }
 
   if (AF_IP4 == ctx->af)
     cnat_translation_ip4 (session, ip4, udp0);
@@ -190,8 +192,7 @@ VLIB_REGISTER_NODE (cnat_input_feature_ip4_node) = {
   .type = VLIB_NODE_TYPE_INTERNAL,
   .n_errors = CNAT_N_ERROR,
   .error_strings = cnat_error_strings,
-  .n_next_nodes = IP_LOOKUP_N_NEXT,
-  .next_nodes = IP4_LOOKUP_NEXT_NODES,
+  .sibling_of = "ip4-lookup",
 };
 
 VNET_FEATURE_INIT (cnat_in_ip4_feature, static) = {
@@ -217,8 +218,7 @@ VLIB_REGISTER_NODE (cnat_input_feature_ip6_node) = {
   .type = VLIB_NODE_TYPE_INTERNAL,
   .n_errors = CNAT_N_ERROR,
   .error_strings = cnat_error_strings,
-  .n_next_nodes = IP6_LOOKUP_N_NEXT,
-  .next_nodes = IP6_LOOKUP_NEXT_NODES,
+  .sibling_of = "ip6-lookup",
 };
 
 VNET_FEATURE_INIT (cnat_in_ip6_feature, static) = {
index 3b6e694..97b0c90 100644 (file)
  */
 extern vlib_combined_counter_main_t cnat_translation_counters;
 
-typedef enum cnat_trk_flag_t_
-{
-  CNAT_TRK_ACTIVE = (1 << 0),
-  CNAT_TRK_FLAG_NO_NAT = (1 << 1),
-} cnat_trk_flag_t;
 
 /**
  * Data used to track an EP in the FIB
index 837f400..9b164c6 100644 (file)
@@ -102,17 +102,29 @@ unformat_cnat_ep (unformat_input_t * input, va_list * args)
   return 1;
 }
 
+uword
+unformat_cnat_ep_flags (unformat_input_t *input, va_list *args)
+{
+  int *a = va_arg (*args, int *);
+  if (unformat (input, ":nonat"))
+    *a = CNAT_TRK_FLAG_NO_NAT;
+  return 1;
+}
+
 uword
 unformat_cnat_ep_tuple (unformat_input_t * input, va_list * args)
 {
   cnat_endpoint_tuple_t *a = va_arg (*args, cnat_endpoint_tuple_t *);
-  if (unformat (input, "%U->%U", unformat_cnat_ep, &a->src_ep,
-               unformat_cnat_ep, &a->dst_ep))
-    ;
-  else if (unformat (input, "->%U", unformat_cnat_ep, &a->dst_ep))
-    ;
-  else if (unformat (input, "%U->", unformat_cnat_ep, &a->src_ep))
-    ;
+  int flgs = 0;
+  if (unformat (input, "%U->%U%U", unformat_cnat_ep, &a->src_ep,
+               unformat_cnat_ep, &a->dst_ep, unformat_cnat_ep_flags, &flgs))
+    a->ep_flags = flgs;
+  else if (unformat (input, "->%U%U", unformat_cnat_ep, &a->dst_ep,
+                    unformat_cnat_ep_flags, &flgs))
+    a->ep_flags = flgs;
+  else if (unformat (input, "%U->%U", unformat_cnat_ep, &a->src_ep,
+                    unformat_cnat_ep_flags, &flgs))
+    a->ep_flags = flgs;
   else
     return 0;
   return 1;
index 47e34e1..c3ec74c 100644 (file)
 
 #define MIN_SRC_PORT ((u16) 0xC000)
 
+typedef enum cnat_trk_flag_t_
+{
+  /* Endpoint is active (static or dhcp resolved) */
+  CNAT_TRK_ACTIVE = (1 << 0),
+  /* Don't translate this endpoint, but still
+   * forward. Used by maglev for DSR */
+  CNAT_TRK_FLAG_NO_NAT = (1 << 1),
+} cnat_trk_flag_t;
+
 typedef enum
 {
   /* Endpoint addr has been resolved */