FD.io VPP  v18.01-8-g0eacf49
Vector Packet Processing
interface_api.c
Go to the documentation of this file.
1 /*
2  *------------------------------------------------------------------
3  * interface_api.c - vnet interface api
4  *
5  * Copyright (c) 2016 Cisco and/or its affiliates.
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at:
9  *
10  * http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  *------------------------------------------------------------------
18  */
19 
20 #include <vnet/vnet.h>
21 #include <vlibmemory/api.h>
22 
23 #include <vnet/interface.h>
24 #include <vnet/api_errno.h>
25 #include <vnet/ethernet/ethernet.h>
26 #include <vnet/ip/ip.h>
27 #include <vnet/fib/fib_table.h>
28 #include <vnet/mfib/mfib_table.h>
29 #include <vnet/l2/l2_vtr.h>
30 #include <vnet/vnet_msg_enum.h>
31 #include <vnet/fib/fib_api.h>
32 #include <vnet/mfib/mfib_table.h>
33 
34 #define vl_typedefs /* define message structures */
35 #include <vnet/vnet_all_api_h.h>
36 #undef vl_typedefs
37 
38 #define vl_endianfun /* define message structures */
39 #include <vnet/vnet_all_api_h.h>
40 #undef vl_endianfun
41 
42 /* instantiate all the print functions we know about */
43 #define vl_print(handle, ...) vlib_cli_output (handle, __VA_ARGS__)
44 #define vl_printfun
45 #include <vnet/vnet_all_api_h.h>
46 #undef vl_printfun
47 
50 
51 #define foreach_vpe_api_msg \
52 _(SW_INTERFACE_SET_FLAGS, sw_interface_set_flags) \
53 _(SW_INTERFACE_SET_MTU, sw_interface_set_mtu) \
54 _(WANT_INTERFACE_EVENTS, want_interface_events) \
55 _(SW_INTERFACE_DUMP, sw_interface_dump) \
56 _(SW_INTERFACE_ADD_DEL_ADDRESS, sw_interface_add_del_address) \
57 _(SW_INTERFACE_SET_RX_MODE, sw_interface_set_rx_mode) \
58 _(SW_INTERFACE_SET_TABLE, sw_interface_set_table) \
59 _(SW_INTERFACE_GET_TABLE, sw_interface_get_table) \
60 _(SW_INTERFACE_SET_UNNUMBERED, sw_interface_set_unnumbered) \
61 _(SW_INTERFACE_CLEAR_STATS, sw_interface_clear_stats) \
62 _(SW_INTERFACE_TAG_ADD_DEL, sw_interface_tag_add_del) \
63 _(SW_INTERFACE_SET_MAC_ADDRESS, sw_interface_set_mac_address) \
64 _(CREATE_VLAN_SUBIF, create_vlan_subif) \
65 _(CREATE_SUBIF, create_subif) \
66 _(DELETE_SUBIF, delete_subif) \
67 _(CREATE_LOOPBACK, create_loopback) \
68 _(CREATE_LOOPBACK_INSTANCE, create_loopback_instance) \
69 _(DELETE_LOOPBACK, delete_loopback) \
70 _(INTERFACE_NAME_RENUMBER, interface_name_renumber)
71 
72 static void
74 {
75  vl_api_sw_interface_set_flags_reply_t *rmp;
76  vnet_main_t *vnm = vnet_get_main ();
77  int rv = 0;
78  clib_error_t *error;
79  u16 flags;
80 
82 
84 
85  error = vnet_sw_interface_set_flags (vnm, ntohl (mp->sw_if_index), flags);
86  if (error)
87  {
88  rv = -1;
89  clib_error_report (error);
90  }
91 
93  REPLY_MACRO (VL_API_SW_INTERFACE_SET_FLAGS_REPLY);
94 }
95 
96 static void
98 {
99  vl_api_sw_interface_set_mtu_reply_t *rmp;
100  vnet_main_t *vnm = vnet_get_main ();
102  u32 sw_if_index = ntohl (mp->sw_if_index);
103  u16 mtu = ntohs (mp->mtu);
105  int rv = 0;
106 
108 
109  vnet_sw_interface_t *si = vnet_get_sw_interface (vnm, sw_if_index);
111  {
112  rv = VNET_API_ERROR_INVALID_VALUE;
113  goto bad_sw_if_index;
114  }
115 
118 
119  if (!eif)
120  {
121  rv = VNET_API_ERROR_FEATURE_DISABLED;
122  goto bad_sw_if_index;
123  }
124 
125  if (mtu < hi->min_supported_packet_bytes)
126  {
127  rv = VNET_API_ERROR_INVALID_VALUE;
128  goto bad_sw_if_index;
129  }
130 
131  if (mtu > hi->max_supported_packet_bytes)
132  {
133  rv = VNET_API_ERROR_INVALID_VALUE;
134  goto bad_sw_if_index;
135  }
136 
137  if (hi->max_packet_bytes != mtu)
138  {
139  hi->max_packet_bytes = mtu;
140  ethernet_set_flags (vnm, si->hw_if_index, flags);
141  }
142 
144  REPLY_MACRO (VL_API_SW_INTERFACE_SET_MTU_REPLY);
145 }
146 
147 static void
150  vnet_sw_interface_t * swif,
151  u8 * interface_name, u32 context)
152 {
155 
156  vl_api_sw_interface_details_t *mp = vl_msg_api_alloc (sizeof (*mp));
157  memset (mp, 0, sizeof (*mp));
158  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_DETAILS);
159  mp->sw_if_index = ntohl (swif->sw_if_index);
160  mp->sup_sw_if_index = ntohl (swif->sup_sw_if_index);
161  mp->admin_up_down = (swif->flags & VNET_SW_INTERFACE_FLAG_ADMIN_UP) ? 1 : 0;
162  mp->link_up_down = (hi->flags & VNET_HW_INTERFACE_FLAG_LINK_UP) ? 1 : 0;
167  mp->link_mtu = ntohs (hi->max_packet_bytes);
168  mp->context = context;
169 
170  strncpy ((char *) mp->interface_name,
171  (char *) interface_name, ARRAY_LEN (mp->interface_name) - 1);
172 
173  /* Send the L2 address for ethernet physical intfcs */
174  if (swif->sup_sw_if_index == swif->sw_if_index
176  {
179 
180  ei = pool_elt_at_index (em->interfaces, hi->hw_instance);
181  ASSERT (sizeof (mp->l2_address) >= sizeof (ei->address));
182  clib_memcpy (mp->l2_address, ei->address, sizeof (ei->address));
183  mp->l2_address_length = ntohl (sizeof (ei->address));
184  }
185  else if (swif->sup_sw_if_index != swif->sw_if_index)
186  {
187  vnet_sub_interface_t *sub = &swif->sub;
188  mp->sub_id = ntohl (sub->id);
189  mp->sub_dot1ad = sub->eth.flags.dot1ad;
190  mp->sub_number_of_tags =
191  sub->eth.flags.one_tag + sub->eth.flags.two_tags * 2;
192  mp->sub_outer_vlan_id = ntohs (sub->eth.outer_vlan_id);
193  mp->sub_inner_vlan_id = ntohs (sub->eth.inner_vlan_id);
194  mp->sub_exact_match = sub->eth.flags.exact_match;
195  mp->sub_default = sub->eth.flags.default_sub;
196  mp->sub_outer_vlan_id_any = sub->eth.flags.outer_vlan_id_any;
197  mp->sub_inner_vlan_id_any = sub->eth.flags.inner_vlan_id_any;
198 
199  /* vlan tag rewrite data */
200  u32 vtr_op = L2_VTR_DISABLED;
201  u32 vtr_push_dot1q = 0, vtr_tag1 = 0, vtr_tag2 = 0;
202 
203  if (l2vtr_get (am->vlib_main, am->vnet_main, swif->sw_if_index,
204  &vtr_op, &vtr_push_dot1q, &vtr_tag1, &vtr_tag2) != 0)
205  {
206  // error - default to disabled
207  mp->vtr_op = ntohl (L2_VTR_DISABLED);
208  clib_warning ("cannot get vlan tag rewrite for sw_if_index %d",
209  swif->sw_if_index);
210  }
211  else
212  {
213  mp->vtr_op = ntohl (vtr_op);
214  mp->vtr_push_dot1q = ntohl (vtr_push_dot1q);
215  mp->vtr_tag1 = ntohl (vtr_tag1);
216  mp->vtr_tag2 = ntohl (vtr_tag2);
217  }
218  }
219 
220  /* pbb tag rewrite data */
221  ethernet_header_t eth_hdr;
222  u32 vtr_op = L2_VTR_DISABLED;
223  u16 outer_tag = 0;
224  u16 b_vlanid = 0;
225  u32 i_sid = 0;
226  memset (&eth_hdr, 0, sizeof (eth_hdr));
227 
228  if (!l2pbb_get (am->vlib_main, am->vnet_main, swif->sw_if_index,
229  &vtr_op, &outer_tag, &eth_hdr, &b_vlanid, &i_sid))
230  {
231  mp->sub_dot1ah = 1;
232  clib_memcpy (mp->b_dmac, eth_hdr.dst_address,
233  sizeof (eth_hdr.dst_address));
234  clib_memcpy (mp->b_smac, eth_hdr.src_address,
235  sizeof (eth_hdr.src_address));
236  mp->b_vlanid = b_vlanid;
237  mp->i_sid = i_sid;
238  }
239 
241  if (tag)
242  strncpy ((char *) mp->tag, (char *) tag, ARRAY_LEN (mp->tag) - 1);
243 
244  vl_msg_api_send (rp, (u8 *) mp);
245 }
246 
247 static void
249 {
251  vnet_sw_interface_t *swif;
254 
256 
257  if (rp == 0)
258  {
259  clib_warning ("Client %d AWOL", mp->client_index);
260  return;
261  }
262 
263  u8 *filter = 0, *name = 0;
264  if (mp->name_filter_valid)
265  {
266  mp->name_filter[ARRAY_LEN (mp->name_filter) - 1] = 0;
267  filter = format (0, "%s%c", mp->name_filter, 0);
268  }
269 
270  char *strcasestr (char *, char *); /* lnx hdr file botch */
271  /* *INDENT-OFF* */
272  pool_foreach (swif, im->sw_interfaces,
273  ({
274  if (!vnet_swif_is_api_visible (swif))
275  continue;
276  vec_reset_length(name);
277  name = format (name, "%U%c", format_vnet_sw_interface_name, am->vnet_main,
278  swif, 0);
279 
280  if (filter && !strcasestr((char *) name, (char *) filter))
281  continue;
282 
283  send_sw_interface_details (am, rp, swif, name, mp->context);
284  }));
285  /* *INDENT-ON* */
286 
287  vec_free (name);
288  vec_free (filter);
289 }
290 
291 static void
294 {
295  vlib_main_t *vm = vlib_get_main ();
296  vnet_main_t *vnm = vnet_get_main ();
297  vl_api_sw_interface_add_del_address_reply_t *rmp;
298  int rv = 0;
299  u32 is_del;
300  clib_error_t *error = 0;
301 
303 
304  is_del = mp->is_add == 0;
305  vnm->api_errno = 0;
306 
307  if (mp->del_all)
309  else if (mp->is_ipv6)
310  error = ip6_add_del_interface_address (vm, ntohl (mp->sw_if_index),
311  (void *) mp->address,
312  mp->address_length, is_del);
313  else
314  error = ip4_add_del_interface_address (vm, ntohl (mp->sw_if_index),
315  (void *) mp->address,
316  mp->address_length, is_del);
317 
318  if (error)
319  {
320  rv = vnm->api_errno;
321  clib_error_report (error);
322  goto done;
323  }
324 
326 
327 done:
328  REPLY_MACRO (VL_API_SW_INTERFACE_ADD_DEL_ADDRESS_REPLY);
329 }
330 
331 void stats_dslock_with_hint (int hint, int tag) __attribute__ ((weak));
332 void
333 stats_dslock_with_hint (int hint, int tag)
334 {
335 }
336 
337 void stats_dsunlock (void) __attribute__ ((weak));
338 void
340 {
341 }
342 
343 static void
345 {
346  vl_api_sw_interface_set_table_reply_t *rmp;
347  u32 sw_if_index = ntohl (mp->sw_if_index);
348  u32 table_id = ntohl (mp->vrf_id);
349  int rv = 0;
350 
352 
353  stats_dslock_with_hint (1 /* release hint */ , 4 /* tag */ );
354 
355  if (mp->is_ipv6)
356  rv = ip_table_bind (FIB_PROTOCOL_IP6, sw_if_index, table_id, 1);
357  else
358  rv = ip_table_bind (FIB_PROTOCOL_IP4, sw_if_index, table_id, 1);
359 
360  stats_dsunlock ();
361 
363 
364  REPLY_MACRO (VL_API_SW_INTERFACE_SET_TABLE_REPLY);
365 }
366 
367 int
369  u32 sw_if_index, u32 table_id, u8 is_api)
370 {
372  u32 fib_index, mfib_index;
373  fib_source_t src;
374  mfib_source_t msrc;
375 
376  if (is_api)
377  {
378  src = FIB_SOURCE_API;
379  msrc = MFIB_SOURCE_API;
380  }
381  else
382  {
383  src = FIB_SOURCE_CLI;
384  msrc = MFIB_SOURCE_CLI;
385  }
386 
387  /*
388  * This is temporary whilst I do the song and dance with the CSIT version
389  */
390  if (0 != table_id)
391  {
392  fib_index = fib_table_find_or_create_and_lock (fproto, table_id, src);
393  mfib_index =
394  mfib_table_find_or_create_and_lock (fproto, table_id, msrc);
395  }
396  else
397  {
398  fib_index = 0;
399  mfib_index = 0;
400  }
401 
402  /*
403  * This if table does not exist = error is what we want in the end.
404  */
405  /* fib_index = fib_table_find (fproto, table_id); */
406  /* mfib_index = mfib_table_find (fproto, table_id); */
407 
408  /* if (~0 == fib_index || ~0 == mfib_index) */
409  /* { */
410  /* return (VNET_API_ERROR_NO_SUCH_FIB); */
411  /* } */
412 
413  if (FIB_PROTOCOL_IP6 == fproto)
414  {
415  /*
416  * If the interface already has in IP address, then a change int
417  * VRF is not allowed. The IP address applied must first be removed.
418  * We do not do that automatically here, since VPP has no knowledge
419  * of whether thoses subnets are valid in the destination VRF.
420  */
421  /* *INDENT-OFF* */
423  ia, sw_if_index,
424  1 /* honor unnumbered */ ,
425  ({
426  return (VNET_API_ERROR_ADDRESS_FOUND_FOR_INTERFACE);
427  }));
428  /* *INDENT-ON* */
429 
432 
433  /*
434  * tell those that are interested that the binding is changing.
435  */
438  cb->function (&ip6_main, cb->function_opaque,
439  sw_if_index,
440  fib_index,
441  ip6_main.fib_index_by_sw_if_index[sw_if_index]);
442 
443  if (0 == table_id)
444  {
445  /* reset back to default */
446  if (0 != ip6_main.fib_index_by_sw_if_index[sw_if_index])
448  FIB_PROTOCOL_IP6, src);
449  if (0 != ip6_main.mfib_index_by_sw_if_index[sw_if_index])
451  [sw_if_index], FIB_PROTOCOL_IP6, msrc);
452 
453  }
454  else
455  {
456  /* we need to lock the table now it's inuse */
457  fib_table_lock (fib_index, FIB_PROTOCOL_IP6, src);
458  mfib_table_lock (mfib_index, FIB_PROTOCOL_IP6, msrc);
459  }
460 
461  ip6_main.fib_index_by_sw_if_index[sw_if_index] = fib_index;
462  ip6_main.mfib_index_by_sw_if_index[sw_if_index] = mfib_index;
463  }
464  else
465  {
466  /*
467  * If the interface already has in IP address, then a change int
468  * VRF is not allowed. The IP address applied must first be removed.
469  * We do not do that automatically here, since VPP has no knowledge
470  * of whether thoses subnets are valid in the destination VRF.
471  */
472  /* *INDENT-OFF* */
474  ia, sw_if_index,
475  1 /* honor unnumbered */ ,
476  ({
477  return (VNET_API_ERROR_ADDRESS_FOUND_FOR_INTERFACE);
478  }));
479  /* *INDENT-ON* */
480 
483 
484  /*
485  * tell those that are interested that the binding is changing.
486  */
489  cb->function (&ip4_main, cb->function_opaque,
490  sw_if_index,
491  fib_index,
492  ip4_main.fib_index_by_sw_if_index[sw_if_index]);
493 
494  if (0 == table_id)
495  {
496  /* reset back to default */
497  if (0 != ip4_main.fib_index_by_sw_if_index[sw_if_index])
499  FIB_PROTOCOL_IP4, src);
500  if (0 != ip4_main.mfib_index_by_sw_if_index[sw_if_index])
502  [sw_if_index], FIB_PROTOCOL_IP4, msrc);
503 
504  }
505  else
506  {
507  /* we need to lock the table now it's inuse */
509  table_id, src);
510 
512  table_id, msrc);
513  }
514 
515  ip4_main.fib_index_by_sw_if_index[sw_if_index] = fib_index;
516  ip4_main.mfib_index_by_sw_if_index[sw_if_index] = mfib_index;
517  }
518 
519  /*
520  * Temporary. undo the locks from the find and create at the staart
521  */
522  if (0 != table_id)
523  {
524  fib_table_unlock (fib_index, fproto, src);
525  mfib_table_unlock (mfib_index, fproto, msrc);
526  }
527 
528  return (0);
529 }
530 
531 static void
533  u32 context, int retval, u32 vrf_id)
534 {
536 
537  mp = vl_msg_api_alloc (sizeof (*mp));
538  memset (mp, 0, sizeof (*mp));
539  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_GET_TABLE_REPLY);
540  mp->context = context;
541  mp->retval = htonl (retval);
542  mp->vrf_id = htonl (vrf_id);
543 
544  vl_msg_api_send_shmem (q, (u8 *) & mp);
545 }
546 
547 static void
549 {
551  fib_table_t *fib_table = 0;
552  u32 sw_if_index = ~0;
553  u32 fib_index = ~0;
554  u32 table_id = ~0;
555  fib_protocol_t fib_proto = FIB_PROTOCOL_IP4;
556  int rv = 0;
557 
559  if (q == 0)
560  return;
561 
563 
564  sw_if_index = ntohl (mp->sw_if_index);
565 
566  if (mp->is_ipv6)
567  fib_proto = FIB_PROTOCOL_IP6;
568 
569  fib_index = fib_table_get_index_for_sw_if_index (fib_proto, sw_if_index);
570  if (fib_index != ~0)
571  {
572  fib_table = fib_table_get (fib_index, fib_proto);
573  table_id = fib_table->ft_table_id;
574  }
575 
577 
578  send_sw_interface_get_table_reply (q, mp->context, rv, table_id);
579 }
580 
583 {
584  vl_api_sw_interface_set_unnumbered_reply_t *rmp;
585  int rv = 0;
586  vnet_main_t *vnm = vnet_get_main ();
587  u32 sw_if_index = ntohl (mp->sw_if_index);
588  u32 unnumbered_sw_if_index = ntohl (mp->unnumbered_sw_if_index);
589  u32 was_unnum;
590 
591  /*
592  * The API message field names are backwards from
593  * the underlying data structure names.
594  * It's not worth changing them now.
595  */
596  if (!vnet_sw_interface_is_api_valid (vnm, unnumbered_sw_if_index))
597  {
598  rv = VNET_API_ERROR_INVALID_SW_IF_INDEX;
599  goto done;
600  }
601 
602  /* Only check the "use loop0" field when setting the binding */
603  if (mp->is_add && !vnet_sw_interface_is_api_valid (vnm, sw_if_index))
604  {
605  rv = VNET_API_ERROR_INVALID_SW_IF_INDEX_2;
606  goto done;
607  }
608 
609  vnet_sw_interface_t *si =
610  vnet_get_sw_interface (vnm, unnumbered_sw_if_index);
611  was_unnum = (si->flags & VNET_SW_INTERFACE_FLAG_UNNUMBERED);
612 
613  if (mp->is_add)
614  {
616  si->unnumbered_sw_if_index = sw_if_index;
617 
619  [unnumbered_sw_if_index] =
620  ip4_main.
621  lookup_main.if_address_pool_index_by_sw_if_index[sw_if_index];
622  ip6_main.
623  lookup_main.if_address_pool_index_by_sw_if_index
624  [unnumbered_sw_if_index] =
625  ip6_main.
626  lookup_main.if_address_pool_index_by_sw_if_index[sw_if_index];
627  }
628  else
629  {
631  si->unnumbered_sw_if_index = (u32) ~ 0;
632 
634  [unnumbered_sw_if_index] = ~0;
636  [unnumbered_sw_if_index] = ~0;
637  }
638 
639  if (was_unnum != (si->flags & VNET_SW_INTERFACE_FLAG_UNNUMBERED))
640  {
641  ip4_sw_interface_enable_disable (unnumbered_sw_if_index, mp->is_add);
642  ip6_sw_interface_enable_disable (unnumbered_sw_if_index, mp->is_add);
643  }
644 
645 done:
646  REPLY_MACRO (VL_API_SW_INTERFACE_SET_UNNUMBERED_REPLY);
647 }
648 
649 static void
651  mp)
652 {
653  vl_api_sw_interface_clear_stats_reply_t *rmp;
654 
655  vnet_main_t *vnm = vnet_get_main ();
659  static vnet_main_t **my_vnet_mains;
660  int i, j, n_counters;
661  int rv = 0;
662 
663  if (mp->sw_if_index != ~0)
665 
666  vec_reset_length (my_vnet_mains);
667 
668  for (i = 0; i < vec_len (vnet_mains); i++)
669  {
670  if (vnet_mains[i])
671  vec_add1 (my_vnet_mains, vnet_mains[i]);
672  }
673 
674  if (vec_len (vnet_mains) == 0)
675  vec_add1 (my_vnet_mains, vnm);
676 
677  n_counters = vec_len (im->combined_sw_if_counters);
678 
679  for (j = 0; j < n_counters; j++)
680  {
681  for (i = 0; i < vec_len (my_vnet_mains); i++)
682  {
683  im = &my_vnet_mains[i]->interface_main;
684  cm = im->combined_sw_if_counters + j;
685  if (mp->sw_if_index == (u32) ~ 0)
687  else
688  vlib_zero_combined_counter (cm, ntohl (mp->sw_if_index));
689  }
690  }
691 
692  n_counters = vec_len (im->sw_if_counters);
693 
694  for (j = 0; j < n_counters; j++)
695  {
696  for (i = 0; i < vec_len (my_vnet_mains); i++)
697  {
698  im = &my_vnet_mains[i]->interface_main;
699  sm = im->sw_if_counters + j;
700  if (mp->sw_if_index == (u32) ~ 0)
702  else
703  vlib_zero_simple_counter (sm, ntohl (mp->sw_if_index));
704  }
705  }
706 
708 
709  REPLY_MACRO (VL_API_SW_INTERFACE_CLEAR_STATS_REPLY);
710 }
711 
712 #define API_LINK_STATE_EVENT 1
713 #define API_ADMIN_UP_DOWN_EVENT 2
714 
715 static int
716 event_data_cmp (void *a1, void *a2)
717 {
718  uword *e1 = a1;
719  uword *e2 = a2;
720 
721  return (word) e1[0] - (word) e2[0];
722 }
723 
724 static void
728  vnet_sw_interface_t * swif)
729 {
731  vnet_main_t *vnm = am->vnet_main;
732 
734  swif->sw_if_index);
735  mp = vl_msg_api_alloc (sizeof (*mp));
736  memset (mp, 0, sizeof (*mp));
737  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_EVENT);
738  mp->sw_if_index = ntohl (swif->sw_if_index);
739  mp->client_index = reg->client_index;
740  mp->pid = reg->client_pid;
741 
742  mp->admin_up_down = (swif->flags & VNET_SW_INTERFACE_FLAG_ADMIN_UP) ? 1 : 0;
743  mp->link_up_down = (hi->flags & VNET_HW_INTERFACE_FLAG_LINK_UP) ? 1 : 0;
744  vl_msg_api_send_shmem (q, (u8 *) & mp);
745 }
746 
747 static uword
750 {
752  vnet_main_t *vnm = vam->vnet_main;
753  vnet_sw_interface_t *swif;
754  uword *event_data = 0;
756  int i;
757  u32 prev_sw_if_index;
759 
760  vam->link_state_process_up = 1;
761 
762  while (1)
763  {
765 
766  /* Unified list of changed link or admin state sw_if_indices */
768  (vm, &event_data, API_LINK_STATE_EVENT);
770  (vm, &event_data, API_ADMIN_UP_DOWN_EVENT);
771 
772  /* Sort, so we can eliminate duplicates */
774 
775  prev_sw_if_index = ~0;
776 
777  for (i = 0; i < vec_len (event_data); i++)
778  {
779  /* Only one message per swif */
780  if (prev_sw_if_index == event_data[i])
781  continue;
782  prev_sw_if_index = event_data[i];
783 
784  /* *INDENT-OFF* */
785  pool_foreach(reg, vam->interface_events_registrations,
786  ({
787  q = vl_api_client_index_to_input_queue (reg->client_index);
788  if (q)
789  {
790  /* sw_interface may be deleted already */
791  if (!pool_is_free_index (vnm->interface_main.sw_interfaces,
792  event_data[i]))
793  {
794  swif = vnet_get_sw_interface (vnm, event_data[i]);
795  send_sw_interface_event (vam, reg, q, swif);
796  }
797  }
798  }));
799  /* *INDENT-ON* */
800  }
801  vec_reset_length (event_data);
802  }
803 
804  return 0;
805 }
806 
807 static clib_error_t *link_up_down_function (vnet_main_t * vm, u32 hw_if_index,
808  u32 flags);
810  u32 hw_if_index, u32 flags);
811 
812 /* *INDENT-OFF* */
813 VLIB_REGISTER_NODE (link_state_process_node,static) = {
814  .function = link_state_process,
815  .type = VLIB_NODE_TYPE_PROCESS,
816  .name = "vpe-link-state-process",
817 };
818 /* *INDENT-ON* */
819 
820 VNET_SW_INTERFACE_ADMIN_UP_DOWN_FUNCTION (admin_up_down_function);
821 VNET_HW_INTERFACE_LINK_UP_DOWN_FUNCTION (link_up_down_function);
822 
823 static clib_error_t *
824 link_up_down_function (vnet_main_t * vm, u32 hw_if_index, u32 flags)
825 {
827  vnet_hw_interface_t *hi = vnet_get_hw_interface (vm, hw_if_index);
828 
829  if (vam->link_state_process_up)
831  link_state_process_node.index,
833  return 0;
834 }
835 
836 static clib_error_t *
837 admin_up_down_function (vnet_main_t * vm, u32 sw_if_index, u32 flags)
838 {
840 
841  /*
842  * Note: it's perfectly fair to set a subif admin up / admin down.
843  * Note the subtle distinction between this routine and the previous
844  * routine.
845  */
846  if (vam->link_state_process_up)
848  link_state_process_node.index,
849  API_ADMIN_UP_DOWN_EVENT, sw_if_index);
850  return 0;
851 }
852 
855 {
856  vnet_main_t *vnm = vnet_get_main ();
857  vl_api_sw_interface_tag_add_del_reply_t *rmp;
858  int rv = 0;
859  u8 *tag;
860  u32 sw_if_index = ntohl (mp->sw_if_index);
861 
863 
864  if (mp->is_add)
865  {
866  if (mp->tag[0] == 0)
867  {
868  rv = VNET_API_ERROR_INVALID_VALUE;
869  goto out;
870  }
871 
872  mp->tag[ARRAY_LEN (mp->tag) - 1] = 0;
873  tag = format (0, "%s%c", mp->tag, 0);
874  vnet_set_sw_interface_tag (vnm, tag, sw_if_index);
875  }
876  else
877  vnet_clear_sw_interface_tag (vnm, sw_if_index);
878 
880 out:
881  REPLY_MACRO (VL_API_SW_INTERFACE_TAG_ADD_DEL_REPLY);
882 }
883 
886 {
887  vl_api_sw_interface_set_mac_address_reply_t *rmp;
888  vnet_main_t *vnm = vnet_get_main ();
889  u32 sw_if_index = ntohl (mp->sw_if_index);
891  clib_error_t *error;
892  int rv = 0;
893 
895 
896  si = vnet_get_sw_interface (vnm, sw_if_index);
898  mp->mac_address);
899  if (error)
900  {
901  rv = VNET_API_ERROR_UNIMPLEMENTED;
902  clib_error_report (error);
903  goto out;
904  }
905 
907 out:
908  REPLY_MACRO (VL_API_SW_INTERFACE_SET_MAC_ADDRESS_REPLY);
909 }
910 
913 {
914  vl_api_sw_interface_set_rx_mode_reply_t *rmp;
915  vnet_main_t *vnm = vnet_get_main ();
916  u32 sw_if_index = ntohl (mp->sw_if_index);
918  clib_error_t *error;
919  int rv = 0;
920 
922 
923  si = vnet_get_sw_interface (vnm, sw_if_index);
925  mp->queue_id_valid,
926  ntohl (mp->queue_id), mp->mode);
927  if (error)
928  {
929  rv = VNET_API_ERROR_UNIMPLEMENTED;
930  clib_error_report (error);
931  goto out;
932  }
933 
935 out:
936  REPLY_MACRO (VL_API_SW_INTERFACE_SET_RX_MODE_REPLY);
937 }
938 
939 static void
941 {
943  vnet_main_t *vnm = vnet_get_main ();
944  u32 sw_if_index = (u32) ~ 0;
946  int rv = 0;
947  u32 id;
948  vnet_sw_interface_t template;
949  uword *p;
951  u64 sup_and_sub_key;
953  clib_error_t *error;
954 
956 
957  hi = vnet_get_sup_hw_interface (vnm, ntohl (mp->sw_if_index));
958 
960  {
961  rv = VNET_API_ERROR_BOND_SLAVE_NOT_ALLOWED;
962  goto out;
963  }
964 
965  id = ntohl (mp->vlan_id);
966  if (id == 0 || id > 4095)
967  {
968  rv = VNET_API_ERROR_INVALID_VLAN;
969  goto out;
970  }
971 
972  sup_and_sub_key = ((u64) (hi->sw_if_index) << 32) | (u64) id;
973 
974  p = hash_get_mem (im->sw_if_index_by_sup_and_sub, &sup_and_sub_key);
975  if (p)
976  {
977  rv = VNET_API_ERROR_VLAN_ALREADY_EXISTS;
978  goto out;
979  }
980 
981  memset (&template, 0, sizeof (template));
982  template.type = VNET_SW_INTERFACE_TYPE_SUB;
983  template.sup_sw_if_index = hi->sw_if_index;
984  template.sub.id = id;
985  template.sub.eth.raw_flags = 0;
986  template.sub.eth.flags.one_tag = 1;
987  template.sub.eth.outer_vlan_id = id;
988  template.sub.eth.flags.exact_match = 1;
989 
990  error = vnet_create_sw_interface (vnm, &template, &sw_if_index);
991  if (error)
992  {
993  clib_error_report (error);
994  rv = VNET_API_ERROR_INVALID_REGISTRATION;
995  goto out;
996  }
997 
998  u64 *kp = clib_mem_alloc (sizeof (*kp));
999  *kp = sup_and_sub_key;
1000 
1001  hash_set (hi->sub_interface_sw_if_index_by_id, id, sw_if_index);
1002  hash_set_mem (im->sw_if_index_by_sup_and_sub, kp, sw_if_index);
1003 
1005 
1006 out:
1008  if (!q)
1009  return;
1010 
1011  rmp = vl_msg_api_alloc (sizeof (*rmp));
1012  rmp->_vl_msg_id = htons (VL_API_CREATE_VLAN_SUBIF_REPLY);
1013  rmp->context = mp->context;
1014  rmp->retval = htonl (rv);
1015  rmp->sw_if_index = htonl (sw_if_index);
1016  vl_msg_api_send_shmem (q, (u8 *) & rmp);
1017 }
1018 
1019 static void
1021 {
1023  vnet_main_t *vnm = vnet_get_main ();
1024  u32 sw_if_index = ~0;
1025  int rv = 0;
1026  u32 sub_id;
1027  vnet_sw_interface_t *si;
1029  vnet_sw_interface_t template;
1030  uword *p;
1032  u64 sup_and_sub_key;
1033  clib_error_t *error;
1034 
1035  VALIDATE_SW_IF_INDEX (mp);
1036 
1037  si = vnet_get_sup_sw_interface (vnm, ntohl (mp->sw_if_index));
1038  hi = vnet_get_sup_hw_interface (vnm, ntohl (mp->sw_if_index));
1039 
1041  {
1042  rv = VNET_API_ERROR_BOND_SLAVE_NOT_ALLOWED;
1043  goto out;
1044  }
1045 
1046  sw_if_index = si->sw_if_index;
1047  sub_id = ntohl (mp->sub_id);
1048 
1049  sup_and_sub_key = ((u64) (sw_if_index) << 32) | (u64) sub_id;
1050 
1051  p = hash_get_mem (im->sw_if_index_by_sup_and_sub, &sup_and_sub_key);
1052  if (p)
1053  {
1054  if (CLIB_DEBUG > 0)
1055  clib_warning ("sup sw_if_index %d, sub id %d already exists\n",
1056  sw_if_index, sub_id);
1057  rv = VNET_API_ERROR_SUBIF_ALREADY_EXISTS;
1058  goto out;
1059  }
1060 
1061  memset (&template, 0, sizeof (template));
1062  template.type = VNET_SW_INTERFACE_TYPE_SUB;
1063  template.sup_sw_if_index = sw_if_index;
1064  template.sub.id = sub_id;
1065  template.sub.eth.flags.no_tags = mp->no_tags;
1066  template.sub.eth.flags.one_tag = mp->one_tag;
1067  template.sub.eth.flags.two_tags = mp->two_tags;
1068  template.sub.eth.flags.dot1ad = mp->dot1ad;
1069  template.sub.eth.flags.exact_match = mp->exact_match;
1070  template.sub.eth.flags.default_sub = mp->default_sub;
1071  template.sub.eth.flags.outer_vlan_id_any = mp->outer_vlan_id_any;
1072  template.sub.eth.flags.inner_vlan_id_any = mp->inner_vlan_id_any;
1073  template.sub.eth.outer_vlan_id = ntohs (mp->outer_vlan_id);
1074  template.sub.eth.inner_vlan_id = ntohs (mp->inner_vlan_id);
1075 
1076  error = vnet_create_sw_interface (vnm, &template, &sw_if_index);
1077  if (error)
1078  {
1079  clib_error_report (error);
1080  rv = VNET_API_ERROR_SUBIF_CREATE_FAILED;
1081  goto out;
1082  }
1083 
1084  u64 *kp = clib_mem_alloc (sizeof (*kp));
1085  *kp = sup_and_sub_key;
1086 
1087  hash_set (hi->sub_interface_sw_if_index_by_id, sub_id, sw_if_index);
1088  hash_set_mem (im->sw_if_index_by_sup_and_sub, kp, sw_if_index);
1089 
1091 
1092 out:
1093 
1094  /* *INDENT-OFF* */
1095  REPLY_MACRO2(VL_API_CREATE_SUBIF_REPLY,
1096  ({
1097  rmp->sw_if_index = ntohl(sw_if_index);
1098  }));
1099  /* *INDENT-ON* */
1100 }
1101 
1102 static void
1104 {
1105  vl_api_delete_subif_reply_t *rmp;
1106  int rv;
1107 
1108  rv = vnet_delete_sub_interface (ntohl (mp->sw_if_index));
1109 
1110  REPLY_MACRO (VL_API_DELETE_SUBIF_REPLY);
1111 }
1112 
1113 static void
1115  mp)
1116 {
1117  vl_api_interface_name_renumber_reply_t *rmp;
1118  int rv = 0;
1119 
1120  VALIDATE_SW_IF_INDEX (mp);
1121 
1123  (ntohl (mp->sw_if_index), ntohl (mp->new_show_dev_instance));
1124 
1126 
1127  REPLY_MACRO (VL_API_INTERFACE_NAME_RENUMBER_REPLY);
1128 }
1129 
1130 static void
1132 {
1134  u32 sw_if_index;
1135  int rv;
1136 
1137  rv = vnet_create_loopback_interface (&sw_if_index, mp->mac_address, 0, 0);
1138 
1139  /* *INDENT-OFF* */
1140  REPLY_MACRO2(VL_API_CREATE_LOOPBACK_REPLY,
1141  ({
1142  rmp->sw_if_index = ntohl (sw_if_index);
1143  }));
1144  /* *INDENT-ON* */
1145 }
1146 
1149 {
1151  u32 sw_if_index;
1152  u8 is_specified = mp->is_specified;
1153  u32 user_instance = ntohl (mp->user_instance);
1154  int rv;
1155 
1156  rv = vnet_create_loopback_interface (&sw_if_index, mp->mac_address,
1157  is_specified, user_instance);
1158 
1159  /* *INDENT-OFF* */
1160  REPLY_MACRO2(VL_API_CREATE_LOOPBACK_INSTANCE_REPLY,
1161  ({
1162  rmp->sw_if_index = ntohl (sw_if_index);
1163  }));
1164  /* *INDENT-ON* */
1165 }
1166 
1167 static void
1169 {
1170  vl_api_delete_loopback_reply_t *rmp;
1171  u32 sw_if_index;
1172  int rv;
1173 
1174  sw_if_index = ntohl (mp->sw_if_index);
1175  rv = vnet_delete_loopback_interface (sw_if_index);
1176 
1177  REPLY_MACRO (VL_API_DELETE_LOOPBACK_REPLY);
1178 }
1179 
1180 /*
1181  * vpe_api_hookup
1182  * Add vpe's API message handlers to the table.
1183  * vlib has alread mapped shared memory and
1184  * added the client registration handlers.
1185  * See .../vlib-api/vlibmemory/memclnt_vlib.c:memclnt_process()
1186  */
1187 #define vl_msg_name_crc_list
1188 #include <vnet/interface.api.h>
1189 #undef vl_msg_name_crc_list
1190 
1191 static void
1193 {
1194 #define _(id,n,crc) vl_msg_api_add_msg_name_crc (am, #n "_" #crc, id);
1195  foreach_vl_msg_name_crc_interface;
1196 #undef _
1197 }
1198 
1199 pub_sub_handler (interface_events, INTERFACE_EVENTS);
1200 
1201 static clib_error_t *
1203 {
1204  api_main_t *am = &api_main;
1205 
1206 #define _(N,n) \
1207  vl_msg_api_set_handlers(VL_API_##N, #n, \
1208  vl_api_##n##_t_handler, \
1209  vl_noop_handler, \
1210  vl_api_##n##_t_endian, \
1211  vl_api_##n##_t_print, \
1212  sizeof(vl_api_##n##_t), 1);
1214 #undef _
1215 
1216  /*
1217  * Set up the (msg_name, crc, message-id) table
1218  */
1220 
1221  return 0;
1222 }
1223 
1225 
1226 /*
1227  * fd.io coding-style-patch-verification: ON
1228  *
1229  * Local Variables:
1230  * eval: (c-set-style "gnu")
1231  * End:
1232  */
static void vl_api_delete_subif_t_handler(vl_api_delete_subif_t *mp)
#define vec_validate(V, I)
Make sure vector is long enough for given index (no header, unspecified alignment) ...
Definition: vec.h:432
#define foreach_ip_interface_address(lm, a, sw_if_index, loop, body)
Definition: lookup.h:179
#define VNET_SW_INTERFACE_FLAG_UNNUMBERED
Definition: interface.h:583
static int event_data_cmp(void *a1, void *a2)
vmrglw vmrglh hi
u32 mfib_table_find_or_create_and_lock(fib_protocol_t proto, u32 table_id, mfib_source_t src)
Get the index of the FIB for a Table-ID.
Definition: mfib_table.c:467
#define hash_set(h, key, value)
Definition: hash.h:254
sll srl srl sll sra u16x4 i
Definition: vector_sse2.h:337
ip4_table_bind_function_t * function
Definition: ip4.h:82
vnet_main_t * vnet_main
#define CLIB_UNUSED(x)
Definition: clib.h:79
static uword * vlib_process_wait_for_event(vlib_main_t *vm)
Definition: node_funcs.h:619
u32 * mfib_index_by_sw_if_index
Table index indexed by software interface.
Definition: ip6.h:176
vnet_main_t * vnet_get_main(void)
Definition: misc.c:47
static void vl_api_interface_name_renumber_t_handler(vl_api_interface_name_renumber_t *mp)
static vnet_hw_interface_t * vnet_get_sup_hw_interface(vnet_main_t *vnm, u32 sw_if_index)
void stats_dsunlock(void)
VNET_HW_INTERFACE_LINK_UP_DOWN_FUNCTION(link_up_down_function)
ethernet_main_t * ethernet_get_main(vlib_main_t *vm)
Definition: init.c:116
Set flags on the interface.
Definition: interface.api:10
vnet_interface_main_t interface_main
Definition: vnet.h:56
static void vl_api_sw_interface_add_del_address_t_handler(vl_api_sw_interface_add_del_address_t *mp)
#define REPLY_MACRO2(t, body)
u32 fib_table_get_index_for_sw_if_index(fib_protocol_t proto, u32 sw_if_index)
Get the index of the FIB bound to the interface.
Definition: fib_table.c:931
u8 src_address[6]
Definition: packet.h:54
vnet_main_t ** vnet_mains
Definition: misc.c:44
static vnet_hw_interface_t * vnet_get_hw_interface(vnet_main_t *vnm, u32 hw_if_index)
From the CLI.
Definition: fib_entry.h:74
add_epi add_epi sub
Definition: vector_sse2.h:283
static void vl_api_delete_loopback_t_handler(vl_api_delete_loopback_t *mp)
#define vec_add1(V, E)
Add 1 element to end of vector (unspecified alignment).
Definition: vec.h:518
int vnet_interface_name_renumber(u32 sw_if_index, u32 new_show_dev_instance)
Definition: interface.c:1286
static void vnet_clear_sw_interface_tag(vnet_main_t *vnm, u32 sw_if_index)
VLIB_API_INIT_FUNCTION(interface_api_hookup)
#define hash_set_mem(h, key, value)
Definition: hash.h:274
ip_lookup_main_t lookup_main
Definition: ip4.h:97
static vnet_sw_interface_t * vnet_get_sw_interface(vnet_main_t *vnm, u32 sw_if_index)
uword * sub_interface_sw_if_index_by_id
Definition: interface.h:475
vlib_main_t * vlib_main
u32 * fib_index_by_sw_if_index
Table index indexed by software interface.
Definition: ip4.h:111
u8 * format(u8 *s, const char *fmt,...)
Definition: format.c:419
static void vl_api_sw_interface_set_unnumbered_t_handler(vl_api_sw_interface_set_unnumbered_t *mp)
#define VNET_HW_INTERFACE_FLAG_LINK_UP
Definition: interface.h:394
vpe_api_main_t vpe_api_main
Definition: interface_api.c:49
static void vl_api_sw_interface_dump_t_handler(vl_api_sw_interface_dump_t *mp)
#define VNET_HW_INTERFACE_FLAG_DUPLEX_MASK
Definition: interface.h:399
static clib_error_t * interface_api_hookup(vlib_main_t *vm)
enum fib_protocol_t_ fib_protocol_t
Protocol Type.
#define vec_reset_length(v)
Reset vector length to zero NULL-pointer tolerant.
static uword link_state_process(vlib_main_t *vm, vlib_node_runtime_t *rt, vlib_frame_t *f)
int ip_table_bind(fib_protocol_t fproto, u32 sw_if_index, u32 table_id, u8 is_api)
static void send_sw_interface_get_table_reply(unix_shared_memory_queue_t *q, u32 context, int retval, u32 vrf_id)
#define VNET_HW_INTERFACE_FLAG_SPEED_MASK
Definition: interface.h:411
enum mfib_source_t_ mfib_source_t
Possible [control plane] sources of MFIB entries.
ethernet_main_t ethernet_main
Definition: init.c:45
u32 * mfib_index_by_sw_if_index
Table index indexed by software interface.
Definition: ip4.h:114
Set an interface&#39;s rx-mode.
Definition: interface.api:404
void vlib_clear_combined_counters(vlib_combined_counter_main_t *cm)
Clear a collection of combined counters.
Definition: counter.c:60
Clear interface statistics.
Definition: interface.api:357
#define pool_foreach(VAR, POOL, BODY)
Iterate through pool.
Definition: pool.h:438
vlib_combined_counter_main_t * combined_sw_if_counters
Definition: interface.h:672
u8 dst_address[6]
Definition: packet.h:53
Reply for the vlan subinterface create request.
Definition: interface.api:469
static vnet_sw_interface_t * vnet_get_sup_sw_interface(vnet_main_t *vnm, u32 sw_if_index)
Get VRF id assigned to interface.
Definition: interface.api:207
unsigned long u64
Definition: types.h:89
A collection of simple counters.
Definition: counter.h:58
void * vl_msg_api_alloc(int nbytes)
u32 max_supported_packet_bytes
Definition: interface.h:458
clib_error_t * ip4_add_del_interface_address(vlib_main_t *vm, u32 sw_if_index, ip4_address_t *address, u32 address_length, u32 is_del)
Definition: ip4_forward.c:988
vnet_api_error_t api_errno
Definition: vnet.h:76
static clib_error_t * link_up_down_function(vnet_main_t *vm, u32 hw_if_index, u32 flags)
#define VNET_HW_INTERFACE_FLAG_DUPLEX_SHIFT
Definition: interface.h:396
#define pool_elt_at_index(p, i)
Returns pointer to element at given index.
Definition: pool.h:459
static void vlib_zero_combined_counter(vlib_combined_counter_main_t *cm, u32 index)
Clear a combined counter Clears the set of per-thread counters.
Definition: counter.h:276
vnet_sub_interface_t sub
Definition: interface.h:612
void ip4_sw_interface_enable_disable(u32 sw_if_index, u32 is_enable)
Definition: ip4_forward.c:866
static void vl_api_sw_interface_get_table_t_handler(vl_api_sw_interface_get_table_t *mp)
static void vlib_process_signal_event(vlib_main_t *vm, uword node_index, uword type_opaque, uword data)
Definition: node_funcs.h:950
enum fib_source_t_ fib_source_t
The different sources that can create a route.
void mfib_table_unlock(u32 fib_index, fib_protocol_t proto, mfib_source_t source)
Take a reference counting lock on the table.
Definition: mfib_table.c:558
#define VNET_HW_INTERFACE_FLAG_SPEED_SHIFT
Definition: interface.h:404
Set interface MTU.
Definition: interface.api:25
uword * sw_if_index_by_sup_and_sub
Definition: interface.h:666
struct vnet_sub_interface_t::@180::@181::@183 flags
static void vl_api_sw_interface_set_mac_address_t_handler(vl_api_sw_interface_set_mac_address_t *mp)
ip6_table_bind_callback_t * table_bind_callbacks
Functions to call when interface to table biding changes.
Definition: ip6.h:197
Reply to get_sw_interface_vrf.
Definition: interface.api:219
#define REPLY_MACRO(t)
clib_error_t * set_hw_interface_change_rx_mode(vnet_main_t *vnm, u32 hw_if_index, u8 queue_id_valid, u32 queue_id, vnet_hw_interface_rx_mode mode)
static void vl_api_create_loopback_t_handler(vl_api_create_loopback_t *mp)
Create loopback interface instance response.
Definition: interface.api:532
vlib_simple_counter_main_t * sw_if_counters
Definition: interface.h:671
void mfib_table_lock(u32 fib_index, fib_protocol_t proto, mfib_source_t source)
Release a reference counting lock on the table.
Definition: mfib_table.c:587
void ip_del_all_interface_addresses(vlib_main_t *vm, u32 sw_if_index)
Definition: ip46_cli.c:80
Set or delete one or all ip addresses on a specified interface.
Definition: interface.api:174
void fib_table_unlock(u32 fib_index, fib_protocol_t proto, fib_source_t source)
Take a reference counting lock on the table.
Definition: fib_table.c:1180
vnet_hw_interface_class_t ethernet_hw_interface_class
API main structure, used by both vpp and binary API clients.
Definition: api_common.h:198
static void setup_message_id_table(api_main_t *am)
int vnet_create_loopback_interface(u32 *sw_if_indexp, u8 *mac_address, u8 is_specified, u32 user_instance)
Definition: interface.c:558
static uword vlib_process_get_events_with_type(vlib_main_t *vm, uword **data_vector, uword with_type_opaque)
Definition: node_funcs.h:597
An API client registration, only in vpp/vlib.
Definition: api_common.h:44
#define VNET_HW_INTERFACE_BOND_INFO_SLAVE
Definition: interface.h:486
#define BAD_SW_IF_INDEX_LABEL
struct vnet_sub_interface_t::@180 eth
api_main_t api_main
Definition: api_shared.c:35
static void vl_api_sw_interface_set_flags_t_handler(vl_api_sw_interface_set_flags_t *mp)
Definition: interface_api.c:73
u32 ft_table_id
Table ID (hash key) for this FIB.
Definition: fib_table.h:50
void stats_dslock_with_hint(int hint, int tag)
int vnet_delete_sub_interface(u32 sw_if_index)
Definition: interface.c:737
#define vec_free(V)
Free vector&#39;s memory (no header).
Definition: vec.h:336
int vnet_delete_loopback_interface(u32 sw_if_index)
Definition: interface.c:710
static clib_error_t * admin_up_down_function(vnet_main_t *vm, u32 hw_if_index, u32 flags)
#define API_ADMIN_UP_DOWN_EVENT
#define clib_warning(format, args...)
Definition: error.h:59
clib_error_t * vnet_hw_interface_change_mac_address(vnet_main_t *vnm, u32 hw_if_index, u8 *mac_address)
Definition: interface.c:1394
#define clib_memcpy(a, b, c)
Definition: string.h:75
unix_shared_memory_queue_t * vl_api_client_index_to_input_queue(u32 index)
#define ETHERNET_INTERFACE_FLAG_MTU
Definition: ethernet.h:124
static void vl_api_create_loopback_instance_t_handler(vl_api_create_loopback_instance_t *mp)
Delete sub interface request.
Definition: interface.api:481
#define ARRAY_LEN(x)
Definition: clib.h:59
static void send_sw_interface_details(vpe_api_main_t *am, vl_api_registration_t *rp, vnet_sw_interface_t *swif, u8 *interface_name, u32 context)
#define foreach_vpe_api_msg
Definition: interface_api.c:51
Delete loopback interface request.
Definition: interface.api:544
VNET_SW_INTERFACE_ADMIN_UP_DOWN_FUNCTION(admin_up_down_function)
void fib_table_lock(u32 fib_index, fib_protocol_t proto, fib_source_t source)
Release a reference counting lock on the table.
Definition: fib_table.c:1209
u32 * if_address_pool_index_by_sw_if_index
Head of doubly linked list of interface addresses for each software interface.
Definition: lookup.h:129
foreach_registration_hash u8 link_state_process_up
#define VNET_SW_INTERFACE_FLAG_ADMIN_UP
Definition: interface.h:576
void vl_msg_api_send_shmem(unix_shared_memory_queue_t *q, u8 *elem)
#define ASSERT(truth)
unsigned int u32
Definition: types.h:88
ip6_main_t ip6_main
Definition: ip6_forward.c:3009
ip_lookup_main_t lookup_main
Definition: ip6.h:158
static void vnet_set_sw_interface_tag(vnet_main_t *vnm, u8 *tag, u32 sw_if_index)
u32 fib_table_find_or_create_and_lock(fib_protocol_t proto, u32 table_id, fib_source_t src)
Get the index of the FIB for a Table-ID.
Definition: fib_table.c:1087
static void vl_api_sw_interface_tag_add_del_t_handler(vl_api_sw_interface_tag_add_del_t *mp)
#define API_LINK_STATE_EVENT
#define clib_error_report(e)
Definition: error.h:113
static void vlib_zero_simple_counter(vlib_simple_counter_main_t *cm, u32 index)
Clear a simple counter Clears the set of per-thread u16 counters, and the u64 counter.
Definition: counter.h:123
static u8 * vnet_get_sw_interface_tag(vnet_main_t *vnm, u32 sw_if_index)
From the control plane API.
Definition: fib_entry.h:70
static void vl_api_sw_interface_clear_stats_t_handler(vl_api_sw_interface_clear_stats_t *mp)
static void * clib_mem_alloc(uword size)
Definition: mem.h:112
static vlib_main_t * vlib_get_main(void)
Definition: global_funcs.h:23
Interface Event generated by want_interface_events.
Definition: interface.api:41
static void vl_api_sw_interface_set_mtu_t_handler(vl_api_sw_interface_set_mtu_t *mp)
Definition: interface_api.c:97
u64 uword
Definition: types.h:112
ip4_table_bind_callback_t * table_bind_callbacks
Functions to call when interface to table biding changes.
Definition: ip4.h:132
static uword vnet_sw_interface_is_api_valid(vnet_main_t *vnm, u32 sw_if_index)
static void vl_api_sw_interface_set_rx_mode_t_handler(vl_api_sw_interface_set_rx_mode_t *mp)
static void vl_api_create_subif_t_handler(vl_api_create_subif_t *mp)
unsigned short u16
Definition: types.h:57
Create loopback interface instance request.
Definition: interface.api:518
i64 word
Definition: types.h:111
ethernet_interface_t * ethernet_get_interface(ethernet_main_t *em, u32 hw_if_index)
Definition: interface.c:700
#define vec_len(v)
Number of elements in vector (rvalue-only, NULL tolerant)
unsigned char u8
Definition: types.h:56
#define vec_sort_with_function(vec, f)
Sort a vector using the supplied element comparison function.
Definition: vec.h:956
vnet_sw_interface_t * sw_interfaces
Definition: interface.h:663
Create loopback interface request.
Definition: interface.api:492
ip6_table_bind_function_t * function
Definition: ip6.h:112
Set unnumbered interface add / del request.
Definition: interface.api:343
fib_table_t * fib_table_get(fib_node_index_t index, fib_protocol_t proto)
Get a pointer to a FIB table.
Definition: fib_table.c:27
A collection of combined counters.
Definition: counter.h:180
Create a new subinterface with the given vlan id.
Definition: interface.api:456
Create loopback interface response.
Definition: interface.api:504
#define hash_get_mem(h, key)
Definition: hash.h:268
u32 l2vtr_get(vlib_main_t *vlib_main, vnet_main_t *vnet_main, u32 sw_if_index, u32 *vtr_op, u32 *push_dot1q, u32 *vtr_tag1, u32 *vtr_tag2)
Get vtag tag rewrite on the given interface.
Definition: l2_vtr.c:347
Set an interface&#39;s MAC address.
Definition: interface.api:386
void vlib_clear_simple_counters(vlib_simple_counter_main_t *cm)
Clear a collection of simple counters.
Definition: counter.c:43
#define VLIB_REGISTER_NODE(x,...)
Definition: node.h:143
vnet_sw_interface_type_t type
Definition: interface.h:571
ip4_main_t ip4_main
Global ip4 main structure.
Definition: ip4_forward.c:1181
pub_sub_handler(interface_events, INTERFACE_EVENTS)
static void send_sw_interface_event(vpe_api_main_t *am, vpe_client_registration_t *reg, unix_shared_memory_queue_t *q, vnet_sw_interface_t *swif)
#define vec_foreach(var, vec)
Vector iterator.
vl_api_registration_t * vl_api_client_index_to_registration(u32 index)
clib_error_t * vnet_sw_interface_set_flags(vnet_main_t *vnm, u32 sw_if_index, u32 flags)
Definition: interface.c:546
static void vl_api_create_vlan_subif_t_handler(vl_api_create_vlan_subif_t *mp)
clib_error_t * ip6_add_del_interface_address(vlib_main_t *vm, u32 sw_if_index, ip6_address_t *address, u32 address_length, u32 is_del)
Definition: ip6_forward.c:467
clib_error_t * vnet_create_sw_interface(vnet_main_t *vnm, vnet_sw_interface_t *template, u32 *sw_if_index)
Definition: interface.c:598
Interface details structure (fix this)
Definition: interface.api:94
static void vl_api_sw_interface_set_table_t_handler(vl_api_sw_interface_set_table_t *mp)
u32 flags
Definition: vhost-user.h:77
Set / clear software interface tag.
Definition: interface.api:371
ethernet_interface_t * interfaces
Definition: ethernet.h:250
Associate the specified interface with a fib table.
Definition: interface.api:193
u32 * fib_index_by_sw_if_index
Definition: ip6.h:173
void vl_msg_api_send(vl_api_registration_t *rp, u8 *elem)
Definition: memory_vlib.c:102
void ip6_sw_interface_enable_disable(u32 sw_if_index, u32 is_enable)
Definition: ip6_forward.c:416
u32 l2pbb_get(vlib_main_t *vlib_main, vnet_main_t *vnet_main, u32 sw_if_index, u32 *vtr_op, u16 *outer_tag, ethernet_header_t *eth_hdr, u16 *b_vlanid, u32 *i_sid)
Get pbb tag rewrite on the given interface.
Definition: l2_vtr.c:686
#define VALIDATE_SW_IF_INDEX(mp)
A protocol Independent FIB table.
Definition: fib_table.h:35
struct _unix_shared_memory_queue unix_shared_memory_queue_t
u32 ethernet_set_flags(vnet_main_t *vnm, u32 hw_if_index, u32 flags)
Definition: interface.c:366