55 memset (adj, 0xfe, n_adj *
sizeof (adj[0]));
58 adj->
n_adj = save_n_adj;
103 if (this_ai == adj_index)
121 while (this_adj != adj)
142 u32 * adj_index_return)
148 if (copy_adj && n_adj == 1)
185 *adj_index_return = p[0];
204 for (i = 0; i < n_adj; i++)
207 adj[
i].rewrite_header.sw_if_index = ~0;
214 adj[
i] = copy_adj[
i];
226 if (copy_adj && n_adj == 1)
229 *adj_index_return = ai;
247 clib_memcpy (&adj->rewrite_header, ©_adj->rewrite_header,
277 if (delete_multipath_adjacency)
295 : (cmp > 0 ? +1 : -1));
306 uword n_nhs, n_adj, n_adj_left,
i;
307 f64 sum_weight, norm, error;
309 n_nhs =
vec_len (raw_next_hops);
315 nhs = *normalized_next_hops;
322 nhs[0] = raw_next_hops[0];
333 nhs[0] = raw_next_hops[cmp];
334 nhs[1] = raw_next_hops[cmp ^ 1];
337 if (nhs[0].weight == nhs[1].weight)
346 clib_memcpy (nhs, raw_next_hops, n_nhs *
sizeof (raw_next_hops[0]));
352 for (i = 0; i < n_nhs; i++)
353 sum_weight += nhs[i].weight;
358 for (i = 0; i < n_nhs; i++)
364 for (i = 0; i < n_nhs; i++)
365 nhs[n_nhs + i].weight = nhs[i].weight;
369 for (n_adj =
max_pow2 (n_nhs); ; n_adj *= 2)
373 norm = n_adj / sum_weight;
375 for (i = 0; i < n_nhs; i++)
380 n = n > n_adj_left ? n_adj_left : n;
382 error +=
fabs (nf - n);
386 nhs[0].
weight += n_adj_left;
389 if (error <= lm->multipath_next_hop_error_tolerance*n_adj)
399 *normalized_next_hops = nhs;
405 {
return 1 + 2*handle; }
421 uword create_if_non_existent)
424 u32 i, j, n_adj, adj_index, adj_heap_handle;
440 if (! create_if_non_existent)
451 for (j = 0; j < nh->
weight; j++)
453 adj[
i] = copy_adj[0];
486 raw_next_hops,
vec_bytes (raw_next_hops));
490 return adj_heap_handle;
497 u32 old_mp_adj_index,
498 u32 next_hop_adj_index,
500 u32 * new_mp_adj_index)
532 for (i_nh = 0; i_nh < n_nhs; i_nh++)
533 if (nhs[i_nh].next_hop_adj_index == next_hop_adj_index)
537 if (i_nh >= n_nhs && is_del)
543 _vec_len (hash_nhs) = 0;
551 vec_add (hash_nhs, nhs + 0, i_nh);
552 if (i_nh + 1 < n_nhs)
553 vec_add (hash_nhs, nhs + i_nh + 1, n_nhs - (i_nh + 1));
559 if (i_nh < n_nhs && nhs[i_nh].weight == next_hop_weight)
561 new_mp_adj_index[0] = ~0;
567 vec_add (hash_nhs, nhs, n_nhs);
582 nh->
weight = next_hop_weight;
599 if (mp_new != mp_old)
626 u32 i, n_nhs, madj_index, new_madj_index;
641 for (i = 0; i < n_nhs; i++)
642 if (nhs[i].next_hop_adj_index == del_adj_index)
654 _vec_len (hash_nhs) = 0;
656 vec_add (hash_nhs, nhs + 0, i);
658 vec_add (hash_nhs, nhs + i + 1, n_nhs - (i + 1));
664 if (new_madj_index == madj_index)
686 memset (a, 0,
sizeof (a[0]));
706 *n_next_hops = n_nhs;
731 return n0 == n1 && ! memcmp (k0, k1, n0 *
sizeof (k0[0]));
740 u32 * result_if_address_index)
750 if ((a && (address_length != a->
address_length)) || (address_length == 0))
752 vnm->
api_errno = VNET_API_ERROR_ADDRESS_LENGTH_MISMATCH;
754 (
"%U wrong length (expected %d) for interface %U",
765 vnm->
api_errno = VNET_API_ERROR_ADDRESS_NOT_FOUND_FOR_INTERFACE;
768 addr_fib, address_length,
793 if (result_if_address_index)
794 *result_if_address_index = ~0;
804 memset (a, ~0,
sizeof (a[0]));
809 while (pi != (
u32)~0)
827 (hi != ~0) ? hi : ai;
828 if (result_if_address_index)
829 *result_if_address_index = ai;
833 if (result_if_address_index)
851 memset (&template_adj, 0,
sizeof (template_adj));
894 sizeof (ip6_address_fib_t));
907 for (i = 0; i < 256; i++)
922 u32 flow_hash_config = va_arg (*args,
u32);
924 #define _(n,v) if (flow_hash_config & v) s = format (s, "%s ", #n); 939 s =
format (s,
"unknown %d", n);
965 u32 if_address_index = va_arg (*args,
u32);
979 u32 adj_index = va_arg (*args,
u32);
987 vnm->
vlib_main, &adj->rewrite_header, sizeof (adj->rewrite_data));
1002 if (adj->
arp.next_hop.ip6.as_u64[0] || adj->
arp.next_hop.ip6.as_u64[1])
1034 u32 adj_index = va_arg (*args,
u32);
1035 u8 * packet_data = va_arg (*args,
u8 *);
1036 u32 n_packet_data_bytes = va_arg (*args,
u32);
1044 vnm->
vlib_main, &adj->rewrite_header, packet_data, n_packet_data_bytes);
1065 else if (
unformat (input,
"local"))
1071 else if (
unformat (input,
"classify"))
1085 u32 node_index = va_arg (*args,
u32);
1087 u32 sw_if_index, is_ip6;
1092 adj->rewrite_header.node_index = node_index;
1110 if (a_adj->rewrite_header.sw_if_index != sw_if_index)
1129 clib_warning (
"classify adj must specify table index");
1135 adj->rewrite_header.node_index = 0;
1141 vm, &adj->rewrite_header, sizeof (adj->rewrite_data)))
1155 u32 table_id, is_del;
1156 u32 weight, * weights = 0;
1157 u32 * table_ids = 0;
1158 u32 sw_if_index, * sw_if_indices = 0;
1159 ip4_address_t ip4_addr, * ip4_dst_addresses = 0, * ip4_via_next_hops = 0;
1160 ip6_address_t ip6_addr, * ip6_dst_addresses = 0, * ip6_via_next_hops = 0;
1161 u32 dst_address_length, * dst_address_lengths = 0;
1175 memset(&parse_adj, 0,
sizeof (parse_adj));
1179 if (
unformat (line_input,
"table %d", &table_id))
1181 else if (
unformat (line_input,
"del"))
1183 else if (
unformat (line_input,
"add"))
1185 else if (
unformat (line_input,
"count %f", &count))
1188 else if (
unformat (line_input,
"%U/%d",
1190 &dst_address_length))
1192 vec_add1 (ip4_dst_addresses, ip4_addr);
1193 vec_add1 (dst_address_lengths, dst_address_length);
1196 else if (
unformat (line_input,
"%U/%d",
1198 &dst_address_length))
1200 vec_add1 (ip6_dst_addresses, ip6_addr);
1201 vec_add1 (dst_address_lengths, dst_address_length);
1204 else if (
unformat (line_input,
"via %U %U weight %u",
1209 vec_add1 (ip4_via_next_hops, ip4_addr);
1210 vec_add1 (sw_if_indices, sw_if_index);
1215 else if (
unformat (line_input,
"via %U %U weight %u",
1220 vec_add1 (ip6_via_next_hops, ip6_addr);
1221 vec_add1 (sw_if_indices, sw_if_index);
1226 else if (
unformat (line_input,
"via %U %U",
1230 vec_add1 (ip4_via_next_hops, ip4_addr);
1231 vec_add1 (sw_if_indices, sw_if_index);
1236 else if (
unformat (line_input,
"via %U %U",
1240 vec_add1 (ip6_via_next_hops, ip6_addr);
1241 vec_add1 (sw_if_indices, sw_if_index);
1245 else if (
unformat (line_input,
"via %U",
1248 vec_add1 (ip4_via_next_hops, ip4_addr);
1253 else if (
unformat (line_input,
"via %U",
1256 vec_add1 (ip6_via_next_hops, ip6_addr);
1262 else if (
vec_len (ip4_dst_addresses) > 0
1267 else if (
vec_len (ip6_dst_addresses) > 0
1271 else if (
unformat (line_input,
"lookup in table %d", &outer_table_id))
1275 if (
vec_len (ip4_dst_addresses) > 0)
1300 if (
vec_len (ip4_dst_addresses) +
vec_len (ip6_dst_addresses) == 0)
1306 if (
vec_len (ip4_dst_addresses) > 0 &&
vec_len (ip6_dst_addresses) > 0)
1312 if (
vec_len (ip4_dst_addresses) > 0 &&
vec_len (ip6_via_next_hops) > 0)
1318 if (
vec_len (ip6_dst_addresses) > 0 &&
vec_len (ip4_via_next_hops) > 0)
1335 for (i = 0; i <
vec_len (ip4_dst_addresses); i++)
1339 memset (&a, 0,
sizeof (a));
1348 if (vec_len (ip4_via_next_hops) == 0)
1350 uword * dst_hash, * dst_result;
1351 u32 dst_address_u32;
1363 dst_result =
hash_get (dst_hash, dst_address_u32);
1380 u32 i, j, n, f, incr;
1386 for (i = 0; i < n; i++)
1390 for (j = 0; j <
vec_len (ip4_via_next_hops); j++)
1392 if (table_ids[j] != (
u32)~0)
1402 table_ids[j] = p[0];
1409 &ip4_via_next_hops[j],
1411 weights[j], (
u32)~0,
1414 dst.
as_u32 = clib_host_to_net_u32 (incr + clib_net_to_host_u32 (dst.
as_u32));
1423 if (vec_len (add_adj) > 0)
1431 else if (vec_len (ip4_via_next_hops) > 0)
1433 u32 i, j, n, f, incr;
1439 for (i = 0; i < n; i++)
1443 for (j = 0; j <
vec_len (ip4_via_next_hops); j++)
1445 if (table_ids[j] != (
u32)~0)
1455 table_ids[j] = p[0];
1461 &ip4_via_next_hops[j],
1463 weights[j], (
u32)~0,
1466 dst.
as_u32 = clib_host_to_net_u32 (incr + clib_net_to_host_u32 (dst.
as_u32));
1475 for (i = 0; i <
vec_len (ip6_dst_addresses); i++)
1480 memset (&a, 0,
sizeof (a));
1489 if (vec_len (ip6_via_next_hops) == 0)
1491 BVT(clib_bihash_kv) kv, value;
1500 dst_address = ip6_dst_addresses[
i];
1505 kv.key[0] = dst_address.
as_u64[0];
1506 kv.key[1] = dst_address.
as_u64[1];
1507 kv.key[2] = ((
u64)(fib - im6->
fibs)<<32)
1529 for (i = 0; i <
vec_len (ip6_via_next_hops); i++)
1535 &ip6_via_next_hops[i],
1537 weights[i], (
u32)~0,
1544 if (vec_len (add_adj) > 0)
1552 else if (vec_len (ip6_via_next_hops) > 0)
1555 for (i = 0; i <
vec_len (ip6_via_next_hops); i++)
1561 &ip6_via_next_hops[i],
1563 weights[i], (
u32)~0,
1584 .short_help =
"Internet protocol (IP) commands",
1589 .short_help =
"Internet protocol (IP) show commands",
1594 .short_help =
"Internet protocol version 4 (IP4) show commands",
1599 .short_help =
"Internet protocol version 6 (IP6) show commands",
1604 .short_help =
"Add/delete IP routes",
1623 uword *event_data = 0;
1627 if (retry_count > 0)
1632 for (i = 0; i < retry_count; i++)
1676 uword *event_data = 0;
1680 if (retry_count > 0)
1685 for (i = 0; i < retry_count; i++)
1732 u32 sw_if_index = ~0;
1733 int retry_count = 3;
1735 int address_set = 0;
1746 else if (
unformat (line_input,
"retry %d", &retry_count))
1763 if (sw_if_index == ~0)
1765 if (address_set == 0)
1767 if (address_set > 1)
1779 .path =
"ip probe-neighbor",
1781 .short_help =
"ip probe-neighbor <intfc> <ip4-addr> | <ip6-addr> [retry nn]",
1788 u32 address_length : 6;
1794 ip4_route_cmp (
void * a1,
void * a2)
1796 ip4_route_t * r1 = a1;
1797 ip4_route_t * r2 = a2;
1800 return cmp ? cmp : ((int) r1->address_length - (
int) r2->address_length);
1808 ip4_route_t * routes, * r;
1812 int verbose, matching, mtrie, include_empty_fibs;
1820 include_empty_fibs = 0;
1829 else if (
unformat (input,
"mtrie"))
1832 else if (
unformat (input,
"include-empty"))
1833 include_empty_fibs = 1;
1838 else if (
unformat (input,
"clear"))
1841 else if (
unformat (input,
"table %d", &table_id))
1863 if (fib_not_empty == 0 && include_empty_fibs == 0)
1866 if (table_id >= 0 && table_id != (
int)fib->
table_id)
1869 if (include_empty_fibs)
1877 if (include_empty_fibs == 0)
1893 _vec_len (routes) = 0;
1895 _vec_len (results) = 0;
1903 x.address_length =
i;
1917 x.index = p->
value[0];
1924 x.address.data_u32 = p->
key;
1927 x.index = vec_len (results);
1928 vec_add (results, p->value, lm->fib_result_n_words);
1931 x.index = p->
value[0];
1940 if (include_empty_fibs == 0)
1947 "Destination",
"Packets",
"Bytes",
"Adjacency");
1952 uword i, j, n_left, n_nhs, adj_index, * result = 0;
1956 adj_index = r->index;
1960 adj_index = result[0];
1964 if (adj->
n_adj == 1)
1981 for (i = j = 0; i < adj->
n_adj; i++)
1996 msg =
format (msg,
"%-20U",
1998 r->address.data, r->address_length);
2005 msg =
format (msg,
"weight %d, index %d",
2006 nhs[j].weight, adj_index + i);
2009 msg =
format (msg,
", multipath");
2011 msg =
format (msg,
"\n%U%U",
2014 vnm, lm, adj_index + i);
2043 .path =
"show ip fib",
2044 .short_help =
"show ip fib [mtrie] [summary] [table <n>] [<ip4-addr>] [clear] [include-empty]",
2073 r->
index = kvp->value;
2079 u64 count_by_prefix_length[129];
2083 (
BVT(clib_bihash_kv) * kvp,
void *arg)
2091 mask_width = kvp->key[2] & 0xFF;
2116 BVT(clib_bihash) * h = &im6->ip6_lookup_table;
2117 __attribute__((unused))
u8 clear = 0;
2148 memset (ca, 0,
sizeof(*ca));
2154 for (len = 128; len >= 0; len--)
2164 _vec_len (routes) = 0;
2166 _vec_len (results) = 0;
2176 "Destination",
"Packets",
"Bytes",
"Adjacency");
2180 uword i, j, n_left, n_nhs, adj_index, * result = 0;
2184 adj_index = r->
index;
2188 adj_index = result[0];
2192 if (adj->
n_adj == 1)
2209 for (i = j = 0; i < adj->
n_adj; i++)
2224 msg =
format (msg,
"%-45U",
2233 msg =
format (msg,
"weight %d, index %d",
2234 nhs[j].weight, adj_index + i);
2237 msg =
format (msg,
", multipath");
2239 msg =
format (msg,
"\n%U%U",
2242 vnm, lm, adj_index + i);
2269 .path =
"show ip6 fib",
2270 .short_help =
"show ip6 fib [summary] [clear]",
static clib_error_t * ip6_probe_neighbor_wait(vlib_main_t *vm, ip6_address_t *a, u32 sw_if_index, int retry_count)
uword * multipath_adjacency_by_next_hops
#define vec_validate(V, I)
Make sure vector is long enough for given index (no header, unspecified alignment) ...
format_function_t * format_fib_result
always_inline uword max_pow2(uword x)
ip4_fib_t * find_ip4_fib_by_table_index_or_id(ip4_main_t *im, u32 table_index_or_id, u32 flags)
Get or create an IPv4 fib.
#define hash_set(h, key, value)
sll srl srl sll sra u16x4 i
void vlib_validate_combined_counter(vlib_combined_counter_main_t *cm, u32 index)
ip_adjacency_t * adjacency_heap
always_inline uword vlib_process_get_events(vlib_main_t *vm, uword **data_vector)
always_inline f64 fabs(f64 x)
#define hash_unset(h, key)
u16 saved_lookup_next_index
void ip4_add_del_route_next_hop(ip4_main_t *im, u32 flags, ip4_address_t *dst_address, u32 dst_address_length, ip4_address_t *next_hop, u32 next_hop_sw_if_index, u32 next_hop_weight, u32 adj_index, u32 explicit_fib_index)
static u32 ip_multipath_normalize_next_hops(ip_lookup_main_t *lm, ip_multipath_next_hop_t *raw_next_hops, ip_multipath_next_hop_t **normalized_next_hops)
static void(BVT(clib_bihash)*h, BVT(clib_bihash_value)*v)
ip_interface_address_t * if_address_pool
static clib_error_t * ip4_probe_neighbor_wait(vlib_main_t *vm, ip4_address_t *a, u32 sw_if_index, int retry_count)
always_inline void ip_poison_adjacencies(ip_adjacency_t *adj, uword n_adj)
static int ip6_route_cmp(void *a1, void *a2)
ip_lookup_next_t lookup_next_index
ip_adjacency_t * aa_bootstrap(ip_adjacency_t *adjs, u32 n)
static int ip_adjacency_is_multipath(ip_lookup_main_t *lm, u32 adj_index)
uword mhash_unset(mhash_t *h, void *key, uword *old_value)
always_inline u32 ip4_fib_lookup(ip4_main_t *im, u32 sw_if_index, ip4_address_t *dst)
ip_adjacency_t * aa_alloc(ip_adjacency_t *adjs, ip_adjacency_t **blockp, u32 n)
void aa_free(ip_adjacency_t *adjs, ip_adjacency_t *adj)
struct ip_multipath_adjacency_t::@117 unnormalized_next_hops
#define vec_add1(V, E)
Add 1 element to end of vector (unspecified alignment).
vlib_node_registration_t ip6_rewrite_node
(constructor) VLIB_REGISTER_NODE (ip6_rewrite_node)
#define heap_elt_at_index(v, index)
ip_adjacency_t * ip_add_adjacency(ip_lookup_main_t *lm, ip_adjacency_t *copy_adj, u32 n_adj, u32 *adj_index_return)
always_inline uword mhash_set(mhash_t *h, void *key, uword new_value, uword *old_value)
static uword unformat_ip_adjacency(unformat_input_t *input, va_list *args)
#define vec_add2(V, P, N)
Add N elements to end of vector V, return pointer to new elements in P.
#define STRUCT_OFFSET_OF(t, f)
ip_lookup_main_t lookup_main
unformat_function_t unformat_vnet_sw_interface
static int vnet_ip_adjacency_share_compare(ip_adjacency_t *a1, ip_adjacency_t *a2)
static uword ip_next_hop_hash_key_sum(hash_t *h, uword key0)
void ip4_maybe_remap_adjacencies(ip4_main_t *im, u32 table_index_or_table_id, u32 flags)
#define vec_bytes(v)
Number of data bytes in vector.
mhash_t address_to_if_address_index
format_function_t format_vnet_sw_if_index_name
u8 * format_mheap(u8 *s, va_list *va)
clib_error_t * vnet_ip_route_cmd(vlib_main_t *vm, unformat_input_t *main_input, vlib_cli_command_t *cmd)
always_inline ip_multipath_next_hop_t * ip_next_hop_hash_key_get_next_hops(ip_lookup_main_t *lm, uword k, uword *n_next_hops)
#define vec_reset_length(v)
Reset vector length to zero NULL-pointer tolerant.
always_inline void * ip_interface_address_get_address(ip_lookup_main_t *lm, ip_interface_address_t *a)
#define vec_add(V, E, N)
Add N elements to end of vector V (no header, unspecified alignment)
u8 * format_ip_lookup_next(u8 *s, va_list *args)
vnet_main_t * vnet_get_main(void)
static u32 ip_multipath_adjacency_get(ip_lookup_main_t *lm, ip_multipath_next_hop_t *raw_next_hops, uword create_if_non_existent)
always_inline void vlib_counter_add(vlib_counter_t *a, vlib_counter_t *b)
void BV() clib_bihash_foreach_key_value_pair(BVT(clib_bihash)*h, void *callback, void *arg)
u32 next_adj_with_signature
static clib_error_t * ip6_show_fib(vlib_main_t *vm, unformat_input_t *input, vlib_cli_command_t *cmd)
void ip6_adjacency_set_interface_route(vnet_main_t *vnm, ip_adjacency_t *adj, u32 sw_if_index, u32 if_address_index)
u32 * adjacency_remap_table
uword * adj_index_by_signature
ip6_fib_t * find_ip6_fib_by_table_index_or_id(ip6_main_t *im, u32 table_index_or_id, u32 flags)
Get or create an IPv6 fib.
#define vec_elt_at_index(v, i)
Get vector value at index i checking that i is in bounds.
u32 ip_multipath_adjacency_add_del_next_hop(ip_lookup_main_t *lm, u32 is_del, u32 old_mp_adj_index, u32 next_hop_adj_index, u32 next_hop_weight, u32 *new_mp_adj_index)
static u8 * format_ip_interface_address(u8 *s, va_list *args)
always_inline uword ip_next_hop_hash_key_from_handle(uword handle)
#define clib_warning(format, args...)
u32 table_index_or_table_id
#define hash_get_pair(h, key)
static uword unformat_ip_lookup_next(unformat_input_t *input, va_list *args)
format_function_t format_vnet_rewrite
void ip6_add_del_route(ip6_main_t *im, ip6_add_del_route_args_t *args)
void ip_del_adjacency(ip_lookup_main_t *lm, u32 adj_index)
static uword pointer_to_uword(const void *p)
always_inline uword ip_next_hop_hash_key_is_heap_handle(uword k)
void ip4_adjacency_set_interface_route(vnet_main_t *vnm, ip_adjacency_t *adj, u32 sw_if_index, u32 if_address_index)
clib_error_t * ip6_probe_neighbor(vlib_main_t *vm, ip6_address_t *dst, u32 sw_if_index)
u32 lookup_table_nbuckets
int BV() clib_bihash_search(BVT(clib_bihash)*h, BVT(clib_bihash_kv)*search_key, BVT(clib_bihash_kv)*valuep)
void ip_multipath_adjacency_free(ip_lookup_main_t *lm, ip_multipath_adjacency_t *a)
clib_error_t * ip4_probe_neighbor(vlib_main_t *vm, ip4_address_t *dst, u32 sw_if_index)
vnet_api_error_t api_errno
#define VLIB_BUFFER_PRE_DATA_SIZE
ip6_address_t dst_address
static int next_hop_sort_by_weight(ip_multipath_next_hop_t *n1, ip_multipath_next_hop_t *n2)
static uword vnet_ip_adjacency_signature(ip_adjacency_t *adj)
format_function_t format_vnet_sw_interface_name
#define pool_elt_at_index(p, i)
void ip6_maybe_remap_adjacencies(ip6_main_t *im, u32 table_index_or_table_id, u32 flags)
uword * fib_index_by_table_id
always_inline void vlib_counter_zero(vlib_counter_t *a)
always_inline f64 vlib_process_wait_for_event_or_clock(vlib_main_t *vm, f64 dt)
int ip6_address_compare(ip6_address_t *a1, ip6_address_t *a2)
static void vlib_get_combined_counter(vlib_combined_counter_main_t *cm, u32 index, vlib_counter_t *result)
u8 local_next_by_ip_protocol[256]
#define clib_error_create(args...)
static void ip_share_adjacency(ip_lookup_main_t *lm, u32 adj_index)
u8 * format_ip_adjacency(u8 *s, va_list *args)
void vlib_cli_output(vlib_main_t *vm, char *fmt,...)
unformat_function_t unformat_vnet_rewrite
#define IP_LOOKUP_MISS_ADJ_INDEX
#define uword_to_pointer(u, type)
typedef CLIB_PACKED(struct{ip4_address_t address;u32 address_length:6;u32 index:26;})
uword * fib_index_by_table_id
ip6_address_t fib_masks[129]
void mhash_init(mhash_t *h, uword n_value_bytes, uword n_key_bytes)
vlib_node_registration_t ip4_rewrite_node
(constructor) VLIB_REGISTER_NODE (ip4_rewrite_node)
static void ip_del_adjacency2(ip_lookup_main_t *lm, u32 adj_index, u32 delete_multipath_adjacency)
int ip4_address_compare(ip4_address_t *a1, ip4_address_t *a2)
static void add_routes_in_fib(BVT(clib_bihash_kv)*kvp, void *arg)
static void ip_multipath_del_adjacency(ip_lookup_main_t *lm, u32 del_adj_index)
#define vec_free(V)
Free vector's memory (no header).
#define clib_memcpy(a, b, c)
#define IP6_ROUTE_FLAG_DEL
void ip_lookup_init(ip_lookup_main_t *lm, u32 is_ip6)
format_function_t format_vnet_rewrite_header
void vnet_register_ip4_arp_resolution_event(vnet_main_t *vnm, void *address_arg, uword node_index, uword type_opaque, uword data)
void ip6_add_del_route_next_hop(ip6_main_t *im, u32 flags, ip6_address_t *dst_address, u32 dst_address_length, ip6_address_t *next_hop, u32 next_hop_sw_if_index, u32 next_hop_weight, u32 adj_index, u32 explicit_fib_index)
struct ip_multipath_adjacency_t::@117 normalized_next_hops
#define IP4_ROUTE_FLAG_DEL
always_inline uword hash_elts(void *v)
vlib_combined_counter_main_t adjacency_counters
u8 builtin_protocol_by_ip_protocol[256]
#define hash_create2(_elts, _user, _value_bytes,_key_sum, _key_equal,_format_pair, _format_pair_arg)
static void count_routes_in_fib_at_prefix_length(BVT(clib_bihash_kv)*kvp, void *arg)
#define VLIB_CLI_COMMAND(x,...)
#define foreach_flow_hash_bit
u32 * if_address_pool_index_by_sw_if_index
#define hash_create(elts, value_bytes)
ip_multipath_next_hop_t * next_hop_hash_lookup_key
ip4_address_t dst_address
#define IP4_ROUTE_FLAG_ADD
#define heap_elt_with_handle(v, handle)
ip_lookup_main_t lookup_main
void heap_dealloc(void *v, uword handle)
uword hash_memory(void *p, word n_bytes, uword state)
static clib_error_t * ip4_show_fib(vlib_main_t *vm, unformat_input_t *input, vlib_cli_command_t *cmd)
#define heap_alloc(v, size, handle)
void ip_update_adjacency(ip_lookup_main_t *lm, u32 adj_index, ip_adjacency_t *copy_adj)
uword heap_len(void *v, word handle)
always_inline void vlib_zero_combined_counter(vlib_combined_counter_main_t *cm, u32 index)
always_inline ip_adjacency_t * ip_get_adjacency(ip_lookup_main_t *lm, u32 adj_index)
void vnet_register_ip6_neighbor_resolution_event(vnet_main_t *vnm, void *address_arg, uword node_index, uword type_opaque, uword data)
struct ip_adjacency_t::@112::@114 arp
format_function_t format_ip4_fib_mtrie
void qsort(void *base, uword n, uword size, int(*compar)(const void *, const void *))
#define vec_len(v)
Number of elements in vector (rvalue-only, NULL tolerant)
static uword ip_next_hop_hash_key_equal(hash_t *h, uword key0, uword key1)
#define hash_foreach_pair(p, v, body)
always_inline vnet_sw_interface_t * vnet_get_sw_interface(vnet_main_t *vnm, u32 sw_if_index)
#define vec_sort_with_function(vec, f)
Sort a vector using the supplied element comparison function.
struct ip_adjacency_t::@112::@115 classify
u32 table_index_or_table_id
clib_error_t * ip_interface_address_add_del(ip_lookup_main_t *lm, u32 sw_if_index, void *addr_fib, u32 address_length, u32 is_del, u32 *result_if_address_index)
static void ip_unshare_adjacency(ip_lookup_main_t *lm, u32 adj_index)
struct ip_adjacency_t::@112::@116 indirect
#define hash_get_mem(h, key)
always_inline uword ip_next_hop_hash_key_get_heap_handle(uword k)
#define IP4_ROUTE_FLAG_NOT_LAST_IN_GROUP
always_inline word flt_round_nearest(f64 x)
ip_multipath_next_hop_t * next_hop_heap
ip_multipath_adjacency_t * multipath_adjacencies
always_inline uword vlib_in_process_context(vlib_main_t *vm)
#define IP4_ROUTE_FLAG_TABLE_ID
always_inline void ip_call_add_del_adjacency_callbacks(ip_lookup_main_t *lm, u32 adj_index, u32 is_del)
#define IP6_ROUTE_FLAG_ADD
always_inline vlib_process_t * vlib_get_current_process(vlib_main_t *vm)
u64 count_by_prefix_length[129]
#define vec_foreach(var, vec)
Vector iterator.
always_inline f64 vlib_time_now(vlib_main_t *vm)
#define CLIB_MEMORY_BARRIER()
ip_multipath_next_hop_t * next_hop_hash_lookup_key_normalized
always_inline void ip6_address_mask(ip6_address_t *a, ip6_address_t *mask)
uword * adj_index_by_dst_address[33]
#define clib_error_return(e, args...)
#define IP6_ROUTE_FLAG_TABLE_ID
u8 * format_ip_flow_hash_config(u8 *s, va_list *args)
void ip4_add_del_route(ip4_main_t *im, ip4_add_del_route_args_t *args)
static clib_error_t * probe_neighbor_address(vlib_main_t *vm, unformat_input_t *input, vlib_cli_command_t *cmd)
u8 * format_ip_adjacency_packet_data(u8 *s, va_list *args)
#define vec_validate_init_empty(V, I, INIT)
Make sure vector is long enough for given index and initialize empty space (no header, unspecified alignment)
#define CLIB_CACHE_LINE_BYTES
always_inline uword * mhash_get(mhash_t *h, void *key)
f64 multipath_next_hop_error_tolerance
u32 ip6_fib_lookup(ip6_main_t *im, u32 sw_if_index, ip6_address_t *dst)
u32 next_this_sw_interface
format_function_t * format_address_and_length
u32 prev_this_sw_interface