test_client.c revision 58989a37
1/*
2 *------------------------------------------------------------------
3 * api.c - message handler registration
4 *
5 * Copyright (c) 2010 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 <stdio.h>
21#include <stdlib.h>
22#include <sys/types.h>
23#include <sys/mman.h>
24#include <sys/stat.h>
25#include <netinet/in.h>
26#include <signal.h>
27#include <pthread.h>
28#include <unistd.h>
29#include <time.h>
30#include <fcntl.h>
31#include <string.h>
32#include <vppinfra/clib.h>
33#include <vppinfra/vec.h>
34#include <vppinfra/hash.h>
35#include <vppinfra/bitmap.h>
36#include <vppinfra/fifo.h>
37#include <vppinfra/time.h>
38#include <vppinfra/mheap.h>
39#include <vppinfra/heap.h>
40#include <vppinfra/pool.h>
41#include <vppinfra/format.h>
42#include <vppinfra/error.h>
43
44#include <vnet/vnet.h>
45#include <vlib/vlib.h>
46#include <vlib/unix/unix.h>
47#include <vlibapi/api.h>
48#include <vlibmemory/api.h>
49
50#include <vpp/api/vpe_msg_enum.h>
51
52#include <vnet/ip/ip.h>
53#include <vnet/interface.h>
54
55#define f64_endian(a)
56#define f64_print(a,b)
57
58#define vl_typedefs		/* define message structures */
59#include <vpp/api/vpe_all_api_h.h>
60#undef vl_typedefs
61
62#define vl_endianfun		/* define message structures */
63#include <vpp/api/vpe_all_api_h.h>
64#undef vl_endianfun
65
66/* instantiate all the print functions we know about */
67#define vl_print(handle, ...)
68#define vl_printfun
69#include <vpp/api/vpe_all_api_h.h>
70#undef vl_printfun
71
72vl_shmem_hdr_t *shmem_hdr;
73
74typedef struct
75{
76  int link_events_on;
77  int stats_on;
78  int oam_events_on;
79
80  /* convenience */
81  svm_queue_t *vl_input_queue;
82  u32 my_client_index;
83} test_main_t;
84
85test_main_t test_main;
86
87/*
88 * Satisfy external references when -lvlib is not available.
89 */
90vlib_main_t vlib_global_main;
91vlib_main_t **vlib_mains;
92
93void
94vlib_cli_output (struct vlib_main_t *vm, char *fmt, ...)
95{
96  clib_warning ("vlib_cli_output called...");
97}
98
99u8 *
100format_ethernet_address (u8 * s, va_list * args)
101{
102  u8 *a = va_arg (*args, u8 *);
103
104  return format (s, "%02x:%02x:%02x:%02x:%02x:%02x",
105		 a[0], a[1], a[2], a[3], a[4], a[5]);
106}
107
108static void
109vl_api_sw_interface_details_t_handler (vl_api_sw_interface_details_t * mp)
110{
111  char *duplex, *speed;
112
113  switch (mp->link_duplex << VNET_HW_INTERFACE_FLAG_DUPLEX_SHIFT)
114    {
115    case VNET_HW_INTERFACE_FLAG_HALF_DUPLEX:
116      duplex = "half";
117      break;
118    case VNET_HW_INTERFACE_FLAG_FULL_DUPLEX:
119      duplex = "full";
120      break;
121    default:
122      duplex = "bogus";
123      break;
124    }
125  switch (mp->link_speed << VNET_HW_INTERFACE_FLAG_SPEED_SHIFT)
126    {
127    case VNET_HW_INTERFACE_FLAG_SPEED_10M:
128      speed = "10Mbps";
129      break;
130    case VNET_HW_INTERFACE_FLAG_SPEED_100M:
131      speed = "100Mbps";
132      break;
133    case VNET_HW_INTERFACE_FLAG_SPEED_1G:
134      speed = "1Gbps";
135      break;
136    case VNET_HW_INTERFACE_FLAG_SPEED_2_5G:
137      speed = "2.5Gbps";
138      break;
139    case VNET_HW_INTERFACE_FLAG_SPEED_5G:
140      speed = "5Gbps";
141      break;
142    case VNET_HW_INTERFACE_FLAG_SPEED_10G:
143      speed = "10Gbps";
144      break;
145    case VNET_HW_INTERFACE_FLAG_SPEED_20G:
146      speed = "20Gbps";
147      break;
148    case VNET_HW_INTERFACE_FLAG_SPEED_25G:
149      speed = "25Gbps";
150      break;
151    case VNET_HW_INTERFACE_FLAG_SPEED_40G:
152      speed = "40Gbps";
153      break;
154    case VNET_HW_INTERFACE_FLAG_SPEED_50G:
155      speed = "50Gbps";
156      break;
157    case VNET_HW_INTERFACE_FLAG_SPEED_56G:
158      speed = "56Gbps";
159      break;
160    case VNET_HW_INTERFACE_FLAG_SPEED_100G:
161      speed = "100Gbps";
162      break;
163    default:
164      speed = "bogus";
165      break;
166    }
167  fformat (stdout,
168	   "details: %s device_type %s sw_if_index %d sup_sw_if_index %d "
169	   "link_duplex %s link_speed %s", mp->interface_name,
170	   mp->interface_dev_type, ntohl (mp->sw_if_index),
171	   ntohl (mp->sup_sw_if_index), duplex, speed);
172
173  if (mp->l2_address_length)
174    fformat (stdout, "  l2 address: %U\n",
175	     format_ethernet_address, mp->l2_address);
176  else
177    fformat (stdout, "\n");
178}
179
180static void
181vl_api_sw_interface_set_flags_t_handler (vl_api_sw_interface_set_flags_t * mp)
182{
183  fformat (stdout, "set flags: sw_if_index %d, admin %s\n",
184	   ntohl (mp->sw_if_index), mp->admin_up_down ? "up" : "down");
185}
186
187static void
188  vl_api_sw_interface_set_flags_reply_t_handler
189  (vl_api_sw_interface_set_flags_reply_t * mp)
190{
191  fformat (stdout, "set flags reply: reply %d\n", ntohl (mp->retval));
192}
193
194static void
195  vl_api_want_interface_events_reply_t_handler
196  (vl_api_want_interface_events_reply_t * mp)
197{
198}
199
200static void
201vl_api_want_stats_reply_t_handler (vl_api_want_stats_reply_t * mp)
202{
203  fformat (stdout, "want stats reply %d\n", ntohl (mp->retval));
204}
205
206static void
207vl_api_want_oam_events_reply_t_handler (vl_api_want_oam_events_reply_t * mp)
208{
209  fformat (stdout, "want oam reply %d\n", ntohl (mp->retval));
210}
211
212static void
213vl_api_ip_add_del_route_reply_t_handler (vl_api_ip_add_del_route_reply_t * mp)
214{
215  fformat (stdout, "add_route reply %d\n", ntohl (mp->retval));
216}
217
218static void
219  vl_api_sw_interface_add_del_address_reply_t_handler
220  (vl_api_sw_interface_add_del_address_reply_t * mp)
221{
222  fformat (stdout, "add_del_address reply %d\n", ntohl (mp->retval));
223}
224
225static void
226  vl_api_sw_interface_set_table_reply_t_handler
227  (vl_api_sw_interface_set_table_reply_t * mp)
228{
229  fformat (stdout, "set_table reply %d\n", ntohl (mp->retval));
230}
231
232static void
233vl_api_tap_connect_reply_t_handler (vl_api_tap_connect_reply_t * mp)
234{
235  fformat (stdout, "tap connect reply %d, sw_if_index %d\n",
236	   ntohl (mp->retval), ntohl (mp->sw_if_index));
237}
238
239static void
240vl_api_create_vlan_subif_reply_t_handler (vl_api_create_vlan_subif_reply_t *
241					  mp)
242{
243  fformat (stdout, "create vlan subif reply %d, sw_if_index %d\n",
244	   ntohl (mp->retval), ntohl (mp->sw_if_index));
245}
246
247static void vl_api_proxy_arp_add_del_reply_t_handler
248  (vl_api_proxy_arp_add_del_reply_t * mp)
249{
250  fformat (stdout, "add del proxy arp reply %d\n", ntohl (mp->retval));
251}
252
253static void vl_api_proxy_arp_intfc_enable_disable_reply_t_handler
254  (vl_api_proxy_arp_intfc_enable_disable_reply_t * mp)
255{
256  fformat (stdout, "proxy arp intfc ena/dis reply %d\n", ntohl (mp->retval));
257}
258
259static void vl_api_ip_neighbor_add_del_reply_t_handler
260  (vl_api_ip_neighbor_add_del_reply_t * mp)
261{
262  fformat (stdout, "ip neighbor add del reply %d\n", ntohl (mp->retval));
263}
264
265#if 0
266static void
267vl_api_vnet_interface_counters_t_handler (vl_api_vnet_interface_counters_t *
268					  mp)
269{
270  char *counter_name;
271  u32 count, sw_if_index;
272  int i;
273
274  count = ntohl (mp->count);
275  sw_if_index = ntohl (mp->first_sw_if_index);
276  if (mp->is_combined == 0)
277    {
278      u64 *vp, v;
279      vp = (u64 *) mp->data;
280
281      switch (mp->vnet_counter_type)
282	{
283	case VNET_INTERFACE_COUNTER_DROP:
284	  counter_name = "drop";
285	  break;
286	case VNET_INTERFACE_COUNTER_PUNT:
287	  counter_name = "punt";
288	  break;
289	case VNET_INTERFACE_COUNTER_IP4:
290	  counter_name = "ip4";
291	  break;
292	case VNET_INTERFACE_COUNTER_IP6:
293	  counter_name = "ip6";
294	  break;
295	case VNET_INTERFACE_COUNTER_RX_NO_BUF:
296	  counter_name = "rx-no-buf";
297	  break;
298	case VNET_INTERFACE_COUNTER_RX_MISS:
299	  counter_name = "rx-miss";
300	  break;
301	case VNET_INTERFACE_COUNTER_RX_ERROR:
302	  counter_name = "rx-error";
303	  break;
304	case VNET_INTERFACE_COUNTER_TX_ERROR:
305	  counter_name = "tx-error (fifo-full)";
306	  break;
307	default:
308	  counter_name = "bogus";
309	  break;
310	}
311      for (i = 0; i < count; i++)
312	{
313	  v = clib_mem_unaligned (vp, u64);
314	  v = clib_net_to_host_u64 (v);
315	  vp++;
316	  fformat (stdout, "%d.%s %lld\n", sw_if_index, counter_name, v);
317	  sw_if_index++;
318	}
319    }
320  else
321    {
322      vlib_counter_t *vp;
323      u64 packets, bytes;
324      vp = (vlib_counter_t *) mp->data;
325
326      switch (mp->vnet_counter_type)
327	{
328	case VNET_INTERFACE_COUNTER_RX:
329	  counter_name = "rx";
330	  break;
331	case VNET_INTERFACE_COUNTER_TX:
332	  counter_name = "tx";
333	  break;
334	default:
335	  counter_name = "bogus";
336	  break;
337	}
338      for (i = 0; i < count; i++)
339	{
340	  packets = clib_mem_unaligned (&vp->packets, u64);
341	  packets = clib_net_to_host_u64 (packets);
342	  bytes = clib_mem_unaligned (&vp->bytes, u64);
343	  bytes = clib_net_to_host_u64 (bytes);
344	  vp++;
345	  fformat (stdout, "%d.%s.packets %lld\n",
346		   sw_if_index, counter_name, packets);
347	  fformat (stdout, "%d.%s.bytes %lld\n",
348		   sw_if_index, counter_name, bytes);
349	  sw_if_index++;
350	}
351    }
352}
353#endif
354
355/* Format an IP4 address. */
356u8 *
357format_ip4_address (u8 * s, va_list * args)
358{
359  u8 *a = va_arg (*args, u8 *);
360  return format (s, "%d.%d.%d.%d", a[0], a[1], a[2], a[3]);
361}
362
363/* Format an IP4 route destination and length. */
364u8 *
365format_ip4_address_and_length (u8 * s, va_list * args)
366{
367  u8 *a = va_arg (*args, u8 *);
368  u8 l = va_arg (*args, u32);
369  return format (s, "%U/%d", format_ip4_address, a, l);
370}
371
372static void
373vl_api_vnet_ip4_fib_counters_t_handler (vl_api_vnet_ip4_fib_counters_t * mp)
374{
375  int i;
376  vl_api_ip4_fib_counter_t *ctrp;
377  u32 count;
378
379  count = ntohl (mp->count);
380
381  fformat (stdout, "fib id %d, count this msg %d\n",
382	   ntohl (mp->vrf_id), count);
383
384  ctrp = mp->c;
385  for (i = 0; i < count; i++)
386    {
387      fformat (stdout, "%U: %lld packets, %lld bytes\n",
388	       format_ip4_address_and_length, &ctrp->address,
389	       (u32) ctrp->address_length,
390	       clib_net_to_host_u64 (ctrp->packets),
391	       clib_net_to_host_u64 (ctrp->bytes));
392      ctrp++;
393    }
394}
395
396/* Format an IP6 address. */
397u8 *
398format_ip6_address (u8 * s, va_list * args)
399{
400  ip6_address_t *a = va_arg (*args, ip6_address_t *);
401  u32 i, i_max_n_zero, max_n_zeros, i_first_zero, n_zeros, last_double_colon;
402
403  i_max_n_zero = ARRAY_LEN (a->as_u16);
404  max_n_zeros = 0;
405  i_first_zero = i_max_n_zero;
406  n_zeros = 0;
407  for (i = 0; i < ARRAY_LEN (a->as_u16); i++)
408    {
409      u32 is_zero = a->as_u16[i] == 0;
410      if (is_zero && i_first_zero >= ARRAY_LEN (a->as_u16))
411	{
412	  i_first_zero = i;
413	  n_zeros = 0;
414	}
415      n_zeros += is_zero;
416      if ((!is_zero && n_zeros > max_n_zeros)
417	  || (i + 1 >= ARRAY_LEN (a->as_u16) && n_zeros > max_n_zeros))
418	{
419	  i_max_n_zero = i_first_zero;
420	  max_n_zeros = n_zeros;
421	  i_first_zero = ARRAY_LEN (a->as_u16);
422	  n_zeros = 0;
423	}
424    }
425
426  last_double_colon = 0;
427  for (i = 0; i < ARRAY_LEN (a->as_u16); i++)
428    {
429      if (i == i_max_n_zero && max_n_zeros > 1)
430	{
431	  s = format (s, "::");
432	  i += max_n_zeros - 1;
433	  last_double_colon = 1;
434	}
435      else
436	{
437	  s = format (s, "%s%x",
438		      (last_double_colon || i == 0) ? "" : ":",
439		      clib_net_to_host_u16 (a->as_u16[i]));
440	  last_double_colon = 0;
441	}
442    }
443
444  return s;
445}
446
447/* Format an IP6 route destination and length. */
448u8 *
449format_ip6_address_and_length (u8 * s, va_list * args)
450{
451  ip6_address_t *a = va_arg (*args, ip6_address_t *);
452  u8 l = va_arg (*args, u32);
453  return format (s, "%U/%d", format_ip6_address, a, l);
454}
455
456static void
457vl_api_vnet_ip6_fib_counters_t_handler (vl_api_vnet_ip6_fib_counters_t * mp)
458{
459  int i;
460  vl_api_ip6_fib_counter_t *ctrp;
461  u32 count;
462
463  count = ntohl (mp->count);
464
465  fformat (stdout, "fib id %d, count this msg %d\n",
466	   ntohl (mp->vrf_id), count);
467
468  ctrp = mp->c;
469  for (i = 0; i < count; i++)
470    {
471      fformat (stdout, "%U: %lld packets, %lld bytes\n",
472	       format_ip6_address_and_length, &ctrp->address,
473	       (u32) ctrp->address_length,
474	       clib_net_to_host_u64 (ctrp->packets),
475	       clib_net_to_host_u64 (ctrp->bytes));
476      ctrp++;
477    }
478}
479
480static void
481vl_api_oam_event_t_handler (vl_api_oam_event_t * mp)
482{
483  fformat (stdout, "OAM: %U now %s\n",
484	   format_ip4_address, &mp->dst_address,
485	   mp->state == 1 ? "alive" : "dead");
486}
487
488static void
489vl_api_oam_add_del_reply_t_handler (vl_api_oam_add_del_reply_t * mp)
490{
491  fformat (stdout, "oam add del reply %d\n", ntohl (mp->retval));
492}
493
494static void
495vl_api_reset_fib_reply_t_handler (vl_api_reset_fib_reply_t * mp)
496{
497  fformat (stdout, "fib reset reply %d\n", ntohl (mp->retval));
498}
499
500static void
501vl_api_dhcp_proxy_set_vss_reply_t_handler (vl_api_dhcp_proxy_set_vss_reply_t *
502					   mp)
503{
504  fformat (stdout, "dhcp proxy set vss reply %d\n", ntohl (mp->retval));
505}
506
507static void
508vl_api_dhcp_proxy_config_reply_t_handler (vl_api_dhcp_proxy_config_reply_t *
509					  mp)
510{
511  fformat (stdout, "dhcp proxy config reply %d\n", ntohl (mp->retval));
512}
513
514static void
515vl_api_set_ip_flow_hash_reply_t_handler (vl_api_set_ip_flow_hash_reply_t * mp)
516{
517  fformat (stdout, "set ip flow hash reply %d\n", ntohl (mp->retval));
518}
519
520static void
521  vl_api_sw_interface_ip6nd_ra_config_reply_t_handler
522  (vl_api_sw_interface_ip6nd_ra_config_reply_t * mp)
523{
524  fformat (stdout, "ip6 nd ra-config  reply %d\n", ntohl (mp->retval));
525}
526
527static void
528  vl_api_sw_interface_ip6nd_ra_prefix_reply_t_handler
529  (vl_api_sw_interface_ip6nd_ra_prefix_reply_t * mp)
530{
531  fformat (stdout, "ip6 nd ra-prefix  reply %d\n", ntohl (mp->retval));
532}
533
534static void
535  vl_api_sw_interface_ip6_enable_disable_reply_t_handler
536  (vl_api_sw_interface_ip6_enable_disable_reply_t * mp)
537{
538  fformat (stdout, "ip6 enable/disable reply %d\n", ntohl (mp->retval));
539}
540
541static void
542  vl_api_sw_interface_ip6_set_link_local_address_reply_t_handler
543  (vl_api_sw_interface_ip6_set_link_local_address_reply_t * mp)
544{
545  fformat (stdout, "ip6 set link-local address reply %d\n",
546	   ntohl (mp->retval));
547}
548
549static void vl_api_create_loopback_reply_t_handler
550  (vl_api_create_loopback_reply_t * mp)
551{
552  fformat (stdout, "create loopback status %d, sw_if_index %d\n",
553	   ntohl (mp->retval), ntohl (mp->sw_if_index));
554}
555
556static void vl_api_create_loopback_instance_reply_t_handler
557  (vl_api_create_loopback_instance_reply_t * mp)
558{
559  fformat (stdout, "create loopback status %d, sw_if_index %d\n",
560	   ntohl (mp->retval), ntohl (mp->sw_if_index));
561}
562
563static void vl_api_l2_patch_add_del_reply_t_handler
564  (vl_api_l2_patch_add_del_reply_t * mp)
565{
566  fformat (stdout, "l2 patch reply %d\n", ntohl (mp->retval));
567}
568
569static void vl_api_sw_interface_set_l2_xconnect_reply_t_handler
570  (vl_api_sw_interface_set_l2_xconnect_reply_t * mp)
571{
572  fformat (stdout, "l2_xconnect reply %d\n", ntohl (mp->retval));
573}
574
575static void vl_api_sw_interface_set_l2_bridge_reply_t_handler
576  (vl_api_sw_interface_set_l2_bridge_reply_t * mp)
577{
578  fformat (stdout, "l2_bridge reply %d\n", ntohl (mp->retval));
579}
580
581static void
582noop_handler (void *notused)
583{
584}
585
586#define vl_api_vnet_ip4_fib_counters_t_endian noop_handler
587#define vl_api_vnet_ip4_fib_counters_t_print noop_handler
588#define vl_api_vnet_ip6_fib_counters_t_endian noop_handler
589#define vl_api_vnet_ip6_fib_counters_t_print noop_handler
590
591#define foreach_api_msg                                                 \
592_(SW_INTERFACE_DETAILS, sw_interface_details)                           \
593_(SW_INTERFACE_SET_FLAGS, sw_interface_set_flags)                       \
594_(SW_INTERFACE_SET_FLAGS_REPLY, sw_interface_set_flags_reply)           \
595_(WANT_INTERFACE_EVENTS_REPLY, want_interface_events_reply)             \
596_(WANT_STATS_REPLY, want_stats_reply)                                   \
597_(WANT_OAM_EVENTS_REPLY, want_oam_events_reply)                         \
598_(OAM_EVENT, oam_event)                                                 \
599_(OAM_ADD_DEL_REPLY, oam_add_del_reply)				        \
600_(VNET_IP4_FIB_COUNTERS, vnet_ip4_fib_counters)                         \
601_(VNET_IP6_FIB_COUNTERS, vnet_ip6_fib_counters)                         \
602_(IP_ADD_DEL_ROUTE_REPLY, ip_add_del_route_reply)                       \
603_(SW_INTERFACE_ADD_DEL_ADDRESS_REPLY, sw_interface_add_del_address_reply) \
604_(SW_INTERFACE_SET_TABLE_REPLY, sw_interface_set_table_reply)           \
605_(TAP_CONNECT_REPLY, tap_connect_reply)                                 \
606_(CREATE_VLAN_SUBIF_REPLY, create_vlan_subif_reply)                     \
607_(PROXY_ARP_ADD_DEL_REPLY, proxy_arp_add_del_reply)			\
608_(PROXY_ARP_INTFC_ENABLE_DISABLE_REPLY, proxy_arp_intfc_enable_disable_reply) \
609_(IP_NEIGHBOR_ADD_DEL_REPLY, ip_neighbor_add_del_reply)                 \
610_(RESET_FIB_REPLY, reset_fib_reply)                                     \
611_(DHCP_PROXY_CONFIG_REPLY, dhcp_proxy_config_reply)                     \
612_(DHCP_PROXY_SET_VSS_REPLY, dhcp_proxy_set_vss_reply)                   \
613_(SET_IP_FLOW_HASH_REPLY, set_ip_flow_hash_reply)                       \
614_(SW_INTERFACE_IP6ND_RA_CONFIG_REPLY, sw_interface_ip6nd_ra_config_reply) \
615_(SW_INTERFACE_IP6ND_RA_PREFIX_REPLY, sw_interface_ip6nd_ra_prefix_reply) \
616_(SW_INTERFACE_IP6_ENABLE_DISABLE_REPLY, sw_interface_ip6_enable_disable_reply) \
617_(SW_INTERFACE_IP6_SET_LINK_LOCAL_ADDRESS_REPLY, sw_interface_ip6_set_link_local_address_reply) \
618 _(CREATE_LOOPBACK_REPLY, create_loopback_reply)			\
619 _(CREATE_LOOPBACK_INSTANCE_REPLY, create_loopback_instance_reply)	\
620_(L2_PATCH_ADD_DEL_REPLY, l2_patch_add_del_reply)			\
621_(SW_INTERFACE_SET_L2_XCONNECT_REPLY, sw_interface_set_l2_xconnect_reply) \
622_(SW_INTERFACE_SET_L2_BRIDGE_REPLY, sw_interface_set_l2_bridge_reply)
623
624int
625connect_to_vpe (char *name)
626{
627  int rv = 0;
628
629  rv = vl_client_connect_to_vlib ("/vpe-api", name, 32);
630
631#define _(N,n)                                                  \
632    vl_msg_api_set_handlers(VL_API_##N, #n,                     \
633                           vl_api_##n##_t_handler,              \
634                           noop_handler,                        \
635                           vl_api_##n##_t_endian,               \
636                           vl_api_##n##_t_print,                \
637                           sizeof(vl_api_##n##_t), 1);
638  foreach_api_msg;
639#undef _
640
641  shmem_hdr = api_main.shmem_hdr;
642
643  return rv;
644}
645
646int
647disconnect_from_vpe (void)
648{
649  vl_client_disconnect_from_vlib ();
650  return 0;
651}
652
653void
654link_up_down_enable_disable (test_main_t * tm, int enable)
655{
656  vl_api_want_interface_events_t *mp;
657
658  /* Request admin / link up down messages */
659  mp = vl_msg_api_alloc (sizeof (*mp));
660  clib_memset (mp, 0, sizeof (*mp));
661  mp->_vl_msg_id = ntohs (VL_API_WANT_INTERFACE_EVENTS);
662  mp->client_index = tm->my_client_index;
663  mp->context = 0xdeadbeef;
664  mp->enable_disable = enable;
665  mp->pid = getpid ();
666  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
667  tm->link_events_on = enable;
668}
669
670void
671stats_enable_disable (test_main_t * tm, int enable)
672{
673  vl_api_want_stats_t *mp;
674
675  mp = vl_msg_api_alloc (sizeof (*mp));
676  clib_memset (mp, 0, sizeof (*mp));
677  mp->_vl_msg_id = ntohs (VL_API_WANT_STATS);
678  mp->client_index = tm->my_client_index;
679  mp->context = 0xdeadbeef;
680  mp->enable_disable = enable;
681  mp->pid = getpid ();
682  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
683  tm->stats_on = enable;
684}
685
686void
687oam_events_enable_disable (test_main_t * tm, int enable)
688{
689  vl_api_want_oam_events_t *mp;
690
691  mp = vl_msg_api_alloc (sizeof (*mp));
692  clib_memset (mp, 0, sizeof (*mp));
693  mp->_vl_msg_id = ntohs (VL_API_WANT_OAM_EVENTS);
694  mp->client_index = tm->my_client_index;
695  mp->context = 0xdeadbeef;
696  mp->enable_disable = enable;
697  mp->pid = getpid ();
698  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
699  tm->oam_events_on = enable;
700}
701
702void
703oam_add_del (test_main_t * tm, int is_add)
704{
705  vl_api_oam_add_del_t *mp;
706  ip4_address_t tmp;
707
708  mp = vl_msg_api_alloc (sizeof (*mp));
709  clib_memset (mp, 0, sizeof (*mp));
710  mp->_vl_msg_id = ntohs (VL_API_OAM_ADD_DEL);
711  mp->client_index = tm->my_client_index;
712  mp->context = 0xdeadbeef;
713  mp->is_add = is_add;
714
715  tmp.as_u32 = ntohl (0xc0a80101);	/* 192.168.1.1 */
716  clib_memcpy (mp->src_address, tmp.as_u8, 4);
717
718  tmp.as_u32 = ntohl (0xc0a80103);	/* 192.168.1.3 */
719  clib_memcpy (mp->dst_address, tmp.as_u8, 4);
720
721  mp->vrf_id = 0;
722  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
723}
724
725void
726dump (test_main_t * tm)
727{
728  vl_api_sw_interface_dump_t *mp;
729
730  mp = vl_msg_api_alloc (sizeof (*mp));
731  clib_memset (mp, 0, sizeof (*mp));
732  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_DUMP);
733  mp->client_index = tm->my_client_index;
734  mp->name_filter_valid = 1;
735  strncpy ((char *) mp->name_filter, "eth", sizeof (mp->name_filter) - 1);
736
737  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
738}
739
740void
741add_del_ip4_route (test_main_t * tm, int enable_disable)
742{
743  vl_api_ip_add_del_route_t *mp;
744  u32 tmp;
745
746  mp = vl_msg_api_alloc (sizeof (*mp));
747  clib_memset (mp, 0, sizeof (*mp));
748  mp->_vl_msg_id = ntohs (VL_API_IP_ADD_DEL_ROUTE);
749  mp->client_index = tm->my_client_index;
750  mp->context = 0xdeadbeef;
751  mp->table_id = ntohl (0);
752
753  mp->next_hop_sw_if_index = ntohl (5);
754  mp->is_add = enable_disable;
755  mp->next_hop_weight = 1;
756
757  /* Next hop: 6.0.0.1 */
758  tmp = ntohl (0x06000001);
759  clib_memcpy (mp->next_hop_address, &tmp, sizeof (tmp));
760
761  /* Destination: 10.0.0.1/32 */
762  tmp = ntohl (0x0);
763  clib_memcpy (mp->dst_address, &tmp, sizeof (tmp));
764  mp->dst_address_length = 0;
765
766  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
767}
768
769void
770add_del_ip6_route (test_main_t * tm, int enable_disable)
771{
772  vl_api_ip_add_del_route_t *mp;
773  u64 tmp[2];
774
775  mp = vl_msg_api_alloc (sizeof (*mp));
776  clib_memset (mp, 0, sizeof (*mp));
777  mp->_vl_msg_id = ntohs (VL_API_IP_ADD_DEL_ROUTE);
778  mp->client_index = tm->my_client_index;
779  mp->context = 0xdeadbeef;
780  mp->next_hop_sw_if_index = ntohl (5);
781  mp->is_add = enable_disable;
782  mp->is_ipv6 = 1;
783  mp->next_hop_weight = 1;
784  mp->dst_address_length = 64;
785
786  /* add/del dabe::/64 via db01::11 */
787
788  tmp[0] = clib_host_to_net_u64 (0xdabe000000000000ULL);
789  tmp[1] = clib_host_to_net_u64 (0x0ULL);
790  clib_memcpy (mp->dst_address, &tmp[0], 8);
791  clib_memcpy (&mp->dst_address[8], &tmp[1], 8);
792
793  tmp[0] = clib_host_to_net_u64 (0xdb01000000000000ULL);
794  tmp[1] = clib_host_to_net_u64 (0x11ULL);
795  clib_memcpy (mp->next_hop_address, &tmp[0], 8);
796  clib_memcpy (&mp->next_hop_address[8], &tmp[1], 8);
797
798  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
799}
800
801void
802add_del_interface_address (test_main_t * tm, int enable_disable)
803{
804  vl_api_sw_interface_add_del_address_t *mp;
805  u32 tmp;
806
807  mp = vl_msg_api_alloc (sizeof (*mp));
808  clib_memset (mp, 0, sizeof (*mp));
809  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_ADD_DEL_ADDRESS);
810  mp->client_index = tm->my_client_index;
811  mp->context = 0xdeadbeef;
812  mp->sw_if_index = ntohl (5);
813  mp->is_add = enable_disable;
814  mp->address_length = 8;
815
816  tmp = ntohl (0x01020304);
817  clib_memcpy (mp->address, &tmp, 4);
818
819  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
820}
821
822void
823add_del_v6_interface_address (test_main_t * tm, int enable_disable)
824{
825  vl_api_sw_interface_add_del_address_t *mp;
826  u64 tmp[2];
827
828  mp = vl_msg_api_alloc (sizeof (*mp));
829  clib_memset (mp, 0, sizeof (*mp));
830  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_ADD_DEL_ADDRESS);
831  mp->client_index = tm->my_client_index;
832  mp->context = 0xdeadbeef;
833  mp->is_ipv6 = 1;
834  mp->sw_if_index = ntohl (5);
835  mp->is_add = enable_disable;
836  mp->address_length = 64;
837
838  tmp[0] = clib_host_to_net_u64 (0xdb01000000000000ULL);
839  tmp[1] = clib_host_to_net_u64 (0x11ULL);
840
841  clib_memcpy (mp->address, &tmp[0], 8);
842  clib_memcpy (&mp->address[8], &tmp[1], 8);
843
844  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
845}
846
847void
848del_all_interface_addresses (test_main_t * tm)
849{
850  vl_api_sw_interface_add_del_address_t *mp;
851
852  mp = vl_msg_api_alloc (sizeof (*mp));
853  clib_memset (mp, 0, sizeof (*mp));
854  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_ADD_DEL_ADDRESS);
855  mp->client_index = tm->my_client_index;
856  mp->context = 0xdeadbeef;
857  mp->sw_if_index = ntohl (5);
858  mp->del_all = 1;
859
860  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
861}
862
863void
864set_interface_table (test_main_t * tm, int is_ipv6, u32 vrf_id)
865{
866  vl_api_sw_interface_set_table_t *mp;
867
868  mp = vl_msg_api_alloc (sizeof (*mp));
869  clib_memset (mp, 0, sizeof (*mp));
870  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_SET_TABLE);
871  mp->client_index = tm->my_client_index;
872  mp->context = 0xdeadbeef;
873  mp->sw_if_index = ntohl (5);
874  mp->is_ipv6 = is_ipv6;
875  mp->vrf_id = ntohl (vrf_id);
876
877  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
878}
879
880void
881connect_unix_tap (test_main_t * tm, char *name)
882{
883  vl_api_tap_connect_t *mp;
884
885  mp = vl_msg_api_alloc (sizeof (*mp));
886  clib_memset (mp, 0, sizeof (*mp));
887  mp->_vl_msg_id = ntohs (VL_API_TAP_CONNECT);
888  mp->client_index = tm->my_client_index;
889  mp->context = 0xdeadbeef;
890  strncpy ((char *) mp->tap_name, name, sizeof (mp->tap_name) - 1);
891  mp->use_random_mac = 1;
892  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
893}
894
895void
896create_vlan_subif (test_main_t * tm, u32 vlan_id)
897{
898  vl_api_create_vlan_subif_t *mp;
899
900  mp = vl_msg_api_alloc (sizeof (*mp));
901  clib_memset (mp, 0, sizeof (*mp));
902  mp->_vl_msg_id = ntohs (VL_API_CREATE_VLAN_SUBIF);
903  mp->client_index = tm->my_client_index;
904  mp->context = 0xdeadbeef;
905  mp->sw_if_index = ntohl (5);
906  mp->vlan_id = ntohl (vlan_id);
907
908  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
909}
910
911void
912add_del_proxy_arp (test_main_t * tm, int is_add)
913{
914  vl_api_proxy_arp_add_del_t *mp;
915  u32 tmp;
916
917  mp = vl_msg_api_alloc (sizeof (*mp));
918  clib_memset (mp, 0, sizeof (*mp));
919  mp->_vl_msg_id = ntohs (VL_API_PROXY_ARP_ADD_DEL);
920  mp->client_index = tm->my_client_index;
921  mp->context = 0xdeadbeef;
922  mp->proxy.vrf_id = ntohl (11);
923  mp->is_add = is_add;
924
925  /* proxy fib 11, 1.1.1.1 -> 1.1.1.10 */
926  tmp = ntohl (0x01010101);
927  clib_memcpy (mp->proxy.low_address, &tmp, 4);
928
929  tmp = ntohl (0x0101010a);
930  clib_memcpy (mp->proxy.hi_address, &tmp, 4);
931
932  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
933}
934
935void
936proxy_arp_intfc_enable_disable (test_main_t * tm, int enable_disable)
937{
938  vl_api_proxy_arp_intfc_enable_disable_t *mp;
939
940  mp = vl_msg_api_alloc (sizeof (*mp));
941  clib_memset (mp, 0, sizeof (*mp));
942  mp->_vl_msg_id = ntohs (VL_API_PROXY_ARP_INTFC_ENABLE_DISABLE);
943  mp->client_index = tm->my_client_index;
944  mp->context = 0xdeadbeef;
945  mp->sw_if_index = ntohl (6);
946  mp->enable_disable = enable_disable;
947
948  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
949}
950
951void
952add_ip4_neighbor (test_main_t * tm, int add_del)
953{
954  vl_api_ip_neighbor_add_del_t *mp;
955  u32 tmp;
956
957  mp = vl_msg_api_alloc (sizeof (*mp));
958  clib_memset (mp, 0, sizeof (*mp));
959  mp->_vl_msg_id = ntohs (VL_API_IP_NEIGHBOR_ADD_DEL);
960  mp->client_index = tm->my_client_index;
961  mp->context = 0xdeadbeef;
962  mp->sw_if_index = ntohl (6);
963  mp->is_add = add_del;
964
965  clib_memset (mp->mac_address, 0xbe, sizeof (mp->mac_address));
966
967  tmp = ntohl (0x0101010a);
968  clib_memcpy (mp->dst_address, &tmp, 4);
969
970  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
971}
972
973void
974add_ip6_neighbor (test_main_t * tm, int add_del)
975{
976  vl_api_ip_neighbor_add_del_t *mp;
977  u64 tmp[2];
978
979  mp = vl_msg_api_alloc (sizeof (*mp));
980  clib_memset (mp, 0, sizeof (*mp));
981  mp->_vl_msg_id = ntohs (VL_API_IP_NEIGHBOR_ADD_DEL);
982  mp->client_index = tm->my_client_index;
983  mp->context = 0xdeadbeef;
984  mp->sw_if_index = ntohl (6);
985  mp->is_add = add_del;
986  mp->is_ipv6 = 1;
987
988  clib_memset (mp->mac_address, 0xbe, sizeof (mp->mac_address));
989
990  tmp[0] = clib_host_to_net_u64 (0xdb01000000000000ULL);
991  tmp[1] = clib_host_to_net_u64 (0x11ULL);
992
993  clib_memcpy (mp->dst_address, &tmp[0], 8);
994  clib_memcpy (&mp->dst_address[8], &tmp[1], 8);
995
996  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
997}
998
999void
1000reset_fib (test_main_t * tm, u8 is_ip6)
1001{
1002  vl_api_reset_fib_t *mp;
1003
1004  mp = vl_msg_api_alloc (sizeof (*mp));
1005  clib_memset (mp, 0, sizeof (*mp));
1006  mp->_vl_msg_id = ntohs (VL_API_RESET_FIB);
1007  mp->client_index = tm->my_client_index;
1008  mp->context = 0xdeadbeef;
1009  mp->vrf_id = ntohl (11);
1010  mp->is_ipv6 = is_ip6;
1011
1012  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1013}
1014
1015void
1016dhcpv6_set_vss (test_main_t * tm)
1017{
1018  vl_api_dhcp_proxy_set_vss_t *mp;
1019
1020  mp = vl_msg_api_alloc (sizeof (*mp));
1021  clib_memset (mp, 0, sizeof (*mp));
1022  mp->_vl_msg_id = ntohs (VL_API_DHCP_PROXY_SET_VSS);
1023  mp->client_index = tm->my_client_index;
1024  mp->context = 0xdeadbeef;
1025  mp->oui = ntohl (6);
1026  mp->tbl_id = ntohl (60);
1027  mp->is_add = 1;
1028  mp->is_ipv6 = 1;
1029  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1030}
1031
1032void
1033dhcpv4_set_vss (test_main_t * tm)
1034{
1035  vl_api_dhcp_proxy_set_vss_t *mp;
1036
1037  mp = vl_msg_api_alloc (sizeof (*mp));
1038  clib_memset (mp, 0, sizeof (*mp));
1039  mp->_vl_msg_id = ntohs (VL_API_DHCP_PROXY_SET_VSS);
1040  mp->client_index = tm->my_client_index;
1041  mp->context = 0xdeadbeef;
1042  mp->oui = ntohl (4);
1043  mp->tbl_id = ntohl (40);
1044  mp->is_add = 1;
1045  mp->is_ipv6 = 0;
1046  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1047}
1048
1049void
1050dhcp_set_vss (test_main_t * tm)
1051{
1052  dhcpv4_set_vss (tm);
1053  dhcpv6_set_vss (tm);
1054}
1055
1056void
1057dhcp_set_proxy (test_main_t * tm, int ipv6)
1058{
1059  vl_api_dhcp_proxy_config_t *mp;
1060
1061  mp = vl_msg_api_alloc (sizeof (*mp));
1062  clib_memset (mp, 0, sizeof (*mp));
1063  mp->_vl_msg_id = ntohs (VL_API_DHCP_PROXY_CONFIG);
1064  mp->client_index = tm->my_client_index;
1065  mp->context = 0xdeadbeef;
1066  mp->is_ipv6 = ipv6;
1067  mp->is_add = 1;
1068  mp->dhcp_server[0] = 0x20;
1069  mp->dhcp_server[1] = 0x01;
1070  mp->dhcp_server[2] = 0xab;
1071  mp->dhcp_server[3] = 0xcd;
1072  mp->dhcp_server[4] = 0x12;
1073  mp->dhcp_server[5] = 0x34;
1074  mp->dhcp_server[6] = 0xfe;
1075  mp->dhcp_server[7] = 0xdc;
1076  mp->dhcp_server[14] = 0;
1077  mp->dhcp_server[15] = 0x2;
1078
1079  mp->dhcp_src_address[0] = 0x20;
1080  mp->dhcp_src_address[1] = 0x01;
1081  mp->dhcp_src_address[2] = 0xab;
1082  mp->dhcp_src_address[3] = 0xcd;
1083  mp->dhcp_src_address[4] = 0x12;
1084  mp->dhcp_src_address[5] = 0x34;
1085  mp->dhcp_src_address[6] = 0x56;
1086  mp->dhcp_src_address[7] = 0x78;
1087  mp->dhcp_src_address[14] = 0;
1088  mp->dhcp_src_address[15] = 0x2;
1089
1090  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1091}
1092
1093void
1094set_ip_flow_hash (test_main_t * tm, u8 is_ip6)
1095{
1096  vl_api_set_ip_flow_hash_t *mp;
1097
1098  mp = vl_msg_api_alloc (sizeof (*mp));
1099  clib_memset (mp, 0, sizeof (*mp));
1100  mp->_vl_msg_id = ntohs (VL_API_SET_IP_FLOW_HASH);
1101  mp->client_index = tm->my_client_index;
1102  mp->context = 0xdeadbeef;
1103  mp->vrf_id = 0;
1104  mp->is_ipv6 = is_ip6;
1105  mp->dst = 1;
1106  mp->reverse = 1;
1107
1108  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1109}
1110
1111void
1112ip6nd_ra_config (test_main_t * tm, int is_no)
1113{
1114  vl_api_sw_interface_ip6nd_ra_config_t *mp;
1115
1116  mp = vl_msg_api_alloc (sizeof (*mp));
1117  clib_memset (mp, 0, sizeof (*mp));
1118
1119  mp->client_index = tm->my_client_index;
1120  mp->context = 0xdeadbeef;
1121  mp->sw_if_index = ntohl (5);
1122  mp->is_no = is_no;
1123
1124  mp->suppress = 1;
1125
1126
1127  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_IP6ND_RA_CONFIG);
1128  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1129}
1130
1131void
1132ip6nd_ra_prefix (test_main_t * tm, int is_no)
1133{
1134  vl_api_sw_interface_ip6nd_ra_prefix_t *mp;
1135  u64 tmp[2];
1136
1137  mp = vl_msg_api_alloc (sizeof (*mp));
1138  clib_memset (mp, 0, sizeof (*mp));
1139
1140  mp->client_index = tm->my_client_index;
1141  mp->context = 0xdeadbeef;
1142  mp->sw_if_index = ntohl (5);
1143  mp->is_no = is_no;
1144
1145  mp->use_default = 1;
1146
1147
1148  tmp[0] = clib_host_to_net_u64 (0xdb01000000000000ULL);
1149  tmp[1] = clib_host_to_net_u64 (0x11ULL);
1150
1151
1152  clib_memcpy (mp->address, &tmp[0], 8);
1153  clib_memcpy (&mp->address[8], &tmp[1], 8);
1154
1155  mp->address_length = 64;
1156
1157
1158  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_IP6ND_RA_PREFIX);
1159  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1160}
1161
1162void
1163ip6_enable_disable (test_main_t * tm, int enable)
1164{
1165  vl_api_sw_interface_ip6_enable_disable_t *mp;
1166
1167  mp = vl_msg_api_alloc (sizeof (*mp));
1168  clib_memset (mp, 0, sizeof (*mp));
1169
1170  mp->client_index = tm->my_client_index;
1171  mp->context = 0xdeadbeef;
1172  mp->sw_if_index = ntohl (5);
1173  mp->enable = (enable == 1);;
1174
1175  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_IP6_ENABLE_DISABLE);
1176  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1177}
1178
1179void
1180loop_create (test_main_t * tm)
1181{
1182  vl_api_create_loopback_t *mp;
1183
1184  mp = vl_msg_api_alloc (sizeof (*mp));
1185  clib_memset (mp, 0, sizeof (*mp));
1186
1187  mp->_vl_msg_id = ntohs (VL_API_CREATE_LOOPBACK);
1188  mp->client_index = tm->my_client_index;
1189  mp->context = 0xdeadbeef;
1190  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1191}
1192
1193void
1194ip6_set_link_local_address (test_main_t * tm)
1195{
1196  vl_api_sw_interface_ip6_set_link_local_address_t *mp;
1197  u64 tmp[2];
1198
1199  mp = vl_msg_api_alloc (sizeof (*mp));
1200  clib_memset (mp, 0, sizeof (*mp));
1201
1202  mp->client_index = tm->my_client_index;
1203  mp->context = 0xdeadbeef;
1204  mp->sw_if_index = ntohl (5);
1205
1206  tmp[0] = clib_host_to_net_u64 (0xfe80000000000000ULL);
1207  tmp[1] = clib_host_to_net_u64 (0x11ULL);
1208
1209  ip6_address_encode ((ip6_address_encode *) & tmp, mp->address);
1210
1211  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_IP6_SET_LINK_LOCAL_ADDRESS);
1212
1213  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1214}
1215
1216
1217void
1218set_flags (test_main_t * tm, int up_down)
1219{
1220  vl_api_sw_interface_set_flags_t *mp;
1221
1222  mp = vl_msg_api_alloc (sizeof (*mp));
1223  clib_memset (mp, 0, sizeof (*mp));
1224
1225  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_SET_FLAGS);
1226  mp->client_index = tm->my_client_index;
1227  mp->context = 0xdeadbeef;
1228  mp->sw_if_index = ntohl (5);
1229  mp->admin_up_down = up_down;
1230  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1231
1232}
1233
1234void
1235l2_patch_add_del (test_main_t * tm, int is_add)
1236{
1237  vl_api_l2_patch_add_del_t *mp;
1238
1239  mp = vl_msg_api_alloc (sizeof (*mp));
1240  clib_memset (mp, 0, sizeof (*mp));
1241  mp->_vl_msg_id = ntohs (VL_API_L2_PATCH_ADD_DEL);
1242  mp->client_index = tm->my_client_index;
1243  mp->context = 0xdeadbeef;
1244  mp->is_add = is_add;
1245  mp->rx_sw_if_index = ntohl (1);
1246  mp->tx_sw_if_index = ntohl (2);
1247
1248  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1249}
1250
1251void
1252l2_xconnect (test_main_t * tm)
1253{
1254  vl_api_sw_interface_set_l2_xconnect_t *mp;
1255
1256  mp = vl_msg_api_alloc (sizeof (*mp));
1257  clib_memset (mp, 0, sizeof (*mp));
1258  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_SET_L2_XCONNECT);
1259  mp->client_index = tm->my_client_index;
1260  mp->context = 0xdeadbeef;
1261  mp->rx_sw_if_index = ntohl (5);
1262  mp->tx_sw_if_index = ntohl (6);
1263  mp->enable = 1;
1264
1265  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1266}
1267
1268void
1269l2_bridge (test_main_t * tm)
1270{
1271  vl_api_sw_interface_set_l2_bridge_t *mp;
1272
1273  mp = vl_msg_api_alloc (sizeof (*mp));
1274  clib_memset (mp, 0, sizeof (*mp));
1275  mp->_vl_msg_id = ntohs (VL_API_SW_INTERFACE_SET_L2_BRIDGE);
1276  mp->client_index = tm->my_client_index;
1277  mp->context = 0xdeadbeef;
1278  mp->rx_sw_if_index = ntohl (5);
1279  mp->bd_id = ntohl (6);
1280  mp->bvi = ntohl (1);
1281  mp->shg = ntohl (0);
1282  mp->enable = 1;
1283
1284  vl_msg_api_send_shmem (tm->vl_input_queue, (u8 *) & mp);
1285}
1286
1287int
1288main (int argc, char **argv)
1289{
1290  api_main_t *am = vlibapi_get_main ();
1291  test_main_t *tm = &test_main;
1292  int ch;
1293
1294  connect_to_vpe ("test_client");
1295
1296  tm->vl_input_queue = shmem_hdr->vl_input_queue;
1297  tm->my_client_index = am->my_client_index;
1298
1299  fformat (stdout, "Type 'h' for help, 'q' to quit...\n");
1300
1301  while (1)
1302    {
1303      ch = getchar ();
1304      switch (ch)
1305	{
1306	case 'q':
1307	  goto done;
1308	case 'd':
1309	  dump (tm);
1310	  break;
1311	case 'L':
1312	  link_up_down_enable_disable (tm, 1 /* enable_disable */ );
1313	  break;
1314	case 'l':
1315	  link_up_down_enable_disable (tm, 0 /* enable_disable */ );
1316	  break;
1317	case 'S':
1318	  stats_enable_disable (tm, 1 /* enable_disable */ );
1319	  break;
1320	case 's':
1321	  stats_enable_disable (tm, 0 /* enable_disable */ );
1322	  break;
1323	case '3':
1324	  add_del_ip4_route (tm, 0 /* add */ );
1325	  break;
1326	case '4':
1327	  add_del_ip4_route (tm, 1 /* add */ );
1328	  break;
1329	case '5':
1330	  add_del_ip6_route (tm, 0 /* add */ );
1331	  break;
1332	case '6':
1333	  add_del_ip6_route (tm, 1 /* add */ );
1334	  break;
1335	case 'A':
1336	  add_del_interface_address (tm, 1 /* add */ );
1337	  break;
1338	case 'a':
1339	  add_del_interface_address (tm, 0 /* add */ );
1340	  break;
1341	case 'B':
1342	  add_del_v6_interface_address (tm, 1 /* add */ );
1343	  break;
1344	case 'b':
1345	  add_del_v6_interface_address (tm, 0 /* add */ );
1346	  break;
1347	case 'E':
1348	  l2_patch_add_del (tm, 1 /* is_add */ );
1349	  break;
1350	case 'e':
1351	  l2_patch_add_del (tm, 0 /* is_add */ );
1352	  break;
1353	case 'z':
1354	  del_all_interface_addresses (tm);
1355	  break;
1356	case 't':
1357	  set_interface_table (tm, 0 /* is_ipv6 */ ,
1358			       11 /* my amp goes to 11 */ );
1359	  break;
1360	case 'T':
1361	  set_interface_table (tm, 1 /* is_ipv6 */ ,
1362			       12 /* my amp goes to 12 */ );
1363	  break;
1364
1365	case 'u':
1366	  create_vlan_subif (tm, 123);
1367	  break;
1368
1369	case 'c':
1370	  connect_unix_tap (tm, "foo");
1371	  break;
1372
1373	case 'n':
1374	  add_ip4_neighbor (tm, 1 /* is_add */ );
1375	  add_ip6_neighbor (tm, 1 /* is_add */ );
1376	  break;
1377
1378	case 'N':
1379	  add_ip4_neighbor (tm, 0 /* is_add */ );
1380	  add_ip6_neighbor (tm, 0 /* is_add */ );
1381	  break;
1382
1383	case 'p':
1384	  add_del_proxy_arp (tm, 1 /* add */ );
1385	  break;
1386
1387	case 'i':
1388	  proxy_arp_intfc_enable_disable (tm, 1 /* enable */ );
1389	  break;
1390
1391	case 'O':
1392	  oam_events_enable_disable (tm, 0 /* enable */ );
1393	  break;
1394
1395	case 'o':
1396	  oam_events_enable_disable (tm, 1 /* enable */ );
1397	  break;
1398
1399	case '0':
1400	  oam_add_del (tm, 0 /* is_add */ );
1401	  break;
1402
1403	case '1':
1404	  oam_add_del (tm, 1 /* is_add */ );
1405	  break;
1406
1407	case 'r':
1408	  reset_fib (tm, 0 /* is_ip6 */ );
1409	  break;
1410
1411	case 'R':
1412	  reset_fib (tm, 1 /* is_ip6 */ );
1413	  break;
1414
1415	case 'j':
1416	  dhcp_set_vss (tm);
1417	  break;
1418
1419	case 'k':
1420	  dhcp_set_proxy (tm, 0);
1421	  break;
1422
1423	case 'K':
1424	  dhcp_set_proxy (tm, 1 /*ipv6 */ );
1425	  break;
1426
1427	case 'v':
1428	  set_ip_flow_hash (tm, 0 /* is_ip6 */ );
1429	  break;
1430
1431	case 'V':
1432	  ip6_set_link_local_address (tm);
1433	  break;
1434
1435	case 'w':
1436	  ip6_enable_disable (tm, 1 /* enable */ );
1437	  break;
1438
1439	case 'W':
1440	  ip6_enable_disable (tm, 0 /* disable */ );
1441	  break;
1442
1443	case 'x':
1444	  ip6nd_ra_config (tm, 0 /* is_no */ );
1445	  break;
1446	case 'X':
1447	  ip6nd_ra_config (tm, 1 /* is_no */ );
1448	  break;
1449	case 'y':
1450	  ip6nd_ra_prefix (tm, 0 /* is_no */ );
1451	  break;
1452	case 'Y':
1453	  ip6nd_ra_prefix (tm, 1 /* is_no */ );
1454	  break;
1455
1456	case '7':
1457	  loop_create (tm);
1458	  break;
1459
1460	case 'F':
1461	  set_flags (tm, 1 /* up_down */ );
1462	  break;
1463
1464	case 'f':
1465	  set_flags (tm, 0 /* up_down */ );
1466	  break;
1467
1468	case '@':
1469	  l2_xconnect (tm);
1470	  break;
1471
1472	case '#':
1473	  l2_bridge (tm);
1474	  break;
1475
1476	case 'h':
1477	  fformat (stdout, "q=quit,d=dump,L=link evts on,l=link evts off\n");
1478	  fformat (stdout, "S=stats on,s=stats off\n");
1479	  fformat (stdout, "4=add v4 route, 3=del v4 route\n");
1480	  fformat (stdout, "6=add v6 route, 5=del v6 route\n");
1481	  fformat (stdout, "A=add v4 intfc route, a=del v4 intfc route\n");
1482	  fformat (stdout, "B=add v6 intfc route, b=del v6 intfc route\n");
1483	  fformat (stdout, "z=del all intfc routes\n");
1484	  fformat (stdout, "t=set v4 intfc table, T=set v6 intfc table\n");
1485	  fformat (stdout, "c=connect unix tap\n");
1486	  fformat (stdout,
1487		   "j=set dhcpv4 and v6 link-address/option-82 params\n");
1488	  fformat (stdout, "k=set dhcpv4 relay agent params\n");
1489	  fformat (stdout, "K=set dhcpv6 relay agent params\n");
1490	  fformat (stdout, "E=add l2 patch, e=del l2 patch\n");
1491	  fformat (stdout, "V=ip6 set link-local address \n");
1492	  fformat (stdout, "w=ip6 enable \n");
1493	  fformat (stdout, "W=ip6 disable \n");
1494	  fformat (stdout, "x=ip6 nd config \n");
1495	  fformat (stdout, "X=no ip6 nd config\n");
1496	  fformat (stdout, "y=ip6 nd prefix \n");
1497	  fformat (stdout, "Y=no ip6 nd prefix\n");
1498	  fformat (stdout, "@=l2 xconnect\n");
1499	  fformat (stdout, "#=l2 bridge\n");
1500
1501	default:
1502	  break;
1503	}
1504
1505    }
1506
1507done:
1508
1509  if (tm->link_events_on)
1510    link_up_down_enable_disable (tm, 0 /* enable */ );
1511  if (tm->stats_on)
1512    stats_enable_disable (tm, 0 /* enable */ );
1513  if (tm->oam_events_on)
1514    oam_events_enable_disable (tm, 0 /* enable */ );
1515
1516  disconnect_from_vpe ();
1517  exit (0);
1518}
1519
1520#undef vl_api_version
1521#define vl_api_version(n,v) static u32 vpe_api_version = v;
1522#include <vpp/api/vpe.api.h>
1523#undef vl_api_version
1524
1525void
1526vl_client_add_api_signatures (vl_api_memclnt_create_t * mp)
1527{
1528  /*
1529   * Send the main API signature in slot 0. This bit of code must
1530   * match the checks in ../vpe/api/api.c: vl_msg_api_version_check().
1531   */
1532  mp->api_versions[0] = clib_host_to_net_u32 (vpe_api_version);
1533}
1534
1535/*
1536 * fd.io coding-style-patch-verification: ON
1537 *
1538 * Local Variables:
1539 * eval: (c-set-style "gnu")
1540 * End:
1541 */
1542