19 #include <vpp/app/version.h> 51 #define foreach_ip6_hop_by_hop_ioam_trace_stats \ 52 _(PROCESSED, "Pkts with ip6 hop-by-hop trace options") \ 53 _(PROFILE_MISS, "Pkts with ip6 hop-by-hop trace options but no profile set") \ 54 _(UPDATED, "Pkts with trace updated") \ 55 _(FULL, "Pkts with trace options but no space") \ 56 _(LOOPBACK, "Pkts with trace options Loopback") \ 57 _(LOOPBACK_REPLY, "Pkts with trace options Loopback Reply") 60 #define _(sym,string) string, 67 #define _(sym,str) IP6_IOAM_TRACE_##sym, 98 u32 *elt = va_arg (*args,
u32 *);
99 u8 *trace_type_p = va_arg (*args,
u8 *);
100 u8 trace_type = *trace_type_p;
105 u32 ttl_node_id_host_byte_order = clib_net_to_host_u32 (*elt);
106 s =
format (s,
"ttl 0x%x node id 0x%x ",
107 ttl_node_id_host_byte_order >> 24,
108 ttl_node_id_host_byte_order & 0x00FFFFFF);
115 u32 ingress_host_byte_order = clib_net_to_host_u32 (*elt);
116 s =
format (s,
"ingress 0x%x egress 0x%x ",
117 ingress_host_byte_order >> 16,
118 ingress_host_byte_order & 0xFFFF);
124 u32 ts_in_host_byte_order = clib_net_to_host_u32 (*elt);
125 s =
format (s,
"ts 0x%x \n", ts_in_host_byte_order);
131 u32 appdata_in_host_byte_order = clib_net_to_host_u32 (*elt);
132 s =
format (s,
"app 0x%x ", appdata_in_host_byte_order);
144 u8 trace_data_size = 0;
159 return VNET_API_ERROR_INVALID_VALUE;
162 return VNET_API_ERROR_INVALID_VALUE;
165 sizeof (ioam_trace_option_t) + (profile->
num_elts * trace_data_size);
177 ioam_trace_option_t *trace_option =
NULL;
178 u8 trace_data_size = 0;
179 u8 trace_option_elts = 0;
194 trace_option_elts = profile->
num_elts;
196 trace_option = (ioam_trace_option_t *) rewrite_string;
199 trace_option->hdr.length = 2 +
200 trace_option_elts * trace_data_size;
201 trace_option->trace_hdr.ioam_trace_type =
203 trace_option->trace_hdr.data_list_elts_left = trace_option_elts;
205 sizeof (ioam_trace_option_t) + (trace_option_elts * trace_data_size);
212 ioam_trace_option_t *
trace)
222 ioam_trace_option_t *opt;
238 opt = (ioam_trace_option_t *)
245 *to_next = buf_index;
259 ioam_trace_option_t *
trace = (ioam_trace_option_t *) opt;
286 if (
PREDICT_TRUE (trace->trace_hdr.data_list_elts_left))
288 trace->trace_hdr.data_list_elts_left--;
293 trace->trace_hdr.data_list_elts_left *
295 elt = &trace->trace_hdr.elts[elt_index];
307 (adj->rewrite_header.sw_if_index & 0xFFFF);
308 *elt = clib_host_to_net_u32 (*elt);
320 *elt = clib_host_to_net_u32 (time_u64.
as_u32[0]);
324 if (trace->trace_hdr.ioam_trace_type &
BIT_APPDATA)
327 *elt = clib_host_to_net_u32 (profile->
app_data);
352 ioam_trace_option_t *
trace;
353 u8 trace_data_size_in_words = 0;
357 trace = (ioam_trace_option_t *) opt;
359 format (s,
" Trace Type 0x%x , %d elts left\n",
360 trace->trace_hdr.ioam_trace_type,
361 trace->trace_hdr.data_list_elts_left);
362 trace_data_size_in_words =
364 elt = &trace->trace_hdr.elts[0];
366 ((
u8 *) (&trace->trace_hdr.elts[0]) + trace->hdr.length - 2
369 s =
format (s,
" [%d] %U\n", elt_index,
371 elt, &trace->trace_hdr.ioam_trace_type);
373 elt += trace_data_size_in_words;
403 .path =
"show ioam trace",
404 .short_help =
"iOAM trace statistics",
411 .version = VPP_BUILD_VER,
412 .description =
"Inbound OAM",
441 (
"registration of HBH_OPTION_TYPE_IOAM_TRACE_DATA_LIST failed"));
445 sizeof (ioam_trace_option_t),
449 (
"registration of HBH_OPTION_TYPE_IOAM_TRACE_DATA_LIST for rewrite failed"));
static vlib_cli_command_t trace
(constructor) VLIB_CLI_COMMAND (trace)
static void ip6_hbh_ioam_trace_set_bit(ioam_trace_option_t *trace, u8 trace_bit)
vnet_main_t * vnet_get_main(void)
#define foreach_ip6_hop_by_hop_ioam_trace_stats
static f64 vlib_time_now(vlib_main_t *vm)
int ip6_hbh_register_option(u8 option, int options(vlib_buffer_t *b, ip6_header_t *ip, ip6_hop_by_hop_option_t *opt), u8 *trace(u8 *s, ip6_hop_by_hop_option_t *opt))
static u8 fetch_trace_data_size(u16 trace_type)
static trace_profile * trace_profile_find(void)
static vlib_buffer_t * vlib_buffer_copy(vlib_main_t *vm, vlib_buffer_t *b)
static ip_adjacency_t * adj_get(adj_index_t adj_index)
Get a pointer to an adjacency object from its index.
memset(h->entries, 0, sizeof(h->entries[0])*entries)
#define VLIB_INIT_FUNCTION(x)
int ip6_trace_profile_setup(void)
int ip6_hop_by_hop_ioam_trace_rewrite_handler(u8 *rewrite_string, u8 *rewrite_size)
ip6_hop_by_hop_ioam_trace_main_t ip6_hop_by_hop_ioam_trace_main
static u32 counter_index(vlib_main_t *vm, vlib_error_t e)
vlib_frame_t * vlib_get_frame_to_node(vlib_main_t *vm, u32 to_node_index)
#define clib_error_create(args...)
#define vlib_call_init_function(vm, x)
u8 options_size[MAX_IP6_HBH_OPTION]
static u32 vlib_get_buffer_index(vlib_main_t *vm, void *p)
Translate buffer pointer into buffer index.
ip6_hop_by_hop_ioam_main_t ip6_hop_by_hop_ioam_main
void vlib_put_frame_to_node(vlib_main_t *vm, u32 to_node_index, vlib_frame_t *f)
static void * vlib_buffer_get_current(vlib_buffer_t *b)
Get pointer to current data to process.
static u8 * format_ioam_data_list_element(u8 *s, va_list *args)
int ip6_hbh_ioam_trace_data_list_handler(vlib_buffer_t *b, ip6_header_t *ip, ip6_hop_by_hop_option_t *opt)
int ip6_trace_profile_cleanup(void)
The fine-grained event logger allows lightweight, thread-safe event logging at minimum cost...
static void ip6_hbh_ioam_loopback_handler(vlib_buffer_t *b, ip6_header_t *ip, ioam_trace_option_t *trace)
clib_error_t * ip_main_init(vlib_main_t *vm)
#define vec_free(V)
Free vector's memory (no header).
static char * ip6_hop_by_hop_ioam_trace_stats_strings[]
static void ip6_ioam_trace_stats_increment_counter(u32 counter_index, u64 increment)
static void udp_ping_create_reply_from_probe_ip6(ip6_header_t *ip, ip6_hop_by_hop_header_t *hbh, udp_ping_t *udp)
Create and send ipv6 udp-ping response packet.
static clib_error_t * ip6_show_ioam_trace_cmd_fn(vlib_main_t *vm, unformat_input_t *input, vlib_cli_command_t *cmd)
vlib_node_t * vlib_get_node_by_name(vlib_main_t *vm, u8 *name)
#define BIT_ING_INTERFACE
#define VLIB_CLI_COMMAND(x,...)
#define BIT_LOOPBACK_REPLY
#define HBH_OPTION_TYPE_IOAM_TRACE_DATA_LIST
static clib_error_t * ip6_hop_by_hop_ioam_init(vlib_main_t *vm)
static ip6_hop_by_hop_option_t * ip6_hbh_get_option(ip6_hop_by_hop_header_t *hbh0, u8 option_to_search)
static void * vlib_frame_vector_args(vlib_frame_t *f)
Get pointer to frame vector data.
#define HBH_OPTION_TYPE_DATA_CHANGE_ENROUTE
static clib_error_t * ip6_hop_by_hop_ioam_trace_init(vlib_main_t *vm)
int ip6_hbh_add_register_option(u8 option, u8 size, int rewrite_options(u8 *rewrite_string, u8 *rewrite_size))
int ip6_ioam_trace_get_sizeof_handler(u32 *result)
static clib_error_t * ip6_lookup_init(vlib_main_t *vm)
static f64 trace_tsp_mul[4]
void vlib_cli_output(vlib_main_t *vm, char *fmt,...)
u8 * ip6_hbh_ioam_trace_data_list_trace_handler(u8 *s, ip6_hop_by_hop_option_t *opt)
u64 counters[ARRAY_LEN(ip6_hop_by_hop_ioam_trace_stats_strings)]