X-Git-Url: https://gerrit.fd.io/r/gitweb?a=blobdiff_plain;f=src%2Fvlib%2Ftrace.c;h=f90f275fa87a9a0d03d1f3255059731a5c6f3f13;hb=85866e782c0e8d49b2fbc5f8fdf77065f1efae14;hp=7ee1b63f07e66d77332428c977d5257b13ded114;hpb=87d24db65facb89ca524c951b8379ca2ec4dbc7a;p=vpp.git diff --git a/src/vlib/trace.c b/src/vlib/trace.c index 7ee1b63f07e..f90f275fa87 100644 --- a/src/vlib/trace.c +++ b/src/vlib/trace.c @@ -40,7 +40,7 @@ #include #include -u8 *vnet_trace_dummy; +u8 *vnet_trace_placeholder; /* Helper function for nodes which only trace buffer data. */ void @@ -122,6 +122,12 @@ clear_trace_buffer (void) tm = &this_vlib_main->trace_main; tm->trace_enable = 0; + vec_free (tm->nodes); + })); + + foreach_vlib_main ( + ({ + tm = &this_vlib_main->trace_main; for (i = 0; i < vec_len (tm->trace_buffer_pool); i++) if (! pool_is_free_index (tm->trace_buffer_pool, i)) @@ -175,8 +181,8 @@ VLIB_CLI_COMMAND (trace_cli_command,static) = { }; /* *INDENT-ON* */ -static int -trace_cmp (void *a1, void *a2) +int +trace_time_cmp (void *a1, void *a2) { vlib_trace_header_t **t1 = a1; vlib_trace_header_t **t2 = a2; @@ -195,6 +201,15 @@ filter_accept (vlib_trace_main_t * tm, vlib_trace_header_t * h) if (tm->filter_flag == 0) return 1; + /* + * When capturing a post-mortem dispatch trace, + * toss all existing traces once per dispatch cycle. + * So we can trace 4 billion pkts without running out of + * memory... + */ + if (tm->filter_flag == FILTER_FLAG_POST_MORTEM) + return 0; + if (tm->filter_flag == FILTER_FLAG_INCLUDE) { while (h < e) @@ -316,7 +331,7 @@ cli_show_trace_buffer (vlib_main_t * vm, } /* Sort them by increasing time. */ - vec_sort_with_function (traces, trace_cmp); + vec_sort_with_function (traces, trace_time_cmp); for (i = 0; i < vec_len (traces); i++) { @@ -352,20 +367,63 @@ VLIB_CLI_COMMAND (show_trace_cli,static) = { /* *INDENT-ON* */ int vlib_enable_disable_pkt_trace_filter (int enable) __attribute__ ((weak)); + int vlib_enable_disable_pkt_trace_filter (int enable) { return 0; } +void +vlib_trace_stop_and_clear (void) +{ + vlib_enable_disable_pkt_trace_filter (0); /* disble tracing */ + clear_trace_buffer (); +} + + +void +trace_update_capture_options (u32 add, u32 node_index, u32 filter, u8 verbose) +{ + vlib_trace_main_t *tm; + vlib_trace_node_t *tn; + + if (add == ~0) + add = 50; + + /* *INDENT-OFF* */ + foreach_vlib_main (( + { + tm = &this_vlib_main->trace_main; + tm->verbose = verbose; + vec_validate (tm->nodes, node_index); + tn = tm->nodes + node_index; + + /* + * Adding 0 makes no real sense, and there wa no other way + * to explicilty zero-out the limits and count, so make + * an "add 0" request really be "set to 0". + */ + if (add == 0) + tn->limit = tn->count = 0; + else + tn->limit += add; + })); + + foreach_vlib_main (( + { + tm = &this_vlib_main->trace_main; + tm->trace_enable = 1; + })); + /* *INDENT-ON* */ +} + static clib_error_t * cli_add_trace_buffer (vlib_main_t * vm, unformat_input_t * input, vlib_cli_command_t * cmd) { unformat_input_t _line_input, *line_input = &_line_input; - vlib_trace_main_t *tm; vlib_node_t *node; - vlib_trace_node_t *tn; u32 node_index, add; u8 verbose = 0; int filter = 0; @@ -374,8 +432,9 @@ cli_add_trace_buffer (vlib_main_t * vm, if (!unformat_user (input, unformat_line_input, line_input)) return 0; - if (vnet_trace_dummy == 0) - vec_validate_aligned (vnet_trace_dummy, 2048, CLIB_CACHE_LINE_BYTES); + if (vnet_trace_placeholder == 0) + vec_validate_aligned (vnet_trace_placeholder, 2048, + CLIB_CACHE_LINE_BYTES); while (unformat_check_input (line_input) != (uword) UNFORMAT_END_OF_INPUT) { @@ -414,17 +473,7 @@ cli_add_trace_buffer (vlib_main_t * vm, } } - /* *INDENT-OFF* */ - foreach_vlib_main (( - { - tm = &this_vlib_main->trace_main; - tm->verbose = verbose; - vec_validate (tm->nodes, node_index); - tn = tm->nodes + node_index; - tn->limit += add; - tm->trace_enable = 1; - })); - /* *INDENT-ON* */ + trace_update_capture_options (add, node_index, filter, verbose); done: unformat_free (line_input); @@ -435,7 +484,7 @@ done: /* *INDENT-OFF* */ VLIB_CLI_COMMAND (add_trace_cli,static) = { .path = "trace add", - .short_help = "Trace given number of packets", + .short_help = "trace add [filter] [verbose]", .function = cli_add_trace_buffer, }; /* *INDENT-ON* */ @@ -477,11 +526,35 @@ VLIB_CLI_COMMAND (add_trace_cli,static) = { * criteria (e.g. input sw_if_index, mac address) but for now just checks if * a specified node is in the trace or not in the trace. */ + +void +trace_filter_set (u32 node_index, u32 flag, u32 count) +{ + /* *INDENT-OFF* */ + foreach_vlib_main ( + ({ + vlib_trace_main_t *tm; + + tm = &this_vlib_main->trace_main; + tm->filter_node_index = node_index; + tm->filter_flag = flag; + tm->filter_count = count; + + /* + * Clear the trace limits to stop any in-progress tracing + * Prevents runaway trace allocations when the filter changes + * (or is removed) + */ + vec_free (tm->nodes); + })); + /* *INDENT-ON* */ +} + + static clib_error_t * cli_filter_trace (vlib_main_t * vm, unformat_input_t * input, vlib_cli_command_t * cmd) { - vlib_trace_main_t *tm = &vm->trace_main; u32 filter_node_index; u32 filter_flag; u32 filter_count; @@ -509,22 +582,7 @@ cli_filter_trace (vlib_main_t * vm, ("expected 'include NODE COUNT' or 'exclude NODE COUNT' or 'none', got `%U'", format_unformat_error, input); - /* *INDENT-OFF* */ - foreach_vlib_main ( - ({ - tm = &this_vlib_main->trace_main; - tm->filter_node_index = filter_node_index; - tm->filter_flag = filter_flag; - tm->filter_count = filter_count; - - /* - * Clear the trace limits to stop any in-progress tracing - * Prevents runaway trace allocations when the filter changes - * (or is removed) - */ - vec_free (tm->nodes); - })); - /* *INDENT-ON* */ + trace_filter_set (filter_node_index, filter_flag, filter_count); return 0; } @@ -532,7 +590,7 @@ cli_filter_trace (vlib_main_t * vm, /* *INDENT-OFF* */ VLIB_CLI_COMMAND (filter_trace_cli,static) = { .path = "trace filter", - .short_help = "filter trace output - include NODE COUNT | exclude NODE COUNT | none", + .short_help = "trace filter none | [include|exclude] NODE COUNT", .function = cli_filter_trace, }; /* *INDENT-ON* */ @@ -541,8 +599,7 @@ static clib_error_t * cli_clear_trace_buffer (vlib_main_t * vm, unformat_input_t * input, vlib_cli_command_t * cmd) { - vlib_enable_disable_pkt_trace_filter (0 /* enable */ ); - clear_trace_buffer (); + vlib_trace_stop_and_clear (); return 0; } @@ -554,7 +611,7 @@ VLIB_CLI_COMMAND (clear_trace_cli,static) = { }; /* *INDENT-ON* */ -/* Dummy function to get us linked in. */ +/* Placeholder function to get us linked in. */ void vlib_trace_cli_reference (void) { @@ -572,6 +629,15 @@ vnet_is_packet_traced (vlib_buffer_t * b, u32 classify_table_index, int func) return 1; } +void * +vlib_add_trace (vlib_main_t * vm, + vlib_node_runtime_t * r, vlib_buffer_t * b, u32 n_data_bytes) +{ + return vlib_add_trace_inline (vm, r, b, n_data_bytes); +} + + + /* * fd.io coding-style-patch-verification: ON *