From 42529e96377891b8e037d849a75a4f628f5b39a9 Mon Sep 17 00:00:00 2001 From: Krzysztof Karas Date: Wed, 1 Dec 2021 10:23:55 +0000 Subject: [PATCH] trace: allow specifying a subset of a group's tpoints This patch aims to introduce a change in enabling tracepoints inside SPDK. Currently every hit tracepoint will be stored inside an internal buffer, what is inconvenient when looking for certain information (eg. starting IO to record some tracepoints, stopping the IO and having the tracepoint buffer flooded with irrelevant information before copying the contents connected with IO operations). The tpoint mask option (-e) has been extended with ':' character. User may now enter tpoint mask for individual trace points inside chosen tpoint group. Example: "-e 0x20:3f", where "0x20" stands for tpoint group, ':' is a separator and "3f" is the tpoint mask. Change-Id: I2a700aa5a75a6abb409376e8f5c44d5501629877 Signed-off-by: Krzysztof Karas Reviewed-on: https://review.spdk.io/gerrit/c/spdk/spdk/+/10431 Reviewed-by: Jim Harris Reviewed-by: Konrad Sztyber Tested-by: SPDK CI Jenkins Community-CI: Mellanox Build Bot Community-CI: Broadcom CI --- lib/event/app.c | 44 +++++++++++++++++++++++++++++++++-------- lib/trace/trace_flags.c | 12 +++++++++-- 2 files changed, 46 insertions(+), 10 deletions(-) diff --git a/lib/event/app.c b/lib/event/app.c index 534662668..f4b34aca1 100644 --- a/lib/event/app.c +++ b/lib/event/app.c @@ -367,9 +367,9 @@ static int app_setup_trace(struct spdk_app_opts *opts) { char shm_name[64]; - uint64_t tpoint_group_mask; - char *end = NULL, *tpoint_group_mask_str; - char *tpoint_group_str, *tp_g_str; + uint64_t tpoint_group_mask, tpoint_mask = -1ULL; + char *end = NULL, *tpoint_group_mask_str, *tpoint_group_str = NULL; + char *tp_g_str, *tpoint_group, *tpoints; if (opts->shm_id >= 0) { snprintf(shm_name, sizeof(shm_name), "/%s_trace.%d", opts->name, opts->shm_id); @@ -394,13 +394,41 @@ app_setup_trace(struct spdk_app_opts *opts) * to free later, because spdk_strsepq() modifies given char*. */ tp_g_str = tpoint_group_mask_str; while ((tpoint_group_str = spdk_strsepq(&tpoint_group_mask_str, ",")) != NULL) { - errno = 0; - tpoint_group_mask = strtoull(tpoint_group_str, &end, 16); - if (*end != '\0' || errno) { - break; + if (strchr(tpoint_group_str, ':')) { + /* Get the tpoint group mask */ + tpoint_group = spdk_strsepq(&tpoint_group_str, ":"); + /* Get the tpoint mask inside that group */ + tpoints = spdk_strsepq(&tpoint_group_str, ":"); + + errno = 0; + tpoint_group_mask = strtoull(tpoint_group, &end, 16); + if (*end != '\0' || errno) { + break; + } + /* Check if tpoint group mask has only one bit set. + * This is to avoid enabling individual tpoints in + * more than one tracepoint group at once. */ + if (!spdk_u64_is_pow2(tpoint_group_mask)) { + SPDK_ERRLOG("Tpoint group mask: %s contains multiple tpoint groups.\n", tpoint_group); + SPDK_ERRLOG("This is not supported, to prevent from activating tpoints by mistake.\n"); + break; + } + + errno = 0; + tpoint_mask = strtoull(tpoints, &end, 16); + if (*end != '\0' || errno) { + break; + } + } else { + errno = 0; + tpoint_group_mask = strtoull(tpoint_group_str, &end, 16); + if (*end != '\0' || errno) { + break; + } + tpoint_mask = -1ULL; } - spdk_trace_set_tpoint_group_mask(tpoint_group_mask); + spdk_trace_set_tpoints(spdk_u64log2(tpoint_group_mask), tpoint_mask); } if (tpoint_group_str != NULL) { diff --git a/lib/trace/trace_flags.c b/lib/trace/trace_flags.c index c2701c6d6..7f5043554 100644 --- a/lib/trace/trace_flags.c +++ b/lib/trace/trace_flags.c @@ -222,8 +222,9 @@ spdk_trace_mask_usage(FILE *f, const char *tmask_arg) { struct spdk_trace_register_fn *register_fn; - fprintf(f, " %s, --tpoint-group-mask \n", tmask_arg); - fprintf(f, " tracepoint group mask for spdk trace buffers (default 0x0"); + fprintf(f, " %s, --tpoint-group-mask [:]\n", tmask_arg); + fprintf(f, " group_mask - tracepoint group mask "); + fprintf(f, "for spdk trace buffers (default 0x0"); register_fn = g_reg_fn_head; while (register_fn) { @@ -232,6 +233,13 @@ spdk_trace_mask_usage(FILE *f, const char *tmask_arg) } fprintf(f, ", all 0xffff)\n"); + fprintf(f, " tpoint_mask - tracepoint mask for enabling individual"); + fprintf(f, " tpoints inside a tracepoint group."); + fprintf(f, " First tpoint inside a group can be"); + fprintf(f, " enabled by setting tpoint_mask to 1 (e.g. 0x8:1).\n"); + fprintf(f, " Masks can be combined (e.g. 0x400,0x8:1).\n"); + fprintf(f, " All available tpoints can be found in"); + fprintf(f, " /include/spdk_internal/trace_defs.h\n"); } void