X-Git-Url: https://gerrit.fd.io/r/gitweb?a=blobdiff_plain;f=vnet%2Fvnet%2Fip%2Fip4_forward.c;h=c08870919fcc380686080f12171e70f1b5602ab2;hb=964f93e59f72b93191ed938d823af337b7d2c17e;hp=e099cd9d04752346c9b9ccd1860cc39541343f58;hpb=102ec52bc41c630f011884250e0f20ea49ac6d33;p=vpp.git diff --git a/vnet/vnet/ip/ip4_forward.c b/vnet/vnet/ip/ip4_forward.c index e099cd9d047..c08870919fc 100644 --- a/vnet/vnet/ip/ip4_forward.c +++ b/vnet/vnet/ip/ip4_forward.c @@ -103,6 +103,14 @@ find_ip4_fib_by_table_index_or_id (ip4_main_t * im, fib_index = table_index_or_id; if (! (flags & IP4_ROUTE_FLAG_FIB_INDEX)) { + if (table_index_or_id == ~0) { + table_index_or_id = 0; + while ((p = hash_get (im->fib_index_by_table_id, table_index_or_id))) { + table_index_or_id++; + } + return create_fib_with_table_id (im, table_index_or_id); + } + p = hash_get (im->fib_index_by_table_id, table_index_or_id); if (! p) return create_fib_with_table_id (im, table_index_or_id); @@ -181,7 +189,7 @@ ip4_fib_set_adj_index (ip4_main_t * im, fib->new_hash_values); p = hash_get (hash, dst_address_u32); - memcpy (p, fib->new_hash_values, vec_bytes (fib->new_hash_values)); + clib_memcpy (p, fib->new_hash_values, vec_bytes (fib->new_hash_values)); } } @@ -242,7 +250,9 @@ void ip4_add_del_route (ip4_main_t * im, ip4_add_del_route_args_t * a) old_adj_index = fib->old_hash_values[0]; /* Avoid spurious reference count increments */ - if (old_adj_index == adj_index && !(a->flags & IP4_ROUTE_FLAG_KEEP_OLD_ADJACENCY)) + if (old_adj_index == adj_index + && adj_index != ~0 + && !(a->flags & IP4_ROUTE_FLAG_KEEP_OLD_ADJACENCY)) { ip_adjacency_t * adj = ip_get_adjacency (lm, adj_index); if (adj->share_count > 0) @@ -332,10 +342,12 @@ ip4_add_del_route_next_hop (ip4_main_t * im, } else { - vnm->api_errno = VNET_API_ERROR_NEXT_HOP_NOT_IN_FIB; - error = clib_error_return (0, "next-hop %U/32 not in FIB", - format_ip4_address, next_hop); - goto done; + /* Next hop is not known, so create indirect adj */ + ip_adjacency_t add_adj; + add_adj.lookup_next_index = IP_LOOKUP_NEXT_INDIRECT; + add_adj.indirect.next_hop.ip4.as_u32 = next_hop->as_u32; + add_adj.explicit_fib_index = explicit_fib_index; + ip_add_adjacency (lm, &add_adj, 1, &nh_adj_index); } } else @@ -545,7 +557,7 @@ void ip4_maybe_remap_adjacencies (ip4_main_t * im, else { /* Remap to new adjacency. */ - memcpy (fib->old_hash_values, p->value, vec_bytes (fib->old_hash_values)); + clib_memcpy (fib->old_hash_values, p->value, vec_bytes (fib->old_hash_values)); /* Set new adjacency value. */ fib->new_hash_values[0] = p->value[0] = m - 1; @@ -620,11 +632,18 @@ void ip4_delete_matching_routes (ip4_main_t * im, ip4_maybe_remap_adjacencies (im, table_index_or_table_id, flags); } +void +ip4_forward_next_trace (vlib_main_t * vm, + vlib_node_runtime_t * node, + vlib_frame_t * frame, + vlib_rx_or_tx_t which_adj_index); + always_inline uword ip4_lookup_inline (vlib_main_t * vm, vlib_node_runtime_t * node, vlib_frame_t * frame, - int lookup_for_responses_to_locally_received_packets) + int lookup_for_responses_to_locally_received_packets, + int is_indirect) { ip4_main_t * im = &ip4_main; ip_lookup_main_t * lm = &im->lookup_main; @@ -651,6 +670,7 @@ ip4_lookup_inline (vlib_main_t * vm, ip_adjacency_t * adj0, * adj1; ip4_fib_mtrie_t * mtrie0, * mtrie1; ip4_fib_mtrie_leaf_t leaf0, leaf1; + ip4_address_t * dst_addr0, *dst_addr1; __attribute__((unused)) u32 pi0, fib_index0, adj_index0, is_tcp_udp0; __attribute__((unused)) u32 pi1, fib_index1, adj_index1, is_tcp_udp1; u32 flow_hash_config0, flow_hash_config1; @@ -680,6 +700,20 @@ ip4_lookup_inline (vlib_main_t * vm, ip0 = vlib_buffer_get_current (p0); ip1 = vlib_buffer_get_current (p1); + if (is_indirect) + { + ip_adjacency_t * iadj0, * iadj1; + iadj0 = ip_get_adjacency (lm, vnet_buffer(p0)->ip.adj_index[VLIB_TX]); + iadj1 = ip_get_adjacency (lm, vnet_buffer(p1)->ip.adj_index[VLIB_TX]); + dst_addr0 = &iadj0->indirect.next_hop.ip4; + dst_addr1 = &iadj1->indirect.next_hop.ip4; + } + else + { + 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]); fib_index0 = (vnet_buffer(p0)->sw_if_index[VLIB_TX] == (u32)~0) ? @@ -695,8 +729,8 @@ ip4_lookup_inline (vlib_main_t * vm, leaf0 = leaf1 = IP4_FIB_MTRIE_LEAF_ROOT; - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, &ip0->dst_address, 0); - leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, &ip1->dst_address, 0); + leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, dst_addr0, 0); + leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, dst_addr1, 0); } tcp0 = (void *) (ip0 + 1); @@ -709,20 +743,20 @@ ip4_lookup_inline (vlib_main_t * vm, if (! lookup_for_responses_to_locally_received_packets) { - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, &ip0->dst_address, 1); - leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, &ip1->dst_address, 1); + leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, dst_addr0, 1); + leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, dst_addr1, 1); } if (! lookup_for_responses_to_locally_received_packets) { - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, &ip0->dst_address, 2); - leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, &ip1->dst_address, 2); + leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, dst_addr0, 2); + leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, dst_addr1, 2); } if (! lookup_for_responses_to_locally_received_packets) { - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, &ip0->dst_address, 3); - leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, &ip1->dst_address, 3); + leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, dst_addr0, 3); + leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, dst_addr1, 3); } if (lookup_for_responses_to_locally_received_packets) @@ -741,10 +775,10 @@ ip4_lookup_inline (vlib_main_t * vm, } ASSERT (adj_index0 == ip4_fib_lookup_with_table (im, fib_index0, - &ip0->dst_address, + dst_addr0, /* no_default_route */ 0)); ASSERT (adj_index1 == ip4_fib_lookup_with_table (im, fib_index1, - &ip1->dst_address, + dst_addr1, /* no_default_route */ 0)); adj0 = ip_get_adjacency (lm, adj_index0); adj1 = ip_get_adjacency (lm, adj_index1); @@ -840,6 +874,7 @@ ip4_lookup_inline (vlib_main_t * vm, ip_adjacency_t * adj0; ip4_fib_mtrie_t * mtrie0; ip4_fib_mtrie_leaf_t leaf0; + ip4_address_t * dst_addr0; __attribute__((unused)) u32 pi0, fib_index0, adj_index0, is_tcp_udp0; u32 flow_hash_config0, hash_c0; @@ -850,6 +885,17 @@ ip4_lookup_inline (vlib_main_t * vm, ip0 = vlib_buffer_get_current (p0); + if (is_indirect) + { + ip_adjacency_t * iadj0; + iadj0 = ip_get_adjacency (lm, vnet_buffer(p0)->ip.adj_index[VLIB_TX]); + dst_addr0 = &iadj0->indirect.next_hop.ip4; + } + else + { + 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]; @@ -860,7 +906,7 @@ ip4_lookup_inline (vlib_main_t * vm, leaf0 = IP4_FIB_MTRIE_LEAF_ROOT; - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, &ip0->dst_address, 0); + leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, dst_addr0, 0); } tcp0 = (void *) (ip0 + 1); @@ -869,13 +915,13 @@ ip4_lookup_inline (vlib_main_t * vm, || ip0->protocol == IP_PROTOCOL_UDP); if (! lookup_for_responses_to_locally_received_packets) - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, &ip0->dst_address, 1); + leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, dst_addr0, 1); if (! lookup_for_responses_to_locally_received_packets) - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, &ip0->dst_address, 2); + leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, dst_addr0, 2); if (! lookup_for_responses_to_locally_received_packets) - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, &ip0->dst_address, 3); + leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, dst_addr0, 3); if (lookup_for_responses_to_locally_received_packets) adj_index0 = vnet_buffer (p0)->ip.adj_index[VLIB_RX]; @@ -887,7 +933,7 @@ ip4_lookup_inline (vlib_main_t * vm, } ASSERT (adj_index0 == ip4_fib_lookup_with_table (im, fib_index0, - &ip0->dst_address, + dst_addr0, /* no_default_route */ 0)); adj0 = ip_get_adjacency (lm, adj_index0); @@ -937,6 +983,9 @@ ip4_lookup_inline (vlib_main_t * vm, vlib_put_next_frame (vm, node, next, n_left_to_next); } + if (node->flags & VLIB_NODE_FLAG_TRACE) + ip4_forward_next_trace(vm, node, frame, VLIB_TX); + return frame->n_vectors; } @@ -945,7 +994,9 @@ ip4_lookup (vlib_main_t * vm, vlib_node_runtime_t * node, vlib_frame_t * frame) { - return ip4_lookup_inline (vm, node, frame, /* lookup_for_responses_to_locally_received_packets */ 0); + return ip4_lookup_inline (vm, node, frame, + /* lookup_for_responses_to_locally_received_packets */ 0, + /* is_indirect */ 0); } @@ -974,6 +1025,7 @@ void ip4_adjacency_set_interface_route (vnet_main_t * vnm, node_index = ip4_arp_node.index; adj->if_address_index = if_address_index; adj->arp.next_hop.ip4.as_u32 = 0; + ip46_address_reset(&adj->arp.next_hop); packet_type = VNET_L3_PACKET_TYPE_ARP; } else @@ -1301,29 +1353,45 @@ ip4_sw_interface_add_del (vnet_main_t * vnm, VNET_SW_INTERFACE_ADD_DEL_FUNCTION (ip4_sw_interface_add_del); +static u8 * format_ip4_lookup_trace (u8 * s, va_list * args); + VLIB_REGISTER_NODE (ip4_lookup_node) = { .function = ip4_lookup, .name = "ip4-lookup", .vector_size = sizeof (u32), + .format_trace = format_ip4_lookup_trace, + .n_next_nodes = IP_LOOKUP_N_NEXT, - .next_nodes = { - [IP_LOOKUP_NEXT_MISS] = "ip4-miss", - [IP_LOOKUP_NEXT_DROP] = "ip4-drop", - [IP_LOOKUP_NEXT_PUNT] = "ip4-punt", - [IP_LOOKUP_NEXT_LOCAL] = "ip4-local", - [IP_LOOKUP_NEXT_ARP] = "ip4-arp", - [IP_LOOKUP_NEXT_REWRITE] = "ip4-rewrite-transit", - [IP_LOOKUP_NEXT_CLASSIFY] = "ip4-classify", - [IP_LOOKUP_NEXT_MAP] = "ip4-map", - [IP_LOOKUP_NEXT_MAP_T] = "ip4-map-t", - [IP_LOOKUP_NEXT_SIXRD] = "ip4-sixrd", - [IP_LOOKUP_NEXT_HOP_BY_HOP] = "ip4-hop-by-hop", - [IP_LOOKUP_NEXT_ADD_HOP_BY_HOP] = "ip4-add-hop-by-hop", - [IP_LOOKUP_NEXT_POP_HOP_BY_HOP] = "ip4-pop-hop-by-hop", - }, + .next_nodes = IP4_LOOKUP_NEXT_NODES, +}; + +VLIB_NODE_FUNCTION_MULTIARCH (ip4_lookup_node, ip4_lookup) + +static uword +ip4_indirect (vlib_main_t * vm, + vlib_node_runtime_t * node, + vlib_frame_t * frame) +{ + return ip4_lookup_inline (vm, node, frame, + /* lookup_for_responses_to_locally_received_packets */ 0, + /* is_indirect */ 1); +} + +VLIB_REGISTER_NODE (ip4_indirect_node) = { + .function = ip4_indirect, + .name = "ip4-indirect", + .vector_size = sizeof (u32), + + .format_trace = format_ip4_lookup_trace, + + .n_next_nodes = IP_LOOKUP_N_NEXT, + .next_nodes = IP4_LOOKUP_NEXT_NODES, }; +VLIB_NODE_FUNCTION_MULTIARCH (ip4_indirect_node, ip4_indirect) + + /* Global IP4 main. */ ip4_main_t ip4_main; @@ -1397,33 +1465,52 @@ typedef struct { } ip4_forward_next_trace_t; static u8 * format_ip4_forward_next_trace (u8 * s, va_list * args) +{ + CLIB_UNUSED (vlib_main_t * vm) = va_arg (*args, vlib_main_t *); + CLIB_UNUSED (vlib_node_t * node) = va_arg (*args, vlib_node_t *); + ip4_forward_next_trace_t * t = va_arg (*args, ip4_forward_next_trace_t *); + uword indent = format_get_indent (s); + s = format (s, "%U%U", + format_white_space, indent, + format_ip4_header, t->packet_data); + return s; +} + +static u8 * format_ip4_lookup_trace (u8 * s, va_list * args) { CLIB_UNUSED (vlib_main_t * vm) = va_arg (*args, vlib_main_t *); CLIB_UNUSED (vlib_node_t * node) = va_arg (*args, vlib_node_t *); ip4_forward_next_trace_t * t = va_arg (*args, ip4_forward_next_trace_t *); vnet_main_t * vnm = vnet_get_main(); ip4_main_t * im = &ip4_main; - ip_adjacency_t * adj; uword indent = format_get_indent (s); - adj = ip_get_adjacency (&im->lookup_main, t->adj_index); s = format (s, "fib %d adj-idx %d : %U flow hash: 0x%08x", - t->fib_index, t->adj_index, format_ip_adjacency, - vnm, &im->lookup_main, t->adj_index, t->flow_hash); - switch (adj->lookup_next_index) - { - case IP_LOOKUP_NEXT_REWRITE: - s = format (s, "\n%U%U", - format_white_space, indent, - format_ip_adjacency_packet_data, - vnm, &im->lookup_main, t->adj_index, - t->packet_data, sizeof (t->packet_data)); - break; + t->fib_index, t->adj_index, format_ip_adjacency, + vnm, &im->lookup_main, t->adj_index, t->flow_hash); + s = format (s, "\n%U%U", + format_white_space, indent, + format_ip4_header, t->packet_data); + return s; +} - default: - break; - } +static u8 * format_ip4_rewrite_trace (u8 * s, va_list * args) +{ + CLIB_UNUSED (vlib_main_t * vm) = va_arg (*args, vlib_main_t *); + CLIB_UNUSED (vlib_node_t * node) = va_arg (*args, vlib_node_t *); + ip4_forward_next_trace_t * t = va_arg (*args, ip4_forward_next_trace_t *); + vnet_main_t * vnm = vnet_get_main(); + ip4_main_t * im = &ip4_main; + uword indent = format_get_indent (s); + s = format (s, "tx_sw_if_index %d adj-idx %d : %U flow hash: 0x%08x", + t->fib_index, t->adj_index, format_ip_adjacency, + vnm, &im->lookup_main, t->adj_index, t->flow_hash); + s = format (s, "\n%U%U", + format_white_space, indent, + format_ip_adjacency_packet_data, + vnm, &im->lookup_main, t->adj_index, + t->packet_data, sizeof (t->packet_data)); return s; } @@ -1461,9 +1548,12 @@ ip4_forward_next_trace (vlib_main_t * vm, t0 = vlib_add_trace (vm, node, b0, sizeof (t0[0])); t0->adj_index = vnet_buffer (b0)->ip.adj_index[which_adj_index]; t0->flow_hash = vnet_buffer (b0)->ip.flow_hash; - t0->fib_index = vec_elt (im->fib_index_by_sw_if_index, - vnet_buffer(b0)->sw_if_index[VLIB_RX]); - memcpy (t0->packet_data, + t0->fib_index = (vnet_buffer(b0)->sw_if_index[VLIB_TX] != (u32)~0) ? + vnet_buffer(b0)->sw_if_index[VLIB_TX] : + vec_elt (im->fib_index_by_sw_if_index, + vnet_buffer(b0)->sw_if_index[VLIB_RX]); + + clib_memcpy (t0->packet_data, vlib_buffer_get_current (b0), sizeof (t0->packet_data)); } @@ -1472,9 +1562,11 @@ ip4_forward_next_trace (vlib_main_t * vm, t1 = vlib_add_trace (vm, node, b1, sizeof (t1[0])); t1->adj_index = vnet_buffer (b1)->ip.adj_index[which_adj_index]; t1->flow_hash = vnet_buffer (b1)->ip.flow_hash; - t1->fib_index = vec_elt (im->fib_index_by_sw_if_index, - vnet_buffer(b1)->sw_if_index[VLIB_RX]); - memcpy (t1->packet_data, + t1->fib_index = (vnet_buffer(b1)->sw_if_index[VLIB_TX] != (u32)~0) ? + vnet_buffer(b1)->sw_if_index[VLIB_TX] : + vec_elt (im->fib_index_by_sw_if_index, + vnet_buffer(b1)->sw_if_index[VLIB_RX]); + clib_memcpy (t1->packet_data, vlib_buffer_get_current (b1), sizeof (t1->packet_data)); } @@ -1497,9 +1589,11 @@ ip4_forward_next_trace (vlib_main_t * vm, t0 = vlib_add_trace (vm, node, b0, sizeof (t0[0])); t0->adj_index = vnet_buffer (b0)->ip.adj_index[which_adj_index]; t0->flow_hash = vnet_buffer (b0)->ip.flow_hash; - t0->fib_index = vec_elt (im->fib_index_by_sw_if_index, - vnet_buffer(b0)->sw_if_index[VLIB_RX]); - memcpy (t0->packet_data, + t0->fib_index = (vnet_buffer(b0)->sw_if_index[VLIB_TX] != (u32)~0) ? + vnet_buffer(b0)->sw_if_index[VLIB_TX] : + vec_elt (im->fib_index_by_sw_if_index, + vnet_buffer(b0)->sw_if_index[VLIB_RX]); + clib_memcpy (t0->packet_data, vlib_buffer_get_current (b0), sizeof (t0->packet_data)); } @@ -1562,6 +1656,8 @@ VLIB_REGISTER_NODE (ip4_drop_node,static) = { }, }; +VLIB_NODE_FUNCTION_MULTIARCH (ip4_drop_node, ip4_drop) + VLIB_REGISTER_NODE (ip4_punt_node,static) = { .function = ip4_punt, .name = "ip4-punt", @@ -1575,6 +1671,8 @@ VLIB_REGISTER_NODE (ip4_punt_node,static) = { }, }; +VLIB_NODE_FUNCTION_MULTIARCH (ip4_punt_node, ip4_punt) + VLIB_REGISTER_NODE (ip4_miss_node,static) = { .function = ip4_miss, .name = "ip4-miss", @@ -1588,6 +1686,8 @@ VLIB_REGISTER_NODE (ip4_miss_node,static) = { }, }; +VLIB_NODE_FUNCTION_MULTIARCH (ip4_miss_node, ip4_miss) + /* Compute TCP/UDP/ICMP4 checksum in software. */ u16 ip4_tcp_udp_compute_checksum (vlib_main_t * vm, vlib_buffer_t * p0, @@ -1723,8 +1823,10 @@ ip4_local (vlib_main_t * vm, leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, &ip0->src_address, 0); leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, &ip1->src_address, 0); - proto0 = ip0->protocol; - proto1 = ip1->protocol; + /* Treat IP frag packets as "experimental" protocol for now + until support of IP frag reassembly is implemented */ + proto0 = ip4_is_fragment(ip0) ? 0xfe : ip0->protocol; + proto1 = ip4_is_fragment(ip1) ? 0xfe : ip1->protocol; is_udp0 = proto0 == IP_PROTOCOL_UDP; is_udp1 = proto1 == IP_PROTOCOL_UDP; is_tcp_udp0 = is_udp0 || proto0 == IP_PROTOCOL_TCP; @@ -1916,7 +2018,9 @@ ip4_local (vlib_main_t * vm, leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, &ip0->src_address, 0); - proto0 = ip0->protocol; + /* Treat IP frag packets as "experimental" protocol for now + until support of IP frag reassembly is implemented */ + proto0 = ip4_is_fragment(ip0) ? 0xfe : ip0->protocol; is_udp0 = proto0 == IP_PROTOCOL_UDP; is_tcp_udp0 = is_udp0 || proto0 == IP_PROTOCOL_TCP; @@ -2026,6 +2130,8 @@ VLIB_REGISTER_NODE (ip4_local_node,static) = { }, }; +VLIB_NODE_FUNCTION_MULTIARCH (ip4_local_node, ip4_local) + void ip4_register_protocol (u32 protocol, u32 node_index) { vlib_main_t * vm = vlib_get_main(); @@ -2210,7 +2316,7 @@ ip4_arp (vlib_main_t * vm, hw_if0 = vnet_get_sup_hw_interface (vnm, sw_if_index0); /* Src ethernet address in ARP header. */ - memcpy (h0->ip4_over_ethernet[0].ethernet, hw_if0->hw_address, + clib_memcpy (h0->ip4_over_ethernet[0].ethernet, hw_if0->hw_address, sizeof (h0->ip4_over_ethernet[0].ethernet)); ip4_src_address_for_packet (im, p0, &h0->ip4_over_ethernet[0].ip4, sw_if_index0); @@ -2323,7 +2429,7 @@ ip4_probe_neighbor (vlib_main_t * vm, ip4_address_t * dst, u32 sw_if_index) hi = vnet_get_sup_hw_interface (vnm, sw_if_index); - memcpy (h->ip4_over_ethernet[0].ethernet, hi->hw_address, sizeof (h->ip4_over_ethernet[0].ethernet)); + clib_memcpy (h->ip4_over_ethernet[0].ethernet, hi->hw_address, sizeof (h->ip4_over_ethernet[0].ethernet)); h->ip4_over_ethernet[0].ip4 = src[0]; h->ip4_over_ethernet[1].ip4 = dst[0]; @@ -2684,7 +2790,7 @@ VLIB_REGISTER_NODE (ip4_rewrite_node) = { .name = "ip4-rewrite-transit", .vector_size = sizeof (u32), - .format_trace = format_ip4_forward_next_trace, + .format_trace = format_ip4_rewrite_trace, .n_next_nodes = 2, .next_nodes = { @@ -2693,22 +2799,22 @@ VLIB_REGISTER_NODE (ip4_rewrite_node) = { }, }; -VLIB_REGISTER_NODE (ip4_rewrite_local_node,static) = { +VLIB_NODE_FUNCTION_MULTIARCH (ip4_rewrite_node, ip4_rewrite_transit) + +VLIB_REGISTER_NODE (ip4_rewrite_local_node) = { .function = ip4_rewrite_local, .name = "ip4-rewrite-local", .vector_size = sizeof (u32), .sibling_of = "ip4-rewrite-transit", - .format_trace = format_ip4_forward_next_trace, + .format_trace = format_ip4_rewrite_trace, - .n_next_nodes = 2, - .next_nodes = { - [IP4_REWRITE_NEXT_DROP] = "error-drop", - [IP4_REWRITE_NEXT_ARP] = "ip4-arp", - }, + .n_next_nodes = 0, }; +VLIB_NODE_FUNCTION_MULTIARCH (ip4_rewrite_local_node, ip4_rewrite_local) + static clib_error_t * add_del_interface_table (vlib_main_t * vm, unformat_input_t * input, @@ -2970,6 +3076,9 @@ ip4_lookup_multicast (vlib_main_t * vm, vlib_put_next_frame (vm, node, next, n_left_to_next); } + if (node->flags & VLIB_NODE_FLAG_TRACE) + ip4_forward_next_trace(vm, node, frame, VLIB_TX); + return frame->n_vectors; } @@ -2978,24 +3087,14 @@ VLIB_REGISTER_NODE (ip4_lookup_multicast_node,static) = { .name = "ip4-lookup-multicast", .vector_size = sizeof (u32), + .format_trace = format_ip4_lookup_trace, + .n_next_nodes = IP_LOOKUP_N_NEXT, - .next_nodes = { - [IP_LOOKUP_NEXT_MISS] = "ip4-miss", - [IP_LOOKUP_NEXT_DROP] = "ip4-drop", - [IP_LOOKUP_NEXT_PUNT] = "ip4-punt", - [IP_LOOKUP_NEXT_LOCAL] = "ip4-local", - [IP_LOOKUP_NEXT_ARP] = "ip4-arp", - [IP_LOOKUP_NEXT_REWRITE] = "ip4-rewrite-transit", - [IP_LOOKUP_NEXT_CLASSIFY] = "ip4-classify", - [IP_LOOKUP_NEXT_MAP] = "ip4-map", - [IP_LOOKUP_NEXT_MAP_T] = "ip4-map-t", - [IP_LOOKUP_NEXT_SIXRD] = "ip4-sixrd", - [IP_LOOKUP_NEXT_HOP_BY_HOP] = "ip4-hop-by-hop", - [IP_LOOKUP_NEXT_ADD_HOP_BY_HOP] = "ip4-add-hop-by-hop", - [IP_LOOKUP_NEXT_POP_HOP_BY_HOP] = "ip4-pop-hop-by-hop", - }, + .next_nodes = IP4_LOOKUP_NEXT_NODES, }; +VLIB_NODE_FUNCTION_MULTIARCH (ip4_lookup_multicast_node, ip4_lookup_multicast) + VLIB_REGISTER_NODE (ip4_multicast_node,static) = { .function = ip4_drop, .name = "ip4-multicast",