ip: save fib index for buffer in ip lookup 59/12859/4
authorFlorin Coras <fcoras@cisco.com>
Fri, 1 Jun 2018 19:22:23 +0000 (12:22 -0700)
committerDave Barach <openvpp@barachs.net>
Mon, 4 Jun 2018 11:09:25 +0000 (11:09 +0000)
Avoids recomputing the fib index in ip local for locally delivered
packets and should incur no extra cost when forwarding packets.

Change-Id: Id826ffa8206392087327f154337eabc8a801b4d7
Signed-off-by: Florin Coras <fcoras@cisco.com>
src/vnet/ip/ip4_forward.c
src/vnet/ip/ip4_forward.h
src/vnet/ip/ip6_forward.c
src/vnet/ip/ip6_forward.h
src/vnet/ip/lookup.h

index 40fe9dc..04cfac0 100644 (file)
@@ -1202,8 +1202,8 @@ ip4_local_inline (vlib_main_t * vm,
          ip4_fib_mtrie_leaf_t leaf0, leaf1;
          const dpo_id_t *dpo0, *dpo1;
          const load_balance_t *lb0, *lb1;
-         u32 pi0, next0, fib_index0, lbi0;
-         u32 pi1, next1, fib_index1, lbi1;
+         u32 pi0, next0, lbi0;
+         u32 pi1, next1, lbi1;
          u8 error0, is_udp0, is_tcp_udp0, good_tcp_udp0, proto0;
          u8 error1, is_udp1, is_tcp_udp1, good_tcp_udp1, proto1;
          u32 sw_if_index0, sw_if_index1;
@@ -1268,22 +1268,19 @@ ip4_local_inline (vlib_main_t * vm,
          error1 = (is_tcp_udp1 && !good_tcp_udp1
                    ? IP4_ERROR_TCP_CHECKSUM + is_udp1 : error1);
 
-         fib_index0 = vec_elt (im->fib_index_by_sw_if_index, sw_if_index0);
-         fib_index0 =
-           (vnet_buffer (p0)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? fib_index0 : vnet_buffer (p0)->sw_if_index[VLIB_TX];
+         vnet_buffer (p0)->ip.fib_index =
+           vnet_buffer (p0)->sw_if_index[VLIB_TX] != ~0 ?
+           vnet_buffer (p0)->sw_if_index[VLIB_TX] :
+           vnet_buffer (p0)->ip.fib_index;
 
-         fib_index1 = vec_elt (im->fib_index_by_sw_if_index, sw_if_index1);
-         fib_index1 =
-           (vnet_buffer (p1)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? fib_index1 : vnet_buffer (p1)->sw_if_index[VLIB_TX];
+         vnet_buffer (p1)->ip.fib_index =
+           vnet_buffer (p1)->sw_if_index[VLIB_TX] != ~0 ?
+           vnet_buffer (p1)->sw_if_index[VLIB_TX] :
+           vnet_buffer (p1)->ip.fib_index;
 
-         /* TODO maybe move to lookup? */
-         vnet_buffer (p0)->ip.fib_index = fib_index0;
-         vnet_buffer (p1)->ip.fib_index = fib_index1;
 
-         mtrie0 = &ip4_fib_get (fib_index0)->mtrie;
-         mtrie1 = &ip4_fib_get (fib_index1)->mtrie;
+         mtrie0 = &ip4_fib_get (vnet_buffer (p0)->ip.fib_index)->mtrie;
+         mtrie1 = &ip4_fib_get (vnet_buffer (p1)->ip.fib_index)->mtrie;
 
          leaf0 = ip4_fib_mtrie_lookup_step_one (mtrie0, &ip0->src_address);
          leaf1 = ip4_fib_mtrie_lookup_step_one (mtrie1, &ip1->src_address);
@@ -1374,7 +1371,7 @@ ip4_local_inline (vlib_main_t * vm,
          ip4_header_t *ip0;
          ip4_fib_mtrie_t *mtrie0;
          ip4_fib_mtrie_leaf_t leaf0;
-         u32 pi0, next0, fib_index0, lbi0;
+         u32 pi0, next0, lbi0;
          u8 error0, is_udp0, is_tcp_udp0, good_tcp_udp0, proto0;
          load_balance_t *lb0;
          const dpo_id_t *dpo0;
@@ -1417,12 +1414,12 @@ ip4_local_inline (vlib_main_t * vm,
          error0 = (is_tcp_udp0 && !good_tcp_udp0
                    ? IP4_ERROR_TCP_CHECKSUM + is_udp0 : error0);
 
-         fib_index0 = vec_elt (im->fib_index_by_sw_if_index, sw_if_index0);
-         fib_index0 =
-           (vnet_buffer (p0)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? fib_index0 : vnet_buffer (p0)->sw_if_index[VLIB_TX];
-         vnet_buffer (p0)->ip.fib_index = fib_index0;
-         mtrie0 = &ip4_fib_get (fib_index0)->mtrie;
+         vnet_buffer (p0)->ip.fib_index =
+           vnet_buffer (p0)->sw_if_index[VLIB_TX] != ~0 ?
+           vnet_buffer (p0)->sw_if_index[VLIB_TX] :
+           vnet_buffer (p0)->ip.fib_index;
+
+         mtrie0 = &ip4_fib_get (vnet_buffer (p0)->ip.fib_index)->mtrie;
          leaf0 = ip4_fib_mtrie_lookup_step_one (mtrie0, &ip0->src_address);
          leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, &ip0->src_address,
                                             2);
index 71f58f1..553a053 100644 (file)
@@ -79,10 +79,7 @@ ip4_lookup_inline (vlib_main_t * vm,
          ip4_fib_mtrie_t *mtrie0, *mtrie1, *mtrie2, *mtrie3;
          ip4_fib_mtrie_leaf_t leaf0, leaf1, leaf2, leaf3;
          ip4_address_t *dst_addr0, *dst_addr1, *dst_addr2, *dst_addr3;
-         u32 pi0, fib_index0, lb_index0;
-         u32 pi1, fib_index1, lb_index1;
-         u32 pi2, fib_index2, lb_index2;
-         u32 pi3, fib_index3, lb_index3;
+         u32 pi0, pi1, pi2, pi3, lb_index0, lb_index1, lb_index2, lb_index3;
          flow_hash_config_t flow_hash_config0, flow_hash_config1;
          flow_hash_config_t flow_hash_config2, flow_hash_config3;
          u32 hash_c0, hash_c1, hash_c2, hash_c3;
@@ -133,38 +130,17 @@ ip4_lookup_inline (vlib_main_t * vm,
          dst_addr2 = &ip2->dst_address;
          dst_addr3 = &ip3->dst_address;
 
-         fib_index0 =
-           vec_elt (im->fib_index_by_sw_if_index,
-                    vnet_buffer (p0)->sw_if_index[VLIB_RX]);
-         fib_index1 =
-           vec_elt (im->fib_index_by_sw_if_index,
-                    vnet_buffer (p1)->sw_if_index[VLIB_RX]);
-         fib_index2 =
-           vec_elt (im->fib_index_by_sw_if_index,
-                    vnet_buffer (p2)->sw_if_index[VLIB_RX]);
-         fib_index3 =
-           vec_elt (im->fib_index_by_sw_if_index,
-                    vnet_buffer (p3)->sw_if_index[VLIB_RX]);
-         fib_index0 =
-           (vnet_buffer (p0)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? fib_index0 : vnet_buffer (p0)->sw_if_index[VLIB_TX];
-         fib_index1 =
-           (vnet_buffer (p1)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? fib_index1 : vnet_buffer (p1)->sw_if_index[VLIB_TX];
-         fib_index2 =
-           (vnet_buffer (p2)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? fib_index2 : vnet_buffer (p2)->sw_if_index[VLIB_TX];
-         fib_index3 =
-           (vnet_buffer (p3)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? fib_index3 : vnet_buffer (p3)->sw_if_index[VLIB_TX];
-
+         ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, p0);
+         ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, p1);
+         ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, p2);
+         ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, p3);
 
          if (!lookup_for_responses_to_locally_received_packets)
            {
-             mtrie0 = &ip4_fib_get (fib_index0)->mtrie;
-             mtrie1 = &ip4_fib_get (fib_index1)->mtrie;
-             mtrie2 = &ip4_fib_get (fib_index2)->mtrie;
-             mtrie3 = &ip4_fib_get (fib_index3)->mtrie;
+             mtrie0 = &ip4_fib_get (vnet_buffer (p0)->ip.fib_index)->mtrie;
+             mtrie1 = &ip4_fib_get (vnet_buffer (p1)->ip.fib_index)->mtrie;
+             mtrie2 = &ip4_fib_get (vnet_buffer (p2)->ip.fib_index)->mtrie;
+             mtrie3 = &ip4_fib_get (vnet_buffer (p3)->ip.fib_index)->mtrie;
 
              leaf0 = ip4_fib_mtrie_lookup_step_one (mtrie0, dst_addr0);
              leaf1 = ip4_fib_mtrie_lookup_step_one (mtrie1, dst_addr1);
@@ -317,7 +293,7 @@ ip4_lookup_inline (vlib_main_t * vm,
          ip4_fib_mtrie_t *mtrie0;
          ip4_fib_mtrie_leaf_t leaf0;
          ip4_address_t *dst_addr0;
-         u32 pi0, fib_index0, lbi0;
+         u32 pi0, lbi0;
          flow_hash_config_t flow_hash_config0;
          const dpo_id_t *dpo0;
          u32 hash_c0;
@@ -326,22 +302,13 @@ ip4_lookup_inline (vlib_main_t * vm,
          to_next[0] = pi0;
 
          p0 = vlib_get_buffer (vm, pi0);
-
          ip0 = vlib_buffer_get_current (p0);
-
          dst_addr0 = &ip0->dst_address;
-
-         fib_index0 =
-           vec_elt (im->fib_index_by_sw_if_index,
-                    vnet_buffer (p0)->sw_if_index[VLIB_RX]);
-         fib_index0 =
-           (vnet_buffer (p0)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? fib_index0 : vnet_buffer (p0)->sw_if_index[VLIB_TX];
+         ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, p0);
 
          if (!lookup_for_responses_to_locally_received_packets)
            {
-             mtrie0 = &ip4_fib_get (fib_index0)->mtrie;
-
+             mtrie0 = &ip4_fib_get (vnet_buffer (p0)->ip.fib_index)->mtrie;
              leaf0 = ip4_fib_mtrie_lookup_step_one (mtrie0, dst_addr0);
            }
 
index f4c51e2..275bcc6 100644 (file)
@@ -1213,23 +1213,15 @@ ip6_local_inline (vlib_main_t * vm, vlib_node_runtime_t * node,
                        ? IP6_ERROR_SRC_LOOKUP_MISS : error1);
            }
 
-         /* TODO maybe move to lookup? */
          vnet_buffer (p0)->ip.fib_index =
-           vec_elt (im->fib_index_by_sw_if_index,
-                    vnet_buffer (p0)->sw_if_index[VLIB_RX]);
-         vnet_buffer (p0)->ip.fib_index =
-           (vnet_buffer (p0)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? vnet_buffer (p0)->ip.
-           fib_index : vnet_buffer (p0)->sw_if_index[VLIB_TX];
+           vnet_buffer (p0)->sw_if_index[VLIB_TX] != ~0 ?
+           vnet_buffer (p0)->sw_if_index[VLIB_TX] :
+           vnet_buffer (p0)->ip.fib_index;
 
          vnet_buffer (p1)->ip.fib_index =
-           vec_elt (im->fib_index_by_sw_if_index,
-                    vnet_buffer (p1)->sw_if_index[VLIB_RX]);
-         vnet_buffer (p1)->ip.fib_index =
-           (vnet_buffer (p1)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? vnet_buffer (p1)->ip.
-           fib_index : vnet_buffer (p1)->sw_if_index[VLIB_TX];
-
+           vnet_buffer (p1)->sw_if_index[VLIB_TX] != ~0 ?
+           vnet_buffer (p1)->sw_if_index[VLIB_TX] :
+           vnet_buffer (p1)->ip.fib_index;
 
        skip_checks:
 
@@ -1343,14 +1335,10 @@ ip6_local_inline (vlib_main_t * vm, vlib_node_runtime_t * node,
              error0 = (!ip6_urpf_loose_check (im, p0, ip0)
                        ? IP6_ERROR_SRC_LOOKUP_MISS : error0);
            }
-
-         vnet_buffer (p0)->ip.fib_index =
-           vec_elt (im->fib_index_by_sw_if_index,
-                    vnet_buffer (p0)->sw_if_index[VLIB_RX]);
          vnet_buffer (p0)->ip.fib_index =
-           (vnet_buffer (p0)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? vnet_buffer (p0)->ip.
-           fib_index : vnet_buffer (p0)->sw_if_index[VLIB_TX];
+           vnet_buffer (p0)->sw_if_index[VLIB_TX] != ~0 ?
+           vnet_buffer (p0)->sw_if_index[VLIB_TX] :
+           vnet_buffer (p0)->ip.fib_index;
 
        skip_check:
 
index 790a2bb..fcdcabd 100644 (file)
@@ -76,7 +76,6 @@ ip6_lookup_inline (vlib_main_t * vm,
          ip_lookup_next_t next0, next1;
          ip6_header_t *ip0, *ip1;
          ip6_address_t *dst_addr0, *dst_addr1;
-         u32 fib_index0, fib_index1;
          u32 flow_hash_config0, flow_hash_config1;
          const dpo_id_t *dpo0, *dpo1;
          const load_balance_t *lb0, *lb1;
@@ -106,20 +105,15 @@ ip6_lookup_inline (vlib_main_t * vm,
          dst_addr0 = &ip0->dst_address;
          dst_addr1 = &ip1->dst_address;
 
-         fib_index0 =
-           vec_elt (im->fib_index_by_sw_if_index,
-                    vnet_buffer (p0)->sw_if_index[VLIB_RX]);
-         fib_index1 =
-           vec_elt (im->fib_index_by_sw_if_index,
-                    vnet_buffer (p1)->sw_if_index[VLIB_RX]);
+         ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, p0);
+         ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, p1);
 
-         fib_index0 = (vnet_buffer (p0)->sw_if_index[VLIB_TX] == (u32) ~ 0) ?
-           fib_index0 : vnet_buffer (p0)->sw_if_index[VLIB_TX];
-         fib_index1 = (vnet_buffer (p1)->sw_if_index[VLIB_TX] == (u32) ~ 0) ?
-           fib_index1 : vnet_buffer (p1)->sw_if_index[VLIB_TX];
-
-         lbi0 = ip6_fib_table_fwding_lookup (im, fib_index0, dst_addr0);
-         lbi1 = ip6_fib_table_fwding_lookup (im, fib_index1, dst_addr1);
+         lbi0 = ip6_fib_table_fwding_lookup (im,
+                                             vnet_buffer (p0)->ip.fib_index,
+                                             dst_addr0);
+         lbi1 = ip6_fib_table_fwding_lookup (im,
+                                             vnet_buffer (p1)->ip.fib_index,
+                                             dst_addr1);
 
          lb0 = load_balance_get (lbi0);
          lb1 = load_balance_get (lbi1);
@@ -233,26 +227,19 @@ ip6_lookup_inline (vlib_main_t * vm,
          ip_lookup_next_t next0;
          load_balance_t *lb0;
          ip6_address_t *dst_addr0;
-         u32 fib_index0, flow_hash_config0;
+         u32 flow_hash_config0;
          const dpo_id_t *dpo0;
 
          pi0 = from[0];
          to_next[0] = pi0;
 
          p0 = vlib_get_buffer (vm, pi0);
-
          ip0 = vlib_buffer_get_current (p0);
-
          dst_addr0 = &ip0->dst_address;
-
-         fib_index0 =
-           vec_elt (im->fib_index_by_sw_if_index,
-                    vnet_buffer (p0)->sw_if_index[VLIB_RX]);
-         fib_index0 =
-           (vnet_buffer (p0)->sw_if_index[VLIB_TX] ==
-            (u32) ~ 0) ? fib_index0 : vnet_buffer (p0)->sw_if_index[VLIB_TX];
-
-         lbi0 = ip6_fib_table_fwding_lookup (im, fib_index0, dst_addr0);
+         ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, p0);
+         lbi0 = ip6_fib_table_fwding_lookup (im,
+                                             vnet_buffer (p0)->ip.fib_index,
+                                             dst_addr0);
 
          lb0 = load_balance_get (lbi0);
          flow_hash_config0 = lb0->lb_hash_config;
index a89546f..ecabd81 100644 (file)
@@ -211,6 +211,18 @@ do {                                                                    \
 } while (0)
 /* *INDENT-ON* */
 
+always_inline void
+ip_lookup_set_buffer_fib_index (u32 * fib_index_by_sw_if_index,
+                               vlib_buffer_t * b)
+{
+  vnet_buffer (b)->ip.fib_index =
+    vec_elt (fib_index_by_sw_if_index, vnet_buffer (b)->sw_if_index[VLIB_RX]);
+  vnet_buffer (b)->ip.fib_index =
+    (vnet_buffer (b)->sw_if_index[VLIB_TX] ==
+     (u32) ~ 0) ? vnet_buffer (b)->ip.
+    fib_index : vnet_buffer (b)->sw_if_index[VLIB_TX];
+}
+
 typedef struct _vnet_ip_container_proxy_args
 {
   fib_prefix_t prefix;