FD.io VPP  v19.08-27-gf4dcae4
Vector Packet Processing
echo_common.c
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2019 Cisco and/or its affiliates.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at:
6  *
7  * http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include <stdio.h>
17 #include <signal.h>
18 
20 
21 typedef struct
22 {
23  /* VNET_API_ERROR_FOO -> "Foo" hash table */
26 
28 
29 u8 *
30 format_ip4_address (u8 * s, va_list * args)
31 {
32  u8 *a = va_arg (*args, u8 *);
33  return format (s, "%d.%d.%d.%d", a[0], a[1], a[2], a[3]);
34 }
35 
36 u8 *
37 format_ip6_address (u8 * s, va_list * args)
38 {
39  ip6_address_t *a = va_arg (*args, ip6_address_t *);
40  u32 i, i_max_n_zero, max_n_zeros, i_first_zero, n_zeros, last_double_colon;
41 
42  i_max_n_zero = ARRAY_LEN (a->as_u16);
43  max_n_zeros = 0;
44  i_first_zero = i_max_n_zero;
45  n_zeros = 0;
46  for (i = 0; i < ARRAY_LEN (a->as_u16); i++)
47  {
48  u32 is_zero = a->as_u16[i] == 0;
49  if (is_zero && i_first_zero >= ARRAY_LEN (a->as_u16))
50  {
51  i_first_zero = i;
52  n_zeros = 0;
53  }
54  n_zeros += is_zero;
55  if ((!is_zero && n_zeros > max_n_zeros)
56  || (i + 1 >= ARRAY_LEN (a->as_u16) && n_zeros > max_n_zeros))
57  {
58  i_max_n_zero = i_first_zero;
59  max_n_zeros = n_zeros;
60  i_first_zero = ARRAY_LEN (a->as_u16);
61  n_zeros = 0;
62  }
63  }
64 
65  last_double_colon = 0;
66  for (i = 0; i < ARRAY_LEN (a->as_u16); i++)
67  {
68  if (i == i_max_n_zero && max_n_zeros > 1)
69  {
70  s = format (s, "::");
71  i += max_n_zeros - 1;
72  last_double_colon = 1;
73  }
74  else
75  {
76  s = format (s, "%s%x",
77  (last_double_colon || i == 0) ? "" : ":",
78  clib_net_to_host_u16 (a->as_u16[i]));
79  last_double_colon = 0;
80  }
81  }
82 
83  return s;
84 }
85 
86 /* Format an IP46 address. */
87 u8 *
88 format_ip46_address (u8 * s, va_list * args)
89 {
90  ip46_address_t *ip46 = va_arg (*args, ip46_address_t *);
91  ip46_type_t type = va_arg (*args, ip46_type_t);
92  int is_ip4 = 1;
93 
94  switch (type)
95  {
96  case IP46_TYPE_ANY:
97  is_ip4 = ip46_address_is_ip4 (ip46);
98  break;
99  case IP46_TYPE_IP4:
100  is_ip4 = 1;
101  break;
102  case IP46_TYPE_IP6:
103  is_ip4 = 0;
104  break;
105  }
106 
107  return is_ip4 ?
108  format (s, "%U", format_ip4_address, &ip46->ip4) :
109  format (s, "%U", format_ip6_address, &ip46->ip6);
110 }
111 
112 static uword
113 unformat_data (unformat_input_t * input, va_list * args)
114 {
115  u64 _a;
116  u64 *a = va_arg (*args, u64 *);
117  if (unformat (input, "%lluGb", &_a))
118  *a = _a << 30;
119  else if (unformat (input, "%lluMb", &_a))
120  *a = _a << 20;
121  else if (unformat (input, "%lluKb", &_a))
122  *a = _a << 10;
123  else if (unformat (input, "%llu", a))
124  ;
125  else
126  return 0;
127  return 1;
128 }
129 
130 static u8 *
131 format_api_error (u8 * s, va_list * args)
132 {
134  i32 error = va_arg (*args, u32);
135  uword *p;
136 
137  p = hash_get (ecm->error_string_by_error_number, -error);
138 
139  if (p)
140  s = format (s, "%s", p[0]);
141  else
142  s = format (s, "%d", error);
143  return s;
144 }
145 
146 static void
148 {
150  ecm->error_string_by_error_number = hash_create (0, sizeof (uword));
151 
152 #define _(n,v,s) hash_set (ecm->error_string_by_error_number, -v, s);
154 #undef _
155 
156  hash_set (ecm->error_string_by_error_number, 99, "Misc");
157 }
158 
u8 * format_ip46_address(u8 *s, va_list *args)
Definition: echo_common.c:88
#define hash_set(h, key, value)
Definition: hash.h:255
u8 * format_ip4_address(u8 *s, va_list *args)
Definition: echo_common.c:30
a
Definition: bitmap.h:538
unsigned long u64
Definition: types.h:89
int i
u8 * format(u8 *s, const char *fmt,...)
Definition: format.c:424
static void init_error_string_table()
Definition: echo_common.c:147
unsigned char u8
Definition: types.h:56
unsigned int u32
Definition: types.h:88
u8 * format_ip6_address(u8 *s, va_list *args)
Definition: echo_common.c:37
vl_api_fib_path_type_t type
Definition: fib_types.api:123
#define hash_get(h, key)
Definition: hash.h:249
struct _unformat_input_t unformat_input_t
#define ip46_address_is_ip4(ip46)
Definition: ip6_packet.h:88
#define ARRAY_LEN(x)
Definition: clib.h:62
static u8 * format_api_error(u8 *s, va_list *args)
Definition: echo_common.c:131
#define foreach_vnet_api_error
Definition: api_errno.h:22
static uword unformat_data(unformat_input_t *input, va_list *args)
Definition: echo_common.c:113
signed int i32
Definition: types.h:77
#define hash_create(elts, value_bytes)
Definition: hash.h:696
ip46_type_t
Definition: ip6_packet.h:70
echo_common_main_t echo_common_main
Definition: echo_common.c:27
u64 uword
Definition: types.h:112
uword * error_string_by_error_number
Definition: echo_common.c:24
u16 as_u16[8]
Definition: ip6_packet.h:49
uword unformat(unformat_input_t *i, const char *fmt,...)
Definition: unformat.c:978