blob: b16f664f52cc27af7b4483e46595837180332468 [file] [log] [blame]
Damjan Marion7cd468a2016-12-19 23:05:39 +01001/*
2 *------------------------------------------------------------------
3 * api_format.c
4 *
Dave Barachac0326f2020-07-14 18:30:05 -04005 * Copyright (c) 2014-2020 Cisco and/or its affiliates.
Damjan Marion7cd468a2016-12-19 23:05:39 +01006 * 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 <vat/vat.h>
jialv01082ebeb2019-09-10 00:23:55 +080021#include <vlib/pci/pci.h>
Neale Ranns86327be2018-11-02 09:14:01 -070022#include <vpp/api/types.h>
Dave Barach59b25652017-09-10 15:04:27 -040023#include <vppinfra/socket.h>
Damjan Marion7cd468a2016-12-19 23:05:39 +010024#include <vlibapi/api.h>
25#include <vlibmemory/api.h>
Damjan Marion7cd468a2016-12-19 23:05:39 +010026#include <vnet/ip/ip.h>
Neale Rannscbe25aa2019-09-30 10:53:31 +000027#include <vnet/ip-neighbor/ip_neighbor.h>
Neale Ranns37029302018-08-10 05:30:06 -070028#include <vnet/ip/ip_types_api.h>
Damjan Marion7cd468a2016-12-19 23:05:39 +010029#include <vnet/l2/l2_input.h>
Damjan Marion7cd468a2016-12-19 23:05:39 +010030#include <vnet/vxlan/vxlan.h>
Damjan Marion7cd468a2016-12-19 23:05:39 +010031#include <vnet/vxlan-gpe/vxlan_gpe.h>
Florin Corasb040f982020-10-20 14:59:43 -070032#include <vnet/udp/udp_local.h>
Damjan Marion7cd468a2016-12-19 23:05:39 +010033
34#include <vpp/api/vpe_msg_enum.h>
35#include <vnet/l2/l2_classify.h>
36#include <vnet/l2/l2_vtr.h>
Andrew Yourtchenko815d7d52018-02-07 11:37:02 +010037#include <vnet/classify/in_out_acl.h>
Damjan Marion7cd468a2016-12-19 23:05:39 +010038#include <vnet/classify/policer_classify.h>
39#include <vnet/classify/flow_classify.h>
40#include <vnet/mpls/mpls.h>
41#include <vnet/ipsec/ipsec.h>
Damjan Marion7cd468a2016-12-19 23:05:39 +010042#include <inttypes.h>
Damjan Marion7cd468a2016-12-19 23:05:39 +010043#include <vnet/ip/ip6_hop_by_hop.h>
44#include <vnet/ip/ip_source_and_port_range_check.h>
45#include <vnet/policer/xlate.h>
46#include <vnet/span/span.h>
47#include <vnet/policer/policer.h>
48#include <vnet/policer/police.h>
Neale Ranns32e1c012016-11-22 17:07:28 +000049#include <vnet/mfib/mfib_types.h>
Steven9cd2d7a2017-12-20 12:43:01 -080050#include <vnet/bonding/node.h>
Igor Mikhailov (imichail)582caa32018-04-26 21:33:02 -070051#include <vnet/qos/qos_types.h>
Neale Ranns37029302018-08-10 05:30:06 -070052#include <vnet/ethernet/ethernet_types_api.h>
53#include <vnet/ip/ip_types_api.h>
Damjan Marion7cd468a2016-12-19 23:05:39 +010054#include "vat/json_format.h"
Neale Ranns86327be2018-11-02 09:14:01 -070055#include <vnet/ip/ip_types_api.h>
56#include <vnet/ethernet/ethernet_types_api.h>
Damjan Marion7cd468a2016-12-19 23:05:39 +010057
58#include <inttypes.h>
59#include <sys/stat.h>
60
61#define vl_typedefs /* define message structures */
62#include <vpp/api/vpe_all_api_h.h>
63#undef vl_typedefs
64
65/* declare message handlers for each api */
66
67#define vl_endianfun /* define message structures */
68#include <vpp/api/vpe_all_api_h.h>
69#undef vl_endianfun
70
71/* instantiate all the print functions we know about */
Dave Barachf35a0722019-06-12 16:50:38 -040072#if VPP_API_TEST_BUILTIN == 0
Damjan Marion7cd468a2016-12-19 23:05:39 +010073#define vl_print(handle, ...)
Dave Barachf35a0722019-06-12 16:50:38 -040074#else
75#define vl_print(handle, ...) vlib_cli_output (handle, __VA_ARGS__)
76#endif
Damjan Marion7cd468a2016-12-19 23:05:39 +010077#define vl_printfun
78#include <vpp/api/vpe_all_api_h.h>
79#undef vl_printfun
80
Dave Barach2d6b2d62017-01-25 16:32:08 -050081#define __plugin_msg_base 0
Dave Barachfe6bdfd2017-01-20 19:50:09 -050082#include <vlibapi/vat_helper_macros.h>
83
Ole Troan33a58172019-09-04 09:12:29 +020084#include <vnet/format_fns.h>
85
Dave Barachb09f4d02019-07-15 16:00:03 -040086void vl_api_set_elog_main (elog_main_t * m);
87int vl_api_set_elog_trace_api_messages (int enable);
88
Dave Barach59b25652017-09-10 15:04:27 -040089#if VPP_API_TEST_BUILTIN == 0
90#include <netdb.h>
91
92u32
93vl (void *p)
94{
95 return vec_len (p);
96}
97
98int
99vat_socket_connect (vat_main_t * vam)
100{
Florin Coras66a10032018-12-21 16:23:09 -0800101 int rv;
Dave Barach69eeadc2020-04-14 09:52:26 -0400102 api_main_t *am = vlibapi_get_main ();
Florin Coras90a63982017-12-19 04:50:01 -0800103 vam->socket_client_main = &socket_client_main;
Florin Coras66a10032018-12-21 16:23:09 -0800104 if ((rv = vl_socket_client_connect ((char *) vam->socket_name,
105 "vpp_api_test",
106 0 /* default socket rx, tx buffer */ )))
107 return rv;
Dave Barach69eeadc2020-04-14 09:52:26 -0400108
Florin Coras66a10032018-12-21 16:23:09 -0800109 /* vpp expects the client index in network order */
110 vam->my_client_index = htonl (socket_client_main.client_index);
Dave Barach69eeadc2020-04-14 09:52:26 -0400111 am->my_client_index = vam->my_client_index;
Florin Coras66a10032018-12-21 16:23:09 -0800112 return 0;
Dave Barach59b25652017-09-10 15:04:27 -0400113}
114#else /* vpp built-in case, we don't do sockets... */
115int
116vat_socket_connect (vat_main_t * vam)
117{
118 return 0;
119}
120
Florin Coras90a63982017-12-19 04:50:01 -0800121int
122vl_socket_client_read (int wait)
Dave Barach59b25652017-09-10 15:04:27 -0400123{
Florin Coras90a63982017-12-19 04:50:01 -0800124 return -1;
Dave Barach59b25652017-09-10 15:04:27 -0400125};
Florin Coras90a63982017-12-19 04:50:01 -0800126
127int
128vl_socket_client_write ()
129{
130 return -1;
131};
132
133void *
134vl_socket_client_msg_alloc (int nbytes)
135{
136 return 0;
137}
Dave Barach59b25652017-09-10 15:04:27 -0400138#endif
139
140
Dave Barachfe6bdfd2017-01-20 19:50:09 -0500141f64
142vat_time_now (vat_main_t * vam)
143{
144#if VPP_API_TEST_BUILTIN
145 return vlib_time_now (vam->vlib_main);
146#else
147 return clib_time_now (&vam->clib_time);
148#endif
149}
150
151void
152errmsg (char *fmt, ...)
153{
154 vat_main_t *vam = &vat_main;
155 va_list va;
156 u8 *s;
157
158 va_start (va, fmt);
159 s = va_format (0, fmt, &va);
160 va_end (va);
161
162 vec_add1 (s, 0);
163
164#if VPP_API_TEST_BUILTIN
165 vlib_cli_output (vam->vlib_main, (char *) s);
166#else
167 {
168 if (vam->ifp != stdin)
169 fformat (vam->ofp, "%s(%d): \n", vam->current_file,
170 vam->input_line_number);
Dave Barachb09f4d02019-07-15 16:00:03 -0400171 else
172 fformat (vam->ofp, "%s\n", (char *) s);
Dave Barachfe6bdfd2017-01-20 19:50:09 -0500173 fflush (vam->ofp);
174 }
175#endif
176
177 vec_free (s);
178}
179
Dave Barach4a3f69c2017-02-22 12:44:56 -0500180#if VPP_API_TEST_BUILTIN == 0
Damjan Marion7cd468a2016-12-19 23:05:39 +0100181static uword
182api_unformat_sw_if_index (unformat_input_t * input, va_list * args)
183{
184 vat_main_t *vam = va_arg (*args, vat_main_t *);
185 u32 *result = va_arg (*args, u32 *);
186 u8 *if_name;
187 uword *p;
188
189 if (!unformat (input, "%s", &if_name))
190 return 0;
191
192 p = hash_get_mem (vam->sw_if_index_by_interface_name, if_name);
193 if (p == 0)
194 return 0;
195 *result = p[0];
196 return 1;
197}
198
eyal bariaf86a482018-04-17 11:20:27 +0300199static uword
200api_unformat_hw_if_index (unformat_input_t * input, va_list * args)
201{
202 return 0;
203}
204
Damjan Marion7cd468a2016-12-19 23:05:39 +0100205/* Parse an IP4 address %d.%d.%d.%d. */
206uword
207unformat_ip4_address (unformat_input_t * input, va_list * args)
208{
209 u8 *result = va_arg (*args, u8 *);
210 unsigned a[4];
211
212 if (!unformat (input, "%d.%d.%d.%d", &a[0], &a[1], &a[2], &a[3]))
213 return 0;
214
215 if (a[0] >= 256 || a[1] >= 256 || a[2] >= 256 || a[3] >= 256)
216 return 0;
217
218 result[0] = a[0];
219 result[1] = a[1];
220 result[2] = a[2];
221 result[3] = a[3];
222
223 return 1;
224}
225
226uword
227unformat_ethernet_address (unformat_input_t * input, va_list * args)
228{
229 u8 *result = va_arg (*args, u8 *);
230 u32 i, a[6];
231
232 if (!unformat (input, "%_%x:%x:%x:%x:%x:%x%_",
233 &a[0], &a[1], &a[2], &a[3], &a[4], &a[5]))
234 return 0;
235
236 /* Check range. */
237 for (i = 0; i < 6; i++)
238 if (a[i] >= (1 << 8))
239 return 0;
240
241 for (i = 0; i < 6; i++)
242 result[i] = a[i];
243
244 return 1;
245}
246
247/* Returns ethernet type as an int in host byte order. */
248uword
249unformat_ethernet_type_host_byte_order (unformat_input_t * input,
250 va_list * args)
251{
252 u16 *result = va_arg (*args, u16 *);
253 int type;
254
255 /* Numeric type. */
256 if (unformat (input, "0x%x", &type) || unformat (input, "%d", &type))
257 {
258 if (type >= (1 << 16))
259 return 0;
260 *result = type;
261 return 1;
262 }
263 return 0;
264}
265
Jakub Grajciar23a386b2020-02-26 11:01:43 +0100266/* Parse an IP46 address. */
267uword
268unformat_ip46_address (unformat_input_t * input, va_list * args)
269{
270 ip46_address_t *ip46 = va_arg (*args, ip46_address_t *);
271 ip46_type_t type = va_arg (*args, ip46_type_t);
272 if ((type != IP46_TYPE_IP6) &&
273 unformat (input, "%U", unformat_ip4_address, &ip46->ip4))
274 {
275 ip46_address_mask_ip4 (ip46);
276 return 1;
277 }
278 else if ((type != IP46_TYPE_IP4) &&
279 unformat (input, "%U", unformat_ip6_address, &ip46->ip6))
280 {
281 return 1;
282 }
283 return 0;
284}
285
Damjan Marion7cd468a2016-12-19 23:05:39 +0100286/* Parse an IP6 address. */
287uword
288unformat_ip6_address (unformat_input_t * input, va_list * args)
289{
290 ip6_address_t *result = va_arg (*args, ip6_address_t *);
291 u16 hex_quads[8];
292 uword hex_quad, n_hex_quads, hex_digit, n_hex_digits;
293 uword c, n_colon, double_colon_index;
294
295 n_hex_quads = hex_quad = n_hex_digits = n_colon = 0;
296 double_colon_index = ARRAY_LEN (hex_quads);
297 while ((c = unformat_get_input (input)) != UNFORMAT_END_OF_INPUT)
298 {
299 hex_digit = 16;
300 if (c >= '0' && c <= '9')
301 hex_digit = c - '0';
302 else if (c >= 'a' && c <= 'f')
303 hex_digit = c + 10 - 'a';
304 else if (c >= 'A' && c <= 'F')
305 hex_digit = c + 10 - 'A';
306 else if (c == ':' && n_colon < 2)
307 n_colon++;
308 else
309 {
310 unformat_put_input (input);
311 break;
312 }
313
314 /* Too many hex quads. */
315 if (n_hex_quads >= ARRAY_LEN (hex_quads))
316 return 0;
317
318 if (hex_digit < 16)
319 {
320 hex_quad = (hex_quad << 4) | hex_digit;
321
322 /* Hex quad must fit in 16 bits. */
323 if (n_hex_digits >= 4)
324 return 0;
325
326 n_colon = 0;
327 n_hex_digits++;
328 }
329
330 /* Save position of :: */
331 if (n_colon == 2)
332 {
333 /* More than one :: ? */
334 if (double_colon_index < ARRAY_LEN (hex_quads))
335 return 0;
336 double_colon_index = n_hex_quads;
337 }
338
339 if (n_colon > 0 && n_hex_digits > 0)
340 {
341 hex_quads[n_hex_quads++] = hex_quad;
342 hex_quad = 0;
343 n_hex_digits = 0;
344 }
345 }
346
347 if (n_hex_digits > 0)
348 hex_quads[n_hex_quads++] = hex_quad;
349
350 {
351 word i;
352
353 /* Expand :: to appropriate number of zero hex quads. */
354 if (double_colon_index < ARRAY_LEN (hex_quads))
355 {
356 word n_zero = ARRAY_LEN (hex_quads) - n_hex_quads;
357
358 for (i = n_hex_quads - 1; i >= (signed) double_colon_index; i--)
359 hex_quads[n_zero + i] = hex_quads[i];
360
361 for (i = 0; i < n_zero; i++)
362 hex_quads[double_colon_index + i] = 0;
363
364 n_hex_quads = ARRAY_LEN (hex_quads);
365 }
366
367 /* Too few hex quads given. */
368 if (n_hex_quads < ARRAY_LEN (hex_quads))
369 return 0;
370
371 for (i = 0; i < ARRAY_LEN (hex_quads); i++)
372 result->as_u16[i] = clib_host_to_net_u16 (hex_quads[i]);
373
374 return 1;
375 }
376}
377
378uword
379unformat_ipsec_policy_action (unformat_input_t * input, va_list * args)
380{
381 u32 *r = va_arg (*args, u32 *);
382
383 if (0);
384#define _(v,f,s) else if (unformat (input, s)) *r = IPSEC_POLICY_ACTION_##f;
385 foreach_ipsec_policy_action
386#undef _
387 else
388 return 0;
389 return 1;
390}
391
Damjan Marion7cd468a2016-12-19 23:05:39 +0100392u8 *
393format_ipsec_crypto_alg (u8 * s, va_list * args)
394{
395 u32 i = va_arg (*args, u32);
396 u8 *t = 0;
397
398 switch (i)
399 {
400#define _(v,f,str) case IPSEC_CRYPTO_ALG_##f: t = (u8 *) str; break;
401 foreach_ipsec_crypto_alg
402#undef _
403 default:
404 return format (s, "unknown");
405 }
406 return format (s, "%s", t);
407}
408
Damjan Marion7cd468a2016-12-19 23:05:39 +0100409u8 *
410format_ipsec_integ_alg (u8 * s, va_list * args)
411{
412 u32 i = va_arg (*args, u32);
413 u8 *t = 0;
414
415 switch (i)
416 {
417#define _(v,f,str) case IPSEC_INTEG_ALG_##f: t = (u8 *) str; break;
418 foreach_ipsec_integ_alg
419#undef _
420 default:
421 return format (s, "unknown");
422 }
423 return format (s, "%s", t);
424}
425
Dave Barach4a3f69c2017-02-22 12:44:56 -0500426#else /* VPP_API_TEST_BUILTIN == 1 */
427static uword
428api_unformat_sw_if_index (unformat_input_t * input, va_list * args)
429{
Benoît Ganne49ee6842019-04-30 11:50:46 +0200430 vat_main_t *vam __clib_unused = va_arg (*args, vat_main_t *);
Dave Barach4a3f69c2017-02-22 12:44:56 -0500431 vnet_main_t *vnm = vnet_get_main ();
432 u32 *result = va_arg (*args, u32 *);
Dave Barach4a3f69c2017-02-22 12:44:56 -0500433
eyal bariaf86a482018-04-17 11:20:27 +0300434 return unformat (input, "%U", unformat_vnet_sw_interface, vnm, result);
Dave Barach4a3f69c2017-02-22 12:44:56 -0500435}
eyal bariaf86a482018-04-17 11:20:27 +0300436
437static uword
438api_unformat_hw_if_index (unformat_input_t * input, va_list * args)
439{
Benoît Ganne49ee6842019-04-30 11:50:46 +0200440 vat_main_t *vam __clib_unused = va_arg (*args, vat_main_t *);
eyal bariaf86a482018-04-17 11:20:27 +0300441 vnet_main_t *vnm = vnet_get_main ();
442 u32 *result = va_arg (*args, u32 *);
443
444 return unformat (input, "%U", unformat_vnet_hw_interface, vnm, result);
445}
446
Damjan Marion7cd468a2016-12-19 23:05:39 +0100447#endif /* VPP_API_TEST_BUILTIN */
448
Neale Ranns17dcec02019-01-09 21:22:20 -0800449uword
450unformat_ipsec_api_crypto_alg (unformat_input_t * input, va_list * args)
451{
452 u32 *r = va_arg (*args, u32 *);
453
454 if (0);
455#define _(v,f,s) else if (unformat (input, s)) *r = IPSEC_API_CRYPTO_ALG_##f;
456 foreach_ipsec_crypto_alg
457#undef _
458 else
459 return 0;
460 return 1;
461}
462
463uword
464unformat_ipsec_api_integ_alg (unformat_input_t * input, va_list * args)
465{
466 u32 *r = va_arg (*args, u32 *);
467
468 if (0);
469#define _(v,f,s) else if (unformat (input, s)) *r = IPSEC_API_INTEG_ALG_##f;
470 foreach_ipsec_integ_alg
471#undef _
472 else
473 return 0;
474 return 1;
475}
476
Damjan Marion7cd468a2016-12-19 23:05:39 +0100477static uword
478unformat_policer_rate_type (unformat_input_t * input, va_list * args)
479{
480 u8 *r = va_arg (*args, u8 *);
481
482 if (unformat (input, "kbps"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000483 *r = QOS_RATE_KBPS;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100484 else if (unformat (input, "pps"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000485 *r = QOS_RATE_PPS;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100486 else
487 return 0;
488 return 1;
489}
490
491static uword
492unformat_policer_round_type (unformat_input_t * input, va_list * args)
493{
494 u8 *r = va_arg (*args, u8 *);
495
496 if (unformat (input, "closest"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000497 *r = QOS_ROUND_TO_CLOSEST;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100498 else if (unformat (input, "up"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000499 *r = QOS_ROUND_TO_UP;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100500 else if (unformat (input, "down"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000501 *r = QOS_ROUND_TO_DOWN;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100502 else
503 return 0;
504 return 1;
505}
506
507static uword
508unformat_policer_type (unformat_input_t * input, va_list * args)
509{
510 u8 *r = va_arg (*args, u8 *);
511
512 if (unformat (input, "1r2c"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000513 *r = QOS_POLICER_TYPE_1R2C;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100514 else if (unformat (input, "1r3c"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000515 *r = QOS_POLICER_TYPE_1R3C_RFC_2697;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100516 else if (unformat (input, "2r3c-2698"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000517 *r = QOS_POLICER_TYPE_2R3C_RFC_2698;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100518 else if (unformat (input, "2r3c-4115"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000519 *r = QOS_POLICER_TYPE_2R3C_RFC_4115;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100520 else if (unformat (input, "2r3c-mef5cf1"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000521 *r = QOS_POLICER_TYPE_2R3C_RFC_MEF5CF1;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100522 else
523 return 0;
524 return 1;
525}
526
527static uword
528unformat_dscp (unformat_input_t * input, va_list * va)
529{
530 u8 *r = va_arg (*va, u8 *);
531
532 if (0);
Brian Russelle3845d72021-02-08 15:33:18 +0000533#define _(v, f) else if (unformat (input, #f)) *r = IP_DSCP_##f;
534 foreach_ip_dscp
Damjan Marion7cd468a2016-12-19 23:05:39 +0100535#undef _
Brian Russelle3845d72021-02-08 15:33:18 +0000536 else return 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100537 return 1;
538}
539
540static uword
541unformat_policer_action_type (unformat_input_t * input, va_list * va)
542{
Brian Russellc5299ff2021-02-09 10:16:58 +0000543 qos_pol_action_params_st *a = va_arg (*va, qos_pol_action_params_st *);
Damjan Marion7cd468a2016-12-19 23:05:39 +0100544
545 if (unformat (input, "drop"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000546 a->action_type = QOS_ACTION_DROP;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100547 else if (unformat (input, "transmit"))
Brian Russellc5299ff2021-02-09 10:16:58 +0000548 a->action_type = QOS_ACTION_TRANSMIT;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100549 else if (unformat (input, "mark-and-transmit %U", unformat_dscp, &a->dscp))
Brian Russellc5299ff2021-02-09 10:16:58 +0000550 a->action_type = QOS_ACTION_MARK_AND_TRANSMIT;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100551 else
552 return 0;
553 return 1;
554}
555
556static uword
557unformat_policer_classify_table_type (unformat_input_t * input, va_list * va)
558{
559 u32 *r = va_arg (*va, u32 *);
560 u32 tid;
561
562 if (unformat (input, "ip4"))
563 tid = POLICER_CLASSIFY_TABLE_IP4;
564 else if (unformat (input, "ip6"))
565 tid = POLICER_CLASSIFY_TABLE_IP6;
566 else if (unformat (input, "l2"))
567 tid = POLICER_CLASSIFY_TABLE_L2;
568 else
569 return 0;
570
571 *r = tid;
572 return 1;
573}
574
575static uword
576unformat_flow_classify_table_type (unformat_input_t * input, va_list * va)
577{
578 u32 *r = va_arg (*va, u32 *);
579 u32 tid;
580
581 if (unformat (input, "ip4"))
582 tid = FLOW_CLASSIFY_TABLE_IP4;
583 else if (unformat (input, "ip6"))
584 tid = FLOW_CLASSIFY_TABLE_IP6;
585 else
586 return 0;
587
588 *r = tid;
589 return 1;
590}
591
Benoît Ganne49ee6842019-04-30 11:50:46 +0200592#if (VPP_API_TEST_BUILTIN==0)
593
Neale Ranns32e1c012016-11-22 17:07:28 +0000594static const char *mfib_flag_names[] = MFIB_ENTRY_NAMES_SHORT;
595static const char *mfib_flag_long_names[] = MFIB_ENTRY_NAMES_LONG;
596static const char *mfib_itf_flag_long_names[] = MFIB_ITF_NAMES_LONG;
597static const char *mfib_itf_flag_names[] = MFIB_ITF_NAMES_SHORT;
598
599uword
600unformat_mfib_itf_flags (unformat_input_t * input, va_list * args)
601{
602 mfib_itf_flags_t old, *iflags = va_arg (*args, mfib_itf_flags_t *);
603 mfib_itf_attribute_t attr;
604
605 old = *iflags;
606 FOR_EACH_MFIB_ITF_ATTRIBUTE (attr)
607 {
608 if (unformat (input, mfib_itf_flag_long_names[attr]))
609 *iflags |= (1 << attr);
610 }
611 FOR_EACH_MFIB_ITF_ATTRIBUTE (attr)
612 {
613 if (unformat (input, mfib_itf_flag_names[attr]))
614 *iflags |= (1 << attr);
615 }
616
617 return (old == *iflags ? 0 : 1);
618}
619
620uword
621unformat_mfib_entry_flags (unformat_input_t * input, va_list * args)
622{
623 mfib_entry_flags_t old, *eflags = va_arg (*args, mfib_entry_flags_t *);
624 mfib_entry_attribute_t attr;
625
626 old = *eflags;
627 FOR_EACH_MFIB_ATTRIBUTE (attr)
628 {
629 if (unformat (input, mfib_flag_long_names[attr]))
630 *eflags |= (1 << attr);
631 }
632 FOR_EACH_MFIB_ATTRIBUTE (attr)
633 {
634 if (unformat (input, mfib_flag_names[attr]))
635 *eflags |= (1 << attr);
636 }
637
638 return (old == *eflags ? 0 : 1);
639}
640
Damjan Marion7cd468a2016-12-19 23:05:39 +0100641u8 *
642format_ip4_address (u8 * s, va_list * args)
643{
644 u8 *a = va_arg (*args, u8 *);
645 return format (s, "%d.%d.%d.%d", a[0], a[1], a[2], a[3]);
646}
647
648u8 *
649format_ip6_address (u8 * s, va_list * args)
650{
651 ip6_address_t *a = va_arg (*args, ip6_address_t *);
652 u32 i, i_max_n_zero, max_n_zeros, i_first_zero, n_zeros, last_double_colon;
653
654 i_max_n_zero = ARRAY_LEN (a->as_u16);
655 max_n_zeros = 0;
656 i_first_zero = i_max_n_zero;
657 n_zeros = 0;
658 for (i = 0; i < ARRAY_LEN (a->as_u16); i++)
659 {
660 u32 is_zero = a->as_u16[i] == 0;
661 if (is_zero && i_first_zero >= ARRAY_LEN (a->as_u16))
662 {
663 i_first_zero = i;
664 n_zeros = 0;
665 }
666 n_zeros += is_zero;
667 if ((!is_zero && n_zeros > max_n_zeros)
668 || (i + 1 >= ARRAY_LEN (a->as_u16) && n_zeros > max_n_zeros))
669 {
670 i_max_n_zero = i_first_zero;
671 max_n_zeros = n_zeros;
672 i_first_zero = ARRAY_LEN (a->as_u16);
673 n_zeros = 0;
674 }
675 }
676
677 last_double_colon = 0;
678 for (i = 0; i < ARRAY_LEN (a->as_u16); i++)
679 {
680 if (i == i_max_n_zero && max_n_zeros > 1)
681 {
682 s = format (s, "::");
683 i += max_n_zeros - 1;
684 last_double_colon = 1;
685 }
686 else
687 {
688 s = format (s, "%s%x",
689 (last_double_colon || i == 0) ? "" : ":",
690 clib_net_to_host_u16 (a->as_u16[i]));
691 last_double_colon = 0;
692 }
693 }
694
695 return s;
696}
697
698/* Format an IP46 address. */
699u8 *
700format_ip46_address (u8 * s, va_list * args)
701{
702 ip46_address_t *ip46 = va_arg (*args, ip46_address_t *);
703 ip46_type_t type = va_arg (*args, ip46_type_t);
704 int is_ip4 = 1;
705
706 switch (type)
707 {
708 case IP46_TYPE_ANY:
709 is_ip4 = ip46_address_is_ip4 (ip46);
710 break;
711 case IP46_TYPE_IP4:
712 is_ip4 = 1;
713 break;
714 case IP46_TYPE_IP6:
715 is_ip4 = 0;
716 break;
717 }
718
719 return is_ip4 ?
720 format (s, "%U", format_ip4_address, &ip46->ip4) :
721 format (s, "%U", format_ip6_address, &ip46->ip6);
722}
723
724u8 *
725format_ethernet_address (u8 * s, va_list * args)
726{
727 u8 *a = va_arg (*args, u8 *);
728
729 return format (s, "%02x:%02x:%02x:%02x:%02x:%02x",
730 a[0], a[1], a[2], a[3], a[4], a[5]);
731}
732#endif
733
734static void
Neale Ranns097fa662018-05-01 05:17:55 -0700735increment_v4_address (vl_api_ip4_address_t * i)
Damjan Marion7cd468a2016-12-19 23:05:39 +0100736{
Neale Ranns097fa662018-05-01 05:17:55 -0700737 ip4_address_t *a = (ip4_address_t *) i;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100738 u32 v;
739
740 v = ntohl (a->as_u32) + 1;
741 a->as_u32 = ntohl (v);
742}
743
744static void
Neale Ranns097fa662018-05-01 05:17:55 -0700745increment_v6_address (vl_api_ip6_address_t * i)
Neale Ranns2b5ba952019-04-02 10:15:40 +0000746{
Neale Ranns097fa662018-05-01 05:17:55 -0700747 ip6_address_t *a = (ip6_address_t *) i;
Damjan Marion7cd468a2016-12-19 23:05:39 +0100748 u64 v0, v1;
749
750 v0 = clib_net_to_host_u64 (a->as_u64[0]);
751 v1 = clib_net_to_host_u64 (a->as_u64[1]);
752
753 v1 += 1;
754 if (v1 == 0)
755 v0 += 1;
756 a->as_u64[0] = clib_net_to_host_u64 (v0);
757 a->as_u64[1] = clib_net_to_host_u64 (v1);
758}
759
760static void
Neale Ranns097fa662018-05-01 05:17:55 -0700761increment_address (vl_api_address_t * a)
762{
Dave Barach54582662020-04-21 08:01:16 -0400763 if (a->af == ADDRESS_IP4)
Neale Ranns097fa662018-05-01 05:17:55 -0700764 increment_v4_address (&a->un.ip4);
Dave Barach54582662020-04-21 08:01:16 -0400765 else if (a->af == ADDRESS_IP6)
Neale Ranns097fa662018-05-01 05:17:55 -0700766 increment_v6_address (&a->un.ip6);
767}
768
769static void
770set_ip4_address (vl_api_address_t * a, u32 v)
771{
772 if (a->af == ADDRESS_IP4)
773 {
774 ip4_address_t *i = (ip4_address_t *) & a->un.ip4;
775 i->as_u32 = v;
776 }
777}
778
Jakub Grajciar23a386b2020-02-26 11:01:43 +0100779void
780ip_set (ip46_address_t * dst, void *src, u8 is_ip4)
781{
782 if (is_ip4)
783 dst->ip4.as_u32 = ((ip4_address_t *) src)->as_u32;
784 else
785 clib_memcpy_fast (&dst->ip6, (ip6_address_t *) src,
786 sizeof (ip6_address_t));
787}
788
Neale Ranns097fa662018-05-01 05:17:55 -0700789static void
Mohsin Kazmi57938f62017-10-27 21:28:07 +0200790increment_mac_address (u8 * mac)
Damjan Marion7cd468a2016-12-19 23:05:39 +0100791{
Mohsin Kazmi57938f62017-10-27 21:28:07 +0200792 u64 tmp = *((u64 *) mac);
Damjan Marion7cd468a2016-12-19 23:05:39 +0100793 tmp = clib_net_to_host_u64 (tmp);
794 tmp += 1 << 16; /* skip unused (least significant) octets */
795 tmp = clib_host_to_net_u64 (tmp);
Mohsin Kazmi57938f62017-10-27 21:28:07 +0200796
797 clib_memcpy (mac, &tmp, 6);
Damjan Marion7cd468a2016-12-19 23:05:39 +0100798}
799
Neale Ranns097fa662018-05-01 05:17:55 -0700800static void
801vat_json_object_add_address (vat_json_node_t * node,
802 const char *str, const vl_api_address_t * addr)
803{
804 if (ADDRESS_IP6 == addr->af)
805 {
806 struct in6_addr ip6;
807
808 clib_memcpy (&ip6, &addr->un.ip6, sizeof (ip6));
809 vat_json_object_add_ip6 (node, str, ip6);
810 }
811 else
812 {
813 struct in_addr ip4;
814
815 clib_memcpy (&ip4, &addr->un.ip4, sizeof (ip4));
816 vat_json_object_add_ip4 (node, str, ip4);
817 }
818}
819
820static void
821vat_json_object_add_prefix (vat_json_node_t * node,
822 const vl_api_prefix_t * prefix)
823{
Paul Vinciguerraab055082019-06-06 14:07:55 -0400824 vat_json_object_add_uint (node, "len", prefix->len);
825 vat_json_object_add_address (node, "address", &prefix->address);
Neale Ranns097fa662018-05-01 05:17:55 -0700826}
827
Damjan Marion7cd468a2016-12-19 23:05:39 +0100828static void vl_api_create_loopback_reply_t_handler
829 (vl_api_create_loopback_reply_t * mp)
830{
831 vat_main_t *vam = &vat_main;
832 i32 retval = ntohl (mp->retval);
833
834 vam->retval = retval;
835 vam->regenerate_interface_table = 1;
836 vam->sw_if_index = ntohl (mp->sw_if_index);
837 vam->result_ready = 1;
838}
839
840static void vl_api_create_loopback_reply_t_handler_json
841 (vl_api_create_loopback_reply_t * mp)
842{
843 vat_main_t *vam = &vat_main;
844 vat_json_node_t node;
845
846 vat_json_init_object (&node);
847 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
848 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
849
850 vat_json_print (vam->ofp, &node);
851 vat_json_free (&node);
852 vam->retval = ntohl (mp->retval);
853 vam->result_ready = 1;
854}
855
Jon Loeligerc83c3b72017-02-23 13:57:35 -0600856static void vl_api_create_loopback_instance_reply_t_handler
857 (vl_api_create_loopback_instance_reply_t * mp)
858{
859 vat_main_t *vam = &vat_main;
860 i32 retval = ntohl (mp->retval);
861
862 vam->retval = retval;
863 vam->regenerate_interface_table = 1;
864 vam->sw_if_index = ntohl (mp->sw_if_index);
865 vam->result_ready = 1;
866}
867
868static void vl_api_create_loopback_instance_reply_t_handler_json
869 (vl_api_create_loopback_instance_reply_t * mp)
870{
871 vat_main_t *vam = &vat_main;
872 vat_json_node_t node;
873
874 vat_json_init_object (&node);
875 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
876 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
877
878 vat_json_print (vam->ofp, &node);
879 vat_json_free (&node);
880 vam->retval = ntohl (mp->retval);
881 vam->result_ready = 1;
882}
883
Damjan Marion7cd468a2016-12-19 23:05:39 +0100884static void vl_api_af_packet_create_reply_t_handler
885 (vl_api_af_packet_create_reply_t * mp)
886{
887 vat_main_t *vam = &vat_main;
888 i32 retval = ntohl (mp->retval);
889
890 vam->retval = retval;
891 vam->regenerate_interface_table = 1;
892 vam->sw_if_index = ntohl (mp->sw_if_index);
893 vam->result_ready = 1;
894}
895
896static void vl_api_af_packet_create_reply_t_handler_json
897 (vl_api_af_packet_create_reply_t * mp)
898{
899 vat_main_t *vam = &vat_main;
900 vat_json_node_t node;
901
902 vat_json_init_object (&node);
903 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
904 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
905
906 vat_json_print (vam->ofp, &node);
907 vat_json_free (&node);
908
909 vam->retval = ntohl (mp->retval);
910 vam->result_ready = 1;
911}
912
913static void vl_api_create_vlan_subif_reply_t_handler
914 (vl_api_create_vlan_subif_reply_t * mp)
915{
916 vat_main_t *vam = &vat_main;
917 i32 retval = ntohl (mp->retval);
918
919 vam->retval = retval;
920 vam->regenerate_interface_table = 1;
921 vam->sw_if_index = ntohl (mp->sw_if_index);
922 vam->result_ready = 1;
923}
924
925static void vl_api_create_vlan_subif_reply_t_handler_json
926 (vl_api_create_vlan_subif_reply_t * mp)
927{
928 vat_main_t *vam = &vat_main;
929 vat_json_node_t node;
930
931 vat_json_init_object (&node);
932 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
933 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
934
935 vat_json_print (vam->ofp, &node);
936 vat_json_free (&node);
937
938 vam->retval = ntohl (mp->retval);
939 vam->result_ready = 1;
940}
941
942static void vl_api_create_subif_reply_t_handler
943 (vl_api_create_subif_reply_t * mp)
944{
945 vat_main_t *vam = &vat_main;
946 i32 retval = ntohl (mp->retval);
947
948 vam->retval = retval;
949 vam->regenerate_interface_table = 1;
950 vam->sw_if_index = ntohl (mp->sw_if_index);
951 vam->result_ready = 1;
952}
953
954static void vl_api_create_subif_reply_t_handler_json
955 (vl_api_create_subif_reply_t * mp)
956{
957 vat_main_t *vam = &vat_main;
958 vat_json_node_t node;
959
960 vat_json_init_object (&node);
961 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
962 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
963
964 vat_json_print (vam->ofp, &node);
965 vat_json_free (&node);
966
967 vam->retval = ntohl (mp->retval);
968 vam->result_ready = 1;
969}
970
971static void vl_api_interface_name_renumber_reply_t_handler
972 (vl_api_interface_name_renumber_reply_t * mp)
973{
974 vat_main_t *vam = &vat_main;
975 i32 retval = ntohl (mp->retval);
976
977 vam->retval = retval;
978 vam->regenerate_interface_table = 1;
979 vam->result_ready = 1;
980}
981
982static void vl_api_interface_name_renumber_reply_t_handler_json
983 (vl_api_interface_name_renumber_reply_t * mp)
984{
985 vat_main_t *vam = &vat_main;
986 vat_json_node_t node;
987
988 vat_json_init_object (&node);
989 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
990
991 vat_json_print (vam->ofp, &node);
992 vat_json_free (&node);
993
994 vam->retval = ntohl (mp->retval);
995 vam->result_ready = 1;
996}
997
998/*
999 * Special-case: build the interface table, maintain
1000 * the next loopback sw_if_index vbl.
1001 */
1002static void vl_api_sw_interface_details_t_handler
1003 (vl_api_sw_interface_details_t * mp)
1004{
1005 vat_main_t *vam = &vat_main;
Ole Troane5ff5a32019-08-23 22:55:18 +02001006 u8 *s = format (0, "%s%c", mp->interface_name, 0);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001007
1008 hash_set_mem (vam->sw_if_index_by_interface_name, s,
1009 ntohl (mp->sw_if_index));
1010
1011 /* In sub interface case, fill the sub interface table entry */
1012 if (mp->sw_if_index != mp->sup_sw_if_index)
1013 {
1014 sw_interface_subif_t *sub = NULL;
1015
1016 vec_add2 (vam->sw_if_subif_table, sub, 1);
1017
1018 vec_validate (sub->interface_name, strlen ((char *) s) + 1);
1019 strncpy ((char *) sub->interface_name, (char *) s,
1020 vec_len (sub->interface_name));
1021 sub->sw_if_index = ntohl (mp->sw_if_index);
1022 sub->sub_id = ntohl (mp->sub_id);
1023
Jakub Grajciar053204a2019-03-18 13:17:53 +01001024 sub->raw_flags = ntohl (mp->sub_if_flags & SUB_IF_API_FLAG_MASK_VNET);
1025
Damjan Marion7cd468a2016-12-19 23:05:39 +01001026 sub->sub_number_of_tags = mp->sub_number_of_tags;
1027 sub->sub_outer_vlan_id = ntohs (mp->sub_outer_vlan_id);
1028 sub->sub_inner_vlan_id = ntohs (mp->sub_inner_vlan_id);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001029
1030 /* vlan tag rewrite */
1031 sub->vtr_op = ntohl (mp->vtr_op);
1032 sub->vtr_push_dot1q = ntohl (mp->vtr_push_dot1q);
1033 sub->vtr_tag1 = ntohl (mp->vtr_tag1);
1034 sub->vtr_tag2 = ntohl (mp->vtr_tag2);
1035 }
1036}
1037
1038static void vl_api_sw_interface_details_t_handler_json
1039 (vl_api_sw_interface_details_t * mp)
1040{
1041 vat_main_t *vam = &vat_main;
1042 vat_json_node_t *node = NULL;
1043
1044 if (VAT_JSON_ARRAY != vam->json_tree.type)
1045 {
1046 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
1047 vat_json_init_array (&vam->json_tree);
1048 }
1049 node = vat_json_array_add (&vam->json_tree);
1050
1051 vat_json_init_object (node);
1052 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
1053 vat_json_object_add_uint (node, "sup_sw_if_index",
1054 ntohl (mp->sup_sw_if_index));
Damjan Marion7cd468a2016-12-19 23:05:39 +01001055 vat_json_object_add_bytes (node, "l2_address", mp->l2_address,
1056 sizeof (mp->l2_address));
1057 vat_json_object_add_string_copy (node, "interface_name",
Ole Troane5ff5a32019-08-23 22:55:18 +02001058 mp->interface_name);
Mohsin Kazmide312c22019-09-27 13:44:28 +02001059 vat_json_object_add_string_copy (node, "interface_dev_type",
1060 mp->interface_dev_type);
Jakub Grajciar053204a2019-03-18 13:17:53 +01001061 vat_json_object_add_uint (node, "flags", mp->flags);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001062 vat_json_object_add_uint (node, "link_duplex", mp->link_duplex);
1063 vat_json_object_add_uint (node, "link_speed", mp->link_speed);
Damjan Marionfe7d4a22018-04-13 19:43:39 +02001064 vat_json_object_add_uint (node, "mtu", ntohs (mp->link_mtu));
Damjan Marion7cd468a2016-12-19 23:05:39 +01001065 vat_json_object_add_uint (node, "sub_id", ntohl (mp->sub_id));
Damjan Marion7cd468a2016-12-19 23:05:39 +01001066 vat_json_object_add_uint (node, "sub_number_of_tags",
1067 mp->sub_number_of_tags);
1068 vat_json_object_add_uint (node, "sub_outer_vlan_id",
1069 ntohs (mp->sub_outer_vlan_id));
1070 vat_json_object_add_uint (node, "sub_inner_vlan_id",
1071 ntohs (mp->sub_inner_vlan_id));
Jakub Grajciar053204a2019-03-18 13:17:53 +01001072 vat_json_object_add_uint (node, "sub_if_flags", ntohl (mp->sub_if_flags));
Damjan Marion7cd468a2016-12-19 23:05:39 +01001073 vat_json_object_add_uint (node, "vtr_op", ntohl (mp->vtr_op));
1074 vat_json_object_add_uint (node, "vtr_push_dot1q",
1075 ntohl (mp->vtr_push_dot1q));
1076 vat_json_object_add_uint (node, "vtr_tag1", ntohl (mp->vtr_tag1));
1077 vat_json_object_add_uint (node, "vtr_tag2", ntohl (mp->vtr_tag2));
Jakub Grajciar053204a2019-03-18 13:17:53 +01001078 if (ntohl (mp->sub_if_flags) & SUB_IF_API_FLAG_DOT1AH)
Pavel Kotucek65e84572017-01-16 17:01:56 +01001079 {
1080 vat_json_object_add_string_copy (node, "pbb_vtr_dmac",
1081 format (0, "%U",
1082 format_ethernet_address,
1083 &mp->b_dmac));
1084 vat_json_object_add_string_copy (node, "pbb_vtr_smac",
1085 format (0, "%U",
1086 format_ethernet_address,
1087 &mp->b_smac));
1088 vat_json_object_add_uint (node, "pbb_vtr_b_vlanid", mp->b_vlanid);
1089 vat_json_object_add_uint (node, "pbb_vtr_i_sid", mp->i_sid);
1090 }
Damjan Marion7cd468a2016-12-19 23:05:39 +01001091}
1092
Dave Baracha1a093d2017-03-02 13:13:23 -05001093#if VPP_API_TEST_BUILTIN == 0
Neale Rannsa07bd702017-08-07 07:53:49 -07001094static void vl_api_sw_interface_event_t_handler
1095 (vl_api_sw_interface_event_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +01001096{
1097 vat_main_t *vam = &vat_main;
1098 if (vam->interface_event_display)
1099 errmsg ("interface flags: sw_if_index %d %s %s",
1100 ntohl (mp->sw_if_index),
Jakub Grajciar053204a2019-03-18 13:17:53 +01001101 ((ntohl (mp->flags)) & IF_STATUS_API_FLAG_ADMIN_UP) ?
1102 "admin-up" : "admin-down",
1103 ((ntohl (mp->flags)) & IF_STATUS_API_FLAG_LINK_UP) ?
1104 "link-up" : "link-down");
Damjan Marion7cd468a2016-12-19 23:05:39 +01001105}
Dave Baracha1a093d2017-03-02 13:13:23 -05001106#endif
Damjan Marion7cd468a2016-12-19 23:05:39 +01001107
Benoît Ganne49ee6842019-04-30 11:50:46 +02001108__clib_unused static void
1109vl_api_sw_interface_event_t_handler_json (vl_api_sw_interface_event_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +01001110{
1111 /* JSON output not supported */
1112}
1113
1114static void
1115vl_api_cli_reply_t_handler (vl_api_cli_reply_t * mp)
1116{
1117 vat_main_t *vam = &vat_main;
1118 i32 retval = ntohl (mp->retval);
1119
1120 vam->retval = retval;
Damjan Marion7bee80c2017-04-26 15:32:12 +02001121 vam->shmem_result = uword_to_pointer (mp->reply_in_shmem, u8 *);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001122 vam->result_ready = 1;
1123}
1124
1125static void
1126vl_api_cli_reply_t_handler_json (vl_api_cli_reply_t * mp)
1127{
1128 vat_main_t *vam = &vat_main;
1129 vat_json_node_t node;
Damjan Marion7cd468a2016-12-19 23:05:39 +01001130 void *oldheap;
1131 u8 *reply;
1132
1133 vat_json_init_object (&node);
1134 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1135 vat_json_object_add_uint (&node, "reply_in_shmem",
1136 ntohl (mp->reply_in_shmem));
1137 /* Toss the shared-memory original... */
Nathan Skrzypczak0aa40132019-11-25 16:29:38 +01001138 oldheap = vl_msg_push_heap ();
Damjan Marion7cd468a2016-12-19 23:05:39 +01001139
Damjan Marion7bee80c2017-04-26 15:32:12 +02001140 reply = uword_to_pointer (mp->reply_in_shmem, u8 *);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001141 vec_free (reply);
1142
Nathan Skrzypczak0aa40132019-11-25 16:29:38 +01001143 vl_msg_pop_heap (oldheap);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001144
1145 vat_json_print (vam->ofp, &node);
1146 vat_json_free (&node);
1147
1148 vam->retval = ntohl (mp->retval);
1149 vam->result_ready = 1;
1150}
1151
1152static void
1153vl_api_cli_inband_reply_t_handler (vl_api_cli_inband_reply_t * mp)
1154{
1155 vat_main_t *vam = &vat_main;
1156 i32 retval = ntohl (mp->retval);
Dave Barach59b25652017-09-10 15:04:27 -04001157
1158 vec_reset_length (vam->cmd_reply);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001159
1160 vam->retval = retval;
Dave Barach59b25652017-09-10 15:04:27 -04001161 if (retval == 0)
Dave Barach77841402020-04-29 17:04:10 -04001162 vam->cmd_reply = vl_api_from_api_to_new_vec (mp, &mp->reply);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001163 vam->result_ready = 1;
1164}
1165
1166static void
1167vl_api_cli_inband_reply_t_handler_json (vl_api_cli_inband_reply_t * mp)
1168{
1169 vat_main_t *vam = &vat_main;
1170 vat_json_node_t node;
Jakub Grajciar2dbee932020-02-07 11:30:26 +01001171 u8 *reply = 0; /* reply vector */
Damjan Marion7cd468a2016-12-19 23:05:39 +01001172
Dave Barach77841402020-04-29 17:04:10 -04001173 reply = vl_api_from_api_to_new_vec (mp, &mp->reply);
Dave Barach59b25652017-09-10 15:04:27 -04001174 vec_reset_length (vam->cmd_reply);
1175
Damjan Marion7cd468a2016-12-19 23:05:39 +01001176 vat_json_init_object (&node);
1177 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
Jakub Grajciar2dbee932020-02-07 11:30:26 +01001178 vat_json_object_add_string_copy (&node, "reply", reply);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001179
1180 vat_json_print (vam->ofp, &node);
1181 vat_json_free (&node);
Jakub Grajciar2dbee932020-02-07 11:30:26 +01001182 vec_free (reply);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001183
1184 vam->retval = ntohl (mp->retval);
1185 vam->result_ready = 1;
1186}
1187
1188static void vl_api_classify_add_del_table_reply_t_handler
1189 (vl_api_classify_add_del_table_reply_t * mp)
1190{
1191 vat_main_t *vam = &vat_main;
1192 i32 retval = ntohl (mp->retval);
1193 if (vam->async_mode)
1194 {
1195 vam->async_errors += (retval < 0);
1196 }
1197 else
1198 {
1199 vam->retval = retval;
1200 if (retval == 0 &&
1201 ((mp->new_table_index != 0xFFFFFFFF) ||
1202 (mp->skip_n_vectors != 0xFFFFFFFF) ||
1203 (mp->match_n_vectors != 0xFFFFFFFF)))
1204 /*
1205 * Note: this is just barely thread-safe, depends on
1206 * the main thread spinning waiting for an answer...
1207 */
1208 errmsg ("new index %d, skip_n_vectors %d, match_n_vectors %d",
1209 ntohl (mp->new_table_index),
1210 ntohl (mp->skip_n_vectors), ntohl (mp->match_n_vectors));
1211 vam->result_ready = 1;
1212 }
1213}
1214
1215static void vl_api_classify_add_del_table_reply_t_handler_json
1216 (vl_api_classify_add_del_table_reply_t * mp)
1217{
1218 vat_main_t *vam = &vat_main;
1219 vat_json_node_t node;
1220
1221 vat_json_init_object (&node);
1222 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1223 vat_json_object_add_uint (&node, "new_table_index",
1224 ntohl (mp->new_table_index));
1225 vat_json_object_add_uint (&node, "skip_n_vectors",
1226 ntohl (mp->skip_n_vectors));
1227 vat_json_object_add_uint (&node, "match_n_vectors",
1228 ntohl (mp->match_n_vectors));
1229
1230 vat_json_print (vam->ofp, &node);
1231 vat_json_free (&node);
1232
1233 vam->retval = ntohl (mp->retval);
1234 vam->result_ready = 1;
1235}
1236
1237static void vl_api_get_node_index_reply_t_handler
1238 (vl_api_get_node_index_reply_t * mp)
1239{
1240 vat_main_t *vam = &vat_main;
1241 i32 retval = ntohl (mp->retval);
1242 if (vam->async_mode)
1243 {
1244 vam->async_errors += (retval < 0);
1245 }
1246 else
1247 {
1248 vam->retval = retval;
1249 if (retval == 0)
1250 errmsg ("node index %d", ntohl (mp->node_index));
1251 vam->result_ready = 1;
1252 }
1253}
1254
1255static void vl_api_get_node_index_reply_t_handler_json
1256 (vl_api_get_node_index_reply_t * mp)
1257{
1258 vat_main_t *vam = &vat_main;
1259 vat_json_node_t node;
1260
1261 vat_json_init_object (&node);
1262 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1263 vat_json_object_add_uint (&node, "node_index", ntohl (mp->node_index));
1264
1265 vat_json_print (vam->ofp, &node);
1266 vat_json_free (&node);
1267
1268 vam->retval = ntohl (mp->retval);
1269 vam->result_ready = 1;
1270}
1271
1272static void vl_api_get_next_index_reply_t_handler
1273 (vl_api_get_next_index_reply_t * mp)
1274{
1275 vat_main_t *vam = &vat_main;
1276 i32 retval = ntohl (mp->retval);
1277 if (vam->async_mode)
1278 {
1279 vam->async_errors += (retval < 0);
1280 }
1281 else
1282 {
1283 vam->retval = retval;
1284 if (retval == 0)
1285 errmsg ("next node index %d", ntohl (mp->next_index));
1286 vam->result_ready = 1;
1287 }
1288}
1289
1290static void vl_api_get_next_index_reply_t_handler_json
1291 (vl_api_get_next_index_reply_t * mp)
1292{
1293 vat_main_t *vam = &vat_main;
1294 vat_json_node_t node;
1295
1296 vat_json_init_object (&node);
1297 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1298 vat_json_object_add_uint (&node, "next_index", ntohl (mp->next_index));
1299
1300 vat_json_print (vam->ofp, &node);
1301 vat_json_free (&node);
1302
1303 vam->retval = ntohl (mp->retval);
1304 vam->result_ready = 1;
1305}
1306
1307static void vl_api_add_node_next_reply_t_handler
1308 (vl_api_add_node_next_reply_t * mp)
1309{
1310 vat_main_t *vam = &vat_main;
1311 i32 retval = ntohl (mp->retval);
1312 if (vam->async_mode)
1313 {
1314 vam->async_errors += (retval < 0);
1315 }
1316 else
1317 {
1318 vam->retval = retval;
1319 if (retval == 0)
1320 errmsg ("next index %d", ntohl (mp->next_index));
1321 vam->result_ready = 1;
1322 }
1323}
1324
1325static void vl_api_add_node_next_reply_t_handler_json
1326 (vl_api_add_node_next_reply_t * mp)
1327{
1328 vat_main_t *vam = &vat_main;
1329 vat_json_node_t node;
1330
1331 vat_json_init_object (&node);
1332 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1333 vat_json_object_add_uint (&node, "next_index", ntohl (mp->next_index));
1334
1335 vat_json_print (vam->ofp, &node);
1336 vat_json_free (&node);
1337
1338 vam->retval = ntohl (mp->retval);
1339 vam->result_ready = 1;
1340}
1341
1342static void vl_api_show_version_reply_t_handler
1343 (vl_api_show_version_reply_t * mp)
1344{
1345 vat_main_t *vam = &vat_main;
1346 i32 retval = ntohl (mp->retval);
1347
1348 if (retval >= 0)
1349 {
Ole Troane5ff5a32019-08-23 22:55:18 +02001350 errmsg (" program: %s", mp->program);
1351 errmsg (" version: %s", mp->version);
1352 errmsg (" build date: %s", mp->build_date);
1353 errmsg ("build directory: %s", mp->build_directory);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001354 }
1355 vam->retval = retval;
1356 vam->result_ready = 1;
1357}
1358
1359static void vl_api_show_version_reply_t_handler_json
1360 (vl_api_show_version_reply_t * mp)
1361{
1362 vat_main_t *vam = &vat_main;
1363 vat_json_node_t node;
1364
1365 vat_json_init_object (&node);
1366 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
Ole Troane5ff5a32019-08-23 22:55:18 +02001367 vat_json_object_add_string_copy (&node, "program", mp->program);
1368 vat_json_object_add_string_copy (&node, "version", mp->version);
1369 vat_json_object_add_string_copy (&node, "build_date", mp->build_date);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001370 vat_json_object_add_string_copy (&node, "build_directory",
Ole Troane5ff5a32019-08-23 22:55:18 +02001371 mp->build_directory);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001372
1373 vat_json_print (vam->ofp, &node);
1374 vat_json_free (&node);
1375
1376 vam->retval = ntohl (mp->retval);
1377 vam->result_ready = 1;
1378}
1379
Mohsin Kazmi5d64c782018-09-11 20:27:09 +02001380static void vl_api_show_threads_reply_t_handler
1381 (vl_api_show_threads_reply_t * mp)
1382{
1383 vat_main_t *vam = &vat_main;
1384 i32 retval = ntohl (mp->retval);
1385 int i, count = 0;
1386
1387 if (retval >= 0)
1388 count = ntohl (mp->count);
1389
1390 for (i = 0; i < count; i++)
1391 print (vam->ofp,
1392 "\n%-2d %-11s %-11s %-5d %-6d %-4d %-6d",
1393 ntohl (mp->thread_data[i].id), mp->thread_data[i].name,
1394 mp->thread_data[i].type, ntohl (mp->thread_data[i].pid),
1395 ntohl (mp->thread_data[i].cpu_id), ntohl (mp->thread_data[i].core),
1396 ntohl (mp->thread_data[i].cpu_socket));
1397
1398 vam->retval = retval;
1399 vam->result_ready = 1;
1400}
1401
1402static void vl_api_show_threads_reply_t_handler_json
1403 (vl_api_show_threads_reply_t * mp)
1404{
1405 vat_main_t *vam = &vat_main;
1406 vat_json_node_t node;
1407 vl_api_thread_data_t *td;
Mohsin Kazmi5df628b2018-10-01 17:41:08 +02001408 i32 retval = ntohl (mp->retval);
1409 int i, count = 0;
1410
1411 if (retval >= 0)
1412 count = ntohl (mp->count);
Mohsin Kazmi5d64c782018-09-11 20:27:09 +02001413
1414 vat_json_init_object (&node);
Mohsin Kazmi5df628b2018-10-01 17:41:08 +02001415 vat_json_object_add_int (&node, "retval", retval);
Mohsin Kazmi5d64c782018-09-11 20:27:09 +02001416 vat_json_object_add_uint (&node, "count", count);
1417
1418 for (i = 0; i < count; i++)
1419 {
1420 td = &mp->thread_data[i];
1421 vat_json_object_add_uint (&node, "id", ntohl (td->id));
1422 vat_json_object_add_string_copy (&node, "name", td->name);
1423 vat_json_object_add_string_copy (&node, "type", td->type);
1424 vat_json_object_add_uint (&node, "pid", ntohl (td->pid));
1425 vat_json_object_add_int (&node, "cpu_id", ntohl (td->cpu_id));
1426 vat_json_object_add_int (&node, "core", ntohl (td->id));
1427 vat_json_object_add_int (&node, "cpu_socket", ntohl (td->cpu_socket));
1428 }
1429
1430 vat_json_print (vam->ofp, &node);
1431 vat_json_free (&node);
1432
Mohsin Kazmi5df628b2018-10-01 17:41:08 +02001433 vam->retval = retval;
Mohsin Kazmi5d64c782018-09-11 20:27:09 +02001434 vam->result_ready = 1;
1435}
1436
1437static int
1438api_show_threads (vat_main_t * vam)
1439{
1440 vl_api_show_threads_t *mp;
1441 int ret;
1442
1443 print (vam->ofp,
1444 "\n%-2s %-11s %-11s %-5s %-6s %-4s %-6s",
1445 "ID", "Name", "Type", "LWP", "cpu_id", "Core", "Socket");
1446
1447 M (SHOW_THREADS, mp);
1448
1449 S (mp);
1450 W (ret);
1451 return ret;
1452}
1453
Damjan Marion7cd468a2016-12-19 23:05:39 +01001454static void
John Lo8d00fff2017-08-03 00:35:36 -04001455vl_api_l2_macs_event_t_handler (vl_api_l2_macs_event_t * mp)
1456{
1457 u32 n_macs = ntohl (mp->n_macs);
Paul Vinciguerraec11b132018-09-24 05:25:00 -07001458 errmsg ("L2MAC event received with pid %d cl-idx %d for %d macs: \n",
John Lo8d00fff2017-08-03 00:35:36 -04001459 ntohl (mp->pid), mp->client_index, n_macs);
1460 int i;
1461 for (i = 0; i < n_macs; i++)
1462 {
1463 vl_api_mac_entry_t *mac = &mp->mac[i];
John Loe23c99e2018-03-13 21:53:18 -04001464 errmsg (" [%d] sw_if_index %d mac_addr %U action %d \n",
John Lo8d00fff2017-08-03 00:35:36 -04001465 i + 1, ntohl (mac->sw_if_index),
John Loe23c99e2018-03-13 21:53:18 -04001466 format_ethernet_address, mac->mac_addr, mac->action);
John Lo8d00fff2017-08-03 00:35:36 -04001467 if (i == 1000)
1468 break;
1469 }
1470}
1471
1472static void
1473vl_api_l2_macs_event_t_handler_json (vl_api_l2_macs_event_t * mp)
1474{
1475 /* JSON output not supported */
1476}
1477
Ole Troan01384fe2017-05-12 11:55:35 +02001478#define vl_api_bridge_domain_details_t_endian vl_noop_handler
1479#define vl_api_bridge_domain_details_t_print vl_noop_handler
1480
Damjan Marion7cd468a2016-12-19 23:05:39 +01001481/*
1482 * Special-case: build the bridge domain table, maintain
1483 * the next bd id vbl.
1484 */
1485static void vl_api_bridge_domain_details_t_handler
1486 (vl_api_bridge_domain_details_t * mp)
1487{
1488 vat_main_t *vam = &vat_main;
1489 u32 n_sw_ifs = ntohl (mp->n_sw_ifs);
Ole Troan01384fe2017-05-12 11:55:35 +02001490 int i;
Damjan Marion7cd468a2016-12-19 23:05:39 +01001491
Mohsin Kazmi762d83c2018-09-27 15:00:32 +02001492 print (vam->ofp, "\n%-3s %-3s %-3s %-3s %-3s %-6s %-3s",
1493 " ID", "LRN", "FWD", "FLD", "BVI", "UU-FWD", "#IF");
Damjan Marion7cd468a2016-12-19 23:05:39 +01001494
Mohsin Kazmi762d83c2018-09-27 15:00:32 +02001495 print (vam->ofp, "%3d %3d %3d %3d %3d %6d %3d",
Damjan Marion7cd468a2016-12-19 23:05:39 +01001496 ntohl (mp->bd_id), mp->learn, mp->forward,
Mohsin Kazmi762d83c2018-09-27 15:00:32 +02001497 mp->flood, ntohl (mp->bvi_sw_if_index),
1498 ntohl (mp->uu_fwd_sw_if_index), n_sw_ifs);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001499
1500 if (n_sw_ifs)
Ole Troan01384fe2017-05-12 11:55:35 +02001501 {
1502 vl_api_bridge_domain_sw_if_t *sw_ifs;
1503 print (vam->ofp, "\n\n%s %s %s", "sw_if_index", "SHG",
1504 "Interface Name");
1505
1506 sw_ifs = mp->sw_if_details;
1507 for (i = 0; i < n_sw_ifs; i++)
1508 {
1509 u8 *sw_if_name = 0;
1510 u32 sw_if_index;
1511 hash_pair_t *p;
1512
1513 sw_if_index = ntohl (sw_ifs->sw_if_index);
1514
1515 /* *INDENT-OFF* */
1516 hash_foreach_pair (p, vam->sw_if_index_by_interface_name,
1517 ({
1518 if ((u32) p->value[0] == sw_if_index)
1519 {
1520 sw_if_name = (u8 *)(p->key);
1521 break;
1522 }
1523 }));
1524 /* *INDENT-ON* */
1525 print (vam->ofp, "%7d %3d %s", sw_if_index,
1526 sw_ifs->shg, sw_if_name ? (char *) sw_if_name :
1527 "sw_if_index not found!");
1528
1529 sw_ifs++;
1530 }
1531 }
Damjan Marion7cd468a2016-12-19 23:05:39 +01001532}
1533
1534static void vl_api_bridge_domain_details_t_handler_json
1535 (vl_api_bridge_domain_details_t * mp)
1536{
1537 vat_main_t *vam = &vat_main;
1538 vat_json_node_t *node, *array = NULL;
Ole Troan01384fe2017-05-12 11:55:35 +02001539 u32 n_sw_ifs = ntohl (mp->n_sw_ifs);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001540
1541 if (VAT_JSON_ARRAY != vam->json_tree.type)
1542 {
1543 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
1544 vat_json_init_array (&vam->json_tree);
1545 }
1546 node = vat_json_array_add (&vam->json_tree);
1547
1548 vat_json_init_object (node);
1549 vat_json_object_add_uint (node, "bd_id", ntohl (mp->bd_id));
1550 vat_json_object_add_uint (node, "flood", mp->flood);
1551 vat_json_object_add_uint (node, "forward", mp->forward);
1552 vat_json_object_add_uint (node, "learn", mp->learn);
1553 vat_json_object_add_uint (node, "bvi_sw_if_index",
1554 ntohl (mp->bvi_sw_if_index));
Ole Troan01384fe2017-05-12 11:55:35 +02001555 vat_json_object_add_uint (node, "n_sw_ifs", n_sw_ifs);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001556 array = vat_json_object_add (node, "sw_if");
1557 vat_json_init_array (array);
Damjan Marion7cd468a2016-12-19 23:05:39 +01001558
Damjan Marion7cd468a2016-12-19 23:05:39 +01001559
Damjan Marion7cd468a2016-12-19 23:05:39 +01001560
Ole Troan01384fe2017-05-12 11:55:35 +02001561 if (n_sw_ifs)
1562 {
1563 vl_api_bridge_domain_sw_if_t *sw_ifs;
1564 int i;
Damjan Marion7cd468a2016-12-19 23:05:39 +01001565
Ole Troan01384fe2017-05-12 11:55:35 +02001566 sw_ifs = mp->sw_if_details;
1567 for (i = 0; i < n_sw_ifs; i++)
1568 {
1569 node = vat_json_array_add (array);
1570 vat_json_init_object (node);
1571 vat_json_object_add_uint (node, "sw_if_index",
1572 ntohl (sw_ifs->sw_if_index));
1573 vat_json_object_add_uint (node, "shg", sw_ifs->shg);
1574 sw_ifs++;
1575 }
1576 }
Damjan Marion7cd468a2016-12-19 23:05:39 +01001577}
1578
1579static void vl_api_control_ping_reply_t_handler
1580 (vl_api_control_ping_reply_t * mp)
1581{
1582 vat_main_t *vam = &vat_main;
1583 i32 retval = ntohl (mp->retval);
1584 if (vam->async_mode)
1585 {
1586 vam->async_errors += (retval < 0);
1587 }
1588 else
1589 {
1590 vam->retval = retval;
1591 vam->result_ready = 1;
1592 }
Florin Coras90a63982017-12-19 04:50:01 -08001593 if (vam->socket_client_main)
1594 vam->socket_client_main->control_pings_outstanding--;
Damjan Marion7cd468a2016-12-19 23:05:39 +01001595}
1596
1597static void vl_api_control_ping_reply_t_handler_json
1598 (vl_api_control_ping_reply_t * mp)
1599{
1600 vat_main_t *vam = &vat_main;
1601 i32 retval = ntohl (mp->retval);
1602
1603 if (VAT_JSON_NONE != vam->json_tree.type)
1604 {
1605 vat_json_print (vam->ofp, &vam->json_tree);
1606 vat_json_free (&vam->json_tree);
1607 vam->json_tree.type = VAT_JSON_NONE;
1608 }
1609 else
1610 {
1611 /* just print [] */
1612 vat_json_init_array (&vam->json_tree);
1613 vat_json_print (vam->ofp, &vam->json_tree);
1614 vam->json_tree.type = VAT_JSON_NONE;
1615 }
1616
1617 vam->retval = retval;
1618 vam->result_ready = 1;
1619}
1620
1621static void
Eyal Barifead6702017-04-04 04:46:32 +03001622 vl_api_bridge_domain_set_mac_age_reply_t_handler
1623 (vl_api_bridge_domain_set_mac_age_reply_t * mp)
1624{
1625 vat_main_t *vam = &vat_main;
1626 i32 retval = ntohl (mp->retval);
1627 if (vam->async_mode)
1628 {
1629 vam->async_errors += (retval < 0);
1630 }
1631 else
1632 {
1633 vam->retval = retval;
1634 vam->result_ready = 1;
1635 }
1636}
1637
1638static void vl_api_bridge_domain_set_mac_age_reply_t_handler_json
1639 (vl_api_bridge_domain_set_mac_age_reply_t * mp)
1640{
1641 vat_main_t *vam = &vat_main;
1642 vat_json_node_t node;
1643
1644 vat_json_init_object (&node);
1645 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1646
1647 vat_json_print (vam->ofp, &node);
1648 vat_json_free (&node);
1649
1650 vam->retval = ntohl (mp->retval);
1651 vam->result_ready = 1;
1652}
1653
1654static void
Damjan Marion7cd468a2016-12-19 23:05:39 +01001655vl_api_l2_flags_reply_t_handler (vl_api_l2_flags_reply_t * mp)
1656{
1657 vat_main_t *vam = &vat_main;
1658 i32 retval = ntohl (mp->retval);
1659 if (vam->async_mode)
1660 {
1661 vam->async_errors += (retval < 0);
1662 }
1663 else
1664 {
1665 vam->retval = retval;
1666 vam->result_ready = 1;
1667 }
1668}
1669
1670static void vl_api_l2_flags_reply_t_handler_json
1671 (vl_api_l2_flags_reply_t * mp)
1672{
1673 vat_main_t *vam = &vat_main;
1674 vat_json_node_t node;
1675
1676 vat_json_init_object (&node);
1677 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1678 vat_json_object_add_uint (&node, "resulting_feature_bitmap",
1679 ntohl (mp->resulting_feature_bitmap));
1680
1681 vat_json_print (vam->ofp, &node);
1682 vat_json_free (&node);
1683
1684 vam->retval = ntohl (mp->retval);
1685 vam->result_ready = 1;
1686}
1687
1688static void vl_api_bridge_flags_reply_t_handler
1689 (vl_api_bridge_flags_reply_t * mp)
1690{
1691 vat_main_t *vam = &vat_main;
1692 i32 retval = ntohl (mp->retval);
1693 if (vam->async_mode)
1694 {
1695 vam->async_errors += (retval < 0);
1696 }
1697 else
1698 {
1699 vam->retval = retval;
1700 vam->result_ready = 1;
1701 }
1702}
1703
1704static void vl_api_bridge_flags_reply_t_handler_json
1705 (vl_api_bridge_flags_reply_t * mp)
1706{
1707 vat_main_t *vam = &vat_main;
1708 vat_json_node_t node;
1709
1710 vat_json_init_object (&node);
1711 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1712 vat_json_object_add_uint (&node, "resulting_feature_bitmap",
1713 ntohl (mp->resulting_feature_bitmap));
1714
1715 vat_json_print (vam->ofp, &node);
1716 vat_json_free (&node);
1717
1718 vam->retval = ntohl (mp->retval);
1719 vam->result_ready = 1;
1720}
1721
Damjan Marion8389fb92017-10-13 18:29:53 +02001722static void
1723vl_api_tap_create_v2_reply_t_handler (vl_api_tap_create_v2_reply_t * mp)
1724{
1725 vat_main_t *vam = &vat_main;
1726 i32 retval = ntohl (mp->retval);
1727 if (vam->async_mode)
1728 {
1729 vam->async_errors += (retval < 0);
1730 }
1731 else
1732 {
1733 vam->retval = retval;
1734 vam->sw_if_index = ntohl (mp->sw_if_index);
1735 vam->result_ready = 1;
1736 }
1737
1738}
1739
1740static void vl_api_tap_create_v2_reply_t_handler_json
1741 (vl_api_tap_create_v2_reply_t * mp)
1742{
1743 vat_main_t *vam = &vat_main;
1744 vat_json_node_t node;
1745
1746 vat_json_init_object (&node);
1747 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1748 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
1749
1750 vat_json_print (vam->ofp, &node);
1751 vat_json_free (&node);
1752
1753 vam->retval = ntohl (mp->retval);
1754 vam->result_ready = 1;
1755
1756}
1757
1758static void
1759vl_api_tap_delete_v2_reply_t_handler (vl_api_tap_delete_v2_reply_t * mp)
1760{
1761 vat_main_t *vam = &vat_main;
1762 i32 retval = ntohl (mp->retval);
1763 if (vam->async_mode)
1764 {
1765 vam->async_errors += (retval < 0);
1766 }
1767 else
1768 {
1769 vam->retval = retval;
1770 vam->result_ready = 1;
1771 }
1772}
1773
1774static void vl_api_tap_delete_v2_reply_t_handler_json
1775 (vl_api_tap_delete_v2_reply_t * mp)
1776{
1777 vat_main_t *vam = &vat_main;
1778 vat_json_node_t node;
1779
1780 vat_json_init_object (&node);
1781 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1782
1783 vat_json_print (vam->ofp, &node);
1784 vat_json_free (&node);
1785
1786 vam->retval = ntohl (mp->retval);
1787 vam->result_ready = 1;
1788}
1789
Steven9cd2d7a2017-12-20 12:43:01 -08001790static void
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01001791vl_api_virtio_pci_create_reply_t_handler (vl_api_virtio_pci_create_reply_t *
1792 mp)
1793{
1794 vat_main_t *vam = &vat_main;
1795 i32 retval = ntohl (mp->retval);
1796 if (vam->async_mode)
1797 {
1798 vam->async_errors += (retval < 0);
1799 }
1800 else
1801 {
1802 vam->retval = retval;
1803 vam->sw_if_index = ntohl (mp->sw_if_index);
1804 vam->result_ready = 1;
1805 }
1806}
1807
1808static void vl_api_virtio_pci_create_reply_t_handler_json
1809 (vl_api_virtio_pci_create_reply_t * mp)
1810{
1811 vat_main_t *vam = &vat_main;
1812 vat_json_node_t node;
1813
1814 vat_json_init_object (&node);
1815 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1816 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
1817
1818 vat_json_print (vam->ofp, &node);
1819 vat_json_free (&node);
1820
1821 vam->retval = ntohl (mp->retval);
1822 vam->result_ready = 1;
1823
1824}
1825
1826static void
Mohsin Kazmi518251b2020-09-01 17:17:44 +00001827 vl_api_virtio_pci_create_v2_reply_t_handler
1828 (vl_api_virtio_pci_create_v2_reply_t * mp)
1829{
1830 vat_main_t *vam = &vat_main;
1831 i32 retval = ntohl (mp->retval);
1832 if (vam->async_mode)
1833 {
1834 vam->async_errors += (retval < 0);
1835 }
1836 else
1837 {
1838 vam->retval = retval;
1839 vam->sw_if_index = ntohl (mp->sw_if_index);
1840 vam->result_ready = 1;
1841 }
1842}
1843
1844static void vl_api_virtio_pci_create_v2_reply_t_handler_json
1845 (vl_api_virtio_pci_create_v2_reply_t * mp)
1846{
1847 vat_main_t *vam = &vat_main;
1848 vat_json_node_t node;
1849
1850 vat_json_init_object (&node);
1851 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1852 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
1853
1854 vat_json_print (vam->ofp, &node);
1855 vat_json_free (&node);
1856
1857 vam->retval = ntohl (mp->retval);
1858 vam->result_ready = 1;
1859}
1860
1861static void
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01001862vl_api_virtio_pci_delete_reply_t_handler (vl_api_virtio_pci_delete_reply_t *
1863 mp)
1864{
1865 vat_main_t *vam = &vat_main;
1866 i32 retval = ntohl (mp->retval);
1867 if (vam->async_mode)
1868 {
1869 vam->async_errors += (retval < 0);
1870 }
1871 else
1872 {
1873 vam->retval = retval;
1874 vam->result_ready = 1;
1875 }
1876}
1877
1878static void vl_api_virtio_pci_delete_reply_t_handler_json
1879 (vl_api_virtio_pci_delete_reply_t * mp)
1880{
1881 vat_main_t *vam = &vat_main;
1882 vat_json_node_t node;
1883
1884 vat_json_init_object (&node);
1885 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1886
1887 vat_json_print (vam->ofp, &node);
1888 vat_json_free (&node);
1889
1890 vam->retval = ntohl (mp->retval);
1891 vam->result_ready = 1;
1892}
1893
1894static void
Steven9cd2d7a2017-12-20 12:43:01 -08001895vl_api_bond_create_reply_t_handler (vl_api_bond_create_reply_t * mp)
1896{
1897 vat_main_t *vam = &vat_main;
1898 i32 retval = ntohl (mp->retval);
1899
1900 if (vam->async_mode)
1901 {
1902 vam->async_errors += (retval < 0);
1903 }
1904 else
1905 {
1906 vam->retval = retval;
1907 vam->sw_if_index = ntohl (mp->sw_if_index);
1908 vam->result_ready = 1;
1909 }
1910}
1911
1912static void vl_api_bond_create_reply_t_handler_json
1913 (vl_api_bond_create_reply_t * mp)
1914{
1915 vat_main_t *vam = &vat_main;
1916 vat_json_node_t node;
1917
1918 vat_json_init_object (&node);
1919 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1920 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
1921
1922 vat_json_print (vam->ofp, &node);
1923 vat_json_free (&node);
1924
1925 vam->retval = ntohl (mp->retval);
1926 vam->result_ready = 1;
1927}
1928
1929static void
Steven Luongea717862020-07-30 07:31:40 -07001930vl_api_bond_create2_reply_t_handler (vl_api_bond_create2_reply_t * mp)
1931{
1932 vat_main_t *vam = &vat_main;
1933 i32 retval = ntohl (mp->retval);
1934
1935 if (vam->async_mode)
1936 {
1937 vam->async_errors += (retval < 0);
1938 }
1939 else
1940 {
1941 vam->retval = retval;
1942 vam->sw_if_index = ntohl (mp->sw_if_index);
1943 vam->result_ready = 1;
1944 }
1945}
1946
1947static void vl_api_bond_create2_reply_t_handler_json
1948 (vl_api_bond_create2_reply_t * mp)
1949{
1950 vat_main_t *vam = &vat_main;
1951 vat_json_node_t node;
1952
1953 vat_json_init_object (&node);
1954 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1955 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
1956
1957 vat_json_print (vam->ofp, &node);
1958 vat_json_free (&node);
1959
1960 vam->retval = ntohl (mp->retval);
1961 vam->result_ready = 1;
1962}
1963
1964static void
Steven9cd2d7a2017-12-20 12:43:01 -08001965vl_api_bond_delete_reply_t_handler (vl_api_bond_delete_reply_t * mp)
1966{
1967 vat_main_t *vam = &vat_main;
1968 i32 retval = ntohl (mp->retval);
1969
1970 if (vam->async_mode)
1971 {
1972 vam->async_errors += (retval < 0);
1973 }
1974 else
1975 {
1976 vam->retval = retval;
1977 vam->result_ready = 1;
1978 }
1979}
1980
1981static void vl_api_bond_delete_reply_t_handler_json
1982 (vl_api_bond_delete_reply_t * mp)
1983{
1984 vat_main_t *vam = &vat_main;
1985 vat_json_node_t node;
1986
1987 vat_json_init_object (&node);
1988 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
1989
1990 vat_json_print (vam->ofp, &node);
1991 vat_json_free (&node);
1992
1993 vam->retval = ntohl (mp->retval);
1994 vam->result_ready = 1;
1995}
1996
1997static void
Steven Luong4c4223e2020-07-15 08:44:54 -07001998vl_api_bond_add_member_reply_t_handler (vl_api_bond_add_member_reply_t * mp)
Steven9cd2d7a2017-12-20 12:43:01 -08001999{
2000 vat_main_t *vam = &vat_main;
2001 i32 retval = ntohl (mp->retval);
2002
2003 if (vam->async_mode)
2004 {
2005 vam->async_errors += (retval < 0);
2006 }
2007 else
2008 {
2009 vam->retval = retval;
2010 vam->result_ready = 1;
2011 }
2012}
2013
Steven Luong4c4223e2020-07-15 08:44:54 -07002014static void vl_api_bond_add_member_reply_t_handler_json
2015 (vl_api_bond_add_member_reply_t * mp)
Steven9cd2d7a2017-12-20 12:43:01 -08002016{
2017 vat_main_t *vam = &vat_main;
2018 vat_json_node_t node;
2019
2020 vat_json_init_object (&node);
2021 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
2022
2023 vat_json_print (vam->ofp, &node);
2024 vat_json_free (&node);
2025
2026 vam->retval = ntohl (mp->retval);
2027 vam->result_ready = 1;
2028}
2029
2030static void
Steven Luong4c4223e2020-07-15 08:44:54 -07002031vl_api_bond_detach_member_reply_t_handler (vl_api_bond_detach_member_reply_t *
2032 mp)
Steven9cd2d7a2017-12-20 12:43:01 -08002033{
2034 vat_main_t *vam = &vat_main;
2035 i32 retval = ntohl (mp->retval);
2036
2037 if (vam->async_mode)
2038 {
2039 vam->async_errors += (retval < 0);
2040 }
2041 else
2042 {
2043 vam->retval = retval;
2044 vam->result_ready = 1;
2045 }
2046}
2047
Steven Luong4c4223e2020-07-15 08:44:54 -07002048static void vl_api_bond_detach_member_reply_t_handler_json
2049 (vl_api_bond_detach_member_reply_t * mp)
Steven9cd2d7a2017-12-20 12:43:01 -08002050{
2051 vat_main_t *vam = &vat_main;
2052 vat_json_node_t node;
2053
2054 vat_json_init_object (&node);
2055 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
2056
2057 vat_json_print (vam->ofp, &node);
2058 vat_json_free (&node);
2059
2060 vam->retval = ntohl (mp->retval);
2061 vam->result_ready = 1;
2062}
2063
Steven Luonga1876b82019-08-20 16:58:00 -07002064static int
2065api_sw_interface_set_bond_weight (vat_main_t * vam)
2066{
2067 unformat_input_t *i = vam->input;
2068 vl_api_sw_interface_set_bond_weight_t *mp;
2069 u32 sw_if_index = ~0;
2070 u32 weight = 0;
2071 u8 weight_enter = 0;
2072 int ret;
2073
2074 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
2075 {
2076 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
2077 ;
2078 else if (unformat (i, "sw_if_index %d", &sw_if_index))
2079 ;
2080 else if (unformat (i, "weight %u", &weight))
2081 weight_enter = 1;
2082 else
2083 break;
2084 }
2085
2086 if (sw_if_index == ~0)
2087 {
2088 errmsg ("missing interface name or sw_if_index");
2089 return -99;
2090 }
2091 if (weight_enter == 0)
2092 {
2093 errmsg ("missing valid weight");
2094 return -99;
2095 }
2096
2097 /* Construct the API message */
2098 M (SW_INTERFACE_SET_BOND_WEIGHT, mp);
2099 mp->sw_if_index = ntohl (sw_if_index);
2100 mp->weight = ntohl (weight);
2101
2102 S (mp);
2103 W (ret);
2104 return ret;
2105}
2106
Steven Luong4c4223e2020-07-15 08:44:54 -07002107static void vl_api_sw_bond_interface_details_t_handler
2108 (vl_api_sw_bond_interface_details_t * mp)
Steven9cd2d7a2017-12-20 12:43:01 -08002109{
2110 vat_main_t *vam = &vat_main;
2111
2112 print (vam->ofp,
2113 "%-16s %-12d %-12U %-13U %-14u %-14u",
2114 mp->interface_name, ntohl (mp->sw_if_index),
Jakub Grajciar3d1ef872019-08-26 12:55:15 +02002115 format_bond_mode, ntohl (mp->mode), format_bond_load_balance,
Steven Luong4c4223e2020-07-15 08:44:54 -07002116 ntohl (mp->lb), ntohl (mp->active_members), ntohl (mp->members));
Steven9cd2d7a2017-12-20 12:43:01 -08002117}
2118
Steven Luong4c4223e2020-07-15 08:44:54 -07002119static void vl_api_sw_bond_interface_details_t_handler_json
2120 (vl_api_sw_bond_interface_details_t * mp)
Steven9cd2d7a2017-12-20 12:43:01 -08002121{
2122 vat_main_t *vam = &vat_main;
2123 vat_json_node_t *node = NULL;
2124
2125 if (VAT_JSON_ARRAY != vam->json_tree.type)
2126 {
2127 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
2128 vat_json_init_array (&vam->json_tree);
2129 }
2130 node = vat_json_array_add (&vam->json_tree);
2131
2132 vat_json_init_object (node);
2133 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
2134 vat_json_object_add_string_copy (node, "interface_name",
2135 mp->interface_name);
Jakub Grajciar3d1ef872019-08-26 12:55:15 +02002136 vat_json_object_add_uint (node, "mode", ntohl (mp->mode));
2137 vat_json_object_add_uint (node, "load_balance", ntohl (mp->lb));
Steven Luong4c4223e2020-07-15 08:44:54 -07002138 vat_json_object_add_uint (node, "active_members",
2139 ntohl (mp->active_members));
2140 vat_json_object_add_uint (node, "members", ntohl (mp->members));
Steven9cd2d7a2017-12-20 12:43:01 -08002141}
2142
2143static int
Steven Luong4c4223e2020-07-15 08:44:54 -07002144api_sw_bond_interface_dump (vat_main_t * vam)
Steven9cd2d7a2017-12-20 12:43:01 -08002145{
Steven Luong4c4223e2020-07-15 08:44:54 -07002146 unformat_input_t *i = vam->input;
2147 vl_api_sw_bond_interface_dump_t *mp;
Steven9cd2d7a2017-12-20 12:43:01 -08002148 vl_api_control_ping_t *mp_ping;
2149 int ret;
Steven Luong4c4223e2020-07-15 08:44:54 -07002150 u32 sw_if_index = ~0;
2151
2152 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
2153 {
2154 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
2155 ;
2156 else if (unformat (i, "sw_if_index %d", &sw_if_index))
2157 ;
2158 else
2159 break;
2160 }
Steven9cd2d7a2017-12-20 12:43:01 -08002161
2162 print (vam->ofp,
2163 "\n%-16s %-12s %-12s %-13s %-14s %-14s",
2164 "interface name", "sw_if_index", "mode", "load balance",
Steven Luong4c4223e2020-07-15 08:44:54 -07002165 "active members", "members");
Steven9cd2d7a2017-12-20 12:43:01 -08002166
2167 /* Get list of bond interfaces */
Steven Luong4c4223e2020-07-15 08:44:54 -07002168 M (SW_BOND_INTERFACE_DUMP, mp);
2169 mp->sw_if_index = ntohl (sw_if_index);
Steven9cd2d7a2017-12-20 12:43:01 -08002170 S (mp);
2171
2172 /* Use a control ping for synchronization */
2173 MPING (CONTROL_PING, mp_ping);
2174 S (mp_ping);
2175
2176 W (ret);
2177 return ret;
2178}
2179
Steven Luong4c4223e2020-07-15 08:44:54 -07002180static void vl_api_sw_member_interface_details_t_handler
2181 (vl_api_sw_member_interface_details_t * mp)
Steven9cd2d7a2017-12-20 12:43:01 -08002182{
2183 vat_main_t *vam = &vat_main;
2184
2185 print (vam->ofp,
Steven Luonga1876b82019-08-20 16:58:00 -07002186 "%-25s %-12d %-7d %-12d %-10d %-10d", mp->interface_name,
2187 ntohl (mp->sw_if_index), mp->is_passive, mp->is_long_timeout,
2188 ntohl (mp->weight), mp->is_local_numa);
Steven9cd2d7a2017-12-20 12:43:01 -08002189}
2190
Steven Luong4c4223e2020-07-15 08:44:54 -07002191static void vl_api_sw_member_interface_details_t_handler_json
2192 (vl_api_sw_member_interface_details_t * mp)
Steven9cd2d7a2017-12-20 12:43:01 -08002193{
2194 vat_main_t *vam = &vat_main;
2195 vat_json_node_t *node = NULL;
2196
2197 if (VAT_JSON_ARRAY != vam->json_tree.type)
2198 {
2199 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
2200 vat_json_init_array (&vam->json_tree);
2201 }
2202 node = vat_json_array_add (&vam->json_tree);
2203
2204 vat_json_init_object (node);
2205 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
2206 vat_json_object_add_string_copy (node, "interface_name",
2207 mp->interface_name);
2208 vat_json_object_add_uint (node, "passive", mp->is_passive);
2209 vat_json_object_add_uint (node, "long_timeout", mp->is_long_timeout);
Steven Luonga1876b82019-08-20 16:58:00 -07002210 vat_json_object_add_uint (node, "weight", ntohl (mp->weight));
2211 vat_json_object_add_uint (node, "is_local_numa", mp->is_local_numa);
Steven9cd2d7a2017-12-20 12:43:01 -08002212}
2213
2214static int
Steven Luong4c4223e2020-07-15 08:44:54 -07002215api_sw_member_interface_dump (vat_main_t * vam)
Steven9cd2d7a2017-12-20 12:43:01 -08002216{
2217 unformat_input_t *i = vam->input;
Steven Luong4c4223e2020-07-15 08:44:54 -07002218 vl_api_sw_member_interface_dump_t *mp;
Steven9cd2d7a2017-12-20 12:43:01 -08002219 vl_api_control_ping_t *mp_ping;
2220 u32 sw_if_index = ~0;
2221 u8 sw_if_index_set = 0;
2222 int ret;
2223
2224 /* Parse args required to build the message */
2225 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
2226 {
2227 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
2228 sw_if_index_set = 1;
2229 else if (unformat (i, "sw_if_index %d", &sw_if_index))
2230 sw_if_index_set = 1;
2231 else
2232 break;
2233 }
2234
2235 if (sw_if_index_set == 0)
2236 {
2237 errmsg ("missing vpp interface name. ");
2238 return -99;
2239 }
2240
2241 print (vam->ofp,
Steven Luonga1876b82019-08-20 16:58:00 -07002242 "\n%-25s %-12s %-7s %-12s %-10s %-10s",
Steven Luong4c4223e2020-07-15 08:44:54 -07002243 "member interface name", "sw_if_index", "passive", "long_timeout",
Steven Luonga1876b82019-08-20 16:58:00 -07002244 "weight", "local numa");
Steven9cd2d7a2017-12-20 12:43:01 -08002245
2246 /* Get list of bond interfaces */
Steven Luong4c4223e2020-07-15 08:44:54 -07002247 M (SW_MEMBER_INTERFACE_DUMP, mp);
Steven9cd2d7a2017-12-20 12:43:01 -08002248 mp->sw_if_index = ntohl (sw_if_index);
2249 S (mp);
2250
2251 /* Use a control ping for synchronization */
2252 MPING (CONTROL_PING, mp_ping);
2253 S (mp_ping);
2254
2255 W (ret);
2256 return ret;
2257}
2258
Damjan Marion7cd468a2016-12-19 23:05:39 +01002259static void vl_api_mpls_tunnel_add_del_reply_t_handler
2260 (vl_api_mpls_tunnel_add_del_reply_t * mp)
2261{
2262 vat_main_t *vam = &vat_main;
2263 i32 retval = ntohl (mp->retval);
2264 if (vam->async_mode)
2265 {
2266 vam->async_errors += (retval < 0);
2267 }
2268 else
2269 {
2270 vam->retval = retval;
John Lo06fda9c2018-10-03 16:32:44 -04002271 vam->sw_if_index = ntohl (mp->sw_if_index);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002272 vam->result_ready = 1;
2273 }
John Lo06fda9c2018-10-03 16:32:44 -04002274 vam->regenerate_interface_table = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01002275}
2276
2277static void vl_api_mpls_tunnel_add_del_reply_t_handler_json
2278 (vl_api_mpls_tunnel_add_del_reply_t * mp)
2279{
2280 vat_main_t *vam = &vat_main;
2281 vat_json_node_t node;
2282
2283 vat_json_init_object (&node);
2284 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
2285 vat_json_object_add_uint (&node, "tunnel_sw_if_index",
2286 ntohl (mp->sw_if_index));
2287
2288 vat_json_print (vam->ofp, &node);
2289 vat_json_free (&node);
2290
2291 vam->retval = ntohl (mp->retval);
2292 vam->result_ready = 1;
2293}
2294
Damjan Marion7cd468a2016-12-19 23:05:39 +01002295static void vl_api_vxlan_add_del_tunnel_reply_t_handler
2296 (vl_api_vxlan_add_del_tunnel_reply_t * mp)
2297{
2298 vat_main_t *vam = &vat_main;
2299 i32 retval = ntohl (mp->retval);
2300 if (vam->async_mode)
2301 {
2302 vam->async_errors += (retval < 0);
2303 }
2304 else
2305 {
2306 vam->retval = retval;
2307 vam->sw_if_index = ntohl (mp->sw_if_index);
2308 vam->result_ready = 1;
2309 }
Dave Barachf72212e2018-01-11 10:25:07 -05002310 vam->regenerate_interface_table = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01002311}
2312
2313static void vl_api_vxlan_add_del_tunnel_reply_t_handler_json
2314 (vl_api_vxlan_add_del_tunnel_reply_t * mp)
2315{
2316 vat_main_t *vam = &vat_main;
2317 vat_json_node_t node;
2318
2319 vat_json_init_object (&node);
2320 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
2321 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
2322
2323 vat_json_print (vam->ofp, &node);
2324 vat_json_free (&node);
2325
2326 vam->retval = ntohl (mp->retval);
2327 vam->result_ready = 1;
2328}
2329
eyal bariaf86a482018-04-17 11:20:27 +03002330static void vl_api_vxlan_offload_rx_reply_t_handler
2331 (vl_api_vxlan_offload_rx_reply_t * mp)
2332{
2333 vat_main_t *vam = &vat_main;
2334 i32 retval = ntohl (mp->retval);
2335 if (vam->async_mode)
2336 {
2337 vam->async_errors += (retval < 0);
2338 }
2339 else
2340 {
2341 vam->retval = retval;
2342 vam->result_ready = 1;
2343 }
2344}
2345
2346static void vl_api_vxlan_offload_rx_reply_t_handler_json
2347 (vl_api_vxlan_offload_rx_reply_t * mp)
2348{
2349 vat_main_t *vam = &vat_main;
2350 vat_json_node_t node;
2351
2352 vat_json_init_object (&node);
2353 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
2354
2355 vat_json_print (vam->ofp, &node);
2356 vat_json_free (&node);
2357
2358 vam->retval = ntohl (mp->retval);
2359 vam->result_ready = 1;
2360}
2361
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +08002362static void vl_api_vxlan_gpe_add_del_tunnel_reply_t_handler
2363 (vl_api_vxlan_gpe_add_del_tunnel_reply_t * mp)
2364{
2365 vat_main_t *vam = &vat_main;
2366 i32 retval = ntohl (mp->retval);
2367 if (vam->async_mode)
2368 {
2369 vam->async_errors += (retval < 0);
2370 }
2371 else
2372 {
2373 vam->retval = retval;
2374 vam->sw_if_index = ntohl (mp->sw_if_index);
2375 vam->result_ready = 1;
2376 }
Dave Barachf72212e2018-01-11 10:25:07 -05002377 vam->regenerate_interface_table = 1;
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +08002378}
2379
2380static void vl_api_vxlan_gpe_add_del_tunnel_reply_t_handler_json
2381 (vl_api_vxlan_gpe_add_del_tunnel_reply_t * mp)
2382{
2383 vat_main_t *vam = &vat_main;
2384 vat_json_node_t node;
2385
2386 vat_json_init_object (&node);
2387 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
2388 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
2389
2390 vat_json_print (vam->ofp, &node);
2391 vat_json_free (&node);
2392
2393 vam->retval = ntohl (mp->retval);
2394 vam->result_ready = 1;
2395}
2396
Damjan Marion7cd468a2016-12-19 23:05:39 +01002397static void vl_api_create_vhost_user_if_reply_t_handler
2398 (vl_api_create_vhost_user_if_reply_t * mp)
2399{
2400 vat_main_t *vam = &vat_main;
2401 i32 retval = ntohl (mp->retval);
2402 if (vam->async_mode)
2403 {
2404 vam->async_errors += (retval < 0);
2405 }
2406 else
2407 {
2408 vam->retval = retval;
2409 vam->sw_if_index = ntohl (mp->sw_if_index);
2410 vam->result_ready = 1;
2411 }
Dave Barachf72212e2018-01-11 10:25:07 -05002412 vam->regenerate_interface_table = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01002413}
2414
2415static void vl_api_create_vhost_user_if_reply_t_handler_json
2416 (vl_api_create_vhost_user_if_reply_t * mp)
2417{
2418 vat_main_t *vam = &vat_main;
2419 vat_json_node_t node;
2420
2421 vat_json_init_object (&node);
2422 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
2423 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
2424
2425 vat_json_print (vam->ofp, &node);
2426 vat_json_free (&node);
2427
2428 vam->retval = ntohl (mp->retval);
2429 vam->result_ready = 1;
2430}
2431
Steven Luong27ba5002020-11-17 13:30:44 -08002432static void vl_api_create_vhost_user_if_v2_reply_t_handler
2433 (vl_api_create_vhost_user_if_v2_reply_t * mp)
2434{
2435 vat_main_t *vam = &vat_main;
2436 i32 retval = ntohl (mp->retval);
2437 if (vam->async_mode)
2438 {
2439 vam->async_errors += (retval < 0);
2440 }
2441 else
2442 {
2443 vam->retval = retval;
2444 vam->sw_if_index = ntohl (mp->sw_if_index);
2445 vam->result_ready = 1;
2446 }
2447 vam->regenerate_interface_table = 1;
2448}
2449
2450static void vl_api_create_vhost_user_if_v2_reply_t_handler_json
2451 (vl_api_create_vhost_user_if_v2_reply_t * mp)
2452{
2453 vat_main_t *vam = &vat_main;
2454 vat_json_node_t node;
2455
2456 vat_json_init_object (&node);
2457 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
2458 vat_json_object_add_uint (&node, "sw_if_index", ntohl (mp->sw_if_index));
2459
2460 vat_json_print (vam->ofp, &node);
2461 vat_json_free (&node);
2462
2463 vam->retval = ntohl (mp->retval);
2464 vam->result_ready = 1;
2465}
2466
Damjan Marion7cd468a2016-12-19 23:05:39 +01002467static void vl_api_ip_address_details_t_handler
2468 (vl_api_ip_address_details_t * mp)
2469{
2470 vat_main_t *vam = &vat_main;
2471 static ip_address_details_t empty_ip_address_details = { {0} };
2472 ip_address_details_t *address = NULL;
2473 ip_details_t *current_ip_details = NULL;
2474 ip_details_t *details = NULL;
2475
2476 details = vam->ip_details_by_sw_if_index[vam->is_ipv6];
2477
2478 if (!details || vam->current_sw_if_index >= vec_len (details)
2479 || !details[vam->current_sw_if_index].present)
2480 {
2481 errmsg ("ip address details arrived but not stored");
2482 errmsg ("ip_dump should be called first");
2483 return;
2484 }
2485
2486 current_ip_details = vec_elt_at_index (details, vam->current_sw_if_index);
2487
2488#define addresses (current_ip_details->addr)
2489
2490 vec_validate_init_empty (addresses, vec_len (addresses),
2491 empty_ip_address_details);
2492
2493 address = vec_elt_at_index (addresses, vec_len (addresses) - 1);
2494
Neale Ranns097fa662018-05-01 05:17:55 -07002495 clib_memcpy (&address->ip, &mp->prefix.address.un, sizeof (address->ip));
Paul Vinciguerraab055082019-06-06 14:07:55 -04002496 address->prefix_length = mp->prefix.len;
Damjan Marion7cd468a2016-12-19 23:05:39 +01002497#undef addresses
2498}
2499
2500static void vl_api_ip_address_details_t_handler_json
2501 (vl_api_ip_address_details_t * mp)
2502{
2503 vat_main_t *vam = &vat_main;
2504 vat_json_node_t *node = NULL;
Damjan Marion7cd468a2016-12-19 23:05:39 +01002505
2506 if (VAT_JSON_ARRAY != vam->json_tree.type)
2507 {
2508 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
2509 vat_json_init_array (&vam->json_tree);
2510 }
2511 node = vat_json_array_add (&vam->json_tree);
2512
2513 vat_json_init_object (node);
Neale Ranns097fa662018-05-01 05:17:55 -07002514 vat_json_object_add_prefix (node, &mp->prefix);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002515}
2516
2517static void
2518vl_api_ip_details_t_handler (vl_api_ip_details_t * mp)
2519{
2520 vat_main_t *vam = &vat_main;
2521 static ip_details_t empty_ip_details = { 0 };
2522 ip_details_t *ip = NULL;
2523 u32 sw_if_index = ~0;
2524
2525 sw_if_index = ntohl (mp->sw_if_index);
2526
2527 vec_validate_init_empty (vam->ip_details_by_sw_if_index[vam->is_ipv6],
2528 sw_if_index, empty_ip_details);
2529
2530 ip = vec_elt_at_index (vam->ip_details_by_sw_if_index[vam->is_ipv6],
2531 sw_if_index);
2532
2533 ip->present = 1;
2534}
2535
2536static void
2537vl_api_ip_details_t_handler_json (vl_api_ip_details_t * mp)
2538{
2539 vat_main_t *vam = &vat_main;
2540
2541 if (VAT_JSON_ARRAY != vam->json_tree.type)
2542 {
2543 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
2544 vat_json_init_array (&vam->json_tree);
2545 }
2546 vat_json_array_add_uint (&vam->json_tree,
2547 clib_net_to_host_u32 (mp->sw_if_index));
2548}
2549
Damjan Marion7cd468a2016-12-19 23:05:39 +01002550static void vl_api_get_first_msg_id_reply_t_handler
2551 (vl_api_get_first_msg_id_reply_t * mp)
2552{
2553 vat_main_t *vam = &vat_main;
2554 i32 retval = ntohl (mp->retval);
2555
2556 if (vam->async_mode)
2557 {
2558 vam->async_errors += (retval < 0);
2559 }
2560 else
2561 {
2562 vam->retval = retval;
2563 vam->result_ready = 1;
2564 }
2565 if (retval >= 0)
2566 {
2567 errmsg ("first message id %d", ntohs (mp->first_msg_id));
2568 }
2569}
2570
2571static void vl_api_get_first_msg_id_reply_t_handler_json
2572 (vl_api_get_first_msg_id_reply_t * mp)
2573{
2574 vat_main_t *vam = &vat_main;
2575 vat_json_node_t node;
2576
2577 vat_json_init_object (&node);
2578 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
2579 vat_json_object_add_uint (&node, "first_msg_id",
2580 (uint) ntohs (mp->first_msg_id));
2581
2582 vat_json_print (vam->ofp, &node);
2583 vat_json_free (&node);
2584
2585 vam->retval = ntohl (mp->retval);
2586 vam->result_ready = 1;
2587}
2588
2589static void vl_api_get_node_graph_reply_t_handler
2590 (vl_api_get_node_graph_reply_t * mp)
2591{
2592 vat_main_t *vam = &vat_main;
Damjan Marion7cd468a2016-12-19 23:05:39 +01002593 i32 retval = ntohl (mp->retval);
2594 u8 *pvt_copy, *reply;
2595 void *oldheap;
2596 vlib_node_t *node;
2597 int i;
2598
2599 if (vam->async_mode)
2600 {
2601 vam->async_errors += (retval < 0);
2602 }
2603 else
2604 {
2605 vam->retval = retval;
2606 vam->result_ready = 1;
2607 }
2608
2609 /* "Should never happen..." */
2610 if (retval != 0)
2611 return;
2612
Damjan Marion7bee80c2017-04-26 15:32:12 +02002613 reply = uword_to_pointer (mp->reply_in_shmem, u8 *);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002614 pvt_copy = vec_dup (reply);
2615
2616 /* Toss the shared-memory original... */
Nathan Skrzypczak0aa40132019-11-25 16:29:38 +01002617 oldheap = vl_msg_push_heap ();
Damjan Marion7cd468a2016-12-19 23:05:39 +01002618
2619 vec_free (reply);
2620
Nathan Skrzypczak0aa40132019-11-25 16:29:38 +01002621 vl_msg_pop_heap (oldheap);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002622
2623 if (vam->graph_nodes)
2624 {
2625 hash_free (vam->graph_node_index_by_name);
2626
Dave Barach1ddbc012018-06-13 09:26:05 -04002627 for (i = 0; i < vec_len (vam->graph_nodes[0]); i++)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002628 {
Dave Barach1ddbc012018-06-13 09:26:05 -04002629 node = vam->graph_nodes[0][i];
Damjan Marion7cd468a2016-12-19 23:05:39 +01002630 vec_free (node->name);
2631 vec_free (node->next_nodes);
2632 vec_free (node);
2633 }
Dave Barach1ddbc012018-06-13 09:26:05 -04002634 vec_free (vam->graph_nodes[0]);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002635 vec_free (vam->graph_nodes);
2636 }
2637
2638 vam->graph_node_index_by_name = hash_create_string (0, sizeof (uword));
2639 vam->graph_nodes = vlib_node_unserialize (pvt_copy);
2640 vec_free (pvt_copy);
2641
Dave Barach1ddbc012018-06-13 09:26:05 -04002642 for (i = 0; i < vec_len (vam->graph_nodes[0]); i++)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002643 {
Dave Barach1ddbc012018-06-13 09:26:05 -04002644 node = vam->graph_nodes[0][i];
Damjan Marion7cd468a2016-12-19 23:05:39 +01002645 hash_set_mem (vam->graph_node_index_by_name, node->name, i);
2646 }
2647}
2648
2649static void vl_api_get_node_graph_reply_t_handler_json
2650 (vl_api_get_node_graph_reply_t * mp)
2651{
2652 vat_main_t *vam = &vat_main;
Damjan Marion7cd468a2016-12-19 23:05:39 +01002653 void *oldheap;
2654 vat_json_node_t node;
2655 u8 *reply;
2656
2657 /* $$$$ make this real? */
2658 vat_json_init_object (&node);
2659 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
2660 vat_json_object_add_uint (&node, "reply_in_shmem", mp->reply_in_shmem);
2661
Damjan Marion7bee80c2017-04-26 15:32:12 +02002662 reply = uword_to_pointer (mp->reply_in_shmem, u8 *);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002663
2664 /* Toss the shared-memory original... */
Nathan Skrzypczak0aa40132019-11-25 16:29:38 +01002665 oldheap = vl_msg_push_heap ();
Damjan Marion7cd468a2016-12-19 23:05:39 +01002666
2667 vec_free (reply);
2668
Nathan Skrzypczak0aa40132019-11-25 16:29:38 +01002669 vl_msg_pop_heap (oldheap);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002670
2671 vat_json_print (vam->ofp, &node);
2672 vat_json_free (&node);
2673
2674 vam->retval = ntohl (mp->retval);
2675 vam->result_ready = 1;
2676}
2677
Damjan Marion7cd468a2016-12-19 23:05:39 +01002678static u8 *
2679format_policer_type (u8 * s, va_list * va)
2680{
2681 u32 i = va_arg (*va, u32);
2682
Brian Russellc5299ff2021-02-09 10:16:58 +00002683 if (i == QOS_POLICER_TYPE_1R2C)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002684 s = format (s, "1r2c");
Brian Russellc5299ff2021-02-09 10:16:58 +00002685 else if (i == QOS_POLICER_TYPE_1R3C_RFC_2697)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002686 s = format (s, "1r3c");
Brian Russellc5299ff2021-02-09 10:16:58 +00002687 else if (i == QOS_POLICER_TYPE_2R3C_RFC_2698)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002688 s = format (s, "2r3c-2698");
Brian Russellc5299ff2021-02-09 10:16:58 +00002689 else if (i == QOS_POLICER_TYPE_2R3C_RFC_4115)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002690 s = format (s, "2r3c-4115");
Brian Russellc5299ff2021-02-09 10:16:58 +00002691 else if (i == QOS_POLICER_TYPE_2R3C_RFC_MEF5CF1)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002692 s = format (s, "2r3c-mef5cf1");
2693 else
2694 s = format (s, "ILLEGAL");
2695 return s;
2696}
2697
2698static u8 *
2699format_policer_rate_type (u8 * s, va_list * va)
2700{
2701 u32 i = va_arg (*va, u32);
2702
Brian Russellc5299ff2021-02-09 10:16:58 +00002703 if (i == QOS_RATE_KBPS)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002704 s = format (s, "kbps");
Brian Russellc5299ff2021-02-09 10:16:58 +00002705 else if (i == QOS_RATE_PPS)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002706 s = format (s, "pps");
2707 else
2708 s = format (s, "ILLEGAL");
2709 return s;
2710}
2711
2712static u8 *
2713format_policer_round_type (u8 * s, va_list * va)
2714{
2715 u32 i = va_arg (*va, u32);
2716
Brian Russellc5299ff2021-02-09 10:16:58 +00002717 if (i == QOS_ROUND_TO_CLOSEST)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002718 s = format (s, "closest");
Brian Russellc5299ff2021-02-09 10:16:58 +00002719 else if (i == QOS_ROUND_TO_UP)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002720 s = format (s, "up");
Brian Russellc5299ff2021-02-09 10:16:58 +00002721 else if (i == QOS_ROUND_TO_DOWN)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002722 s = format (s, "down");
2723 else
2724 s = format (s, "ILLEGAL");
2725 return s;
2726}
2727
2728static u8 *
2729format_policer_action_type (u8 * s, va_list * va)
2730{
2731 u32 i = va_arg (*va, u32);
2732
Brian Russellc5299ff2021-02-09 10:16:58 +00002733 if (i == QOS_ACTION_DROP)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002734 s = format (s, "drop");
Brian Russellc5299ff2021-02-09 10:16:58 +00002735 else if (i == QOS_ACTION_TRANSMIT)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002736 s = format (s, "transmit");
Brian Russellc5299ff2021-02-09 10:16:58 +00002737 else if (i == QOS_ACTION_MARK_AND_TRANSMIT)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002738 s = format (s, "mark-and-transmit");
2739 else
2740 s = format (s, "ILLEGAL");
2741 return s;
2742}
2743
2744static u8 *
2745format_dscp (u8 * s, va_list * va)
2746{
2747 u32 i = va_arg (*va, u32);
2748 char *t = 0;
2749
2750 switch (i)
2751 {
Brian Russelle3845d72021-02-08 15:33:18 +00002752#define _(v, f) \
2753 case IP_DSCP_##f: \
2754 return (format (s, "%s", #f));
2755 foreach_ip_dscp
Damjan Marion7cd468a2016-12-19 23:05:39 +01002756#undef _
Damjan Marion7cd468a2016-12-19 23:05:39 +01002757 }
2758 s = format (s, "%s", t);
Brian Russelle3845d72021-02-08 15:33:18 +00002759 return (format (s, "ILLEGAL"));
Damjan Marion7cd468a2016-12-19 23:05:39 +01002760}
2761
2762static void
2763vl_api_policer_details_t_handler (vl_api_policer_details_t * mp)
2764{
2765 vat_main_t *vam = &vat_main;
2766 u8 *conform_dscp_str, *exceed_dscp_str, *violate_dscp_str;
2767
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002768 if (mp->conform_action.type == SSE2_QOS_ACTION_API_MARK_AND_TRANSMIT)
2769 conform_dscp_str = format (0, "%U", format_dscp, mp->conform_action.dscp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002770 else
2771 conform_dscp_str = format (0, "");
2772
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002773 if (mp->exceed_action.type == SSE2_QOS_ACTION_API_MARK_AND_TRANSMIT)
2774 exceed_dscp_str = format (0, "%U", format_dscp, mp->exceed_action.dscp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002775 else
2776 exceed_dscp_str = format (0, "");
2777
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002778 if (mp->violate_action.type == SSE2_QOS_ACTION_API_MARK_AND_TRANSMIT)
2779 violate_dscp_str = format (0, "%U", format_dscp, mp->violate_action.dscp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002780 else
2781 violate_dscp_str = format (0, "");
2782
2783 print (vam->ofp, "Name \"%s\", type %U, cir %u, eir %u, cb %u, eb %u, "
2784 "rate type %U, round type %U, %s rate, %s color-aware, "
2785 "cir %u tok/period, pir %u tok/period, scale %u, cur lim %u, "
2786 "cur bkt %u, ext lim %u, ext bkt %u, last update %llu"
2787 "conform action %U%s, exceed action %U%s, violate action %U%s",
2788 mp->name,
2789 format_policer_type, mp->type,
2790 ntohl (mp->cir),
2791 ntohl (mp->eir),
2792 clib_net_to_host_u64 (mp->cb),
2793 clib_net_to_host_u64 (mp->eb),
2794 format_policer_rate_type, mp->rate_type,
2795 format_policer_round_type, mp->round_type,
2796 mp->single_rate ? "single" : "dual",
2797 mp->color_aware ? "is" : "not",
2798 ntohl (mp->cir_tokens_per_period),
2799 ntohl (mp->pir_tokens_per_period),
2800 ntohl (mp->scale),
2801 ntohl (mp->current_limit),
2802 ntohl (mp->current_bucket),
2803 ntohl (mp->extended_limit),
2804 ntohl (mp->extended_bucket),
2805 clib_net_to_host_u64 (mp->last_update_time),
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002806 format_policer_action_type, mp->conform_action.type,
Damjan Marion7cd468a2016-12-19 23:05:39 +01002807 conform_dscp_str,
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002808 format_policer_action_type, mp->exceed_action.type,
Damjan Marion7cd468a2016-12-19 23:05:39 +01002809 exceed_dscp_str,
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002810 format_policer_action_type, mp->violate_action.type,
Damjan Marion7cd468a2016-12-19 23:05:39 +01002811 violate_dscp_str);
2812
2813 vec_free (conform_dscp_str);
2814 vec_free (exceed_dscp_str);
2815 vec_free (violate_dscp_str);
2816}
2817
2818static void vl_api_policer_details_t_handler_json
2819 (vl_api_policer_details_t * mp)
2820{
2821 vat_main_t *vam = &vat_main;
2822 vat_json_node_t *node;
2823 u8 *rate_type_str, *round_type_str, *type_str;
2824 u8 *conform_action_str, *exceed_action_str, *violate_action_str;
2825
2826 rate_type_str = format (0, "%U", format_policer_rate_type, mp->rate_type);
2827 round_type_str =
2828 format (0, "%U", format_policer_round_type, mp->round_type);
2829 type_str = format (0, "%U", format_policer_type, mp->type);
2830 conform_action_str = format (0, "%U", format_policer_action_type,
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002831 mp->conform_action.type);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002832 exceed_action_str = format (0, "%U", format_policer_action_type,
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002833 mp->exceed_action.type);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002834 violate_action_str = format (0, "%U", format_policer_action_type,
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002835 mp->violate_action.type);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002836
2837 if (VAT_JSON_ARRAY != vam->json_tree.type)
2838 {
2839 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
2840 vat_json_init_array (&vam->json_tree);
2841 }
2842 node = vat_json_array_add (&vam->json_tree);
2843
2844 vat_json_init_object (node);
2845 vat_json_object_add_string_copy (node, "name", mp->name);
2846 vat_json_object_add_uint (node, "cir", ntohl (mp->cir));
2847 vat_json_object_add_uint (node, "eir", ntohl (mp->eir));
Marek Gradzki59ed4902017-03-21 11:51:54 +01002848 vat_json_object_add_uint (node, "cb", clib_net_to_host_u64 (mp->cb));
2849 vat_json_object_add_uint (node, "eb", clib_net_to_host_u64 (mp->eb));
Damjan Marion7cd468a2016-12-19 23:05:39 +01002850 vat_json_object_add_string_copy (node, "rate_type", rate_type_str);
2851 vat_json_object_add_string_copy (node, "round_type", round_type_str);
2852 vat_json_object_add_string_copy (node, "type", type_str);
2853 vat_json_object_add_uint (node, "single_rate", mp->single_rate);
2854 vat_json_object_add_uint (node, "color_aware", mp->color_aware);
2855 vat_json_object_add_uint (node, "scale", ntohl (mp->scale));
2856 vat_json_object_add_uint (node, "cir_tokens_per_period",
2857 ntohl (mp->cir_tokens_per_period));
2858 vat_json_object_add_uint (node, "eir_tokens_per_period",
2859 ntohl (mp->pir_tokens_per_period));
2860 vat_json_object_add_uint (node, "current_limit", ntohl (mp->current_limit));
2861 vat_json_object_add_uint (node, "current_bucket",
2862 ntohl (mp->current_bucket));
2863 vat_json_object_add_uint (node, "extended_limit",
2864 ntohl (mp->extended_limit));
2865 vat_json_object_add_uint (node, "extended_bucket",
2866 ntohl (mp->extended_bucket));
2867 vat_json_object_add_uint (node, "last_update_time",
2868 ntohl (mp->last_update_time));
2869 vat_json_object_add_string_copy (node, "conform_action",
2870 conform_action_str);
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002871 if (mp->conform_action.type == SSE2_QOS_ACTION_API_MARK_AND_TRANSMIT)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002872 {
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002873 u8 *dscp_str = format (0, "%U", format_dscp, mp->conform_action.dscp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002874 vat_json_object_add_string_copy (node, "conform_dscp", dscp_str);
2875 vec_free (dscp_str);
2876 }
2877 vat_json_object_add_string_copy (node, "exceed_action", exceed_action_str);
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002878 if (mp->exceed_action.type == SSE2_QOS_ACTION_API_MARK_AND_TRANSMIT)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002879 {
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002880 u8 *dscp_str = format (0, "%U", format_dscp, mp->exceed_action.dscp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002881 vat_json_object_add_string_copy (node, "exceed_dscp", dscp_str);
2882 vec_free (dscp_str);
2883 }
2884 vat_json_object_add_string_copy (node, "violate_action",
2885 violate_action_str);
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002886 if (mp->violate_action.type == SSE2_QOS_ACTION_API_MARK_AND_TRANSMIT)
Damjan Marion7cd468a2016-12-19 23:05:39 +01002887 {
Jakub Grajciarcd01fb42020-03-02 13:16:53 +01002888 u8 *dscp_str = format (0, "%U", format_dscp, mp->violate_action.dscp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01002889 vat_json_object_add_string_copy (node, "violate_dscp", dscp_str);
2890 vec_free (dscp_str);
2891 }
2892
2893 vec_free (rate_type_str);
2894 vec_free (round_type_str);
2895 vec_free (type_str);
2896 vec_free (conform_action_str);
2897 vec_free (exceed_action_str);
2898 vec_free (violate_action_str);
2899}
2900
2901static void
2902vl_api_classify_table_ids_reply_t_handler (vl_api_classify_table_ids_reply_t *
2903 mp)
2904{
2905 vat_main_t *vam = &vat_main;
2906 int i, count = ntohl (mp->count);
2907
2908 if (count > 0)
2909 print (vam->ofp, "classify table ids (%d) : ", count);
2910 for (i = 0; i < count; i++)
2911 {
2912 print (vam->ofp, "%d", ntohl (mp->ids[i]));
2913 print (vam->ofp, (i < count - 1) ? "," : "");
2914 }
2915 vam->retval = ntohl (mp->retval);
2916 vam->result_ready = 1;
2917}
2918
2919static void
2920 vl_api_classify_table_ids_reply_t_handler_json
2921 (vl_api_classify_table_ids_reply_t * mp)
2922{
2923 vat_main_t *vam = &vat_main;
2924 int i, count = ntohl (mp->count);
2925
2926 if (count > 0)
2927 {
2928 vat_json_node_t node;
2929
2930 vat_json_init_object (&node);
2931 for (i = 0; i < count; i++)
2932 {
2933 vat_json_object_add_uint (&node, "table_id", ntohl (mp->ids[i]));
2934 }
2935 vat_json_print (vam->ofp, &node);
2936 vat_json_free (&node);
2937 }
2938 vam->retval = ntohl (mp->retval);
2939 vam->result_ready = 1;
2940}
2941
2942static void
2943 vl_api_classify_table_by_interface_reply_t_handler
2944 (vl_api_classify_table_by_interface_reply_t * mp)
2945{
2946 vat_main_t *vam = &vat_main;
2947 u32 table_id;
2948
2949 table_id = ntohl (mp->l2_table_id);
2950 if (table_id != ~0)
2951 print (vam->ofp, "l2 table id : %d", table_id);
2952 else
2953 print (vam->ofp, "l2 table id : No input ACL tables configured");
2954 table_id = ntohl (mp->ip4_table_id);
2955 if (table_id != ~0)
2956 print (vam->ofp, "ip4 table id : %d", table_id);
2957 else
2958 print (vam->ofp, "ip4 table id : No input ACL tables configured");
2959 table_id = ntohl (mp->ip6_table_id);
2960 if (table_id != ~0)
2961 print (vam->ofp, "ip6 table id : %d", table_id);
2962 else
2963 print (vam->ofp, "ip6 table id : No input ACL tables configured");
2964 vam->retval = ntohl (mp->retval);
2965 vam->result_ready = 1;
2966}
2967
2968static void
2969 vl_api_classify_table_by_interface_reply_t_handler_json
2970 (vl_api_classify_table_by_interface_reply_t * mp)
2971{
2972 vat_main_t *vam = &vat_main;
2973 vat_json_node_t node;
2974
2975 vat_json_init_object (&node);
2976
2977 vat_json_object_add_int (&node, "l2_table_id", ntohl (mp->l2_table_id));
2978 vat_json_object_add_int (&node, "ip4_table_id", ntohl (mp->ip4_table_id));
2979 vat_json_object_add_int (&node, "ip6_table_id", ntohl (mp->ip6_table_id));
2980
2981 vat_json_print (vam->ofp, &node);
2982 vat_json_free (&node);
2983
2984 vam->retval = ntohl (mp->retval);
2985 vam->result_ready = 1;
2986}
2987
2988static void vl_api_policer_add_del_reply_t_handler
2989 (vl_api_policer_add_del_reply_t * mp)
2990{
2991 vat_main_t *vam = &vat_main;
2992 i32 retval = ntohl (mp->retval);
2993 if (vam->async_mode)
2994 {
2995 vam->async_errors += (retval < 0);
2996 }
2997 else
2998 {
2999 vam->retval = retval;
3000 vam->result_ready = 1;
3001 if (retval == 0 && mp->policer_index != 0xFFFFFFFF)
3002 /*
3003 * Note: this is just barely thread-safe, depends on
3004 * the main thread spinning waiting for an answer...
3005 */
3006 errmsg ("policer index %d", ntohl (mp->policer_index));
3007 }
3008}
3009
3010static void vl_api_policer_add_del_reply_t_handler_json
3011 (vl_api_policer_add_del_reply_t * mp)
3012{
3013 vat_main_t *vam = &vat_main;
3014 vat_json_node_t node;
3015
3016 vat_json_init_object (&node);
3017 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
3018 vat_json_object_add_uint (&node, "policer_index",
3019 ntohl (mp->policer_index));
3020
3021 vat_json_print (vam->ofp, &node);
3022 vat_json_free (&node);
3023
3024 vam->retval = ntohl (mp->retval);
3025 vam->result_ready = 1;
3026}
3027
3028/* Format hex dump. */
3029u8 *
3030format_hex_bytes (u8 * s, va_list * va)
3031{
3032 u8 *bytes = va_arg (*va, u8 *);
3033 int n_bytes = va_arg (*va, int);
3034 uword i;
3035
3036 /* Print short or long form depending on byte count. */
3037 uword short_form = n_bytes <= 32;
Christophe Fontained3c008d2017-10-02 18:10:54 +02003038 u32 indent = format_get_indent (s);
Damjan Marion7cd468a2016-12-19 23:05:39 +01003039
3040 if (n_bytes == 0)
3041 return s;
3042
3043 for (i = 0; i < n_bytes; i++)
3044 {
3045 if (!short_form && (i % 32) == 0)
3046 s = format (s, "%08x: ", i);
3047 s = format (s, "%02x", bytes[i]);
3048 if (!short_form && ((i + 1) % 32) == 0 && (i + 1) < n_bytes)
3049 s = format (s, "\n%U", format_white_space, indent);
3050 }
3051
3052 return s;
3053}
3054
3055static void
3056vl_api_classify_table_info_reply_t_handler (vl_api_classify_table_info_reply_t
3057 * mp)
3058{
3059 vat_main_t *vam = &vat_main;
3060 i32 retval = ntohl (mp->retval);
3061 if (retval == 0)
3062 {
3063 print (vam->ofp, "classify table info :");
3064 print (vam->ofp, "sessions: %d nexttbl: %d nextnode: %d",
3065 ntohl (mp->active_sessions), ntohl (mp->next_table_index),
3066 ntohl (mp->miss_next_index));
3067 print (vam->ofp, "nbuckets: %d skip: %d match: %d",
3068 ntohl (mp->nbuckets), ntohl (mp->skip_n_vectors),
3069 ntohl (mp->match_n_vectors));
3070 print (vam->ofp, "mask: %U", format_hex_bytes, mp->mask,
3071 ntohl (mp->mask_length));
3072 }
3073 vam->retval = retval;
3074 vam->result_ready = 1;
3075}
3076
3077static void
3078 vl_api_classify_table_info_reply_t_handler_json
3079 (vl_api_classify_table_info_reply_t * mp)
3080{
3081 vat_main_t *vam = &vat_main;
3082 vat_json_node_t node;
3083
3084 i32 retval = ntohl (mp->retval);
3085 if (retval == 0)
3086 {
3087 vat_json_init_object (&node);
3088
3089 vat_json_object_add_int (&node, "sessions",
3090 ntohl (mp->active_sessions));
3091 vat_json_object_add_int (&node, "nexttbl",
3092 ntohl (mp->next_table_index));
3093 vat_json_object_add_int (&node, "nextnode",
3094 ntohl (mp->miss_next_index));
3095 vat_json_object_add_int (&node, "nbuckets", ntohl (mp->nbuckets));
3096 vat_json_object_add_int (&node, "skip", ntohl (mp->skip_n_vectors));
3097 vat_json_object_add_int (&node, "match", ntohl (mp->match_n_vectors));
3098 u8 *s = format (0, "%U%c", format_hex_bytes, mp->mask,
3099 ntohl (mp->mask_length), 0);
3100 vat_json_object_add_string_copy (&node, "mask", s);
3101
3102 vat_json_print (vam->ofp, &node);
3103 vat_json_free (&node);
3104 }
3105 vam->retval = ntohl (mp->retval);
3106 vam->result_ready = 1;
3107}
3108
3109static void
3110vl_api_classify_session_details_t_handler (vl_api_classify_session_details_t *
3111 mp)
3112{
3113 vat_main_t *vam = &vat_main;
3114
3115 print (vam->ofp, "next_index: %d advance: %d opaque: %d ",
3116 ntohl (mp->hit_next_index), ntohl (mp->advance),
3117 ntohl (mp->opaque_index));
3118 print (vam->ofp, "mask: %U", format_hex_bytes, mp->match,
3119 ntohl (mp->match_length));
3120}
3121
3122static void
3123 vl_api_classify_session_details_t_handler_json
3124 (vl_api_classify_session_details_t * mp)
3125{
3126 vat_main_t *vam = &vat_main;
3127 vat_json_node_t *node = NULL;
3128
3129 if (VAT_JSON_ARRAY != vam->json_tree.type)
3130 {
3131 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
3132 vat_json_init_array (&vam->json_tree);
3133 }
3134 node = vat_json_array_add (&vam->json_tree);
3135
3136 vat_json_init_object (node);
3137 vat_json_object_add_int (node, "next_index", ntohl (mp->hit_next_index));
3138 vat_json_object_add_int (node, "advance", ntohl (mp->advance));
3139 vat_json_object_add_int (node, "opaque", ntohl (mp->opaque_index));
3140 u8 *s =
3141 format (0, "%U%c", format_hex_bytes, mp->match, ntohl (mp->match_length),
3142 0);
3143 vat_json_object_add_string_copy (node, "match", s);
3144}
3145
3146static void vl_api_pg_create_interface_reply_t_handler
3147 (vl_api_pg_create_interface_reply_t * mp)
3148{
3149 vat_main_t *vam = &vat_main;
3150
3151 vam->retval = ntohl (mp->retval);
3152 vam->result_ready = 1;
3153}
3154
3155static void vl_api_pg_create_interface_reply_t_handler_json
3156 (vl_api_pg_create_interface_reply_t * mp)
3157{
3158 vat_main_t *vam = &vat_main;
3159 vat_json_node_t node;
3160
3161 i32 retval = ntohl (mp->retval);
3162 if (retval == 0)
3163 {
3164 vat_json_init_object (&node);
3165
3166 vat_json_object_add_int (&node, "sw_if_index", ntohl (mp->sw_if_index));
3167
3168 vat_json_print (vam->ofp, &node);
3169 vat_json_free (&node);
3170 }
3171 vam->retval = ntohl (mp->retval);
3172 vam->result_ready = 1;
3173}
3174
3175static void vl_api_policer_classify_details_t_handler
3176 (vl_api_policer_classify_details_t * mp)
3177{
3178 vat_main_t *vam = &vat_main;
3179
3180 print (vam->ofp, "%10d%20d", ntohl (mp->sw_if_index),
3181 ntohl (mp->table_index));
3182}
3183
3184static void vl_api_policer_classify_details_t_handler_json
3185 (vl_api_policer_classify_details_t * mp)
3186{
3187 vat_main_t *vam = &vat_main;
3188 vat_json_node_t *node;
3189
3190 if (VAT_JSON_ARRAY != vam->json_tree.type)
3191 {
3192 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
3193 vat_json_init_array (&vam->json_tree);
3194 }
3195 node = vat_json_array_add (&vam->json_tree);
3196
3197 vat_json_init_object (node);
3198 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
3199 vat_json_object_add_uint (node, "table_index", ntohl (mp->table_index));
3200}
3201
Damjan Marion7cd468a2016-12-19 23:05:39 +01003202static void vl_api_flow_classify_details_t_handler
3203 (vl_api_flow_classify_details_t * mp)
3204{
3205 vat_main_t *vam = &vat_main;
3206
3207 print (vam->ofp, "%10d%20d", ntohl (mp->sw_if_index),
3208 ntohl (mp->table_index));
3209}
3210
3211static void vl_api_flow_classify_details_t_handler_json
3212 (vl_api_flow_classify_details_t * mp)
3213{
3214 vat_main_t *vam = &vat_main;
3215 vat_json_node_t *node;
3216
3217 if (VAT_JSON_ARRAY != vam->json_tree.type)
3218 {
3219 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
3220 vat_json_init_array (&vam->json_tree);
3221 }
3222 node = vat_json_array_add (&vam->json_tree);
3223
3224 vat_json_init_object (node);
3225 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
3226 vat_json_object_add_uint (node, "table_index", ntohl (mp->table_index));
3227}
3228
Damjan Marion7cd468a2016-12-19 23:05:39 +01003229/*
3230 * Generate boilerplate reply handlers, which
3231 * dig the return value out of the xxx_reply_t API message,
3232 * stick it into vam->retval, and set vam->result_ready
3233 *
3234 * Could also do this by pointing N message decode slots at
3235 * a single function, but that could break in subtle ways.
3236 */
3237
3238#define foreach_standard_reply_retval_handler \
3239_(sw_interface_set_flags_reply) \
3240_(sw_interface_add_del_address_reply) \
Stevenad8015b2017-10-29 22:10:46 -07003241_(sw_interface_set_rx_mode_reply) \
Mohsin Kazmi54f7c512018-08-23 18:28:11 +02003242_(sw_interface_set_rx_placement_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003243_(sw_interface_set_table_reply) \
3244_(sw_interface_set_mpls_enable_reply) \
3245_(sw_interface_set_vpath_reply) \
3246_(sw_interface_set_vxlan_bypass_reply) \
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +08003247_(sw_interface_set_vxlan_gpe_bypass_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003248_(sw_interface_set_l2_bridge_reply) \
Steven Luonga1876b82019-08-20 16:58:00 -07003249_(sw_interface_set_bond_weight_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003250_(bridge_domain_add_del_reply) \
3251_(sw_interface_set_l2_xconnect_reply) \
3252_(l2fib_add_del_reply) \
Eyal Barif24991c2017-04-05 05:33:21 +03003253_(l2fib_flush_int_reply) \
3254_(l2fib_flush_bd_reply) \
Neale Ranns097fa662018-05-01 05:17:55 -07003255_(ip_route_add_del_reply) \
Neale Ranns28ab9cc2017-08-14 07:18:42 -07003256_(ip_table_add_del_reply) \
Neale Ranns9db6ada2019-11-08 12:42:31 +00003257_(ip_table_replace_begin_reply) \
3258_(ip_table_flush_reply) \
3259_(ip_table_replace_end_reply) \
Neale Ranns32e1c012016-11-22 17:07:28 +00003260_(ip_mroute_add_del_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003261_(mpls_route_add_del_reply) \
Neale Ranns28ab9cc2017-08-14 07:18:42 -07003262_(mpls_table_add_del_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003263_(mpls_ip_bind_unbind_reply) \
Neale Rannsd792d9c2017-10-21 10:53:20 -07003264_(bier_route_add_del_reply) \
3265_(bier_table_add_del_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003266_(sw_interface_set_unnumbered_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003267_(set_ip_flow_hash_reply) \
3268_(sw_interface_ip6_enable_disable_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003269_(l2_patch_add_del_reply) \
John Loe166fd92018-09-13 14:08:59 -04003270_(sr_mpls_policy_add_reply) \
3271_(sr_mpls_policy_mod_reply) \
3272_(sr_mpls_policy_del_reply) \
Pablo Camarillofb380952016-12-07 18:34:18 +01003273_(sr_policy_add_reply) \
3274_(sr_policy_mod_reply) \
3275_(sr_policy_del_reply) \
3276_(sr_localsid_add_del_reply) \
3277_(sr_steering_add_del_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003278_(classify_add_del_session_reply) \
3279_(classify_set_interface_ip_table_reply) \
3280_(classify_set_interface_l2_tables_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003281_(l2_fib_clear_table_reply) \
3282_(l2_interface_efp_filter_reply) \
3283_(l2_interface_vlan_tag_rewrite_reply) \
3284_(modify_vhost_user_if_reply) \
Steven Luong27ba5002020-11-17 13:30:44 -08003285_(modify_vhost_user_if_v2_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003286_(delete_vhost_user_if_reply) \
John Lo8d00fff2017-08-03 00:35:36 -04003287_(want_l2_macs_events_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003288_(input_acl_set_interface_reply) \
3289_(ipsec_spd_add_del_reply) \
3290_(ipsec_interface_add_del_spd_reply) \
Neale Ranns17dcec02019-01-09 21:22:20 -08003291_(ipsec_spd_entry_add_del_reply) \
3292_(ipsec_sad_entry_add_del_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003293_(delete_loopback_reply) \
3294_(bd_ip_mac_add_del_reply) \
John Loe26c81f2019-01-07 15:16:33 -05003295_(bd_ip_mac_flush_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003296_(want_interface_events_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003297_(cop_interface_enable_disable_reply) \
3298_(cop_whitelist_enable_disable_reply) \
3299_(sw_interface_clear_stats_reply) \
Dave Barach65457162017-10-10 17:53:14 -04003300_(ioam_enable_reply) \
3301_(ioam_disable_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003302_(af_packet_delete_reply) \
3303_(policer_classify_set_interface_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003304_(set_ipfix_exporter_reply) \
3305_(set_ipfix_classify_stream_reply) \
3306_(ipfix_classify_table_add_del_reply) \
3307_(flow_classify_set_interface_reply) \
3308_(sw_interface_span_enable_disable_reply) \
3309_(pg_capture_reply) \
3310_(pg_enable_disable_reply) \
Mohsin Kazmif382b062020-08-11 15:00:44 +02003311_(pg_interface_enable_disable_coalesce_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003312_(ip_source_and_port_range_check_add_del_reply) \
3313_(ip_source_and_port_range_check_interface_add_del_reply)\
3314_(delete_subif_reply) \
3315_(l2_interface_pbb_tag_rewrite_reply) \
Pavel Kotuceke88865d2018-11-28 07:42:11 +01003316_(set_punt_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003317_(feature_enable_disable_reply) \
Mohsin Kazmi29467b52019-10-08 19:42:38 +02003318_(feature_gso_enable_disable_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003319_(sw_interface_tag_add_del_reply) \
Matthew Smithe0792fd2019-07-12 11:48:24 -05003320_(sw_interface_add_del_mac_address_reply) \
Ole Troand7231612018-06-07 10:17:57 +02003321_(hw_interface_set_mtu_reply) \
Pavel Kotucek6899a302017-06-08 08:46:10 +02003322_(p2p_ethernet_add_reply) \
Steve Shin99a0e602017-07-01 04:16:20 +00003323_(p2p_ethernet_del_reply) \
Florin Corascea194d2017-10-02 00:18:51 -07003324_(tcp_configure_src_addresses_reply) \
Florin Coras595992c2017-11-06 17:17:08 -08003325_(session_rule_add_del_reply) \
Andrew Yourtchenko815d7d52018-02-07 11:37:02 +01003326_(ip_container_proxy_add_del_reply) \
Igor Mikhailov (imichail)582caa32018-04-26 21:33:02 -07003327_(output_acl_set_interface_reply) \
Chenmin Sund0236f72020-07-27 17:54:40 +08003328_(qos_record_enable_disable_reply) \
3329_(flow_add_reply)
Damjan Marion7cd468a2016-12-19 23:05:39 +01003330
3331#define _(n) \
3332 static void vl_api_##n##_t_handler \
3333 (vl_api_##n##_t * mp) \
3334 { \
3335 vat_main_t * vam = &vat_main; \
3336 i32 retval = ntohl(mp->retval); \
3337 if (vam->async_mode) { \
3338 vam->async_errors += (retval < 0); \
3339 } else { \
3340 vam->retval = retval; \
3341 vam->result_ready = 1; \
3342 } \
3343 }
3344foreach_standard_reply_retval_handler;
3345#undef _
3346
3347#define _(n) \
3348 static void vl_api_##n##_t_handler_json \
3349 (vl_api_##n##_t * mp) \
3350 { \
3351 vat_main_t * vam = &vat_main; \
3352 vat_json_node_t node; \
3353 vat_json_init_object(&node); \
3354 vat_json_object_add_int(&node, "retval", ntohl(mp->retval)); \
3355 vat_json_print(vam->ofp, &node); \
3356 vam->retval = ntohl(mp->retval); \
3357 vam->result_ready = 1; \
3358 }
3359foreach_standard_reply_retval_handler;
3360#undef _
3361
3362/*
3363 * Table of message reply handlers, must include boilerplate handlers
3364 * we just generated
3365 */
3366
3367#define foreach_vpe_api_reply_msg \
3368_(CREATE_LOOPBACK_REPLY, create_loopback_reply) \
Jon Loeligerc83c3b72017-02-23 13:57:35 -06003369_(CREATE_LOOPBACK_INSTANCE_REPLY, create_loopback_instance_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003370_(SW_INTERFACE_DETAILS, sw_interface_details) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003371_(SW_INTERFACE_SET_FLAGS_REPLY, sw_interface_set_flags_reply) \
3372_(CONTROL_PING_REPLY, control_ping_reply) \
3373_(CLI_REPLY, cli_reply) \
3374_(CLI_INBAND_REPLY, cli_inband_reply) \
3375_(SW_INTERFACE_ADD_DEL_ADDRESS_REPLY, \
3376 sw_interface_add_del_address_reply) \
Stevenad8015b2017-10-29 22:10:46 -07003377_(SW_INTERFACE_SET_RX_MODE_REPLY, sw_interface_set_rx_mode_reply) \
Mohsin Kazmi54f7c512018-08-23 18:28:11 +02003378_(SW_INTERFACE_SET_RX_PLACEMENT_REPLY, sw_interface_set_rx_placement_reply) \
Mohsin Kazmif0b42f42018-09-10 18:11:00 +02003379_(SW_INTERFACE_RX_PLACEMENT_DETAILS, sw_interface_rx_placement_details) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003380_(SW_INTERFACE_SET_TABLE_REPLY, sw_interface_set_table_reply) \
3381_(SW_INTERFACE_SET_MPLS_ENABLE_REPLY, sw_interface_set_mpls_enable_reply) \
3382_(SW_INTERFACE_SET_VPATH_REPLY, sw_interface_set_vpath_reply) \
3383_(SW_INTERFACE_SET_VXLAN_BYPASS_REPLY, sw_interface_set_vxlan_bypass_reply) \
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +08003384_(SW_INTERFACE_SET_VXLAN_GPE_BYPASS_REPLY, sw_interface_set_vxlan_gpe_bypass_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003385_(SW_INTERFACE_SET_L2_XCONNECT_REPLY, \
3386 sw_interface_set_l2_xconnect_reply) \
3387_(SW_INTERFACE_SET_L2_BRIDGE_REPLY, \
3388 sw_interface_set_l2_bridge_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003389_(BRIDGE_DOMAIN_ADD_DEL_REPLY, bridge_domain_add_del_reply) \
3390_(BRIDGE_DOMAIN_DETAILS, bridge_domain_details) \
Eyal Barifead6702017-04-04 04:46:32 +03003391_(BRIDGE_DOMAIN_SET_MAC_AGE_REPLY, bridge_domain_set_mac_age_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003392_(L2FIB_ADD_DEL_REPLY, l2fib_add_del_reply) \
Eyal Barif24991c2017-04-05 05:33:21 +03003393_(L2FIB_FLUSH_INT_REPLY, l2fib_flush_int_reply) \
3394_(L2FIB_FLUSH_BD_REPLY, l2fib_flush_bd_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003395_(L2_FLAGS_REPLY, l2_flags_reply) \
3396_(BRIDGE_FLAGS_REPLY, bridge_flags_reply) \
Damjan Marion8389fb92017-10-13 18:29:53 +02003397_(TAP_CREATE_V2_REPLY, tap_create_v2_reply) \
3398_(TAP_DELETE_V2_REPLY, tap_delete_v2_reply) \
3399_(SW_INTERFACE_TAP_V2_DETAILS, sw_interface_tap_v2_details) \
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01003400_(VIRTIO_PCI_CREATE_REPLY, virtio_pci_create_reply) \
Mohsin Kazmi518251b2020-09-01 17:17:44 +00003401_(VIRTIO_PCI_CREATE_V2_REPLY, virtio_pci_create_v2_reply) \
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01003402_(VIRTIO_PCI_DELETE_REPLY, virtio_pci_delete_reply) \
3403_(SW_INTERFACE_VIRTIO_PCI_DETAILS, sw_interface_virtio_pci_details) \
Steven9cd2d7a2017-12-20 12:43:01 -08003404_(BOND_CREATE_REPLY, bond_create_reply) \
Steven Luongea717862020-07-30 07:31:40 -07003405_(BOND_CREATE2_REPLY, bond_create2_reply) \
Steven9cd2d7a2017-12-20 12:43:01 -08003406_(BOND_DELETE_REPLY, bond_delete_reply) \
Steven Luong4c4223e2020-07-15 08:44:54 -07003407_(BOND_ADD_MEMBER_REPLY, bond_add_member_reply) \
3408_(BOND_DETACH_MEMBER_REPLY, bond_detach_member_reply) \
Steven Luonga1876b82019-08-20 16:58:00 -07003409_(SW_INTERFACE_SET_BOND_WEIGHT_REPLY, sw_interface_set_bond_weight_reply) \
Steven Luong4c4223e2020-07-15 08:44:54 -07003410_(SW_BOND_INTERFACE_DETAILS, sw_bond_interface_details) \
3411_(SW_MEMBER_INTERFACE_DETAILS, sw_member_interface_details) \
Neale Ranns097fa662018-05-01 05:17:55 -07003412_(IP_ROUTE_ADD_DEL_REPLY, ip_route_add_del_reply) \
Neale Ranns28ab9cc2017-08-14 07:18:42 -07003413_(IP_TABLE_ADD_DEL_REPLY, ip_table_add_del_reply) \
Neale Ranns9db6ada2019-11-08 12:42:31 +00003414_(IP_TABLE_REPLACE_BEGIN_REPLY, ip_table_replace_begin_reply) \
3415_(IP_TABLE_FLUSH_REPLY, ip_table_flush_reply) \
3416_(IP_TABLE_REPLACE_END_REPLY, ip_table_replace_end_reply) \
Neale Ranns32e1c012016-11-22 17:07:28 +00003417_(IP_MROUTE_ADD_DEL_REPLY, ip_mroute_add_del_reply) \
Neale Ranns28ab9cc2017-08-14 07:18:42 -07003418_(MPLS_TABLE_ADD_DEL_REPLY, mpls_table_add_del_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003419_(MPLS_ROUTE_ADD_DEL_REPLY, mpls_route_add_del_reply) \
3420_(MPLS_IP_BIND_UNBIND_REPLY, mpls_ip_bind_unbind_reply) \
Neale Rannsd792d9c2017-10-21 10:53:20 -07003421_(BIER_ROUTE_ADD_DEL_REPLY, bier_route_add_del_reply) \
3422_(BIER_TABLE_ADD_DEL_REPLY, bier_table_add_del_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003423_(MPLS_TUNNEL_ADD_DEL_REPLY, mpls_tunnel_add_del_reply) \
3424_(SW_INTERFACE_SET_UNNUMBERED_REPLY, \
3425 sw_interface_set_unnumbered_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003426_(CREATE_VLAN_SUBIF_REPLY, create_vlan_subif_reply) \
3427_(CREATE_SUBIF_REPLY, create_subif_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003428_(SET_IP_FLOW_HASH_REPLY, set_ip_flow_hash_reply) \
3429_(SW_INTERFACE_IP6_ENABLE_DISABLE_REPLY, \
3430 sw_interface_ip6_enable_disable_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003431_(L2_PATCH_ADD_DEL_REPLY, l2_patch_add_del_reply) \
John Loe166fd92018-09-13 14:08:59 -04003432_(SR_MPLS_POLICY_ADD_REPLY, sr_mpls_policy_add_reply) \
3433_(SR_MPLS_POLICY_MOD_REPLY, sr_mpls_policy_mod_reply) \
3434_(SR_MPLS_POLICY_DEL_REPLY, sr_mpls_policy_del_reply) \
Pablo Camarillofb380952016-12-07 18:34:18 +01003435_(SR_POLICY_ADD_REPLY, sr_policy_add_reply) \
3436_(SR_POLICY_MOD_REPLY, sr_policy_mod_reply) \
3437_(SR_POLICY_DEL_REPLY, sr_policy_del_reply) \
3438_(SR_LOCALSID_ADD_DEL_REPLY, sr_localsid_add_del_reply) \
3439_(SR_STEERING_ADD_DEL_REPLY, sr_steering_add_del_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003440_(CLASSIFY_ADD_DEL_TABLE_REPLY, classify_add_del_table_reply) \
3441_(CLASSIFY_ADD_DEL_SESSION_REPLY, classify_add_del_session_reply) \
3442_(CLASSIFY_SET_INTERFACE_IP_TABLE_REPLY, \
3443classify_set_interface_ip_table_reply) \
3444_(CLASSIFY_SET_INTERFACE_L2_TABLES_REPLY, \
3445 classify_set_interface_l2_tables_reply) \
3446_(GET_NODE_INDEX_REPLY, get_node_index_reply) \
3447_(ADD_NODE_NEXT_REPLY, add_node_next_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003448_(VXLAN_ADD_DEL_TUNNEL_REPLY, vxlan_add_del_tunnel_reply) \
eyal bariaf86a482018-04-17 11:20:27 +03003449_(VXLAN_OFFLOAD_RX_REPLY, vxlan_offload_rx_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003450_(VXLAN_TUNNEL_DETAILS, vxlan_tunnel_details) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003451_(L2_FIB_CLEAR_TABLE_REPLY, l2_fib_clear_table_reply) \
3452_(L2_INTERFACE_EFP_FILTER_REPLY, l2_interface_efp_filter_reply) \
3453_(L2_INTERFACE_VLAN_TAG_REWRITE_REPLY, l2_interface_vlan_tag_rewrite_reply) \
3454_(SW_INTERFACE_VHOST_USER_DETAILS, sw_interface_vhost_user_details) \
3455_(CREATE_VHOST_USER_IF_REPLY, create_vhost_user_if_reply) \
3456_(MODIFY_VHOST_USER_IF_REPLY, modify_vhost_user_if_reply) \
Steven Luong27ba5002020-11-17 13:30:44 -08003457_(CREATE_VHOST_USER_IF_V2_REPLY, create_vhost_user_if_v2_reply) \
3458_(MODIFY_VHOST_USER_IF_V2_REPLY, modify_vhost_user_if_v2_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003459_(DELETE_VHOST_USER_IF_REPLY, delete_vhost_user_if_reply) \
3460_(SHOW_VERSION_REPLY, show_version_reply) \
Mohsin Kazmi5d64c782018-09-11 20:27:09 +02003461_(SHOW_THREADS_REPLY, show_threads_reply) \
Ole Troan01384fe2017-05-12 11:55:35 +02003462_(L2_FIB_TABLE_DETAILS, l2_fib_table_details) \
John Loc7b43042018-04-13 16:46:22 -04003463_(VXLAN_GPE_ADD_DEL_TUNNEL_REPLY, vxlan_gpe_add_del_tunnel_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003464_(VXLAN_GPE_TUNNEL_DETAILS, vxlan_gpe_tunnel_details) \
3465_(INTERFACE_NAME_RENUMBER_REPLY, interface_name_renumber_reply) \
John Lo8d00fff2017-08-03 00:35:36 -04003466_(WANT_L2_MACS_EVENTS_REPLY, want_l2_macs_events_reply) \
3467_(L2_MACS_EVENT, l2_macs_event) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003468_(INPUT_ACL_SET_INTERFACE_REPLY, input_acl_set_interface_reply) \
3469_(IP_ADDRESS_DETAILS, ip_address_details) \
3470_(IP_DETAILS, ip_details) \
3471_(IPSEC_SPD_ADD_DEL_REPLY, ipsec_spd_add_del_reply) \
3472_(IPSEC_INTERFACE_ADD_DEL_SPD_REPLY, ipsec_interface_add_del_spd_reply) \
Neale Ranns17dcec02019-01-09 21:22:20 -08003473_(IPSEC_SPD_ENTRY_ADD_DEL_REPLY, ipsec_spd_entry_add_del_reply) \
3474_(IPSEC_SAD_ENTRY_ADD_DEL_REPLY, ipsec_sad_entry_add_del_reply) \
Matthew Smith28029532017-09-26 13:33:44 -05003475_(IPSEC_SA_DETAILS, ipsec_sa_details) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003476_(DELETE_LOOPBACK_REPLY, delete_loopback_reply) \
3477_(BD_IP_MAC_ADD_DEL_REPLY, bd_ip_mac_add_del_reply) \
John Loe26c81f2019-01-07 15:16:33 -05003478_(BD_IP_MAC_FLUSH_REPLY, bd_ip_mac_flush_reply) \
Mohsin Kazmi5d82d2f2018-08-13 19:17:54 +02003479_(BD_IP_MAC_DETAILS, bd_ip_mac_details) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003480_(WANT_INTERFACE_EVENTS_REPLY, want_interface_events_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003481_(GET_FIRST_MSG_ID_REPLY, get_first_msg_id_reply) \
3482_(COP_INTERFACE_ENABLE_DISABLE_REPLY, cop_interface_enable_disable_reply) \
3483_(COP_WHITELIST_ENABLE_DISABLE_REPLY, cop_whitelist_enable_disable_reply) \
3484_(GET_NODE_GRAPH_REPLY, get_node_graph_reply) \
3485_(SW_INTERFACE_CLEAR_STATS_REPLY, sw_interface_clear_stats_reply) \
3486_(IOAM_ENABLE_REPLY, ioam_enable_reply) \
3487_(IOAM_DISABLE_REPLY, ioam_disable_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003488_(AF_PACKET_CREATE_REPLY, af_packet_create_reply) \
3489_(AF_PACKET_DELETE_REPLY, af_packet_delete_reply) \
Mohsin Kazmi04e0bb22018-05-28 18:55:37 +02003490_(AF_PACKET_DETAILS, af_packet_details) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003491_(POLICER_ADD_DEL_REPLY, policer_add_del_reply) \
3492_(POLICER_DETAILS, policer_details) \
3493_(POLICER_CLASSIFY_SET_INTERFACE_REPLY, policer_classify_set_interface_reply) \
3494_(POLICER_CLASSIFY_DETAILS, policer_classify_details) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003495_(MPLS_TUNNEL_DETAILS, mpls_tunnel_details) \
Neale Ranns097fa662018-05-01 05:17:55 -07003496_(MPLS_TABLE_DETAILS, mpls_table_details) \
3497_(MPLS_ROUTE_DETAILS, mpls_route_details) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003498_(CLASSIFY_TABLE_IDS_REPLY, classify_table_ids_reply) \
3499_(CLASSIFY_TABLE_BY_INTERFACE_REPLY, classify_table_by_interface_reply) \
3500_(CLASSIFY_TABLE_INFO_REPLY, classify_table_info_reply) \
3501_(CLASSIFY_SESSION_DETAILS, classify_session_details) \
3502_(SET_IPFIX_EXPORTER_REPLY, set_ipfix_exporter_reply) \
3503_(IPFIX_EXPORTER_DETAILS, ipfix_exporter_details) \
3504_(SET_IPFIX_CLASSIFY_STREAM_REPLY, set_ipfix_classify_stream_reply) \
3505_(IPFIX_CLASSIFY_STREAM_DETAILS, ipfix_classify_stream_details) \
3506_(IPFIX_CLASSIFY_TABLE_ADD_DEL_REPLY, ipfix_classify_table_add_del_reply) \
3507_(IPFIX_CLASSIFY_TABLE_DETAILS, ipfix_classify_table_details) \
3508_(FLOW_CLASSIFY_SET_INTERFACE_REPLY, flow_classify_set_interface_reply) \
3509_(FLOW_CLASSIFY_DETAILS, flow_classify_details) \
3510_(SW_INTERFACE_SPAN_ENABLE_DISABLE_REPLY, sw_interface_span_enable_disable_reply) \
3511_(SW_INTERFACE_SPAN_DETAILS, sw_interface_span_details) \
3512_(GET_NEXT_INDEX_REPLY, get_next_index_reply) \
3513_(PG_CREATE_INTERFACE_REPLY, pg_create_interface_reply) \
3514_(PG_CAPTURE_REPLY, pg_capture_reply) \
3515_(PG_ENABLE_DISABLE_REPLY, pg_enable_disable_reply) \
Mohsin Kazmif382b062020-08-11 15:00:44 +02003516_(PG_INTERFACE_ENABLE_DISABLE_COALESCE_REPLY, pg_interface_enable_disable_coalesce_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003517_(IP_SOURCE_AND_PORT_RANGE_CHECK_ADD_DEL_REPLY, \
3518 ip_source_and_port_range_check_add_del_reply) \
3519_(IP_SOURCE_AND_PORT_RANGE_CHECK_INTERFACE_ADD_DEL_REPLY, \
3520 ip_source_and_port_range_check_interface_add_del_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003521_(DELETE_SUBIF_REPLY, delete_subif_reply) \
3522_(L2_INTERFACE_PBB_TAG_REWRITE_REPLY, l2_interface_pbb_tag_rewrite_reply) \
Pavel Kotuceke88865d2018-11-28 07:42:11 +01003523_(SET_PUNT_REPLY, set_punt_reply) \
Neale Ranns097fa662018-05-01 05:17:55 -07003524_(IP_TABLE_DETAILS, ip_table_details) \
3525_(IP_ROUTE_DETAILS, ip_route_details) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003526_(FEATURE_ENABLE_DISABLE_REPLY, feature_enable_disable_reply) \
Mohsin Kazmi29467b52019-10-08 19:42:38 +02003527_(FEATURE_GSO_ENABLE_DISABLE_REPLY, feature_gso_enable_disable_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003528_(SW_INTERFACE_TAG_ADD_DEL_REPLY, sw_interface_tag_add_del_reply) \
Matthew Smithe0792fd2019-07-12 11:48:24 -05003529_(SW_INTERFACE_ADD_DEL_MAC_ADDRESS_REPLY, sw_interface_add_del_mac_address_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003530_(L2_XCONNECT_DETAILS, l2_xconnect_details) \
Ole Troand7231612018-06-07 10:17:57 +02003531_(HW_INTERFACE_SET_MTU_REPLY, hw_interface_set_mtu_reply) \
Pavel Kotucek6899a302017-06-08 08:46:10 +02003532_(SW_INTERFACE_GET_TABLE_REPLY, sw_interface_get_table_reply) \
3533_(P2P_ETHERNET_ADD_REPLY, p2p_ethernet_add_reply) \
Steve Shin99a0e602017-07-01 04:16:20 +00003534_(P2P_ETHERNET_DEL_REPLY, p2p_ethernet_del_reply) \
Florin Corascea194d2017-10-02 00:18:51 -07003535_(TCP_CONFIGURE_SRC_ADDRESSES_REPLY, tcp_configure_src_addresses_reply) \
Dave Barach65457162017-10-10 17:53:14 -04003536_(APP_NAMESPACE_ADD_DEL_REPLY, app_namespace_add_del_reply) \
Florin Coras6c36f532017-11-03 18:32:34 -07003537_(SESSION_RULE_ADD_DEL_REPLY, session_rule_add_del_reply) \
Florin Coras595992c2017-11-06 17:17:08 -08003538_(SESSION_RULES_DETAILS, session_rules_details) \
3539_(IP_CONTAINER_PROXY_ADD_DEL_REPLY, ip_container_proxy_add_del_reply) \
Andrew Yourtchenko815d7d52018-02-07 11:37:02 +01003540_(OUTPUT_ACL_SET_INTERFACE_REPLY, output_acl_set_interface_reply) \
Chenmin Sund0236f72020-07-27 17:54:40 +08003541_(QOS_RECORD_ENABLE_DISABLE_REPLY, qos_record_enable_disable_reply) \
3542_(FLOW_ADD_REPLY, flow_add_reply) \
Damjan Marion7cd468a2016-12-19 23:05:39 +01003543
Dave Baracha1a093d2017-03-02 13:13:23 -05003544#define foreach_standalone_reply_msg \
Ole Troanf49ba0e2018-11-13 14:04:50 +01003545_(SW_INTERFACE_EVENT, sw_interface_event)
Dave Baracha1a093d2017-03-02 13:13:23 -05003546
Damjan Marion7cd468a2016-12-19 23:05:39 +01003547typedef struct
3548{
3549 u8 *name;
3550 u32 value;
3551} name_sort_t;
3552
Damjan Marion7cd468a2016-12-19 23:05:39 +01003553#define STR_VTR_OP_CASE(op) \
3554 case L2_VTR_ ## op: \
3555 return "" # op;
3556
3557static const char *
3558str_vtr_op (u32 vtr_op)
3559{
3560 switch (vtr_op)
3561 {
3562 STR_VTR_OP_CASE (DISABLED);
3563 STR_VTR_OP_CASE (PUSH_1);
3564 STR_VTR_OP_CASE (PUSH_2);
3565 STR_VTR_OP_CASE (POP_1);
3566 STR_VTR_OP_CASE (POP_2);
3567 STR_VTR_OP_CASE (TRANSLATE_1_1);
3568 STR_VTR_OP_CASE (TRANSLATE_1_2);
3569 STR_VTR_OP_CASE (TRANSLATE_2_1);
3570 STR_VTR_OP_CASE (TRANSLATE_2_2);
3571 }
3572
3573 return "UNKNOWN";
3574}
3575
3576static int
3577dump_sub_interface_table (vat_main_t * vam)
3578{
3579 const sw_interface_subif_t *sub = NULL;
3580
3581 if (vam->json_output)
3582 {
3583 clib_warning
3584 ("JSON output supported only for VPE API calls and dump_stats_table");
3585 return -99;
3586 }
3587
3588 print (vam->ofp,
3589 "%-30s%-12s%-11s%-7s%-5s%-9s%-9s%-6s%-8s%-10s%-10s",
3590 "Interface", "sw_if_index",
3591 "sub id", "dot1ad", "tags", "outer id",
3592 "inner id", "exact", "default", "outer any", "inner any");
3593
3594 vec_foreach (sub, vam->sw_if_subif_table)
3595 {
3596 print (vam->ofp,
3597 "%-30s%-12d%-11d%-7s%-5d%-9d%-9d%-6d%-8d%-10d%-10d",
3598 sub->interface_name,
3599 sub->sw_if_index,
3600 sub->sub_id, sub->sub_dot1ad ? "dot1ad" : "dot1q",
3601 sub->sub_number_of_tags, sub->sub_outer_vlan_id,
3602 sub->sub_inner_vlan_id, sub->sub_exact_match, sub->sub_default,
3603 sub->sub_outer_vlan_id_any, sub->sub_inner_vlan_id_any);
3604 if (sub->vtr_op != L2_VTR_DISABLED)
3605 {
3606 print (vam->ofp,
3607 " vlan-tag-rewrite - op: %-14s [ dot1q: %d "
3608 "tag1: %d tag2: %d ]",
3609 str_vtr_op (sub->vtr_op), sub->vtr_push_dot1q,
3610 sub->vtr_tag1, sub->vtr_tag2);
3611 }
3612 }
3613
3614 return 0;
3615}
3616
3617static int
3618name_sort_cmp (void *a1, void *a2)
3619{
3620 name_sort_t *n1 = a1;
3621 name_sort_t *n2 = a2;
3622
3623 return strcmp ((char *) n1->name, (char *) n2->name);
3624}
3625
3626static int
3627dump_interface_table (vat_main_t * vam)
3628{
3629 hash_pair_t *p;
3630 name_sort_t *nses = 0, *ns;
3631
3632 if (vam->json_output)
3633 {
3634 clib_warning
3635 ("JSON output supported only for VPE API calls and dump_stats_table");
3636 return -99;
3637 }
3638
3639 /* *INDENT-OFF* */
3640 hash_foreach_pair (p, vam->sw_if_index_by_interface_name,
3641 ({
3642 vec_add2 (nses, ns, 1);
3643 ns->name = (u8 *)(p->key);
3644 ns->value = (u32) p->value[0];
3645 }));
3646 /* *INDENT-ON* */
3647
3648 vec_sort_with_function (nses, name_sort_cmp);
3649
3650 print (vam->ofp, "%-25s%-15s", "Interface", "sw_if_index");
3651 vec_foreach (ns, nses)
3652 {
3653 print (vam->ofp, "%-25s%-15d", ns->name, ns->value);
3654 }
3655 vec_free (nses);
3656 return 0;
3657}
3658
3659static int
3660dump_ip_table (vat_main_t * vam, int is_ipv6)
3661{
3662 const ip_details_t *det = NULL;
3663 const ip_address_details_t *address = NULL;
3664 u32 i = ~0;
3665
3666 print (vam->ofp, "%-12s", "sw_if_index");
3667
3668 vec_foreach (det, vam->ip_details_by_sw_if_index[is_ipv6])
3669 {
3670 i++;
3671 if (!det->present)
3672 {
3673 continue;
3674 }
3675 print (vam->ofp, "%-12d", i);
3676 print (vam->ofp, " %-30s%-13s", "Address", "Prefix length");
3677 if (!det->addr)
3678 {
3679 continue;
3680 }
3681 vec_foreach (address, det->addr)
3682 {
3683 print (vam->ofp,
3684 " %-30U%-13d",
3685 is_ipv6 ? format_ip6_address : format_ip4_address,
3686 address->ip, address->prefix_length);
3687 }
3688 }
3689
3690 return 0;
3691}
3692
3693static int
3694dump_ipv4_table (vat_main_t * vam)
3695{
3696 if (vam->json_output)
3697 {
3698 clib_warning
3699 ("JSON output supported only for VPE API calls and dump_stats_table");
3700 return -99;
3701 }
3702
3703 return dump_ip_table (vam, 0);
3704}
3705
3706static int
3707dump_ipv6_table (vat_main_t * vam)
3708{
3709 if (vam->json_output)
3710 {
3711 clib_warning
3712 ("JSON output supported only for VPE API calls and dump_stats_table");
3713 return -99;
3714 }
3715
3716 return dump_ip_table (vam, 1);
3717}
3718
Damjan Marion7cd468a2016-12-19 23:05:39 +01003719/*
Dave Barach59b25652017-09-10 15:04:27 -04003720 * Pass CLI buffers directly in the CLI_INBAND API message,
3721 * instead of an additional shared memory area.
Damjan Marion7cd468a2016-12-19 23:05:39 +01003722 */
3723static int
3724exec_inband (vat_main_t * vam)
3725{
3726 vl_api_cli_inband_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003727 unformat_input_t *i = vam->input;
Jon Loeliger56c7b012017-02-01 12:31:41 -06003728 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003729
3730 if (vec_len (i->buffer) == 0)
3731 return -1;
3732
3733 if (vam->exec_mode == 0 && unformat (i, "mode"))
3734 {
3735 vam->exec_mode = 1;
3736 return 0;
3737 }
3738 if (vam->exec_mode == 1 && (unformat (i, "exit") || unformat (i, "quit")))
3739 {
3740 vam->exec_mode = 0;
3741 return 0;
3742 }
3743
3744 /*
3745 * In order for the CLI command to work, it
3746 * must be a vector ending in \n, not a C-string ending
3747 * in \n\0.
3748 */
Jakub Grajciar2dbee932020-02-07 11:30:26 +01003749 M2 (CLI_INBAND, mp, vec_len (vam->input->buffer));
3750 vl_api_vec_to_api_string (vam->input->buffer, &mp->cmd);
Damjan Marion7cd468a2016-12-19 23:05:39 +01003751
Jon Loeliger7bc770c2017-01-31 14:03:33 -06003752 S (mp);
Dave Barach59b25652017-09-10 15:04:27 -04003753 W (ret);
3754 /* json responses may or may not include a useful reply... */
3755 if (vec_len (vam->cmd_reply))
Dave Barachcf5e8482017-10-17 11:48:29 -04003756 print (vam->ofp, "%v", (char *) (vam->cmd_reply));
Jon Loeliger56c7b012017-02-01 12:31:41 -06003757 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003758}
3759
Dave Barach59b25652017-09-10 15:04:27 -04003760int
3761exec (vat_main_t * vam)
3762{
3763 return exec_inband (vam);
3764}
3765
Damjan Marion7cd468a2016-12-19 23:05:39 +01003766static int
3767api_create_loopback (vat_main_t * vam)
3768{
3769 unformat_input_t *i = vam->input;
3770 vl_api_create_loopback_t *mp;
Jon Loeligerc83c3b72017-02-23 13:57:35 -06003771 vl_api_create_loopback_instance_t *mp_lbi;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003772 u8 mac_address[6];
3773 u8 mac_set = 0;
Jon Loeligerc83c3b72017-02-23 13:57:35 -06003774 u8 is_specified = 0;
3775 u32 user_instance = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06003776 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003777
Dave Barachb7b92992018-10-17 10:38:51 -04003778 clib_memset (mac_address, 0, sizeof (mac_address));
Damjan Marion7cd468a2016-12-19 23:05:39 +01003779
3780 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
3781 {
3782 if (unformat (i, "mac %U", unformat_ethernet_address, mac_address))
3783 mac_set = 1;
Jon Loeligerc83c3b72017-02-23 13:57:35 -06003784 if (unformat (i, "instance %d", &user_instance))
3785 is_specified = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003786 else
3787 break;
3788 }
3789
Jon Loeligerc83c3b72017-02-23 13:57:35 -06003790 if (is_specified)
3791 {
3792 M (CREATE_LOOPBACK_INSTANCE, mp_lbi);
3793 mp_lbi->is_specified = is_specified;
3794 if (is_specified)
3795 mp_lbi->user_instance = htonl (user_instance);
3796 if (mac_set)
3797 clib_memcpy (mp_lbi->mac_address, mac_address, sizeof (mac_address));
3798 S (mp_lbi);
3799 }
3800 else
3801 {
3802 /* Construct the API message */
3803 M (CREATE_LOOPBACK, mp);
3804 if (mac_set)
3805 clib_memcpy (mp->mac_address, mac_address, sizeof (mac_address));
3806 S (mp);
3807 }
Damjan Marion7cd468a2016-12-19 23:05:39 +01003808
Jon Loeliger56c7b012017-02-01 12:31:41 -06003809 W (ret);
3810 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003811}
3812
3813static int
3814api_delete_loopback (vat_main_t * vam)
3815{
3816 unformat_input_t *i = vam->input;
3817 vl_api_delete_loopback_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003818 u32 sw_if_index = ~0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06003819 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003820
3821 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
3822 {
3823 if (unformat (i, "sw_if_index %d", &sw_if_index))
3824 ;
3825 else
3826 break;
3827 }
3828
3829 if (sw_if_index == ~0)
3830 {
3831 errmsg ("missing sw_if_index");
3832 return -99;
3833 }
3834
3835 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06003836 M (DELETE_LOOPBACK, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01003837 mp->sw_if_index = ntohl (sw_if_index);
3838
Jon Loeliger7bc770c2017-01-31 14:03:33 -06003839 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06003840 W (ret);
3841 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003842}
3843
3844static int
Damjan Marion7cd468a2016-12-19 23:05:39 +01003845api_want_interface_events (vat_main_t * vam)
3846{
3847 unformat_input_t *i = vam->input;
3848 vl_api_want_interface_events_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003849 int enable = -1;
Jon Loeliger56c7b012017-02-01 12:31:41 -06003850 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003851
3852 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
3853 {
3854 if (unformat (i, "enable"))
3855 enable = 1;
3856 else if (unformat (i, "disable"))
3857 enable = 0;
3858 else
3859 break;
3860 }
3861
3862 if (enable == -1)
3863 {
3864 errmsg ("missing enable|disable");
3865 return -99;
3866 }
3867
Jon Loeliger8a2aea32017-01-31 13:19:40 -06003868 M (WANT_INTERFACE_EVENTS, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01003869 mp->enable_disable = enable;
3870
3871 vam->interface_event_display = enable;
3872
Jon Loeliger7bc770c2017-01-31 14:03:33 -06003873 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06003874 W (ret);
3875 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003876}
3877
3878
3879/* Note: non-static, called once to set up the initial intfc table */
3880int
3881api_sw_interface_dump (vat_main_t * vam)
3882{
3883 vl_api_sw_interface_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -06003884 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003885 hash_pair_t *p;
3886 name_sort_t *nses = 0, *ns;
3887 sw_interface_subif_t *sub = NULL;
Jon Loeliger56c7b012017-02-01 12:31:41 -06003888 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003889
3890 /* Toss the old name table */
3891 /* *INDENT-OFF* */
3892 hash_foreach_pair (p, vam->sw_if_index_by_interface_name,
3893 ({
3894 vec_add2 (nses, ns, 1);
3895 ns->name = (u8 *)(p->key);
3896 ns->value = (u32) p->value[0];
3897 }));
3898 /* *INDENT-ON* */
3899
3900 hash_free (vam->sw_if_index_by_interface_name);
3901
3902 vec_foreach (ns, nses) vec_free (ns->name);
3903
3904 vec_free (nses);
3905
3906 vec_foreach (sub, vam->sw_if_subif_table)
3907 {
3908 vec_free (sub->interface_name);
3909 }
3910 vec_free (vam->sw_if_subif_table);
3911
3912 /* recreate the interface name hash table */
3913 vam->sw_if_index_by_interface_name = hash_create_string (0, sizeof (uword));
3914
Dave Barachf72212e2018-01-11 10:25:07 -05003915 /*
3916 * Ask for all interface names. Otherwise, the epic catalog of
3917 * name filters becomes ridiculously long, and vat ends up needing
3918 * to be taught about new interface types.
3919 */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06003920 M (SW_INTERFACE_DUMP, mp);
Jon Loeliger7bc770c2017-01-31 14:03:33 -06003921 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01003922
3923 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -04003924 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -06003925 S (mp_ping);
3926
Jon Loeliger56c7b012017-02-01 12:31:41 -06003927 W (ret);
3928 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003929}
3930
3931static int
3932api_sw_interface_set_flags (vat_main_t * vam)
3933{
3934 unformat_input_t *i = vam->input;
3935 vl_api_sw_interface_set_flags_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003936 u32 sw_if_index;
3937 u8 sw_if_index_set = 0;
Neale Rannsa07bd702017-08-07 07:53:49 -07003938 u8 admin_up = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06003939 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003940
3941 /* Parse args required to build the message */
3942 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
3943 {
3944 if (unformat (i, "admin-up"))
3945 admin_up = 1;
3946 else if (unformat (i, "admin-down"))
3947 admin_up = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003948 else
3949 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
3950 sw_if_index_set = 1;
3951 else if (unformat (i, "sw_if_index %d", &sw_if_index))
3952 sw_if_index_set = 1;
3953 else
3954 break;
3955 }
3956
3957 if (sw_if_index_set == 0)
3958 {
3959 errmsg ("missing interface name or sw_if_index");
3960 return -99;
3961 }
3962
3963 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06003964 M (SW_INTERFACE_SET_FLAGS, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01003965 mp->sw_if_index = ntohl (sw_if_index);
Jakub Grajciar053204a2019-03-18 13:17:53 +01003966 mp->flags = ntohl ((admin_up) ? IF_STATUS_API_FLAG_ADMIN_UP : 0);
Damjan Marion7cd468a2016-12-19 23:05:39 +01003967
3968 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06003969 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01003970
3971 /* Wait for a reply, return the good/bad news... */
Jon Loeliger56c7b012017-02-01 12:31:41 -06003972 W (ret);
3973 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01003974}
3975
3976static int
Stevenad8015b2017-10-29 22:10:46 -07003977api_sw_interface_set_rx_mode (vat_main_t * vam)
3978{
3979 unformat_input_t *i = vam->input;
3980 vl_api_sw_interface_set_rx_mode_t *mp;
3981 u32 sw_if_index;
3982 u8 sw_if_index_set = 0;
3983 int ret;
3984 u8 queue_id_valid = 0;
3985 u32 queue_id;
Damjan Marioneabd4242020-10-07 20:59:07 +02003986 vnet_hw_if_rx_mode mode = VNET_HW_IF_RX_MODE_UNKNOWN;
Stevenad8015b2017-10-29 22:10:46 -07003987
3988 /* Parse args required to build the message */
3989 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
3990 {
3991 if (unformat (i, "queue %d", &queue_id))
3992 queue_id_valid = 1;
3993 else if (unformat (i, "polling"))
Damjan Marioneabd4242020-10-07 20:59:07 +02003994 mode = VNET_HW_IF_RX_MODE_POLLING;
Stevenad8015b2017-10-29 22:10:46 -07003995 else if (unformat (i, "interrupt"))
Damjan Marioneabd4242020-10-07 20:59:07 +02003996 mode = VNET_HW_IF_RX_MODE_INTERRUPT;
Stevenad8015b2017-10-29 22:10:46 -07003997 else if (unformat (i, "adaptive"))
Damjan Marioneabd4242020-10-07 20:59:07 +02003998 mode = VNET_HW_IF_RX_MODE_ADAPTIVE;
Stevenad8015b2017-10-29 22:10:46 -07003999 else
4000 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
4001 sw_if_index_set = 1;
4002 else if (unformat (i, "sw_if_index %d", &sw_if_index))
4003 sw_if_index_set = 1;
4004 else
4005 break;
4006 }
4007
4008 if (sw_if_index_set == 0)
4009 {
4010 errmsg ("missing interface name or sw_if_index");
4011 return -99;
4012 }
Damjan Marioneabd4242020-10-07 20:59:07 +02004013 if (mode == VNET_HW_IF_RX_MODE_UNKNOWN)
Stevenad8015b2017-10-29 22:10:46 -07004014 {
4015 errmsg ("missing rx-mode");
4016 return -99;
4017 }
4018
4019 /* Construct the API message */
4020 M (SW_INTERFACE_SET_RX_MODE, mp);
4021 mp->sw_if_index = ntohl (sw_if_index);
Jakub Grajciar053204a2019-03-18 13:17:53 +01004022 mp->mode = (vl_api_rx_mode_t) mode;
Stevenad8015b2017-10-29 22:10:46 -07004023 mp->queue_id_valid = queue_id_valid;
4024 mp->queue_id = queue_id_valid ? ntohl (queue_id) : ~0;
4025
4026 /* send it... */
4027 S (mp);
4028
4029 /* Wait for a reply, return the good/bad news... */
4030 W (ret);
4031 return ret;
4032}
4033
4034static int
Mohsin Kazmi54f7c512018-08-23 18:28:11 +02004035api_sw_interface_set_rx_placement (vat_main_t * vam)
4036{
4037 unformat_input_t *i = vam->input;
4038 vl_api_sw_interface_set_rx_placement_t *mp;
4039 u32 sw_if_index;
4040 u8 sw_if_index_set = 0;
4041 int ret;
4042 u8 is_main = 0;
4043 u32 queue_id, thread_index;
4044
4045 /* Parse args required to build the message */
4046 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4047 {
4048 if (unformat (i, "queue %d", &queue_id))
4049 ;
4050 else if (unformat (i, "main"))
4051 is_main = 1;
4052 else if (unformat (i, "worker %d", &thread_index))
4053 ;
4054 else
4055 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
4056 sw_if_index_set = 1;
4057 else if (unformat (i, "sw_if_index %d", &sw_if_index))
4058 sw_if_index_set = 1;
4059 else
4060 break;
4061 }
4062
4063 if (sw_if_index_set == 0)
4064 {
4065 errmsg ("missing interface name or sw_if_index");
4066 return -99;
4067 }
4068
4069 if (is_main)
4070 thread_index = 0;
4071 /* Construct the API message */
4072 M (SW_INTERFACE_SET_RX_PLACEMENT, mp);
4073 mp->sw_if_index = ntohl (sw_if_index);
4074 mp->worker_id = ntohl (thread_index);
4075 mp->queue_id = ntohl (queue_id);
4076 mp->is_main = is_main;
4077
4078 /* send it... */
4079 S (mp);
4080 /* Wait for a reply, return the good/bad news... */
4081 W (ret);
4082 return ret;
4083}
4084
Mohsin Kazmif0b42f42018-09-10 18:11:00 +02004085static void vl_api_sw_interface_rx_placement_details_t_handler
4086 (vl_api_sw_interface_rx_placement_details_t * mp)
4087{
4088 vat_main_t *vam = &vat_main;
4089 u32 worker_id = ntohl (mp->worker_id);
4090
4091 print (vam->ofp,
4092 "\n%-11d %-11s %-6d %-5d %-9s",
4093 ntohl (mp->sw_if_index), (worker_id == 0) ? "main" : "worker",
4094 worker_id, ntohl (mp->queue_id),
4095 (mp->mode ==
4096 1) ? "polling" : ((mp->mode == 2) ? "interrupt" : "adaptive"));
4097}
4098
4099static void vl_api_sw_interface_rx_placement_details_t_handler_json
4100 (vl_api_sw_interface_rx_placement_details_t * mp)
4101{
4102 vat_main_t *vam = &vat_main;
4103 vat_json_node_t *node = NULL;
4104
4105 if (VAT_JSON_ARRAY != vam->json_tree.type)
4106 {
4107 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
4108 vat_json_init_array (&vam->json_tree);
4109 }
4110 node = vat_json_array_add (&vam->json_tree);
4111
4112 vat_json_init_object (node);
4113 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
4114 vat_json_object_add_uint (node, "worker_id", ntohl (mp->worker_id));
4115 vat_json_object_add_uint (node, "queue_id", ntohl (mp->queue_id));
4116 vat_json_object_add_uint (node, "mode", mp->mode);
4117}
4118
4119static int
4120api_sw_interface_rx_placement_dump (vat_main_t * vam)
4121{
4122 unformat_input_t *i = vam->input;
4123 vl_api_sw_interface_rx_placement_dump_t *mp;
4124 vl_api_control_ping_t *mp_ping;
4125 int ret;
4126 u32 sw_if_index;
4127 u8 sw_if_index_set = 0;
4128
4129 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4130 {
4131 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
4132 sw_if_index_set++;
4133 else if (unformat (i, "sw_if_index %d", &sw_if_index))
4134 sw_if_index_set++;
4135 else
4136 break;
4137 }
4138
4139 print (vam->ofp,
4140 "\n%-11s %-11s %-6s %-5s %-4s",
4141 "sw_if_index", "main/worker", "thread", "queue", "mode");
4142
4143 /* Dump Interface rx placement */
4144 M (SW_INTERFACE_RX_PLACEMENT_DUMP, mp);
4145
4146 if (sw_if_index_set)
4147 mp->sw_if_index = htonl (sw_if_index);
4148 else
4149 mp->sw_if_index = ~0;
4150
4151 S (mp);
4152
4153 /* Use a control ping for synchronization */
4154 MPING (CONTROL_PING, mp_ping);
4155 S (mp_ping);
4156
4157 W (ret);
4158 return ret;
4159}
4160
Mohsin Kazmi54f7c512018-08-23 18:28:11 +02004161static int
Damjan Marion7cd468a2016-12-19 23:05:39 +01004162api_sw_interface_clear_stats (vat_main_t * vam)
4163{
4164 unformat_input_t *i = vam->input;
4165 vl_api_sw_interface_clear_stats_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004166 u32 sw_if_index;
4167 u8 sw_if_index_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06004168 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004169
4170 /* Parse args required to build the message */
4171 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4172 {
4173 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
4174 sw_if_index_set = 1;
4175 else if (unformat (i, "sw_if_index %d", &sw_if_index))
4176 sw_if_index_set = 1;
4177 else
4178 break;
4179 }
4180
4181 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004182 M (SW_INTERFACE_CLEAR_STATS, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004183
4184 if (sw_if_index_set == 1)
4185 mp->sw_if_index = ntohl (sw_if_index);
4186 else
4187 mp->sw_if_index = ~0;
4188
4189 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004190 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004191
4192 /* Wait for a reply, return the good/bad news... */
Jon Loeliger56c7b012017-02-01 12:31:41 -06004193 W (ret);
4194 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004195}
4196
Damjan Marion7cd468a2016-12-19 23:05:39 +01004197static int
4198api_sw_interface_add_del_address (vat_main_t * vam)
4199{
4200 unformat_input_t *i = vam->input;
4201 vl_api_sw_interface_add_del_address_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004202 u32 sw_if_index;
4203 u8 sw_if_index_set = 0;
4204 u8 is_add = 1, del_all = 0;
4205 u32 address_length = 0;
4206 u8 v4_address_set = 0;
4207 u8 v6_address_set = 0;
4208 ip4_address_t v4address;
4209 ip6_address_t v6address;
Jon Loeliger56c7b012017-02-01 12:31:41 -06004210 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004211
4212 /* Parse args required to build the message */
4213 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4214 {
4215 if (unformat (i, "del-all"))
4216 del_all = 1;
4217 else if (unformat (i, "del"))
4218 is_add = 0;
4219 else
4220 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
4221 sw_if_index_set = 1;
4222 else if (unformat (i, "sw_if_index %d", &sw_if_index))
4223 sw_if_index_set = 1;
4224 else if (unformat (i, "%U/%d",
4225 unformat_ip4_address, &v4address, &address_length))
4226 v4_address_set = 1;
4227 else if (unformat (i, "%U/%d",
4228 unformat_ip6_address, &v6address, &address_length))
4229 v6_address_set = 1;
4230 else
4231 break;
4232 }
4233
4234 if (sw_if_index_set == 0)
4235 {
4236 errmsg ("missing interface name or sw_if_index");
4237 return -99;
4238 }
4239 if (v4_address_set && v6_address_set)
4240 {
4241 errmsg ("both v4 and v6 addresses set");
4242 return -99;
4243 }
4244 if (!v4_address_set && !v6_address_set && !del_all)
4245 {
4246 errmsg ("no addresses set");
4247 return -99;
4248 }
4249
4250 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004251 M (SW_INTERFACE_ADD_DEL_ADDRESS, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004252
4253 mp->sw_if_index = ntohl (sw_if_index);
4254 mp->is_add = is_add;
4255 mp->del_all = del_all;
4256 if (v6_address_set)
4257 {
Jakub Grajciar053204a2019-03-18 13:17:53 +01004258 mp->prefix.address.af = ADDRESS_IP6;
4259 clib_memcpy (mp->prefix.address.un.ip6, &v6address, sizeof (v6address));
Damjan Marion7cd468a2016-12-19 23:05:39 +01004260 }
4261 else
4262 {
Jakub Grajciar053204a2019-03-18 13:17:53 +01004263 mp->prefix.address.af = ADDRESS_IP4;
4264 clib_memcpy (mp->prefix.address.un.ip4, &v4address, sizeof (v4address));
Damjan Marion7cd468a2016-12-19 23:05:39 +01004265 }
Jakub Grajciar053204a2019-03-18 13:17:53 +01004266 mp->prefix.len = address_length;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004267
4268 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004269 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004270
4271 /* Wait for a reply, return good/bad news */
Jon Loeliger56c7b012017-02-01 12:31:41 -06004272 W (ret);
4273 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004274}
4275
4276static int
4277api_sw_interface_set_mpls_enable (vat_main_t * vam)
4278{
4279 unformat_input_t *i = vam->input;
4280 vl_api_sw_interface_set_mpls_enable_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004281 u32 sw_if_index;
4282 u8 sw_if_index_set = 0;
4283 u8 enable = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -06004284 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004285
4286 /* Parse args required to build the message */
4287 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4288 {
4289 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
4290 sw_if_index_set = 1;
4291 else if (unformat (i, "sw_if_index %d", &sw_if_index))
4292 sw_if_index_set = 1;
4293 else if (unformat (i, "disable"))
4294 enable = 0;
4295 else if (unformat (i, "dis"))
4296 enable = 0;
4297 else
4298 break;
4299 }
4300
4301 if (sw_if_index_set == 0)
4302 {
4303 errmsg ("missing interface name or sw_if_index");
4304 return -99;
4305 }
4306
4307 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004308 M (SW_INTERFACE_SET_MPLS_ENABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004309
4310 mp->sw_if_index = ntohl (sw_if_index);
4311 mp->enable = enable;
4312
4313 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004314 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004315
4316 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -06004317 W (ret);
4318 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004319}
4320
4321static int
4322api_sw_interface_set_table (vat_main_t * vam)
4323{
4324 unformat_input_t *i = vam->input;
4325 vl_api_sw_interface_set_table_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004326 u32 sw_if_index, vrf_id = 0;
4327 u8 sw_if_index_set = 0;
4328 u8 is_ipv6 = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06004329 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004330
4331 /* Parse args required to build the message */
4332 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4333 {
4334 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
4335 sw_if_index_set = 1;
4336 else if (unformat (i, "sw_if_index %d", &sw_if_index))
4337 sw_if_index_set = 1;
4338 else if (unformat (i, "vrf %d", &vrf_id))
4339 ;
4340 else if (unformat (i, "ipv6"))
4341 is_ipv6 = 1;
4342 else
4343 break;
4344 }
4345
4346 if (sw_if_index_set == 0)
4347 {
4348 errmsg ("missing interface name or sw_if_index");
4349 return -99;
4350 }
4351
4352 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004353 M (SW_INTERFACE_SET_TABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004354
4355 mp->sw_if_index = ntohl (sw_if_index);
4356 mp->is_ipv6 = is_ipv6;
4357 mp->vrf_id = ntohl (vrf_id);
4358
4359 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004360 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004361
4362 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -06004363 W (ret);
4364 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004365}
4366
4367static void vl_api_sw_interface_get_table_reply_t_handler
4368 (vl_api_sw_interface_get_table_reply_t * mp)
4369{
4370 vat_main_t *vam = &vat_main;
4371
4372 print (vam->ofp, "%d", ntohl (mp->vrf_id));
4373
4374 vam->retval = ntohl (mp->retval);
4375 vam->result_ready = 1;
4376
4377}
4378
4379static void vl_api_sw_interface_get_table_reply_t_handler_json
4380 (vl_api_sw_interface_get_table_reply_t * mp)
4381{
4382 vat_main_t *vam = &vat_main;
4383 vat_json_node_t node;
4384
4385 vat_json_init_object (&node);
4386 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
4387 vat_json_object_add_int (&node, "vrf_id", ntohl (mp->vrf_id));
4388
4389 vat_json_print (vam->ofp, &node);
4390 vat_json_free (&node);
4391
4392 vam->retval = ntohl (mp->retval);
4393 vam->result_ready = 1;
4394}
4395
4396static int
4397api_sw_interface_get_table (vat_main_t * vam)
4398{
4399 unformat_input_t *i = vam->input;
4400 vl_api_sw_interface_get_table_t *mp;
4401 u32 sw_if_index;
4402 u8 sw_if_index_set = 0;
4403 u8 is_ipv6 = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06004404 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004405
4406 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4407 {
4408 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
4409 sw_if_index_set = 1;
4410 else if (unformat (i, "sw_if_index %d", &sw_if_index))
4411 sw_if_index_set = 1;
4412 else if (unformat (i, "ipv6"))
4413 is_ipv6 = 1;
4414 else
4415 break;
4416 }
4417
4418 if (sw_if_index_set == 0)
4419 {
4420 errmsg ("missing interface name or sw_if_index");
4421 return -99;
4422 }
4423
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004424 M (SW_INTERFACE_GET_TABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004425 mp->sw_if_index = htonl (sw_if_index);
4426 mp->is_ipv6 = is_ipv6;
4427
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004428 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06004429 W (ret);
4430 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004431}
4432
4433static int
4434api_sw_interface_set_vpath (vat_main_t * vam)
4435{
4436 unformat_input_t *i = vam->input;
4437 vl_api_sw_interface_set_vpath_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004438 u32 sw_if_index = 0;
4439 u8 sw_if_index_set = 0;
4440 u8 is_enable = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06004441 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004442
4443 /* Parse args required to build the message */
4444 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4445 {
4446 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
4447 sw_if_index_set = 1;
4448 else if (unformat (i, "sw_if_index %d", &sw_if_index))
4449 sw_if_index_set = 1;
4450 else if (unformat (i, "enable"))
4451 is_enable = 1;
4452 else if (unformat (i, "disable"))
4453 is_enable = 0;
4454 else
4455 break;
4456 }
4457
4458 if (sw_if_index_set == 0)
4459 {
4460 errmsg ("missing interface name or sw_if_index");
4461 return -99;
4462 }
4463
4464 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004465 M (SW_INTERFACE_SET_VPATH, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004466
4467 mp->sw_if_index = ntohl (sw_if_index);
4468 mp->enable = is_enable;
4469
4470 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004471 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004472
4473 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -06004474 W (ret);
4475 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004476}
4477
4478static int
4479api_sw_interface_set_vxlan_bypass (vat_main_t * vam)
4480{
4481 unformat_input_t *i = vam->input;
4482 vl_api_sw_interface_set_vxlan_bypass_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004483 u32 sw_if_index = 0;
4484 u8 sw_if_index_set = 0;
John Lo2b81eb82017-01-30 13:12:10 -05004485 u8 is_enable = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004486 u8 is_ipv6 = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06004487 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004488
4489 /* Parse args required to build the message */
4490 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4491 {
4492 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
4493 sw_if_index_set = 1;
4494 else if (unformat (i, "sw_if_index %d", &sw_if_index))
4495 sw_if_index_set = 1;
4496 else if (unformat (i, "enable"))
4497 is_enable = 1;
4498 else if (unformat (i, "disable"))
4499 is_enable = 0;
4500 else if (unformat (i, "ip4"))
4501 is_ipv6 = 0;
4502 else if (unformat (i, "ip6"))
4503 is_ipv6 = 1;
4504 else
4505 break;
4506 }
4507
4508 if (sw_if_index_set == 0)
4509 {
4510 errmsg ("missing interface name or sw_if_index");
4511 return -99;
4512 }
4513
4514 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004515 M (SW_INTERFACE_SET_VXLAN_BYPASS, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004516
4517 mp->sw_if_index = ntohl (sw_if_index);
4518 mp->enable = is_enable;
4519 mp->is_ipv6 = is_ipv6;
4520
4521 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004522 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004523
4524 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -06004525 W (ret);
4526 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004527}
4528
Marco Varleseb598f1d2017-09-19 14:25:28 +02004529static int
Damjan Marion7cd468a2016-12-19 23:05:39 +01004530api_sw_interface_set_l2_xconnect (vat_main_t * vam)
4531{
4532 unformat_input_t *i = vam->input;
4533 vl_api_sw_interface_set_l2_xconnect_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004534 u32 rx_sw_if_index;
4535 u8 rx_sw_if_index_set = 0;
4536 u32 tx_sw_if_index;
4537 u8 tx_sw_if_index_set = 0;
4538 u8 enable = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -06004539 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004540
4541 /* Parse args required to build the message */
4542 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4543 {
4544 if (unformat (i, "rx_sw_if_index %d", &rx_sw_if_index))
4545 rx_sw_if_index_set = 1;
4546 else if (unformat (i, "tx_sw_if_index %d", &tx_sw_if_index))
4547 tx_sw_if_index_set = 1;
4548 else if (unformat (i, "rx"))
4549 {
4550 if (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4551 {
4552 if (unformat (i, "%U", api_unformat_sw_if_index, vam,
4553 &rx_sw_if_index))
4554 rx_sw_if_index_set = 1;
4555 }
4556 else
4557 break;
4558 }
4559 else if (unformat (i, "tx"))
4560 {
4561 if (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4562 {
4563 if (unformat (i, "%U", api_unformat_sw_if_index, vam,
4564 &tx_sw_if_index))
4565 tx_sw_if_index_set = 1;
4566 }
4567 else
4568 break;
4569 }
4570 else if (unformat (i, "enable"))
4571 enable = 1;
4572 else if (unformat (i, "disable"))
4573 enable = 0;
4574 else
4575 break;
4576 }
4577
4578 if (rx_sw_if_index_set == 0)
4579 {
4580 errmsg ("missing rx interface name or rx_sw_if_index");
4581 return -99;
4582 }
4583
4584 if (enable && (tx_sw_if_index_set == 0))
4585 {
4586 errmsg ("missing tx interface name or tx_sw_if_index");
4587 return -99;
4588 }
4589
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004590 M (SW_INTERFACE_SET_L2_XCONNECT, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004591
4592 mp->rx_sw_if_index = ntohl (rx_sw_if_index);
4593 mp->tx_sw_if_index = ntohl (tx_sw_if_index);
4594 mp->enable = enable;
4595
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004596 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06004597 W (ret);
4598 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004599}
4600
4601static int
4602api_sw_interface_set_l2_bridge (vat_main_t * vam)
4603{
4604 unformat_input_t *i = vam->input;
4605 vl_api_sw_interface_set_l2_bridge_t *mp;
Neale Rannsb4743802018-09-05 09:13:57 -07004606 vl_api_l2_port_type_t port_type;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004607 u32 rx_sw_if_index;
4608 u8 rx_sw_if_index_set = 0;
4609 u32 bd_id;
4610 u8 bd_id_set = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004611 u32 shg = 0;
4612 u8 enable = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -06004613 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004614
Neale Rannsb4743802018-09-05 09:13:57 -07004615 port_type = L2_API_PORT_TYPE_NORMAL;
4616
Damjan Marion7cd468a2016-12-19 23:05:39 +01004617 /* Parse args required to build the message */
4618 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4619 {
4620 if (unformat (i, "sw_if_index %d", &rx_sw_if_index))
4621 rx_sw_if_index_set = 1;
4622 else if (unformat (i, "bd_id %d", &bd_id))
4623 bd_id_set = 1;
4624 else
4625 if (unformat
4626 (i, "%U", api_unformat_sw_if_index, vam, &rx_sw_if_index))
4627 rx_sw_if_index_set = 1;
4628 else if (unformat (i, "shg %d", &shg))
4629 ;
4630 else if (unformat (i, "bvi"))
Neale Rannsb4743802018-09-05 09:13:57 -07004631 port_type = L2_API_PORT_TYPE_BVI;
4632 else if (unformat (i, "uu-fwd"))
4633 port_type = L2_API_PORT_TYPE_UU_FWD;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004634 else if (unformat (i, "enable"))
4635 enable = 1;
4636 else if (unformat (i, "disable"))
4637 enable = 0;
4638 else
4639 break;
4640 }
4641
4642 if (rx_sw_if_index_set == 0)
4643 {
4644 errmsg ("missing rx interface name or sw_if_index");
4645 return -99;
4646 }
4647
4648 if (enable && (bd_id_set == 0))
4649 {
4650 errmsg ("missing bridge domain");
4651 return -99;
4652 }
4653
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004654 M (SW_INTERFACE_SET_L2_BRIDGE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004655
4656 mp->rx_sw_if_index = ntohl (rx_sw_if_index);
4657 mp->bd_id = ntohl (bd_id);
4658 mp->shg = (u8) shg;
Neale Rannsb4743802018-09-05 09:13:57 -07004659 mp->port_type = ntohl (port_type);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004660 mp->enable = enable;
4661
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004662 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06004663 W (ret);
4664 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004665}
4666
4667static int
4668api_bridge_domain_dump (vat_main_t * vam)
4669{
4670 unformat_input_t *i = vam->input;
4671 vl_api_bridge_domain_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -06004672 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004673 u32 bd_id = ~0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06004674 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004675
4676 /* Parse args required to build the message */
4677 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4678 {
4679 if (unformat (i, "bd_id %d", &bd_id))
4680 ;
4681 else
4682 break;
4683 }
4684
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004685 M (BRIDGE_DOMAIN_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004686 mp->bd_id = ntohl (bd_id);
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004687 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004688
4689 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -04004690 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -06004691 S (mp_ping);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004692
Jon Loeliger56c7b012017-02-01 12:31:41 -06004693 W (ret);
4694 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004695}
4696
4697static int
4698api_bridge_domain_add_del (vat_main_t * vam)
4699{
4700 unformat_input_t *i = vam->input;
4701 vl_api_bridge_domain_add_del_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004702 u32 bd_id = ~0;
4703 u8 is_add = 1;
4704 u32 flood = 1, forward = 1, learn = 1, uu_flood = 1, arp_term = 0;
Jerome Tollet50570ec2017-09-14 12:53:56 +01004705 u8 *bd_tag = NULL;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004706 u32 mac_age = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06004707 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004708
4709 /* Parse args required to build the message */
4710 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4711 {
4712 if (unformat (i, "bd_id %d", &bd_id))
4713 ;
4714 else if (unformat (i, "flood %d", &flood))
4715 ;
4716 else if (unformat (i, "uu-flood %d", &uu_flood))
4717 ;
4718 else if (unformat (i, "forward %d", &forward))
4719 ;
4720 else if (unformat (i, "learn %d", &learn))
4721 ;
4722 else if (unformat (i, "arp-term %d", &arp_term))
4723 ;
4724 else if (unformat (i, "mac-age %d", &mac_age))
4725 ;
Jerome Tollet50570ec2017-09-14 12:53:56 +01004726 else if (unformat (i, "bd-tag %s", &bd_tag))
4727 ;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004728 else if (unformat (i, "del"))
4729 {
4730 is_add = 0;
4731 flood = uu_flood = forward = learn = 0;
4732 }
4733 else
4734 break;
4735 }
4736
4737 if (bd_id == ~0)
4738 {
4739 errmsg ("missing bridge domain");
Jerome Tollet50570ec2017-09-14 12:53:56 +01004740 ret = -99;
4741 goto done;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004742 }
4743
4744 if (mac_age > 255)
4745 {
4746 errmsg ("mac age must be less than 256 ");
Jerome Tollet50570ec2017-09-14 12:53:56 +01004747 ret = -99;
4748 goto done;
4749 }
4750
John Lo70bfcaf2017-11-14 13:19:26 -05004751 if ((bd_tag) && (vec_len (bd_tag) > 63))
Jerome Tollet50570ec2017-09-14 12:53:56 +01004752 {
4753 errmsg ("bd-tag cannot be longer than 63");
4754 ret = -99;
4755 goto done;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004756 }
4757
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004758 M (BRIDGE_DOMAIN_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004759
4760 mp->bd_id = ntohl (bd_id);
4761 mp->flood = flood;
4762 mp->uu_flood = uu_flood;
4763 mp->forward = forward;
4764 mp->learn = learn;
4765 mp->arp_term = arp_term;
4766 mp->is_add = is_add;
4767 mp->mac_age = (u8) mac_age;
Jerome Tollet50570ec2017-09-14 12:53:56 +01004768 if (bd_tag)
John Lo70bfcaf2017-11-14 13:19:26 -05004769 {
4770 clib_memcpy (mp->bd_tag, bd_tag, vec_len (bd_tag));
4771 mp->bd_tag[vec_len (bd_tag)] = 0;
4772 }
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004773 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06004774 W (ret);
Jerome Tollet50570ec2017-09-14 12:53:56 +01004775
4776done:
4777 vec_free (bd_tag);
Jon Loeliger56c7b012017-02-01 12:31:41 -06004778 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004779}
4780
4781static int
Eyal Barif24991c2017-04-05 05:33:21 +03004782api_l2fib_flush_bd (vat_main_t * vam)
4783{
4784 unformat_input_t *i = vam->input;
4785 vl_api_l2fib_flush_bd_t *mp;
4786 u32 bd_id = ~0;
4787 int ret;
4788
4789 /* Parse args required to build the message */
4790 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4791 {
4792 if (unformat (i, "bd_id %d", &bd_id));
4793 else
4794 break;
4795 }
4796
4797 if (bd_id == ~0)
4798 {
4799 errmsg ("missing bridge domain");
4800 return -99;
4801 }
4802
4803 M (L2FIB_FLUSH_BD, mp);
4804
4805 mp->bd_id = htonl (bd_id);
4806
4807 S (mp);
4808 W (ret);
4809 return ret;
4810}
4811
4812static int
4813api_l2fib_flush_int (vat_main_t * vam)
4814{
4815 unformat_input_t *i = vam->input;
4816 vl_api_l2fib_flush_int_t *mp;
4817 u32 sw_if_index = ~0;
4818 int ret;
4819
4820 /* Parse args required to build the message */
4821 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4822 {
4823 if (unformat (i, "sw_if_index %d", &sw_if_index));
4824 else
4825 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index));
4826 else
4827 break;
4828 }
4829
4830 if (sw_if_index == ~0)
4831 {
4832 errmsg ("missing interface name or sw_if_index");
4833 return -99;
4834 }
4835
4836 M (L2FIB_FLUSH_INT, mp);
4837
4838 mp->sw_if_index = ntohl (sw_if_index);
4839
4840 S (mp);
4841 W (ret);
4842 return ret;
4843}
4844
4845static int
Damjan Marion7cd468a2016-12-19 23:05:39 +01004846api_l2fib_add_del (vat_main_t * vam)
4847{
4848 unformat_input_t *i = vam->input;
4849 vl_api_l2fib_add_del_t *mp;
4850 f64 timeout;
Mohsin Kazmi57938f62017-10-27 21:28:07 +02004851 u8 mac[6] = { 0 };
Damjan Marion7cd468a2016-12-19 23:05:39 +01004852 u8 mac_set = 0;
4853 u32 bd_id;
4854 u8 bd_id_set = 0;
John Lo7dbd7262018-05-31 10:25:18 -04004855 u32 sw_if_index = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004856 u8 sw_if_index_set = 0;
4857 u8 is_add = 1;
4858 u8 static_mac = 0;
4859 u8 filter_mac = 0;
4860 u8 bvi_mac = 0;
4861 int count = 1;
4862 f64 before = 0;
4863 int j;
4864
4865 /* Parse args required to build the message */
4866 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4867 {
Mohsin Kazmi57938f62017-10-27 21:28:07 +02004868 if (unformat (i, "mac %U", unformat_ethernet_address, mac))
Damjan Marion7cd468a2016-12-19 23:05:39 +01004869 mac_set = 1;
4870 else if (unformat (i, "bd_id %d", &bd_id))
4871 bd_id_set = 1;
4872 else if (unformat (i, "sw_if_index %d", &sw_if_index))
4873 sw_if_index_set = 1;
4874 else if (unformat (i, "sw_if"))
4875 {
4876 if (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
4877 {
4878 if (unformat
4879 (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
4880 sw_if_index_set = 1;
4881 }
4882 else
4883 break;
4884 }
4885 else if (unformat (i, "static"))
4886 static_mac = 1;
4887 else if (unformat (i, "filter"))
4888 {
4889 filter_mac = 1;
4890 static_mac = 1;
4891 }
4892 else if (unformat (i, "bvi"))
4893 {
4894 bvi_mac = 1;
4895 static_mac = 1;
4896 }
4897 else if (unformat (i, "del"))
4898 is_add = 0;
4899 else if (unformat (i, "count %d", &count))
4900 ;
4901 else
4902 break;
4903 }
4904
4905 if (mac_set == 0)
4906 {
4907 errmsg ("missing mac address");
4908 return -99;
4909 }
4910
4911 if (bd_id_set == 0)
4912 {
4913 errmsg ("missing bridge domain");
4914 return -99;
4915 }
4916
4917 if (is_add && sw_if_index_set == 0 && filter_mac == 0)
4918 {
4919 errmsg ("missing interface name or sw_if_index");
4920 return -99;
4921 }
4922
4923 if (count > 1)
4924 {
4925 /* Turn on async mode */
4926 vam->async_mode = 1;
4927 vam->async_errors = 0;
4928 before = vat_time_now (vam);
4929 }
4930
4931 for (j = 0; j < count; j++)
4932 {
Jon Loeliger8a2aea32017-01-31 13:19:40 -06004933 M (L2FIB_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004934
Mohsin Kazmi57938f62017-10-27 21:28:07 +02004935 clib_memcpy (mp->mac, mac, 6);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004936 mp->bd_id = ntohl (bd_id);
4937 mp->is_add = is_add;
John Lo7dbd7262018-05-31 10:25:18 -04004938 mp->sw_if_index = ntohl (sw_if_index);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004939
4940 if (is_add)
4941 {
Damjan Marion7cd468a2016-12-19 23:05:39 +01004942 mp->static_mac = static_mac;
4943 mp->filter_mac = filter_mac;
4944 mp->bvi_mac = bvi_mac;
4945 }
Mohsin Kazmi57938f62017-10-27 21:28:07 +02004946 increment_mac_address (mac);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004947 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06004948 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004949 }
4950
4951 if (count > 1)
4952 {
Jon Loeliger2d23eca2017-02-01 13:09:58 -06004953 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004954 f64 after;
4955
4956 /* Shut off async mode */
4957 vam->async_mode = 0;
4958
Dave Barach59b25652017-09-10 15:04:27 -04004959 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -06004960 S (mp_ping);
Damjan Marion7cd468a2016-12-19 23:05:39 +01004961
4962 timeout = vat_time_now (vam) + 1.0;
4963 while (vat_time_now (vam) < timeout)
4964 if (vam->result_ready == 1)
4965 goto out;
4966 vam->retval = -99;
4967
4968 out:
4969 if (vam->retval == -99)
4970 errmsg ("timeout");
4971
4972 if (vam->async_errors > 0)
4973 {
4974 errmsg ("%d asynchronous errors", vam->async_errors);
4975 vam->retval = -98;
4976 }
4977 vam->async_errors = 0;
4978 after = vat_time_now (vam);
4979
4980 print (vam->ofp, "%d routes in %.6f secs, %.2f routes/sec",
4981 count, after - before, count / (after - before));
4982 }
4983 else
4984 {
Jon Loeliger56c7b012017-02-01 12:31:41 -06004985 int ret;
4986
Damjan Marion7cd468a2016-12-19 23:05:39 +01004987 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -06004988 W (ret);
4989 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01004990 }
4991 /* Return the good/bad news */
4992 return (vam->retval);
4993}
4994
4995static int
Eyal Barifead6702017-04-04 04:46:32 +03004996api_bridge_domain_set_mac_age (vat_main_t * vam)
4997{
4998 unformat_input_t *i = vam->input;
4999 vl_api_bridge_domain_set_mac_age_t *mp;
5000 u32 bd_id = ~0;
5001 u32 mac_age = 0;
5002 int ret;
5003
5004 /* Parse args required to build the message */
5005 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5006 {
5007 if (unformat (i, "bd_id %d", &bd_id));
5008 else if (unformat (i, "mac-age %d", &mac_age));
5009 else
5010 break;
5011 }
5012
5013 if (bd_id == ~0)
5014 {
5015 errmsg ("missing bridge domain");
5016 return -99;
5017 }
5018
5019 if (mac_age > 255)
5020 {
5021 errmsg ("mac age must be less than 256 ");
5022 return -99;
5023 }
5024
5025 M (BRIDGE_DOMAIN_SET_MAC_AGE, mp);
5026
5027 mp->bd_id = htonl (bd_id);
5028 mp->mac_age = (u8) mac_age;
5029
5030 S (mp);
5031 W (ret);
5032 return ret;
5033}
5034
5035static int
Damjan Marion7cd468a2016-12-19 23:05:39 +01005036api_l2_flags (vat_main_t * vam)
5037{
5038 unformat_input_t *i = vam->input;
5039 vl_api_l2_flags_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005040 u32 sw_if_index;
John Lo8d00fff2017-08-03 00:35:36 -04005041 u32 flags = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005042 u8 sw_if_index_set = 0;
John Lo8d00fff2017-08-03 00:35:36 -04005043 u8 is_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06005044 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005045
5046 /* Parse args required to build the message */
5047 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5048 {
5049 if (unformat (i, "sw_if_index %d", &sw_if_index))
5050 sw_if_index_set = 1;
5051 else if (unformat (i, "sw_if"))
5052 {
5053 if (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5054 {
5055 if (unformat
5056 (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
5057 sw_if_index_set = 1;
5058 }
5059 else
5060 break;
5061 }
5062 else if (unformat (i, "learn"))
John Lo8d00fff2017-08-03 00:35:36 -04005063 flags |= L2_LEARN;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005064 else if (unformat (i, "forward"))
John Lo8d00fff2017-08-03 00:35:36 -04005065 flags |= L2_FWD;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005066 else if (unformat (i, "flood"))
John Lo8d00fff2017-08-03 00:35:36 -04005067 flags |= L2_FLOOD;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005068 else if (unformat (i, "uu-flood"))
John Lo8d00fff2017-08-03 00:35:36 -04005069 flags |= L2_UU_FLOOD;
5070 else if (unformat (i, "arp-term"))
5071 flags |= L2_ARP_TERM;
5072 else if (unformat (i, "off"))
5073 is_set = 0;
5074 else if (unformat (i, "disable"))
5075 is_set = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005076 else
5077 break;
5078 }
5079
5080 if (sw_if_index_set == 0)
5081 {
5082 errmsg ("missing interface name or sw_if_index");
5083 return -99;
5084 }
5085
Jon Loeliger8a2aea32017-01-31 13:19:40 -06005086 M (L2_FLAGS, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01005087
5088 mp->sw_if_index = ntohl (sw_if_index);
John Lo8d00fff2017-08-03 00:35:36 -04005089 mp->feature_bitmap = ntohl (flags);
5090 mp->is_set = is_set;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005091
Jon Loeliger7bc770c2017-01-31 14:03:33 -06005092 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06005093 W (ret);
5094 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005095}
5096
5097static int
5098api_bridge_flags (vat_main_t * vam)
5099{
5100 unformat_input_t *i = vam->input;
5101 vl_api_bridge_flags_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005102 u32 bd_id;
5103 u8 bd_id_set = 0;
5104 u8 is_set = 1;
Neale Rannsb4743802018-09-05 09:13:57 -07005105 bd_flags_t flags = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06005106 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005107
5108 /* Parse args required to build the message */
5109 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5110 {
5111 if (unformat (i, "bd_id %d", &bd_id))
5112 bd_id_set = 1;
5113 else if (unformat (i, "learn"))
Neale Rannsb4743802018-09-05 09:13:57 -07005114 flags |= BRIDGE_API_FLAG_LEARN;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005115 else if (unformat (i, "forward"))
Neale Rannsb4743802018-09-05 09:13:57 -07005116 flags |= BRIDGE_API_FLAG_FWD;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005117 else if (unformat (i, "flood"))
Neale Rannsb4743802018-09-05 09:13:57 -07005118 flags |= BRIDGE_API_FLAG_FLOOD;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005119 else if (unformat (i, "uu-flood"))
Neale Rannsb4743802018-09-05 09:13:57 -07005120 flags |= BRIDGE_API_FLAG_UU_FLOOD;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005121 else if (unformat (i, "arp-term"))
Neale Rannsb4743802018-09-05 09:13:57 -07005122 flags |= BRIDGE_API_FLAG_ARP_TERM;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005123 else if (unformat (i, "off"))
5124 is_set = 0;
5125 else if (unformat (i, "disable"))
5126 is_set = 0;
5127 else
5128 break;
5129 }
5130
5131 if (bd_id_set == 0)
5132 {
5133 errmsg ("missing bridge domain");
5134 return -99;
5135 }
5136
Jon Loeliger8a2aea32017-01-31 13:19:40 -06005137 M (BRIDGE_FLAGS, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01005138
5139 mp->bd_id = ntohl (bd_id);
Neale Rannsb4743802018-09-05 09:13:57 -07005140 mp->flags = ntohl (flags);
Damjan Marion7cd468a2016-12-19 23:05:39 +01005141 mp->is_set = is_set;
5142
Jon Loeliger7bc770c2017-01-31 14:03:33 -06005143 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06005144 W (ret);
5145 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005146}
5147
5148static int
5149api_bd_ip_mac_add_del (vat_main_t * vam)
5150{
Neale Ranns4d5b9172018-10-24 02:57:49 -07005151 vl_api_address_t ip = VL_API_ZERO_ADDRESS;
Ole Troan8006c6a2018-12-17 12:02:26 +01005152 vl_api_mac_address_t mac = { 0 };
Damjan Marion7cd468a2016-12-19 23:05:39 +01005153 unformat_input_t *i = vam->input;
5154 vl_api_bd_ip_mac_add_del_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005155 u32 bd_id;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005156 u8 is_add = 1;
5157 u8 bd_id_set = 0;
5158 u8 ip_set = 0;
5159 u8 mac_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06005160 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005161
5162
5163 /* Parse args required to build the message */
5164 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5165 {
5166 if (unformat (i, "bd_id %d", &bd_id))
5167 {
5168 bd_id_set++;
5169 }
Neale Ranns4d5b9172018-10-24 02:57:49 -07005170 else if (unformat (i, "%U", unformat_vl_api_address, &ip))
Damjan Marion7cd468a2016-12-19 23:05:39 +01005171 {
5172 ip_set++;
5173 }
Neale Ranns4d5b9172018-10-24 02:57:49 -07005174 else if (unformat (i, "%U", unformat_vl_api_mac_address, &mac))
Damjan Marion7cd468a2016-12-19 23:05:39 +01005175 {
5176 mac_set++;
5177 }
5178 else if (unformat (i, "del"))
5179 is_add = 0;
5180 else
5181 break;
5182 }
5183
5184 if (bd_id_set == 0)
5185 {
5186 errmsg ("missing bridge domain");
5187 return -99;
5188 }
5189 else if (ip_set == 0)
5190 {
5191 errmsg ("missing IP address");
5192 return -99;
5193 }
5194 else if (mac_set == 0)
5195 {
5196 errmsg ("missing MAC address");
5197 return -99;
5198 }
5199
Jon Loeliger8a2aea32017-01-31 13:19:40 -06005200 M (BD_IP_MAC_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01005201
Neale Rannsbc764c82019-06-19 07:07:13 -07005202 mp->entry.bd_id = ntohl (bd_id);
Damjan Marion7cd468a2016-12-19 23:05:39 +01005203 mp->is_add = is_add;
Neale Ranns4d5b9172018-10-24 02:57:49 -07005204
Neale Rannsbc764c82019-06-19 07:07:13 -07005205 clib_memcpy (&mp->entry.ip, &ip, sizeof (ip));
5206 clib_memcpy (&mp->entry.mac, &mac, sizeof (mac));
Neale Ranns4d5b9172018-10-24 02:57:49 -07005207
Jon Loeliger7bc770c2017-01-31 14:03:33 -06005208 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06005209 W (ret);
5210 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01005211}
5212
John Loe26c81f2019-01-07 15:16:33 -05005213static int
5214api_bd_ip_mac_flush (vat_main_t * vam)
5215{
5216 unformat_input_t *i = vam->input;
5217 vl_api_bd_ip_mac_flush_t *mp;
5218 u32 bd_id;
5219 u8 bd_id_set = 0;
5220 int ret;
5221
5222 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5223 {
5224 if (unformat (i, "bd_id %d", &bd_id))
5225 {
5226 bd_id_set++;
5227 }
5228 else
5229 break;
5230 }
5231
5232 if (bd_id_set == 0)
5233 {
5234 errmsg ("missing bridge domain");
5235 return -99;
5236 }
5237
5238 M (BD_IP_MAC_FLUSH, mp);
5239
5240 mp->bd_id = ntohl (bd_id);
5241
5242 S (mp);
5243 W (ret);
5244 return ret;
5245}
5246
Mohsin Kazmi5d82d2f2018-08-13 19:17:54 +02005247static void vl_api_bd_ip_mac_details_t_handler
5248 (vl_api_bd_ip_mac_details_t * mp)
5249{
5250 vat_main_t *vam = &vat_main;
Mohsin Kazmi5d82d2f2018-08-13 19:17:54 +02005251
5252 print (vam->ofp,
Neale Rannsbc764c82019-06-19 07:07:13 -07005253 "\n%-5d %U %U",
5254 ntohl (mp->entry.bd_id),
5255 format_vl_api_mac_address, mp->entry.mac,
5256 format_vl_api_address, &mp->entry.ip);
Mohsin Kazmi5d82d2f2018-08-13 19:17:54 +02005257}
5258
5259static void vl_api_bd_ip_mac_details_t_handler_json
5260 (vl_api_bd_ip_mac_details_t * mp)
5261{
5262 vat_main_t *vam = &vat_main;
5263 vat_json_node_t *node = NULL;
5264
5265 if (VAT_JSON_ARRAY != vam->json_tree.type)
5266 {
5267 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
5268 vat_json_init_array (&vam->json_tree);
5269 }
5270 node = vat_json_array_add (&vam->json_tree);
5271
5272 vat_json_init_object (node);
Neale Rannsbc764c82019-06-19 07:07:13 -07005273 vat_json_object_add_uint (node, "bd_id", ntohl (mp->entry.bd_id));
Mohsin Kazmi5d82d2f2018-08-13 19:17:54 +02005274 vat_json_object_add_string_copy (node, "mac_address",
Neale Rannsbc764c82019-06-19 07:07:13 -07005275 format (0, "%U", format_vl_api_mac_address,
5276 &mp->entry.mac));
Mohsin Kazmi5d82d2f2018-08-13 19:17:54 +02005277 u8 *ip = 0;
5278
Neale Rannsbc764c82019-06-19 07:07:13 -07005279 ip = format (0, "%U", format_vl_api_address, &mp->entry.ip);
Mohsin Kazmi5d82d2f2018-08-13 19:17:54 +02005280 vat_json_object_add_string_copy (node, "ip_address", ip);
5281 vec_free (ip);
5282}
5283
5284static int
5285api_bd_ip_mac_dump (vat_main_t * vam)
5286{
5287 unformat_input_t *i = vam->input;
5288 vl_api_bd_ip_mac_dump_t *mp;
5289 vl_api_control_ping_t *mp_ping;
5290 int ret;
5291 u32 bd_id;
5292 u8 bd_id_set = 0;
5293
5294 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5295 {
5296 if (unformat (i, "bd_id %d", &bd_id))
5297 {
5298 bd_id_set++;
5299 }
5300 else
5301 break;
5302 }
5303
5304 print (vam->ofp,
5305 "\n%-5s %-7s %-20s %-30s",
5306 "bd_id", "is_ipv6", "mac_address", "ip_address");
5307
5308 /* Dump Bridge Domain Ip to Mac entries */
5309 M (BD_IP_MAC_DUMP, mp);
5310
5311 if (bd_id_set)
5312 mp->bd_id = htonl (bd_id);
5313 else
5314 mp->bd_id = ~0;
5315
5316 S (mp);
5317
5318 /* Use a control ping for synchronization */
5319 MPING (CONTROL_PING, mp_ping);
5320 S (mp_ping);
5321
5322 W (ret);
5323 return ret;
5324}
5325
Damjan Marion7cd468a2016-12-19 23:05:39 +01005326static int
Damjan Marion8389fb92017-10-13 18:29:53 +02005327api_tap_create_v2 (vat_main_t * vam)
5328{
5329 unformat_input_t *i = vam->input;
5330 vl_api_tap_create_v2_t *mp;
5331 u8 mac_address[6];
5332 u8 random_mac = 1;
Damjan Marion2df39092017-12-04 20:03:37 +01005333 u32 id = ~0;
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005334 u32 num_rx_queues = 0;
Damjan Marion2df39092017-12-04 20:03:37 +01005335 u8 *host_if_name = 0;
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005336 u8 host_if_name_set = 0;
Damjan Marion2df39092017-12-04 20:03:37 +01005337 u8 *host_ns = 0;
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005338 u8 host_ns_set = 0;
Damjan Marion2df39092017-12-04 20:03:37 +01005339 u8 host_mac_addr[6];
5340 u8 host_mac_addr_set = 0;
Damjan Marion91c6ef72017-12-01 13:34:24 +01005341 u8 *host_bridge = 0;
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005342 u8 host_bridge_set = 0;
5343 u8 host_ip4_prefix_set = 0;
5344 u8 host_ip6_prefix_set = 0;
Damjan Marion91c6ef72017-12-01 13:34:24 +01005345 ip4_address_t host_ip4_addr;
Damjan Marion7866c452018-01-18 13:35:11 +01005346 ip4_address_t host_ip4_gw;
5347 u8 host_ip4_gw_set = 0;
Damjan Marion91c6ef72017-12-01 13:34:24 +01005348 u32 host_ip4_prefix_len = 0;
5349 ip6_address_t host_ip6_addr;
Damjan Marion7866c452018-01-18 13:35:11 +01005350 ip6_address_t host_ip6_gw;
5351 u8 host_ip6_gw_set = 0;
Damjan Marion91c6ef72017-12-01 13:34:24 +01005352 u32 host_ip6_prefix_len = 0;
Mohsin Kazmi97d54ed2019-06-10 11:20:15 +02005353 u32 host_mtu_size = 0;
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005354 u8 host_mtu_set = 0;
Mohsin Kazmi97d54ed2019-06-10 11:20:15 +02005355 u32 tap_flags = 0;
Damjan Marion8389fb92017-10-13 18:29:53 +02005356 int ret;
Steven9e635692018-03-01 09:36:01 -08005357 u32 rx_ring_sz = 0, tx_ring_sz = 0;
Damjan Marion8389fb92017-10-13 18:29:53 +02005358
Dave Barachb7b92992018-10-17 10:38:51 -04005359 clib_memset (mac_address, 0, sizeof (mac_address));
Damjan Marion8389fb92017-10-13 18:29:53 +02005360
5361 /* Parse args required to build the message */
5362 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5363 {
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005364 if (unformat (i, "id %u", &id))
Damjan Marion91c6ef72017-12-01 13:34:24 +01005365 ;
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005366 else
5367 if (unformat
5368 (i, "hw-addr %U", unformat_ethernet_address, mac_address))
5369 random_mac = 0;
Damjan Marion2df39092017-12-04 20:03:37 +01005370 else if (unformat (i, "host-if-name %s", &host_if_name))
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005371 host_if_name_set = 1;
5372 else if (unformat (i, "num-rx-queues %u", &num_rx_queues))
Damjan Marion91c6ef72017-12-01 13:34:24 +01005373 ;
Damjan Marion2df39092017-12-04 20:03:37 +01005374 else if (unformat (i, "host-ns %s", &host_ns))
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005375 host_ns_set = 1;
Damjan Marion2df39092017-12-04 20:03:37 +01005376 else if (unformat (i, "host-mac-addr %U", unformat_ethernet_address,
5377 host_mac_addr))
5378 host_mac_addr_set = 1;
Damjan Marion91c6ef72017-12-01 13:34:24 +01005379 else if (unformat (i, "host-bridge %s", &host_bridge))
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005380 host_bridge_set = 1;
5381 else if (unformat (i, "host-ip4-addr %U/%u", unformat_ip4_address,
Damjan Marion91c6ef72017-12-01 13:34:24 +01005382 &host_ip4_addr, &host_ip4_prefix_len))
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005383 host_ip4_prefix_set = 1;
5384 else if (unformat (i, "host-ip6-addr %U/%u", unformat_ip6_address,
Damjan Marion91c6ef72017-12-01 13:34:24 +01005385 &host_ip6_addr, &host_ip6_prefix_len))
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005386 host_ip6_prefix_set = 1;
Damjan Marion7866c452018-01-18 13:35:11 +01005387 else if (unformat (i, "host-ip4-gw %U", unformat_ip4_address,
5388 &host_ip4_gw))
5389 host_ip4_gw_set = 1;
5390 else if (unformat (i, "host-ip6-gw %U", unformat_ip6_address,
5391 &host_ip6_gw))
5392 host_ip6_gw_set = 1;
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005393 else if (unformat (i, "rx-ring-size %u", &rx_ring_sz))
Damjan Marion8389fb92017-10-13 18:29:53 +02005394 ;
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005395 else if (unformat (i, "tx-ring-size %u", &tx_ring_sz))
Damjan Marion8389fb92017-10-13 18:29:53 +02005396 ;
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005397 else if (unformat (i, "host-mtu-size %u", &host_mtu_size))
Mohsin Kazmi97d54ed2019-06-10 11:20:15 +02005398 host_mtu_set = 1;
5399 else if (unformat (i, "no-gso"))
Mohsin Kazmid88fc0f2020-04-30 19:05:56 +02005400 tap_flags &= ~TAP_API_FLAG_GSO;
Mohsin Kazmi97d54ed2019-06-10 11:20:15 +02005401 else if (unformat (i, "gso"))
Mohsin Kazmid88fc0f2020-04-30 19:05:56 +02005402 tap_flags |= TAP_API_FLAG_GSO;
Mohsin Kazmiba0061f2019-12-18 17:08:54 +01005403 else if (unformat (i, "csum-offload"))
Mohsin Kazmid88fc0f2020-04-30 19:05:56 +02005404 tap_flags |= TAP_API_FLAG_CSUM_OFFLOAD;
Mohsin Kazmib49bc1a2020-02-14 17:51:04 +00005405 else if (unformat (i, "persist"))
Mohsin Kazmid88fc0f2020-04-30 19:05:56 +02005406 tap_flags |= TAP_API_FLAG_PERSIST;
Mohsin Kazmib49bc1a2020-02-14 17:51:04 +00005407 else if (unformat (i, "attach"))
Mohsin Kazmid88fc0f2020-04-30 19:05:56 +02005408 tap_flags |= TAP_API_FLAG_ATTACH;
5409 else if (unformat (i, "tun"))
5410 tap_flags |= TAP_API_FLAG_TUN;
5411 else if (unformat (i, "gro-coalesce"))
5412 tap_flags |= TAP_API_FLAG_GRO_COALESCE;
Mohsin Kazmi50bd1652020-08-26 11:07:48 +02005413 else if (unformat (i, "packed"))
5414 tap_flags |= TAP_API_FLAG_PACKED;
5415 else if (unformat (i, "in-order"))
5416 tap_flags |= TAP_API_FLAG_IN_ORDER;
Damjan Marion8389fb92017-10-13 18:29:53 +02005417 else
5418 break;
5419 }
5420
Damjan Marion2df39092017-12-04 20:03:37 +01005421 if (vec_len (host_if_name) > 63)
Damjan Marion8389fb92017-10-13 18:29:53 +02005422 {
5423 errmsg ("tap name too long. ");
5424 return -99;
5425 }
Damjan Marion2df39092017-12-04 20:03:37 +01005426 if (vec_len (host_ns) > 63)
Damjan Marion8389fb92017-10-13 18:29:53 +02005427 {
5428 errmsg ("host name space too long. ");
5429 return -99;
5430 }
Damjan Marion91c6ef72017-12-01 13:34:24 +01005431 if (vec_len (host_bridge) > 63)
5432 {
5433 errmsg ("host bridge name too long. ");
5434 return -99;
5435 }
5436 if (host_ip4_prefix_len > 32)
5437 {
5438 errmsg ("host ip4 prefix length not valid. ");
5439 return -99;
5440 }
5441 if (host_ip6_prefix_len > 128)
5442 {
5443 errmsg ("host ip6 prefix length not valid. ");
5444 return -99;
5445 }
Damjan Marion8389fb92017-10-13 18:29:53 +02005446 if (!is_pow2 (rx_ring_sz))
5447 {
5448 errmsg ("rx ring size must be power of 2. ");
5449 return -99;
5450 }
5451 if (rx_ring_sz > 32768)
5452 {
5453 errmsg ("rx ring size must be 32768 or lower. ");
5454 return -99;
5455 }
5456 if (!is_pow2 (tx_ring_sz))
5457 {
5458 errmsg ("tx ring size must be power of 2. ");
5459 return -99;
5460 }
5461 if (tx_ring_sz > 32768)
5462 {
5463 errmsg ("tx ring size must be 32768 or lower. ");
5464 return -99;
5465 }
Mohsin Kazmi97d54ed2019-06-10 11:20:15 +02005466 if (host_mtu_set && (host_mtu_size < 64 || host_mtu_size > 65355))
5467 {
5468 errmsg ("host MTU size must be in between 64 and 65355. ");
5469 return -99;
5470 }
Damjan Marion8389fb92017-10-13 18:29:53 +02005471
Damjan Marion8389fb92017-10-13 18:29:53 +02005472 /* Construct the API message */
5473 M (TAP_CREATE_V2, mp);
5474
Steven9e635692018-03-01 09:36:01 -08005475 mp->id = ntohl (id);
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005476 mp->use_random_mac = random_mac;
5477 mp->num_rx_queues = (u8) num_rx_queues;
Steven9e635692018-03-01 09:36:01 -08005478 mp->tx_ring_sz = ntohs (tx_ring_sz);
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005479 mp->rx_ring_sz = ntohs (rx_ring_sz);
Mohsin Kazmi97d54ed2019-06-10 11:20:15 +02005480 mp->host_mtu_set = host_mtu_set;
5481 mp->host_mtu_size = ntohl (host_mtu_size);
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005482 mp->host_mac_addr_set = host_mac_addr_set;
5483 mp->host_ip4_prefix_set = host_ip4_prefix_set;
5484 mp->host_ip6_prefix_set = host_ip6_prefix_set;
5485 mp->host_ip4_gw_set = host_ip4_gw_set;
5486 mp->host_ip6_gw_set = host_ip6_gw_set;
Mohsin Kazmi97d54ed2019-06-10 11:20:15 +02005487 mp->tap_flags = ntohl (tap_flags);
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005488 mp->host_namespace_set = host_ns_set;
5489 mp->host_if_name_set = host_if_name_set;
5490 mp->host_bridge_set = host_bridge_set;
Damjan Marion2df39092017-12-04 20:03:37 +01005491
Steven9e635692018-03-01 09:36:01 -08005492 if (random_mac == 0)
Damjan Marion2df39092017-12-04 20:03:37 +01005493 clib_memcpy (mp->mac_address, mac_address, 6);
5494 if (host_mac_addr_set)
5495 clib_memcpy (mp->host_mac_addr, host_mac_addr, 6);
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005496 if (host_if_name_set)
Damjan Marion2df39092017-12-04 20:03:37 +01005497 clib_memcpy (mp->host_if_name, host_if_name, vec_len (host_if_name));
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005498 if (host_ns_set)
Damjan Marion2df39092017-12-04 20:03:37 +01005499 clib_memcpy (mp->host_namespace, host_ns, vec_len (host_ns));
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005500 if (host_bridge_set)
Damjan Marion91c6ef72017-12-01 13:34:24 +01005501 clib_memcpy (mp->host_bridge, host_bridge, vec_len (host_bridge));
Mohsin Kazmi9f32b6a2020-02-14 12:09:04 +00005502 if (host_ip4_prefix_set)
5503 {
5504 clib_memcpy (mp->host_ip4_prefix.address, &host_ip4_addr, 4);
5505 mp->host_ip4_prefix.len = (u8) host_ip4_prefix_len;
5506 }
5507 if (host_ip6_prefix_set)
5508 {
5509 clib_memcpy (mp->host_ip6_prefix.address, &host_ip6_addr, 16);
5510 mp->host_ip6_prefix.len = (u8) host_ip6_prefix_len;
5511 }
Damjan Marion7866c452018-01-18 13:35:11 +01005512 if (host_ip4_gw_set)
5513 clib_memcpy (mp->host_ip4_gw, &host_ip4_gw, 4);
5514 if (host_ip6_gw_set)
5515 clib_memcpy (mp->host_ip6_gw, &host_ip6_gw, 16);
Damjan Marion8389fb92017-10-13 18:29:53 +02005516
Damjan Marion2df39092017-12-04 20:03:37 +01005517 vec_free (host_ns);
5518 vec_free (host_if_name);
5519 vec_free (host_bridge);
Damjan Marion8389fb92017-10-13 18:29:53 +02005520
5521 /* send it... */
5522 S (mp);
5523
5524 /* Wait for a reply... */
5525 W (ret);
5526 return ret;
5527}
5528
5529static int
5530api_tap_delete_v2 (vat_main_t * vam)
5531{
5532 unformat_input_t *i = vam->input;
5533 vl_api_tap_delete_v2_t *mp;
5534 u32 sw_if_index = ~0;
5535 u8 sw_if_index_set = 0;
5536 int ret;
5537
5538 /* Parse args required to build the message */
5539 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5540 {
5541 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
5542 sw_if_index_set = 1;
5543 else if (unformat (i, "sw_if_index %d", &sw_if_index))
5544 sw_if_index_set = 1;
5545 else
5546 break;
5547 }
5548
5549 if (sw_if_index_set == 0)
5550 {
5551 errmsg ("missing vpp interface name. ");
5552 return -99;
5553 }
5554
5555 /* Construct the API message */
5556 M (TAP_DELETE_V2, mp);
5557
5558 mp->sw_if_index = ntohl (sw_if_index);
5559
5560 /* send it... */
5561 S (mp);
5562
5563 /* Wait for a reply... */
5564 W (ret);
5565 return ret;
5566}
5567
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005568uword
jialv01082ebeb2019-09-10 00:23:55 +08005569unformat_vlib_pci_addr (unformat_input_t * input, va_list * args)
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005570{
jialv01082ebeb2019-09-10 00:23:55 +08005571 vlib_pci_addr_t *addr = va_arg (*args, vlib_pci_addr_t *);
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005572 u32 x[4];
5573
5574 if (!unformat (input, "%x:%x:%x.%x", &x[0], &x[1], &x[2], &x[3]))
5575 return 0;
5576
5577 addr->domain = x[0];
5578 addr->bus = x[1];
5579 addr->slot = x[2];
5580 addr->function = x[3];
5581
5582 return 1;
5583}
5584
5585static int
Mohsin Kazmi518251b2020-09-01 17:17:44 +00005586api_virtio_pci_create_v2 (vat_main_t * vam)
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005587{
5588 unformat_input_t *i = vam->input;
Mohsin Kazmi518251b2020-09-01 17:17:44 +00005589 vl_api_virtio_pci_create_v2_t *mp;
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005590 u8 mac_address[6];
5591 u8 random_mac = 1;
5592 u32 pci_addr = 0;
5593 u64 features = (u64) ~ (0ULL);
Mohsin Kazmi518251b2020-09-01 17:17:44 +00005594 u32 virtio_flags = 0;
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005595 int ret;
5596
5597 clib_memset (mac_address, 0, sizeof (mac_address));
5598
5599 /* Parse args required to build the message */
5600 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5601 {
5602 if (unformat (i, "hw-addr %U", unformat_ethernet_address, mac_address))
5603 {
5604 random_mac = 0;
5605 }
jialv01082ebeb2019-09-10 00:23:55 +08005606 else if (unformat (i, "pci-addr %U", unformat_vlib_pci_addr, &pci_addr))
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005607 ;
5608 else if (unformat (i, "features 0x%llx", &features))
5609 ;
Mohsin Kazmibbd6b742019-05-02 13:54:59 +02005610 else if (unformat (i, "gso-enabled"))
Mohsin Kazmi518251b2020-09-01 17:17:44 +00005611 virtio_flags |= VIRTIO_API_FLAG_GSO;
Mohsin Kazmi6d4af892020-01-03 15:11:53 +00005612 else if (unformat (i, "csum-offload-enabled"))
Mohsin Kazmi518251b2020-09-01 17:17:44 +00005613 virtio_flags |= VIRTIO_API_FLAG_CSUM_OFFLOAD;
5614 else if (unformat (i, "gro-coalesce"))
5615 virtio_flags |= VIRTIO_API_FLAG_GRO_COALESCE;
5616 else if (unformat (i, "packed"))
5617 virtio_flags |= VIRTIO_API_FLAG_PACKED;
5618 else if (unformat (i, "in-order"))
5619 virtio_flags |= VIRTIO_API_FLAG_IN_ORDER;
Mohsin Kazmie347acb2020-09-28 10:26:33 +00005620 else if (unformat (i, "buffering"))
5621 virtio_flags |= VIRTIO_API_FLAG_BUFFERING;
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005622 else
5623 break;
5624 }
5625
5626 if (pci_addr == 0)
5627 {
5628 errmsg ("pci address must be non zero. ");
5629 return -99;
5630 }
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005631
5632 /* Construct the API message */
Mohsin Kazmi518251b2020-09-01 17:17:44 +00005633 M (VIRTIO_PCI_CREATE_V2, mp);
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005634
5635 mp->use_random_mac = random_mac;
5636
Jakub Grajciar2c504f82019-09-26 10:34:41 +02005637 mp->pci_addr.domain = htons (((vlib_pci_addr_t) pci_addr).domain);
5638 mp->pci_addr.bus = ((vlib_pci_addr_t) pci_addr).bus;
5639 mp->pci_addr.slot = ((vlib_pci_addr_t) pci_addr).slot;
5640 mp->pci_addr.function = ((vlib_pci_addr_t) pci_addr).function;
5641
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005642 mp->features = clib_host_to_net_u64 (features);
Mohsin Kazmi518251b2020-09-01 17:17:44 +00005643 mp->virtio_flags = clib_host_to_net_u32 (virtio_flags);
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01005644
5645 if (random_mac == 0)
5646 clib_memcpy (mp->mac_address, mac_address, 6);
5647
5648 /* send it... */
5649 S (mp);
5650
5651 /* Wait for a reply... */
5652 W (ret);
5653 return ret;
5654}
5655
5656static int
5657api_virtio_pci_delete (vat_main_t * vam)
5658{
5659 unformat_input_t *i = vam->input;
5660 vl_api_virtio_pci_delete_t *mp;
5661 u32 sw_if_index = ~0;
5662 u8 sw_if_index_set = 0;
5663 int ret;
5664
5665 /* Parse args required to build the message */
5666 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5667 {
5668 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
5669 sw_if_index_set = 1;
5670 else if (unformat (i, "sw_if_index %d", &sw_if_index))
5671 sw_if_index_set = 1;
5672 else
5673 break;
5674 }
5675
5676 if (sw_if_index_set == 0)
5677 {
5678 errmsg ("missing vpp interface name. ");
5679 return -99;
5680 }
5681
5682 /* Construct the API message */
5683 M (VIRTIO_PCI_DELETE, mp);
5684
5685 mp->sw_if_index = htonl (sw_if_index);
5686
5687 /* send it... */
5688 S (mp);
5689
5690 /* Wait for a reply... */
5691 W (ret);
5692 return ret;
5693}
5694
Damjan Marion8389fb92017-10-13 18:29:53 +02005695static int
Steven9cd2d7a2017-12-20 12:43:01 -08005696api_bond_create (vat_main_t * vam)
5697{
5698 unformat_input_t *i = vam->input;
5699 vl_api_bond_create_t *mp;
5700 u8 mac_address[6];
5701 u8 custom_mac = 0;
5702 int ret;
5703 u8 mode;
5704 u8 lb;
5705 u8 mode_is_set = 0;
Alexander Chernavinad9d5282018-12-13 09:08:09 -05005706 u32 id = ~0;
Zhiyong Yang751e3f32019-06-26 05:49:14 -04005707 u8 numa_only = 0;
Steven9cd2d7a2017-12-20 12:43:01 -08005708
Dave Barachb7b92992018-10-17 10:38:51 -04005709 clib_memset (mac_address, 0, sizeof (mac_address));
Steven9cd2d7a2017-12-20 12:43:01 -08005710 lb = BOND_LB_L2;
5711
5712 /* Parse args required to build the message */
5713 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5714 {
5715 if (unformat (i, "mode %U", unformat_bond_mode, &mode))
5716 mode_is_set = 1;
5717 else if (((mode == BOND_MODE_LACP) || (mode == BOND_MODE_XOR))
5718 && unformat (i, "lb %U", unformat_bond_load_balance, &lb))
5719 ;
5720 else if (unformat (i, "hw-addr %U", unformat_ethernet_address,
5721 mac_address))
5722 custom_mac = 1;
Zhiyong Yang751e3f32019-06-26 05:49:14 -04005723 else if (unformat (i, "numa-only"))
5724 numa_only = 1;
Alexander Chernavinad9d5282018-12-13 09:08:09 -05005725 else if (unformat (i, "id %u", &id))
5726 ;
Steven9cd2d7a2017-12-20 12:43:01 -08005727 else
5728 break;
5729 }
5730
5731 if (mode_is_set == 0)
5732 {
5733 errmsg ("Missing bond mode. ");
5734 return -99;
5735 }
5736
5737 /* Construct the API message */
5738 M (BOND_CREATE, mp);
5739
5740 mp->use_custom_mac = custom_mac;
5741
Jakub Grajciar3d1ef872019-08-26 12:55:15 +02005742 mp->mode = htonl (mode);
5743 mp->lb = htonl (lb);
Alexander Chernavinad9d5282018-12-13 09:08:09 -05005744 mp->id = htonl (id);
Zhiyong Yang751e3f32019-06-26 05:49:14 -04005745 mp->numa_only = numa_only;
Steven9cd2d7a2017-12-20 12:43:01 -08005746
5747 if (custom_mac)
5748 clib_memcpy (mp->mac_address, mac_address, 6);
5749
5750 /* send it... */
5751 S (mp);
5752
5753 /* Wait for a reply... */
5754 W (ret);
5755 return ret;
5756}
5757
5758static int
Steven Luongea717862020-07-30 07:31:40 -07005759api_bond_create2 (vat_main_t * vam)
5760{
5761 unformat_input_t *i = vam->input;
5762 vl_api_bond_create2_t *mp;
5763 u8 mac_address[6];
5764 u8 custom_mac = 0;
5765 int ret;
5766 u8 mode;
5767 u8 lb;
5768 u8 mode_is_set = 0;
5769 u32 id = ~0;
5770 u8 numa_only = 0;
5771 u8 gso = 0;
5772
5773 clib_memset (mac_address, 0, sizeof (mac_address));
5774 lb = BOND_LB_L2;
5775
5776 /* Parse args required to build the message */
5777 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5778 {
5779 if (unformat (i, "mode %U", unformat_bond_mode, &mode))
5780 mode_is_set = 1;
5781 else if (((mode == BOND_MODE_LACP) || (mode == BOND_MODE_XOR))
5782 && unformat (i, "lb %U", unformat_bond_load_balance, &lb))
5783 ;
5784 else if (unformat (i, "hw-addr %U", unformat_ethernet_address,
5785 mac_address))
5786 custom_mac = 1;
5787 else if (unformat (i, "numa-only"))
5788 numa_only = 1;
5789 else if (unformat (i, "gso"))
5790 gso = 1;
5791 else if (unformat (i, "id %u", &id))
5792 ;
5793 else
5794 break;
5795 }
5796
5797 if (mode_is_set == 0)
5798 {
5799 errmsg ("Missing bond mode. ");
5800 return -99;
5801 }
5802
5803 /* Construct the API message */
5804 M (BOND_CREATE2, mp);
5805
5806 mp->use_custom_mac = custom_mac;
5807
5808 mp->mode = htonl (mode);
5809 mp->lb = htonl (lb);
5810 mp->id = htonl (id);
5811 mp->numa_only = numa_only;
5812 mp->enable_gso = gso;
5813
5814 if (custom_mac)
5815 clib_memcpy (mp->mac_address, mac_address, 6);
5816
5817 /* send it... */
5818 S (mp);
5819
5820 /* Wait for a reply... */
5821 W (ret);
5822 return ret;
5823}
5824
5825static int
Steven9cd2d7a2017-12-20 12:43:01 -08005826api_bond_delete (vat_main_t * vam)
5827{
5828 unformat_input_t *i = vam->input;
5829 vl_api_bond_delete_t *mp;
5830 u32 sw_if_index = ~0;
5831 u8 sw_if_index_set = 0;
5832 int ret;
5833
5834 /* Parse args required to build the message */
5835 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5836 {
5837 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
5838 sw_if_index_set = 1;
5839 else if (unformat (i, "sw_if_index %d", &sw_if_index))
5840 sw_if_index_set = 1;
5841 else
5842 break;
5843 }
5844
5845 if (sw_if_index_set == 0)
5846 {
5847 errmsg ("missing vpp interface name. ");
5848 return -99;
5849 }
5850
5851 /* Construct the API message */
5852 M (BOND_DELETE, mp);
5853
5854 mp->sw_if_index = ntohl (sw_if_index);
5855
5856 /* send it... */
5857 S (mp);
5858
5859 /* Wait for a reply... */
5860 W (ret);
5861 return ret;
5862}
5863
5864static int
Steven Luong4c4223e2020-07-15 08:44:54 -07005865api_bond_add_member (vat_main_t * vam)
Steven9cd2d7a2017-12-20 12:43:01 -08005866{
5867 unformat_input_t *i = vam->input;
Steven Luong4c4223e2020-07-15 08:44:54 -07005868 vl_api_bond_add_member_t *mp;
Steven9cd2d7a2017-12-20 12:43:01 -08005869 u32 bond_sw_if_index;
5870 int ret;
5871 u8 is_passive;
5872 u8 is_long_timeout;
5873 u32 bond_sw_if_index_is_set = 0;
5874 u32 sw_if_index;
5875 u8 sw_if_index_is_set = 0;
5876
5877 /* Parse args required to build the message */
5878 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5879 {
5880 if (unformat (i, "sw_if_index %d", &sw_if_index))
5881 sw_if_index_is_set = 1;
5882 else if (unformat (i, "bond %u", &bond_sw_if_index))
5883 bond_sw_if_index_is_set = 1;
5884 else if (unformat (i, "passive %d", &is_passive))
5885 ;
5886 else if (unformat (i, "long-timeout %d", &is_long_timeout))
5887 ;
5888 else
5889 break;
5890 }
5891
5892 if (bond_sw_if_index_is_set == 0)
5893 {
5894 errmsg ("Missing bond sw_if_index. ");
5895 return -99;
5896 }
5897 if (sw_if_index_is_set == 0)
5898 {
Steven Luong4c4223e2020-07-15 08:44:54 -07005899 errmsg ("Missing member sw_if_index. ");
Steven9cd2d7a2017-12-20 12:43:01 -08005900 return -99;
5901 }
5902
5903 /* Construct the API message */
Steven Luong4c4223e2020-07-15 08:44:54 -07005904 M (BOND_ADD_MEMBER, mp);
Steven9cd2d7a2017-12-20 12:43:01 -08005905
5906 mp->bond_sw_if_index = ntohl (bond_sw_if_index);
5907 mp->sw_if_index = ntohl (sw_if_index);
5908 mp->is_long_timeout = is_long_timeout;
5909 mp->is_passive = is_passive;
5910
5911 /* send it... */
5912 S (mp);
5913
5914 /* Wait for a reply... */
5915 W (ret);
5916 return ret;
5917}
5918
5919static int
Steven Luong4c4223e2020-07-15 08:44:54 -07005920api_bond_detach_member (vat_main_t * vam)
Steven9cd2d7a2017-12-20 12:43:01 -08005921{
5922 unformat_input_t *i = vam->input;
Steven Luong4c4223e2020-07-15 08:44:54 -07005923 vl_api_bond_detach_member_t *mp;
Steven9cd2d7a2017-12-20 12:43:01 -08005924 u32 sw_if_index = ~0;
5925 u8 sw_if_index_set = 0;
5926 int ret;
5927
5928 /* Parse args required to build the message */
5929 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5930 {
5931 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
5932 sw_if_index_set = 1;
5933 else if (unformat (i, "sw_if_index %d", &sw_if_index))
5934 sw_if_index_set = 1;
5935 else
5936 break;
5937 }
5938
5939 if (sw_if_index_set == 0)
5940 {
5941 errmsg ("missing vpp interface name. ");
5942 return -99;
5943 }
5944
5945 /* Construct the API message */
Steven Luong4c4223e2020-07-15 08:44:54 -07005946 M (BOND_DETACH_MEMBER, mp);
Steven9cd2d7a2017-12-20 12:43:01 -08005947
5948 mp->sw_if_index = ntohl (sw_if_index);
5949
5950 /* send it... */
5951 S (mp);
5952
5953 /* Wait for a reply... */
5954 W (ret);
5955 return ret;
5956}
5957
5958static int
Neale Ranns28ab9cc2017-08-14 07:18:42 -07005959api_ip_table_add_del (vat_main_t * vam)
5960{
5961 unformat_input_t *i = vam->input;
5962 vl_api_ip_table_add_del_t *mp;
5963 u32 table_id = ~0;
5964 u8 is_ipv6 = 0;
5965 u8 is_add = 1;
5966 int ret = 0;
5967
5968 /* Parse args required to build the message */
5969 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
5970 {
5971 if (unformat (i, "ipv6"))
5972 is_ipv6 = 1;
5973 else if (unformat (i, "del"))
5974 is_add = 0;
5975 else if (unformat (i, "add"))
5976 is_add = 1;
5977 else if (unformat (i, "table %d", &table_id))
5978 ;
5979 else
5980 {
5981 clib_warning ("parse error '%U'", format_unformat_error, i);
5982 return -99;
5983 }
5984 }
5985
5986 if (~0 == table_id)
5987 {
5988 errmsg ("missing table-ID");
5989 return -99;
5990 }
5991
5992 /* Construct the API message */
5993 M (IP_TABLE_ADD_DEL, mp);
5994
Neale Ranns097fa662018-05-01 05:17:55 -07005995 mp->table.table_id = ntohl (table_id);
5996 mp->table.is_ip6 = is_ipv6;
Neale Ranns28ab9cc2017-08-14 07:18:42 -07005997 mp->is_add = is_add;
5998
5999 /* send it... */
6000 S (mp);
6001
6002 /* Wait for a reply... */
6003 W (ret);
6004
6005 return ret;
6006}
6007
Neale Ranns097fa662018-05-01 05:17:55 -07006008uword
6009unformat_fib_path (unformat_input_t * input, va_list * args)
6010{
6011 vat_main_t *vam = va_arg (*args, vat_main_t *);
6012 vl_api_fib_path_t *path = va_arg (*args, vl_api_fib_path_t *);
6013 u32 weight, preference;
6014 mpls_label_t out_label;
6015
6016 clib_memset (path, 0, sizeof (*path));
6017 path->weight = 1;
6018 path->sw_if_index = ~0;
6019 path->rpf_id = ~0;
6020 path->n_labels = 0;
6021
6022 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
6023 {
6024 if (unformat (input, "%U %U",
6025 unformat_vl_api_ip4_address,
6026 &path->nh.address.ip4,
6027 api_unformat_sw_if_index, vam, &path->sw_if_index))
6028 {
6029 path->proto = FIB_API_PATH_NH_PROTO_IP4;
6030 }
6031 else if (unformat (input, "%U %U",
6032 unformat_vl_api_ip6_address,
6033 &path->nh.address.ip6,
6034 api_unformat_sw_if_index, vam, &path->sw_if_index))
6035 {
6036 path->proto = FIB_API_PATH_NH_PROTO_IP6;
6037 }
6038 else if (unformat (input, "weight %u", &weight))
6039 {
6040 path->weight = weight;
6041 }
6042 else if (unformat (input, "preference %u", &preference))
6043 {
6044 path->preference = preference;
6045 }
6046 else if (unformat (input, "%U next-hop-table %d",
6047 unformat_vl_api_ip4_address,
6048 &path->nh.address.ip4, &path->table_id))
6049 {
6050 path->proto = FIB_API_PATH_NH_PROTO_IP4;
6051 }
6052 else if (unformat (input, "%U next-hop-table %d",
6053 unformat_vl_api_ip6_address,
6054 &path->nh.address.ip6, &path->table_id))
6055 {
6056 path->proto = FIB_API_PATH_NH_PROTO_IP6;
6057 }
6058 else if (unformat (input, "%U",
6059 unformat_vl_api_ip4_address, &path->nh.address.ip4))
6060 {
6061 /*
6062 * the recursive next-hops are by default in the default table
6063 */
6064 path->table_id = 0;
6065 path->sw_if_index = ~0;
6066 path->proto = FIB_API_PATH_NH_PROTO_IP4;
6067 }
6068 else if (unformat (input, "%U",
6069 unformat_vl_api_ip6_address, &path->nh.address.ip6))
6070 {
6071 /*
6072 * the recursive next-hops are by default in the default table
6073 */
6074 path->table_id = 0;
6075 path->sw_if_index = ~0;
6076 path->proto = FIB_API_PATH_NH_PROTO_IP6;
6077 }
6078 else if (unformat (input, "resolve-via-host"))
6079 {
6080 path->flags |= FIB_API_PATH_FLAG_RESOLVE_VIA_HOST;
6081 }
6082 else if (unformat (input, "resolve-via-attached"))
6083 {
6084 path->flags |= FIB_API_PATH_FLAG_RESOLVE_VIA_ATTACHED;
6085 }
6086 else if (unformat (input, "ip4-lookup-in-table %d", &path->table_id))
6087 {
6088 path->type = FIB_API_PATH_TYPE_LOCAL;
6089 path->sw_if_index = ~0;
6090 path->proto = FIB_API_PATH_NH_PROTO_IP4;
6091 }
6092 else if (unformat (input, "ip6-lookup-in-table %d", &path->table_id))
6093 {
6094 path->type = FIB_API_PATH_TYPE_LOCAL;
6095 path->sw_if_index = ~0;
6096 path->proto = FIB_API_PATH_NH_PROTO_IP6;
6097 }
6098 else if (unformat (input, "sw_if_index %d", &path->sw_if_index))
6099 ;
6100 else if (unformat (input, "via-label %d", &path->nh.via_label))
6101 {
6102 path->proto = FIB_API_PATH_NH_PROTO_MPLS;
6103 path->sw_if_index = ~0;
6104 }
6105 else if (unformat (input, "l2-input-on %d", &path->sw_if_index))
6106 {
6107 path->proto = FIB_API_PATH_NH_PROTO_ETHERNET;
6108 path->type = FIB_API_PATH_TYPE_INTERFACE_RX;
6109 }
6110 else if (unformat (input, "local"))
6111 {
6112 path->type = FIB_API_PATH_TYPE_LOCAL;
6113 }
6114 else if (unformat (input, "out-labels"))
6115 {
6116 while (unformat (input, "%d", &out_label))
6117 {
6118 path->label_stack[path->n_labels].label = out_label;
6119 path->label_stack[path->n_labels].is_uniform = 0;
6120 path->label_stack[path->n_labels].ttl = 64;
6121 path->n_labels++;
6122 }
6123 }
6124 else if (unformat (input, "via"))
6125 {
6126 /* new path, back up and return */
6127 unformat_put_input (input);
6128 unformat_put_input (input);
6129 unformat_put_input (input);
6130 unformat_put_input (input);
6131 break;
6132 }
6133 else
6134 {
6135 return (0);
6136 }
6137 }
6138
6139 path->proto = ntohl (path->proto);
6140 path->type = ntohl (path->type);
6141 path->flags = ntohl (path->flags);
6142 path->table_id = ntohl (path->table_id);
6143 path->sw_if_index = ntohl (path->sw_if_index);
6144
6145 return (1);
6146}
6147
Neale Ranns28ab9cc2017-08-14 07:18:42 -07006148static int
Neale Ranns097fa662018-05-01 05:17:55 -07006149api_ip_route_add_del (vat_main_t * vam)
Damjan Marion7cd468a2016-12-19 23:05:39 +01006150{
6151 unformat_input_t *i = vam->input;
Neale Ranns097fa662018-05-01 05:17:55 -07006152 vl_api_ip_route_add_del_t *mp;
6153 u32 vrf_id = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006154 u8 is_add = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006155 u8 is_multipath = 0;
Neale Ranns097fa662018-05-01 05:17:55 -07006156 u8 prefix_set = 0;
6157 u8 path_count = 0;
6158 vl_api_prefix_t pfx = { };
6159 vl_api_fib_path_t paths[8];
Damjan Marion7cd468a2016-12-19 23:05:39 +01006160 int count = 1;
6161 int j;
6162 f64 before = 0;
6163 u32 random_add_del = 0;
6164 u32 *random_vector = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006165 u32 random_seed = 0xdeaddabe;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006166
6167 /* Parse args required to build the message */
6168 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
6169 {
Neale Ranns097fa662018-05-01 05:17:55 -07006170 if (unformat (i, "%U", unformat_vl_api_prefix, &pfx))
6171 prefix_set = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006172 else if (unformat (i, "del"))
6173 is_add = 0;
6174 else if (unformat (i, "add"))
6175 is_add = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006176 else if (unformat (i, "vrf %d", &vrf_id))
6177 ;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006178 else if (unformat (i, "count %d", &count))
6179 ;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006180 else if (unformat (i, "random"))
6181 random_add_del = 1;
Neale Ranns097fa662018-05-01 05:17:55 -07006182 else if (unformat (i, "multipath"))
6183 is_multipath = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006184 else if (unformat (i, "seed %d", &random_seed))
6185 ;
6186 else
Neale Ranns097fa662018-05-01 05:17:55 -07006187 if (unformat
6188 (i, "via %U", unformat_fib_path, vam, &paths[path_count]))
6189 {
6190 path_count++;
6191 if (8 == path_count)
6192 {
6193 errmsg ("max 8 paths");
6194 return -99;
6195 }
6196 }
6197 else
Damjan Marion7cd468a2016-12-19 23:05:39 +01006198 {
6199 clib_warning ("parse error '%U'", format_unformat_error, i);
6200 return -99;
6201 }
6202 }
6203
Neale Ranns097fa662018-05-01 05:17:55 -07006204 if (!path_count)
Damjan Marion7cd468a2016-12-19 23:05:39 +01006205 {
Neale Ranns097fa662018-05-01 05:17:55 -07006206 errmsg ("specify a path; via ...");
Damjan Marion7cd468a2016-12-19 23:05:39 +01006207 return -99;
6208 }
Neale Ranns097fa662018-05-01 05:17:55 -07006209 if (prefix_set == 0)
Damjan Marion7cd468a2016-12-19 23:05:39 +01006210 {
Neale Ranns097fa662018-05-01 05:17:55 -07006211 errmsg ("missing prefix");
Damjan Marion7cd468a2016-12-19 23:05:39 +01006212 return -99;
6213 }
6214
6215 /* Generate a pile of unique, random routes */
6216 if (random_add_del)
6217 {
Neale Ranns097fa662018-05-01 05:17:55 -07006218 ip4_address_t *i = (ip4_address_t *) & paths[0].nh.address.ip4;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006219 u32 this_random_address;
Neale Ranns097fa662018-05-01 05:17:55 -07006220 uword *random_hash;
6221
Damjan Marion7cd468a2016-12-19 23:05:39 +01006222 random_hash = hash_create (count, sizeof (uword));
6223
Neale Ranns097fa662018-05-01 05:17:55 -07006224 hash_set (random_hash, i->as_u32, 1);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006225 for (j = 0; j <= count; j++)
6226 {
6227 do
6228 {
6229 this_random_address = random_u32 (&random_seed);
6230 this_random_address =
6231 clib_host_to_net_u32 (this_random_address);
6232 }
6233 while (hash_get (random_hash, this_random_address));
6234 vec_add1 (random_vector, this_random_address);
6235 hash_set (random_hash, this_random_address, 1);
6236 }
6237 hash_free (random_hash);
Neale Ranns097fa662018-05-01 05:17:55 -07006238 set_ip4_address (&pfx.address, random_vector[0]);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006239 }
6240
6241 if (count > 1)
6242 {
6243 /* Turn on async mode */
6244 vam->async_mode = 1;
6245 vam->async_errors = 0;
6246 before = vat_time_now (vam);
6247 }
6248
6249 for (j = 0; j < count; j++)
6250 {
6251 /* Construct the API message */
Neale Ranns097fa662018-05-01 05:17:55 -07006252 M2 (IP_ROUTE_ADD_DEL, mp, sizeof (vl_api_fib_path_t) * path_count);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006253
6254 mp->is_add = is_add;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006255 mp->is_multipath = is_multipath;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006256
Neale Ranns097fa662018-05-01 05:17:55 -07006257 clib_memcpy (&mp->route.prefix, &pfx, sizeof (pfx));
6258 mp->route.table_id = ntohl (vrf_id);
6259 mp->route.n_paths = path_count;
6260
6261 clib_memcpy (&mp->route.paths, &paths, sizeof (paths[0]) * path_count);
6262
6263 if (random_add_del)
6264 set_ip4_address (&pfx.address, random_vector[j + 1]);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006265 else
Neale Ranns097fa662018-05-01 05:17:55 -07006266 increment_address (&pfx.address);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006267 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06006268 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006269 /* If we receive SIGTERM, stop now... */
6270 if (vam->do_exit)
6271 break;
6272 }
6273
6274 /* When testing multiple add/del ops, use a control-ping to sync */
6275 if (count > 1)
6276 {
Jon Loeliger2d23eca2017-02-01 13:09:58 -06006277 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006278 f64 after;
Jon Loeliger1f9191f2017-01-31 15:27:19 -06006279 f64 timeout;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006280
6281 /* Shut off async mode */
6282 vam->async_mode = 0;
6283
Dave Barach59b25652017-09-10 15:04:27 -04006284 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -06006285 S (mp_ping);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006286
6287 timeout = vat_time_now (vam) + 1.0;
6288 while (vat_time_now (vam) < timeout)
6289 if (vam->result_ready == 1)
6290 goto out;
6291 vam->retval = -99;
6292
6293 out:
6294 if (vam->retval == -99)
6295 errmsg ("timeout");
6296
6297 if (vam->async_errors > 0)
6298 {
6299 errmsg ("%d asynchronous errors", vam->async_errors);
6300 vam->retval = -98;
6301 }
6302 vam->async_errors = 0;
6303 after = vat_time_now (vam);
6304
6305 /* slim chance, but we might have eaten SIGTERM on the first iteration */
6306 if (j > 0)
6307 count = j;
6308
6309 print (vam->ofp, "%d routes in %.6f secs, %.2f routes/sec",
6310 count, after - before, count / (after - before));
6311 }
6312 else
6313 {
Jon Loeliger56c7b012017-02-01 12:31:41 -06006314 int ret;
6315
Damjan Marion7cd468a2016-12-19 23:05:39 +01006316 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -06006317 W (ret);
6318 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006319 }
6320
6321 /* Return the good/bad news */
6322 return (vam->retval);
6323}
6324
6325static int
Neale Ranns32e1c012016-11-22 17:07:28 +00006326api_ip_mroute_add_del (vat_main_t * vam)
6327{
6328 unformat_input_t *i = vam->input;
Neale Ranns097fa662018-05-01 05:17:55 -07006329 u8 path_set = 0, prefix_set = 0, is_add = 1;
Neale Ranns32e1c012016-11-22 17:07:28 +00006330 vl_api_ip_mroute_add_del_t *mp;
Neale Ranns32e1c012016-11-22 17:07:28 +00006331 mfib_entry_flags_t eflags = 0;
Neale Ranns097fa662018-05-01 05:17:55 -07006332 vl_api_mfib_path_t path;
6333 vl_api_mprefix_t pfx = { };
6334 u32 vrf_id = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06006335 int ret;
Neale Ranns32e1c012016-11-22 17:07:28 +00006336
6337 /* Parse args required to build the message */
6338 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
6339 {
Neale Ranns097fa662018-05-01 05:17:55 -07006340 if (unformat (i, "%U", unformat_vl_api_mprefix, &pfx))
Neale Ranns32e1c012016-11-22 17:07:28 +00006341 {
Neale Ranns097fa662018-05-01 05:17:55 -07006342 prefix_set = 1;
6343 pfx.grp_address_length = htons (pfx.grp_address_length);
Neale Ranns32e1c012016-11-22 17:07:28 +00006344 }
6345 else if (unformat (i, "del"))
6346 is_add = 0;
6347 else if (unformat (i, "add"))
6348 is_add = 1;
6349 else if (unformat (i, "vrf %d", &vrf_id))
6350 ;
Neale Ranns097fa662018-05-01 05:17:55 -07006351 else if (unformat (i, "%U", unformat_mfib_itf_flags, &path.itf_flags))
6352 path.itf_flags = htonl (path.itf_flags);
Neale Ranns32e1c012016-11-22 17:07:28 +00006353 else if (unformat (i, "%U", unformat_mfib_entry_flags, &eflags))
6354 ;
Neale Ranns097fa662018-05-01 05:17:55 -07006355 else if (unformat (i, "via %U", unformat_fib_path, vam, &path.path))
6356 path_set = 1;
Neale Ranns32e1c012016-11-22 17:07:28 +00006357 else
6358 {
6359 clib_warning ("parse error '%U'", format_unformat_error, i);
6360 return -99;
6361 }
6362 }
6363
Neale Ranns097fa662018-05-01 05:17:55 -07006364 if (prefix_set == 0)
Neale Ranns32e1c012016-11-22 17:07:28 +00006365 {
6366 errmsg ("missing addresses\n");
6367 return -99;
6368 }
Neale Ranns097fa662018-05-01 05:17:55 -07006369 if (path_set == 0)
6370 {
6371 errmsg ("missing path\n");
6372 return -99;
6373 }
Neale Ranns32e1c012016-11-22 17:07:28 +00006374
6375 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06006376 M (IP_MROUTE_ADD_DEL, mp);
Neale Ranns32e1c012016-11-22 17:07:28 +00006377
Neale Ranns32e1c012016-11-22 17:07:28 +00006378 mp->is_add = is_add;
Neale Ranns097fa662018-05-01 05:17:55 -07006379 mp->is_multipath = 1;
Neale Ranns32e1c012016-11-22 17:07:28 +00006380
Neale Ranns097fa662018-05-01 05:17:55 -07006381 clib_memcpy (&mp->route.prefix, &pfx, sizeof (pfx));
6382 mp->route.table_id = htonl (vrf_id);
6383 mp->route.n_paths = 1;
6384 mp->route.entry_flags = htonl (eflags);
Neale Ranns32e1c012016-11-22 17:07:28 +00006385
Neale Ranns097fa662018-05-01 05:17:55 -07006386 clib_memcpy (&mp->route.paths, &path, sizeof (path));
Neale Ranns32e1c012016-11-22 17:07:28 +00006387
6388 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06006389 S (mp);
Neale Ranns32e1c012016-11-22 17:07:28 +00006390 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -06006391 W (ret);
6392 return ret;
Neale Ranns32e1c012016-11-22 17:07:28 +00006393}
6394
6395static int
Neale Ranns28ab9cc2017-08-14 07:18:42 -07006396api_mpls_table_add_del (vat_main_t * vam)
6397{
6398 unformat_input_t *i = vam->input;
6399 vl_api_mpls_table_add_del_t *mp;
6400 u32 table_id = ~0;
6401 u8 is_add = 1;
6402 int ret = 0;
6403
6404 /* Parse args required to build the message */
6405 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
6406 {
Florin Corasd0a59722017-10-15 17:41:21 +00006407 if (unformat (i, "table %d", &table_id))
6408 ;
6409 else if (unformat (i, "del"))
Neale Ranns28ab9cc2017-08-14 07:18:42 -07006410 is_add = 0;
6411 else if (unformat (i, "add"))
6412 is_add = 1;
6413 else
6414 {
6415 clib_warning ("parse error '%U'", format_unformat_error, i);
6416 return -99;
6417 }
6418 }
6419
6420 if (~0 == table_id)
6421 {
6422 errmsg ("missing table-ID");
6423 return -99;
6424 }
6425
6426 /* Construct the API message */
6427 M (MPLS_TABLE_ADD_DEL, mp);
6428
Neale Ranns097fa662018-05-01 05:17:55 -07006429 mp->mt_table.mt_table_id = ntohl (table_id);
Neale Ranns28ab9cc2017-08-14 07:18:42 -07006430 mp->mt_is_add = is_add;
6431
6432 /* send it... */
6433 S (mp);
6434
6435 /* Wait for a reply... */
6436 W (ret);
6437
6438 return ret;
6439}
6440
6441static int
Damjan Marion7cd468a2016-12-19 23:05:39 +01006442api_mpls_route_add_del (vat_main_t * vam)
6443{
Neale Ranns097fa662018-05-01 05:17:55 -07006444 u8 is_add = 1, path_count = 0, is_multipath = 0, is_eos = 0;
6445 mpls_label_t local_label = MPLS_LABEL_INVALID;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006446 unformat_input_t *i = vam->input;
6447 vl_api_mpls_route_add_del_t *mp;
Neale Ranns097fa662018-05-01 05:17:55 -07006448 vl_api_fib_path_t paths[8];
6449 int count = 1, j;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006450 f64 before = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006451
6452 /* Parse args required to build the message */
6453 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
6454 {
Neale Ranns097fa662018-05-01 05:17:55 -07006455 if (unformat (i, "%d", &local_label))
Damjan Marion7cd468a2016-12-19 23:05:39 +01006456 ;
6457 else if (unformat (i, "eos"))
6458 is_eos = 1;
6459 else if (unformat (i, "non-eos"))
6460 is_eos = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006461 else if (unformat (i, "del"))
6462 is_add = 0;
6463 else if (unformat (i, "add"))
6464 is_add = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006465 else if (unformat (i, "multipath"))
6466 is_multipath = 1;
6467 else if (unformat (i, "count %d", &count))
6468 ;
John Loe166fd92018-09-13 14:08:59 -04006469 else
6470 if (unformat
Neale Ranns097fa662018-05-01 05:17:55 -07006471 (i, "via %U", unformat_fib_path, vam, &paths[path_count]))
John Loe166fd92018-09-13 14:08:59 -04006472 {
Neale Ranns097fa662018-05-01 05:17:55 -07006473 path_count++;
6474 if (8 == path_count)
6475 {
6476 errmsg ("max 8 paths");
6477 return -99;
6478 }
John Loe166fd92018-09-13 14:08:59 -04006479 }
Damjan Marion7cd468a2016-12-19 23:05:39 +01006480 else
6481 {
6482 clib_warning ("parse error '%U'", format_unformat_error, i);
6483 return -99;
6484 }
6485 }
6486
Neale Ranns097fa662018-05-01 05:17:55 -07006487 if (!path_count)
Damjan Marion7cd468a2016-12-19 23:05:39 +01006488 {
Neale Ranns097fa662018-05-01 05:17:55 -07006489 errmsg ("specify a path; via ...");
Damjan Marion7cd468a2016-12-19 23:05:39 +01006490 return -99;
6491 }
6492
6493 if (MPLS_LABEL_INVALID == local_label)
6494 {
6495 errmsg ("missing label");
6496 return -99;
6497 }
6498
6499 if (count > 1)
6500 {
6501 /* Turn on async mode */
6502 vam->async_mode = 1;
6503 vam->async_errors = 0;
6504 before = vat_time_now (vam);
6505 }
6506
6507 for (j = 0; j < count; j++)
6508 {
6509 /* Construct the API message */
Neale Ranns097fa662018-05-01 05:17:55 -07006510 M2 (MPLS_ROUTE_ADD_DEL, mp, sizeof (vl_api_fib_path_t) * path_count);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006511
6512 mp->mr_is_add = is_add;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006513 mp->mr_is_multipath = is_multipath;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006514
Neale Ranns097fa662018-05-01 05:17:55 -07006515 mp->mr_route.mr_label = local_label;
6516 mp->mr_route.mr_eos = is_eos;
6517 mp->mr_route.mr_table_id = 0;
6518 mp->mr_route.mr_n_paths = path_count;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006519
Neale Ranns097fa662018-05-01 05:17:55 -07006520 clib_memcpy (&mp->mr_route.mr_paths, paths,
6521 sizeof (paths[0]) * path_count);
Neale Rannsda78f952017-05-24 09:15:43 -07006522
Damjan Marion7cd468a2016-12-19 23:05:39 +01006523 local_label++;
6524
6525 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06006526 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006527 /* If we receive SIGTERM, stop now... */
6528 if (vam->do_exit)
6529 break;
6530 }
6531
6532 /* When testing multiple add/del ops, use a control-ping to sync */
6533 if (count > 1)
6534 {
Jon Loeliger2d23eca2017-02-01 13:09:58 -06006535 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006536 f64 after;
Jon Loeliger1f9191f2017-01-31 15:27:19 -06006537 f64 timeout;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006538
6539 /* Shut off async mode */
6540 vam->async_mode = 0;
6541
Dave Barach59b25652017-09-10 15:04:27 -04006542 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -06006543 S (mp_ping);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006544
6545 timeout = vat_time_now (vam) + 1.0;
6546 while (vat_time_now (vam) < timeout)
6547 if (vam->result_ready == 1)
6548 goto out;
6549 vam->retval = -99;
6550
6551 out:
6552 if (vam->retval == -99)
6553 errmsg ("timeout");
6554
6555 if (vam->async_errors > 0)
6556 {
6557 errmsg ("%d asynchronous errors", vam->async_errors);
6558 vam->retval = -98;
6559 }
6560 vam->async_errors = 0;
6561 after = vat_time_now (vam);
6562
6563 /* slim chance, but we might have eaten SIGTERM on the first iteration */
6564 if (j > 0)
6565 count = j;
6566
6567 print (vam->ofp, "%d routes in %.6f secs, %.2f routes/sec",
6568 count, after - before, count / (after - before));
6569 }
6570 else
6571 {
Jon Loeliger56c7b012017-02-01 12:31:41 -06006572 int ret;
6573
Damjan Marion7cd468a2016-12-19 23:05:39 +01006574 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -06006575 W (ret);
6576 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006577 }
6578
6579 /* Return the good/bad news */
6580 return (vam->retval);
Neale Ranns097fa662018-05-01 05:17:55 -07006581 return (0);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006582}
6583
6584static int
6585api_mpls_ip_bind_unbind (vat_main_t * vam)
6586{
6587 unformat_input_t *i = vam->input;
6588 vl_api_mpls_ip_bind_unbind_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006589 u32 ip_table_id = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006590 u8 is_bind = 1;
Neale Ranns097fa662018-05-01 05:17:55 -07006591 vl_api_prefix_t pfx;
6592 u8 prefix_set = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006593 mpls_label_t local_label = MPLS_LABEL_INVALID;
Jon Loeliger56c7b012017-02-01 12:31:41 -06006594 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006595
6596 /* Parse args required to build the message */
6597 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
6598 {
Neale Ranns097fa662018-05-01 05:17:55 -07006599 if (unformat (i, "%U", unformat_vl_api_prefix, &pfx))
6600 prefix_set = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006601 else if (unformat (i, "%d", &local_label))
6602 ;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006603 else if (unformat (i, "table-id %d", &ip_table_id))
6604 ;
6605 else if (unformat (i, "unbind"))
6606 is_bind = 0;
6607 else if (unformat (i, "bind"))
6608 is_bind = 1;
6609 else
6610 {
6611 clib_warning ("parse error '%U'", format_unformat_error, i);
6612 return -99;
6613 }
6614 }
6615
Neale Ranns097fa662018-05-01 05:17:55 -07006616 if (!prefix_set)
Damjan Marion7cd468a2016-12-19 23:05:39 +01006617 {
Neale Ranns097fa662018-05-01 05:17:55 -07006618 errmsg ("IP prefix not set");
Damjan Marion7cd468a2016-12-19 23:05:39 +01006619 return -99;
6620 }
6621
6622 if (MPLS_LABEL_INVALID == local_label)
6623 {
6624 errmsg ("missing label");
6625 return -99;
6626 }
6627
6628 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06006629 M (MPLS_IP_BIND_UNBIND, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006630
Damjan Marion7cd468a2016-12-19 23:05:39 +01006631 mp->mb_is_bind = is_bind;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006632 mp->mb_ip_table_id = ntohl (ip_table_id);
6633 mp->mb_mpls_table_id = 0;
6634 mp->mb_label = ntohl (local_label);
Neale Ranns097fa662018-05-01 05:17:55 -07006635 clib_memcpy (&mp->mb_prefix, &pfx, sizeof (pfx));
Damjan Marion7cd468a2016-12-19 23:05:39 +01006636
6637 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -06006638 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006639
6640 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -06006641 W (ret);
6642 return ret;
Neale Ranns097fa662018-05-01 05:17:55 -07006643 return (0);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006644}
6645
6646static int
John Loe166fd92018-09-13 14:08:59 -04006647api_sr_mpls_policy_add (vat_main_t * vam)
6648{
6649 unformat_input_t *i = vam->input;
6650 vl_api_sr_mpls_policy_add_t *mp;
6651 u32 bsid = 0;
6652 u32 weight = 1;
6653 u8 type = 0;
6654 u8 n_segments = 0;
6655 u32 sid;
6656 u32 *segments = NULL;
6657 int ret;
6658
6659 /* Parse args required to build the message */
6660 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
6661 {
6662 if (unformat (i, "bsid %d", &bsid))
6663 ;
6664 else if (unformat (i, "weight %d", &weight))
6665 ;
6666 else if (unformat (i, "spray"))
6667 type = 1;
6668 else if (unformat (i, "next %d", &sid))
6669 {
6670 n_segments += 1;
6671 vec_add1 (segments, htonl (sid));
6672 }
6673 else
6674 {
6675 clib_warning ("parse error '%U'", format_unformat_error, i);
6676 return -99;
6677 }
6678 }
6679
6680 if (bsid == 0)
6681 {
6682 errmsg ("bsid not set");
6683 return -99;
6684 }
6685
6686 if (n_segments == 0)
6687 {
6688 errmsg ("no sid in segment stack");
6689 return -99;
6690 }
6691
6692 /* Construct the API message */
6693 M2 (SR_MPLS_POLICY_ADD, mp, sizeof (u32) * n_segments);
6694
6695 mp->bsid = htonl (bsid);
6696 mp->weight = htonl (weight);
Jakub Grajciar00ec4012020-01-31 10:17:29 +01006697 mp->is_spray = type;
John Loe166fd92018-09-13 14:08:59 -04006698 mp->n_segments = n_segments;
6699 memcpy (mp->segments, segments, sizeof (u32) * n_segments);
6700 vec_free (segments);
6701
6702 /* send it... */
6703 S (mp);
6704
6705 /* Wait for a reply... */
6706 W (ret);
6707 return ret;
6708}
6709
6710static int
6711api_sr_mpls_policy_del (vat_main_t * vam)
6712{
6713 unformat_input_t *i = vam->input;
6714 vl_api_sr_mpls_policy_del_t *mp;
6715 u32 bsid = 0;
6716 int ret;
6717
6718 /* Parse args required to build the message */
6719 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
6720 {
6721 if (unformat (i, "bsid %d", &bsid))
6722 ;
6723 else
6724 {
6725 clib_warning ("parse error '%U'", format_unformat_error, i);
6726 return -99;
6727 }
6728 }
6729
6730 if (bsid == 0)
6731 {
6732 errmsg ("bsid not set");
6733 return -99;
6734 }
6735
6736 /* Construct the API message */
6737 M (SR_MPLS_POLICY_DEL, mp);
6738
6739 mp->bsid = htonl (bsid);
6740
6741 /* send it... */
6742 S (mp);
6743
6744 /* Wait for a reply... */
6745 W (ret);
6746 return ret;
6747}
6748
6749static int
Neale Rannsd792d9c2017-10-21 10:53:20 -07006750api_bier_table_add_del (vat_main_t * vam)
6751{
6752 unformat_input_t *i = vam->input;
6753 vl_api_bier_table_add_del_t *mp;
6754 u8 is_add = 1;
6755 u32 set = 0, sub_domain = 0, hdr_len = 3;
6756 mpls_label_t local_label = MPLS_LABEL_INVALID;
6757 int ret;
6758
6759 /* Parse args required to build the message */
6760 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
6761 {
6762 if (unformat (i, "sub-domain %d", &sub_domain))
6763 ;
6764 else if (unformat (i, "set %d", &set))
6765 ;
6766 else if (unformat (i, "label %d", &local_label))
6767 ;
6768 else if (unformat (i, "hdr-len %d", &hdr_len))
6769 ;
6770 else if (unformat (i, "add"))
6771 is_add = 1;
6772 else if (unformat (i, "del"))
6773 is_add = 0;
6774 else
6775 {
6776 clib_warning ("parse error '%U'", format_unformat_error, i);
6777 return -99;
6778 }
6779 }
6780
6781 if (MPLS_LABEL_INVALID == local_label)
6782 {
6783 errmsg ("missing label\n");
6784 return -99;
6785 }
6786
6787 /* Construct the API message */
6788 M (BIER_TABLE_ADD_DEL, mp);
6789
6790 mp->bt_is_add = is_add;
6791 mp->bt_label = ntohl (local_label);
6792 mp->bt_tbl_id.bt_set = set;
6793 mp->bt_tbl_id.bt_sub_domain = sub_domain;
6794 mp->bt_tbl_id.bt_hdr_len_id = hdr_len;
6795
6796 /* send it... */
6797 S (mp);
6798
6799 /* Wait for a reply... */
6800 W (ret);
6801
6802 return (ret);
6803}
6804
6805static int
6806api_bier_route_add_del (vat_main_t * vam)
6807{
6808 unformat_input_t *i = vam->input;
6809 vl_api_bier_route_add_del_t *mp;
6810 u8 is_add = 1;
6811 u32 set = 0, sub_domain = 0, hdr_len = 3, bp = 0;
6812 ip4_address_t v4_next_hop_address;
6813 ip6_address_t v6_next_hop_address;
6814 u8 next_hop_set = 0;
6815 u8 next_hop_proto_is_ip4 = 1;
6816 mpls_label_t next_hop_out_label = MPLS_LABEL_INVALID;
6817 int ret;
6818
6819 /* Parse args required to build the message */
6820 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
6821 {
6822 if (unformat (i, "%U", unformat_ip4_address, &v4_next_hop_address))
6823 {
6824 next_hop_proto_is_ip4 = 1;
6825 next_hop_set = 1;
6826 }
6827 else if (unformat (i, "%U", unformat_ip6_address, &v6_next_hop_address))
6828 {
6829 next_hop_proto_is_ip4 = 0;
6830 next_hop_set = 1;
6831 }
6832 if (unformat (i, "sub-domain %d", &sub_domain))
6833 ;
6834 else if (unformat (i, "set %d", &set))
6835 ;
6836 else if (unformat (i, "hdr-len %d", &hdr_len))
6837 ;
6838 else if (unformat (i, "bp %d", &bp))
6839 ;
6840 else if (unformat (i, "add"))
6841 is_add = 1;
6842 else if (unformat (i, "del"))
6843 is_add = 0;
6844 else if (unformat (i, "out-label %d", &next_hop_out_label))
6845 ;
6846 else
6847 {
6848 clib_warning ("parse error '%U'", format_unformat_error, i);
6849 return -99;
6850 }
6851 }
6852
6853 if (!next_hop_set || (MPLS_LABEL_INVALID == next_hop_out_label))
6854 {
6855 errmsg ("next hop / label set\n");
6856 return -99;
6857 }
6858 if (0 == bp)
6859 {
6860 errmsg ("bit=position not set\n");
6861 return -99;
6862 }
6863
6864 /* Construct the API message */
Neale Ranns31ed7442018-02-23 05:29:09 -08006865 M2 (BIER_ROUTE_ADD_DEL, mp, sizeof (vl_api_fib_path_t));
Neale Rannsd792d9c2017-10-21 10:53:20 -07006866
6867 mp->br_is_add = is_add;
Neale Ranns097fa662018-05-01 05:17:55 -07006868 mp->br_route.br_tbl_id.bt_set = set;
6869 mp->br_route.br_tbl_id.bt_sub_domain = sub_domain;
6870 mp->br_route.br_tbl_id.bt_hdr_len_id = hdr_len;
6871 mp->br_route.br_bp = ntohs (bp);
6872 mp->br_route.br_n_paths = 1;
6873 mp->br_route.br_paths[0].n_labels = 1;
6874 mp->br_route.br_paths[0].label_stack[0].label = ntohl (next_hop_out_label);
6875 mp->br_route.br_paths[0].proto = (next_hop_proto_is_ip4 ?
6876 FIB_API_PATH_NH_PROTO_IP4 :
6877 FIB_API_PATH_NH_PROTO_IP6);
Neale Rannsd792d9c2017-10-21 10:53:20 -07006878
6879 if (next_hop_proto_is_ip4)
6880 {
Neale Ranns097fa662018-05-01 05:17:55 -07006881 clib_memcpy (&mp->br_route.br_paths[0].nh.address.ip4,
Neale Rannsd792d9c2017-10-21 10:53:20 -07006882 &v4_next_hop_address, sizeof (v4_next_hop_address));
6883 }
6884 else
6885 {
Neale Ranns097fa662018-05-01 05:17:55 -07006886 clib_memcpy (&mp->br_route.br_paths[0].nh.address.ip6,
Neale Rannsd792d9c2017-10-21 10:53:20 -07006887 &v6_next_hop_address, sizeof (v6_next_hop_address));
6888 }
6889
6890 /* send it... */
6891 S (mp);
6892
6893 /* Wait for a reply... */
6894 W (ret);
6895
6896 return (ret);
6897}
6898
6899static int
Damjan Marion7cd468a2016-12-19 23:05:39 +01006900api_mpls_tunnel_add_del (vat_main_t * vam)
6901{
6902 unformat_input_t *i = vam->input;
6903 vl_api_mpls_tunnel_add_del_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006904
Neale Ranns097fa662018-05-01 05:17:55 -07006905 vl_api_fib_path_t paths[8];
Damjan Marion7cd468a2016-12-19 23:05:39 +01006906 u32 sw_if_index = ~0;
Neale Ranns097fa662018-05-01 05:17:55 -07006907 u8 path_count = 0;
6908 u8 l2_only = 0;
6909 u8 is_add = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -06006910 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006911
6912 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
6913 {
6914 if (unformat (i, "add"))
6915 is_add = 1;
John Lo06fda9c2018-10-03 16:32:44 -04006916 else
6917 if (unformat
6918 (i, "del %U", api_unformat_sw_if_index, vam, &sw_if_index))
6919 is_add = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006920 else if (unformat (i, "del sw_if_index %d", &sw_if_index))
6921 is_add = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006922 else if (unformat (i, "l2-only"))
6923 l2_only = 1;
Neale Ranns097fa662018-05-01 05:17:55 -07006924 else
6925 if (unformat
6926 (i, "via %U", unformat_fib_path, vam, &paths[path_count]))
John Lo06fda9c2018-10-03 16:32:44 -04006927 {
Neale Ranns097fa662018-05-01 05:17:55 -07006928 path_count++;
6929 if (8 == path_count)
6930 {
6931 errmsg ("max 8 paths");
6932 return -99;
6933 }
John Lo06fda9c2018-10-03 16:32:44 -04006934 }
Damjan Marion7cd468a2016-12-19 23:05:39 +01006935 else
6936 {
6937 clib_warning ("parse error '%U'", format_unformat_error, i);
6938 return -99;
6939 }
6940 }
6941
Neale Ranns097fa662018-05-01 05:17:55 -07006942 M2 (MPLS_TUNNEL_ADD_DEL, mp, sizeof (vl_api_fib_path_t) * path_count);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006943
Damjan Marion7cd468a2016-12-19 23:05:39 +01006944 mp->mt_is_add = is_add;
Neale Ranns097fa662018-05-01 05:17:55 -07006945 mp->mt_tunnel.mt_sw_if_index = ntohl (sw_if_index);
6946 mp->mt_tunnel.mt_l2_only = l2_only;
6947 mp->mt_tunnel.mt_is_multicast = 0;
6948 mp->mt_tunnel.mt_n_paths = path_count;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006949
Neale Ranns097fa662018-05-01 05:17:55 -07006950 clib_memcpy (&mp->mt_tunnel.mt_paths, &paths,
6951 sizeof (paths[0]) * path_count);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006952
Jon Loeliger7bc770c2017-01-31 14:03:33 -06006953 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06006954 W (ret);
6955 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006956}
6957
6958static int
6959api_sw_interface_set_unnumbered (vat_main_t * vam)
6960{
6961 unformat_input_t *i = vam->input;
6962 vl_api_sw_interface_set_unnumbered_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006963 u32 sw_if_index;
6964 u32 unnum_sw_index = ~0;
6965 u8 is_add = 1;
6966 u8 sw_if_index_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06006967 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01006968
6969 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
6970 {
6971 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
6972 sw_if_index_set = 1;
6973 else if (unformat (i, "sw_if_index %d", &sw_if_index))
6974 sw_if_index_set = 1;
6975 else if (unformat (i, "unnum_if_index %d", &unnum_sw_index))
6976 ;
6977 else if (unformat (i, "del"))
6978 is_add = 0;
6979 else
6980 {
6981 clib_warning ("parse error '%U'", format_unformat_error, i);
6982 return -99;
6983 }
6984 }
6985
6986 if (sw_if_index_set == 0)
6987 {
6988 errmsg ("missing interface name or sw_if_index");
6989 return -99;
6990 }
6991
Jon Loeliger8a2aea32017-01-31 13:19:40 -06006992 M (SW_INTERFACE_SET_UNNUMBERED, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01006993
6994 mp->sw_if_index = ntohl (sw_if_index);
6995 mp->unnumbered_sw_if_index = ntohl (unnum_sw_index);
6996 mp->is_add = is_add;
6997
Jon Loeliger7bc770c2017-01-31 14:03:33 -06006998 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06006999 W (ret);
7000 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007001}
7002
Damjan Marion7cd468a2016-12-19 23:05:39 +01007003
7004static int
Damjan Marion7cd468a2016-12-19 23:05:39 +01007005api_create_vlan_subif (vat_main_t * vam)
7006{
7007 unformat_input_t *i = vam->input;
7008 vl_api_create_vlan_subif_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007009 u32 sw_if_index;
7010 u8 sw_if_index_set = 0;
7011 u32 vlan_id;
7012 u8 vlan_id_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06007013 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007014
7015 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
7016 {
7017 if (unformat (i, "sw_if_index %d", &sw_if_index))
7018 sw_if_index_set = 1;
7019 else
7020 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
7021 sw_if_index_set = 1;
7022 else if (unformat (i, "vlan %d", &vlan_id))
7023 vlan_id_set = 1;
7024 else
7025 {
7026 clib_warning ("parse error '%U'", format_unformat_error, i);
7027 return -99;
7028 }
7029 }
7030
7031 if (sw_if_index_set == 0)
7032 {
7033 errmsg ("missing interface name or sw_if_index");
7034 return -99;
7035 }
7036
7037 if (vlan_id_set == 0)
7038 {
7039 errmsg ("missing vlan_id");
7040 return -99;
7041 }
Jon Loeliger8a2aea32017-01-31 13:19:40 -06007042 M (CREATE_VLAN_SUBIF, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01007043
7044 mp->sw_if_index = ntohl (sw_if_index);
7045 mp->vlan_id = ntohl (vlan_id);
7046
Jon Loeliger7bc770c2017-01-31 14:03:33 -06007047 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06007048 W (ret);
7049 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007050}
7051
7052#define foreach_create_subif_bit \
7053_(no_tags) \
7054_(one_tag) \
7055_(two_tags) \
7056_(dot1ad) \
7057_(exact_match) \
7058_(default_sub) \
7059_(outer_vlan_id_any) \
7060_(inner_vlan_id_any)
7061
Jakub Grajciar053204a2019-03-18 13:17:53 +01007062#define foreach_create_subif_flag \
7063_(0, "no_tags") \
7064_(1, "one_tag") \
7065_(2, "two_tags") \
7066_(3, "dot1ad") \
7067_(4, "exact_match") \
7068_(5, "default_sub") \
7069_(6, "outer_vlan_id_any") \
7070_(7, "inner_vlan_id_any")
7071
Damjan Marion7cd468a2016-12-19 23:05:39 +01007072static int
7073api_create_subif (vat_main_t * vam)
7074{
7075 unformat_input_t *i = vam->input;
7076 vl_api_create_subif_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007077 u32 sw_if_index;
7078 u8 sw_if_index_set = 0;
7079 u32 sub_id;
7080 u8 sub_id_set = 0;
Jakub Grajciar053204a2019-03-18 13:17:53 +01007081 u32 __attribute__ ((unused)) no_tags = 0;
7082 u32 __attribute__ ((unused)) one_tag = 0;
7083 u32 __attribute__ ((unused)) two_tags = 0;
7084 u32 __attribute__ ((unused)) dot1ad = 0;
7085 u32 __attribute__ ((unused)) exact_match = 0;
7086 u32 __attribute__ ((unused)) default_sub = 0;
7087 u32 __attribute__ ((unused)) outer_vlan_id_any = 0;
7088 u32 __attribute__ ((unused)) inner_vlan_id_any = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007089 u32 tmp;
7090 u16 outer_vlan_id = 0;
7091 u16 inner_vlan_id = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06007092 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007093
7094 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
7095 {
7096 if (unformat (i, "sw_if_index %d", &sw_if_index))
7097 sw_if_index_set = 1;
7098 else
7099 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
7100 sw_if_index_set = 1;
7101 else if (unformat (i, "sub_id %d", &sub_id))
7102 sub_id_set = 1;
7103 else if (unformat (i, "outer_vlan_id %d", &tmp))
7104 outer_vlan_id = tmp;
7105 else if (unformat (i, "inner_vlan_id %d", &tmp))
7106 inner_vlan_id = tmp;
7107
7108#define _(a) else if (unformat (i, #a)) a = 1 ;
7109 foreach_create_subif_bit
7110#undef _
7111 else
7112 {
7113 clib_warning ("parse error '%U'", format_unformat_error, i);
7114 return -99;
7115 }
7116 }
7117
7118 if (sw_if_index_set == 0)
7119 {
7120 errmsg ("missing interface name or sw_if_index");
7121 return -99;
7122 }
7123
7124 if (sub_id_set == 0)
7125 {
7126 errmsg ("missing sub_id");
7127 return -99;
7128 }
Jon Loeliger8a2aea32017-01-31 13:19:40 -06007129 M (CREATE_SUBIF, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01007130
7131 mp->sw_if_index = ntohl (sw_if_index);
7132 mp->sub_id = ntohl (sub_id);
7133
Jakub Grajciar053204a2019-03-18 13:17:53 +01007134#define _(a,b) mp->sub_if_flags |= (1 << a);
7135 foreach_create_subif_flag;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007136#undef _
7137
7138 mp->outer_vlan_id = ntohs (outer_vlan_id);
7139 mp->inner_vlan_id = ntohs (inner_vlan_id);
7140
Jon Loeliger7bc770c2017-01-31 14:03:33 -06007141 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06007142 W (ret);
7143 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007144}
7145
7146static int
Neale Ranns9db6ada2019-11-08 12:42:31 +00007147api_ip_table_replace_begin (vat_main_t * vam)
Damjan Marion7cd468a2016-12-19 23:05:39 +01007148{
7149 unformat_input_t *i = vam->input;
Neale Ranns9db6ada2019-11-08 12:42:31 +00007150 vl_api_ip_table_replace_begin_t *mp;
7151 u32 table_id = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007152 u8 is_ipv6 = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007153
Jon Loeliger56c7b012017-02-01 12:31:41 -06007154 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007155 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
7156 {
Neale Ranns9db6ada2019-11-08 12:42:31 +00007157 if (unformat (i, "table %d", &table_id))
7158 ;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007159 else if (unformat (i, "ipv6"))
7160 is_ipv6 = 1;
7161 else
7162 {
7163 clib_warning ("parse error '%U'", format_unformat_error, i);
7164 return -99;
7165 }
7166 }
7167
Neale Ranns9db6ada2019-11-08 12:42:31 +00007168 M (IP_TABLE_REPLACE_BEGIN, mp);
7169
7170 mp->table.table_id = ntohl (table_id);
7171 mp->table.is_ip6 = is_ipv6;
7172
7173 S (mp);
7174 W (ret);
7175 return ret;
7176}
7177
7178static int
7179api_ip_table_flush (vat_main_t * vam)
7180{
7181 unformat_input_t *i = vam->input;
7182 vl_api_ip_table_flush_t *mp;
7183 u32 table_id = 0;
7184 u8 is_ipv6 = 0;
7185
7186 int ret;
7187 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
Damjan Marion7cd468a2016-12-19 23:05:39 +01007188 {
Neale Ranns9db6ada2019-11-08 12:42:31 +00007189 if (unformat (i, "table %d", &table_id))
7190 ;
7191 else if (unformat (i, "ipv6"))
7192 is_ipv6 = 1;
7193 else
7194 {
7195 clib_warning ("parse error '%U'", format_unformat_error, i);
7196 return -99;
7197 }
Damjan Marion7cd468a2016-12-19 23:05:39 +01007198 }
7199
Neale Ranns9db6ada2019-11-08 12:42:31 +00007200 M (IP_TABLE_FLUSH, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01007201
Neale Ranns9db6ada2019-11-08 12:42:31 +00007202 mp->table.table_id = ntohl (table_id);
7203 mp->table.is_ip6 = is_ipv6;
7204
7205 S (mp);
7206 W (ret);
7207 return ret;
7208}
7209
7210static int
7211api_ip_table_replace_end (vat_main_t * vam)
7212{
7213 unformat_input_t *i = vam->input;
7214 vl_api_ip_table_replace_end_t *mp;
7215 u32 table_id = 0;
7216 u8 is_ipv6 = 0;
7217
7218 int ret;
7219 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
7220 {
7221 if (unformat (i, "table %d", &table_id))
7222 ;
7223 else if (unformat (i, "ipv6"))
7224 is_ipv6 = 1;
7225 else
7226 {
7227 clib_warning ("parse error '%U'", format_unformat_error, i);
7228 return -99;
7229 }
7230 }
7231
7232 M (IP_TABLE_REPLACE_END, mp);
7233
7234 mp->table.table_id = ntohl (table_id);
7235 mp->table.is_ip6 = is_ipv6;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007236
Jon Loeliger7bc770c2017-01-31 14:03:33 -06007237 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06007238 W (ret);
7239 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007240}
7241
7242static int
Damjan Marion7cd468a2016-12-19 23:05:39 +01007243api_set_ip_flow_hash (vat_main_t * vam)
7244{
7245 unformat_input_t *i = vam->input;
7246 vl_api_set_ip_flow_hash_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007247 u32 vrf_id = 0;
7248 u8 is_ipv6 = 0;
7249 u8 vrf_id_set = 0;
7250 u8 src = 0;
7251 u8 dst = 0;
7252 u8 sport = 0;
7253 u8 dport = 0;
7254 u8 proto = 0;
7255 u8 reverse = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06007256 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007257
7258 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
7259 {
7260 if (unformat (i, "vrf %d", &vrf_id))
7261 vrf_id_set = 1;
7262 else if (unformat (i, "ipv6"))
7263 is_ipv6 = 1;
7264 else if (unformat (i, "src"))
7265 src = 1;
7266 else if (unformat (i, "dst"))
7267 dst = 1;
7268 else if (unformat (i, "sport"))
7269 sport = 1;
7270 else if (unformat (i, "dport"))
7271 dport = 1;
7272 else if (unformat (i, "proto"))
7273 proto = 1;
7274 else if (unformat (i, "reverse"))
7275 reverse = 1;
7276
7277 else
7278 {
7279 clib_warning ("parse error '%U'", format_unformat_error, i);
7280 return -99;
7281 }
7282 }
7283
7284 if (vrf_id_set == 0)
7285 {
7286 errmsg ("missing vrf id");
7287 return -99;
7288 }
7289
Jon Loeliger8a2aea32017-01-31 13:19:40 -06007290 M (SET_IP_FLOW_HASH, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01007291 mp->src = src;
7292 mp->dst = dst;
7293 mp->sport = sport;
7294 mp->dport = dport;
7295 mp->proto = proto;
7296 mp->reverse = reverse;
7297 mp->vrf_id = ntohl (vrf_id);
7298 mp->is_ipv6 = is_ipv6;
7299
Jon Loeliger7bc770c2017-01-31 14:03:33 -06007300 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06007301 W (ret);
7302 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007303}
7304
7305static int
7306api_sw_interface_ip6_enable_disable (vat_main_t * vam)
7307{
7308 unformat_input_t *i = vam->input;
7309 vl_api_sw_interface_ip6_enable_disable_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007310 u32 sw_if_index;
7311 u8 sw_if_index_set = 0;
7312 u8 enable = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06007313 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007314
7315 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
7316 {
7317 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
7318 sw_if_index_set = 1;
7319 else if (unformat (i, "sw_if_index %d", &sw_if_index))
7320 sw_if_index_set = 1;
7321 else if (unformat (i, "enable"))
7322 enable = 1;
7323 else if (unformat (i, "disable"))
7324 enable = 0;
7325 else
7326 {
7327 clib_warning ("parse error '%U'", format_unformat_error, i);
7328 return -99;
7329 }
7330 }
7331
7332 if (sw_if_index_set == 0)
7333 {
7334 errmsg ("missing interface name or sw_if_index");
7335 return -99;
7336 }
7337
Jon Loeliger8a2aea32017-01-31 13:19:40 -06007338 M (SW_INTERFACE_IP6_ENABLE_DISABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01007339
7340 mp->sw_if_index = ntohl (sw_if_index);
7341 mp->enable = enable;
7342
Jon Loeliger7bc770c2017-01-31 14:03:33 -06007343 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06007344 W (ret);
7345 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007346}
7347
Damjan Marion7cd468a2016-12-19 23:05:39 +01007348
7349static int
7350api_l2_patch_add_del (vat_main_t * vam)
7351{
7352 unformat_input_t *i = vam->input;
7353 vl_api_l2_patch_add_del_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007354 u32 rx_sw_if_index;
7355 u8 rx_sw_if_index_set = 0;
7356 u32 tx_sw_if_index;
7357 u8 tx_sw_if_index_set = 0;
7358 u8 is_add = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -06007359 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007360
7361 /* Parse args required to build the message */
7362 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
7363 {
7364 if (unformat (i, "rx_sw_if_index %d", &rx_sw_if_index))
7365 rx_sw_if_index_set = 1;
7366 else if (unformat (i, "tx_sw_if_index %d", &tx_sw_if_index))
7367 tx_sw_if_index_set = 1;
7368 else if (unformat (i, "rx"))
7369 {
7370 if (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
7371 {
7372 if (unformat (i, "%U", api_unformat_sw_if_index, vam,
7373 &rx_sw_if_index))
7374 rx_sw_if_index_set = 1;
7375 }
7376 else
7377 break;
7378 }
7379 else if (unformat (i, "tx"))
7380 {
7381 if (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
7382 {
7383 if (unformat (i, "%U", api_unformat_sw_if_index, vam,
7384 &tx_sw_if_index))
7385 tx_sw_if_index_set = 1;
7386 }
7387 else
7388 break;
7389 }
7390 else if (unformat (i, "del"))
7391 is_add = 0;
7392 else
7393 break;
7394 }
7395
7396 if (rx_sw_if_index_set == 0)
7397 {
7398 errmsg ("missing rx interface name or rx_sw_if_index");
7399 return -99;
7400 }
7401
7402 if (tx_sw_if_index_set == 0)
7403 {
7404 errmsg ("missing tx interface name or tx_sw_if_index");
7405 return -99;
7406 }
7407
Jon Loeliger8a2aea32017-01-31 13:19:40 -06007408 M (L2_PATCH_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01007409
7410 mp->rx_sw_if_index = ntohl (rx_sw_if_index);
7411 mp->tx_sw_if_index = ntohl (tx_sw_if_index);
7412 mp->is_add = is_add;
7413
Jon Loeliger7bc770c2017-01-31 14:03:33 -06007414 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06007415 W (ret);
7416 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007417}
7418
Pablo Camarillofb380952016-12-07 18:34:18 +01007419u8 is_del;
7420u8 localsid_addr[16];
7421u8 end_psp;
7422u8 behavior;
7423u32 sw_if_index;
7424u32 vlan_index;
7425u32 fib_table;
7426u8 nh_addr[16];
7427
7428static int
7429api_sr_localsid_add_del (vat_main_t * vam)
7430{
7431 unformat_input_t *i = vam->input;
7432 vl_api_sr_localsid_add_del_t *mp;
7433
7434 u8 is_del;
7435 ip6_address_t localsid;
7436 u8 end_psp = 0;
7437 u8 behavior = ~0;
7438 u32 sw_if_index;
7439 u32 fib_table = ~(u32) 0;
Jakub Grajciar0938eba2020-03-04 13:08:27 +01007440 ip46_address_t nh_addr;
7441 clib_memset (&nh_addr, 0, sizeof (ip46_address_t));
Pablo Camarillofb380952016-12-07 18:34:18 +01007442
7443 bool nexthop_set = 0;
7444
7445 int ret;
7446
7447 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
7448 {
7449 if (unformat (i, "del"))
7450 is_del = 1;
7451 else if (unformat (i, "address %U", unformat_ip6_address, &localsid));
Jakub Grajciar0938eba2020-03-04 13:08:27 +01007452 else if (unformat (i, "next-hop %U", unformat_ip46_address, &nh_addr))
Pablo Camarillofb380952016-12-07 18:34:18 +01007453 nexthop_set = 1;
7454 else if (unformat (i, "behavior %u", &behavior));
7455 else if (unformat (i, "sw_if_index %u", &sw_if_index));
7456 else if (unformat (i, "fib-table %u", &fib_table));
7457 else if (unformat (i, "end.psp %u", &behavior));
7458 else
7459 break;
7460 }
7461
7462 M (SR_LOCALSID_ADD_DEL, mp);
7463
Jakub Grajciar0938eba2020-03-04 13:08:27 +01007464 clib_memcpy (mp->localsid, &localsid, sizeof (mp->localsid));
Tetsuya Murakami1b81e6e2019-11-06 11:05:51 -08007465
Pablo Camarillofb380952016-12-07 18:34:18 +01007466 if (nexthop_set)
Pablo Camarillo3337bd22018-06-19 15:49:02 +02007467 {
Jakub Grajciar0938eba2020-03-04 13:08:27 +01007468 clib_memcpy (&mp->nh_addr.un, &nh_addr, sizeof (mp->nh_addr.un));
Pablo Camarillo3337bd22018-06-19 15:49:02 +02007469 }
Pablo Camarillofb380952016-12-07 18:34:18 +01007470 mp->behavior = behavior;
7471 mp->sw_if_index = ntohl (sw_if_index);
7472 mp->fib_table = ntohl (fib_table);
7473 mp->end_psp = end_psp;
7474 mp->is_del = is_del;
7475
7476 S (mp);
7477 W (ret);
7478 return ret;
7479}
7480
Damjan Marion7cd468a2016-12-19 23:05:39 +01007481static int
7482api_ioam_enable (vat_main_t * vam)
7483{
7484 unformat_input_t *input = vam->input;
7485 vl_api_ioam_enable_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007486 u32 id = 0;
7487 int has_trace_option = 0;
7488 int has_pot_option = 0;
7489 int has_seqno_option = 0;
7490 int has_analyse_option = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06007491 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007492
7493 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
7494 {
7495 if (unformat (input, "trace"))
7496 has_trace_option = 1;
7497 else if (unformat (input, "pot"))
7498 has_pot_option = 1;
7499 else if (unformat (input, "seqno"))
7500 has_seqno_option = 1;
7501 else if (unformat (input, "analyse"))
7502 has_analyse_option = 1;
7503 else
7504 break;
7505 }
Jon Loeliger8a2aea32017-01-31 13:19:40 -06007506 M (IOAM_ENABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01007507 mp->id = htons (id);
7508 mp->seqno = has_seqno_option;
7509 mp->analyse = has_analyse_option;
7510 mp->pot_enable = has_pot_option;
7511 mp->trace_enable = has_trace_option;
7512
Jon Loeliger7bc770c2017-01-31 14:03:33 -06007513 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06007514 W (ret);
7515 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007516}
7517
7518
7519static int
7520api_ioam_disable (vat_main_t * vam)
7521{
7522 vl_api_ioam_disable_t *mp;
Jon Loeliger56c7b012017-02-01 12:31:41 -06007523 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007524
Jon Loeliger8a2aea32017-01-31 13:19:40 -06007525 M (IOAM_DISABLE, mp);
Jon Loeliger7bc770c2017-01-31 14:03:33 -06007526 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06007527 W (ret);
7528 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01007529}
7530
Damjan Marion7cd468a2016-12-19 23:05:39 +01007531#define foreach_tcp_proto_field \
7532_(src_port) \
7533_(dst_port)
7534
7535#define foreach_udp_proto_field \
7536_(src_port) \
7537_(dst_port)
7538
7539#define foreach_ip4_proto_field \
7540_(src_address) \
7541_(dst_address) \
7542_(tos) \
7543_(length) \
7544_(fragment_id) \
7545_(ttl) \
7546_(protocol) \
7547_(checksum)
7548
Dave Barach4a3f69c2017-02-22 12:44:56 -05007549typedef struct
7550{
7551 u16 src_port, dst_port;
7552} tcpudp_header_t;
7553
7554#if VPP_API_TEST_BUILTIN == 0
Damjan Marion7cd468a2016-12-19 23:05:39 +01007555uword
7556unformat_tcp_mask (unformat_input_t * input, va_list * args)
7557{
7558 u8 **maskp = va_arg (*args, u8 **);
7559 u8 *mask = 0;
7560 u8 found_something = 0;
7561 tcp_header_t *tcp;
7562
7563#define _(a) u8 a=0;
7564 foreach_tcp_proto_field;
7565#undef _
7566
7567 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
7568 {
7569 if (0);
7570#define _(a) else if (unformat (input, #a)) a=1;
7571 foreach_tcp_proto_field
7572#undef _
7573 else
7574 break;
7575 }
7576
7577#define _(a) found_something += a;
7578 foreach_tcp_proto_field;
7579#undef _
7580
7581 if (found_something == 0)
7582 return 0;
7583
7584 vec_validate (mask, sizeof (*tcp) - 1);
7585
7586 tcp = (tcp_header_t *) mask;
7587
Dave Barachb7b92992018-10-17 10:38:51 -04007588#define _(a) if (a) clib_memset (&tcp->a, 0xff, sizeof (tcp->a));
Damjan Marion7cd468a2016-12-19 23:05:39 +01007589 foreach_tcp_proto_field;
7590#undef _
7591
7592 *maskp = mask;
7593 return 1;
7594}
7595
7596uword
7597unformat_udp_mask (unformat_input_t * input, va_list * args)
7598{
7599 u8 **maskp = va_arg (*args, u8 **);
7600 u8 *mask = 0;
7601 u8 found_something = 0;
7602 udp_header_t *udp;
7603
7604#define _(a) u8 a=0;
7605 foreach_udp_proto_field;
7606#undef _
7607
7608 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
7609 {
7610 if (0);
7611#define _(a) else if (unformat (input, #a)) a=1;
7612 foreach_udp_proto_field
7613#undef _
7614 else
7615 break;
7616 }
7617
7618#define _(a) found_something += a;
7619 foreach_udp_proto_field;
7620#undef _
7621
7622 if (found_something == 0)
7623 return 0;
7624
7625 vec_validate (mask, sizeof (*udp) - 1);
7626
7627 udp = (udp_header_t *) mask;
7628
Dave Barachb7b92992018-10-17 10:38:51 -04007629#define _(a) if (a) clib_memset (&udp->a, 0xff, sizeof (udp->a));
Damjan Marion7cd468a2016-12-19 23:05:39 +01007630 foreach_udp_proto_field;
7631#undef _
7632
7633 *maskp = mask;
7634 return 1;
7635}
7636
Damjan Marion7cd468a2016-12-19 23:05:39 +01007637uword
7638unformat_l4_mask (unformat_input_t * input, va_list * args)
7639{
7640 u8 **maskp = va_arg (*args, u8 **);
7641 u16 src_port = 0, dst_port = 0;
7642 tcpudp_header_t *tcpudp;
7643
7644 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
7645 {
7646 if (unformat (input, "tcp %U", unformat_tcp_mask, maskp))
7647 return 1;
7648 else if (unformat (input, "udp %U", unformat_udp_mask, maskp))
7649 return 1;
7650 else if (unformat (input, "src_port"))
7651 src_port = 0xFFFF;
7652 else if (unformat (input, "dst_port"))
7653 dst_port = 0xFFFF;
7654 else
7655 return 0;
7656 }
7657
7658 if (!src_port && !dst_port)
7659 return 0;
7660
7661 u8 *mask = 0;
7662 vec_validate (mask, sizeof (tcpudp_header_t) - 1);
7663
7664 tcpudp = (tcpudp_header_t *) mask;
7665 tcpudp->src_port = src_port;
7666 tcpudp->dst_port = dst_port;
7667
7668 *maskp = mask;
7669
7670 return 1;
7671}
7672
7673uword
7674unformat_ip4_mask (unformat_input_t * input, va_list * args)
7675{
7676 u8 **maskp = va_arg (*args, u8 **);
7677 u8 *mask = 0;
7678 u8 found_something = 0;
7679 ip4_header_t *ip;
7680
7681#define _(a) u8 a=0;
7682 foreach_ip4_proto_field;
7683#undef _
7684 u8 version = 0;
7685 u8 hdr_length = 0;
7686
7687
7688 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
7689 {
7690 if (unformat (input, "version"))
7691 version = 1;
7692 else if (unformat (input, "hdr_length"))
7693 hdr_length = 1;
7694 else if (unformat (input, "src"))
7695 src_address = 1;
7696 else if (unformat (input, "dst"))
7697 dst_address = 1;
7698 else if (unformat (input, "proto"))
7699 protocol = 1;
7700
7701#define _(a) else if (unformat (input, #a)) a=1;
7702 foreach_ip4_proto_field
7703#undef _
7704 else
7705 break;
7706 }
7707
7708#define _(a) found_something += a;
7709 foreach_ip4_proto_field;
7710#undef _
7711
7712 if (found_something == 0)
7713 return 0;
7714
7715 vec_validate (mask, sizeof (*ip) - 1);
7716
7717 ip = (ip4_header_t *) mask;
7718
Dave Barachb7b92992018-10-17 10:38:51 -04007719#define _(a) if (a) clib_memset (&ip->a, 0xff, sizeof (ip->a));
Damjan Marion7cd468a2016-12-19 23:05:39 +01007720 foreach_ip4_proto_field;
7721#undef _
7722
7723 ip->ip_version_and_header_length = 0;
7724
7725 if (version)
7726 ip->ip_version_and_header_length |= 0xF0;
7727
7728 if (hdr_length)
7729 ip->ip_version_and_header_length |= 0x0F;
7730
7731 *maskp = mask;
7732 return 1;
7733}
7734
7735#define foreach_ip6_proto_field \
7736_(src_address) \
7737_(dst_address) \
7738_(payload_length) \
7739_(hop_limit) \
7740_(protocol)
7741
7742uword
7743unformat_ip6_mask (unformat_input_t * input, va_list * args)
7744{
7745 u8 **maskp = va_arg (*args, u8 **);
7746 u8 *mask = 0;
7747 u8 found_something = 0;
7748 ip6_header_t *ip;
7749 u32 ip_version_traffic_class_and_flow_label;
7750
7751#define _(a) u8 a=0;
7752 foreach_ip6_proto_field;
7753#undef _
7754 u8 version = 0;
7755 u8 traffic_class = 0;
7756 u8 flow_label = 0;
7757
7758 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
7759 {
7760 if (unformat (input, "version"))
7761 version = 1;
7762 else if (unformat (input, "traffic-class"))
7763 traffic_class = 1;
7764 else if (unformat (input, "flow-label"))
7765 flow_label = 1;
7766 else if (unformat (input, "src"))
7767 src_address = 1;
7768 else if (unformat (input, "dst"))
7769 dst_address = 1;
7770 else if (unformat (input, "proto"))
7771 protocol = 1;
7772
7773#define _(a) else if (unformat (input, #a)) a=1;
7774 foreach_ip6_proto_field
7775#undef _
7776 else
7777 break;
7778 }
7779
7780#define _(a) found_something += a;
7781 foreach_ip6_proto_field;
7782#undef _
7783
7784 if (found_something == 0)
7785 return 0;
7786
7787 vec_validate (mask, sizeof (*ip) - 1);
7788
7789 ip = (ip6_header_t *) mask;
7790
Dave Barachb7b92992018-10-17 10:38:51 -04007791#define _(a) if (a) clib_memset (&ip->a, 0xff, sizeof (ip->a));
Damjan Marion7cd468a2016-12-19 23:05:39 +01007792 foreach_ip6_proto_field;
7793#undef _
7794
7795 ip_version_traffic_class_and_flow_label = 0;
7796
7797 if (version)
7798 ip_version_traffic_class_and_flow_label |= 0xF0000000;
7799
7800 if (traffic_class)
7801 ip_version_traffic_class_and_flow_label |= 0x0FF00000;
7802
7803 if (flow_label)
7804 ip_version_traffic_class_and_flow_label |= 0x000FFFFF;
7805
7806 ip->ip_version_traffic_class_and_flow_label =
7807 clib_host_to_net_u32 (ip_version_traffic_class_and_flow_label);
7808
7809 *maskp = mask;
7810 return 1;
7811}
7812
7813uword
7814unformat_l3_mask (unformat_input_t * input, va_list * args)
7815{
7816 u8 **maskp = va_arg (*args, u8 **);
7817
7818 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
7819 {
7820 if (unformat (input, "ip4 %U", unformat_ip4_mask, maskp))
7821 return 1;
7822 else if (unformat (input, "ip6 %U", unformat_ip6_mask, maskp))
7823 return 1;
7824 else
7825 break;
7826 }
7827 return 0;
7828}
7829
7830uword
7831unformat_l2_mask (unformat_input_t * input, va_list * args)
7832{
7833 u8 **maskp = va_arg (*args, u8 **);
7834 u8 *mask = 0;
7835 u8 src = 0;
7836 u8 dst = 0;
7837 u8 proto = 0;
7838 u8 tag1 = 0;
7839 u8 tag2 = 0;
7840 u8 ignore_tag1 = 0;
7841 u8 ignore_tag2 = 0;
7842 u8 cos1 = 0;
7843 u8 cos2 = 0;
7844 u8 dot1q = 0;
7845 u8 dot1ad = 0;
7846 int len = 14;
7847
7848 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
7849 {
7850 if (unformat (input, "src"))
7851 src = 1;
7852 else if (unformat (input, "dst"))
7853 dst = 1;
7854 else if (unformat (input, "proto"))
7855 proto = 1;
7856 else if (unformat (input, "tag1"))
7857 tag1 = 1;
7858 else if (unformat (input, "tag2"))
7859 tag2 = 1;
7860 else if (unformat (input, "ignore-tag1"))
7861 ignore_tag1 = 1;
7862 else if (unformat (input, "ignore-tag2"))
7863 ignore_tag2 = 1;
7864 else if (unformat (input, "cos1"))
7865 cos1 = 1;
7866 else if (unformat (input, "cos2"))
7867 cos2 = 1;
7868 else if (unformat (input, "dot1q"))
7869 dot1q = 1;
7870 else if (unformat (input, "dot1ad"))
7871 dot1ad = 1;
7872 else
7873 break;
7874 }
7875 if ((src + dst + proto + tag1 + tag2 + dot1q + dot1ad +
7876 ignore_tag1 + ignore_tag2 + cos1 + cos2) == 0)
7877 return 0;
7878
7879 if (tag1 || ignore_tag1 || cos1 || dot1q)
7880 len = 18;
7881 if (tag2 || ignore_tag2 || cos2 || dot1ad)
7882 len = 22;
7883
7884 vec_validate (mask, len - 1);
7885
7886 if (dst)
Dave Barachb7b92992018-10-17 10:38:51 -04007887 clib_memset (mask, 0xff, 6);
Damjan Marion7cd468a2016-12-19 23:05:39 +01007888
7889 if (src)
Dave Barachb7b92992018-10-17 10:38:51 -04007890 clib_memset (mask + 6, 0xff, 6);
Damjan Marion7cd468a2016-12-19 23:05:39 +01007891
7892 if (tag2 || dot1ad)
7893 {
7894 /* inner vlan tag */
7895 if (tag2)
7896 {
7897 mask[19] = 0xff;
7898 mask[18] = 0x0f;
7899 }
7900 if (cos2)
7901 mask[18] |= 0xe0;
7902 if (proto)
7903 mask[21] = mask[20] = 0xff;
7904 if (tag1)
7905 {
7906 mask[15] = 0xff;
7907 mask[14] = 0x0f;
7908 }
7909 if (cos1)
7910 mask[14] |= 0xe0;
7911 *maskp = mask;
7912 return 1;
7913 }
7914 if (tag1 | dot1q)
7915 {
7916 if (tag1)
7917 {
7918 mask[15] = 0xff;
7919 mask[14] = 0x0f;
7920 }
7921 if (cos1)
7922 mask[14] |= 0xe0;
7923 if (proto)
7924 mask[16] = mask[17] = 0xff;
7925
7926 *maskp = mask;
7927 return 1;
7928 }
7929 if (cos2)
7930 mask[18] |= 0xe0;
7931 if (cos1)
7932 mask[14] |= 0xe0;
7933 if (proto)
7934 mask[12] = mask[13] = 0xff;
7935
7936 *maskp = mask;
7937 return 1;
7938}
7939
7940uword
7941unformat_classify_mask (unformat_input_t * input, va_list * args)
7942{
7943 u8 **maskp = va_arg (*args, u8 **);
7944 u32 *skipp = va_arg (*args, u32 *);
7945 u32 *matchp = va_arg (*args, u32 *);
7946 u32 match;
7947 u8 *mask = 0;
7948 u8 *l2 = 0;
7949 u8 *l3 = 0;
7950 u8 *l4 = 0;
7951 int i;
7952
7953 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
7954 {
7955 if (unformat (input, "hex %U", unformat_hex_string, &mask))
7956 ;
7957 else if (unformat (input, "l2 %U", unformat_l2_mask, &l2))
7958 ;
7959 else if (unformat (input, "l3 %U", unformat_l3_mask, &l3))
7960 ;
7961 else if (unformat (input, "l4 %U", unformat_l4_mask, &l4))
7962 ;
7963 else
7964 break;
7965 }
7966
7967 if (l4 && !l3)
7968 {
7969 vec_free (mask);
7970 vec_free (l2);
7971 vec_free (l4);
7972 return 0;
7973 }
7974
7975 if (mask || l2 || l3 || l4)
7976 {
7977 if (l2 || l3 || l4)
7978 {
7979 /* "With a free Ethernet header in every package" */
7980 if (l2 == 0)
7981 vec_validate (l2, 13);
7982 mask = l2;
7983 if (vec_len (l3))
7984 {
7985 vec_append (mask, l3);
7986 vec_free (l3);
7987 }
7988 if (vec_len (l4))
7989 {
7990 vec_append (mask, l4);
7991 vec_free (l4);
7992 }
7993 }
7994
7995 /* Scan forward looking for the first significant mask octet */
7996 for (i = 0; i < vec_len (mask); i++)
7997 if (mask[i])
7998 break;
7999
8000 /* compute (skip, match) params */
8001 *skipp = i / sizeof (u32x4);
8002 vec_delete (mask, *skipp * sizeof (u32x4), 0);
8003
8004 /* Pad mask to an even multiple of the vector size */
8005 while (vec_len (mask) % sizeof (u32x4))
8006 vec_add1 (mask, 0);
8007
8008 match = vec_len (mask) / sizeof (u32x4);
8009
8010 for (i = match * sizeof (u32x4); i > 0; i -= sizeof (u32x4))
8011 {
8012 u64 *tmp = (u64 *) (mask + (i - sizeof (u32x4)));
8013 if (*tmp || *(tmp + 1))
8014 break;
8015 match--;
8016 }
8017 if (match == 0)
8018 clib_warning ("BUG: match 0");
8019
8020 _vec_len (mask) = match * sizeof (u32x4);
8021
8022 *matchp = match;
8023 *maskp = mask;
8024
8025 return 1;
8026 }
8027
8028 return 0;
8029}
Dave Barach4a3f69c2017-02-22 12:44:56 -05008030#endif /* VPP_API_TEST_BUILTIN */
Damjan Marion7cd468a2016-12-19 23:05:39 +01008031
8032#define foreach_l2_next \
8033_(drop, DROP) \
8034_(ethernet, ETHERNET_INPUT) \
8035_(ip4, IP4_INPUT) \
8036_(ip6, IP6_INPUT)
8037
8038uword
8039unformat_l2_next_index (unformat_input_t * input, va_list * args)
8040{
8041 u32 *miss_next_indexp = va_arg (*args, u32 *);
8042 u32 next_index = 0;
8043 u32 tmp;
8044
8045#define _(n,N) \
8046 if (unformat (input, #n)) { next_index = L2_INPUT_CLASSIFY_NEXT_##N; goto out;}
8047 foreach_l2_next;
8048#undef _
8049
8050 if (unformat (input, "%d", &tmp))
8051 {
8052 next_index = tmp;
8053 goto out;
8054 }
8055
8056 return 0;
8057
8058out:
8059 *miss_next_indexp = next_index;
8060 return 1;
8061}
8062
8063#define foreach_ip_next \
8064_(drop, DROP) \
8065_(local, LOCAL) \
8066_(rewrite, REWRITE)
8067
8068uword
Dave Barach4a3f69c2017-02-22 12:44:56 -05008069api_unformat_ip_next_index (unformat_input_t * input, va_list * args)
Damjan Marion7cd468a2016-12-19 23:05:39 +01008070{
8071 u32 *miss_next_indexp = va_arg (*args, u32 *);
8072 u32 next_index = 0;
8073 u32 tmp;
8074
8075#define _(n,N) \
8076 if (unformat (input, #n)) { next_index = IP_LOOKUP_NEXT_##N; goto out;}
8077 foreach_ip_next;
8078#undef _
8079
8080 if (unformat (input, "%d", &tmp))
8081 {
8082 next_index = tmp;
8083 goto out;
8084 }
8085
8086 return 0;
8087
8088out:
8089 *miss_next_indexp = next_index;
8090 return 1;
8091}
8092
8093#define foreach_acl_next \
8094_(deny, DENY)
8095
8096uword
Dave Barach4a3f69c2017-02-22 12:44:56 -05008097api_unformat_acl_next_index (unformat_input_t * input, va_list * args)
Damjan Marion7cd468a2016-12-19 23:05:39 +01008098{
8099 u32 *miss_next_indexp = va_arg (*args, u32 *);
8100 u32 next_index = 0;
8101 u32 tmp;
8102
8103#define _(n,N) \
8104 if (unformat (input, #n)) { next_index = ACL_NEXT_INDEX_##N; goto out;}
8105 foreach_acl_next;
8106#undef _
8107
8108 if (unformat (input, "permit"))
8109 {
8110 next_index = ~0;
8111 goto out;
8112 }
8113 else if (unformat (input, "%d", &tmp))
8114 {
8115 next_index = tmp;
8116 goto out;
8117 }
8118
8119 return 0;
8120
8121out:
8122 *miss_next_indexp = next_index;
8123 return 1;
8124}
8125
8126uword
8127unformat_policer_precolor (unformat_input_t * input, va_list * args)
8128{
8129 u32 *r = va_arg (*args, u32 *);
8130
8131 if (unformat (input, "conform-color"))
8132 *r = POLICE_CONFORM;
8133 else if (unformat (input, "exceed-color"))
8134 *r = POLICE_EXCEED;
8135 else
8136 return 0;
8137
8138 return 1;
8139}
8140
8141static int
8142api_classify_add_del_table (vat_main_t * vam)
8143{
8144 unformat_input_t *i = vam->input;
8145 vl_api_classify_add_del_table_t *mp;
8146
8147 u32 nbuckets = 2;
8148 u32 skip = ~0;
8149 u32 match = ~0;
8150 int is_add = 1;
8151 int del_chain = 0;
8152 u32 table_index = ~0;
8153 u32 next_table_index = ~0;
8154 u32 miss_next_index = ~0;
8155 u32 memory_size = 32 << 20;
8156 u8 *mask = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008157 u32 current_data_flag = 0;
8158 int current_data_offset = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06008159 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008160
8161 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
8162 {
8163 if (unformat (i, "del"))
8164 is_add = 0;
8165 else if (unformat (i, "del-chain"))
8166 {
8167 is_add = 0;
8168 del_chain = 1;
8169 }
8170 else if (unformat (i, "buckets %d", &nbuckets))
8171 ;
8172 else if (unformat (i, "memory_size %d", &memory_size))
8173 ;
8174 else if (unformat (i, "skip %d", &skip))
8175 ;
8176 else if (unformat (i, "match %d", &match))
8177 ;
8178 else if (unformat (i, "table %d", &table_index))
8179 ;
8180 else if (unformat (i, "mask %U", unformat_classify_mask,
8181 &mask, &skip, &match))
8182 ;
8183 else if (unformat (i, "next-table %d", &next_table_index))
8184 ;
Dave Barach4a3f69c2017-02-22 12:44:56 -05008185 else if (unformat (i, "miss-next %U", api_unformat_ip_next_index,
Damjan Marion7cd468a2016-12-19 23:05:39 +01008186 &miss_next_index))
8187 ;
8188 else if (unformat (i, "l2-miss-next %U", unformat_l2_next_index,
8189 &miss_next_index))
8190 ;
Dave Barach4a3f69c2017-02-22 12:44:56 -05008191 else if (unformat (i, "acl-miss-next %U", api_unformat_acl_next_index,
Damjan Marion7cd468a2016-12-19 23:05:39 +01008192 &miss_next_index))
8193 ;
8194 else if (unformat (i, "current-data-flag %d", &current_data_flag))
8195 ;
8196 else if (unformat (i, "current-data-offset %d", &current_data_offset))
8197 ;
8198 else
8199 break;
8200 }
8201
8202 if (is_add && mask == 0)
8203 {
8204 errmsg ("Mask required");
8205 return -99;
8206 }
8207
8208 if (is_add && skip == ~0)
8209 {
8210 errmsg ("skip count required");
8211 return -99;
8212 }
8213
8214 if (is_add && match == ~0)
8215 {
8216 errmsg ("match count required");
8217 return -99;
8218 }
8219
8220 if (!is_add && table_index == ~0)
8221 {
8222 errmsg ("table index required for delete");
8223 return -99;
8224 }
8225
Jon Loeliger8a2aea32017-01-31 13:19:40 -06008226 M2 (CLASSIFY_ADD_DEL_TABLE, mp, vec_len (mask));
Damjan Marion7cd468a2016-12-19 23:05:39 +01008227
8228 mp->is_add = is_add;
8229 mp->del_chain = del_chain;
8230 mp->table_index = ntohl (table_index);
8231 mp->nbuckets = ntohl (nbuckets);
8232 mp->memory_size = ntohl (memory_size);
8233 mp->skip_n_vectors = ntohl (skip);
8234 mp->match_n_vectors = ntohl (match);
8235 mp->next_table_index = ntohl (next_table_index);
8236 mp->miss_next_index = ntohl (miss_next_index);
8237 mp->current_data_flag = ntohl (current_data_flag);
8238 mp->current_data_offset = ntohl (current_data_offset);
Juraj Sloboda75282452018-06-12 14:20:49 +02008239 mp->mask_len = ntohl (vec_len (mask));
Damjan Marion7cd468a2016-12-19 23:05:39 +01008240 clib_memcpy (mp->mask, mask, vec_len (mask));
8241
8242 vec_free (mask);
8243
Jon Loeliger7bc770c2017-01-31 14:03:33 -06008244 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06008245 W (ret);
8246 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008247}
8248
Dave Barach4a3f69c2017-02-22 12:44:56 -05008249#if VPP_API_TEST_BUILTIN == 0
Damjan Marion7cd468a2016-12-19 23:05:39 +01008250uword
8251unformat_l4_match (unformat_input_t * input, va_list * args)
8252{
8253 u8 **matchp = va_arg (*args, u8 **);
8254
8255 u8 *proto_header = 0;
8256 int src_port = 0;
8257 int dst_port = 0;
8258
8259 tcpudp_header_t h;
8260
8261 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
8262 {
8263 if (unformat (input, "src_port %d", &src_port))
8264 ;
8265 else if (unformat (input, "dst_port %d", &dst_port))
8266 ;
8267 else
8268 return 0;
8269 }
8270
8271 h.src_port = clib_host_to_net_u16 (src_port);
8272 h.dst_port = clib_host_to_net_u16 (dst_port);
8273 vec_validate (proto_header, sizeof (h) - 1);
8274 memcpy (proto_header, &h, sizeof (h));
8275
8276 *matchp = proto_header;
8277
8278 return 1;
8279}
8280
8281uword
8282unformat_ip4_match (unformat_input_t * input, va_list * args)
8283{
8284 u8 **matchp = va_arg (*args, u8 **);
8285 u8 *match = 0;
8286 ip4_header_t *ip;
8287 int version = 0;
8288 u32 version_val;
8289 int hdr_length = 0;
8290 u32 hdr_length_val;
8291 int src = 0, dst = 0;
8292 ip4_address_t src_val, dst_val;
8293 int proto = 0;
8294 u32 proto_val;
8295 int tos = 0;
8296 u32 tos_val;
8297 int length = 0;
8298 u32 length_val;
8299 int fragment_id = 0;
8300 u32 fragment_id_val;
8301 int ttl = 0;
8302 int ttl_val;
8303 int checksum = 0;
8304 u32 checksum_val;
8305
8306 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
8307 {
8308 if (unformat (input, "version %d", &version_val))
8309 version = 1;
8310 else if (unformat (input, "hdr_length %d", &hdr_length_val))
8311 hdr_length = 1;
8312 else if (unformat (input, "src %U", unformat_ip4_address, &src_val))
8313 src = 1;
8314 else if (unformat (input, "dst %U", unformat_ip4_address, &dst_val))
8315 dst = 1;
8316 else if (unformat (input, "proto %d", &proto_val))
8317 proto = 1;
8318 else if (unformat (input, "tos %d", &tos_val))
8319 tos = 1;
8320 else if (unformat (input, "length %d", &length_val))
8321 length = 1;
8322 else if (unformat (input, "fragment_id %d", &fragment_id_val))
8323 fragment_id = 1;
8324 else if (unformat (input, "ttl %d", &ttl_val))
8325 ttl = 1;
8326 else if (unformat (input, "checksum %d", &checksum_val))
8327 checksum = 1;
8328 else
8329 break;
8330 }
8331
8332 if (version + hdr_length + src + dst + proto + tos + length + fragment_id
8333 + ttl + checksum == 0)
8334 return 0;
8335
8336 /*
8337 * Aligned because we use the real comparison functions
8338 */
8339 vec_validate_aligned (match, sizeof (*ip) - 1, sizeof (u32x4));
8340
8341 ip = (ip4_header_t *) match;
8342
8343 /* These are realistically matched in practice */
8344 if (src)
8345 ip->src_address.as_u32 = src_val.as_u32;
8346
8347 if (dst)
8348 ip->dst_address.as_u32 = dst_val.as_u32;
8349
8350 if (proto)
8351 ip->protocol = proto_val;
8352
8353
8354 /* These are not, but they're included for completeness */
8355 if (version)
8356 ip->ip_version_and_header_length |= (version_val & 0xF) << 4;
8357
8358 if (hdr_length)
8359 ip->ip_version_and_header_length |= (hdr_length_val & 0xF);
8360
8361 if (tos)
8362 ip->tos = tos_val;
8363
8364 if (length)
8365 ip->length = clib_host_to_net_u16 (length_val);
8366
8367 if (ttl)
8368 ip->ttl = ttl_val;
8369
8370 if (checksum)
8371 ip->checksum = clib_host_to_net_u16 (checksum_val);
8372
8373 *matchp = match;
8374 return 1;
8375}
8376
8377uword
8378unformat_ip6_match (unformat_input_t * input, va_list * args)
8379{
8380 u8 **matchp = va_arg (*args, u8 **);
8381 u8 *match = 0;
8382 ip6_header_t *ip;
8383 int version = 0;
8384 u32 version_val;
8385 u8 traffic_class = 0;
8386 u32 traffic_class_val = 0;
8387 u8 flow_label = 0;
8388 u8 flow_label_val;
8389 int src = 0, dst = 0;
8390 ip6_address_t src_val, dst_val;
8391 int proto = 0;
8392 u32 proto_val;
8393 int payload_length = 0;
8394 u32 payload_length_val;
8395 int hop_limit = 0;
8396 int hop_limit_val;
8397 u32 ip_version_traffic_class_and_flow_label;
8398
8399 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
8400 {
8401 if (unformat (input, "version %d", &version_val))
8402 version = 1;
8403 else if (unformat (input, "traffic_class %d", &traffic_class_val))
8404 traffic_class = 1;
8405 else if (unformat (input, "flow_label %d", &flow_label_val))
8406 flow_label = 1;
8407 else if (unformat (input, "src %U", unformat_ip6_address, &src_val))
8408 src = 1;
8409 else if (unformat (input, "dst %U", unformat_ip6_address, &dst_val))
8410 dst = 1;
8411 else if (unformat (input, "proto %d", &proto_val))
8412 proto = 1;
8413 else if (unformat (input, "payload_length %d", &payload_length_val))
8414 payload_length = 1;
8415 else if (unformat (input, "hop_limit %d", &hop_limit_val))
8416 hop_limit = 1;
8417 else
8418 break;
8419 }
8420
8421 if (version + traffic_class + flow_label + src + dst + proto +
8422 payload_length + hop_limit == 0)
8423 return 0;
8424
8425 /*
8426 * Aligned because we use the real comparison functions
8427 */
8428 vec_validate_aligned (match, sizeof (*ip) - 1, sizeof (u32x4));
8429
8430 ip = (ip6_header_t *) match;
8431
8432 if (src)
8433 clib_memcpy (&ip->src_address, &src_val, sizeof (ip->src_address));
8434
8435 if (dst)
8436 clib_memcpy (&ip->dst_address, &dst_val, sizeof (ip->dst_address));
8437
8438 if (proto)
8439 ip->protocol = proto_val;
8440
8441 ip_version_traffic_class_and_flow_label = 0;
8442
8443 if (version)
8444 ip_version_traffic_class_and_flow_label |= (version_val & 0xF) << 28;
8445
8446 if (traffic_class)
8447 ip_version_traffic_class_and_flow_label |=
8448 (traffic_class_val & 0xFF) << 20;
8449
8450 if (flow_label)
8451 ip_version_traffic_class_and_flow_label |= (flow_label_val & 0xFFFFF);
8452
8453 ip->ip_version_traffic_class_and_flow_label =
8454 clib_host_to_net_u32 (ip_version_traffic_class_and_flow_label);
8455
8456 if (payload_length)
8457 ip->payload_length = clib_host_to_net_u16 (payload_length_val);
8458
8459 if (hop_limit)
8460 ip->hop_limit = hop_limit_val;
8461
8462 *matchp = match;
8463 return 1;
8464}
8465
8466uword
8467unformat_l3_match (unformat_input_t * input, va_list * args)
8468{
8469 u8 **matchp = va_arg (*args, u8 **);
8470
8471 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
8472 {
8473 if (unformat (input, "ip4 %U", unformat_ip4_match, matchp))
8474 return 1;
8475 else if (unformat (input, "ip6 %U", unformat_ip6_match, matchp))
8476 return 1;
8477 else
8478 break;
8479 }
8480 return 0;
8481}
8482
8483uword
8484unformat_vlan_tag (unformat_input_t * input, va_list * args)
8485{
8486 u8 *tagp = va_arg (*args, u8 *);
8487 u32 tag;
8488
8489 if (unformat (input, "%d", &tag))
8490 {
8491 tagp[0] = (tag >> 8) & 0x0F;
8492 tagp[1] = tag & 0xFF;
8493 return 1;
8494 }
8495
8496 return 0;
8497}
8498
8499uword
8500unformat_l2_match (unformat_input_t * input, va_list * args)
8501{
8502 u8 **matchp = va_arg (*args, u8 **);
8503 u8 *match = 0;
8504 u8 src = 0;
8505 u8 src_val[6];
8506 u8 dst = 0;
8507 u8 dst_val[6];
8508 u8 proto = 0;
8509 u16 proto_val;
8510 u8 tag1 = 0;
8511 u8 tag1_val[2];
8512 u8 tag2 = 0;
8513 u8 tag2_val[2];
8514 int len = 14;
8515 u8 ignore_tag1 = 0;
8516 u8 ignore_tag2 = 0;
8517 u8 cos1 = 0;
8518 u8 cos2 = 0;
8519 u32 cos1_val = 0;
8520 u32 cos2_val = 0;
8521
8522 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
8523 {
8524 if (unformat (input, "src %U", unformat_ethernet_address, &src_val))
8525 src = 1;
8526 else
8527 if (unformat (input, "dst %U", unformat_ethernet_address, &dst_val))
8528 dst = 1;
8529 else if (unformat (input, "proto %U",
8530 unformat_ethernet_type_host_byte_order, &proto_val))
8531 proto = 1;
8532 else if (unformat (input, "tag1 %U", unformat_vlan_tag, tag1_val))
8533 tag1 = 1;
8534 else if (unformat (input, "tag2 %U", unformat_vlan_tag, tag2_val))
8535 tag2 = 1;
8536 else if (unformat (input, "ignore-tag1"))
8537 ignore_tag1 = 1;
8538 else if (unformat (input, "ignore-tag2"))
8539 ignore_tag2 = 1;
8540 else if (unformat (input, "cos1 %d", &cos1_val))
8541 cos1 = 1;
8542 else if (unformat (input, "cos2 %d", &cos2_val))
8543 cos2 = 1;
8544 else
8545 break;
8546 }
8547 if ((src + dst + proto + tag1 + tag2 +
8548 ignore_tag1 + ignore_tag2 + cos1 + cos2) == 0)
8549 return 0;
8550
8551 if (tag1 || ignore_tag1 || cos1)
8552 len = 18;
8553 if (tag2 || ignore_tag2 || cos2)
8554 len = 22;
8555
8556 vec_validate_aligned (match, len - 1, sizeof (u32x4));
8557
8558 if (dst)
8559 clib_memcpy (match, dst_val, 6);
8560
8561 if (src)
8562 clib_memcpy (match + 6, src_val, 6);
8563
8564 if (tag2)
8565 {
8566 /* inner vlan tag */
8567 match[19] = tag2_val[1];
8568 match[18] = tag2_val[0];
8569 if (cos2)
8570 match[18] |= (cos2_val & 0x7) << 5;
8571 if (proto)
8572 {
8573 match[21] = proto_val & 0xff;
8574 match[20] = proto_val >> 8;
8575 }
8576 if (tag1)
8577 {
8578 match[15] = tag1_val[1];
8579 match[14] = tag1_val[0];
8580 }
8581 if (cos1)
8582 match[14] |= (cos1_val & 0x7) << 5;
8583 *matchp = match;
8584 return 1;
8585 }
8586 if (tag1)
8587 {
8588 match[15] = tag1_val[1];
8589 match[14] = tag1_val[0];
8590 if (proto)
8591 {
8592 match[17] = proto_val & 0xff;
8593 match[16] = proto_val >> 8;
8594 }
8595 if (cos1)
8596 match[14] |= (cos1_val & 0x7) << 5;
8597
8598 *matchp = match;
8599 return 1;
8600 }
8601 if (cos2)
8602 match[18] |= (cos2_val & 0x7) << 5;
8603 if (cos1)
8604 match[14] |= (cos1_val & 0x7) << 5;
8605 if (proto)
8606 {
8607 match[13] = proto_val & 0xff;
8608 match[12] = proto_val >> 8;
8609 }
8610
8611 *matchp = match;
8612 return 1;
8613}
Igor Mikhailov (imichail)582caa32018-04-26 21:33:02 -07008614
8615uword
8616unformat_qos_source (unformat_input_t * input, va_list * args)
8617{
8618 int *qs = va_arg (*args, int *);
8619
8620 if (unformat (input, "ip"))
8621 *qs = QOS_SOURCE_IP;
8622 else if (unformat (input, "mpls"))
8623 *qs = QOS_SOURCE_MPLS;
8624 else if (unformat (input, "ext"))
8625 *qs = QOS_SOURCE_EXT;
8626 else if (unformat (input, "vlan"))
8627 *qs = QOS_SOURCE_VLAN;
8628 else
8629 return 0;
8630
8631 return 1;
8632}
Dave Barach4a3f69c2017-02-22 12:44:56 -05008633#endif
Damjan Marion7cd468a2016-12-19 23:05:39 +01008634
8635uword
Dave Barach4a3f69c2017-02-22 12:44:56 -05008636api_unformat_classify_match (unformat_input_t * input, va_list * args)
Damjan Marion7cd468a2016-12-19 23:05:39 +01008637{
8638 u8 **matchp = va_arg (*args, u8 **);
8639 u32 skip_n_vectors = va_arg (*args, u32);
8640 u32 match_n_vectors = va_arg (*args, u32);
8641
8642 u8 *match = 0;
8643 u8 *l2 = 0;
8644 u8 *l3 = 0;
8645 u8 *l4 = 0;
8646
8647 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
8648 {
8649 if (unformat (input, "hex %U", unformat_hex_string, &match))
8650 ;
8651 else if (unformat (input, "l2 %U", unformat_l2_match, &l2))
8652 ;
8653 else if (unformat (input, "l3 %U", unformat_l3_match, &l3))
8654 ;
8655 else if (unformat (input, "l4 %U", unformat_l4_match, &l4))
8656 ;
8657 else
8658 break;
8659 }
8660
8661 if (l4 && !l3)
8662 {
8663 vec_free (match);
8664 vec_free (l2);
8665 vec_free (l4);
8666 return 0;
8667 }
8668
8669 if (match || l2 || l3 || l4)
8670 {
8671 if (l2 || l3 || l4)
8672 {
8673 /* "Win a free Ethernet header in every packet" */
8674 if (l2 == 0)
8675 vec_validate_aligned (l2, 13, sizeof (u32x4));
8676 match = l2;
8677 if (vec_len (l3))
8678 {
8679 vec_append_aligned (match, l3, sizeof (u32x4));
8680 vec_free (l3);
8681 }
8682 if (vec_len (l4))
8683 {
8684 vec_append_aligned (match, l4, sizeof (u32x4));
8685 vec_free (l4);
8686 }
8687 }
8688
8689 /* Make sure the vector is big enough even if key is all 0's */
8690 vec_validate_aligned
8691 (match, ((match_n_vectors + skip_n_vectors) * sizeof (u32x4)) - 1,
8692 sizeof (u32x4));
8693
8694 /* Set size, include skipped vectors */
8695 _vec_len (match) = (match_n_vectors + skip_n_vectors) * sizeof (u32x4);
8696
8697 *matchp = match;
8698
8699 return 1;
8700 }
8701
8702 return 0;
8703}
8704
8705static int
8706api_classify_add_del_session (vat_main_t * vam)
8707{
8708 unformat_input_t *i = vam->input;
8709 vl_api_classify_add_del_session_t *mp;
8710 int is_add = 1;
8711 u32 table_index = ~0;
8712 u32 hit_next_index = ~0;
8713 u32 opaque_index = ~0;
8714 u8 *match = 0;
8715 i32 advance = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008716 u32 skip_n_vectors = 0;
8717 u32 match_n_vectors = 0;
8718 u32 action = 0;
8719 u32 metadata = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06008720 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008721
8722 /*
8723 * Warning: you have to supply skip_n and match_n
8724 * because the API client cant simply look at the classify
8725 * table object.
8726 */
8727
8728 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
8729 {
8730 if (unformat (i, "del"))
8731 is_add = 0;
Dave Barach4a3f69c2017-02-22 12:44:56 -05008732 else if (unformat (i, "hit-next %U", api_unformat_ip_next_index,
Damjan Marion7cd468a2016-12-19 23:05:39 +01008733 &hit_next_index))
8734 ;
8735 else if (unformat (i, "l2-hit-next %U", unformat_l2_next_index,
8736 &hit_next_index))
8737 ;
Dave Barach4a3f69c2017-02-22 12:44:56 -05008738 else if (unformat (i, "acl-hit-next %U", api_unformat_acl_next_index,
Damjan Marion7cd468a2016-12-19 23:05:39 +01008739 &hit_next_index))
8740 ;
8741 else if (unformat (i, "policer-hit-next %d", &hit_next_index))
8742 ;
8743 else if (unformat (i, "%U", unformat_policer_precolor, &opaque_index))
8744 ;
8745 else if (unformat (i, "opaque-index %d", &opaque_index))
8746 ;
8747 else if (unformat (i, "skip_n %d", &skip_n_vectors))
8748 ;
8749 else if (unformat (i, "match_n %d", &match_n_vectors))
8750 ;
Dave Barach4a3f69c2017-02-22 12:44:56 -05008751 else if (unformat (i, "match %U", api_unformat_classify_match,
Damjan Marion7cd468a2016-12-19 23:05:39 +01008752 &match, skip_n_vectors, match_n_vectors))
8753 ;
8754 else if (unformat (i, "advance %d", &advance))
8755 ;
8756 else if (unformat (i, "table-index %d", &table_index))
8757 ;
8758 else if (unformat (i, "action set-ip4-fib-id %d", &metadata))
8759 action = 1;
8760 else if (unformat (i, "action set-ip6-fib-id %d", &metadata))
8761 action = 2;
8762 else if (unformat (i, "action %d", &action))
8763 ;
8764 else if (unformat (i, "metadata %d", &metadata))
8765 ;
8766 else
8767 break;
8768 }
8769
8770 if (table_index == ~0)
8771 {
8772 errmsg ("Table index required");
8773 return -99;
8774 }
8775
8776 if (is_add && match == 0)
8777 {
8778 errmsg ("Match value required");
8779 return -99;
8780 }
8781
Jon Loeliger8a2aea32017-01-31 13:19:40 -06008782 M2 (CLASSIFY_ADD_DEL_SESSION, mp, vec_len (match));
Damjan Marion7cd468a2016-12-19 23:05:39 +01008783
8784 mp->is_add = is_add;
8785 mp->table_index = ntohl (table_index);
8786 mp->hit_next_index = ntohl (hit_next_index);
8787 mp->opaque_index = ntohl (opaque_index);
8788 mp->advance = ntohl (advance);
8789 mp->action = action;
8790 mp->metadata = ntohl (metadata);
Juraj Sloboda75282452018-06-12 14:20:49 +02008791 mp->match_len = ntohl (vec_len (match));
Damjan Marion7cd468a2016-12-19 23:05:39 +01008792 clib_memcpy (mp->match, match, vec_len (match));
8793 vec_free (match);
8794
Jon Loeliger7bc770c2017-01-31 14:03:33 -06008795 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06008796 W (ret);
8797 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008798}
8799
8800static int
8801api_classify_set_interface_ip_table (vat_main_t * vam)
8802{
8803 unformat_input_t *i = vam->input;
8804 vl_api_classify_set_interface_ip_table_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008805 u32 sw_if_index;
8806 int sw_if_index_set;
8807 u32 table_index = ~0;
8808 u8 is_ipv6 = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06008809 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008810
8811 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
8812 {
8813 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
8814 sw_if_index_set = 1;
8815 else if (unformat (i, "sw_if_index %d", &sw_if_index))
8816 sw_if_index_set = 1;
8817 else if (unformat (i, "table %d", &table_index))
8818 ;
8819 else
8820 {
8821 clib_warning ("parse error '%U'", format_unformat_error, i);
8822 return -99;
8823 }
8824 }
8825
8826 if (sw_if_index_set == 0)
8827 {
8828 errmsg ("missing interface name or sw_if_index");
8829 return -99;
8830 }
8831
8832
Jon Loeliger8a2aea32017-01-31 13:19:40 -06008833 M (CLASSIFY_SET_INTERFACE_IP_TABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01008834
8835 mp->sw_if_index = ntohl (sw_if_index);
8836 mp->table_index = ntohl (table_index);
8837 mp->is_ipv6 = is_ipv6;
8838
Jon Loeliger7bc770c2017-01-31 14:03:33 -06008839 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06008840 W (ret);
8841 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008842}
8843
8844static int
8845api_classify_set_interface_l2_tables (vat_main_t * vam)
8846{
8847 unformat_input_t *i = vam->input;
8848 vl_api_classify_set_interface_l2_tables_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008849 u32 sw_if_index;
8850 int sw_if_index_set;
8851 u32 ip4_table_index = ~0;
8852 u32 ip6_table_index = ~0;
8853 u32 other_table_index = ~0;
8854 u32 is_input = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -06008855 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008856
8857 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
8858 {
8859 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
8860 sw_if_index_set = 1;
8861 else if (unformat (i, "sw_if_index %d", &sw_if_index))
8862 sw_if_index_set = 1;
8863 else if (unformat (i, "ip4-table %d", &ip4_table_index))
8864 ;
8865 else if (unformat (i, "ip6-table %d", &ip6_table_index))
8866 ;
8867 else if (unformat (i, "other-table %d", &other_table_index))
8868 ;
8869 else if (unformat (i, "is-input %d", &is_input))
8870 ;
8871 else
8872 {
8873 clib_warning ("parse error '%U'", format_unformat_error, i);
8874 return -99;
8875 }
8876 }
8877
8878 if (sw_if_index_set == 0)
8879 {
8880 errmsg ("missing interface name or sw_if_index");
8881 return -99;
8882 }
8883
8884
Jon Loeliger8a2aea32017-01-31 13:19:40 -06008885 M (CLASSIFY_SET_INTERFACE_L2_TABLES, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01008886
8887 mp->sw_if_index = ntohl (sw_if_index);
8888 mp->ip4_table_index = ntohl (ip4_table_index);
8889 mp->ip6_table_index = ntohl (ip6_table_index);
8890 mp->other_table_index = ntohl (other_table_index);
8891 mp->is_input = (u8) is_input;
8892
Jon Loeliger7bc770c2017-01-31 14:03:33 -06008893 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06008894 W (ret);
8895 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008896}
8897
8898static int
8899api_set_ipfix_exporter (vat_main_t * vam)
8900{
8901 unformat_input_t *i = vam->input;
8902 vl_api_set_ipfix_exporter_t *mp;
8903 ip4_address_t collector_address;
8904 u8 collector_address_set = 0;
8905 u32 collector_port = ~0;
8906 ip4_address_t src_address;
8907 u8 src_address_set = 0;
8908 u32 vrf_id = ~0;
8909 u32 path_mtu = ~0;
8910 u32 template_interval = ~0;
8911 u8 udp_checksum = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06008912 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008913
8914 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
8915 {
8916 if (unformat (i, "collector_address %U", unformat_ip4_address,
8917 &collector_address))
8918 collector_address_set = 1;
8919 else if (unformat (i, "collector_port %d", &collector_port))
8920 ;
8921 else if (unformat (i, "src_address %U", unformat_ip4_address,
8922 &src_address))
8923 src_address_set = 1;
8924 else if (unformat (i, "vrf_id %d", &vrf_id))
8925 ;
8926 else if (unformat (i, "path_mtu %d", &path_mtu))
8927 ;
8928 else if (unformat (i, "template_interval %d", &template_interval))
8929 ;
8930 else if (unformat (i, "udp_checksum"))
8931 udp_checksum = 1;
8932 else
8933 break;
8934 }
8935
8936 if (collector_address_set == 0)
8937 {
8938 errmsg ("collector_address required");
8939 return -99;
8940 }
8941
8942 if (src_address_set == 0)
8943 {
8944 errmsg ("src_address required");
8945 return -99;
8946 }
8947
Jon Loeliger8a2aea32017-01-31 13:19:40 -06008948 M (SET_IPFIX_EXPORTER, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01008949
Jakub Grajciar2f71a882019-10-10 14:21:22 +02008950 memcpy (mp->collector_address.un.ip4, collector_address.data,
Damjan Marion7cd468a2016-12-19 23:05:39 +01008951 sizeof (collector_address.data));
8952 mp->collector_port = htons ((u16) collector_port);
Jakub Grajciar2f71a882019-10-10 14:21:22 +02008953 memcpy (mp->src_address.un.ip4, src_address.data,
8954 sizeof (src_address.data));
Damjan Marion7cd468a2016-12-19 23:05:39 +01008955 mp->vrf_id = htonl (vrf_id);
8956 mp->path_mtu = htonl (path_mtu);
8957 mp->template_interval = htonl (template_interval);
8958 mp->udp_checksum = udp_checksum;
8959
Jon Loeliger7bc770c2017-01-31 14:03:33 -06008960 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06008961 W (ret);
8962 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008963}
8964
8965static int
8966api_set_ipfix_classify_stream (vat_main_t * vam)
8967{
8968 unformat_input_t *i = vam->input;
8969 vl_api_set_ipfix_classify_stream_t *mp;
8970 u32 domain_id = 0;
8971 u32 src_port = UDP_DST_PORT_ipfix;
Jon Loeliger56c7b012017-02-01 12:31:41 -06008972 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008973
8974 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
8975 {
8976 if (unformat (i, "domain %d", &domain_id))
8977 ;
8978 else if (unformat (i, "src_port %d", &src_port))
8979 ;
8980 else
8981 {
8982 errmsg ("unknown input `%U'", format_unformat_error, i);
8983 return -99;
8984 }
8985 }
8986
Jon Loeliger8a2aea32017-01-31 13:19:40 -06008987 M (SET_IPFIX_CLASSIFY_STREAM, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01008988
8989 mp->domain_id = htonl (domain_id);
8990 mp->src_port = htons ((u16) src_port);
8991
Jon Loeliger7bc770c2017-01-31 14:03:33 -06008992 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06008993 W (ret);
8994 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01008995}
8996
8997static int
8998api_ipfix_classify_table_add_del (vat_main_t * vam)
8999{
9000 unformat_input_t *i = vam->input;
9001 vl_api_ipfix_classify_table_add_del_t *mp;
9002 int is_add = -1;
9003 u32 classify_table_index = ~0;
9004 u8 ip_version = 0;
9005 u8 transport_protocol = 255;
Jon Loeliger56c7b012017-02-01 12:31:41 -06009006 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009007
9008 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
9009 {
9010 if (unformat (i, "add"))
9011 is_add = 1;
9012 else if (unformat (i, "del"))
9013 is_add = 0;
9014 else if (unformat (i, "table %d", &classify_table_index))
9015 ;
9016 else if (unformat (i, "ip4"))
9017 ip_version = 4;
9018 else if (unformat (i, "ip6"))
9019 ip_version = 6;
9020 else if (unformat (i, "tcp"))
9021 transport_protocol = 6;
9022 else if (unformat (i, "udp"))
9023 transport_protocol = 17;
9024 else
9025 {
9026 errmsg ("unknown input `%U'", format_unformat_error, i);
9027 return -99;
9028 }
9029 }
9030
9031 if (is_add == -1)
9032 {
9033 errmsg ("expecting: add|del");
9034 return -99;
9035 }
9036 if (classify_table_index == ~0)
9037 {
9038 errmsg ("classifier table not specified");
9039 return -99;
9040 }
9041 if (ip_version == 0)
9042 {
9043 errmsg ("IP version not specified");
9044 return -99;
9045 }
9046
Jon Loeliger8a2aea32017-01-31 13:19:40 -06009047 M (IPFIX_CLASSIFY_TABLE_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009048
9049 mp->is_add = is_add;
9050 mp->table_id = htonl (classify_table_index);
9051 mp->ip_version = ip_version;
9052 mp->transport_protocol = transport_protocol;
9053
Jon Loeliger7bc770c2017-01-31 14:03:33 -06009054 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06009055 W (ret);
9056 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009057}
9058
9059static int
9060api_get_node_index (vat_main_t * vam)
9061{
9062 unformat_input_t *i = vam->input;
9063 vl_api_get_node_index_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009064 u8 *name = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06009065 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009066
9067 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
9068 {
9069 if (unformat (i, "node %s", &name))
9070 ;
9071 else
9072 break;
9073 }
9074 if (name == 0)
9075 {
9076 errmsg ("node name required");
9077 return -99;
9078 }
9079 if (vec_len (name) >= ARRAY_LEN (mp->node_name))
9080 {
9081 errmsg ("node name too long, max %d", ARRAY_LEN (mp->node_name));
9082 return -99;
9083 }
9084
Jon Loeliger8a2aea32017-01-31 13:19:40 -06009085 M (GET_NODE_INDEX, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009086 clib_memcpy (mp->node_name, name, vec_len (name));
9087 vec_free (name);
9088
Jon Loeliger7bc770c2017-01-31 14:03:33 -06009089 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06009090 W (ret);
9091 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009092}
9093
9094static int
9095api_get_next_index (vat_main_t * vam)
9096{
9097 unformat_input_t *i = vam->input;
9098 vl_api_get_next_index_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009099 u8 *node_name = 0, *next_node_name = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06009100 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009101
9102 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
9103 {
9104 if (unformat (i, "node-name %s", &node_name))
9105 ;
9106 else if (unformat (i, "next-node-name %s", &next_node_name))
9107 break;
9108 }
9109
9110 if (node_name == 0)
9111 {
9112 errmsg ("node name required");
9113 return -99;
9114 }
9115 if (vec_len (node_name) >= ARRAY_LEN (mp->node_name))
9116 {
9117 errmsg ("node name too long, max %d", ARRAY_LEN (mp->node_name));
9118 return -99;
9119 }
9120
9121 if (next_node_name == 0)
9122 {
9123 errmsg ("next node name required");
9124 return -99;
9125 }
9126 if (vec_len (next_node_name) >= ARRAY_LEN (mp->next_name))
9127 {
9128 errmsg ("next node name too long, max %d", ARRAY_LEN (mp->next_name));
9129 return -99;
9130 }
9131
Jon Loeliger8a2aea32017-01-31 13:19:40 -06009132 M (GET_NEXT_INDEX, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009133 clib_memcpy (mp->node_name, node_name, vec_len (node_name));
9134 clib_memcpy (mp->next_name, next_node_name, vec_len (next_node_name));
9135 vec_free (node_name);
9136 vec_free (next_node_name);
9137
Jon Loeliger7bc770c2017-01-31 14:03:33 -06009138 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06009139 W (ret);
9140 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009141}
9142
9143static int
9144api_add_node_next (vat_main_t * vam)
9145{
9146 unformat_input_t *i = vam->input;
9147 vl_api_add_node_next_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009148 u8 *name = 0;
9149 u8 *next = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06009150 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009151
9152 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
9153 {
9154 if (unformat (i, "node %s", &name))
9155 ;
9156 else if (unformat (i, "next %s", &next))
9157 ;
9158 else
9159 break;
9160 }
9161 if (name == 0)
9162 {
9163 errmsg ("node name required");
9164 return -99;
9165 }
9166 if (vec_len (name) >= ARRAY_LEN (mp->node_name))
9167 {
9168 errmsg ("node name too long, max %d", ARRAY_LEN (mp->node_name));
9169 return -99;
9170 }
9171 if (next == 0)
9172 {
9173 errmsg ("next node required");
9174 return -99;
9175 }
9176 if (vec_len (next) >= ARRAY_LEN (mp->next_name))
9177 {
9178 errmsg ("next name too long, max %d", ARRAY_LEN (mp->next_name));
9179 return -99;
9180 }
9181
Jon Loeliger8a2aea32017-01-31 13:19:40 -06009182 M (ADD_NODE_NEXT, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009183 clib_memcpy (mp->node_name, name, vec_len (name));
9184 clib_memcpy (mp->next_name, next, vec_len (next));
9185 vec_free (name);
9186 vec_free (next);
9187
Jon Loeliger7bc770c2017-01-31 14:03:33 -06009188 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06009189 W (ret);
9190 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009191}
9192
Damjan Marion8389fb92017-10-13 18:29:53 +02009193static void vl_api_sw_interface_tap_v2_details_t_handler
9194 (vl_api_sw_interface_tap_v2_details_t * mp)
9195{
9196 vat_main_t *vam = &vat_main;
9197
Jakub Grajciar5de4fb72019-09-03 10:40:01 +02009198 u8 *ip4 =
9199 format (0, "%U/%d", format_ip4_address, mp->host_ip4_prefix.address,
9200 mp->host_ip4_prefix.len);
9201 u8 *ip6 =
9202 format (0, "%U/%d", format_ip6_address, mp->host_ip6_prefix.address,
9203 mp->host_ip6_prefix.len);
Milan Lenco73e7f422017-12-14 10:04:25 +01009204
9205 print (vam->ofp,
Andrew Yourtchenko754f24b2019-01-07 20:56:46 +01009206 "\n%-16s %-12d %-5d %-12d %-12d %-14U %-30s %-20s %-20s %-30s 0x%-08x",
Milan Lenco73e7f422017-12-14 10:04:25 +01009207 mp->dev_name, ntohl (mp->sw_if_index), ntohl (mp->id),
9208 ntohs (mp->rx_ring_sz), ntohs (mp->tx_ring_sz),
9209 format_ethernet_address, mp->host_mac_addr, mp->host_namespace,
Andrew Yourtchenko754f24b2019-01-07 20:56:46 +01009210 mp->host_bridge, ip4, ip6, ntohl (mp->tap_flags));
Milan Lenco73e7f422017-12-14 10:04:25 +01009211
9212 vec_free (ip4);
9213 vec_free (ip6);
Damjan Marion8389fb92017-10-13 18:29:53 +02009214}
9215
9216static void vl_api_sw_interface_tap_v2_details_t_handler_json
9217 (vl_api_sw_interface_tap_v2_details_t * mp)
9218{
9219 vat_main_t *vam = &vat_main;
9220 vat_json_node_t *node = NULL;
9221
9222 if (VAT_JSON_ARRAY != vam->json_tree.type)
9223 {
9224 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
9225 vat_json_init_array (&vam->json_tree);
9226 }
9227 node = vat_json_array_add (&vam->json_tree);
9228
9229 vat_json_init_object (node);
Milan Lenco73e7f422017-12-14 10:04:25 +01009230 vat_json_object_add_uint (node, "id", ntohl (mp->id));
Damjan Marion8389fb92017-10-13 18:29:53 +02009231 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
Andrew Yourtchenko754f24b2019-01-07 20:56:46 +01009232 vat_json_object_add_uint (node, "tap_flags", ntohl (mp->tap_flags));
Damjan Marion8389fb92017-10-13 18:29:53 +02009233 vat_json_object_add_string_copy (node, "dev_name", mp->dev_name);
Milan Lenco73e7f422017-12-14 10:04:25 +01009234 vat_json_object_add_uint (node, "rx_ring_sz", ntohs (mp->rx_ring_sz));
9235 vat_json_object_add_uint (node, "tx_ring_sz", ntohs (mp->tx_ring_sz));
9236 vat_json_object_add_string_copy (node, "host_mac_addr",
9237 format (0, "%U", format_ethernet_address,
9238 &mp->host_mac_addr));
9239 vat_json_object_add_string_copy (node, "host_namespace",
9240 mp->host_namespace);
9241 vat_json_object_add_string_copy (node, "host_bridge", mp->host_bridge);
9242 vat_json_object_add_string_copy (node, "host_ip4_addr",
9243 format (0, "%U/%d", format_ip4_address,
Jakub Grajciar5de4fb72019-09-03 10:40:01 +02009244 mp->host_ip4_prefix.address,
9245 mp->host_ip4_prefix.len));
9246 vat_json_object_add_string_copy (node, "host_ip6_prefix",
Milan Lenco73e7f422017-12-14 10:04:25 +01009247 format (0, "%U/%d", format_ip6_address,
Jakub Grajciar5de4fb72019-09-03 10:40:01 +02009248 mp->host_ip6_prefix.address,
9249 mp->host_ip6_prefix.len));
Milan Lenco73e7f422017-12-14 10:04:25 +01009250
Damjan Marion8389fb92017-10-13 18:29:53 +02009251}
9252
9253static int
9254api_sw_interface_tap_v2_dump (vat_main_t * vam)
9255{
9256 vl_api_sw_interface_tap_v2_dump_t *mp;
9257 vl_api_control_ping_t *mp_ping;
9258 int ret;
9259
Milan Lenco73e7f422017-12-14 10:04:25 +01009260 print (vam->ofp,
9261 "\n%-16s %-12s %-5s %-12s %-12s %-14s %-30s %-20s %-20s %-30s",
9262 "dev_name", "sw_if_index", "id", "rx_ring_sz", "tx_ring_sz",
9263 "host_mac_addr", "host_namespace", "host_bridge", "host_ip4_addr",
9264 "host_ip6_addr");
9265
Damjan Marion8389fb92017-10-13 18:29:53 +02009266 /* Get list of tap interfaces */
9267 M (SW_INTERFACE_TAP_V2_DUMP, mp);
9268 S (mp);
9269
9270 /* Use a control ping for synchronization */
9271 MPING (CONTROL_PING, mp_ping);
9272 S (mp_ping);
9273
9274 W (ret);
9275 return ret;
9276}
9277
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01009278static void vl_api_sw_interface_virtio_pci_details_t_handler
9279 (vl_api_sw_interface_virtio_pci_details_t * mp)
9280{
9281 vat_main_t *vam = &vat_main;
9282
9283 typedef union
9284 {
9285 struct
9286 {
9287 u16 domain;
9288 u8 bus;
9289 u8 slot:5;
9290 u8 function:3;
9291 };
9292 u32 as_u32;
9293 } pci_addr_t;
9294 pci_addr_t addr;
Jakub Grajciar2c504f82019-09-26 10:34:41 +02009295
9296 addr.domain = ntohs (mp->pci_addr.domain);
9297 addr.bus = mp->pci_addr.bus;
9298 addr.slot = mp->pci_addr.slot;
9299 addr.function = mp->pci_addr.function;
9300
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01009301 u8 *pci_addr = format (0, "%04x:%02x:%02x.%x", addr.domain, addr.bus,
9302 addr.slot, addr.function);
9303
9304 print (vam->ofp,
9305 "\n%-12s %-12d %-12d %-12d %-17U 0x%-08llx",
9306 pci_addr, ntohl (mp->sw_if_index),
9307 ntohs (mp->rx_ring_sz), ntohs (mp->tx_ring_sz),
9308 format_ethernet_address, mp->mac_addr,
9309 clib_net_to_host_u64 (mp->features));
9310 vec_free (pci_addr);
9311}
9312
9313static void vl_api_sw_interface_virtio_pci_details_t_handler_json
9314 (vl_api_sw_interface_virtio_pci_details_t * mp)
9315{
9316 vat_main_t *vam = &vat_main;
9317 vat_json_node_t *node = NULL;
Jakub Grajciar2c504f82019-09-26 10:34:41 +02009318 vlib_pci_addr_t pci_addr;
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01009319
9320 if (VAT_JSON_ARRAY != vam->json_tree.type)
9321 {
9322 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
9323 vat_json_init_array (&vam->json_tree);
9324 }
9325 node = vat_json_array_add (&vam->json_tree);
9326
Jakub Grajciar2c504f82019-09-26 10:34:41 +02009327 pci_addr.domain = ntohs (mp->pci_addr.domain);
9328 pci_addr.bus = mp->pci_addr.bus;
9329 pci_addr.slot = mp->pci_addr.slot;
9330 pci_addr.function = mp->pci_addr.function;
9331
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01009332 vat_json_init_object (node);
Jakub Grajciar2c504f82019-09-26 10:34:41 +02009333 vat_json_object_add_uint (node, "pci-addr", pci_addr.as_u32);
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +01009334 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
9335 vat_json_object_add_uint (node, "rx_ring_sz", ntohs (mp->rx_ring_sz));
9336 vat_json_object_add_uint (node, "tx_ring_sz", ntohs (mp->tx_ring_sz));
9337 vat_json_object_add_uint (node, "features",
9338 clib_net_to_host_u64 (mp->features));
9339 vat_json_object_add_string_copy (node, "mac_addr",
9340 format (0, "%U", format_ethernet_address,
9341 &mp->mac_addr));
9342}
9343
9344static int
9345api_sw_interface_virtio_pci_dump (vat_main_t * vam)
9346{
9347 vl_api_sw_interface_virtio_pci_dump_t *mp;
9348 vl_api_control_ping_t *mp_ping;
9349 int ret;
9350
9351 print (vam->ofp,
9352 "\n%-12s %-12s %-12s %-12s %-17s %-08s",
9353 "pci_addr", "sw_if_index", "rx_ring_sz", "tx_ring_sz",
9354 "mac_addr", "features");
9355
9356 /* Get list of tap interfaces */
9357 M (SW_INTERFACE_VIRTIO_PCI_DUMP, mp);
9358 S (mp);
9359
9360 /* Use a control ping for synchronization */
9361 MPING (CONTROL_PING, mp_ping);
9362 S (mp_ping);
9363
9364 W (ret);
9365 return ret;
9366}
9367
eyal bariaf86a482018-04-17 11:20:27 +03009368static int
9369api_vxlan_offload_rx (vat_main_t * vam)
9370{
9371 unformat_input_t *line_input = vam->input;
9372 vl_api_vxlan_offload_rx_t *mp;
9373 u32 hw_if_index = ~0, rx_if_index = ~0;
9374 u8 is_add = 1;
9375 int ret;
9376
9377 while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
9378 {
9379 if (unformat (line_input, "del"))
9380 is_add = 0;
9381 else if (unformat (line_input, "hw %U", api_unformat_hw_if_index, vam,
9382 &hw_if_index))
9383 ;
9384 else if (unformat (line_input, "hw hw_if_index %u", &hw_if_index))
9385 ;
9386 else if (unformat (line_input, "rx %U", api_unformat_sw_if_index, vam,
9387 &rx_if_index))
9388 ;
9389 else if (unformat (line_input, "rx sw_if_index %u", &rx_if_index))
9390 ;
9391 else
9392 {
9393 errmsg ("parse error '%U'", format_unformat_error, line_input);
9394 return -99;
9395 }
9396 }
9397
9398 if (hw_if_index == ~0)
9399 {
9400 errmsg ("no hw interface");
9401 return -99;
9402 }
9403
9404 if (rx_if_index == ~0)
9405 {
9406 errmsg ("no rx tunnel");
9407 return -99;
9408 }
9409
9410 M (VXLAN_OFFLOAD_RX, mp);
9411
9412 mp->hw_if_index = ntohl (hw_if_index);
9413 mp->sw_if_index = ntohl (rx_if_index);
9414 mp->enable = is_add;
9415
9416 S (mp);
9417 W (ret);
9418 return ret;
9419}
9420
Damjan Marion7cd468a2016-12-19 23:05:39 +01009421static uword unformat_vxlan_decap_next
9422 (unformat_input_t * input, va_list * args)
9423{
9424 u32 *result = va_arg (*args, u32 *);
9425 u32 tmp;
9426
9427 if (unformat (input, "l2"))
9428 *result = VXLAN_INPUT_NEXT_L2_INPUT;
9429 else if (unformat (input, "%d", &tmp))
9430 *result = tmp;
9431 else
9432 return 0;
9433 return 1;
9434}
9435
9436static int
9437api_vxlan_add_del_tunnel (vat_main_t * vam)
9438{
9439 unformat_input_t *line_input = vam->input;
9440 vl_api_vxlan_add_del_tunnel_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009441 ip46_address_t src, dst;
9442 u8 is_add = 1;
9443 u8 ipv4_set = 0, ipv6_set = 0;
9444 u8 src_set = 0;
9445 u8 dst_set = 0;
9446 u8 grp_set = 0;
Jon Loeliger3d460bd2018-02-01 16:36:12 -06009447 u32 instance = ~0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009448 u32 mcast_sw_if_index = ~0;
9449 u32 encap_vrf_id = 0;
9450 u32 decap_next_index = ~0;
9451 u32 vni = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06009452 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009453
9454 /* Can't "universally zero init" (={0}) due to GCC bug 53119 */
Dave Barachb7b92992018-10-17 10:38:51 -04009455 clib_memset (&src, 0, sizeof src);
9456 clib_memset (&dst, 0, sizeof dst);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009457
9458 while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
9459 {
9460 if (unformat (line_input, "del"))
9461 is_add = 0;
Jon Loeliger3d460bd2018-02-01 16:36:12 -06009462 else if (unformat (line_input, "instance %d", &instance))
9463 ;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009464 else
9465 if (unformat (line_input, "src %U", unformat_ip4_address, &src.ip4))
9466 {
9467 ipv4_set = 1;
9468 src_set = 1;
9469 }
9470 else
9471 if (unformat (line_input, "dst %U", unformat_ip4_address, &dst.ip4))
9472 {
9473 ipv4_set = 1;
9474 dst_set = 1;
9475 }
9476 else
9477 if (unformat (line_input, "src %U", unformat_ip6_address, &src.ip6))
9478 {
9479 ipv6_set = 1;
9480 src_set = 1;
9481 }
9482 else
9483 if (unformat (line_input, "dst %U", unformat_ip6_address, &dst.ip6))
9484 {
9485 ipv6_set = 1;
9486 dst_set = 1;
9487 }
9488 else if (unformat (line_input, "group %U %U",
9489 unformat_ip4_address, &dst.ip4,
9490 api_unformat_sw_if_index, vam, &mcast_sw_if_index))
9491 {
9492 grp_set = dst_set = 1;
9493 ipv4_set = 1;
9494 }
9495 else if (unformat (line_input, "group %U",
9496 unformat_ip4_address, &dst.ip4))
9497 {
9498 grp_set = dst_set = 1;
9499 ipv4_set = 1;
9500 }
9501 else if (unformat (line_input, "group %U %U",
9502 unformat_ip6_address, &dst.ip6,
9503 api_unformat_sw_if_index, vam, &mcast_sw_if_index))
9504 {
9505 grp_set = dst_set = 1;
9506 ipv6_set = 1;
9507 }
9508 else if (unformat (line_input, "group %U",
9509 unformat_ip6_address, &dst.ip6))
9510 {
9511 grp_set = dst_set = 1;
9512 ipv6_set = 1;
9513 }
9514 else
9515 if (unformat (line_input, "mcast_sw_if_index %u", &mcast_sw_if_index))
9516 ;
9517 else if (unformat (line_input, "encap-vrf-id %d", &encap_vrf_id))
9518 ;
9519 else if (unformat (line_input, "decap-next %U",
9520 unformat_vxlan_decap_next, &decap_next_index))
9521 ;
9522 else if (unformat (line_input, "vni %d", &vni))
9523 ;
9524 else
9525 {
9526 errmsg ("parse error '%U'", format_unformat_error, line_input);
9527 return -99;
9528 }
9529 }
9530
9531 if (src_set == 0)
9532 {
9533 errmsg ("tunnel src address not specified");
9534 return -99;
9535 }
9536 if (dst_set == 0)
9537 {
9538 errmsg ("tunnel dst address not specified");
9539 return -99;
9540 }
9541
9542 if (grp_set && !ip46_address_is_multicast (&dst))
9543 {
9544 errmsg ("tunnel group address not multicast");
9545 return -99;
9546 }
9547 if (grp_set && mcast_sw_if_index == ~0)
9548 {
9549 errmsg ("tunnel nonexistent multicast device");
9550 return -99;
9551 }
9552 if (grp_set == 0 && ip46_address_is_multicast (&dst))
9553 {
9554 errmsg ("tunnel dst address must be unicast");
9555 return -99;
9556 }
9557
9558
9559 if (ipv4_set && ipv6_set)
9560 {
9561 errmsg ("both IPv4 and IPv6 addresses specified");
9562 return -99;
9563 }
9564
9565 if ((vni == 0) || (vni >> 24))
9566 {
9567 errmsg ("vni not specified or out of range");
9568 return -99;
9569 }
9570
Jon Loeliger8a2aea32017-01-31 13:19:40 -06009571 M (VXLAN_ADD_DEL_TUNNEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009572
9573 if (ipv6_set)
9574 {
Jakub Grajciar7c0eb562020-03-02 13:55:31 +01009575 clib_memcpy (mp->src_address.un.ip6, &src.ip6, sizeof (src.ip6));
9576 clib_memcpy (mp->dst_address.un.ip6, &dst.ip6, sizeof (dst.ip6));
Damjan Marion7cd468a2016-12-19 23:05:39 +01009577 }
9578 else
9579 {
Jakub Grajciar7c0eb562020-03-02 13:55:31 +01009580 clib_memcpy (mp->src_address.un.ip4, &src.ip4, sizeof (src.ip4));
9581 clib_memcpy (mp->dst_address.un.ip4, &dst.ip4, sizeof (dst.ip4));
Damjan Marion7cd468a2016-12-19 23:05:39 +01009582 }
Jakub Grajciar7c0eb562020-03-02 13:55:31 +01009583 mp->src_address.af = ipv6_set;
9584 mp->dst_address.af = ipv6_set;
Jon Loeliger3d460bd2018-02-01 16:36:12 -06009585
9586 mp->instance = htonl (instance);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009587 mp->encap_vrf_id = ntohl (encap_vrf_id);
9588 mp->decap_next_index = ntohl (decap_next_index);
9589 mp->mcast_sw_if_index = ntohl (mcast_sw_if_index);
9590 mp->vni = ntohl (vni);
9591 mp->is_add = is_add;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009592
Jon Loeliger7bc770c2017-01-31 14:03:33 -06009593 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06009594 W (ret);
9595 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009596}
9597
9598static void vl_api_vxlan_tunnel_details_t_handler
9599 (vl_api_vxlan_tunnel_details_t * mp)
9600{
9601 vat_main_t *vam = &vat_main;
Jakub Grajciar7c0eb562020-03-02 13:55:31 +01009602 ip46_address_t src =
9603 to_ip46 (mp->dst_address.af, (u8 *) & mp->dst_address.un);
9604 ip46_address_t dst =
9605 to_ip46 (mp->dst_address.af, (u8 *) & mp->src_address.un);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009606
Jon Loeliger3d460bd2018-02-01 16:36:12 -06009607 print (vam->ofp, "%11d%11d%24U%24U%14d%18d%13d%19d",
Damjan Marion7cd468a2016-12-19 23:05:39 +01009608 ntohl (mp->sw_if_index),
Jon Loeliger3d460bd2018-02-01 16:36:12 -06009609 ntohl (mp->instance),
Damjan Marion7cd468a2016-12-19 23:05:39 +01009610 format_ip46_address, &src, IP46_TYPE_ANY,
9611 format_ip46_address, &dst, IP46_TYPE_ANY,
9612 ntohl (mp->encap_vrf_id),
9613 ntohl (mp->decap_next_index), ntohl (mp->vni),
9614 ntohl (mp->mcast_sw_if_index));
9615}
9616
9617static void vl_api_vxlan_tunnel_details_t_handler_json
9618 (vl_api_vxlan_tunnel_details_t * mp)
9619{
9620 vat_main_t *vam = &vat_main;
9621 vat_json_node_t *node = NULL;
9622
9623 if (VAT_JSON_ARRAY != vam->json_tree.type)
9624 {
9625 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
9626 vat_json_init_array (&vam->json_tree);
9627 }
9628 node = vat_json_array_add (&vam->json_tree);
9629
9630 vat_json_init_object (node);
9631 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
Jon Loeliger3d460bd2018-02-01 16:36:12 -06009632
9633 vat_json_object_add_uint (node, "instance", ntohl (mp->instance));
9634
Jakub Grajciar7c0eb562020-03-02 13:55:31 +01009635 if (mp->src_address.af)
Damjan Marion7cd468a2016-12-19 23:05:39 +01009636 {
9637 struct in6_addr ip6;
9638
Jakub Grajciar7c0eb562020-03-02 13:55:31 +01009639 clib_memcpy (&ip6, mp->src_address.un.ip6, sizeof (ip6));
Damjan Marion7cd468a2016-12-19 23:05:39 +01009640 vat_json_object_add_ip6 (node, "src_address", ip6);
Jakub Grajciar7c0eb562020-03-02 13:55:31 +01009641 clib_memcpy (&ip6, mp->dst_address.un.ip6, sizeof (ip6));
Damjan Marion7cd468a2016-12-19 23:05:39 +01009642 vat_json_object_add_ip6 (node, "dst_address", ip6);
9643 }
9644 else
9645 {
9646 struct in_addr ip4;
9647
Jakub Grajciar7c0eb562020-03-02 13:55:31 +01009648 clib_memcpy (&ip4, mp->src_address.un.ip4, sizeof (ip4));
Damjan Marion7cd468a2016-12-19 23:05:39 +01009649 vat_json_object_add_ip4 (node, "src_address", ip4);
Jakub Grajciar7c0eb562020-03-02 13:55:31 +01009650 clib_memcpy (&ip4, mp->dst_address.un.ip4, sizeof (ip4));
Damjan Marion7cd468a2016-12-19 23:05:39 +01009651 vat_json_object_add_ip4 (node, "dst_address", ip4);
9652 }
9653 vat_json_object_add_uint (node, "encap_vrf_id", ntohl (mp->encap_vrf_id));
9654 vat_json_object_add_uint (node, "decap_next_index",
9655 ntohl (mp->decap_next_index));
9656 vat_json_object_add_uint (node, "vni", ntohl (mp->vni));
Damjan Marion7cd468a2016-12-19 23:05:39 +01009657 vat_json_object_add_uint (node, "mcast_sw_if_index",
9658 ntohl (mp->mcast_sw_if_index));
9659}
9660
9661static int
9662api_vxlan_tunnel_dump (vat_main_t * vam)
9663{
9664 unformat_input_t *i = vam->input;
9665 vl_api_vxlan_tunnel_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -06009666 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009667 u32 sw_if_index;
9668 u8 sw_if_index_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06009669 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009670
9671 /* Parse args required to build the message */
9672 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
9673 {
9674 if (unformat (i, "sw_if_index %d", &sw_if_index))
9675 sw_if_index_set = 1;
9676 else
9677 break;
9678 }
9679
9680 if (sw_if_index_set == 0)
9681 {
9682 sw_if_index = ~0;
9683 }
9684
9685 if (!vam->json_output)
9686 {
Jon Loeliger3d460bd2018-02-01 16:36:12 -06009687 print (vam->ofp, "%11s%11s%24s%24s%14s%18s%13s%19s",
9688 "sw_if_index", "instance", "src_address", "dst_address",
Damjan Marion7cd468a2016-12-19 23:05:39 +01009689 "encap_vrf_id", "decap_next_index", "vni", "mcast_sw_if_index");
9690 }
9691
9692 /* Get list of vxlan-tunnel interfaces */
Jon Loeliger8a2aea32017-01-31 13:19:40 -06009693 M (VXLAN_TUNNEL_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009694
9695 mp->sw_if_index = htonl (sw_if_index);
9696
Jon Loeliger7bc770c2017-01-31 14:03:33 -06009697 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009698
9699 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -04009700 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -06009701 S (mp_ping);
9702
Jon Loeliger56c7b012017-02-01 12:31:41 -06009703 W (ret);
9704 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009705}
9706
9707static int
Damjan Marion7cd468a2016-12-19 23:05:39 +01009708api_l2_fib_clear_table (vat_main_t * vam)
9709{
9710// unformat_input_t * i = vam->input;
9711 vl_api_l2_fib_clear_table_t *mp;
Jon Loeliger56c7b012017-02-01 12:31:41 -06009712 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009713
Jon Loeliger8a2aea32017-01-31 13:19:40 -06009714 M (L2_FIB_CLEAR_TABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009715
Jon Loeliger7bc770c2017-01-31 14:03:33 -06009716 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06009717 W (ret);
9718 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009719}
9720
9721static int
9722api_l2_interface_efp_filter (vat_main_t * vam)
9723{
9724 unformat_input_t *i = vam->input;
9725 vl_api_l2_interface_efp_filter_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009726 u32 sw_if_index;
9727 u8 enable = 1;
9728 u8 sw_if_index_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06009729 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009730
9731 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
9732 {
9733 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
9734 sw_if_index_set = 1;
9735 else if (unformat (i, "sw_if_index %d", &sw_if_index))
9736 sw_if_index_set = 1;
9737 else if (unformat (i, "enable"))
9738 enable = 1;
9739 else if (unformat (i, "disable"))
9740 enable = 0;
9741 else
9742 {
9743 clib_warning ("parse error '%U'", format_unformat_error, i);
9744 return -99;
9745 }
9746 }
9747
9748 if (sw_if_index_set == 0)
9749 {
9750 errmsg ("missing sw_if_index");
9751 return -99;
9752 }
9753
Jon Loeliger8a2aea32017-01-31 13:19:40 -06009754 M (L2_INTERFACE_EFP_FILTER, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009755
9756 mp->sw_if_index = ntohl (sw_if_index);
9757 mp->enable_disable = enable;
9758
Jon Loeliger7bc770c2017-01-31 14:03:33 -06009759 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06009760 W (ret);
9761 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009762}
9763
9764#define foreach_vtr_op \
9765_("disable", L2_VTR_DISABLED) \
9766_("push-1", L2_VTR_PUSH_1) \
9767_("push-2", L2_VTR_PUSH_2) \
9768_("pop-1", L2_VTR_POP_1) \
9769_("pop-2", L2_VTR_POP_2) \
9770_("translate-1-1", L2_VTR_TRANSLATE_1_1) \
9771_("translate-1-2", L2_VTR_TRANSLATE_1_2) \
9772_("translate-2-1", L2_VTR_TRANSLATE_2_1) \
9773_("translate-2-2", L2_VTR_TRANSLATE_2_2)
9774
9775static int
9776api_l2_interface_vlan_tag_rewrite (vat_main_t * vam)
9777{
9778 unformat_input_t *i = vam->input;
9779 vl_api_l2_interface_vlan_tag_rewrite_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009780 u32 sw_if_index;
9781 u8 sw_if_index_set = 0;
9782 u8 vtr_op_set = 0;
9783 u32 vtr_op = 0;
9784 u32 push_dot1q = 1;
9785 u32 tag1 = ~0;
9786 u32 tag2 = ~0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06009787 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009788
9789 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
9790 {
9791 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
9792 sw_if_index_set = 1;
9793 else if (unformat (i, "sw_if_index %d", &sw_if_index))
9794 sw_if_index_set = 1;
9795 else if (unformat (i, "vtr_op %d", &vtr_op))
9796 vtr_op_set = 1;
9797#define _(n,v) else if (unformat(i, n)) {vtr_op = v; vtr_op_set = 1;}
9798 foreach_vtr_op
9799#undef _
9800 else if (unformat (i, "push_dot1q %d", &push_dot1q))
9801 ;
9802 else if (unformat (i, "tag1 %d", &tag1))
9803 ;
9804 else if (unformat (i, "tag2 %d", &tag2))
9805 ;
9806 else
9807 {
9808 clib_warning ("parse error '%U'", format_unformat_error, i);
9809 return -99;
9810 }
9811 }
9812
9813 if ((sw_if_index_set == 0) || (vtr_op_set == 0))
9814 {
9815 errmsg ("missing vtr operation or sw_if_index");
9816 return -99;
9817 }
9818
Jon Loeliger8a2aea32017-01-31 13:19:40 -06009819 M (L2_INTERFACE_VLAN_TAG_REWRITE, mp);
9820 mp->sw_if_index = ntohl (sw_if_index);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009821 mp->vtr_op = ntohl (vtr_op);
9822 mp->push_dot1q = ntohl (push_dot1q);
9823 mp->tag1 = ntohl (tag1);
9824 mp->tag2 = ntohl (tag2);
9825
Jon Loeliger7bc770c2017-01-31 14:03:33 -06009826 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06009827 W (ret);
9828 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009829}
9830
9831static int
9832api_create_vhost_user_if (vat_main_t * vam)
9833{
9834 unformat_input_t *i = vam->input;
9835 vl_api_create_vhost_user_if_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009836 u8 *file_name;
9837 u8 is_server = 0;
9838 u8 file_name_set = 0;
9839 u32 custom_dev_instance = ~0;
9840 u8 hwaddr[6];
9841 u8 use_custom_mac = 0;
Mohsin Kazmiee2e58f2018-08-21 16:07:03 +02009842 u8 disable_mrg_rxbuf = 0;
9843 u8 disable_indirect_desc = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009844 u8 *tag = 0;
Steven Luong4208a4c2019-05-06 08:51:56 -07009845 u8 enable_gso = 0;
Steven Luongbc0d9ff2020-03-23 09:34:59 -07009846 u8 enable_packed = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06009847 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009848
9849 /* Shut up coverity */
Dave Barachb7b92992018-10-17 10:38:51 -04009850 clib_memset (hwaddr, 0, sizeof (hwaddr));
Damjan Marion7cd468a2016-12-19 23:05:39 +01009851
9852 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
9853 {
9854 if (unformat (i, "socket %s", &file_name))
9855 {
9856 file_name_set = 1;
9857 }
9858 else if (unformat (i, "renumber %" PRIu32, &custom_dev_instance))
9859 ;
9860 else if (unformat (i, "mac %U", unformat_ethernet_address, hwaddr))
9861 use_custom_mac = 1;
9862 else if (unformat (i, "server"))
9863 is_server = 1;
Mohsin Kazmiee2e58f2018-08-21 16:07:03 +02009864 else if (unformat (i, "disable_mrg_rxbuf"))
9865 disable_mrg_rxbuf = 1;
9866 else if (unformat (i, "disable_indirect_desc"))
9867 disable_indirect_desc = 1;
Steven Luong4208a4c2019-05-06 08:51:56 -07009868 else if (unformat (i, "gso"))
9869 enable_gso = 1;
Steven Luongbc0d9ff2020-03-23 09:34:59 -07009870 else if (unformat (i, "packed"))
9871 enable_packed = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009872 else if (unformat (i, "tag %s", &tag))
9873 ;
9874 else
9875 break;
9876 }
9877
9878 if (file_name_set == 0)
9879 {
9880 errmsg ("missing socket file name");
9881 return -99;
9882 }
9883
9884 if (vec_len (file_name) > 255)
9885 {
9886 errmsg ("socket file name too long");
9887 return -99;
9888 }
9889 vec_add1 (file_name, 0);
9890
Jon Loeliger8a2aea32017-01-31 13:19:40 -06009891 M (CREATE_VHOST_USER_IF, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009892
9893 mp->is_server = is_server;
Mohsin Kazmiee2e58f2018-08-21 16:07:03 +02009894 mp->disable_mrg_rxbuf = disable_mrg_rxbuf;
9895 mp->disable_indirect_desc = disable_indirect_desc;
Steven Luong4208a4c2019-05-06 08:51:56 -07009896 mp->enable_gso = enable_gso;
Steven Luongbc0d9ff2020-03-23 09:34:59 -07009897 mp->enable_packed = enable_packed;
Steven Luong27ba5002020-11-17 13:30:44 -08009898 mp->custom_dev_instance = ntohl (custom_dev_instance);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009899 clib_memcpy (mp->sock_filename, file_name, vec_len (file_name));
9900 vec_free (file_name);
9901 if (custom_dev_instance != ~0)
Steven Luong27ba5002020-11-17 13:30:44 -08009902 mp->renumber = 1;
Mohsin Kazmiee2e58f2018-08-21 16:07:03 +02009903
Damjan Marion7cd468a2016-12-19 23:05:39 +01009904 mp->use_custom_mac = use_custom_mac;
9905 clib_memcpy (mp->mac_address, hwaddr, 6);
9906 if (tag)
9907 strncpy ((char *) mp->tag, (char *) tag, ARRAY_LEN (mp->tag) - 1);
9908 vec_free (tag);
9909
Jon Loeliger7bc770c2017-01-31 14:03:33 -06009910 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -06009911 W (ret);
9912 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009913}
9914
9915static int
9916api_modify_vhost_user_if (vat_main_t * vam)
9917{
9918 unformat_input_t *i = vam->input;
9919 vl_api_modify_vhost_user_if_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009920 u8 *file_name;
9921 u8 is_server = 0;
9922 u8 file_name_set = 0;
9923 u32 custom_dev_instance = ~0;
9924 u8 sw_if_index_set = 0;
9925 u32 sw_if_index = (u32) ~ 0;
Steven Luong4208a4c2019-05-06 08:51:56 -07009926 u8 enable_gso = 0;
Steven Luongbc0d9ff2020-03-23 09:34:59 -07009927 u8 enable_packed = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -06009928 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009929
9930 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
9931 {
9932 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
9933 sw_if_index_set = 1;
9934 else if (unformat (i, "sw_if_index %d", &sw_if_index))
9935 sw_if_index_set = 1;
9936 else if (unformat (i, "socket %s", &file_name))
9937 {
9938 file_name_set = 1;
9939 }
9940 else if (unformat (i, "renumber %" PRIu32, &custom_dev_instance))
9941 ;
9942 else if (unformat (i, "server"))
9943 is_server = 1;
Steven Luong4208a4c2019-05-06 08:51:56 -07009944 else if (unformat (i, "gso"))
9945 enable_gso = 1;
Steven Luongbc0d9ff2020-03-23 09:34:59 -07009946 else if (unformat (i, "packed"))
9947 enable_packed = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +01009948 else
9949 break;
9950 }
9951
9952 if (sw_if_index_set == 0)
9953 {
9954 errmsg ("missing sw_if_index or interface name");
9955 return -99;
9956 }
9957
9958 if (file_name_set == 0)
9959 {
9960 errmsg ("missing socket file name");
9961 return -99;
9962 }
9963
9964 if (vec_len (file_name) > 255)
9965 {
9966 errmsg ("socket file name too long");
9967 return -99;
9968 }
9969 vec_add1 (file_name, 0);
9970
Jon Loeliger8a2aea32017-01-31 13:19:40 -06009971 M (MODIFY_VHOST_USER_IF, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009972
9973 mp->sw_if_index = ntohl (sw_if_index);
9974 mp->is_server = is_server;
Steven Luong4208a4c2019-05-06 08:51:56 -07009975 mp->enable_gso = enable_gso;
Steven Luongbc0d9ff2020-03-23 09:34:59 -07009976 mp->enable_packed = enable_packed;
Steven Luong27ba5002020-11-17 13:30:44 -08009977 mp->custom_dev_instance = ntohl (custom_dev_instance);
Damjan Marion7cd468a2016-12-19 23:05:39 +01009978 clib_memcpy (mp->sock_filename, file_name, vec_len (file_name));
9979 vec_free (file_name);
9980 if (custom_dev_instance != ~0)
Steven Luong27ba5002020-11-17 13:30:44 -08009981 mp->renumber = 1;
9982
9983 S (mp);
9984 W (ret);
9985 return ret;
9986}
9987
9988static int
9989api_create_vhost_user_if_v2 (vat_main_t * vam)
9990{
9991 unformat_input_t *i = vam->input;
9992 vl_api_create_vhost_user_if_v2_t *mp;
9993 u8 *file_name;
9994 u8 is_server = 0;
9995 u8 file_name_set = 0;
9996 u32 custom_dev_instance = ~0;
9997 u8 hwaddr[6];
9998 u8 use_custom_mac = 0;
9999 u8 disable_mrg_rxbuf = 0;
10000 u8 disable_indirect_desc = 0;
10001 u8 *tag = 0;
10002 u8 enable_gso = 0;
10003 u8 enable_packed = 0;
10004 u8 enable_event_idx = 0;
10005 int ret;
10006
10007 /* Shut up coverity */
10008 clib_memset (hwaddr, 0, sizeof (hwaddr));
10009
10010 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
Damjan Marion7cd468a2016-12-19 23:05:39 +010010011 {
Steven Luong27ba5002020-11-17 13:30:44 -080010012 if (unformat (i, "socket %s", &file_name))
10013 {
10014 file_name_set = 1;
10015 }
10016 else if (unformat (i, "renumber %" PRIu32, &custom_dev_instance))
10017 ;
10018 else if (unformat (i, "mac %U", unformat_ethernet_address, hwaddr))
10019 use_custom_mac = 1;
10020 else if (unformat (i, "server"))
10021 is_server = 1;
10022 else if (unformat (i, "disable_mrg_rxbuf"))
10023 disable_mrg_rxbuf = 1;
10024 else if (unformat (i, "disable_indirect_desc"))
10025 disable_indirect_desc = 1;
10026 else if (unformat (i, "gso"))
10027 enable_gso = 1;
10028 else if (unformat (i, "packed"))
10029 enable_packed = 1;
10030 else if (unformat (i, "event-idx"))
10031 enable_event_idx = 1;
10032 else if (unformat (i, "tag %s", &tag))
10033 ;
10034 else
10035 break;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010036 }
10037
Steven Luong27ba5002020-11-17 13:30:44 -080010038 if (file_name_set == 0)
10039 {
10040 errmsg ("missing socket file name");
10041 return -99;
10042 }
10043
10044 if (vec_len (file_name) > 255)
10045 {
10046 errmsg ("socket file name too long");
10047 return -99;
10048 }
10049 vec_add1 (file_name, 0);
10050
10051 M (CREATE_VHOST_USER_IF_V2, mp);
10052
10053 mp->is_server = is_server;
10054 mp->disable_mrg_rxbuf = disable_mrg_rxbuf;
10055 mp->disable_indirect_desc = disable_indirect_desc;
10056 mp->enable_gso = enable_gso;
10057 mp->enable_packed = enable_packed;
10058 mp->enable_event_idx = enable_event_idx;
10059 mp->custom_dev_instance = ntohl (custom_dev_instance);
10060 clib_memcpy (mp->sock_filename, file_name, vec_len (file_name));
10061 vec_free (file_name);
10062 if (custom_dev_instance != ~0)
10063 mp->renumber = 1;
10064
10065 mp->use_custom_mac = use_custom_mac;
10066 clib_memcpy (mp->mac_address, hwaddr, 6);
10067 if (tag)
10068 strncpy ((char *) mp->tag, (char *) tag, ARRAY_LEN (mp->tag) - 1);
10069 vec_free (tag);
10070
10071 S (mp);
10072 W (ret);
10073 return ret;
10074}
10075
10076static int
10077api_modify_vhost_user_if_v2 (vat_main_t * vam)
10078{
10079 unformat_input_t *i = vam->input;
10080 vl_api_modify_vhost_user_if_v2_t *mp;
10081 u8 *file_name;
10082 u8 is_server = 0;
10083 u8 file_name_set = 0;
10084 u32 custom_dev_instance = ~0;
10085 u8 sw_if_index_set = 0;
10086 u32 sw_if_index = (u32) ~ 0;
10087 u8 enable_gso = 0;
10088 u8 enable_packed = 0;
10089 u8 enable_event_idx = 0;
10090 int ret;
10091
10092 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
10093 {
10094 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
10095 sw_if_index_set = 1;
10096 else if (unformat (i, "sw_if_index %d", &sw_if_index))
10097 sw_if_index_set = 1;
10098 else if (unformat (i, "socket %s", &file_name))
10099 {
10100 file_name_set = 1;
10101 }
10102 else if (unformat (i, "renumber %" PRIu32, &custom_dev_instance))
10103 ;
10104 else if (unformat (i, "server"))
10105 is_server = 1;
10106 else if (unformat (i, "gso"))
10107 enable_gso = 1;
10108 else if (unformat (i, "packed"))
10109 enable_packed = 1;
10110 else if (unformat (i, "event-idx"))
10111 enable_event_idx = 1;
10112 else
10113 break;
10114 }
10115
10116 if (sw_if_index_set == 0)
10117 {
10118 errmsg ("missing sw_if_index or interface name");
10119 return -99;
10120 }
10121
10122 if (file_name_set == 0)
10123 {
10124 errmsg ("missing socket file name");
10125 return -99;
10126 }
10127
10128 if (vec_len (file_name) > 255)
10129 {
10130 errmsg ("socket file name too long");
10131 return -99;
10132 }
10133 vec_add1 (file_name, 0);
10134
10135 M (MODIFY_VHOST_USER_IF_V2, mp);
10136
10137 mp->sw_if_index = ntohl (sw_if_index);
10138 mp->is_server = is_server;
10139 mp->enable_gso = enable_gso;
10140 mp->enable_packed = enable_packed;
10141 mp->enable_event_idx = enable_event_idx;
10142 mp->custom_dev_instance = ntohl (custom_dev_instance);
10143 clib_memcpy (mp->sock_filename, file_name, vec_len (file_name));
10144 vec_free (file_name);
10145 if (custom_dev_instance != ~0)
10146 mp->renumber = 1;
10147
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010148 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060010149 W (ret);
10150 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010151}
10152
10153static int
10154api_delete_vhost_user_if (vat_main_t * vam)
10155{
10156 unformat_input_t *i = vam->input;
10157 vl_api_delete_vhost_user_if_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010158 u32 sw_if_index = ~0;
10159 u8 sw_if_index_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010160 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010161
10162 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
10163 {
10164 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
10165 sw_if_index_set = 1;
10166 else if (unformat (i, "sw_if_index %d", &sw_if_index))
10167 sw_if_index_set = 1;
10168 else
10169 break;
10170 }
10171
10172 if (sw_if_index_set == 0)
10173 {
10174 errmsg ("missing sw_if_index or interface name");
10175 return -99;
10176 }
10177
10178
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010179 M (DELETE_VHOST_USER_IF, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010180
10181 mp->sw_if_index = ntohl (sw_if_index);
10182
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010183 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060010184 W (ret);
10185 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010186}
10187
10188static void vl_api_sw_interface_vhost_user_details_t_handler
10189 (vl_api_sw_interface_vhost_user_details_t * mp)
10190{
10191 vat_main_t *vam = &vat_main;
Jakub Grajciar5d4c99f2019-09-26 10:21:59 +020010192 u64 features;
10193
10194 features =
10195 clib_net_to_host_u32 (mp->features_first_32) | ((u64)
10196 clib_net_to_host_u32
10197 (mp->features_last_32) <<
10198 32);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010199
Steven Luong150bf5a2020-11-17 15:56:10 -080010200 print (vam->ofp, "%-25s %3" PRIu32 " %6" PRIu32 " %16llx %6d %7d %s",
10201 (char *) mp->interface_name, ntohl (mp->sw_if_index),
10202 ntohl (mp->virtio_net_hdr_sz), features, mp->is_server,
Stevenf3b53642017-05-01 14:03:02 -070010203 ntohl (mp->num_regions), (char *) mp->sock_filename);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010204 print (vam->ofp, " Status: '%s'", strerror (ntohl (mp->sock_errno)));
10205}
10206
10207static void vl_api_sw_interface_vhost_user_details_t_handler_json
10208 (vl_api_sw_interface_vhost_user_details_t * mp)
10209{
10210 vat_main_t *vam = &vat_main;
10211 vat_json_node_t *node = NULL;
10212
10213 if (VAT_JSON_ARRAY != vam->json_tree.type)
10214 {
10215 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
10216 vat_json_init_array (&vam->json_tree);
10217 }
10218 node = vat_json_array_add (&vam->json_tree);
10219
10220 vat_json_init_object (node);
10221 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
10222 vat_json_object_add_string_copy (node, "interface_name",
10223 mp->interface_name);
10224 vat_json_object_add_uint (node, "virtio_net_hdr_sz",
10225 ntohl (mp->virtio_net_hdr_sz));
Jakub Grajciar5d4c99f2019-09-26 10:21:59 +020010226 vat_json_object_add_uint (node, "features_first_32",
10227 clib_net_to_host_u32 (mp->features_first_32));
10228 vat_json_object_add_uint (node, "features_last_32",
10229 clib_net_to_host_u32 (mp->features_last_32));
Damjan Marion7cd468a2016-12-19 23:05:39 +010010230 vat_json_object_add_uint (node, "is_server", mp->is_server);
10231 vat_json_object_add_string_copy (node, "sock_filename", mp->sock_filename);
10232 vat_json_object_add_uint (node, "num_regions", ntohl (mp->num_regions));
10233 vat_json_object_add_uint (node, "sock_errno", ntohl (mp->sock_errno));
10234}
10235
10236static int
10237api_sw_interface_vhost_user_dump (vat_main_t * vam)
10238{
Steven Luonga0e8d962020-05-18 17:12:56 -070010239 unformat_input_t *i = vam->input;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010240 vl_api_sw_interface_vhost_user_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060010241 vl_api_control_ping_t *mp_ping;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010242 int ret;
Steven Luonga0e8d962020-05-18 17:12:56 -070010243 u32 sw_if_index = ~0;
10244
10245 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
10246 {
10247 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
10248 ;
10249 else if (unformat (i, "sw_if_index %d", &sw_if_index))
10250 ;
10251 else
10252 break;
10253 }
10254
Steven Luong150bf5a2020-11-17 15:56:10 -080010255 print (vam->ofp, "Interface name idx hdr_sz features "
10256 "server regions filename");
Damjan Marion7cd468a2016-12-19 23:05:39 +010010257
10258 /* Get list of vhost-user interfaces */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010259 M (SW_INTERFACE_VHOST_USER_DUMP, mp);
Steven Luonga0e8d962020-05-18 17:12:56 -070010260 mp->sw_if_index = ntohl (sw_if_index);
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010261 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010262
10263 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040010264 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060010265 S (mp_ping);
10266
Jon Loeliger56c7b012017-02-01 12:31:41 -060010267 W (ret);
10268 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010269}
10270
10271static int
10272api_show_version (vat_main_t * vam)
10273{
10274 vl_api_show_version_t *mp;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010275 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010276
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010277 M (SHOW_VERSION, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010278
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010279 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060010280 W (ret);
10281 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010282}
10283
10284
10285static int
10286api_vxlan_gpe_add_del_tunnel (vat_main_t * vam)
10287{
10288 unformat_input_t *line_input = vam->input;
10289 vl_api_vxlan_gpe_add_del_tunnel_t *mp;
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010290 ip46_address_t local, remote;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010291 u8 is_add = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010292 u8 local_set = 0;
10293 u8 remote_set = 0;
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010294 u8 grp_set = 0;
10295 u32 mcast_sw_if_index = ~0;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010296 u32 encap_vrf_id = 0;
10297 u32 decap_vrf_id = 0;
10298 u8 protocol = ~0;
10299 u32 vni;
10300 u8 vni_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010301 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010302
10303 while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
10304 {
10305 if (unformat (line_input, "del"))
10306 is_add = 0;
10307 else if (unformat (line_input, "local %U",
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010308 unformat_ip46_address, &local))
Damjan Marion7cd468a2016-12-19 23:05:39 +010010309 {
10310 local_set = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010311 }
10312 else if (unformat (line_input, "remote %U",
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010313 unformat_ip46_address, &remote))
Damjan Marion7cd468a2016-12-19 23:05:39 +010010314 {
10315 remote_set = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010316 }
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010317 else if (unformat (line_input, "group %U %U",
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010318 unformat_ip46_address, &remote,
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010319 api_unformat_sw_if_index, vam, &mcast_sw_if_index))
10320 {
10321 grp_set = remote_set = 1;
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010322 }
10323 else if (unformat (line_input, "group %U",
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010324 unformat_ip46_address, &remote))
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010325 {
10326 grp_set = remote_set = 1;
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010327 }
10328 else
10329 if (unformat (line_input, "mcast_sw_if_index %u", &mcast_sw_if_index))
10330 ;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010331 else if (unformat (line_input, "encap-vrf-id %d", &encap_vrf_id))
10332 ;
10333 else if (unformat (line_input, "decap-vrf-id %d", &decap_vrf_id))
10334 ;
10335 else if (unformat (line_input, "vni %d", &vni))
10336 vni_set = 1;
10337 else if (unformat (line_input, "next-ip4"))
10338 protocol = 1;
10339 else if (unformat (line_input, "next-ip6"))
10340 protocol = 2;
10341 else if (unformat (line_input, "next-ethernet"))
10342 protocol = 3;
10343 else if (unformat (line_input, "next-nsh"))
10344 protocol = 4;
10345 else
10346 {
10347 errmsg ("parse error '%U'", format_unformat_error, line_input);
10348 return -99;
10349 }
10350 }
10351
10352 if (local_set == 0)
10353 {
10354 errmsg ("tunnel local address not specified");
10355 return -99;
10356 }
10357 if (remote_set == 0)
10358 {
10359 errmsg ("tunnel remote address not specified");
10360 return -99;
10361 }
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010362 if (grp_set && mcast_sw_if_index == ~0)
10363 {
10364 errmsg ("tunnel nonexistent multicast device");
10365 return -99;
10366 }
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010367 if (ip46_address_is_ip4 (&local) != ip46_address_is_ip4 (&remote))
Damjan Marion7cd468a2016-12-19 23:05:39 +010010368 {
10369 errmsg ("both IPv4 and IPv6 addresses specified");
10370 return -99;
10371 }
10372
10373 if (vni_set == 0)
10374 {
10375 errmsg ("vni not specified");
10376 return -99;
10377 }
10378
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010379 M (VXLAN_GPE_ADD_DEL_TUNNEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010380
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010381 ip_address_encode (&local,
10382 ip46_address_is_ip4 (&local) ? IP46_TYPE_IP4 :
10383 IP46_TYPE_IP6, &mp->local);
10384 ip_address_encode (&remote,
10385 ip46_address_is_ip4 (&remote) ? IP46_TYPE_IP4 :
10386 IP46_TYPE_IP6, &mp->remote);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010387
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010388 mp->mcast_sw_if_index = ntohl (mcast_sw_if_index);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010389 mp->encap_vrf_id = ntohl (encap_vrf_id);
10390 mp->decap_vrf_id = ntohl (decap_vrf_id);
10391 mp->protocol = protocol;
10392 mp->vni = ntohl (vni);
10393 mp->is_add = is_add;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010394
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010395 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060010396 W (ret);
10397 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010398}
10399
10400static void vl_api_vxlan_gpe_tunnel_details_t_handler
10401 (vl_api_vxlan_gpe_tunnel_details_t * mp)
10402{
10403 vat_main_t *vam = &vat_main;
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010404 ip46_address_t local, remote;
10405
10406 ip_address_decode (&mp->local, &local);
10407 ip_address_decode (&mp->remote, &remote);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010408
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010409 print (vam->ofp, "%11d%24U%24U%13d%12d%19d%14d%14d",
Damjan Marion7cd468a2016-12-19 23:05:39 +010010410 ntohl (mp->sw_if_index),
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010411 format_ip46_address, &local, IP46_TYPE_ANY,
10412 format_ip46_address, &remote, IP46_TYPE_ANY,
10413 ntohl (mp->vni), mp->protocol,
10414 ntohl (mp->mcast_sw_if_index),
Damjan Marion7cd468a2016-12-19 23:05:39 +010010415 ntohl (mp->encap_vrf_id), ntohl (mp->decap_vrf_id));
10416}
10417
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010418
Damjan Marion7cd468a2016-12-19 23:05:39 +010010419static void vl_api_vxlan_gpe_tunnel_details_t_handler_json
10420 (vl_api_vxlan_gpe_tunnel_details_t * mp)
10421{
10422 vat_main_t *vam = &vat_main;
10423 vat_json_node_t *node = NULL;
10424 struct in_addr ip4;
10425 struct in6_addr ip6;
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010426 ip46_address_t local, remote;
10427
10428 ip_address_decode (&mp->local, &local);
10429 ip_address_decode (&mp->remote, &remote);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010430
10431 if (VAT_JSON_ARRAY != vam->json_tree.type)
10432 {
10433 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
10434 vat_json_init_array (&vam->json_tree);
10435 }
10436 node = vat_json_array_add (&vam->json_tree);
10437
10438 vat_json_init_object (node);
10439 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010440 if (ip46_address_is_ip4 (&local))
Damjan Marion7cd468a2016-12-19 23:05:39 +010010441 {
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010442 clib_memcpy (&ip4, &local.ip4, sizeof (ip4));
10443 vat_json_object_add_ip4 (node, "local", ip4);
10444 clib_memcpy (&ip4, &remote.ip4, sizeof (ip4));
10445 vat_json_object_add_ip4 (node, "remote", ip4);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010446 }
10447 else
10448 {
Jakub Grajciar1c2002a2020-01-31 10:45:30 +010010449 clib_memcpy (&ip6, &local.ip6, sizeof (ip6));
10450 vat_json_object_add_ip6 (node, "local", ip6);
10451 clib_memcpy (&ip6, &remote.ip6, sizeof (ip6));
10452 vat_json_object_add_ip6 (node, "remote", ip6);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010453 }
10454 vat_json_object_add_uint (node, "vni", ntohl (mp->vni));
10455 vat_json_object_add_uint (node, "protocol", ntohl (mp->protocol));
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010456 vat_json_object_add_uint (node, "mcast_sw_if_index",
10457 ntohl (mp->mcast_sw_if_index));
Damjan Marion7cd468a2016-12-19 23:05:39 +010010458 vat_json_object_add_uint (node, "encap_vrf_id", ntohl (mp->encap_vrf_id));
10459 vat_json_object_add_uint (node, "decap_vrf_id", ntohl (mp->decap_vrf_id));
10460 vat_json_object_add_uint (node, "is_ipv6", mp->is_ipv6 ? 1 : 0);
10461}
10462
10463static int
10464api_vxlan_gpe_tunnel_dump (vat_main_t * vam)
10465{
10466 unformat_input_t *i = vam->input;
10467 vl_api_vxlan_gpe_tunnel_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060010468 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010469 u32 sw_if_index;
10470 u8 sw_if_index_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010471 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010472
10473 /* Parse args required to build the message */
10474 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
10475 {
10476 if (unformat (i, "sw_if_index %d", &sw_if_index))
10477 sw_if_index_set = 1;
10478 else
10479 break;
10480 }
10481
10482 if (sw_if_index_set == 0)
10483 {
10484 sw_if_index = ~0;
10485 }
10486
10487 if (!vam->json_output)
10488 {
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010489 print (vam->ofp, "%11s%24s%24s%13s%15s%19s%14s%14s",
Damjan Marion7cd468a2016-12-19 23:05:39 +010010490 "sw_if_index", "local", "remote", "vni",
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080010491 "protocol", "mcast_sw_if_index", "encap_vrf_id", "decap_vrf_id");
Damjan Marion7cd468a2016-12-19 23:05:39 +010010492 }
10493
10494 /* Get list of vxlan-tunnel interfaces */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010495 M (VXLAN_GPE_TUNNEL_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010496
10497 mp->sw_if_index = htonl (sw_if_index);
10498
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010499 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010500
10501 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040010502 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060010503 S (mp_ping);
10504
Jon Loeliger56c7b012017-02-01 12:31:41 -060010505 W (ret);
10506 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010507}
10508
Ole Troan01384fe2017-05-12 11:55:35 +020010509static void vl_api_l2_fib_table_details_t_handler
10510 (vl_api_l2_fib_table_details_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +010010511{
10512 vat_main_t *vam = &vat_main;
10513
10514 print (vam->ofp, "%3" PRIu32 " %U %3" PRIu32
10515 " %d %d %d",
Mohsin Kazmi57938f62017-10-27 21:28:07 +020010516 ntohl (mp->bd_id), format_ethernet_address, mp->mac,
Damjan Marion7cd468a2016-12-19 23:05:39 +010010517 ntohl (mp->sw_if_index), mp->static_mac, mp->filter_mac,
10518 mp->bvi_mac);
10519}
10520
Ole Troan01384fe2017-05-12 11:55:35 +020010521static void vl_api_l2_fib_table_details_t_handler_json
10522 (vl_api_l2_fib_table_details_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +010010523{
10524 vat_main_t *vam = &vat_main;
10525 vat_json_node_t *node = NULL;
10526
10527 if (VAT_JSON_ARRAY != vam->json_tree.type)
10528 {
10529 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
10530 vat_json_init_array (&vam->json_tree);
10531 }
10532 node = vat_json_array_add (&vam->json_tree);
10533
10534 vat_json_init_object (node);
10535 vat_json_object_add_uint (node, "bd_id", ntohl (mp->bd_id));
Mohsin Kazmi57938f62017-10-27 21:28:07 +020010536 vat_json_object_add_bytes (node, "mac", mp->mac, 6);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010537 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
10538 vat_json_object_add_uint (node, "static_mac", mp->static_mac);
10539 vat_json_object_add_uint (node, "filter_mac", mp->filter_mac);
10540 vat_json_object_add_uint (node, "bvi_mac", mp->bvi_mac);
10541}
10542
10543static int
10544api_l2_fib_table_dump (vat_main_t * vam)
10545{
10546 unformat_input_t *i = vam->input;
10547 vl_api_l2_fib_table_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060010548 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010549 u32 bd_id;
10550 u8 bd_id_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010551 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010552
10553 /* Parse args required to build the message */
10554 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
10555 {
10556 if (unformat (i, "bd_id %d", &bd_id))
10557 bd_id_set = 1;
10558 else
10559 break;
10560 }
10561
10562 if (bd_id_set == 0)
10563 {
10564 errmsg ("missing bridge domain");
10565 return -99;
10566 }
10567
10568 print (vam->ofp, "BD-ID Mac Address sw-ndx Static Filter BVI");
10569
10570 /* Get list of l2 fib entries */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010571 M (L2_FIB_TABLE_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010572
10573 mp->bd_id = ntohl (bd_id);
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010574 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010575
10576 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040010577 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060010578 S (mp_ping);
10579
Jon Loeliger56c7b012017-02-01 12:31:41 -060010580 W (ret);
10581 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010582}
10583
10584
10585static int
10586api_interface_name_renumber (vat_main_t * vam)
10587{
10588 unformat_input_t *line_input = vam->input;
10589 vl_api_interface_name_renumber_t *mp;
10590 u32 sw_if_index = ~0;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010591 u32 new_show_dev_instance = ~0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010592 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010593
10594 while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
10595 {
10596 if (unformat (line_input, "%U", api_unformat_sw_if_index, vam,
10597 &sw_if_index))
10598 ;
10599 else if (unformat (line_input, "sw_if_index %d", &sw_if_index))
10600 ;
10601 else if (unformat (line_input, "new_show_dev_instance %d",
10602 &new_show_dev_instance))
10603 ;
10604 else
10605 break;
10606 }
10607
10608 if (sw_if_index == ~0)
10609 {
10610 errmsg ("missing interface name or sw_if_index");
10611 return -99;
10612 }
10613
10614 if (new_show_dev_instance == ~0)
10615 {
10616 errmsg ("missing new_show_dev_instance");
10617 return -99;
10618 }
10619
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010620 M (INTERFACE_NAME_RENUMBER, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010621
10622 mp->sw_if_index = ntohl (sw_if_index);
10623 mp->new_show_dev_instance = ntohl (new_show_dev_instance);
10624
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010625 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060010626 W (ret);
10627 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010628}
10629
10630static int
John Lo8d00fff2017-08-03 00:35:36 -040010631api_want_l2_macs_events (vat_main_t * vam)
10632{
10633 unformat_input_t *line_input = vam->input;
10634 vl_api_want_l2_macs_events_t *mp;
10635 u8 enable_disable = 1;
10636 u32 scan_delay = 0;
10637 u32 max_macs_in_event = 0;
10638 u32 learn_limit = 0;
10639 int ret;
10640
10641 while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
10642 {
10643 if (unformat (line_input, "learn-limit %d", &learn_limit))
10644 ;
10645 else if (unformat (line_input, "scan-delay %d", &scan_delay))
10646 ;
10647 else if (unformat (line_input, "max-entries %d", &max_macs_in_event))
10648 ;
10649 else if (unformat (line_input, "disable"))
10650 enable_disable = 0;
10651 else
10652 break;
10653 }
10654
10655 M (WANT_L2_MACS_EVENTS, mp);
10656 mp->enable_disable = enable_disable;
10657 mp->pid = htonl (getpid ());
10658 mp->learn_limit = htonl (learn_limit);
10659 mp->scan_delay = (u8) scan_delay;
10660 mp->max_macs_in_event = (u8) (max_macs_in_event / 10);
10661 S (mp);
10662 W (ret);
10663 return ret;
10664}
10665
10666static int
Damjan Marion7cd468a2016-12-19 23:05:39 +010010667api_input_acl_set_interface (vat_main_t * vam)
10668{
10669 unformat_input_t *i = vam->input;
10670 vl_api_input_acl_set_interface_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010671 u32 sw_if_index;
10672 int sw_if_index_set;
10673 u32 ip4_table_index = ~0;
10674 u32 ip6_table_index = ~0;
10675 u32 l2_table_index = ~0;
10676 u8 is_add = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010677 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010678
10679 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
10680 {
10681 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
10682 sw_if_index_set = 1;
10683 else if (unformat (i, "sw_if_index %d", &sw_if_index))
10684 sw_if_index_set = 1;
10685 else if (unformat (i, "del"))
10686 is_add = 0;
10687 else if (unformat (i, "ip4-table %d", &ip4_table_index))
10688 ;
10689 else if (unformat (i, "ip6-table %d", &ip6_table_index))
10690 ;
10691 else if (unformat (i, "l2-table %d", &l2_table_index))
10692 ;
10693 else
10694 {
10695 clib_warning ("parse error '%U'", format_unformat_error, i);
10696 return -99;
10697 }
10698 }
10699
10700 if (sw_if_index_set == 0)
10701 {
10702 errmsg ("missing interface name or sw_if_index");
10703 return -99;
10704 }
10705
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010706 M (INPUT_ACL_SET_INTERFACE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010707
10708 mp->sw_if_index = ntohl (sw_if_index);
10709 mp->ip4_table_index = ntohl (ip4_table_index);
10710 mp->ip6_table_index = ntohl (ip6_table_index);
10711 mp->l2_table_index = ntohl (l2_table_index);
10712 mp->is_add = is_add;
10713
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010714 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060010715 W (ret);
10716 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010717}
10718
10719static int
Andrew Yourtchenko815d7d52018-02-07 11:37:02 +010010720api_output_acl_set_interface (vat_main_t * vam)
10721{
10722 unformat_input_t *i = vam->input;
10723 vl_api_output_acl_set_interface_t *mp;
10724 u32 sw_if_index;
10725 int sw_if_index_set;
10726 u32 ip4_table_index = ~0;
10727 u32 ip6_table_index = ~0;
10728 u32 l2_table_index = ~0;
10729 u8 is_add = 1;
10730 int ret;
10731
10732 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
10733 {
10734 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
10735 sw_if_index_set = 1;
10736 else if (unformat (i, "sw_if_index %d", &sw_if_index))
10737 sw_if_index_set = 1;
10738 else if (unformat (i, "del"))
10739 is_add = 0;
10740 else if (unformat (i, "ip4-table %d", &ip4_table_index))
10741 ;
10742 else if (unformat (i, "ip6-table %d", &ip6_table_index))
10743 ;
10744 else if (unformat (i, "l2-table %d", &l2_table_index))
10745 ;
10746 else
10747 {
10748 clib_warning ("parse error '%U'", format_unformat_error, i);
10749 return -99;
10750 }
10751 }
10752
10753 if (sw_if_index_set == 0)
10754 {
10755 errmsg ("missing interface name or sw_if_index");
10756 return -99;
10757 }
10758
10759 M (OUTPUT_ACL_SET_INTERFACE, mp);
10760
10761 mp->sw_if_index = ntohl (sw_if_index);
10762 mp->ip4_table_index = ntohl (ip4_table_index);
10763 mp->ip6_table_index = ntohl (ip6_table_index);
10764 mp->l2_table_index = ntohl (l2_table_index);
10765 mp->is_add = is_add;
10766
10767 S (mp);
10768 W (ret);
10769 return ret;
10770}
10771
10772static int
Damjan Marion7cd468a2016-12-19 23:05:39 +010010773api_ip_address_dump (vat_main_t * vam)
10774{
10775 unformat_input_t *i = vam->input;
10776 vl_api_ip_address_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060010777 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010778 u32 sw_if_index = ~0;
10779 u8 sw_if_index_set = 0;
10780 u8 ipv4_set = 0;
10781 u8 ipv6_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010782 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010783
10784 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
10785 {
10786 if (unformat (i, "sw_if_index %d", &sw_if_index))
10787 sw_if_index_set = 1;
10788 else
10789 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
10790 sw_if_index_set = 1;
10791 else if (unformat (i, "ipv4"))
10792 ipv4_set = 1;
10793 else if (unformat (i, "ipv6"))
10794 ipv6_set = 1;
10795 else
10796 break;
10797 }
10798
10799 if (ipv4_set && ipv6_set)
10800 {
10801 errmsg ("ipv4 and ipv6 flags cannot be both set");
10802 return -99;
10803 }
10804
10805 if ((!ipv4_set) && (!ipv6_set))
10806 {
10807 errmsg ("no ipv4 nor ipv6 flag set");
10808 return -99;
10809 }
10810
10811 if (sw_if_index_set == 0)
10812 {
10813 errmsg ("missing interface name or sw_if_index");
10814 return -99;
10815 }
10816
10817 vam->current_sw_if_index = sw_if_index;
10818 vam->is_ipv6 = ipv6_set;
10819
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010820 M (IP_ADDRESS_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010821 mp->sw_if_index = ntohl (sw_if_index);
10822 mp->is_ipv6 = ipv6_set;
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010823 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010824
10825 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040010826 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060010827 S (mp_ping);
10828
Jon Loeliger56c7b012017-02-01 12:31:41 -060010829 W (ret);
10830 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010831}
10832
10833static int
10834api_ip_dump (vat_main_t * vam)
10835{
10836 vl_api_ip_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060010837 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010838 unformat_input_t *in = vam->input;
10839 int ipv4_set = 0;
10840 int ipv6_set = 0;
10841 int is_ipv6;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010842 int i;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010843 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010844
10845 while (unformat_check_input (in) != UNFORMAT_END_OF_INPUT)
10846 {
10847 if (unformat (in, "ipv4"))
10848 ipv4_set = 1;
10849 else if (unformat (in, "ipv6"))
10850 ipv6_set = 1;
10851 else
10852 break;
10853 }
10854
10855 if (ipv4_set && ipv6_set)
10856 {
10857 errmsg ("ipv4 and ipv6 flags cannot be both set");
10858 return -99;
10859 }
10860
10861 if ((!ipv4_set) && (!ipv6_set))
10862 {
10863 errmsg ("no ipv4 nor ipv6 flag set");
10864 return -99;
10865 }
10866
10867 is_ipv6 = ipv6_set;
10868 vam->is_ipv6 = is_ipv6;
10869
10870 /* free old data */
10871 for (i = 0; i < vec_len (vam->ip_details_by_sw_if_index[is_ipv6]); i++)
10872 {
10873 vec_free (vam->ip_details_by_sw_if_index[is_ipv6][i].addr);
10874 }
10875 vec_free (vam->ip_details_by_sw_if_index[is_ipv6]);
10876
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010877 M (IP_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010878 mp->is_ipv6 = ipv6_set;
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010879 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010880
10881 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040010882 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060010883 S (mp_ping);
10884
Jon Loeliger56c7b012017-02-01 12:31:41 -060010885 W (ret);
10886 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010887}
10888
10889static int
10890api_ipsec_spd_add_del (vat_main_t * vam)
10891{
10892 unformat_input_t *i = vam->input;
10893 vl_api_ipsec_spd_add_del_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010894 u32 spd_id = ~0;
10895 u8 is_add = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010896 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010897
10898 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
10899 {
10900 if (unformat (i, "spd_id %d", &spd_id))
10901 ;
10902 else if (unformat (i, "del"))
10903 is_add = 0;
10904 else
10905 {
10906 clib_warning ("parse error '%U'", format_unformat_error, i);
10907 return -99;
10908 }
10909 }
10910 if (spd_id == ~0)
10911 {
10912 errmsg ("spd_id must be set");
10913 return -99;
10914 }
10915
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010916 M (IPSEC_SPD_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010917
10918 mp->spd_id = ntohl (spd_id);
10919 mp->is_add = is_add;
10920
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010921 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060010922 W (ret);
10923 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010924}
10925
10926static int
10927api_ipsec_interface_add_del_spd (vat_main_t * vam)
10928{
10929 unformat_input_t *i = vam->input;
10930 vl_api_ipsec_interface_add_del_spd_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010931 u32 sw_if_index;
10932 u8 sw_if_index_set = 0;
10933 u32 spd_id = (u32) ~ 0;
10934 u8 is_add = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060010935 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010936
10937 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
10938 {
10939 if (unformat (i, "del"))
10940 is_add = 0;
10941 else if (unformat (i, "spd_id %d", &spd_id))
10942 ;
10943 else
10944 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
10945 sw_if_index_set = 1;
10946 else if (unformat (i, "sw_if_index %d", &sw_if_index))
10947 sw_if_index_set = 1;
10948 else
10949 {
10950 clib_warning ("parse error '%U'", format_unformat_error, i);
10951 return -99;
10952 }
10953
10954 }
10955
10956 if (spd_id == (u32) ~ 0)
10957 {
10958 errmsg ("spd_id must be set");
10959 return -99;
10960 }
10961
10962 if (sw_if_index_set == 0)
10963 {
10964 errmsg ("missing interface name or sw_if_index");
10965 return -99;
10966 }
10967
Jon Loeliger8a2aea32017-01-31 13:19:40 -060010968 M (IPSEC_INTERFACE_ADD_DEL_SPD, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010010969
10970 mp->spd_id = ntohl (spd_id);
10971 mp->sw_if_index = ntohl (sw_if_index);
10972 mp->is_add = is_add;
10973
Jon Loeliger7bc770c2017-01-31 14:03:33 -060010974 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060010975 W (ret);
10976 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010977}
10978
10979static int
Neale Ranns17dcec02019-01-09 21:22:20 -080010980api_ipsec_spd_entry_add_del (vat_main_t * vam)
Damjan Marion7cd468a2016-12-19 23:05:39 +010010981{
10982 unformat_input_t *i = vam->input;
Neale Ranns17dcec02019-01-09 21:22:20 -080010983 vl_api_ipsec_spd_entry_add_del_t *mp;
Benoît Ganne49ee6842019-04-30 11:50:46 +020010984 u8 is_add = 1, is_outbound = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010985 u32 spd_id = 0, sa_id = 0, protocol = 0, policy = 0;
10986 i32 priority = 0;
10987 u32 rport_start = 0, rport_stop = (u32) ~ 0;
10988 u32 lport_start = 0, lport_stop = (u32) ~ 0;
Neale Ranns17dcec02019-01-09 21:22:20 -080010989 vl_api_address_t laddr_start = { }, laddr_stop =
10990 {
10991 }, raddr_start =
10992 {
10993 }, raddr_stop =
10994 {
10995 };
Jon Loeliger56c7b012017-02-01 12:31:41 -060010996 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010010997
Damjan Marion7cd468a2016-12-19 23:05:39 +010010998 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
10999 {
11000 if (unformat (i, "del"))
11001 is_add = 0;
11002 if (unformat (i, "outbound"))
11003 is_outbound = 1;
11004 if (unformat (i, "inbound"))
11005 is_outbound = 0;
11006 else if (unformat (i, "spd_id %d", &spd_id))
11007 ;
11008 else if (unformat (i, "sa_id %d", &sa_id))
11009 ;
11010 else if (unformat (i, "priority %d", &priority))
11011 ;
11012 else if (unformat (i, "protocol %d", &protocol))
11013 ;
11014 else if (unformat (i, "lport_start %d", &lport_start))
11015 ;
11016 else if (unformat (i, "lport_stop %d", &lport_stop))
11017 ;
11018 else if (unformat (i, "rport_start %d", &rport_start))
11019 ;
11020 else if (unformat (i, "rport_stop %d", &rport_stop))
11021 ;
Neale Ranns17dcec02019-01-09 21:22:20 -080011022 else if (unformat (i, "laddr_start %U",
11023 unformat_vl_api_address, &laddr_start))
Benoît Ganne49ee6842019-04-30 11:50:46 +020011024 ;
Neale Ranns17dcec02019-01-09 21:22:20 -080011025 else if (unformat (i, "laddr_stop %U", unformat_vl_api_address,
11026 &laddr_stop))
Benoît Ganne49ee6842019-04-30 11:50:46 +020011027 ;
Neale Ranns17dcec02019-01-09 21:22:20 -080011028 else if (unformat (i, "raddr_start %U", unformat_vl_api_address,
11029 &raddr_start))
Benoît Ganne49ee6842019-04-30 11:50:46 +020011030 ;
Neale Ranns17dcec02019-01-09 21:22:20 -080011031 else if (unformat (i, "raddr_stop %U", unformat_vl_api_address,
11032 &raddr_stop))
Benoît Ganne49ee6842019-04-30 11:50:46 +020011033 ;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011034 else
11035 if (unformat (i, "action %U", unformat_ipsec_policy_action, &policy))
11036 {
11037 if (policy == IPSEC_POLICY_ACTION_RESOLVE)
11038 {
11039 clib_warning ("unsupported action: 'resolve'");
11040 return -99;
11041 }
11042 }
11043 else
11044 {
11045 clib_warning ("parse error '%U'", format_unformat_error, i);
11046 return -99;
11047 }
11048
11049 }
11050
Neale Ranns17dcec02019-01-09 21:22:20 -080011051 M (IPSEC_SPD_ENTRY_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011052
Damjan Marion7cd468a2016-12-19 23:05:39 +010011053 mp->is_add = is_add;
Neale Ranns17dcec02019-01-09 21:22:20 -080011054
11055 mp->entry.spd_id = ntohl (spd_id);
11056 mp->entry.priority = ntohl (priority);
11057 mp->entry.is_outbound = is_outbound;
11058
11059 clib_memcpy (&mp->entry.remote_address_start, &raddr_start,
11060 sizeof (vl_api_address_t));
11061 clib_memcpy (&mp->entry.remote_address_stop, &raddr_stop,
11062 sizeof (vl_api_address_t));
11063 clib_memcpy (&mp->entry.local_address_start, &laddr_start,
11064 sizeof (vl_api_address_t));
11065 clib_memcpy (&mp->entry.local_address_stop, &laddr_stop,
11066 sizeof (vl_api_address_t));
11067
11068 mp->entry.protocol = (u8) protocol;
11069 mp->entry.local_port_start = ntohs ((u16) lport_start);
11070 mp->entry.local_port_stop = ntohs ((u16) lport_stop);
11071 mp->entry.remote_port_start = ntohs ((u16) rport_start);
11072 mp->entry.remote_port_stop = ntohs ((u16) rport_stop);
11073 mp->entry.policy = (u8) policy;
11074 mp->entry.sa_id = ntohl (sa_id);
Neale Ranns17dcec02019-01-09 21:22:20 -080011075
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011076 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060011077 W (ret);
11078 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011079}
11080
11081static int
Neale Ranns17dcec02019-01-09 21:22:20 -080011082api_ipsec_sad_entry_add_del (vat_main_t * vam)
Damjan Marion7cd468a2016-12-19 23:05:39 +010011083{
11084 unformat_input_t *i = vam->input;
Neale Ranns17dcec02019-01-09 21:22:20 -080011085 vl_api_ipsec_sad_entry_add_del_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011086 u32 sad_id = 0, spi = 0;
11087 u8 *ck = 0, *ik = 0;
11088 u8 is_add = 1;
11089
Neale Ranns17dcec02019-01-09 21:22:20 -080011090 vl_api_ipsec_crypto_alg_t crypto_alg = IPSEC_API_CRYPTO_ALG_NONE;
11091 vl_api_ipsec_integ_alg_t integ_alg = IPSEC_API_INTEG_ALG_NONE;
11092 vl_api_ipsec_sad_flags_t flags = IPSEC_API_SAD_FLAG_NONE;
11093 vl_api_ipsec_proto_t protocol = IPSEC_API_PROTO_AH;
11094 vl_api_address_t tun_src, tun_dst;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011095 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011096
11097 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
11098 {
11099 if (unformat (i, "del"))
11100 is_add = 0;
11101 else if (unformat (i, "sad_id %d", &sad_id))
11102 ;
11103 else if (unformat (i, "spi %d", &spi))
11104 ;
11105 else if (unformat (i, "esp"))
Neale Ranns17dcec02019-01-09 21:22:20 -080011106 protocol = IPSEC_API_PROTO_ESP;
11107 else
11108 if (unformat (i, "tunnel_src %U", unformat_vl_api_address, &tun_src))
Damjan Marion7cd468a2016-12-19 23:05:39 +010011109 {
Neale Ranns17dcec02019-01-09 21:22:20 -080011110 flags |= IPSEC_API_SAD_FLAG_IS_TUNNEL;
11111 if (ADDRESS_IP6 == tun_src.af)
11112 flags |= IPSEC_API_SAD_FLAG_IS_TUNNEL_V6;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011113 }
11114 else
Neale Ranns17dcec02019-01-09 21:22:20 -080011115 if (unformat (i, "tunnel_dst %U", unformat_vl_api_address, &tun_dst))
Damjan Marion7cd468a2016-12-19 23:05:39 +010011116 {
Neale Ranns17dcec02019-01-09 21:22:20 -080011117 flags |= IPSEC_API_SAD_FLAG_IS_TUNNEL;
11118 if (ADDRESS_IP6 == tun_src.af)
11119 flags |= IPSEC_API_SAD_FLAG_IS_TUNNEL_V6;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011120 }
Neale Ranns17dcec02019-01-09 21:22:20 -080011121 else
11122 if (unformat (i, "crypto_alg %U",
11123 unformat_ipsec_api_crypto_alg, &crypto_alg))
11124 ;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011125 else if (unformat (i, "crypto_key %U", unformat_hex_string, &ck))
11126 ;
Neale Ranns17dcec02019-01-09 21:22:20 -080011127 else if (unformat (i, "integ_alg %U",
11128 unformat_ipsec_api_integ_alg, &integ_alg))
11129 ;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011130 else if (unformat (i, "integ_key %U", unformat_hex_string, &ik))
11131 ;
11132 else
11133 {
11134 clib_warning ("parse error '%U'", format_unformat_error, i);
11135 return -99;
11136 }
11137
11138 }
11139
Neale Ranns17dcec02019-01-09 21:22:20 -080011140 M (IPSEC_SAD_ENTRY_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011141
Damjan Marion7cd468a2016-12-19 23:05:39 +010011142 mp->is_add = is_add;
Neale Ranns17dcec02019-01-09 21:22:20 -080011143 mp->entry.sad_id = ntohl (sad_id);
11144 mp->entry.protocol = protocol;
11145 mp->entry.spi = ntohl (spi);
11146 mp->entry.flags = flags;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011147
Neale Ranns17dcec02019-01-09 21:22:20 -080011148 mp->entry.crypto_algorithm = crypto_alg;
11149 mp->entry.integrity_algorithm = integ_alg;
11150 mp->entry.crypto_key.length = vec_len (ck);
11151 mp->entry.integrity_key.length = vec_len (ik);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011152
Neale Ranns17dcec02019-01-09 21:22:20 -080011153 if (mp->entry.crypto_key.length > sizeof (mp->entry.crypto_key.data))
11154 mp->entry.crypto_key.length = sizeof (mp->entry.crypto_key.data);
11155
11156 if (mp->entry.integrity_key.length > sizeof (mp->entry.integrity_key.data))
11157 mp->entry.integrity_key.length = sizeof (mp->entry.integrity_key.data);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011158
11159 if (ck)
Neale Ranns17dcec02019-01-09 21:22:20 -080011160 clib_memcpy (mp->entry.crypto_key.data, ck, mp->entry.crypto_key.length);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011161 if (ik)
Neale Ranns17dcec02019-01-09 21:22:20 -080011162 clib_memcpy (mp->entry.integrity_key.data, ik,
11163 mp->entry.integrity_key.length);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011164
Neale Ranns17dcec02019-01-09 21:22:20 -080011165 if (flags & IPSEC_API_SAD_FLAG_IS_TUNNEL)
Damjan Marion7cd468a2016-12-19 23:05:39 +010011166 {
Neale Ranns17dcec02019-01-09 21:22:20 -080011167 clib_memcpy (&mp->entry.tunnel_src, &tun_src,
11168 sizeof (mp->entry.tunnel_src));
11169 clib_memcpy (&mp->entry.tunnel_dst, &tun_dst,
11170 sizeof (mp->entry.tunnel_dst));
Damjan Marion7cd468a2016-12-19 23:05:39 +010011171 }
11172
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011173 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060011174 W (ret);
11175 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011176}
11177
Matthew Smith28029532017-09-26 13:33:44 -050011178static void
11179vl_api_ipsec_sa_details_t_handler (vl_api_ipsec_sa_details_t * mp)
11180{
11181 vat_main_t *vam = &vat_main;
11182
11183 print (vam->ofp, "sa_id %u sw_if_index %u spi %u proto %u crypto_alg %u "
Neale Ranns8d7c5022019-02-06 01:41:05 -080011184 "crypto_key %U integ_alg %u integ_key %U flags %x "
Matthew Smith28029532017-09-26 13:33:44 -050011185 "tunnel_src_addr %U tunnel_dst_addr %U "
11186 "salt %u seq_outbound %lu last_seq_inbound %lu "
Matthew Smith48d32b42020-04-02 07:45:49 -050011187 "replay_window %lu stat_index %u\n",
Neale Ranns8d7c5022019-02-06 01:41:05 -080011188 ntohl (mp->entry.sad_id),
11189 ntohl (mp->sw_if_index),
11190 ntohl (mp->entry.spi),
11191 ntohl (mp->entry.protocol),
11192 ntohl (mp->entry.crypto_algorithm),
11193 format_hex_bytes, mp->entry.crypto_key.data,
11194 mp->entry.crypto_key.length, ntohl (mp->entry.integrity_algorithm),
11195 format_hex_bytes, mp->entry.integrity_key.data,
11196 mp->entry.integrity_key.length, ntohl (mp->entry.flags),
11197 format_vl_api_address, &mp->entry.tunnel_src, format_vl_api_address,
11198 &mp->entry.tunnel_dst, ntohl (mp->salt),
Matthew Smith28029532017-09-26 13:33:44 -050011199 clib_net_to_host_u64 (mp->seq_outbound),
11200 clib_net_to_host_u64 (mp->last_seq_inbound),
Matthew Smith48d32b42020-04-02 07:45:49 -050011201 clib_net_to_host_u64 (mp->replay_window), ntohl (mp->stat_index));
Matthew Smith28029532017-09-26 13:33:44 -050011202}
11203
11204#define vl_api_ipsec_sa_details_t_endian vl_noop_handler
11205#define vl_api_ipsec_sa_details_t_print vl_noop_handler
11206
11207static void vl_api_ipsec_sa_details_t_handler_json
11208 (vl_api_ipsec_sa_details_t * mp)
11209{
11210 vat_main_t *vam = &vat_main;
11211 vat_json_node_t *node = NULL;
Neale Ranns8d7c5022019-02-06 01:41:05 -080011212 vl_api_ipsec_sad_flags_t flags;
Matthew Smith28029532017-09-26 13:33:44 -050011213
11214 if (VAT_JSON_ARRAY != vam->json_tree.type)
11215 {
11216 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
11217 vat_json_init_array (&vam->json_tree);
11218 }
11219 node = vat_json_array_add (&vam->json_tree);
11220
11221 vat_json_init_object (node);
Neale Ranns8d7c5022019-02-06 01:41:05 -080011222 vat_json_object_add_uint (node, "sa_id", ntohl (mp->entry.sad_id));
Matthew Smith28029532017-09-26 13:33:44 -050011223 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
Neale Ranns8d7c5022019-02-06 01:41:05 -080011224 vat_json_object_add_uint (node, "spi", ntohl (mp->entry.spi));
11225 vat_json_object_add_uint (node, "proto", ntohl (mp->entry.protocol));
11226 vat_json_object_add_uint (node, "crypto_alg",
11227 ntohl (mp->entry.crypto_algorithm));
11228 vat_json_object_add_uint (node, "integ_alg",
11229 ntohl (mp->entry.integrity_algorithm));
11230 flags = ntohl (mp->entry.flags);
11231 vat_json_object_add_uint (node, "use_esn",
Damjan Marion1e3aa5e2019-03-28 10:58:59 +010011232 ! !(flags & IPSEC_API_SAD_FLAG_USE_ESN));
Neale Ranns8d7c5022019-02-06 01:41:05 -080011233 vat_json_object_add_uint (node, "use_anti_replay",
11234 ! !(flags & IPSEC_API_SAD_FLAG_USE_ANTI_REPLAY));
11235 vat_json_object_add_uint (node, "is_tunnel",
11236 ! !(flags & IPSEC_API_SAD_FLAG_IS_TUNNEL));
11237 vat_json_object_add_uint (node, "is_tunnel_ip6",
11238 ! !(flags & IPSEC_API_SAD_FLAG_IS_TUNNEL_V6));
11239 vat_json_object_add_uint (node, "udp_encap",
11240 ! !(flags & IPSEC_API_SAD_FLAG_UDP_ENCAP));
11241 vat_json_object_add_bytes (node, "crypto_key", mp->entry.crypto_key.data,
11242 mp->entry.crypto_key.length);
11243 vat_json_object_add_bytes (node, "integ_key", mp->entry.integrity_key.data,
11244 mp->entry.integrity_key.length);
Neale Ranns5a8844b2019-04-16 07:15:35 +000011245 vat_json_object_add_address (node, "src", &mp->entry.tunnel_src);
11246 vat_json_object_add_address (node, "dst", &mp->entry.tunnel_dst);
Matthew Smith28029532017-09-26 13:33:44 -050011247 vat_json_object_add_uint (node, "replay_window",
11248 clib_net_to_host_u64 (mp->replay_window));
Matthew Smith48d32b42020-04-02 07:45:49 -050011249 vat_json_object_add_uint (node, "stat_index", ntohl (mp->stat_index));
Matthew Smith28029532017-09-26 13:33:44 -050011250}
11251
11252static int
11253api_ipsec_sa_dump (vat_main_t * vam)
11254{
11255 unformat_input_t *i = vam->input;
11256 vl_api_ipsec_sa_dump_t *mp;
11257 vl_api_control_ping_t *mp_ping;
11258 u32 sa_id = ~0;
11259 int ret;
11260
11261 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
11262 {
11263 if (unformat (i, "sa_id %d", &sa_id))
11264 ;
11265 else
11266 {
11267 clib_warning ("parse error '%U'", format_unformat_error, i);
11268 return -99;
11269 }
11270 }
11271
11272 M (IPSEC_SA_DUMP, mp);
11273
11274 mp->sa_id = ntohl (sa_id);
11275
11276 S (mp);
11277
11278 /* Use a control ping for synchronization */
11279 M (CONTROL_PING, mp_ping);
11280 S (mp_ping);
11281
11282 W (ret);
11283 return ret;
11284}
11285
Matthew Smithb0972cb2017-05-02 16:20:41 -050011286static int
Damjan Marion7cd468a2016-12-19 23:05:39 +010011287api_get_first_msg_id (vat_main_t * vam)
11288{
11289 vl_api_get_first_msg_id_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011290 unformat_input_t *i = vam->input;
11291 u8 *name;
11292 u8 name_set = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011293 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011294
11295 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
11296 {
11297 if (unformat (i, "client %s", &name))
11298 name_set = 1;
11299 else
11300 break;
11301 }
11302
11303 if (name_set == 0)
11304 {
11305 errmsg ("missing client name");
11306 return -99;
11307 }
11308 vec_add1 (name, 0);
11309
11310 if (vec_len (name) > 63)
11311 {
11312 errmsg ("client name too long");
11313 return -99;
11314 }
11315
Jon Loeliger8a2aea32017-01-31 13:19:40 -060011316 M (GET_FIRST_MSG_ID, mp);
Ole Troan7adaa222019-08-27 15:05:27 +020011317 clib_memcpy (mp->name, name, vec_len (name));
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011318 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060011319 W (ret);
11320 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011321}
11322
11323static int
11324api_cop_interface_enable_disable (vat_main_t * vam)
11325{
11326 unformat_input_t *line_input = vam->input;
11327 vl_api_cop_interface_enable_disable_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011328 u32 sw_if_index = ~0;
11329 u8 enable_disable = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011330 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011331
11332 while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
11333 {
11334 if (unformat (line_input, "disable"))
11335 enable_disable = 0;
11336 if (unformat (line_input, "enable"))
11337 enable_disable = 1;
11338 else if (unformat (line_input, "%U", api_unformat_sw_if_index,
11339 vam, &sw_if_index))
11340 ;
11341 else if (unformat (line_input, "sw_if_index %d", &sw_if_index))
11342 ;
11343 else
11344 break;
11345 }
11346
11347 if (sw_if_index == ~0)
11348 {
11349 errmsg ("missing interface name or sw_if_index");
11350 return -99;
11351 }
11352
11353 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060011354 M (COP_INTERFACE_ENABLE_DISABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011355 mp->sw_if_index = ntohl (sw_if_index);
11356 mp->enable_disable = enable_disable;
11357
11358 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011359 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011360 /* Wait for the reply */
Jon Loeliger56c7b012017-02-01 12:31:41 -060011361 W (ret);
11362 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011363}
11364
11365static int
11366api_cop_whitelist_enable_disable (vat_main_t * vam)
11367{
11368 unformat_input_t *line_input = vam->input;
11369 vl_api_cop_whitelist_enable_disable_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011370 u32 sw_if_index = ~0;
11371 u8 ip4 = 0, ip6 = 0, default_cop = 0;
11372 u32 fib_id = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011373 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011374
11375 while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
11376 {
11377 if (unformat (line_input, "ip4"))
11378 ip4 = 1;
11379 else if (unformat (line_input, "ip6"))
11380 ip6 = 1;
11381 else if (unformat (line_input, "default"))
11382 default_cop = 1;
11383 else if (unformat (line_input, "%U", api_unformat_sw_if_index,
11384 vam, &sw_if_index))
11385 ;
11386 else if (unformat (line_input, "sw_if_index %d", &sw_if_index))
11387 ;
11388 else if (unformat (line_input, "fib-id %d", &fib_id))
11389 ;
11390 else
11391 break;
11392 }
11393
11394 if (sw_if_index == ~0)
11395 {
11396 errmsg ("missing interface name or sw_if_index");
11397 return -99;
11398 }
11399
11400 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060011401 M (COP_WHITELIST_ENABLE_DISABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011402 mp->sw_if_index = ntohl (sw_if_index);
11403 mp->fib_id = ntohl (fib_id);
11404 mp->ip4 = ip4;
11405 mp->ip6 = ip6;
11406 mp->default_cop = default_cop;
11407
11408 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011409 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011410 /* Wait for the reply */
Jon Loeliger56c7b012017-02-01 12:31:41 -060011411 W (ret);
11412 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011413}
11414
11415static int
11416api_get_node_graph (vat_main_t * vam)
11417{
11418 vl_api_get_node_graph_t *mp;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011419 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011420
Jon Loeliger8a2aea32017-01-31 13:19:40 -060011421 M (GET_NODE_GRAPH, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011422
11423 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011424 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011425 /* Wait for the reply */
Jon Loeliger56c7b012017-02-01 12:31:41 -060011426 W (ret);
11427 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011428}
11429
Damjan Marion7cd468a2016-12-19 23:05:39 +010011430static int
11431api_af_packet_create (vat_main_t * vam)
11432{
11433 unformat_input_t *i = vam->input;
11434 vl_api_af_packet_create_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011435 u8 *host_if_name = 0;
11436 u8 hw_addr[6];
11437 u8 random_hw_addr = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011438 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011439
Dave Barachb7b92992018-10-17 10:38:51 -040011440 clib_memset (hw_addr, 0, sizeof (hw_addr));
Damjan Marion7cd468a2016-12-19 23:05:39 +010011441
11442 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
11443 {
11444 if (unformat (i, "name %s", &host_if_name))
11445 vec_add1 (host_if_name, 0);
11446 else if (unformat (i, "hw_addr %U", unformat_ethernet_address, hw_addr))
11447 random_hw_addr = 0;
11448 else
11449 break;
11450 }
11451
11452 if (!vec_len (host_if_name))
11453 {
11454 errmsg ("host-interface name must be specified");
11455 return -99;
11456 }
11457
11458 if (vec_len (host_if_name) > 64)
11459 {
11460 errmsg ("host-interface name too long");
11461 return -99;
11462 }
11463
Jon Loeliger8a2aea32017-01-31 13:19:40 -060011464 M (AF_PACKET_CREATE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011465
11466 clib_memcpy (mp->host_if_name, host_if_name, vec_len (host_if_name));
11467 clib_memcpy (mp->hw_addr, hw_addr, 6);
11468 mp->use_random_hw_addr = random_hw_addr;
11469 vec_free (host_if_name);
11470
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011471 S (mp);
Dave Baracha1a093d2017-03-02 13:13:23 -050011472
11473 /* *INDENT-OFF* */
11474 W2 (ret,
11475 ({
11476 if (ret == 0)
11477 fprintf (vam->ofp ? vam->ofp : stderr,
11478 " new sw_if_index = %d\n", vam->sw_if_index);
11479 }));
11480 /* *INDENT-ON* */
Jon Loeliger56c7b012017-02-01 12:31:41 -060011481 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011482}
11483
11484static int
11485api_af_packet_delete (vat_main_t * vam)
11486{
11487 unformat_input_t *i = vam->input;
11488 vl_api_af_packet_delete_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011489 u8 *host_if_name = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011490 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011491
11492 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
11493 {
11494 if (unformat (i, "name %s", &host_if_name))
11495 vec_add1 (host_if_name, 0);
11496 else
11497 break;
11498 }
11499
11500 if (!vec_len (host_if_name))
11501 {
11502 errmsg ("host-interface name must be specified");
11503 return -99;
11504 }
11505
11506 if (vec_len (host_if_name) > 64)
11507 {
11508 errmsg ("host-interface name too long");
11509 return -99;
11510 }
11511
Jon Loeliger8a2aea32017-01-31 13:19:40 -060011512 M (AF_PACKET_DELETE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011513
11514 clib_memcpy (mp->host_if_name, host_if_name, vec_len (host_if_name));
11515 vec_free (host_if_name);
11516
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011517 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060011518 W (ret);
11519 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011520}
11521
Mohsin Kazmi04e0bb22018-05-28 18:55:37 +020011522static void vl_api_af_packet_details_t_handler
11523 (vl_api_af_packet_details_t * mp)
11524{
11525 vat_main_t *vam = &vat_main;
11526
11527 print (vam->ofp, "%-16s %d",
11528 mp->host_if_name, clib_net_to_host_u32 (mp->sw_if_index));
11529}
11530
11531static void vl_api_af_packet_details_t_handler_json
11532 (vl_api_af_packet_details_t * mp)
11533{
11534 vat_main_t *vam = &vat_main;
11535 vat_json_node_t *node = NULL;
11536
11537 if (VAT_JSON_ARRAY != vam->json_tree.type)
11538 {
11539 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
11540 vat_json_init_array (&vam->json_tree);
11541 }
11542 node = vat_json_array_add (&vam->json_tree);
11543
11544 vat_json_init_object (node);
11545 vat_json_object_add_uint (node, "sw_if_index", ntohl (mp->sw_if_index));
11546 vat_json_object_add_string_copy (node, "dev_name", mp->host_if_name);
11547}
11548
11549static int
11550api_af_packet_dump (vat_main_t * vam)
11551{
11552 vl_api_af_packet_dump_t *mp;
11553 vl_api_control_ping_t *mp_ping;
11554 int ret;
11555
11556 print (vam->ofp, "\n%-16s %s", "dev_name", "sw_if_index");
11557 /* Get list of tap interfaces */
11558 M (AF_PACKET_DUMP, mp);
11559 S (mp);
11560
11561 /* Use a control ping for synchronization */
11562 MPING (CONTROL_PING, mp_ping);
11563 S (mp_ping);
11564
11565 W (ret);
11566 return ret;
11567}
11568
Damjan Marion7cd468a2016-12-19 23:05:39 +010011569static int
11570api_policer_add_del (vat_main_t * vam)
11571{
11572 unformat_input_t *i = vam->input;
11573 vl_api_policer_add_del_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011574 u8 is_add = 1;
11575 u8 *name = 0;
11576 u32 cir = 0;
11577 u32 eir = 0;
11578 u64 cb = 0;
11579 u64 eb = 0;
11580 u8 rate_type = 0;
11581 u8 round_type = 0;
11582 u8 type = 0;
11583 u8 color_aware = 0;
Brian Russellc5299ff2021-02-09 10:16:58 +000011584 qos_pol_action_params_st conform_action, exceed_action, violate_action;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011585 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011586
Brian Russellc5299ff2021-02-09 10:16:58 +000011587 conform_action.action_type = QOS_ACTION_TRANSMIT;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011588 conform_action.dscp = 0;
Brian Russellc5299ff2021-02-09 10:16:58 +000011589 exceed_action.action_type = QOS_ACTION_MARK_AND_TRANSMIT;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011590 exceed_action.dscp = 0;
Brian Russellc5299ff2021-02-09 10:16:58 +000011591 violate_action.action_type = QOS_ACTION_DROP;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011592 violate_action.dscp = 0;
11593
11594 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
11595 {
11596 if (unformat (i, "del"))
11597 is_add = 0;
11598 else if (unformat (i, "name %s", &name))
11599 vec_add1 (name, 0);
11600 else if (unformat (i, "cir %u", &cir))
11601 ;
11602 else if (unformat (i, "eir %u", &eir))
11603 ;
11604 else if (unformat (i, "cb %u", &cb))
11605 ;
11606 else if (unformat (i, "eb %u", &eb))
11607 ;
11608 else if (unformat (i, "rate_type %U", unformat_policer_rate_type,
11609 &rate_type))
11610 ;
11611 else if (unformat (i, "round_type %U", unformat_policer_round_type,
11612 &round_type))
11613 ;
11614 else if (unformat (i, "type %U", unformat_policer_type, &type))
11615 ;
11616 else if (unformat (i, "conform_action %U", unformat_policer_action_type,
11617 &conform_action))
11618 ;
11619 else if (unformat (i, "exceed_action %U", unformat_policer_action_type,
11620 &exceed_action))
11621 ;
11622 else if (unformat (i, "violate_action %U", unformat_policer_action_type,
11623 &violate_action))
11624 ;
11625 else if (unformat (i, "color-aware"))
11626 color_aware = 1;
11627 else
11628 break;
11629 }
11630
11631 if (!vec_len (name))
11632 {
11633 errmsg ("policer name must be specified");
11634 return -99;
11635 }
11636
11637 if (vec_len (name) > 64)
11638 {
11639 errmsg ("policer name too long");
11640 return -99;
11641 }
11642
Jon Loeliger8a2aea32017-01-31 13:19:40 -060011643 M (POLICER_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011644
11645 clib_memcpy (mp->name, name, vec_len (name));
11646 vec_free (name);
11647 mp->is_add = is_add;
Neale Rannsd91c1db2017-07-31 02:30:50 -070011648 mp->cir = ntohl (cir);
11649 mp->eir = ntohl (eir);
11650 mp->cb = clib_net_to_host_u64 (cb);
11651 mp->eb = clib_net_to_host_u64 (eb);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011652 mp->rate_type = rate_type;
11653 mp->round_type = round_type;
11654 mp->type = type;
Jakub Grajciarcd01fb42020-03-02 13:16:53 +010011655 mp->conform_action.type = conform_action.action_type;
11656 mp->conform_action.dscp = conform_action.dscp;
11657 mp->exceed_action.type = exceed_action.action_type;
11658 mp->exceed_action.dscp = exceed_action.dscp;
11659 mp->violate_action.type = violate_action.action_type;
11660 mp->violate_action.dscp = violate_action.dscp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011661 mp->color_aware = color_aware;
11662
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011663 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060011664 W (ret);
11665 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011666}
11667
11668static int
11669api_policer_dump (vat_main_t * vam)
11670{
11671 unformat_input_t *i = vam->input;
11672 vl_api_policer_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060011673 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011674 u8 *match_name = 0;
11675 u8 match_name_valid = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011676 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011677
11678 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
11679 {
11680 if (unformat (i, "name %s", &match_name))
11681 {
11682 vec_add1 (match_name, 0);
11683 match_name_valid = 1;
11684 }
11685 else
11686 break;
11687 }
11688
Jon Loeliger8a2aea32017-01-31 13:19:40 -060011689 M (POLICER_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011690 mp->match_name_valid = match_name_valid;
11691 clib_memcpy (mp->match_name, match_name, vec_len (match_name));
11692 vec_free (match_name);
11693 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011694 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011695
11696 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040011697 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060011698 S (mp_ping);
11699
Damjan Marion7cd468a2016-12-19 23:05:39 +010011700 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -060011701 W (ret);
11702 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011703}
11704
11705static int
11706api_policer_classify_set_interface (vat_main_t * vam)
11707{
11708 unformat_input_t *i = vam->input;
11709 vl_api_policer_classify_set_interface_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011710 u32 sw_if_index;
11711 int sw_if_index_set;
11712 u32 ip4_table_index = ~0;
11713 u32 ip6_table_index = ~0;
11714 u32 l2_table_index = ~0;
11715 u8 is_add = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011716 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011717
11718 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
11719 {
11720 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
11721 sw_if_index_set = 1;
11722 else if (unformat (i, "sw_if_index %d", &sw_if_index))
11723 sw_if_index_set = 1;
11724 else if (unformat (i, "del"))
11725 is_add = 0;
11726 else if (unformat (i, "ip4-table %d", &ip4_table_index))
11727 ;
11728 else if (unformat (i, "ip6-table %d", &ip6_table_index))
11729 ;
11730 else if (unformat (i, "l2-table %d", &l2_table_index))
11731 ;
11732 else
11733 {
11734 clib_warning ("parse error '%U'", format_unformat_error, i);
11735 return -99;
11736 }
11737 }
11738
11739 if (sw_if_index_set == 0)
11740 {
11741 errmsg ("missing interface name or sw_if_index");
11742 return -99;
11743 }
11744
Jon Loeliger8a2aea32017-01-31 13:19:40 -060011745 M (POLICER_CLASSIFY_SET_INTERFACE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011746
11747 mp->sw_if_index = ntohl (sw_if_index);
11748 mp->ip4_table_index = ntohl (ip4_table_index);
11749 mp->ip6_table_index = ntohl (ip6_table_index);
11750 mp->l2_table_index = ntohl (l2_table_index);
11751 mp->is_add = is_add;
11752
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011753 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060011754 W (ret);
11755 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011756}
11757
11758static int
11759api_policer_classify_dump (vat_main_t * vam)
11760{
11761 unformat_input_t *i = vam->input;
11762 vl_api_policer_classify_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060011763 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011764 u8 type = POLICER_CLASSIFY_N_TABLES;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011765 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011766
11767 if (unformat (i, "type %U", unformat_policer_classify_table_type, &type))
11768 ;
11769 else
11770 {
11771 errmsg ("classify table type must be specified");
11772 return -99;
11773 }
11774
11775 if (!vam->json_output)
11776 {
11777 print (vam->ofp, "%10s%20s", "Intfc idx", "Classify table");
11778 }
11779
Jon Loeliger8a2aea32017-01-31 13:19:40 -060011780 M (POLICER_CLASSIFY_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011781 mp->type = type;
11782 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011783 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011784
11785 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040011786 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060011787 S (mp_ping);
11788
Damjan Marion7cd468a2016-12-19 23:05:39 +010011789 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -060011790 W (ret);
11791 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011792}
11793
Neale Ranns097fa662018-05-01 05:17:55 -070011794static u8 *
11795format_fib_api_path_nh_proto (u8 * s, va_list * args)
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011796{
Neale Ranns097fa662018-05-01 05:17:55 -070011797 vl_api_fib_path_nh_proto_t proto =
11798 va_arg (*args, vl_api_fib_path_nh_proto_t);
11799
11800 switch (proto)
11801 {
11802 case FIB_API_PATH_NH_PROTO_IP4:
11803 s = format (s, "ip4");
11804 break;
11805 case FIB_API_PATH_NH_PROTO_IP6:
11806 s = format (s, "ip6");
11807 break;
11808 case FIB_API_PATH_NH_PROTO_MPLS:
11809 s = format (s, "mpls");
11810 break;
11811 case FIB_API_PATH_NH_PROTO_BIER:
11812 s = format (s, "bier");
11813 break;
11814 case FIB_API_PATH_NH_PROTO_ETHERNET:
11815 s = format (s, "ethernet");
11816 break;
11817 }
11818
11819 return (s);
11820}
11821
11822static u8 *
11823format_vl_api_ip_address_union (u8 * s, va_list * args)
11824{
Jakub Grajciar7dd63e52020-03-19 08:03:55 +010011825 vl_api_address_family_t af = va_arg (*args, int);
Neale Ranns097fa662018-05-01 05:17:55 -070011826 const vl_api_address_union_t *u = va_arg (*args, vl_api_address_union_t *);
11827
11828 switch (af)
11829 {
11830 case ADDRESS_IP4:
11831 s = format (s, "%U", format_ip4_address, u->ip4);
11832 break;
11833 case ADDRESS_IP6:
11834 s = format (s, "%U", format_ip6_address, u->ip6);
11835 break;
11836 }
11837 return (s);
11838}
11839
11840static u8 *
11841format_vl_api_fib_path_type (u8 * s, va_list * args)
11842{
11843 vl_api_fib_path_type_t t = va_arg (*args, vl_api_fib_path_type_t);
11844
11845 switch (t)
11846 {
11847 case FIB_API_PATH_TYPE_NORMAL:
11848 s = format (s, "normal");
11849 break;
11850 case FIB_API_PATH_TYPE_LOCAL:
11851 s = format (s, "local");
11852 break;
11853 case FIB_API_PATH_TYPE_DROP:
11854 s = format (s, "drop");
11855 break;
11856 case FIB_API_PATH_TYPE_UDP_ENCAP:
11857 s = format (s, "udp-encap");
11858 break;
11859 case FIB_API_PATH_TYPE_BIER_IMP:
11860 s = format (s, "bier-imp");
11861 break;
11862 case FIB_API_PATH_TYPE_ICMP_UNREACH:
11863 s = format (s, "unreach");
11864 break;
11865 case FIB_API_PATH_TYPE_ICMP_PROHIBIT:
11866 s = format (s, "prohibit");
11867 break;
11868 case FIB_API_PATH_TYPE_SOURCE_LOOKUP:
11869 s = format (s, "src-lookup");
11870 break;
11871 case FIB_API_PATH_TYPE_DVR:
11872 s = format (s, "dvr");
11873 break;
11874 case FIB_API_PATH_TYPE_INTERFACE_RX:
11875 s = format (s, "interface-rx");
11876 break;
11877 case FIB_API_PATH_TYPE_CLASSIFY:
11878 s = format (s, "classify");
11879 break;
11880 }
11881
11882 return (s);
11883}
11884
11885static void
11886vl_api_fib_path_print (vat_main_t * vam, vl_api_fib_path_t * fp)
11887{
11888 print (vam->ofp,
11889 " weight %d, sw_if_index %d, type %U, afi %U, next_hop %U",
11890 ntohl (fp->weight), ntohl (fp->sw_if_index),
11891 format_vl_api_fib_path_type, fp->type,
11892 format_fib_api_path_nh_proto, fp->proto,
11893 format_vl_api_ip_address_union, &fp->nh.address);
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011894}
11895
11896static void
11897vl_api_mpls_fib_path_json_print (vat_json_node_t * node,
Neale Ranns31ed7442018-02-23 05:29:09 -080011898 vl_api_fib_path_t * fp)
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011899{
11900 struct in_addr ip4;
11901 struct in6_addr ip6;
11902
11903 vat_json_object_add_uint (node, "weight", ntohl (fp->weight));
11904 vat_json_object_add_uint (node, "sw_if_index", ntohl (fp->sw_if_index));
Neale Ranns097fa662018-05-01 05:17:55 -070011905 vat_json_object_add_uint (node, "type", fp->type);
11906 vat_json_object_add_uint (node, "next_hop_proto", fp->proto);
11907 if (fp->proto == FIB_API_PATH_NH_PROTO_IP4)
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011908 {
Neale Ranns097fa662018-05-01 05:17:55 -070011909 clib_memcpy (&ip4, &fp->nh.address.ip4, sizeof (ip4));
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011910 vat_json_object_add_ip4 (node, "next_hop", ip4);
11911 }
Dave Barachc35f3e82020-04-02 10:44:09 -040011912 else if (fp->proto == FIB_API_PATH_NH_PROTO_IP6)
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011913 {
Neale Ranns097fa662018-05-01 05:17:55 -070011914 clib_memcpy (&ip6, &fp->nh.address.ip6, sizeof (ip6));
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011915 vat_json_object_add_ip6 (node, "next_hop", ip6);
11916 }
11917}
11918
11919static void
11920vl_api_mpls_tunnel_details_t_handler (vl_api_mpls_tunnel_details_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +010011921{
11922 vat_main_t *vam = &vat_main;
Neale Ranns097fa662018-05-01 05:17:55 -070011923 int count = ntohl (mp->mt_tunnel.mt_n_paths);
Neale Ranns31ed7442018-02-23 05:29:09 -080011924 vl_api_fib_path_t *fp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011925 i32 i;
11926
Neale Ranns097fa662018-05-01 05:17:55 -070011927 print (vam->ofp, "sw_if_index %d via:",
11928 ntohl (mp->mt_tunnel.mt_sw_if_index));
11929 fp = mp->mt_tunnel.mt_paths;
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011930 for (i = 0; i < count; i++)
Damjan Marion7cd468a2016-12-19 23:05:39 +010011931 {
Neale Ranns097fa662018-05-01 05:17:55 -070011932 vl_api_fib_path_print (vam, fp);
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011933 fp++;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011934 }
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011935
Damjan Marion7cd468a2016-12-19 23:05:39 +010011936 print (vam->ofp, "");
11937}
11938
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011939#define vl_api_mpls_tunnel_details_t_endian vl_noop_handler
11940#define vl_api_mpls_tunnel_details_t_print vl_noop_handler
11941
11942static void
11943vl_api_mpls_tunnel_details_t_handler_json (vl_api_mpls_tunnel_details_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +010011944{
11945 vat_main_t *vam = &vat_main;
11946 vat_json_node_t *node = NULL;
Neale Ranns097fa662018-05-01 05:17:55 -070011947 int count = ntohl (mp->mt_tunnel.mt_n_paths);
Neale Ranns31ed7442018-02-23 05:29:09 -080011948 vl_api_fib_path_t *fp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011949 i32 i;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011950
11951 if (VAT_JSON_ARRAY != vam->json_tree.type)
11952 {
11953 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
11954 vat_json_init_array (&vam->json_tree);
11955 }
11956 node = vat_json_array_add (&vam->json_tree);
11957
11958 vat_json_init_object (node);
Neale Ranns097fa662018-05-01 05:17:55 -070011959 vat_json_object_add_uint (node, "sw_if_index",
11960 ntohl (mp->mt_tunnel.mt_sw_if_index));
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011961
Neale Ranns097fa662018-05-01 05:17:55 -070011962 vat_json_object_add_uint (node, "l2_only", mp->mt_tunnel.mt_l2_only);
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011963
Neale Ranns097fa662018-05-01 05:17:55 -070011964 fp = mp->mt_tunnel.mt_paths;
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011965 for (i = 0; i < count; i++)
Damjan Marion7cd468a2016-12-19 23:05:39 +010011966 {
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011967 vl_api_mpls_fib_path_json_print (node, fp);
11968 fp++;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011969 }
11970}
11971
11972static int
11973api_mpls_tunnel_dump (vat_main_t * vam)
11974{
11975 vl_api_mpls_tunnel_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060011976 vl_api_control_ping_t *mp_ping;
Jon Loeliger56c7b012017-02-01 12:31:41 -060011977 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011978
Jon Loeliger8a2aea32017-01-31 13:19:40 -060011979 M (MPLS_TUNNEL_DUMP, mp);
Neale Ranns097fa662018-05-01 05:17:55 -070011980
Jon Loeliger7bc770c2017-01-31 14:03:33 -060011981 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010011982
11983 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040011984 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060011985 S (mp_ping);
11986
Jon Loeliger56c7b012017-02-01 12:31:41 -060011987 W (ret);
11988 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010011989}
11990
Neale Ranns097fa662018-05-01 05:17:55 -070011991#define vl_api_mpls_table_details_t_endian vl_noop_handler
11992#define vl_api_mpls_table_details_t_print vl_noop_handler
Damjan Marion7cd468a2016-12-19 23:05:39 +010011993
Neale Ranns0f26c5a2017-03-01 15:12:11 -080011994
Damjan Marion7cd468a2016-12-19 23:05:39 +010011995static void
Neale Ranns097fa662018-05-01 05:17:55 -070011996vl_api_mpls_table_details_t_handler (vl_api_mpls_table_details_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +010011997{
11998 vat_main_t *vam = &vat_main;
Neale Ranns097fa662018-05-01 05:17:55 -070011999
12000 print (vam->ofp, "table-id %d,", ntohl (mp->mt_table.mt_table_id));
12001}
12002
12003static void vl_api_mpls_table_details_t_handler_json
12004 (vl_api_mpls_table_details_t * mp)
12005{
12006 vat_main_t *vam = &vat_main;
12007 vat_json_node_t *node = NULL;
12008
12009 if (VAT_JSON_ARRAY != vam->json_tree.type)
12010 {
12011 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
12012 vat_json_init_array (&vam->json_tree);
12013 }
12014 node = vat_json_array_add (&vam->json_tree);
12015
12016 vat_json_init_object (node);
12017 vat_json_object_add_uint (node, "table", ntohl (mp->mt_table.mt_table_id));
12018}
12019
12020static int
12021api_mpls_table_dump (vat_main_t * vam)
12022{
12023 vl_api_mpls_table_dump_t *mp;
12024 vl_api_control_ping_t *mp_ping;
12025 int ret;
12026
12027 M (MPLS_TABLE_DUMP, mp);
12028 S (mp);
12029
12030 /* Use a control ping for synchronization */
12031 MPING (CONTROL_PING, mp_ping);
12032 S (mp_ping);
12033
12034 W (ret);
12035 return ret;
12036}
12037
12038#define vl_api_mpls_route_details_t_endian vl_noop_handler
12039#define vl_api_mpls_route_details_t_print vl_noop_handler
12040
12041static void
12042vl_api_mpls_route_details_t_handler (vl_api_mpls_route_details_t * mp)
12043{
12044 vat_main_t *vam = &vat_main;
Dave Barach4bda2d92019-07-03 15:21:50 -040012045 int count = (int) clib_net_to_host_u32 (mp->mr_route.mr_n_paths);
Neale Ranns31ed7442018-02-23 05:29:09 -080012046 vl_api_fib_path_t *fp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012047 int i;
12048
12049 print (vam->ofp,
12050 "table-id %d, label %u, ess_bit %u",
Neale Ranns097fa662018-05-01 05:17:55 -070012051 ntohl (mp->mr_route.mr_table_id),
12052 ntohl (mp->mr_route.mr_label), mp->mr_route.mr_eos);
12053 fp = mp->mr_route.mr_paths;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012054 for (i = 0; i < count; i++)
12055 {
Neale Ranns097fa662018-05-01 05:17:55 -070012056 vl_api_fib_path_print (vam, fp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012057 fp++;
12058 }
12059}
12060
Neale Ranns097fa662018-05-01 05:17:55 -070012061static void vl_api_mpls_route_details_t_handler_json
12062 (vl_api_mpls_route_details_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +010012063{
12064 vat_main_t *vam = &vat_main;
Dave Barach4bda2d92019-07-03 15:21:50 -040012065 int count = (int) clib_host_to_net_u32 (mp->mr_route.mr_n_paths);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012066 vat_json_node_t *node = NULL;
Neale Ranns31ed7442018-02-23 05:29:09 -080012067 vl_api_fib_path_t *fp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012068 int i;
12069
12070 if (VAT_JSON_ARRAY != vam->json_tree.type)
12071 {
12072 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
12073 vat_json_init_array (&vam->json_tree);
12074 }
12075 node = vat_json_array_add (&vam->json_tree);
12076
12077 vat_json_init_object (node);
Neale Ranns097fa662018-05-01 05:17:55 -070012078 vat_json_object_add_uint (node, "table", ntohl (mp->mr_route.mr_table_id));
12079 vat_json_object_add_uint (node, "s_bit", mp->mr_route.mr_eos);
12080 vat_json_object_add_uint (node, "label", ntohl (mp->mr_route.mr_label));
Damjan Marion7cd468a2016-12-19 23:05:39 +010012081 vat_json_object_add_uint (node, "path_count", count);
Neale Ranns097fa662018-05-01 05:17:55 -070012082 fp = mp->mr_route.mr_paths;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012083 for (i = 0; i < count; i++)
12084 {
Neale Ranns0f26c5a2017-03-01 15:12:11 -080012085 vl_api_mpls_fib_path_json_print (node, fp);
12086 fp++;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012087 }
12088}
12089
12090static int
Neale Ranns097fa662018-05-01 05:17:55 -070012091api_mpls_route_dump (vat_main_t * vam)
Damjan Marion7cd468a2016-12-19 23:05:39 +010012092{
Neale Ranns097fa662018-05-01 05:17:55 -070012093 unformat_input_t *input = vam->input;
12094 vl_api_mpls_route_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012095 vl_api_control_ping_t *mp_ping;
Neale Ranns097fa662018-05-01 05:17:55 -070012096 u32 table_id;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012097 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012098
Neale Ranns097fa662018-05-01 05:17:55 -070012099 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12100 {
12101 if (unformat (input, "table_id %d", &table_id))
12102 ;
12103 else
12104 break;
12105 }
12106 if (table_id == ~0)
12107 {
12108 errmsg ("missing table id");
12109 return -99;
12110 }
12111
12112 M (MPLS_ROUTE_DUMP, mp);
12113
12114 mp->table.mt_table_id = ntohl (table_id);
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012115 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012116
12117 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040012118 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012119 S (mp_ping);
12120
Jon Loeliger56c7b012017-02-01 12:31:41 -060012121 W (ret);
12122 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012123}
12124
Neale Ranns097fa662018-05-01 05:17:55 -070012125#define vl_api_ip_table_details_t_endian vl_noop_handler
12126#define vl_api_ip_table_details_t_print vl_noop_handler
Damjan Marion7cd468a2016-12-19 23:05:39 +010012127
12128static void
Neale Ranns097fa662018-05-01 05:17:55 -070012129vl_api_ip_table_details_t_handler (vl_api_ip_table_details_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +010012130{
12131 vat_main_t *vam = &vat_main;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012132
12133 print (vam->ofp,
Neale Ranns097fa662018-05-01 05:17:55 -070012134 "%s; table-id %d, prefix %U/%d",
12135 mp->table.name, ntohl (mp->table.table_id));
Damjan Marion7cd468a2016-12-19 23:05:39 +010012136}
12137
Neale Ranns097fa662018-05-01 05:17:55 -070012138
12139static void vl_api_ip_table_details_t_handler_json
12140 (vl_api_ip_table_details_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +010012141{
12142 vat_main_t *vam = &vat_main;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012143 vat_json_node_t *node = NULL;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012144
12145 if (VAT_JSON_ARRAY != vam->json_tree.type)
12146 {
12147 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
12148 vat_json_init_array (&vam->json_tree);
12149 }
12150 node = vat_json_array_add (&vam->json_tree);
12151
12152 vat_json_init_object (node);
Neale Ranns097fa662018-05-01 05:17:55 -070012153 vat_json_object_add_uint (node, "table", ntohl (mp->table.table_id));
Damjan Marion7cd468a2016-12-19 23:05:39 +010012154}
12155
12156static int
Neale Ranns097fa662018-05-01 05:17:55 -070012157api_ip_table_dump (vat_main_t * vam)
Damjan Marion7cd468a2016-12-19 23:05:39 +010012158{
Neale Ranns097fa662018-05-01 05:17:55 -070012159 vl_api_ip_table_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012160 vl_api_control_ping_t *mp_ping;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012161 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012162
Neale Ranns097fa662018-05-01 05:17:55 -070012163 M (IP_TABLE_DUMP, mp);
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012164 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012165
12166 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040012167 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012168 S (mp_ping);
12169
Jon Loeliger56c7b012017-02-01 12:31:41 -060012170 W (ret);
12171 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012172}
12173
Neale Ranns5a8123b2017-01-26 01:18:23 -080012174static int
Neale Ranns097fa662018-05-01 05:17:55 -070012175api_ip_mtable_dump (vat_main_t * vam)
Neale Ranns5a8123b2017-01-26 01:18:23 -080012176{
Neale Ranns097fa662018-05-01 05:17:55 -070012177 vl_api_ip_mtable_dump_t *mp;
Neale Ranns5a8123b2017-01-26 01:18:23 -080012178 vl_api_control_ping_t *mp_ping;
12179 int ret;
12180
Neale Ranns097fa662018-05-01 05:17:55 -070012181 M (IP_MTABLE_DUMP, mp);
12182 S (mp);
12183
12184 /* Use a control ping for synchronization */
12185 MPING (CONTROL_PING, mp_ping);
12186 S (mp_ping);
12187
12188 W (ret);
12189 return ret;
12190}
12191
12192static int
12193api_ip_mroute_dump (vat_main_t * vam)
12194{
12195 unformat_input_t *input = vam->input;
12196 vl_api_control_ping_t *mp_ping;
12197 vl_api_ip_mroute_dump_t *mp;
12198 int ret, is_ip6;
12199 u32 table_id;
12200
12201 is_ip6 = 0;
12202 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12203 {
12204 if (unformat (input, "table_id %d", &table_id))
12205 ;
12206 else if (unformat (input, "ip6"))
12207 is_ip6 = 1;
12208 else if (unformat (input, "ip4"))
12209 is_ip6 = 0;
12210 else
12211 break;
12212 }
12213 if (table_id == ~0)
12214 {
12215 errmsg ("missing table id");
12216 return -99;
12217 }
12218
12219 M (IP_MROUTE_DUMP, mp);
12220 mp->table.table_id = table_id;
12221 mp->table.is_ip6 = is_ip6;
Neale Ranns5a8123b2017-01-26 01:18:23 -080012222 S (mp);
12223
12224 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040012225 MPING (CONTROL_PING, mp_ping);
Neale Ranns5a8123b2017-01-26 01:18:23 -080012226 S (mp_ping);
12227
12228 W (ret);
12229 return ret;
12230}
12231
Neale Ranns097fa662018-05-01 05:17:55 -070012232#define vl_api_ip_route_details_t_endian vl_noop_handler
12233#define vl_api_ip_route_details_t_print vl_noop_handler
Damjan Marion7cd468a2016-12-19 23:05:39 +010012234
12235static void
Neale Ranns097fa662018-05-01 05:17:55 -070012236vl_api_ip_route_details_t_handler (vl_api_ip_route_details_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +010012237{
12238 vat_main_t *vam = &vat_main;
Neale Ranns097fa662018-05-01 05:17:55 -070012239 u8 count = mp->route.n_paths;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012240 vl_api_fib_path_t *fp;
12241 int i;
12242
12243 print (vam->ofp,
Neale Ranns097fa662018-05-01 05:17:55 -070012244 "table-id %d, prefix %U/%d",
12245 ntohl (mp->route.table_id),
Paul Vinciguerraab055082019-06-06 14:07:55 -040012246 format_ip46_address, mp->route.prefix.address, mp->route.prefix.len);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012247 for (i = 0; i < count; i++)
12248 {
Neale Ranns097fa662018-05-01 05:17:55 -070012249 fp = &mp->route.paths[i];
12250
12251 vl_api_fib_path_print (vam, fp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012252 fp++;
12253 }
12254}
12255
Neale Ranns097fa662018-05-01 05:17:55 -070012256static void vl_api_ip_route_details_t_handler_json
12257 (vl_api_ip_route_details_t * mp)
Damjan Marion7cd468a2016-12-19 23:05:39 +010012258{
12259 vat_main_t *vam = &vat_main;
Neale Ranns097fa662018-05-01 05:17:55 -070012260 u8 count = mp->route.n_paths;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012261 vat_json_node_t *node = NULL;
12262 struct in_addr ip4;
12263 struct in6_addr ip6;
12264 vl_api_fib_path_t *fp;
12265 int i;
12266
12267 if (VAT_JSON_ARRAY != vam->json_tree.type)
12268 {
12269 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
12270 vat_json_init_array (&vam->json_tree);
12271 }
12272 node = vat_json_array_add (&vam->json_tree);
12273
12274 vat_json_init_object (node);
Neale Ranns097fa662018-05-01 05:17:55 -070012275 vat_json_object_add_uint (node, "table", ntohl (mp->route.table_id));
12276 if (ADDRESS_IP6 == mp->route.prefix.address.af)
12277 {
12278 clib_memcpy (&ip6, &mp->route.prefix.address.un.ip6, sizeof (ip6));
12279 vat_json_object_add_ip6 (node, "prefix", ip6);
12280 }
12281 else
12282 {
12283 clib_memcpy (&ip4, &mp->route.prefix.address.un.ip4, sizeof (ip4));
12284 vat_json_object_add_ip4 (node, "prefix", ip4);
12285 }
Paul Vinciguerraab055082019-06-06 14:07:55 -040012286 vat_json_object_add_uint (node, "mask_length", mp->route.prefix.len);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012287 vat_json_object_add_uint (node, "path_count", count);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012288 for (i = 0; i < count; i++)
12289 {
Neale Ranns097fa662018-05-01 05:17:55 -070012290 fp = &mp->route.paths[i];
12291 vl_api_mpls_fib_path_json_print (node, fp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012292 }
12293}
12294
12295static int
Neale Ranns097fa662018-05-01 05:17:55 -070012296api_ip_route_dump (vat_main_t * vam)
Damjan Marion7cd468a2016-12-19 23:05:39 +010012297{
Neale Ranns097fa662018-05-01 05:17:55 -070012298 unformat_input_t *input = vam->input;
12299 vl_api_ip_route_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012300 vl_api_control_ping_t *mp_ping;
Neale Ranns097fa662018-05-01 05:17:55 -070012301 u32 table_id;
12302 u8 is_ip6;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012303 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012304
Neale Ranns097fa662018-05-01 05:17:55 -070012305 is_ip6 = 0;
12306 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12307 {
12308 if (unformat (input, "table_id %d", &table_id))
12309 ;
12310 else if (unformat (input, "ip6"))
12311 is_ip6 = 1;
12312 else if (unformat (input, "ip4"))
12313 is_ip6 = 0;
12314 else
12315 break;
12316 }
12317 if (table_id == ~0)
12318 {
12319 errmsg ("missing table id");
12320 return -99;
12321 }
Damjan Marion7cd468a2016-12-19 23:05:39 +010012322
Neale Ranns097fa662018-05-01 05:17:55 -070012323 M (IP_ROUTE_DUMP, mp);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012324
Neale Ranns097fa662018-05-01 05:17:55 -070012325 mp->table.table_id = table_id;
12326 mp->table.is_ip6 = is_ip6;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012327
Neale Ranns5a8123b2017-01-26 01:18:23 -080012328 S (mp);
12329
12330 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040012331 MPING (CONTROL_PING, mp_ping);
Neale Ranns5a8123b2017-01-26 01:18:23 -080012332 S (mp_ping);
12333
12334 W (ret);
12335 return ret;
12336}
12337
Damjan Marion7cd468a2016-12-19 23:05:39 +010012338int
12339api_classify_table_ids (vat_main_t * vam)
12340{
12341 vl_api_classify_table_ids_t *mp;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012342 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012343
12344 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012345 M (CLASSIFY_TABLE_IDS, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012346 mp->context = 0;
12347
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012348 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060012349 W (ret);
12350 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012351}
12352
12353int
12354api_classify_table_by_interface (vat_main_t * vam)
12355{
12356 unformat_input_t *input = vam->input;
12357 vl_api_classify_table_by_interface_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012358
12359 u32 sw_if_index = ~0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012360 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012361 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12362 {
12363 if (unformat (input, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
12364 ;
12365 else if (unformat (input, "sw_if_index %d", &sw_if_index))
12366 ;
12367 else
12368 break;
12369 }
12370 if (sw_if_index == ~0)
12371 {
12372 errmsg ("missing interface name or sw_if_index");
12373 return -99;
12374 }
12375
12376 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012377 M (CLASSIFY_TABLE_BY_INTERFACE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012378 mp->context = 0;
12379 mp->sw_if_index = ntohl (sw_if_index);
12380
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012381 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060012382 W (ret);
12383 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012384}
12385
12386int
12387api_classify_table_info (vat_main_t * vam)
12388{
12389 unformat_input_t *input = vam->input;
12390 vl_api_classify_table_info_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012391
12392 u32 table_id = ~0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012393 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012394 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12395 {
12396 if (unformat (input, "table_id %d", &table_id))
12397 ;
12398 else
12399 break;
12400 }
12401 if (table_id == ~0)
12402 {
12403 errmsg ("missing table id");
12404 return -99;
12405 }
12406
12407 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012408 M (CLASSIFY_TABLE_INFO, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012409 mp->context = 0;
12410 mp->table_id = ntohl (table_id);
12411
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012412 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060012413 W (ret);
12414 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012415}
12416
12417int
12418api_classify_session_dump (vat_main_t * vam)
12419{
12420 unformat_input_t *input = vam->input;
12421 vl_api_classify_session_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012422 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012423
12424 u32 table_id = ~0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012425 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012426 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12427 {
12428 if (unformat (input, "table_id %d", &table_id))
12429 ;
12430 else
12431 break;
12432 }
12433 if (table_id == ~0)
12434 {
12435 errmsg ("missing table id");
12436 return -99;
12437 }
12438
12439 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012440 M (CLASSIFY_SESSION_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012441 mp->context = 0;
12442 mp->table_id = ntohl (table_id);
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012443 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012444
12445 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040012446 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012447 S (mp_ping);
12448
Jon Loeliger56c7b012017-02-01 12:31:41 -060012449 W (ret);
12450 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012451}
12452
12453static void
12454vl_api_ipfix_exporter_details_t_handler (vl_api_ipfix_exporter_details_t * mp)
12455{
12456 vat_main_t *vam = &vat_main;
12457
12458 print (vam->ofp, "collector_address %U, collector_port %d, "
12459 "src_address %U, vrf_id %d, path_mtu %u, "
12460 "template_interval %u, udp_checksum %d",
12461 format_ip4_address, mp->collector_address,
12462 ntohs (mp->collector_port),
12463 format_ip4_address, mp->src_address,
12464 ntohl (mp->vrf_id), ntohl (mp->path_mtu),
12465 ntohl (mp->template_interval), mp->udp_checksum);
12466
12467 vam->retval = 0;
12468 vam->result_ready = 1;
12469}
12470
12471static void
12472 vl_api_ipfix_exporter_details_t_handler_json
12473 (vl_api_ipfix_exporter_details_t * mp)
12474{
12475 vat_main_t *vam = &vat_main;
12476 vat_json_node_t node;
12477 struct in_addr collector_address;
12478 struct in_addr src_address;
12479
12480 vat_json_init_object (&node);
12481 clib_memcpy (&collector_address, &mp->collector_address,
12482 sizeof (collector_address));
12483 vat_json_object_add_ip4 (&node, "collector_address", collector_address);
12484 vat_json_object_add_uint (&node, "collector_port",
12485 ntohs (mp->collector_port));
12486 clib_memcpy (&src_address, &mp->src_address, sizeof (src_address));
12487 vat_json_object_add_ip4 (&node, "src_address", src_address);
12488 vat_json_object_add_int (&node, "vrf_id", ntohl (mp->vrf_id));
12489 vat_json_object_add_uint (&node, "path_mtu", ntohl (mp->path_mtu));
12490 vat_json_object_add_uint (&node, "template_interval",
12491 ntohl (mp->template_interval));
12492 vat_json_object_add_int (&node, "udp_checksum", mp->udp_checksum);
12493
12494 vat_json_print (vam->ofp, &node);
12495 vat_json_free (&node);
12496 vam->retval = 0;
12497 vam->result_ready = 1;
12498}
12499
12500int
12501api_ipfix_exporter_dump (vat_main_t * vam)
12502{
12503 vl_api_ipfix_exporter_dump_t *mp;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012504 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012505
12506 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012507 M (IPFIX_EXPORTER_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012508 mp->context = 0;
12509
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012510 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060012511 W (ret);
12512 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012513}
12514
12515static int
12516api_ipfix_classify_stream_dump (vat_main_t * vam)
12517{
12518 vl_api_ipfix_classify_stream_dump_t *mp;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012519 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012520
12521 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012522 M (IPFIX_CLASSIFY_STREAM_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012523 mp->context = 0;
12524
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012525 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060012526 W (ret);
12527 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012528 /* NOTREACHED */
12529 return 0;
12530}
12531
12532static void
12533 vl_api_ipfix_classify_stream_details_t_handler
12534 (vl_api_ipfix_classify_stream_details_t * mp)
12535{
12536 vat_main_t *vam = &vat_main;
12537 print (vam->ofp, "domain_id %d, src_port %d",
12538 ntohl (mp->domain_id), ntohs (mp->src_port));
12539 vam->retval = 0;
12540 vam->result_ready = 1;
12541}
12542
12543static void
12544 vl_api_ipfix_classify_stream_details_t_handler_json
12545 (vl_api_ipfix_classify_stream_details_t * mp)
12546{
12547 vat_main_t *vam = &vat_main;
12548 vat_json_node_t node;
12549
12550 vat_json_init_object (&node);
12551 vat_json_object_add_uint (&node, "domain_id", ntohl (mp->domain_id));
12552 vat_json_object_add_uint (&node, "src_port", ntohs (mp->src_port));
12553
12554 vat_json_print (vam->ofp, &node);
12555 vat_json_free (&node);
12556 vam->retval = 0;
12557 vam->result_ready = 1;
12558}
12559
12560static int
12561api_ipfix_classify_table_dump (vat_main_t * vam)
12562{
12563 vl_api_ipfix_classify_table_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012564 vl_api_control_ping_t *mp_ping;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012565 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012566
12567 if (!vam->json_output)
12568 {
12569 print (vam->ofp, "%15s%15s%20s", "table_id", "ip_version",
12570 "transport_protocol");
12571 }
12572
12573 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012574 M (IPFIX_CLASSIFY_TABLE_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012575
12576 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012577 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012578
12579 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040012580 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012581 S (mp_ping);
12582
Jon Loeliger56c7b012017-02-01 12:31:41 -060012583 W (ret);
12584 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012585}
12586
12587static void
12588 vl_api_ipfix_classify_table_details_t_handler
12589 (vl_api_ipfix_classify_table_details_t * mp)
12590{
12591 vat_main_t *vam = &vat_main;
12592 print (vam->ofp, "%15d%15d%20d", ntohl (mp->table_id), mp->ip_version,
12593 mp->transport_protocol);
12594}
12595
12596static void
12597 vl_api_ipfix_classify_table_details_t_handler_json
12598 (vl_api_ipfix_classify_table_details_t * mp)
12599{
12600 vat_json_node_t *node = NULL;
12601 vat_main_t *vam = &vat_main;
12602
12603 if (VAT_JSON_ARRAY != vam->json_tree.type)
12604 {
12605 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
12606 vat_json_init_array (&vam->json_tree);
12607 }
12608
12609 node = vat_json_array_add (&vam->json_tree);
12610 vat_json_init_object (node);
12611
12612 vat_json_object_add_uint (node, "table_id", ntohl (mp->table_id));
12613 vat_json_object_add_uint (node, "ip_version", mp->ip_version);
12614 vat_json_object_add_uint (node, "transport_protocol",
12615 mp->transport_protocol);
12616}
12617
12618static int
12619api_sw_interface_span_enable_disable (vat_main_t * vam)
12620{
12621 unformat_input_t *i = vam->input;
12622 vl_api_sw_interface_span_enable_disable_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012623 u32 src_sw_if_index = ~0;
12624 u32 dst_sw_if_index = ~0;
12625 u8 state = 3;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012626 int ret;
Eyal Bari001fd402017-07-16 09:34:53 +030012627 u8 is_l2 = 0;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012628
12629 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
12630 {
12631 if (unformat
12632 (i, "src %U", api_unformat_sw_if_index, vam, &src_sw_if_index))
12633 ;
12634 else if (unformat (i, "src_sw_if_index %d", &src_sw_if_index))
12635 ;
12636 else
12637 if (unformat
12638 (i, "dst %U", api_unformat_sw_if_index, vam, &dst_sw_if_index))
12639 ;
12640 else if (unformat (i, "dst_sw_if_index %d", &dst_sw_if_index))
12641 ;
12642 else if (unformat (i, "disable"))
12643 state = 0;
12644 else if (unformat (i, "rx"))
12645 state = 1;
12646 else if (unformat (i, "tx"))
12647 state = 2;
12648 else if (unformat (i, "both"))
12649 state = 3;
Eyal Bari001fd402017-07-16 09:34:53 +030012650 else if (unformat (i, "l2"))
12651 is_l2 = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012652 else
12653 break;
12654 }
12655
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012656 M (SW_INTERFACE_SPAN_ENABLE_DISABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012657
12658 mp->sw_if_index_from = htonl (src_sw_if_index);
12659 mp->sw_if_index_to = htonl (dst_sw_if_index);
12660 mp->state = state;
Eyal Bari001fd402017-07-16 09:34:53 +030012661 mp->is_l2 = is_l2;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012662
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012663 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060012664 W (ret);
12665 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012666}
12667
12668static void
12669vl_api_sw_interface_span_details_t_handler (vl_api_sw_interface_span_details_t
12670 * mp)
12671{
12672 vat_main_t *vam = &vat_main;
12673 u8 *sw_if_from_name = 0;
12674 u8 *sw_if_to_name = 0;
12675 u32 sw_if_index_from = ntohl (mp->sw_if_index_from);
12676 u32 sw_if_index_to = ntohl (mp->sw_if_index_to);
12677 char *states[] = { "none", "rx", "tx", "both" };
12678 hash_pair_t *p;
12679
12680 /* *INDENT-OFF* */
12681 hash_foreach_pair (p, vam->sw_if_index_by_interface_name,
12682 ({
12683 if ((u32) p->value[0] == sw_if_index_from)
12684 {
12685 sw_if_from_name = (u8 *)(p->key);
12686 if (sw_if_to_name)
12687 break;
12688 }
12689 if ((u32) p->value[0] == sw_if_index_to)
12690 {
12691 sw_if_to_name = (u8 *)(p->key);
12692 if (sw_if_from_name)
12693 break;
12694 }
12695 }));
12696 /* *INDENT-ON* */
Jon Loeliger179ab362018-03-12 14:50:08 -050012697 print (vam->ofp, "%20s => %20s (%s) %s",
12698 sw_if_from_name, sw_if_to_name, states[mp->state],
12699 mp->is_l2 ? "l2" : "device");
Damjan Marion7cd468a2016-12-19 23:05:39 +010012700}
12701
12702static void
12703 vl_api_sw_interface_span_details_t_handler_json
12704 (vl_api_sw_interface_span_details_t * mp)
12705{
12706 vat_main_t *vam = &vat_main;
12707 vat_json_node_t *node = NULL;
12708 u8 *sw_if_from_name = 0;
12709 u8 *sw_if_to_name = 0;
12710 u32 sw_if_index_from = ntohl (mp->sw_if_index_from);
12711 u32 sw_if_index_to = ntohl (mp->sw_if_index_to);
12712 hash_pair_t *p;
12713
12714 /* *INDENT-OFF* */
12715 hash_foreach_pair (p, vam->sw_if_index_by_interface_name,
12716 ({
12717 if ((u32) p->value[0] == sw_if_index_from)
12718 {
12719 sw_if_from_name = (u8 *)(p->key);
12720 if (sw_if_to_name)
12721 break;
12722 }
12723 if ((u32) p->value[0] == sw_if_index_to)
12724 {
12725 sw_if_to_name = (u8 *)(p->key);
12726 if (sw_if_from_name)
12727 break;
12728 }
12729 }));
12730 /* *INDENT-ON* */
12731
12732 if (VAT_JSON_ARRAY != vam->json_tree.type)
12733 {
12734 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
12735 vat_json_init_array (&vam->json_tree);
12736 }
12737 node = vat_json_array_add (&vam->json_tree);
12738
12739 vat_json_init_object (node);
12740 vat_json_object_add_uint (node, "src-if-index", sw_if_index_from);
12741 vat_json_object_add_string_copy (node, "src-if-name", sw_if_from_name);
12742 vat_json_object_add_uint (node, "dst-if-index", sw_if_index_to);
Neale Ranns05b2bf22017-01-30 06:44:58 -080012743 if (0 != sw_if_to_name)
12744 {
12745 vat_json_object_add_string_copy (node, "dst-if-name", sw_if_to_name);
12746 }
Damjan Marion7cd468a2016-12-19 23:05:39 +010012747 vat_json_object_add_uint (node, "state", mp->state);
Jon Loeliger179ab362018-03-12 14:50:08 -050012748 vat_json_object_add_uint (node, "is-l2", mp->is_l2);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012749}
12750
12751static int
12752api_sw_interface_span_dump (vat_main_t * vam)
12753{
Eyal Bari5b311202017-07-31 13:12:30 +030012754 unformat_input_t *input = vam->input;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012755 vl_api_sw_interface_span_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012756 vl_api_control_ping_t *mp_ping;
Eyal Bari5b311202017-07-31 13:12:30 +030012757 u8 is_l2 = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012758 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012759
Eyal Bari5b311202017-07-31 13:12:30 +030012760 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12761 {
12762 if (unformat (input, "l2"))
12763 is_l2 = 1;
12764 else
12765 break;
12766 }
12767
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012768 M (SW_INTERFACE_SPAN_DUMP, mp);
Eyal Bari5b311202017-07-31 13:12:30 +030012769 mp->is_l2 = is_l2;
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012770 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012771
12772 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040012773 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060012774 S (mp_ping);
12775
Jon Loeliger56c7b012017-02-01 12:31:41 -060012776 W (ret);
12777 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012778}
12779
12780int
12781api_pg_create_interface (vat_main_t * vam)
12782{
12783 unformat_input_t *input = vam->input;
12784 vl_api_pg_create_interface_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012785
Mohsin Kazmi22e9cfd2019-07-23 11:54:48 +020012786 u32 if_id = ~0, gso_size = 0;
12787 u8 gso_enabled = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012788 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012789 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12790 {
12791 if (unformat (input, "if_id %d", &if_id))
12792 ;
Mohsin Kazmi22e9cfd2019-07-23 11:54:48 +020012793 else if (unformat (input, "gso-enabled"))
12794 {
12795 gso_enabled = 1;
12796 if (unformat (input, "gso-size %u", &gso_size))
12797 ;
12798 else
12799 {
12800 errmsg ("missing gso-size");
12801 return -99;
12802 }
12803 }
Damjan Marion7cd468a2016-12-19 23:05:39 +010012804 else
12805 break;
12806 }
12807 if (if_id == ~0)
12808 {
12809 errmsg ("missing pg interface index");
12810 return -99;
12811 }
12812
12813 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012814 M (PG_CREATE_INTERFACE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012815 mp->context = 0;
12816 mp->interface_id = ntohl (if_id);
Mohsin Kazmi22e9cfd2019-07-23 11:54:48 +020012817 mp->gso_enabled = gso_enabled;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012818
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012819 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060012820 W (ret);
12821 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012822}
12823
12824int
12825api_pg_capture (vat_main_t * vam)
12826{
12827 unformat_input_t *input = vam->input;
12828 vl_api_pg_capture_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012829
12830 u32 if_id = ~0;
12831 u8 enable = 1;
12832 u32 count = 1;
12833 u8 pcap_file_set = 0;
12834 u8 *pcap_file = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012835 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012836 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12837 {
12838 if (unformat (input, "if_id %d", &if_id))
12839 ;
12840 else if (unformat (input, "pcap %s", &pcap_file))
12841 pcap_file_set = 1;
12842 else if (unformat (input, "count %d", &count))
12843 ;
12844 else if (unformat (input, "disable"))
12845 enable = 0;
12846 else
12847 break;
12848 }
12849 if (if_id == ~0)
12850 {
12851 errmsg ("missing pg interface index");
12852 return -99;
12853 }
12854 if (pcap_file_set > 0)
12855 {
12856 if (vec_len (pcap_file) > 255)
12857 {
12858 errmsg ("pcap file name is too long");
12859 return -99;
12860 }
12861 }
12862
Damjan Marion7cd468a2016-12-19 23:05:39 +010012863 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012864 M (PG_CAPTURE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012865 mp->context = 0;
12866 mp->interface_id = ntohl (if_id);
12867 mp->is_enabled = enable;
12868 mp->count = ntohl (count);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012869 if (pcap_file_set != 0)
12870 {
Jakub Grajciardb863292020-01-30 14:14:15 +010012871 vl_api_vec_to_api_string (pcap_file, &mp->pcap_file_name);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012872 }
12873 vec_free (pcap_file);
12874
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012875 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060012876 W (ret);
12877 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012878}
12879
12880int
12881api_pg_enable_disable (vat_main_t * vam)
12882{
12883 unformat_input_t *input = vam->input;
12884 vl_api_pg_enable_disable_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012885
12886 u8 enable = 1;
12887 u8 stream_name_set = 0;
12888 u8 *stream_name = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012889 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012890 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12891 {
12892 if (unformat (input, "stream %s", &stream_name))
12893 stream_name_set = 1;
12894 else if (unformat (input, "disable"))
12895 enable = 0;
12896 else
12897 break;
12898 }
12899
12900 if (stream_name_set > 0)
12901 {
12902 if (vec_len (stream_name) > 255)
12903 {
12904 errmsg ("stream name too long");
12905 return -99;
12906 }
12907 }
12908
Damjan Marion7cd468a2016-12-19 23:05:39 +010012909 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060012910 M (PG_ENABLE_DISABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012911 mp->context = 0;
12912 mp->is_enabled = enable;
12913 if (stream_name_set != 0)
12914 {
Jakub Grajciardb863292020-01-30 14:14:15 +010012915 vl_api_vec_to_api_string (stream_name, &mp->stream_name);
Damjan Marion7cd468a2016-12-19 23:05:39 +010012916 }
12917 vec_free (stream_name);
12918
Jon Loeliger7bc770c2017-01-31 14:03:33 -060012919 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060012920 W (ret);
12921 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012922}
12923
12924int
Mohsin Kazmif382b062020-08-11 15:00:44 +020012925api_pg_interface_enable_disable_coalesce (vat_main_t * vam)
12926{
12927 unformat_input_t *input = vam->input;
12928 vl_api_pg_interface_enable_disable_coalesce_t *mp;
12929
12930 u32 sw_if_index = ~0;
12931 u8 enable = 1;
12932 int ret;
12933 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12934 {
12935 if (unformat (input, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
12936 ;
12937 else if (unformat (input, "sw_if_index %d", &sw_if_index))
12938 ;
12939 else if (unformat (input, "disable"))
12940 enable = 0;
12941 else
12942 break;
12943 }
12944
12945 if (sw_if_index == ~0)
12946 {
12947 errmsg ("Interface required but not specified");
12948 return -99;
12949 }
12950
12951 /* Construct the API message */
12952 M (PG_INTERFACE_ENABLE_DISABLE_COALESCE, mp);
12953 mp->context = 0;
12954 mp->coalesce_enabled = enable;
12955 mp->sw_if_index = htonl (sw_if_index);
12956
12957 S (mp);
12958 W (ret);
12959 return ret;
12960}
12961
12962int
Damjan Marion7cd468a2016-12-19 23:05:39 +010012963api_ip_source_and_port_range_check_add_del (vat_main_t * vam)
12964{
12965 unformat_input_t *input = vam->input;
12966 vl_api_ip_source_and_port_range_check_add_del_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012967
12968 u16 *low_ports = 0;
12969 u16 *high_ports = 0;
12970 u16 this_low;
12971 u16 this_hi;
Neale Ranns37029302018-08-10 05:30:06 -070012972 vl_api_prefix_t prefix;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012973 u32 tmp, tmp2;
12974 u8 prefix_set = 0;
12975 u32 vrf_id = ~0;
12976 u8 is_add = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060012977 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012978
12979 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
12980 {
Neale Ranns37029302018-08-10 05:30:06 -070012981 if (unformat (input, "%U", unformat_vl_api_prefix, &prefix))
12982 prefix_set = 1;
Damjan Marion7cd468a2016-12-19 23:05:39 +010012983 else if (unformat (input, "vrf %d", &vrf_id))
12984 ;
12985 else if (unformat (input, "del"))
12986 is_add = 0;
12987 else if (unformat (input, "port %d", &tmp))
12988 {
12989 if (tmp == 0 || tmp > 65535)
12990 {
12991 errmsg ("port %d out of range", tmp);
12992 return -99;
12993 }
12994 this_low = tmp;
12995 this_hi = this_low + 1;
12996 vec_add1 (low_ports, this_low);
12997 vec_add1 (high_ports, this_hi);
12998 }
12999 else if (unformat (input, "range %d - %d", &tmp, &tmp2))
13000 {
13001 if ((tmp > tmp2) || (tmp == 0) || (tmp2 > 65535))
13002 {
13003 errmsg ("incorrect range parameters");
13004 return -99;
13005 }
13006 this_low = tmp;
13007 /* Note: in debug CLI +1 is added to high before
13008 passing to real fn that does "the work"
13009 (ip_source_and_port_range_check_add_del).
13010 This fn is a wrapper around the binary API fn a
13011 control plane will call, which expects this increment
13012 to have occurred. Hence letting the binary API control
13013 plane fn do the increment for consistency between VAT
13014 and other control planes.
13015 */
13016 this_hi = tmp2;
13017 vec_add1 (low_ports, this_low);
13018 vec_add1 (high_ports, this_hi);
13019 }
13020 else
13021 break;
13022 }
13023
13024 if (prefix_set == 0)
13025 {
13026 errmsg ("<address>/<mask> not specified");
13027 return -99;
13028 }
13029
13030 if (vrf_id == ~0)
13031 {
13032 errmsg ("VRF ID required, not specified");
13033 return -99;
13034 }
13035
13036 if (vrf_id == 0)
13037 {
13038 errmsg
13039 ("VRF ID should not be default. Should be distinct VRF for this purpose.");
13040 return -99;
13041 }
13042
13043 if (vec_len (low_ports) == 0)
13044 {
13045 errmsg ("At least one port or port range required");
13046 return -99;
13047 }
13048
Jon Loeliger8a2aea32017-01-31 13:19:40 -060013049 M (IP_SOURCE_AND_PORT_RANGE_CHECK_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013050
13051 mp->is_add = is_add;
13052
Neale Ranns37029302018-08-10 05:30:06 -070013053 clib_memcpy (&mp->prefix, &prefix, sizeof (prefix));
Damjan Marion7cd468a2016-12-19 23:05:39 +010013054
Damjan Marion7cd468a2016-12-19 23:05:39 +010013055 mp->number_of_ranges = vec_len (low_ports);
13056
13057 clib_memcpy (mp->low_ports, low_ports, vec_len (low_ports));
13058 vec_free (low_ports);
13059
13060 clib_memcpy (mp->high_ports, high_ports, vec_len (high_ports));
13061 vec_free (high_ports);
13062
13063 mp->vrf_id = ntohl (vrf_id);
13064
Jon Loeliger7bc770c2017-01-31 14:03:33 -060013065 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060013066 W (ret);
13067 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013068}
13069
13070int
13071api_ip_source_and_port_range_check_interface_add_del (vat_main_t * vam)
13072{
13073 unformat_input_t *input = vam->input;
13074 vl_api_ip_source_and_port_range_check_interface_add_del_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013075 u32 sw_if_index = ~0;
13076 int vrf_set = 0;
13077 u32 tcp_out_vrf_id = ~0, udp_out_vrf_id = ~0;
13078 u32 tcp_in_vrf_id = ~0, udp_in_vrf_id = ~0;
13079 u8 is_add = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060013080 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013081
13082 while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
13083 {
13084 if (unformat (input, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
13085 ;
13086 else if (unformat (input, "sw_if_index %d", &sw_if_index))
13087 ;
13088 else if (unformat (input, "tcp-out-vrf %d", &tcp_out_vrf_id))
13089 vrf_set = 1;
13090 else if (unformat (input, "udp-out-vrf %d", &udp_out_vrf_id))
13091 vrf_set = 1;
13092 else if (unformat (input, "tcp-in-vrf %d", &tcp_in_vrf_id))
13093 vrf_set = 1;
13094 else if (unformat (input, "udp-in-vrf %d", &udp_in_vrf_id))
13095 vrf_set = 1;
13096 else if (unformat (input, "del"))
13097 is_add = 0;
13098 else
13099 break;
13100 }
13101
13102 if (sw_if_index == ~0)
13103 {
13104 errmsg ("Interface required but not specified");
13105 return -99;
13106 }
13107
13108 if (vrf_set == 0)
13109 {
13110 errmsg ("VRF ID required but not specified");
13111 return -99;
13112 }
13113
13114 if (tcp_out_vrf_id == 0
13115 || udp_out_vrf_id == 0 || tcp_in_vrf_id == 0 || udp_in_vrf_id == 0)
13116 {
13117 errmsg
13118 ("VRF ID should not be default. Should be distinct VRF for this purpose.");
13119 return -99;
13120 }
13121
13122 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060013123 M (IP_SOURCE_AND_PORT_RANGE_CHECK_INTERFACE_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013124
13125 mp->sw_if_index = ntohl (sw_if_index);
13126 mp->is_add = is_add;
13127 mp->tcp_out_vrf_id = ntohl (tcp_out_vrf_id);
13128 mp->udp_out_vrf_id = ntohl (udp_out_vrf_id);
13129 mp->tcp_in_vrf_id = ntohl (tcp_in_vrf_id);
13130 mp->udp_in_vrf_id = ntohl (udp_in_vrf_id);
13131
13132 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -060013133 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013134
13135 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -060013136 W (ret);
13137 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013138}
13139
13140static int
Pavel Kotuceke88865d2018-11-28 07:42:11 +010013141api_set_punt (vat_main_t * vam)
Damjan Marion7cd468a2016-12-19 23:05:39 +010013142{
13143 unformat_input_t *i = vam->input;
Neale Ranns50f0ac02019-05-15 02:13:37 -070013144 vl_api_address_family_t af;
Pavel Kotuceke88865d2018-11-28 07:42:11 +010013145 vl_api_set_punt_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013146 u32 protocol = ~0;
13147 u32 port = ~0;
13148 int is_add = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060013149 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013150
13151 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13152 {
Neale Ranns50f0ac02019-05-15 02:13:37 -070013153 if (unformat (i, "%U", unformat_vl_api_address_family, &af))
Damjan Marion7cd468a2016-12-19 23:05:39 +010013154 ;
13155 else if (unformat (i, "protocol %d", &protocol))
13156 ;
13157 else if (unformat (i, "port %d", &port))
13158 ;
13159 else if (unformat (i, "del"))
13160 is_add = 0;
13161 else
13162 {
13163 clib_warning ("parse error '%U'", format_unformat_error, i);
13164 return -99;
13165 }
13166 }
13167
Pavel Kotuceke88865d2018-11-28 07:42:11 +010013168 M (SET_PUNT, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013169
13170 mp->is_add = (u8) is_add;
Neale Ranns50f0ac02019-05-15 02:13:37 -070013171 mp->punt.type = PUNT_API_TYPE_L4;
13172 mp->punt.punt.l4.af = af;
13173 mp->punt.punt.l4.protocol = (u8) protocol;
13174 mp->punt.punt.l4.port = htons ((u16) port);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013175
Jon Loeliger7bc770c2017-01-31 14:03:33 -060013176 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060013177 W (ret);
13178 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013179}
13180
Damjan Marion7cd468a2016-12-19 23:05:39 +010013181static int
13182api_delete_subif (vat_main_t * vam)
13183{
13184 unformat_input_t *i = vam->input;
13185 vl_api_delete_subif_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013186 u32 sw_if_index = ~0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060013187 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013188
13189 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13190 {
13191 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
13192 ;
13193 if (unformat (i, "sw_if_index %d", &sw_if_index))
13194 ;
13195 else
13196 break;
13197 }
13198
13199 if (sw_if_index == ~0)
13200 {
13201 errmsg ("missing sw_if_index");
13202 return -99;
13203 }
13204
13205 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060013206 M (DELETE_SUBIF, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013207 mp->sw_if_index = ntohl (sw_if_index);
13208
Jon Loeliger7bc770c2017-01-31 14:03:33 -060013209 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060013210 W (ret);
13211 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013212}
13213
13214#define foreach_pbb_vtr_op \
13215_("disable", L2_VTR_DISABLED) \
13216_("pop", L2_VTR_POP_2) \
13217_("push", L2_VTR_PUSH_2)
13218
13219static int
13220api_l2_interface_pbb_tag_rewrite (vat_main_t * vam)
13221{
13222 unformat_input_t *i = vam->input;
13223 vl_api_l2_interface_pbb_tag_rewrite_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013224 u32 sw_if_index = ~0, vtr_op = ~0;
13225 u16 outer_tag = ~0;
13226 u8 dmac[6], smac[6];
13227 u8 dmac_set = 0, smac_set = 0;
13228 u16 vlanid = 0;
13229 u32 sid = ~0;
13230 u32 tmp;
Jon Loeliger56c7b012017-02-01 12:31:41 -060013231 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013232
13233 /* Shut up coverity */
Dave Barachb7b92992018-10-17 10:38:51 -040013234 clib_memset (dmac, 0, sizeof (dmac));
13235 clib_memset (smac, 0, sizeof (smac));
Damjan Marion7cd468a2016-12-19 23:05:39 +010013236
13237 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13238 {
13239 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
13240 ;
13241 else if (unformat (i, "sw_if_index %d", &sw_if_index))
13242 ;
13243 else if (unformat (i, "vtr_op %d", &vtr_op))
13244 ;
13245#define _(n,v) else if (unformat(i, n)) {vtr_op = v;}
13246 foreach_pbb_vtr_op
13247#undef _
13248 else if (unformat (i, "translate_pbb_stag"))
13249 {
13250 if (unformat (i, "%d", &tmp))
13251 {
13252 vtr_op = L2_VTR_TRANSLATE_2_1;
13253 outer_tag = tmp;
13254 }
13255 else
13256 {
13257 errmsg
13258 ("translate_pbb_stag operation requires outer tag definition");
13259 return -99;
13260 }
13261 }
13262 else if (unformat (i, "dmac %U", unformat_ethernet_address, dmac))
13263 dmac_set++;
13264 else if (unformat (i, "smac %U", unformat_ethernet_address, smac))
13265 smac_set++;
13266 else if (unformat (i, "sid %d", &sid))
13267 ;
13268 else if (unformat (i, "vlanid %d", &tmp))
13269 vlanid = tmp;
13270 else
13271 {
13272 clib_warning ("parse error '%U'", format_unformat_error, i);
13273 return -99;
13274 }
13275 }
13276
13277 if ((sw_if_index == ~0) || (vtr_op == ~0))
13278 {
13279 errmsg ("missing sw_if_index or vtr operation");
13280 return -99;
13281 }
13282 if (((vtr_op == L2_VTR_PUSH_2) || (vtr_op == L2_VTR_TRANSLATE_2_2))
13283 && ((dmac_set == 0) || (smac_set == 0) || (sid == ~0)))
13284 {
13285 errmsg
13286 ("push and translate_qinq operations require dmac, smac, sid and optionally vlanid");
13287 return -99;
13288 }
13289
Jon Loeliger8a2aea32017-01-31 13:19:40 -060013290 M (L2_INTERFACE_PBB_TAG_REWRITE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013291 mp->sw_if_index = ntohl (sw_if_index);
13292 mp->vtr_op = ntohl (vtr_op);
13293 mp->outer_tag = ntohs (outer_tag);
13294 clib_memcpy (mp->b_dmac, dmac, sizeof (dmac));
13295 clib_memcpy (mp->b_smac, smac, sizeof (smac));
13296 mp->b_vlanid = ntohs (vlanid);
13297 mp->i_sid = ntohl (sid);
13298
Jon Loeliger7bc770c2017-01-31 14:03:33 -060013299 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060013300 W (ret);
13301 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013302}
13303
13304static int
13305api_flow_classify_set_interface (vat_main_t * vam)
13306{
13307 unformat_input_t *i = vam->input;
13308 vl_api_flow_classify_set_interface_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013309 u32 sw_if_index;
13310 int sw_if_index_set;
13311 u32 ip4_table_index = ~0;
13312 u32 ip6_table_index = ~0;
13313 u8 is_add = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060013314 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013315
13316 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13317 {
13318 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
13319 sw_if_index_set = 1;
13320 else if (unformat (i, "sw_if_index %d", &sw_if_index))
13321 sw_if_index_set = 1;
13322 else if (unformat (i, "del"))
13323 is_add = 0;
13324 else if (unformat (i, "ip4-table %d", &ip4_table_index))
13325 ;
13326 else if (unformat (i, "ip6-table %d", &ip6_table_index))
13327 ;
13328 else
13329 {
13330 clib_warning ("parse error '%U'", format_unformat_error, i);
13331 return -99;
13332 }
13333 }
13334
13335 if (sw_if_index_set == 0)
13336 {
13337 errmsg ("missing interface name or sw_if_index");
13338 return -99;
13339 }
13340
Jon Loeliger8a2aea32017-01-31 13:19:40 -060013341 M (FLOW_CLASSIFY_SET_INTERFACE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013342
13343 mp->sw_if_index = ntohl (sw_if_index);
13344 mp->ip4_table_index = ntohl (ip4_table_index);
13345 mp->ip6_table_index = ntohl (ip6_table_index);
13346 mp->is_add = is_add;
13347
Jon Loeliger7bc770c2017-01-31 14:03:33 -060013348 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060013349 W (ret);
13350 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013351}
13352
13353static int
13354api_flow_classify_dump (vat_main_t * vam)
13355{
13356 unformat_input_t *i = vam->input;
13357 vl_api_flow_classify_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060013358 vl_api_control_ping_t *mp_ping;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013359 u8 type = FLOW_CLASSIFY_N_TABLES;
Jon Loeliger56c7b012017-02-01 12:31:41 -060013360 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013361
13362 if (unformat (i, "type %U", unformat_flow_classify_table_type, &type))
13363 ;
13364 else
13365 {
13366 errmsg ("classify table type must be specified");
13367 return -99;
13368 }
13369
13370 if (!vam->json_output)
13371 {
13372 print (vam->ofp, "%10s%20s", "Intfc idx", "Classify table");
13373 }
13374
Jon Loeliger8a2aea32017-01-31 13:19:40 -060013375 M (FLOW_CLASSIFY_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013376 mp->type = type;
13377 /* send it... */
Jon Loeliger7bc770c2017-01-31 14:03:33 -060013378 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013379
13380 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040013381 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060013382 S (mp_ping);
13383
Damjan Marion7cd468a2016-12-19 23:05:39 +010013384 /* Wait for a reply... */
Jon Loeliger56c7b012017-02-01 12:31:41 -060013385 W (ret);
13386 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013387}
13388
13389static int
13390api_feature_enable_disable (vat_main_t * vam)
13391{
13392 unformat_input_t *i = vam->input;
13393 vl_api_feature_enable_disable_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013394 u8 *arc_name = 0;
13395 u8 *feature_name = 0;
13396 u32 sw_if_index = ~0;
13397 u8 enable = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060013398 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013399
13400 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13401 {
13402 if (unformat (i, "arc_name %s", &arc_name))
13403 ;
13404 else if (unformat (i, "feature_name %s", &feature_name))
13405 ;
13406 else
13407 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
13408 ;
13409 else if (unformat (i, "sw_if_index %d", &sw_if_index))
13410 ;
13411 else if (unformat (i, "disable"))
13412 enable = 0;
13413 else
13414 break;
13415 }
13416
13417 if (arc_name == 0)
13418 {
13419 errmsg ("missing arc name");
13420 return -99;
13421 }
13422 if (vec_len (arc_name) > 63)
13423 {
13424 errmsg ("arc name too long");
13425 }
13426
13427 if (feature_name == 0)
13428 {
13429 errmsg ("missing feature name");
13430 return -99;
13431 }
13432 if (vec_len (feature_name) > 63)
13433 {
13434 errmsg ("feature name too long");
13435 }
13436
13437 if (sw_if_index == ~0)
13438 {
13439 errmsg ("missing interface name or sw_if_index");
13440 return -99;
13441 }
13442
13443 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060013444 M (FEATURE_ENABLE_DISABLE, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013445 mp->sw_if_index = ntohl (sw_if_index);
13446 mp->enable = enable;
13447 clib_memcpy (mp->arc_name, arc_name, vec_len (arc_name));
13448 clib_memcpy (mp->feature_name, feature_name, vec_len (feature_name));
13449 vec_free (arc_name);
13450 vec_free (feature_name);
13451
Jon Loeliger7bc770c2017-01-31 14:03:33 -060013452 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060013453 W (ret);
13454 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013455}
13456
13457static int
Mohsin Kazmi29467b52019-10-08 19:42:38 +020013458api_feature_gso_enable_disable (vat_main_t * vam)
13459{
13460 unformat_input_t *i = vam->input;
13461 vl_api_feature_gso_enable_disable_t *mp;
13462 u32 sw_if_index = ~0;
13463 u8 enable = 1;
13464 int ret;
13465
13466 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13467 {
13468 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
13469 ;
13470 else if (unformat (i, "sw_if_index %d", &sw_if_index))
13471 ;
13472 else if (unformat (i, "enable"))
13473 enable = 1;
13474 else if (unformat (i, "disable"))
13475 enable = 0;
13476 else
13477 break;
13478 }
13479
13480 if (sw_if_index == ~0)
13481 {
13482 errmsg ("missing interface name or sw_if_index");
13483 return -99;
13484 }
13485
13486 /* Construct the API message */
13487 M (FEATURE_GSO_ENABLE_DISABLE, mp);
13488 mp->sw_if_index = ntohl (sw_if_index);
13489 mp->enable_disable = enable;
13490
13491 S (mp);
13492 W (ret);
13493 return ret;
13494}
13495
13496static int
Damjan Marion7cd468a2016-12-19 23:05:39 +010013497api_sw_interface_tag_add_del (vat_main_t * vam)
13498{
13499 unformat_input_t *i = vam->input;
13500 vl_api_sw_interface_tag_add_del_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013501 u32 sw_if_index = ~0;
13502 u8 *tag = 0;
13503 u8 enable = 1;
Jon Loeliger56c7b012017-02-01 12:31:41 -060013504 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013505
13506 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13507 {
13508 if (unformat (i, "tag %s", &tag))
13509 ;
13510 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
13511 ;
13512 else if (unformat (i, "sw_if_index %d", &sw_if_index))
13513 ;
13514 else if (unformat (i, "del"))
13515 enable = 0;
13516 else
13517 break;
13518 }
13519
13520 if (sw_if_index == ~0)
13521 {
13522 errmsg ("missing interface name or sw_if_index");
13523 return -99;
13524 }
13525
13526 if (enable && (tag == 0))
13527 {
13528 errmsg ("no tag specified");
13529 return -99;
13530 }
13531
13532 /* Construct the API message */
Jon Loeliger8a2aea32017-01-31 13:19:40 -060013533 M (SW_INTERFACE_TAG_ADD_DEL, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013534 mp->sw_if_index = ntohl (sw_if_index);
13535 mp->is_add = enable;
13536 if (enable)
Ole Troane5ff5a32019-08-23 22:55:18 +020013537 strncpy ((char *) mp->tag, (char *) tag, ARRAY_LEN (mp->tag) - 1);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013538 vec_free (tag);
13539
Jon Loeliger7bc770c2017-01-31 14:03:33 -060013540 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060013541 W (ret);
13542 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013543}
13544
Matthew Smithe0792fd2019-07-12 11:48:24 -050013545static int
13546api_sw_interface_add_del_mac_address (vat_main_t * vam)
13547{
13548 unformat_input_t *i = vam->input;
13549 vl_api_mac_address_t mac = { 0 };
13550 vl_api_sw_interface_add_del_mac_address_t *mp;
13551 u32 sw_if_index = ~0;
13552 u8 is_add = 1;
13553 u8 mac_set = 0;
13554 int ret;
13555
13556 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13557 {
13558 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
13559 ;
13560 else if (unformat (i, "sw_if_index %d", &sw_if_index))
13561 ;
13562 else if (unformat (i, "%U", unformat_vl_api_mac_address, &mac))
13563 mac_set++;
13564 else if (unformat (i, "del"))
13565 is_add = 0;
13566 else
13567 break;
13568 }
13569
13570 if (sw_if_index == ~0)
13571 {
13572 errmsg ("missing interface name or sw_if_index");
13573 return -99;
13574 }
13575
13576 if (!mac_set)
13577 {
13578 errmsg ("missing MAC address");
13579 return -99;
13580 }
13581
13582 /* Construct the API message */
13583 M (SW_INTERFACE_ADD_DEL_MAC_ADDRESS, mp);
13584 mp->sw_if_index = ntohl (sw_if_index);
13585 mp->is_add = is_add;
13586 clib_memcpy (&mp->addr, &mac, sizeof (mac));
13587
13588 S (mp);
13589 W (ret);
13590 return ret;
13591}
13592
Damjan Marion7cd468a2016-12-19 23:05:39 +010013593static void vl_api_l2_xconnect_details_t_handler
13594 (vl_api_l2_xconnect_details_t * mp)
13595{
13596 vat_main_t *vam = &vat_main;
13597
13598 print (vam->ofp, "%15d%15d",
13599 ntohl (mp->rx_sw_if_index), ntohl (mp->tx_sw_if_index));
13600}
13601
13602static void vl_api_l2_xconnect_details_t_handler_json
13603 (vl_api_l2_xconnect_details_t * mp)
13604{
13605 vat_main_t *vam = &vat_main;
13606 vat_json_node_t *node = NULL;
13607
13608 if (VAT_JSON_ARRAY != vam->json_tree.type)
13609 {
13610 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
13611 vat_json_init_array (&vam->json_tree);
13612 }
13613 node = vat_json_array_add (&vam->json_tree);
13614
13615 vat_json_init_object (node);
13616 vat_json_object_add_uint (node, "rx_sw_if_index",
13617 ntohl (mp->rx_sw_if_index));
13618 vat_json_object_add_uint (node, "tx_sw_if_index",
13619 ntohl (mp->tx_sw_if_index));
13620}
13621
13622static int
13623api_l2_xconnect_dump (vat_main_t * vam)
13624{
13625 vl_api_l2_xconnect_dump_t *mp;
Jon Loeliger2d23eca2017-02-01 13:09:58 -060013626 vl_api_control_ping_t *mp_ping;
Jon Loeliger56c7b012017-02-01 12:31:41 -060013627 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013628
13629 if (!vam->json_output)
13630 {
13631 print (vam->ofp, "%15s%15s", "rx_sw_if_index", "tx_sw_if_index");
13632 }
13633
Jon Loeliger8a2aea32017-01-31 13:19:40 -060013634 M (L2_XCONNECT_DUMP, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013635
Jon Loeliger7bc770c2017-01-31 14:03:33 -060013636 S (mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013637
13638 /* Use a control ping for synchronization */
Dave Barach59b25652017-09-10 15:04:27 -040013639 MPING (CONTROL_PING, mp_ping);
Jon Loeliger2d23eca2017-02-01 13:09:58 -060013640 S (mp_ping);
13641
Jon Loeliger56c7b012017-02-01 12:31:41 -060013642 W (ret);
13643 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013644}
13645
13646static int
Ole Troand7231612018-06-07 10:17:57 +020013647api_hw_interface_set_mtu (vat_main_t * vam)
Damjan Marion7cd468a2016-12-19 23:05:39 +010013648{
13649 unformat_input_t *i = vam->input;
Ole Troand7231612018-06-07 10:17:57 +020013650 vl_api_hw_interface_set_mtu_t *mp;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013651 u32 sw_if_index = ~0;
13652 u32 mtu = 0;
Jon Loeliger56c7b012017-02-01 12:31:41 -060013653 int ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013654
13655 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13656 {
13657 if (unformat (i, "mtu %d", &mtu))
13658 ;
13659 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
13660 ;
13661 else if (unformat (i, "sw_if_index %d", &sw_if_index))
13662 ;
13663 else
13664 break;
13665 }
13666
13667 if (sw_if_index == ~0)
13668 {
13669 errmsg ("missing interface name or sw_if_index");
13670 return -99;
13671 }
13672
13673 if (mtu == 0)
13674 {
13675 errmsg ("no mtu specified");
13676 return -99;
13677 }
13678
13679 /* Construct the API message */
Ole Troand7231612018-06-07 10:17:57 +020013680 M (HW_INTERFACE_SET_MTU, mp);
Damjan Marion7cd468a2016-12-19 23:05:39 +010013681 mp->sw_if_index = ntohl (sw_if_index);
13682 mp->mtu = ntohs ((u16) mtu);
13683
Jon Loeliger7bc770c2017-01-31 14:03:33 -060013684 S (mp);
Jon Loeliger56c7b012017-02-01 12:31:41 -060013685 W (ret);
13686 return ret;
Damjan Marion7cd468a2016-12-19 23:05:39 +010013687}
13688
Pavel Kotucek6899a302017-06-08 08:46:10 +020013689static int
13690api_p2p_ethernet_add (vat_main_t * vam)
13691{
13692 unformat_input_t *i = vam->input;
13693 vl_api_p2p_ethernet_add_t *mp;
13694 u32 parent_if_index = ~0;
Pavel Kotucek15ac81c2017-06-20 14:00:26 +020013695 u32 sub_id = ~0;
Pavel Kotucek6899a302017-06-08 08:46:10 +020013696 u8 remote_mac[6];
13697 u8 mac_set = 0;
13698 int ret;
13699
Dave Barachb7b92992018-10-17 10:38:51 -040013700 clib_memset (remote_mac, 0, sizeof (remote_mac));
Pavel Kotucek6899a302017-06-08 08:46:10 +020013701 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13702 {
13703 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &parent_if_index))
13704 ;
13705 else if (unformat (i, "sw_if_index %d", &parent_if_index))
13706 ;
13707 else
13708 if (unformat
13709 (i, "remote_mac %U", unformat_ethernet_address, remote_mac))
13710 mac_set++;
Pavel Kotucek15ac81c2017-06-20 14:00:26 +020013711 else if (unformat (i, "sub_id %d", &sub_id))
13712 ;
Pavel Kotucek6899a302017-06-08 08:46:10 +020013713 else
13714 {
13715 clib_warning ("parse error '%U'", format_unformat_error, i);
13716 return -99;
13717 }
13718 }
13719
13720 if (parent_if_index == ~0)
13721 {
13722 errmsg ("missing interface name or sw_if_index");
13723 return -99;
13724 }
13725 if (mac_set == 0)
13726 {
13727 errmsg ("missing remote mac address");
13728 return -99;
13729 }
Pavel Kotucek15ac81c2017-06-20 14:00:26 +020013730 if (sub_id == ~0)
13731 {
13732 errmsg ("missing sub-interface id");
13733 return -99;
13734 }
Pavel Kotucek6899a302017-06-08 08:46:10 +020013735
13736 M (P2P_ETHERNET_ADD, mp);
13737 mp->parent_if_index = ntohl (parent_if_index);
Pavel Kotucek15ac81c2017-06-20 14:00:26 +020013738 mp->subif_id = ntohl (sub_id);
Pavel Kotucek6899a302017-06-08 08:46:10 +020013739 clib_memcpy (mp->remote_mac, remote_mac, sizeof (remote_mac));
13740
13741 S (mp);
13742 W (ret);
13743 return ret;
13744}
13745
13746static int
13747api_p2p_ethernet_del (vat_main_t * vam)
13748{
13749 unformat_input_t *i = vam->input;
13750 vl_api_p2p_ethernet_del_t *mp;
13751 u32 parent_if_index = ~0;
13752 u8 remote_mac[6];
13753 u8 mac_set = 0;
13754 int ret;
13755
Dave Barachb7b92992018-10-17 10:38:51 -040013756 clib_memset (remote_mac, 0, sizeof (remote_mac));
Pavel Kotucek6899a302017-06-08 08:46:10 +020013757 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13758 {
13759 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &parent_if_index))
13760 ;
13761 else if (unformat (i, "sw_if_index %d", &parent_if_index))
13762 ;
13763 else
13764 if (unformat
13765 (i, "remote_mac %U", unformat_ethernet_address, remote_mac))
13766 mac_set++;
13767 else
13768 {
13769 clib_warning ("parse error '%U'", format_unformat_error, i);
13770 return -99;
13771 }
13772 }
13773
13774 if (parent_if_index == ~0)
13775 {
13776 errmsg ("missing interface name or sw_if_index");
13777 return -99;
13778 }
13779 if (mac_set == 0)
13780 {
13781 errmsg ("missing remote mac address");
13782 return -99;
13783 }
13784
13785 M (P2P_ETHERNET_DEL, mp);
13786 mp->parent_if_index = ntohl (parent_if_index);
13787 clib_memcpy (mp->remote_mac, remote_mac, sizeof (remote_mac));
13788
13789 S (mp);
13790 W (ret);
13791 return ret;
13792}
Damjan Marion7cd468a2016-12-19 23:05:39 +010013793
13794static int
Dave Barach3bbcfab2017-08-15 19:03:44 -040013795api_tcp_configure_src_addresses (vat_main_t * vam)
13796{
13797 vl_api_tcp_configure_src_addresses_t *mp;
13798 unformat_input_t *i = vam->input;
Neale Rannscbe25aa2019-09-30 10:53:31 +000013799 vl_api_address_t first, last;
Dave Barach3bbcfab2017-08-15 19:03:44 -040013800 u8 range_set = 0;
13801 u32 vrf_id = 0;
13802 int ret;
13803
13804 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13805 {
13806 if (unformat (i, "%U - %U",
Neale Rannscbe25aa2019-09-30 10:53:31 +000013807 unformat_vl_api_address, &first,
13808 unformat_vl_api_address, &last))
Dave Barach3bbcfab2017-08-15 19:03:44 -040013809 {
13810 if (range_set)
13811 {
13812 errmsg ("one range per message (range already set)");
13813 return -99;
13814 }
13815 range_set = 1;
13816 }
Dave Barach3bbcfab2017-08-15 19:03:44 -040013817 else if (unformat (i, "vrf %d", &vrf_id))
13818 ;
13819 else
13820 break;
13821 }
13822
13823 if (range_set == 0)
13824 {
13825 errmsg ("address range not set");
13826 return -99;
13827 }
13828
13829 M (TCP_CONFIGURE_SRC_ADDRESSES, mp);
Neale Rannscbe25aa2019-09-30 10:53:31 +000013830
Dave Barach3bbcfab2017-08-15 19:03:44 -040013831 mp->vrf_id = ntohl (vrf_id);
Neale Rannscbe25aa2019-09-30 10:53:31 +000013832 clib_memcpy (&mp->first_address, &first, sizeof (first));
13833 clib_memcpy (&mp->last_address, &last, sizeof (last));
13834
Dave Barach3bbcfab2017-08-15 19:03:44 -040013835 S (mp);
13836 W (ret);
13837 return ret;
13838}
13839
Florin Coras6e8c6672017-11-10 09:03:54 -080013840static void vl_api_app_namespace_add_del_reply_t_handler
13841 (vl_api_app_namespace_add_del_reply_t * mp)
13842{
13843 vat_main_t *vam = &vat_main;
13844 i32 retval = ntohl (mp->retval);
13845 if (vam->async_mode)
13846 {
13847 vam->async_errors += (retval < 0);
13848 }
13849 else
13850 {
13851 vam->retval = retval;
13852 if (retval == 0)
13853 errmsg ("app ns index %d\n", ntohl (mp->appns_index));
13854 vam->result_ready = 1;
13855 }
13856}
13857
13858static void vl_api_app_namespace_add_del_reply_t_handler_json
13859 (vl_api_app_namespace_add_del_reply_t * mp)
13860{
13861 vat_main_t *vam = &vat_main;
13862 vat_json_node_t node;
13863
13864 vat_json_init_object (&node);
13865 vat_json_object_add_int (&node, "retval", ntohl (mp->retval));
13866 vat_json_object_add_uint (&node, "appns_index", ntohl (mp->appns_index));
13867
13868 vat_json_print (vam->ofp, &node);
13869 vat_json_free (&node);
13870
13871 vam->retval = ntohl (mp->retval);
13872 vam->result_ready = 1;
13873}
13874
Dave Barach3bbcfab2017-08-15 19:03:44 -040013875static int
Florin Corascea194d2017-10-02 00:18:51 -070013876api_app_namespace_add_del (vat_main_t * vam)
13877{
13878 vl_api_app_namespace_add_del_t *mp;
13879 unformat_input_t *i = vam->input;
13880 u8 *ns_id = 0, secret_set = 0, sw_if_index_set = 0;
13881 u32 sw_if_index, ip4_fib_id, ip6_fib_id;
13882 u64 secret;
13883 int ret;
13884
13885 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13886 {
13887 if (unformat (i, "id %_%v%_", &ns_id))
13888 ;
13889 else if (unformat (i, "secret %lu", &secret))
13890 secret_set = 1;
13891 else if (unformat (i, "sw_if_index %d", &sw_if_index))
13892 sw_if_index_set = 1;
13893 else if (unformat (i, "ip4_fib_id %d", &ip4_fib_id))
13894 ;
13895 else if (unformat (i, "ip6_fib_id %d", &ip6_fib_id))
13896 ;
13897 else
13898 break;
13899 }
13900 if (!ns_id || !secret_set || !sw_if_index_set)
13901 {
13902 errmsg ("namespace id, secret and sw_if_index must be set");
13903 return -99;
13904 }
13905 if (vec_len (ns_id) > 64)
13906 {
13907 errmsg ("namespace id too long");
13908 return -99;
13909 }
13910 M (APP_NAMESPACE_ADD_DEL, mp);
13911
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010013912 vl_api_vec_to_api_string (ns_id, &mp->namespace_id);
Florin Coras9a9adb22017-10-26 08:16:59 -070013913 mp->secret = clib_host_to_net_u64 (secret);
Florin Corascea194d2017-10-02 00:18:51 -070013914 mp->sw_if_index = clib_host_to_net_u32 (sw_if_index);
13915 mp->ip4_fib_id = clib_host_to_net_u32 (ip4_fib_id);
13916 mp->ip6_fib_id = clib_host_to_net_u32 (ip6_fib_id);
13917 vec_free (ns_id);
13918 S (mp);
13919 W (ret);
13920 return ret;
13921}
13922
13923static int
Florin Coras90a63982017-12-19 04:50:01 -080013924api_sock_init_shm (vat_main_t * vam)
13925{
13926#if VPP_API_TEST_BUILTIN == 0
13927 unformat_input_t *i = vam->input;
13928 vl_api_shm_elem_config_t *config = 0;
13929 u64 size = 64 << 20;
13930 int rv;
13931
13932 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
13933 {
13934 if (unformat (i, "size %U", unformat_memory_size, &size))
13935 ;
13936 else
13937 break;
13938 }
13939
Dave Barach78958722018-05-10 16:44:27 -040013940 /*
13941 * Canned custom ring allocator config.
13942 * Should probably parse all of this
13943 */
13944 vec_validate (config, 6);
Florin Coras90a63982017-12-19 04:50:01 -080013945 config[0].type = VL_API_VLIB_RING;
Florin Coras90a63982017-12-19 04:50:01 -080013946 config[0].size = 256;
Dave Barach78958722018-05-10 16:44:27 -040013947 config[0].count = 32;
13948
13949 config[1].type = VL_API_VLIB_RING;
Florin Coras90a63982017-12-19 04:50:01 -080013950 config[1].size = 1024;
Dave Barach78958722018-05-10 16:44:27 -040013951 config[1].count = 16;
13952
13953 config[2].type = VL_API_VLIB_RING;
Florin Coras90a63982017-12-19 04:50:01 -080013954 config[2].size = 4096;
Dave Barach78958722018-05-10 16:44:27 -040013955 config[2].count = 2;
13956
13957 config[3].type = VL_API_CLIENT_RING;
13958 config[3].size = 256;
13959 config[3].count = 32;
13960
13961 config[4].type = VL_API_CLIENT_RING;
13962 config[4].size = 1024;
13963 config[4].count = 16;
13964
13965 config[5].type = VL_API_CLIENT_RING;
13966 config[5].size = 4096;
13967 config[5].count = 2;
13968
13969 config[6].type = VL_API_QUEUE;
13970 config[6].count = 128;
13971 config[6].size = sizeof (uword);
13972
Tomasz Kulasek97dcf5b2019-01-31 18:26:32 +010013973 rv = vl_socket_client_init_shm (config, 1 /* want_pthread */ );
Florin Coras90a63982017-12-19 04:50:01 -080013974 if (!rv)
13975 vam->client_index_invalid = 1;
13976 return rv;
13977#else
13978 return -99;
13979#endif
13980}
13981
Florin Coras6c36f532017-11-03 18:32:34 -070013982static void
13983vl_api_session_rules_details_t_handler (vl_api_session_rules_details_t * mp)
13984{
13985 vat_main_t *vam = &vat_main;
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010013986 fib_prefix_t lcl, rmt;
Florin Coras6c36f532017-11-03 18:32:34 -070013987
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010013988 ip_prefix_decode (&mp->lcl, &lcl);
13989 ip_prefix_decode (&mp->rmt, &rmt);
13990
13991 if (lcl.fp_proto == FIB_PROTOCOL_IP4)
Florin Coras6c36f532017-11-03 18:32:34 -070013992 {
Florin Corasc97a7392017-11-05 23:07:07 -080013993 print (vam->ofp,
13994 "appns %u tp %u scope %d %U/%d %d %U/%d %d action: %d tag: %s",
Steven85dbac02017-11-07 16:29:53 -080013995 clib_net_to_host_u32 (mp->appns_index), mp->transport_proto,
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010013996 mp->scope, format_ip4_address, &lcl.fp_addr.ip4, lcl.fp_len,
Steven85dbac02017-11-07 16:29:53 -080013997 clib_net_to_host_u16 (mp->lcl_port), format_ip4_address,
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010013998 &rmt.fp_addr.ip4, rmt.fp_len,
13999 clib_net_to_host_u16 (mp->rmt_port),
Steven85dbac02017-11-07 16:29:53 -080014000 clib_net_to_host_u32 (mp->action_index), mp->tag);
Florin Coras6c36f532017-11-03 18:32:34 -070014001 }
14002 else
14003 {
Florin Corasc97a7392017-11-05 23:07:07 -080014004 print (vam->ofp,
14005 "appns %u tp %u scope %d %U/%d %d %U/%d %d action: %d tag: %s",
Steven85dbac02017-11-07 16:29:53 -080014006 clib_net_to_host_u32 (mp->appns_index), mp->transport_proto,
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014007 mp->scope, format_ip6_address, &lcl.fp_addr.ip6, lcl.fp_len,
Steven85dbac02017-11-07 16:29:53 -080014008 clib_net_to_host_u16 (mp->lcl_port), format_ip6_address,
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014009 &rmt.fp_addr.ip6, rmt.fp_len,
14010 clib_net_to_host_u16 (mp->rmt_port),
Steven85dbac02017-11-07 16:29:53 -080014011 clib_net_to_host_u32 (mp->action_index), mp->tag);
Florin Coras6c36f532017-11-03 18:32:34 -070014012 }
14013}
14014
14015static void
14016vl_api_session_rules_details_t_handler_json (vl_api_session_rules_details_t *
14017 mp)
14018{
14019 vat_main_t *vam = &vat_main;
14020 vat_json_node_t *node = NULL;
14021 struct in6_addr ip6;
14022 struct in_addr ip4;
14023
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014024 fib_prefix_t lcl, rmt;
14025
14026 ip_prefix_decode (&mp->lcl, &lcl);
14027 ip_prefix_decode (&mp->rmt, &rmt);
14028
Florin Coras6c36f532017-11-03 18:32:34 -070014029 if (VAT_JSON_ARRAY != vam->json_tree.type)
14030 {
14031 ASSERT (VAT_JSON_NONE == vam->json_tree.type);
14032 vat_json_init_array (&vam->json_tree);
14033 }
14034 node = vat_json_array_add (&vam->json_tree);
14035 vat_json_init_object (node);
14036
Florin Coras6c36f532017-11-03 18:32:34 -070014037 vat_json_object_add_uint (node, "appns_index",
14038 clib_net_to_host_u32 (mp->appns_index));
14039 vat_json_object_add_uint (node, "transport_proto", mp->transport_proto);
14040 vat_json_object_add_uint (node, "scope", mp->scope);
14041 vat_json_object_add_uint (node, "action_index",
14042 clib_net_to_host_u32 (mp->action_index));
14043 vat_json_object_add_uint (node, "lcl_port",
14044 clib_net_to_host_u16 (mp->lcl_port));
14045 vat_json_object_add_uint (node, "rmt_port",
14046 clib_net_to_host_u16 (mp->rmt_port));
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014047 vat_json_object_add_uint (node, "lcl_plen", lcl.fp_len);
14048 vat_json_object_add_uint (node, "rmt_plen", rmt.fp_len);
Florin Corasc97a7392017-11-05 23:07:07 -080014049 vat_json_object_add_string_copy (node, "tag", mp->tag);
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014050 if (lcl.fp_proto == FIB_PROTOCOL_IP4)
Florin Coras6c36f532017-11-03 18:32:34 -070014051 {
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014052 clib_memcpy (&ip4, &lcl.fp_addr.ip4, sizeof (ip4));
Florin Coras6c36f532017-11-03 18:32:34 -070014053 vat_json_object_add_ip4 (node, "lcl_ip", ip4);
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014054 clib_memcpy (&ip4, &rmt.fp_addr.ip4, sizeof (ip4));
Florin Coras6c36f532017-11-03 18:32:34 -070014055 vat_json_object_add_ip4 (node, "rmt_ip", ip4);
14056 }
14057 else
14058 {
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014059 clib_memcpy (&ip6, &lcl.fp_addr.ip6, sizeof (ip6));
Florin Coras6c36f532017-11-03 18:32:34 -070014060 vat_json_object_add_ip6 (node, "lcl_ip", ip6);
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014061 clib_memcpy (&ip6, &rmt.fp_addr.ip6, sizeof (ip6));
Florin Coras6c36f532017-11-03 18:32:34 -070014062 vat_json_object_add_ip6 (node, "rmt_ip", ip6);
14063 }
14064}
14065
Florin Coras1c710452017-10-17 00:03:13 -070014066static int
14067api_session_rule_add_del (vat_main_t * vam)
14068{
14069 vl_api_session_rule_add_del_t *mp;
14070 unformat_input_t *i = vam->input;
14071 u32 proto = ~0, lcl_port, rmt_port, action = 0, lcl_plen, rmt_plen;
14072 u32 appns_index = 0, scope = 0;
14073 ip4_address_t lcl_ip4, rmt_ip4;
14074 ip6_address_t lcl_ip6, rmt_ip6;
14075 u8 is_ip4 = 1, conn_set = 0;
Florin Corasc97a7392017-11-05 23:07:07 -080014076 u8 is_add = 1, *tag = 0;
Florin Coras1c710452017-10-17 00:03:13 -070014077 int ret;
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014078 fib_prefix_t lcl, rmt;
Florin Coras1c710452017-10-17 00:03:13 -070014079
14080 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
14081 {
14082 if (unformat (i, "del"))
14083 is_add = 0;
14084 else if (unformat (i, "add"))
14085 ;
14086 else if (unformat (i, "proto tcp"))
14087 proto = 0;
14088 else if (unformat (i, "proto udp"))
14089 proto = 1;
14090 else if (unformat (i, "appns %d", &appns_index))
14091 ;
14092 else if (unformat (i, "scope %d", &scope))
14093 ;
Florin Corasc97a7392017-11-05 23:07:07 -080014094 else if (unformat (i, "tag %_%v%_", &tag))
14095 ;
Florin Coras1c710452017-10-17 00:03:13 -070014096 else
14097 if (unformat
14098 (i, "%U/%d %d %U/%d %d", unformat_ip4_address, &lcl_ip4,
14099 &lcl_plen, &lcl_port, unformat_ip4_address, &rmt_ip4, &rmt_plen,
14100 &rmt_port))
14101 {
14102 is_ip4 = 1;
14103 conn_set = 1;
14104 }
14105 else
14106 if (unformat
14107 (i, "%U/%d %d %U/%d %d", unformat_ip6_address, &lcl_ip6,
14108 &lcl_plen, &lcl_port, unformat_ip6_address, &rmt_ip6, &rmt_plen,
14109 &rmt_port))
14110 {
14111 is_ip4 = 0;
14112 conn_set = 1;
14113 }
14114 else if (unformat (i, "action %d", &action))
14115 ;
14116 else
14117 break;
14118 }
14119 if (proto == ~0 || !conn_set || action == ~0)
14120 {
14121 errmsg ("transport proto, connection and action must be set");
14122 return -99;
14123 }
14124
14125 if (scope > 3)
14126 {
14127 errmsg ("scope should be 0-3");
14128 return -99;
14129 }
14130
14131 M (SESSION_RULE_ADD_DEL, mp);
14132
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014133 clib_memset (&lcl, 0, sizeof (lcl));
14134 clib_memset (&rmt, 0, sizeof (rmt));
14135 if (is_ip4)
14136 {
14137 ip_set (&lcl.fp_addr, &lcl_ip4, 1);
14138 ip_set (&rmt.fp_addr, &rmt_ip4, 1);
14139 lcl.fp_len = lcl_plen;
14140 rmt.fp_len = rmt_plen;
14141 }
14142 else
14143 {
14144 ip_set (&lcl.fp_addr, &lcl_ip6, 0);
14145 ip_set (&rmt.fp_addr, &rmt_ip6, 0);
14146 lcl.fp_len = lcl_plen;
14147 rmt.fp_len = rmt_plen;
14148 }
14149
14150
14151 ip_prefix_encode (&lcl, &mp->lcl);
14152 ip_prefix_encode (&rmt, &mp->rmt);
Florin Corasc97a7392017-11-05 23:07:07 -080014153 mp->lcl_port = clib_host_to_net_u16 ((u16) lcl_port);
14154 mp->rmt_port = clib_host_to_net_u16 ((u16) rmt_port);
Jakub Grajciarb4e5e502020-01-31 09:35:29 +010014155 mp->transport_proto =
14156 proto ? TRANSPORT_PROTO_API_UDP : TRANSPORT_PROTO_API_TCP;
Florin Coras1c710452017-10-17 00:03:13 -070014157 mp->action_index = clib_host_to_net_u32 (action);
14158 mp->appns_index = clib_host_to_net_u32 (appns_index);
14159 mp->scope = scope;
14160 mp->is_add = is_add;
Florin Corasc97a7392017-11-05 23:07:07 -080014161 if (tag)
14162 {
14163 clib_memcpy (mp->tag, tag, vec_len (tag));
14164 vec_free (tag);
14165 }
Florin Coras1c710452017-10-17 00:03:13 -070014166
14167 S (mp);
14168 W (ret);
14169 return ret;
14170}
Dave Barach65457162017-10-10 17:53:14 -040014171
14172static int
Florin Coras6c36f532017-11-03 18:32:34 -070014173api_session_rules_dump (vat_main_t * vam)
14174{
14175 vl_api_session_rules_dump_t *mp;
14176 vl_api_control_ping_t *mp_ping;
14177 int ret;
14178
14179 if (!vam->json_output)
14180 {
14181 print (vam->ofp, "%=20s", "Session Rules");
14182 }
14183
14184 M (SESSION_RULES_DUMP, mp);
14185 /* send it... */
14186 S (mp);
14187
14188 /* Use a control ping for synchronization */
14189 MPING (CONTROL_PING, mp_ping);
14190 S (mp_ping);
14191
14192 /* Wait for a reply... */
14193 W (ret);
14194 return ret;
14195}
14196
14197static int
Florin Coras595992c2017-11-06 17:17:08 -080014198api_ip_container_proxy_add_del (vat_main_t * vam)
14199{
14200 vl_api_ip_container_proxy_add_del_t *mp;
14201 unformat_input_t *i = vam->input;
Neale Ranns37029302018-08-10 05:30:06 -070014202 u32 sw_if_index = ~0;
14203 vl_api_prefix_t pfx = { };
Florin Coras595992c2017-11-06 17:17:08 -080014204 u8 is_add = 1;
14205 int ret;
14206
14207 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
14208 {
14209 if (unformat (i, "del"))
14210 is_add = 0;
14211 else if (unformat (i, "add"))
14212 ;
Neale Ranns37029302018-08-10 05:30:06 -070014213 if (unformat (i, "%U", unformat_vl_api_prefix, &pfx))
14214 ;
Florin Coras595992c2017-11-06 17:17:08 -080014215 else if (unformat (i, "sw_if_index %u", &sw_if_index))
14216 ;
14217 else
14218 break;
14219 }
Paul Vinciguerraab055082019-06-06 14:07:55 -040014220 if (sw_if_index == ~0 || pfx.len == 0)
Florin Coras595992c2017-11-06 17:17:08 -080014221 {
14222 errmsg ("address and sw_if_index must be set");
14223 return -99;
14224 }
14225
14226 M (IP_CONTAINER_PROXY_ADD_DEL, mp);
14227
Florin Coras595992c2017-11-06 17:17:08 -080014228 mp->sw_if_index = clib_host_to_net_u32 (sw_if_index);
Florin Coras595992c2017-11-06 17:17:08 -080014229 mp->is_add = is_add;
Neale Ranns37029302018-08-10 05:30:06 -070014230 clib_memcpy (&mp->pfx, &pfx, sizeof (pfx));
Florin Coras595992c2017-11-06 17:17:08 -080014231
14232 S (mp);
14233 W (ret);
14234 return ret;
14235}
14236
14237static int
Igor Mikhailov (imichail)582caa32018-04-26 21:33:02 -070014238api_qos_record_enable_disable (vat_main_t * vam)
14239{
14240 unformat_input_t *i = vam->input;
14241 vl_api_qos_record_enable_disable_t *mp;
14242 u32 sw_if_index, qs = 0xff;
14243 u8 sw_if_index_set = 0;
14244 u8 enable = 1;
14245 int ret;
14246
14247 while (unformat_check_input (i) != UNFORMAT_END_OF_INPUT)
14248 {
14249 if (unformat (i, "%U", api_unformat_sw_if_index, vam, &sw_if_index))
14250 sw_if_index_set = 1;
14251 else if (unformat (i, "sw_if_index %d", &sw_if_index))
14252 sw_if_index_set = 1;
14253 else if (unformat (i, "%U", unformat_qos_source, &qs))
14254 ;
14255 else if (unformat (i, "disable"))
14256 enable = 0;
14257 else
14258 {
14259 clib_warning ("parse error '%U'", format_unformat_error, i);
14260 return -99;
14261 }
14262 }
14263
14264 if (sw_if_index_set == 0)
14265 {
14266 errmsg ("missing interface name or sw_if_index");
14267 return -99;
14268 }
14269 if (qs == 0xff)
14270 {
14271 errmsg ("input location must be specified");
14272 return -99;
14273 }
14274
14275 M (QOS_RECORD_ENABLE_DISABLE, mp);
14276
Neale Ranns5281a902019-07-23 08:16:19 -070014277 mp->record.sw_if_index = ntohl (sw_if_index);
14278 mp->record.input_source = qs;
Igor Mikhailov (imichail)582caa32018-04-26 21:33:02 -070014279 mp->enable = enable;
14280
14281 S (mp);
14282 W (ret);
14283 return ret;
14284}
14285
Dave Barach048a4e52018-06-01 18:52:25 -040014286
Igor Mikhailov (imichail)582caa32018-04-26 21:33:02 -070014287static int
Damjan Marion7cd468a2016-12-19 23:05:39 +010014288q_or_quit (vat_main_t * vam)
14289{
Dave Barachdef19da2017-02-22 17:29:20 -050014290#if VPP_API_TEST_BUILTIN == 0
Damjan Marion7cd468a2016-12-19 23:05:39 +010014291 longjmp (vam->jump_buf, 1);
Dave Barachdef19da2017-02-22 17:29:20 -050014292#endif
Damjan Marion7cd468a2016-12-19 23:05:39 +010014293 return 0; /* not so much */
14294}
14295
14296static int
14297q (vat_main_t * vam)
14298{
14299 return q_or_quit (vam);
14300}
14301
14302static int
14303quit (vat_main_t * vam)
14304{
14305 return q_or_quit (vam);
14306}
14307
14308static int
14309comment (vat_main_t * vam)
14310{
14311 return 0;
14312}
14313
14314static int
Dave Barachb09f4d02019-07-15 16:00:03 -040014315elog_save (vat_main_t * vam)
14316{
14317#if VPP_API_TEST_BUILTIN == 0
14318 elog_main_t *em = &vam->elog_main;
14319 unformat_input_t *i = vam->input;
14320 char *file, *chroot_file;
14321 clib_error_t *error;
14322
14323 if (!unformat (i, "%s", &file))
14324 {
14325 errmsg ("expected file name, got `%U'", format_unformat_error, i);
14326 return 0;
14327 }
14328
14329 /* It's fairly hard to get "../oopsie" through unformat; just in case */
14330 if (strstr (file, "..") || index (file, '/'))
14331 {
14332 errmsg ("illegal characters in filename '%s'", file);
14333 return 0;
14334 }
14335
14336 chroot_file = (char *) format (0, "/tmp/%s%c", file, 0);
14337
14338 vec_free (file);
14339
14340 errmsg ("Saving %wd of %wd events to %s",
14341 elog_n_events_in_buffer (em),
14342 elog_buffer_capacity (em), chroot_file);
14343
14344 error = elog_write_file (em, chroot_file, 1 /* flush ring */ );
14345 vec_free (chroot_file);
14346
14347 if (error)
14348 clib_error_report (error);
14349#else
14350 errmsg ("Use the vpp event loger...");
14351#endif
14352
14353 return 0;
14354}
14355
14356static int
14357elog_setup (vat_main_t * vam)
14358{
14359#if VPP_API_TEST_BUILTIN == 0
14360 elog_main_t *em = &vam->elog_main;
14361 unformat_input_t *i = vam->input;
14362 u32 nevents = 128 << 10;
14363
14364 (void) unformat (i, "nevents %d", &nevents);
14365
14366 elog_init (em, nevents);
14367 vl_api_set_elog_main (em);
14368 vl_api_set_elog_trace_api_messages (1);
14369 errmsg ("Event logger initialized with %u events", nevents);
14370#else
14371 errmsg ("Use the vpp event loger...");
14372#endif
14373 return 0;
14374}
14375
14376static int
14377elog_enable (vat_main_t * vam)
14378{
14379#if VPP_API_TEST_BUILTIN == 0
14380 elog_main_t *em = &vam->elog_main;
14381
14382 elog_enable_disable (em, 1 /* enable */ );
14383 vl_api_set_elog_trace_api_messages (1);
14384 errmsg ("Event logger enabled...");
14385#else
14386 errmsg ("Use the vpp event loger...");
14387#endif
14388 return 0;
14389}
14390
14391static int
14392elog_disable (vat_main_t * vam)
14393{
14394#if VPP_API_TEST_BUILTIN == 0
14395 elog_main_t *em = &vam->elog_main;
14396
14397 elog_enable_disable (em, 0 /* enable */ );
14398 vl_api_set_elog_trace_api_messages (1);
14399 errmsg ("Event logger disabled...");
14400#else
14401 errmsg ("Use the vpp event loger...");
14402#endif
14403 return 0;
14404}
14405
14406static int
Dave Barach048a4e52018-06-01 18:52:25 -040014407statseg (vat_main_t * vam)
14408{
14409 ssvm_private_t *ssvmp = &vam->stat_segment;
14410 ssvm_shared_header_t *shared_header = ssvmp->sh;
14411 vlib_counter_t **counters;
14412 u64 thread0_index1_packets;
14413 u64 thread0_index1_bytes;
14414 f64 vector_rate, input_rate;
14415 uword *p;
14416
14417 uword *counter_vector_by_name;
14418 if (vam->stat_segment_lockp == 0)
14419 {
14420 errmsg ("Stat segment not mapped...");
14421 return -99;
14422 }
14423
14424 /* look up "/if/rx for sw_if_index 1 as a test */
14425
14426 clib_spinlock_lock (vam->stat_segment_lockp);
14427
14428 counter_vector_by_name = (uword *) shared_header->opaque[1];
14429
14430 p = hash_get_mem (counter_vector_by_name, "/if/rx");
14431 if (p == 0)
14432 {
14433 clib_spinlock_unlock (vam->stat_segment_lockp);
14434 errmsg ("/if/tx not found?");
14435 return -99;
14436 }
14437
14438 /* Fish per-thread vector of combined counters from shared memory */
14439 counters = (vlib_counter_t **) p[0];
14440
14441 if (vec_len (counters[0]) < 2)
14442 {
14443 clib_spinlock_unlock (vam->stat_segment_lockp);
14444 errmsg ("/if/tx vector length %d", vec_len (counters[0]));
14445 return -99;
14446 }
14447
14448 /* Read thread 0 sw_if_index 1 counter */
14449 thread0_index1_packets = counters[0][1].packets;
14450 thread0_index1_bytes = counters[0][1].bytes;
14451
14452 p = hash_get_mem (counter_vector_by_name, "vector_rate");
14453 if (p == 0)
14454 {
14455 clib_spinlock_unlock (vam->stat_segment_lockp);
14456 errmsg ("vector_rate not found?");
14457 return -99;
14458 }
14459
14460 vector_rate = *(f64 *) (p[0]);
14461 p = hash_get_mem (counter_vector_by_name, "input_rate");
14462 if (p == 0)
14463 {
14464 clib_spinlock_unlock (vam->stat_segment_lockp);
14465 errmsg ("input_rate not found?");
14466 return -99;
14467 }
14468 input_rate = *(f64 *) (p[0]);
14469
14470 clib_spinlock_unlock (vam->stat_segment_lockp);
14471
14472 print (vam->ofp, "vector_rate %.2f input_rate %.2f",
14473 vector_rate, input_rate);
14474 print (vam->ofp, "thread 0 sw_if_index 1 rx pkts %lld, bytes %lld",
14475 thread0_index1_packets, thread0_index1_bytes);
14476
14477 return 0;
14478}
14479
14480static int
Damjan Marion7cd468a2016-12-19 23:05:39 +010014481cmd_cmp (void *a1, void *a2)
14482{
14483 u8 **c1 = a1;
14484 u8 **c2 = a2;
14485
14486 return strcmp ((char *) (c1[0]), (char *) (c2[0]));
14487}
14488
14489static int
14490help (vat_main_t * vam)
14491{
14492 u8 **cmds = 0;
14493 u8 *name = 0;
14494 hash_pair_t *p;
14495 unformat_input_t *i = vam->input;
14496 int j;
14497
14498 if (unformat (i, "%s", &name))
14499 {
14500 uword *hs;
14501
14502 vec_add1 (name, 0);
14503
14504 hs = hash_get_mem (vam->help_by_name, name);
14505 if (hs)
14506 print (vam->ofp, "usage: %s %s", name, hs[0]);
14507 else
14508 print (vam->ofp, "No such msg / command '%s'", name);
14509 vec_free (name);
14510 return 0;
14511 }
14512
14513 print (vam->ofp, "Help is available for the following:");
14514
14515 /* *INDENT-OFF* */
14516 hash_foreach_pair (p, vam->function_by_name,
14517 ({
14518 vec_add1 (cmds, (u8 *)(p->key));
14519 }));
14520 /* *INDENT-ON* */
14521
14522 vec_sort_with_function (cmds, cmd_cmp);
14523
14524 for (j = 0; j < vec_len (cmds); j++)
14525 print (vam->ofp, "%s", cmds[j]);
14526
14527 vec_free (cmds);
14528 return 0;
14529}
14530
14531static int
14532set (vat_main_t * vam)
14533{
14534 u8 *name = 0, *value = 0;
14535 unformat_input_t *i = vam->input;
14536
14537 if (unformat (i, "%s", &name))
14538 {
14539 /* The input buffer is a vector, not a string. */
14540 value = vec_dup (i->buffer);
14541 vec_delete (value, i->index, 0);
14542 /* Almost certainly has a trailing newline */
14543 if (value[vec_len (value) - 1] == '\n')
14544 value[vec_len (value) - 1] = 0;
14545 /* Make sure it's a proper string, one way or the other */
14546 vec_add1 (value, 0);
14547 (void) clib_macro_set_value (&vam->macro_main,
14548 (char *) name, (char *) value);
14549 }
14550 else
14551 errmsg ("usage: set <name> <value>");
14552
14553 vec_free (name);
14554 vec_free (value);
14555 return 0;
14556}
14557
14558static int
14559unset (vat_main_t * vam)
14560{
14561 u8 *name = 0;
14562
14563 if (unformat (vam->input, "%s", &name))
14564 if (clib_macro_unset (&vam->macro_main, (char *) name) == 1)
14565 errmsg ("unset: %s wasn't set", name);
14566 vec_free (name);
14567 return 0;
14568}
14569
14570typedef struct
14571{
14572 u8 *name;
14573 u8 *value;
14574} macro_sort_t;
14575
14576
14577static int
14578macro_sort_cmp (void *a1, void *a2)
14579{
14580 macro_sort_t *s1 = a1;
14581 macro_sort_t *s2 = a2;
14582
14583 return strcmp ((char *) (s1->name), (char *) (s2->name));
14584}
14585
14586static int
14587dump_macro_table (vat_main_t * vam)
14588{
14589 macro_sort_t *sort_me = 0, *sm;
14590 int i;
14591 hash_pair_t *p;
14592
14593 /* *INDENT-OFF* */
14594 hash_foreach_pair (p, vam->macro_main.the_value_table_hash,
14595 ({
14596 vec_add2 (sort_me, sm, 1);
14597 sm->name = (u8 *)(p->key);
14598 sm->value = (u8 *) (p->value[0]);
14599 }));
14600 /* *INDENT-ON* */
14601
14602 vec_sort_with_function (sort_me, macro_sort_cmp);
14603
14604 if (vec_len (sort_me))
14605 print (vam->ofp, "%-15s%s", "Name", "Value");
14606 else
14607 print (vam->ofp, "The macro table is empty...");
14608
14609 for (i = 0; i < vec_len (sort_me); i++)
14610 print (vam->ofp, "%-15s%s", sort_me[i].name, sort_me[i].value);
14611 return 0;
14612}
14613
14614static int
14615dump_node_table (vat_main_t * vam)
14616{
14617 int i, j;
14618 vlib_node_t *node, *next_node;
14619
14620 if (vec_len (vam->graph_nodes) == 0)
14621 {
14622 print (vam->ofp, "Node table empty, issue get_node_graph...");
14623 return 0;
14624 }
14625
Dave Barach1ddbc012018-06-13 09:26:05 -040014626 for (i = 0; i < vec_len (vam->graph_nodes[0]); i++)
Damjan Marion7cd468a2016-12-19 23:05:39 +010014627 {
Dave Barach1ddbc012018-06-13 09:26:05 -040014628 node = vam->graph_nodes[0][i];
Damjan Marion7cd468a2016-12-19 23:05:39 +010014629 print (vam->ofp, "[%d] %s", i, node->name);
14630 for (j = 0; j < vec_len (node->next_nodes); j++)
14631 {
14632 if (node->next_nodes[j] != ~0)
14633 {
Dave Barach1ddbc012018-06-13 09:26:05 -040014634 next_node = vam->graph_nodes[0][node->next_nodes[j]];
Damjan Marion7cd468a2016-12-19 23:05:39 +010014635 print (vam->ofp, " [%d] %s", j, next_node->name);
14636 }
14637 }
14638 }
14639 return 0;
14640}
14641
14642static int
14643value_sort_cmp (void *a1, void *a2)
14644{
14645 name_sort_t *n1 = a1;
14646 name_sort_t *n2 = a2;
14647
14648 if (n1->value < n2->value)
14649 return -1;
14650 if (n1->value > n2->value)
14651 return 1;
14652 return 0;
14653}
14654
14655
14656static int
14657dump_msg_api_table (vat_main_t * vam)
14658{
Dave Barach39d69112019-11-27 11:42:13 -050014659 api_main_t *am = vlibapi_get_main ();
Damjan Marion7cd468a2016-12-19 23:05:39 +010014660 name_sort_t *nses = 0, *ns;
14661 hash_pair_t *hp;
14662 int i;
14663
14664 /* *INDENT-OFF* */
14665 hash_foreach_pair (hp, am->msg_index_by_name_and_crc,
14666 ({
14667 vec_add2 (nses, ns, 1);
14668 ns->name = (u8 *)(hp->key);
14669 ns->value = (u32) hp->value[0];
14670 }));
14671 /* *INDENT-ON* */
14672
14673 vec_sort_with_function (nses, value_sort_cmp);
14674
14675 for (i = 0; i < vec_len (nses); i++)
14676 print (vam->ofp, " [%d]: %s", nses[i].value, nses[i].name);
14677 vec_free (nses);
14678 return 0;
14679}
14680
14681static int
14682get_msg_id (vat_main_t * vam)
14683{
14684 u8 *name_and_crc;
14685 u32 message_index;
14686
14687 if (unformat (vam->input, "%s", &name_and_crc))
14688 {
Florin Corase86a8ed2018-01-05 03:20:25 -080014689 message_index = vl_msg_api_get_msg_index (name_and_crc);
Damjan Marion7cd468a2016-12-19 23:05:39 +010014690 if (message_index == ~0)
14691 {
14692 print (vam->ofp, " '%s' not found", name_and_crc);
14693 return 0;
14694 }
14695 print (vam->ofp, " '%s' has message index %d",
14696 name_and_crc, message_index);
14697 return 0;
14698 }
14699 errmsg ("name_and_crc required...");
14700 return 0;
14701}
14702
14703static int
14704search_node_table (vat_main_t * vam)
14705{
14706 unformat_input_t *line_input = vam->input;
14707 u8 *node_to_find;
14708 int j;
14709 vlib_node_t *node, *next_node;
14710 uword *p;
14711
14712 if (vam->graph_node_index_by_name == 0)
14713 {
14714 print (vam->ofp, "Node table empty, issue get_node_graph...");
14715 return 0;
14716 }
14717
14718 while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT)
14719 {
14720 if (unformat (line_input, "%s", &node_to_find))
14721 {
14722 vec_add1 (node_to_find, 0);
14723 p = hash_get_mem (vam->graph_node_index_by_name, node_to_find);
14724 if (p == 0)
14725 {
14726 print (vam->ofp, "%s not found...", node_to_find);
14727 goto out;
14728 }
Dave Barach1ddbc012018-06-13 09:26:05 -040014729 node = vam->graph_nodes[0][p[0]];
Damjan Marion7cd468a2016-12-19 23:05:39 +010014730 print (vam->ofp, "[%d] %s", p[0], node->name);
14731 for (j = 0; j < vec_len (node->next_nodes); j++)
14732 {
14733 if (node->next_nodes[j] != ~0)
14734 {
Dave Barach1ddbc012018-06-13 09:26:05 -040014735 next_node = vam->graph_nodes[0][node->next_nodes[j]];
Damjan Marion7cd468a2016-12-19 23:05:39 +010014736 print (vam->ofp, " [%d] %s", j, next_node->name);
14737 }
14738 }
14739 }
14740
14741 else
14742 {
14743 clib_warning ("parse error '%U'", format_unformat_error,
14744 line_input);
14745 return -99;
14746 }
14747
14748 out:
14749 vec_free (node_to_find);
14750
14751 }
14752
14753 return 0;
14754}
14755
14756
14757static int
14758script (vat_main_t * vam)
14759{
14760#if (VPP_API_TEST_BUILTIN==0)
14761 u8 *s = 0;
14762 char *save_current_file;
14763 unformat_input_t save_input;
14764 jmp_buf save_jump_buf;
14765 u32 save_line_number;
14766
14767 FILE *new_fp, *save_ifp;
14768
14769 if (unformat (vam->input, "%s", &s))
14770 {
14771 new_fp = fopen ((char *) s, "r");
14772 if (new_fp == 0)
14773 {
14774 errmsg ("Couldn't open script file %s", s);
14775 vec_free (s);
14776 return -99;
14777 }
14778 }
14779 else
14780 {
14781 errmsg ("Missing script name");
14782 return -99;
14783 }
14784
14785 clib_memcpy (&save_input, &vam->input, sizeof (save_input));
14786 clib_memcpy (&save_jump_buf, &vam->jump_buf, sizeof (save_jump_buf));
14787 save_ifp = vam->ifp;
14788 save_line_number = vam->input_line_number;
14789 save_current_file = (char *) vam->current_file;
14790
14791 vam->input_line_number = 0;
14792 vam->ifp = new_fp;
14793 vam->current_file = s;
14794 do_one_file (vam);
14795
Sirshak Dasb0861822018-05-29 21:13:21 -050014796 clib_memcpy (&vam->input, &save_input, sizeof (save_input));
Damjan Marion7cd468a2016-12-19 23:05:39 +010014797 clib_memcpy (&vam->jump_buf, &save_jump_buf, sizeof (save_jump_buf));
14798 vam->ifp = save_ifp;
14799 vam->input_line_number = save_line_number;
14800 vam->current_file = (u8 *) save_current_file;
14801 vec_free (s);
14802
14803 return 0;
14804#else
14805 clib_warning ("use the exec command...");
14806 return -99;
14807#endif
14808}
14809
14810static int
14811echo (vat_main_t * vam)
14812{
14813 print (vam->ofp, "%v", vam->input->buffer);
14814 return 0;
14815}
14816
14817/* List of API message constructors, CLI names map to api_xxx */
14818#define foreach_vpe_api_msg \
Jon Loeligerc83c3b72017-02-23 13:57:35 -060014819_(create_loopback,"[mac <mac-addr>] [instance <instance>]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014820_(sw_interface_dump,"") \
14821_(sw_interface_set_flags, \
14822 "<intfc> | sw_if_index <id> admin-up | admin-down link-up | link down") \
14823_(sw_interface_add_del_address, \
14824 "<intfc> | sw_if_index <id> <ip4-address> | <ip6-address> [del] [del-all] ") \
Stevenad8015b2017-10-29 22:10:46 -070014825_(sw_interface_set_rx_mode, \
14826 "<intfc> | sw_if_index <id> [queue <id>] <polling | interrupt | adaptive>") \
Mohsin Kazmi54f7c512018-08-23 18:28:11 +020014827_(sw_interface_set_rx_placement, \
14828 "<intfc> | sw_if_index <id> [queue <id>] [worker <id> | main]") \
Mohsin Kazmif0b42f42018-09-10 18:11:00 +020014829_(sw_interface_rx_placement_dump, \
14830 "[<intfc> | sw_if_index <id>]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014831_(sw_interface_set_table, \
14832 "<intfc> | sw_if_index <id> vrf <table-id> [ipv6]") \
14833_(sw_interface_set_mpls_enable, \
14834 "<intfc> | sw_if_index [disable | dis]") \
14835_(sw_interface_set_vpath, \
14836 "<intfc> | sw_if_index <id> enable | disable") \
14837_(sw_interface_set_vxlan_bypass, \
John Lo2b81eb82017-01-30 13:12:10 -050014838 "<intfc> | sw_if_index <id> [ip4 | ip6] [enable | disable]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014839_(sw_interface_set_l2_xconnect, \
14840 "rx <intfc> | rx_sw_if_index <id> tx <intfc> | tx_sw_if_index <id>\n" \
14841 "enable | disable") \
14842_(sw_interface_set_l2_bridge, \
Eyal Barif24991c2017-04-05 05:33:21 +030014843 "{<intfc> | sw_if_index <id>} bd_id <bridge-domain-id>\n" \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014844 "[shg <split-horizon-group>] [bvi]\n" \
14845 "enable | disable") \
Eyal Barif24991c2017-04-05 05:33:21 +030014846_(bridge_domain_set_mac_age, "bd_id <bridge-domain-id> mac-age 0-255") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014847_(bridge_domain_add_del, \
John Lo70bfcaf2017-11-14 13:19:26 -050014848 "bd_id <bridge-domain-id> [flood 1|0] [uu-flood 1|0] [forward 1|0] [learn 1|0] [arp-term 1|0] [mac-age 0-255] [bd-tag <text>] [del]\n") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014849_(bridge_domain_dump, "[bd_id <bridge-domain-id>]\n") \
14850_(l2fib_add_del, \
14851 "mac <mac-addr> bd_id <bridge-domain-id> [del] | sw_if <intfc> | sw_if_index <id> [static] [filter] [bvi] [count <nn>]\n") \
Eyal Barif24991c2017-04-05 05:33:21 +030014852_(l2fib_flush_bd, "bd_id <bridge-domain-id>") \
14853_(l2fib_flush_int, "<intfc> | sw_if_index <id>") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014854_(l2_flags, \
John Lo8d00fff2017-08-03 00:35:36 -040014855 "sw_if <intfc> | sw_if_index <id> [learn] [forward] [uu-flood] [flood] [arp-term] [disable]\n") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014856_(bridge_flags, \
14857 "bd_id <bridge-domain-id> [learn] [forward] [uu-flood] [flood] [arp-term] [disable]\n") \
Damjan Marion8389fb92017-10-13 18:29:53 +020014858_(tap_create_v2, \
Mohsin Kazmi50bd1652020-08-26 11:07:48 +020014859 "id <num> [hw-addr <mac-addr>] [host-if-name <name>] [host-ns <name>] [num-rx-queues <num>] [rx-ring-size <num>] [tx-ring-size <num>] [host-bridge <name>] [host-mac-addr <mac-addr>] [host-ip4-addr <ip4addr/mask>] [host-ip6-addr <ip6addr/mask>] [host-mtu-size <mtu>] [gso | no-gso | csum-offload | gro-coalesce] [persist] [attach] [tun] [packed] [in-order]") \
Damjan Marion8389fb92017-10-13 18:29:53 +020014860_(tap_delete_v2, \
14861 "<vpp-if-name> | sw_if_index <id>") \
14862_(sw_interface_tap_v2_dump, "") \
Mohsin Kazmi518251b2020-09-01 17:17:44 +000014863_(virtio_pci_create_v2, \
Mohsin Kazmie347acb2020-09-28 10:26:33 +000014864 "pci-addr <pci-address> [use_random_mac | hw-addr <mac-addr>] [features <hex-value>] [gso-enabled [gro-coalesce] | csum-offload-enabled] [packed] [in-order] [buffering]") \
Mohsin Kazmi03ae24b2019-01-18 11:50:00 +010014865_(virtio_pci_delete, \
14866 "<vpp-if-name> | sw_if_index <id>") \
14867_(sw_interface_virtio_pci_dump, "") \
Steven9cd2d7a2017-12-20 12:43:01 -080014868_(bond_create, \
14869 "[hw-addr <mac-addr>] {round-robin | active-backup | " \
Alexander Chernavinad9d5282018-12-13 09:08:09 -050014870 "broadcast | {lacp | xor} [load-balance { l2 | l23 | l34 }]} " \
Steven Luonga1876b82019-08-20 16:58:00 -070014871 "[id <if-id>]") \
Steven Luongea717862020-07-30 07:31:40 -070014872_(bond_create2, \
14873 "[hw-addr <mac-addr>] {mode round-robin | active-backup | " \
14874 "broadcast | {lacp | xor} [load-balance { l2 | l23 | l34 }]} " \
14875 "[id <if-id>] [gso]") \
Steven9cd2d7a2017-12-20 12:43:01 -080014876_(bond_delete, \
14877 "<vpp-if-name> | sw_if_index <id>") \
Steven Luong4c4223e2020-07-15 08:44:54 -070014878_(bond_add_member, \
Steven Luonga1876b82019-08-20 16:58:00 -070014879 "sw_if_index <n> bond <sw_if_index> [is_passive] [is_long_timeout]") \
Steven Luong4c4223e2020-07-15 08:44:54 -070014880_(bond_detach_member, \
Steven9cd2d7a2017-12-20 12:43:01 -080014881 "sw_if_index <n>") \
Steven Luonga1876b82019-08-20 16:58:00 -070014882 _(sw_interface_set_bond_weight, "<intfc> | sw_if_index <nn> weight <value>") \
Steven Luong4c4223e2020-07-15 08:44:54 -070014883 _(sw_bond_interface_dump, "<intfc> | sw_if_index <nn>") \
14884 _(sw_member_interface_dump, \
Steven9cd2d7a2017-12-20 12:43:01 -080014885 "<vpp-if-name> | sw_if_index <id>") \
Neale Ranns28ab9cc2017-08-14 07:18:42 -070014886_(ip_table_add_del, \
John Loe166fd92018-09-13 14:08:59 -040014887 "table <n> [ipv6] [add | del]\n") \
Neale Ranns097fa662018-05-01 05:17:55 -070014888_(ip_route_add_del, \
John Lo22030432018-09-20 16:07:00 -040014889 "<addr>/<mask> via <<addr>|<intfc>|sw_if_index <id>|via-label <n>>\n" \
14890 "[table-id <n>] [<intfc> | sw_if_index <id>] [resolve-attempts <n>]\n"\
John Lo06fda9c2018-10-03 16:32:44 -040014891 "[weight <n>] [drop] [local] [classify <n>] [out-label <n>]\n" \
14892 "[multipath] [count <n>] [del]") \
Neale Ranns32e1c012016-11-22 17:07:28 +000014893_(ip_mroute_add_del, \
14894 "<src> <grp>/<mask> [table-id <n>]\n" \
14895 "[<intfc> | sw_if_index <id>] [local] [del]") \
Neale Ranns28ab9cc2017-08-14 07:18:42 -070014896_(mpls_table_add_del, \
John Loe166fd92018-09-13 14:08:59 -040014897 "table <n> [add | del]\n") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014898_(mpls_route_add_del, \
John Loe166fd92018-09-13 14:08:59 -040014899 "<label> <eos> via <addr | next-hop-table <n> | via-label <n> |\n" \
14900 "lookup-ip4-table <n> | lookup-in-ip6-table <n> |\n" \
14901 "l2-input-on <intfc> | l2-input-on sw_if_index <id>>\n" \
14902 "[<intfc> | sw_if_index <id>] [resolve-attempts <n>] [weight <n>]\n" \
John Lo06fda9c2018-10-03 16:32:44 -040014903 "[drop] [local] [classify <n>] [out-label <n>] [multipath]\n" \
14904 "[count <n>] [del]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014905_(mpls_ip_bind_unbind, \
14906 "<label> <addr/len>") \
14907_(mpls_tunnel_add_del, \
John Lo06fda9c2018-10-03 16:32:44 -040014908 "[add | del <intfc | sw_if_index <id>>] via <addr | via-label <n>>\n" \
14909 "[<intfc> | sw_if_index <id> | next-hop-table <id>]\n" \
14910 "[l2-only] [out-label <n>]") \
John Loe166fd92018-09-13 14:08:59 -040014911_(sr_mpls_policy_add, \
14912 "bsid <id> [weight <n>] [spray] next <sid> [next <sid>]") \
14913_(sr_mpls_policy_del, \
14914 "bsid <id>") \
Neale Rannsd792d9c2017-10-21 10:53:20 -070014915_(bier_table_add_del, \
14916 "<label> <sub-domain> <set> <bsl> [del]") \
14917_(bier_route_add_del, \
14918 "<bit-position> <sub-domain> <set> <bsl> via <addr> [table-id <n>]\n" \
14919 "[<intfc> | sw_if_index <id>]" \
14920 "[weight <n>] [del] [multipath]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014921_(sw_interface_set_unnumbered, \
14922 "<intfc> | sw_if_index <id> unnum_if_index <id> [del]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014923_(create_vlan_subif, "<intfc> | sw_if_index <id> vlan <n>") \
14924_(create_subif, "<intfc> | sw_if_index <id> sub_id <n>\n" \
14925 "[outer_vlan_id <n>][inner_vlan_id <n>]\n" \
14926 "[no_tags][one_tag][two_tags][dot1ad][exact_match][default_sub]\n" \
14927 "[outer_vlan_id_any][inner_vlan_id_any]") \
Neale Ranns9db6ada2019-11-08 12:42:31 +000014928_(ip_table_replace_begin, "table <n> [ipv6]") \
14929_(ip_table_flush, "table <n> [ipv6]") \
14930_(ip_table_replace_end, "table <n> [ipv6]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014931_(set_ip_flow_hash, \
14932 "vrf <n> [src] [dst] [sport] [dport] [proto] [reverse] [ipv6]") \
14933_(sw_interface_ip6_enable_disable, \
14934 "<intfc> | sw_if_index <id> enable | disable") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014935_(l2_patch_add_del, \
14936 "rx <intfc> | rx_sw_if_index <id> tx <intfc> | tx_sw_if_index <id>\n" \
14937 "enable | disable") \
Pablo Camarillofb380952016-12-07 18:34:18 +010014938_(sr_localsid_add_del, \
14939 "(del) address <addr> next_hop <addr> behavior <beh>\n" \
14940 "fib-table <num> (end.psp) sw_if_index <num>") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014941_(classify_add_del_table, \
14942 "buckets <nn> [skip <n>] [match <n>] [memory_size <nn-bytes>]\n" \
14943 " [del] [del-chain] mask <mask-value>\n" \
14944 " [l2-miss-next | miss-next | acl-miss-next] <name|nn>\n" \
14945 " [current-data-flag <n>] [current-data-offset <nn>] [table <nn>]") \
14946_(classify_add_del_session, \
14947 "[hit-next|l2-hit-next|acl-hit-next|policer-hit-next] <name|nn>\n" \
14948 " table-index <nn> skip_n <nn> match_n <nn> match [hex] [l2]\n" \
14949 " [l3 [ip4|ip6]] [action set-ip4-fib-id <nn>]\n" \
14950 " [action set-ip6-fib-id <nn> | action <n> metadata <nn>] [del]") \
14951_(classify_set_interface_ip_table, \
14952 "<intfc> | sw_if_index <nn> table <nn>") \
14953_(classify_set_interface_l2_tables, \
14954 "<intfc> | sw_if_index <nn> [ip4-table <nn>] [ip6-table <nn>]\n" \
14955 " [other-table <nn>]") \
14956_(get_node_index, "node <node-name") \
14957_(add_node_next, "node <node-name> next <next-node-name>") \
eyal bariaf86a482018-04-17 11:20:27 +030014958_(vxlan_offload_rx, \
14959 "hw { <interface name> | hw_if_index <nn>} " \
14960 "rx { <vxlan tunnel name> | sw_if_index <nn> } [del]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014961_(vxlan_add_del_tunnel, \
14962 "src <ip-addr> { dst <ip-addr> | group <mcast-ip-addr>\n" \
Jon Loeliger3d460bd2018-02-01 16:36:12 -060014963 "{ <intfc> | mcast_sw_if_index <nn> } [instance <id>]}\n" \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014964 "vni <vni> [encap-vrf-id <nn>] [decap-next <l2|nn>] [del]") \
14965_(vxlan_tunnel_dump, "[<intfc> | sw_if_index <nn>]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014966_(l2_fib_clear_table, "") \
14967_(l2_interface_efp_filter, "sw_if_index <nn> enable | disable") \
14968_(l2_interface_vlan_tag_rewrite, \
14969 "<intfc> | sw_if_index <nn> \n" \
14970 "[disable][push-[1|2]][pop-[1|2]][translate-1-[1|2]] \n" \
14971 "[translate-2-[1|2]] [push_dot1q 0] tag1 <nn> tag2 <nn>") \
14972_(create_vhost_user_if, \
14973 "socket <filename> [server] [renumber <dev_instance>] " \
Steven Luong4208a4c2019-05-06 08:51:56 -070014974 "[disable_mrg_rxbuf] [disable_indirect_desc] [gso] " \
Steven Luongbc0d9ff2020-03-23 09:34:59 -070014975 "[mac <mac_address>] [packed]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014976_(modify_vhost_user_if, \
14977 "<intfc> | sw_if_index <nn> socket <filename>\n" \
Steven Luongbc0d9ff2020-03-23 09:34:59 -070014978 "[server] [renumber <dev_instance>] [gso] [packed]") \
Steven Luong27ba5002020-11-17 13:30:44 -080014979_(create_vhost_user_if_v2, \
14980 "socket <filename> [server] [renumber <dev_instance>] " \
14981 "[disable_mrg_rxbuf] [disable_indirect_desc] [gso] " \
14982 "[mac <mac_address>] [packed] [event-idx]") \
14983_(modify_vhost_user_if_v2, \
14984 "<intfc> | sw_if_index <nn> socket <filename>\n" \
14985 "[server] [renumber <dev_instance>] [gso] [packed] [event-idx]")\
Damjan Marion7cd468a2016-12-19 23:05:39 +010014986_(delete_vhost_user_if, "<intfc> | sw_if_index <nn>") \
Steven Luonga0e8d962020-05-18 17:12:56 -070014987_(sw_interface_vhost_user_dump, "<intfc> | sw_if_index <nn>") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014988_(show_version, "") \
Mohsin Kazmi5d64c782018-09-11 20:27:09 +020014989_(show_threads, "") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014990_(vxlan_gpe_add_del_tunnel, \
Hongjun Ni04ffd0ad2017-06-23 00:18:40 +080014991 "local <addr> remote <addr> | group <mcast-ip-addr>\n" \
14992 "{ <intfc> | mcast_sw_if_index <nn> } }\n" \
14993 "vni <nn> [encap-vrf-id <nn>] [decap-vrf-id <nn>]\n" \
14994 "[next-ip4][next-ip6][next-ethernet] [next-nsh] [del]\n") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010014995_(vxlan_gpe_tunnel_dump, "[<intfc> | sw_if_index <nn>]") \
14996_(l2_fib_table_dump, "bd_id <bridge-domain-id>") \
14997_(interface_name_renumber, \
14998 "<intfc> | sw_if_index <nn> new_show_dev_instance <nn>") \
14999_(input_acl_set_interface, \
15000 "<intfc> | sw_if_index <nn> [ip4-table <nn>] [ip6-table <nn>]\n" \
15001 " [l2-table <nn>] [del]") \
John Lo8d00fff2017-08-03 00:35:36 -040015002_(want_l2_macs_events, "[disable] [learn-limit <n>] [scan-delay <n>] [max-entries <n>]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015003_(ip_address_dump, "(ipv4 | ipv6) (<intfc> | sw_if_index <id>)") \
15004_(ip_dump, "ipv4 | ipv6") \
15005_(ipsec_spd_add_del, "spd_id <n> [del]") \
15006_(ipsec_interface_add_del_spd, "(<intfc> | sw_if_index <id>)\n" \
15007 " spid_id <n> ") \
Neale Ranns17dcec02019-01-09 21:22:20 -080015008_(ipsec_sad_entry_add_del, "sad_id <n> spi <n> crypto_alg <alg>\n" \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015009 " crypto_key <hex> tunnel_src <ip4|ip6> tunnel_dst <ip4|ip6>\n" \
15010 " integ_alg <alg> integ_key <hex>") \
Neale Ranns17dcec02019-01-09 21:22:20 -080015011_(ipsec_spd_entry_add_del, "spd_id <n> priority <n> action <action>\n" \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015012 " (inbound|outbound) [sa_id <n>] laddr_start <ip4|ip6>\n" \
15013 " laddr_stop <ip4|ip6> raddr_start <ip4|ip6> raddr_stop <ip4|ip6>\n" \
15014 " [lport_start <n> lport_stop <n>] [rport_start <n> rport_stop <n>]" ) \
Matthew Smith28029532017-09-26 13:33:44 -050015015_(ipsec_sa_dump, "[sa_id <n>]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015016_(delete_loopback,"sw_if_index <nn>") \
15017_(bd_ip_mac_add_del, "bd_id <bridge-domain-id> <ip4/6-addr> <mac-addr> [del]") \
John Loe26c81f2019-01-07 15:16:33 -050015018_(bd_ip_mac_flush, "bd_id <bridge-domain-id>") \
15019_(bd_ip_mac_dump, "[bd_id] <bridge-domain-id>") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015020_(want_interface_events, "enable|disable") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015021_(get_first_msg_id, "client <name>") \
15022_(cop_interface_enable_disable, "<intfc> | sw_if_index <nn> [disable]") \
15023_(cop_whitelist_enable_disable, "<intfc> | sw_if_index <nn>\n" \
15024 "fib-id <nn> [ip4][ip6][default]") \
15025_(get_node_graph, " ") \
15026_(sw_interface_clear_stats,"<intfc> | sw_if_index <nn>") \
15027_(ioam_enable, "[trace] [pow] [ppc <encap|decap>]") \
15028_(ioam_disable, "") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015029_(af_packet_create, "name <host interface name> [hw_addr <mac>]") \
15030_(af_packet_delete, "name <host interface name>") \
Mohsin Kazmi04e0bb22018-05-28 18:55:37 +020015031_(af_packet_dump, "") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015032_(policer_add_del, "name <policer name> <params> [del]") \
15033_(policer_dump, "[name <policer name>]") \
15034_(policer_classify_set_interface, \
15035 "<intfc> | sw_if_index <nn> [ip4-table <nn>] [ip6-table <nn>]\n" \
15036 " [l2-table <nn>] [del]") \
15037_(policer_classify_dump, "type [ip4|ip6|l2]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015038_(mpls_tunnel_dump, "tunnel_index <tunnel-id>") \
Neale Ranns097fa662018-05-01 05:17:55 -070015039_(mpls_table_dump, "") \
15040_(mpls_route_dump, "table-id <ID>") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015041_(classify_table_ids, "") \
15042_(classify_table_by_interface, "sw_if_index <sw_if_index>") \
15043_(classify_table_info, "table_id <nn>") \
15044_(classify_session_dump, "table_id <nn>") \
15045_(set_ipfix_exporter, "collector_address <ip4> [collector_port <nn>] " \
15046 "src_address <ip4> [vrf_id <nn>] [path_mtu <nn>] " \
15047 "[template_interval <nn>] [udp_checksum]") \
15048_(ipfix_exporter_dump, "") \
15049_(set_ipfix_classify_stream, "[domain <domain-id>] [src_port <src-port>]") \
15050_(ipfix_classify_stream_dump, "") \
15051_(ipfix_classify_table_add_del, "table <table-index> ip4|ip6 [tcp|udp]") \
15052_(ipfix_classify_table_dump, "") \
Eyal Bari001fd402017-07-16 09:34:53 +030015053_(sw_interface_span_enable_disable, "[l2] [src <intfc> | src_sw_if_index <id>] [disable | [[dst <intfc> | dst_sw_if_index <id>] [both|rx|tx]]]") \
Eyal Bari5b311202017-07-31 13:12:30 +030015054_(sw_interface_span_dump, "[l2]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015055_(get_next_index, "node-name <node-name> next-node-name <node-name>") \
Mohsin Kazmi22e9cfd2019-07-23 11:54:48 +020015056_(pg_create_interface, "if_id <nn> [gso-enabled gso-size <size>]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015057_(pg_capture, "if_id <nnn> pcap <file_name> count <nnn> [disable]") \
15058_(pg_enable_disable, "[stream <id>] disable") \
Mohsin Kazmif382b062020-08-11 15:00:44 +020015059_(pg_interface_enable_disable_coalesce, "<intf> | sw_if_index <nn> enable | disable") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015060_(ip_source_and_port_range_check_add_del, \
15061 "<ip-addr>/<mask> range <nn>-<nn> vrf <id>") \
15062_(ip_source_and_port_range_check_interface_add_del, \
15063 "<intf> | sw_if_index <nn> [tcp-out-vrf <id>] [tcp-in-vrf <id>]" \
15064 "[udp-in-vrf <id>] [udp-out-vrf <id>]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015065_(delete_subif,"<intfc> | sw_if_index <nn>") \
15066_(l2_interface_pbb_tag_rewrite, \
15067 "<intfc> | sw_if_index <nn> \n" \
15068 "[disable | push | pop | translate_pbb_stag <outer_tag>] \n" \
15069 "dmac <mac> smac <mac> sid <nn> [vlanid <nn>]") \
Pavel Kotuceke88865d2018-11-28 07:42:11 +010015070_(set_punt, "protocol <l4-protocol> [ip <ver>] [port <l4-port>] [del]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015071_(flow_classify_set_interface, \
15072 "<intfc> | sw_if_index <nn> [ip4-table <nn>] [ip6-table <nn>] [del]") \
15073_(flow_classify_dump, "type [ip4|ip6]") \
Neale Ranns097fa662018-05-01 05:17:55 -070015074_(ip_table_dump, "") \
15075_(ip_route_dump, "table-id [ip4|ip6]") \
15076_(ip_mtable_dump, "") \
15077_(ip_mroute_dump, "table-id [ip4|ip6]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015078_(feature_enable_disable, "arc_name <arc_name> " \
15079 "feature_name <feature_name> <intfc> | sw_if_index <nn> [disable]") \
Mohsin Kazmi29467b52019-10-08 19:42:38 +020015080_(feature_gso_enable_disable, "<intfc> | sw_if_index <nn> " \
15081 "[enable | disable] ") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015082_(sw_interface_tag_add_del, "<intfc> | sw_if_index <nn> tag <text>" \
15083"[disable]") \
Matthew Smithe0792fd2019-07-12 11:48:24 -050015084_(sw_interface_add_del_mac_address, "<intfc> | sw_if_index <nn> " \
15085 "mac <mac-address> [del]") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015086_(l2_xconnect_dump, "") \
Ole Troand7231612018-06-07 10:17:57 +020015087_(hw_interface_set_mtu, "<intfc> | hw_if_index <nn> mtu <nn>") \
Pavel Kotucek6899a302017-06-08 08:46:10 +020015088_(sw_interface_get_table, "<intfc> | sw_if_index <id> [ipv6]") \
Pavel Kotucek15ac81c2017-06-20 14:00:26 +020015089_(p2p_ethernet_add, "<intfc> | sw_if_index <nn> remote_mac <mac-address> sub_id <id>") \
Steve Shin99a0e602017-07-01 04:16:20 +000015090_(p2p_ethernet_del, "<intfc> | sw_if_index <nn> remote_mac <mac-address>") \
Dave Barach59b25652017-09-10 15:04:27 -040015091_(tcp_configure_src_addresses, "<ip4|6>first-<ip4|6>last [vrf <id>]") \
Florin Coras90a63982017-12-19 04:50:01 -080015092_(sock_init_shm, "size <nnn>") \
Florin Corascea194d2017-10-02 00:18:51 -070015093_(app_namespace_add_del, "[add] id <ns-id> secret <nn> sw_if_index <nn>")\
Florin Coras1c710452017-10-17 00:03:13 -070015094_(session_rule_add_del, "[add|del] proto <tcp/udp> <lcl-ip>/<plen> " \
15095 "<lcl-port> <rmt-ip>/<plen> <rmt-port> action <nn>") \
Florin Coras6c36f532017-11-03 18:32:34 -070015096_(session_rules_dump, "") \
Florin Coras595992c2017-11-06 17:17:08 -080015097_(ip_container_proxy_add_del, "[add|del] <address> <sw_if_index>") \
Andrew Yourtchenko815d7d52018-02-07 11:37:02 +010015098_(output_acl_set_interface, \
15099 "<intfc> | sw_if_index <nn> [ip4-table <nn>] [ip6-table <nn>]\n" \
15100 " [l2-table <nn>] [del]") \
Ole Troane906aac2018-06-14 14:42:14 +020015101_(qos_record_enable_disable, "<record-source> <intfc> | sw_if_index <id> [disable]")
Damjan Marion7cd468a2016-12-19 23:05:39 +010015102
15103/* List of command functions, CLI names map directly to functions */
15104#define foreach_cli_function \
15105_(comment, "usage: comment <ignore-rest-of-line>") \
15106_(dump_interface_table, "usage: dump_interface_table") \
15107_(dump_sub_interface_table, "usage: dump_sub_interface_table") \
15108_(dump_ipv4_table, "usage: dump_ipv4_table") \
15109_(dump_ipv6_table, "usage: dump_ipv6_table") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015110_(dump_macro_table, "usage: dump_macro_table ") \
15111_(dump_node_table, "usage: dump_node_table") \
15112_(dump_msg_api_table, "usage: dump_msg_api_table") \
Dave Barachb09f4d02019-07-15 16:00:03 -040015113_(elog_setup, "usage: elog_setup [nevents, default 128K]") \
15114_(elog_disable, "usage: elog_disable") \
15115_(elog_enable, "usage: elog_enable") \
15116_(elog_save, "usage: elog_save <filename>") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015117_(get_msg_id, "usage: get_msg_id name_and_crc") \
15118_(echo, "usage: echo <message>") \
15119_(exec, "usage: exec <vpe-debug-CLI-command>") \
15120_(exec_inband, "usage: exec_inband <vpe-debug-CLI-command>") \
15121_(help, "usage: help") \
15122_(q, "usage: quit") \
15123_(quit, "usage: quit") \
15124_(search_node_table, "usage: search_node_table <name>...") \
15125_(set, "usage: set <variable-name> <value>") \
15126_(script, "usage: script <file-name>") \
Neale Ranns097fa662018-05-01 05:17:55 -070015127_(statseg, "usage: statseg") \
Damjan Marion7cd468a2016-12-19 23:05:39 +010015128_(unset, "usage: unset <variable-name>")
Dave Barach048a4e52018-06-01 18:52:25 -040015129
Damjan Marion7cd468a2016-12-19 23:05:39 +010015130#define _(N,n) \
15131 static void vl_api_##n##_t_handler_uni \
15132 (vl_api_##n##_t * mp) \
15133 { \
15134 vat_main_t * vam = &vat_main; \
15135 if (vam->json_output) { \
15136 vl_api_##n##_t_handler_json(mp); \
15137 } else { \
15138 vl_api_##n##_t_handler(mp); \
15139 } \
15140 }
15141foreach_vpe_api_reply_msg;
Dave Baracha1a093d2017-03-02 13:13:23 -050015142#if VPP_API_TEST_BUILTIN == 0
15143foreach_standalone_reply_msg;
15144#endif
Damjan Marion7cd468a2016-12-19 23:05:39 +010015145#undef _
15146
15147void
15148vat_api_hookup (vat_main_t * vam)
15149{
15150#define _(N,n) \
15151 vl_msg_api_set_handlers(VL_API_##N, #n, \
15152 vl_api_##n##_t_handler_uni, \
15153 vl_noop_handler, \
15154 vl_api_##n##_t_endian, \
15155 vl_api_##n##_t_print, \
15156 sizeof(vl_api_##n##_t), 1);
15157 foreach_vpe_api_reply_msg;
Dave Baracha1a093d2017-03-02 13:13:23 -050015158#if VPP_API_TEST_BUILTIN == 0
15159 foreach_standalone_reply_msg;
15160#endif
Damjan Marion7cd468a2016-12-19 23:05:39 +010015161#undef _
15162
15163#if (VPP_API_TEST_BUILTIN==0)
15164 vl_msg_api_set_first_available_msg_id (VL_MSG_FIRST_AVAILABLE);
Damjan Marion7cd468a2016-12-19 23:05:39 +010015165
15166 vam->sw_if_index_by_interface_name = hash_create_string (0, sizeof (uword));
15167
15168 vam->function_by_name = hash_create_string (0, sizeof (uword));
15169
15170 vam->help_by_name = hash_create_string (0, sizeof (uword));
Dave Barach45e4f362017-03-07 12:52:31 -050015171#endif
Damjan Marion7cd468a2016-12-19 23:05:39 +010015172
15173 /* API messages we can send */
15174#define _(n,h) hash_set_mem (vam->function_by_name, #n, api_##n);
15175 foreach_vpe_api_msg;
15176#undef _
15177
15178 /* Help strings */
15179#define _(n,h) hash_set_mem (vam->help_by_name, #n, h);
15180 foreach_vpe_api_msg;
15181#undef _
Damjan Marion7cd468a2016-12-19 23:05:39 +010015182
15183 /* CLI functions */
15184#define _(n,h) hash_set_mem (vam->function_by_name, #n, n);
15185 foreach_cli_function;
15186#undef _
15187
15188 /* Help strings */
15189#define _(n,h) hash_set_mem (vam->help_by_name, #n, h);
15190 foreach_cli_function;
15191#undef _
15192}
15193
Dave Baracha1a093d2017-03-02 13:13:23 -050015194#if VPP_API_TEST_BUILTIN
15195static clib_error_t *
15196vat_api_hookup_shim (vlib_main_t * vm)
15197{
15198 vat_api_hookup (&vat_main);
15199 return 0;
15200}
15201
15202VLIB_API_INIT_FUNCTION (vat_api_hookup_shim);
15203#endif
15204
Damjan Marion7cd468a2016-12-19 23:05:39 +010015205/*
15206 * fd.io coding-style-patch-verification: ON
15207 *
15208 * Local Variables:
15209 * eval: (c-set-style "gnu")
15210 * End:
15211 */