33 #define NSH_MD2_IOAM_TRACE_SIZE_DUMMY 20 47 u8 data_list_elts_left;
51 }) nsh_md2_ioam_trace_option_t;
55 #define foreach_nsh_md2_ioam_trace_stats \ 56 _(SUCCESS, "Pkts updated with TRACE records") \ 57 _(FAILED, "Errors in TRACE due to lack of TRACE records") 59 static char *nsh_md2_ioam_trace_stats_strings[] = {
60 #define _(sym,string) string, 67 #define _(sym,str) NSH_MD2_IOAM_TRACE_##sym, 112 u32 *elt = va_arg (*args,
u32 *);
113 u8 *trace_type_p = va_arg (*args,
u8 *);
114 u8 trace_type = *trace_type_p;
119 u32 ttl_node_id_host_byte_order = clib_net_to_host_u32 (*elt);
120 s =
format (s,
"ttl 0x%x node id 0x%x ",
121 ttl_node_id_host_byte_order >> 24,
122 ttl_node_id_host_byte_order & 0x00FFFFFF);
129 u32 ingress_host_byte_order = clib_net_to_host_u32 (*elt);
130 s =
format (s,
"ingress 0x%x egress 0x%x ",
131 ingress_host_byte_order >> 16,
132 ingress_host_byte_order & 0xFFFF);
138 u32 ts_in_host_byte_order = clib_net_to_host_u32 (*elt);
139 s =
format (s,
"ts 0x%x \n", ts_in_host_byte_order);
145 u32 appdata_in_host_byte_order = clib_net_to_host_u32 (*elt);
146 s =
format (s,
"app 0x%x ", appdata_in_host_byte_order);
158 nsh_md2_ioam_trace_option_t *trace_option =
NULL;
159 u8 trace_data_size = 0;
160 u8 trace_option_elts = 0;
173 trace_option_elts = profile->
num_elts;
176 trace_option = (nsh_md2_ioam_trace_option_t *) rewrite_string;
177 trace_option->class = clib_host_to_net_u16 (0x9);
179 trace_option->length = (trace_option_elts * trace_data_size) + 4;
180 trace_option->data_list_elts_left = trace_option_elts;
181 trace_option->ioam_trace_type =
185 sizeof (nsh_md2_ioam_trace_option_t) +
186 (trace_option_elts * trace_data_size);
194 nsh_tlv_header_t * opt)
197 nsh_md2_ioam_trace_option_t *
trace =
198 (nsh_md2_ioam_trace_option_t *) ((
u8 *) opt);
205 u16 ioam_trace_type = 0;
220 trace->data_list_elts_left--;
225 trace->data_list_elts_left *
227 elt = &trace->elts[elt_index];
231 *elt = clib_host_to_net_u32 (((ip0->
ttl - 1) << 24) |
242 *elt = clib_host_to_net_u32 (*elt);
255 *elt = clib_host_to_net_u32 (time_u64.
as_u32[0]);
262 *elt = clib_host_to_net_u32 (profile->
app_data);
266 (NSH_MD2_IOAM_TRACE_SUCCESS, 1);
271 (NSH_MD2_IOAM_TRACE_FAILED, 1);
281 nsh_md2_ioam_trace_option_t *
trace;
282 u8 trace_data_size_in_words = 0;
285 u16 ioam_trace_type = 0;
287 trace = (nsh_md2_ioam_trace_option_t *) ((
u8 *) opt);
288 ioam_trace_type = clib_net_to_host_u16 (trace->ioam_trace_type);
290 elt = &trace->elts[0];
292 format (s,
" Trace Type 0x%x , %d elts left\n", ioam_trace_type,
293 trace->data_list_elts_left);
294 while ((
u8 *) elt < ((
u8 *) (&trace->elts[0]) + trace->length - 4
297 s =
format (s,
" [%d] %U\n", elt_index,
300 elt += trace_data_size_in_words;
307 nsh_tlv_header_t * old_opt,
308 nsh_tlv_header_t * new_opt)
312 new_opt->length + sizeof (nsh_tlv_header_t));
327 s =
format (s,
" %s - %lu\n", nsh_md2_ioam_trace_stats_strings[i],
339 .path =
"show ioam nsh-lisp-gpe trace",
340 .short_help =
"iOAM trace statistics",
373 (clib_host_to_net_u16 (0x9),
382 (
"registration of NSH_MD2_IOAM_OPTION_TYPE_TRACE failed"));
404 u8 trace_data_size = 0;
418 return VNET_API_ERROR_INVALID_VALUE;
421 return VNET_API_ERROR_INVALID_VALUE;
424 sizeof (nsh_md2_ioam_trace_option_t) +
425 profile->
num_elts * trace_data_size;
int nsh_md2_ioam_trace_profile_cleanup(void)
static clib_error_t * nsh_md2_ioam_init(vlib_main_t *vm)
static vlib_cli_command_t trace
(constructor) VLIB_CLI_COMMAND (trace)
vnet_main_t * vnet_get_main(void)
typedef CLIB_PACKED(struct { u16 class;u8 type;u8 length;u8 data_list_elts_left;u16 ioam_trace_type;u8 reserve;u32 elts[0];})
#define clib_memcpy_fast(a, b, c)
clib_memset(h->entries, 0, sizeof(h->entries[0]) *entries)
static f64 vlib_time_now(vlib_main_t *vm)
static u8 fetch_trace_data_size(u16 trace_type)
nsh_md2_ioam_trace_stats_t
int nsh_md2_ioam_trace_data_list_handler(vlib_buffer_t *b, nsh_tlv_header_t *opt)
int nsh_md2_ioam_trace_pop_handler(vlib_buffer_t *b, nsh_tlv_header_t *opt)
int nsh_md2_ioam_trace_rewrite_handler(u8 *rewrite_string, u8 *rewrite_size)
static trace_profile * nsh_trace_profile_find(void)
int nsh_md2_ioam_trace_swap_handler(vlib_buffer_t *b, nsh_tlv_header_t *old_opt, nsh_tlv_header_t *new_opt)
u8 options_size[MAX_MD2_OPTIONS]
static f64 trace_tsp_mul[4]
#define NSH_MD2_IOAM_TRACE_SIZE_DUMMY
#define VLIB_INIT_FUNCTION(x)
static u32 counter_index(vlib_main_t *vm, vlib_error_t e)
#define clib_error_create(args...)
#define vlib_call_init_function(vm, x)
nsh_md2_ioam_main_t nsh_md2_ioam_main
static u8 * format_ioam_data_list_element(u8 *s, va_list *args)
static void * vlib_buffer_get_current(vlib_buffer_t *b)
Get pointer to current data to process.
static clib_error_t * nsh_md2_ioam_show_ioam_trace_cmd_fn(vlib_main_t *vm, unformat_input_t *input, vlib_cli_command_t *cmd)
#define foreach_nsh_md2_ioam_trace_stats
The fine-grained event logger allows lightweight, thread-safe event logging at minimum cost...
clib_error_t * nsh_init(vlib_main_t *vm)
u8 * nsh_md2_ioam_trace_data_list_trace_handler(u8 *s, nsh_tlv_header_t *opt)
static clib_error_t * nsh_md2_ioam_trace_init(vlib_main_t *vm)
#define vec_free(V)
Free vector's memory (no header).
#define BIT_ING_INTERFACE
static void nsh_md2_ioam_trace_stats_increment_counter(u32 counter_index, u64 increment)
#define VLIB_CLI_COMMAND(x,...)
static int nsh_md2_ioam_trace_get_sizeof_handler(u32 *result)
u64 counters[ARRAY_LEN(nsh_md2_ioam_trace_stats_strings)]
int nsh_md2_register_option(u16 class, u8 type, u8 option_size, int add_options(u8 *opt, u8 *opt_size), int options(vlib_buffer_t *b, nsh_tlv_header_t *opt), int swap_options(vlib_buffer_t *b, nsh_tlv_header_t *old_opt, nsh_tlv_header_t *new_opt), int pop_options(vlib_buffer_t *b, nsh_tlv_header_t *opt), u8 *trace(u8 *s, nsh_tlv_header_t *opt))
void vlib_cli_output(vlib_main_t *vm, char *fmt,...)
int nsh_md2_ioam_trace_profile_setup(void)
nsh_md2_ioam_trace_main_t nsh_md2_ioam_trace_main
#define NSH_MD2_IOAM_OPTION_TYPE_TRACE