From owner-svn-src-head@freebsd.org Wed Aug 5 19:05:50 2020 Return-Path: Delivered-To: svn-src-head@mailman.nyi.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2610:1c1:1:606c::19:1]) by mailman.nyi.freebsd.org (Postfix) with ESMTP id B54093A6D35; Wed, 5 Aug 2020 19:05:50 +0000 (UTC) (envelope-from mjg@FreeBSD.org) Received: from mxrelay.nyi.freebsd.org (mxrelay.nyi.freebsd.org [IPv6:2610:1c1:1:606c::19:3]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256 client-signature RSA-PSS (4096 bits) client-digest SHA256) (Client CN "mxrelay.nyi.freebsd.org", Issuer "Let's Encrypt Authority X3" (verified OK)) by mx1.freebsd.org (Postfix) with ESMTPS id 4BMLgL4P7Pz46V8; Wed, 5 Aug 2020 19:05:50 +0000 (UTC) (envelope-from mjg@FreeBSD.org) Received: from repo.freebsd.org (repo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:0]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by mxrelay.nyi.freebsd.org (Postfix) with ESMTPS id 6DAD61AE54; Wed, 5 Aug 2020 19:05:50 +0000 (UTC) (envelope-from mjg@FreeBSD.org) Received: from repo.freebsd.org ([127.0.1.37]) by repo.freebsd.org (8.15.2/8.15.2) with ESMTP id 075J5oX4068263; Wed, 5 Aug 2020 19:05:50 GMT (envelope-from mjg@FreeBSD.org) Received: (from mjg@localhost) by repo.freebsd.org (8.15.2/8.15.2/Submit) id 075J5nAf068258; Wed, 5 Aug 2020 19:05:49 GMT (envelope-from mjg@FreeBSD.org) Message-Id: <202008051905.075J5nAf068258@repo.freebsd.org> X-Authentication-Warning: repo.freebsd.org: mjg set sender to mjg@FreeBSD.org using -f From: Mateusz Guzik Date: Wed, 5 Aug 2020 19:05:49 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r363928 - in head: lib/libpmcstat usr.sbin/pmcstat X-SVN-Group: head X-SVN-Commit-Author: mjg X-SVN-Commit-Paths: in head: lib/libpmcstat usr.sbin/pmcstat X-SVN-Commit-Revision: 363928 X-SVN-Commit-Repository: base MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-src-head@freebsd.org X-Mailman-Version: 2.1.33 Precedence: list List-Id: SVN commit messages for the src tree for head/-current List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Wed, 05 Aug 2020 19:05:50 -0000 Author: mjg Date: Wed Aug 5 19:05:49 2020 New Revision: 363928 URL: https://svnweb.freebsd.org/changeset/base/363928 Log: pmcstat: implement showing offsets into symbols in top mode The -I option (and hotkey) is reused for this. Skipping symbol resolution is moved to the new -A option (and hotkey). While arguably this violates POLA I think it's a change for the better. ALso note the -I option was added in head. Differential Revision: https://reviews.freebsd.org/D21658 Modified: head/lib/libpmcstat/libpmcstat.h head/usr.sbin/pmcstat/pmcpl_callgraph.c head/usr.sbin/pmcstat/pmcstat.8 head/usr.sbin/pmcstat/pmcstat.c head/usr.sbin/pmcstat/pmcstat_log.c Modified: head/lib/libpmcstat/libpmcstat.h ============================================================================== --- head/lib/libpmcstat/libpmcstat.h Wed Aug 5 18:22:24 2020 (r363927) +++ head/lib/libpmcstat/libpmcstat.h Wed Aug 5 19:05:49 2020 (r363928) @@ -107,8 +107,9 @@ struct pmcstat_args { #define FLAGS_HAS_CPUMASK 0x00040000 /* -c */ #define FLAG_HAS_DURATION 0x00080000 /* -l secs */ #define FLAG_DO_WIDE_GPROF_HC 0x00100000 /* -e */ -#define FLAG_SKIP_TOP_FN_RES 0x00200000 /* -I */ +#define FLAG_SKIP_TOP_FN_RES 0x00200000 /* -A */ #define FLAG_FILTER_THREAD_ID 0x00400000 /* -L */ +#define FLAG_SHOW_OFFSET 0x00800000 /* -I */ int pa_required; /* required features */ int pa_pplugin; /* pre-processing plugin */ Modified: head/usr.sbin/pmcstat/pmcpl_callgraph.c ============================================================================== --- head/usr.sbin/pmcstat/pmcpl_callgraph.c Wed Aug 5 18:22:24 2020 (r363927) +++ head/usr.sbin/pmcstat/pmcpl_callgraph.c Wed Aug 5 19:05:49 2020 (r363928) @@ -152,10 +152,12 @@ pmcstat_cgnode_hash_lookup_pc(struct pmcstat_process * * Try determine the function at this offset. If we can't * find a function round leave the `pc' value alone. */ - if ((sym = pmcstat_symbol_search(image, pc)) != NULL) - pc = sym->ps_start; - else - pmcstat_stats.ps_samples_unknown_function++; + if (!(args.pa_flags & (FLAG_SKIP_TOP_FN_RES | FLAG_SHOW_OFFSET))) { + if ((sym = pmcstat_symbol_search(image, pc)) != NULL) + pc = sym->ps_start; + else + pmcstat_stats.ps_samples_unknown_function++; + } for (hash = i = 0; i < sizeof(uintfptr_t); i++) hash += (pc >> i) & 0xFF; @@ -485,22 +487,35 @@ pmcstat_cgnode_topprint(struct pmcstat_cgnode *cg, v = PMCPL_CG_COUNTP(cg); snprintf(vs, sizeof(vs), "%.1f", v); v_attrs = PMCSTAT_ATTRPERCENT(v); - sym = NULL; /* Format name. */ - if (!(args.pa_flags & FLAG_SKIP_TOP_FN_RES)) - sym = pmcstat_symbol_search(cg->pcg_image, cg->pcg_func); - if (sym != NULL) { - snprintf(ns, sizeof(ns), "%s", - pmcstat_string_unintern(sym->ps_name)); - } else + sym = pmcstat_symbol_search(cg->pcg_image, cg->pcg_func); + if (sym == NULL) { snprintf(ns, sizeof(ns), "%p", (void *)(cg->pcg_image->pi_vaddr + cg->pcg_func)); + } else { + switch (args.pa_flags & (FLAG_SKIP_TOP_FN_RES | FLAG_SHOW_OFFSET)) { + case FLAG_SKIP_TOP_FN_RES | FLAG_SHOW_OFFSET: + case FLAG_SKIP_TOP_FN_RES: + snprintf(ns, sizeof(ns), "%p", + (void *)(cg->pcg_image->pi_vaddr + cg->pcg_func)); + break; + case FLAG_SHOW_OFFSET: + snprintf(ns, sizeof(ns), "%s+%#0lx", + pmcstat_string_unintern(sym->ps_name), + cg->pcg_func - sym->ps_start); + break; + default: + snprintf(ns, sizeof(ns), "%s", + pmcstat_string_unintern(sym->ps_name)); + break; + } + } PMCSTAT_ATTRON(v_attrs); PMCSTAT_PRINTW("%5.5s", vs); PMCSTAT_ATTROFF(v_attrs); - PMCSTAT_PRINTW(" %-10.10s %-20.20s", + PMCSTAT_PRINTW(" %-10.10s %-30.30s", pmcstat_string_unintern(cg->pcg_image->pi_name), ns); @@ -624,7 +639,7 @@ pmcpl_cg_topdisplay(void) qsort(sortbuffer, nentries, sizeof(struct pmcstat_cgnode *), pmcstat_cgnode_compare); - PMCSTAT_PRINTW("%5.5s %-10.10s %-20.20s %s\n", + PMCSTAT_PRINTW("%5.5s %-10.10s %-30.30s %s\n", "%SAMP", "IMAGE", "FUNCTION", "CALLERS"); nentries = min(pmcstat_displayheight - 2, nentries); Modified: head/usr.sbin/pmcstat/pmcstat.8 ============================================================================== --- head/usr.sbin/pmcstat/pmcstat.8 Wed Aug 5 18:22:24 2020 (r363927) +++ head/usr.sbin/pmcstat/pmcstat.8 Wed Aug 5 19:05:49 2020 (r363928) @@ -25,7 +25,7 @@ .\" .\" $FreeBSD$ .\" -.Dd May 25, 2018 +.Dd August 5, 2020 .Dt PMCSTAT 8 .Os .Sh NAME @@ -33,6 +33,7 @@ .Nd "performance measurement with performance monitoring hardware" .Sh SYNOPSIS .Nm +.Op Fl A .Op Fl C .Op Fl D Ar pathname .Op Fl E @@ -123,6 +124,8 @@ process' current and future children. .Sh OPTIONS The following options are available: .Bl -tag -width indent +.It Fl A +Skip symbol lookup and display address instead. .It Fl C Toggle between showing cumulative or incremental counts for subsequent counting mode PMCs specified on the command line. @@ -161,7 +164,7 @@ this information is sent to the output file specified .Fl o option. .It Fl I -Skip symbol lookup and display address instead. +Show the offset of the instruction pointer into the symbol. .It Fl L List all event names. .It Fl M Ar mapfilename @@ -222,10 +225,10 @@ specified in .Ar event-spec . .It Fl T Use a top like mode for sampling PMCs. The following hotkeys -can be used: 'c+a' switch to accumulative mode, 'c+d' switch -to delta mode, 'm' merge PMCs, 'n' change view, 'p' show next -PMC, ' ' pause, 'q' quit. calltree only: 'f' cost under threshold -is seen as a dot. +can be used: 'A' toggle symbol resolution, 'c+a' switch to accumulative mode, 'c+d' +switch to delta mode, 'I' toggle showing offsets into symbols, 'm' merge PMCs, 'n' +change view, 'p' show next PMC, ' ' pause, 'q' quit. calltree only: 'f' cost under +threshold is seen as a dot. .It Fl U Toggle capturing user-space call traces while in kernel mode. The default is for sampling PMCs to capture user-space callchain information Modified: head/usr.sbin/pmcstat/pmcstat.c ============================================================================== --- head/usr.sbin/pmcstat/pmcstat.c Wed Aug 5 18:22:24 2020 (r363927) +++ head/usr.sbin/pmcstat/pmcstat.c Wed Aug 5 19:05:49 2020 (r363928) @@ -511,8 +511,12 @@ main(int argc, char **argv) CPU_COPY(&rootmask, &cpumask); while ((option = getopt(argc, argv, - "CD:EF:G:ILM:NO:P:R:S:TUWZa:c:def:gi:k:l:m:n:o:p:qr:s:t:u:vw:z:")) != -1) + "ACD:EF:G:ILM:NO:P:R:S:TUWZa:c:def:gi:k:l:m:n:o:p:qr:s:t:u:vw:z:")) != -1) switch (option) { + case 'A': + args.pa_flags |= FLAG_SKIP_TOP_FN_RES; + break; + case 'a': /* Annotate + callgraph */ args.pa_flags |= FLAG_DO_ANNOTATE; args.pa_plugin = PMCSTAT_PL_ANNOTATE_CG; @@ -586,12 +590,13 @@ main(int argc, char **argv) args.pa_plugin = PMCSTAT_PL_GPROF; break; - case 'I': - args.pa_flags |= FLAG_SKIP_TOP_FN_RES; - break; case 'i': args.pa_flags |= FLAG_FILTER_THREAD_ID; args.pa_tid = strtol(optarg, &end, 0); + break; + + case 'I': + args.pa_flags |= FLAG_SHOW_OFFSET; break; case 'k': /* pathname to the kernel */ Modified: head/usr.sbin/pmcstat/pmcstat_log.c ============================================================================== --- head/usr.sbin/pmcstat/pmcstat_log.c Wed Aug 5 18:22:24 2020 (r363927) +++ head/usr.sbin/pmcstat/pmcstat_log.c Wed Aug 5 19:05:49 2020 (r363928) @@ -612,6 +612,12 @@ pmcstat_keypress_log(void) c = wgetch(w); wprintw(w, "Key: %c => ", c); switch (c) { + case 'A': + if (args.pa_flags & FLAG_SKIP_TOP_FN_RES) + args.pa_flags &= ~FLAG_SKIP_TOP_FN_RES; + else + args.pa_flags |= FLAG_SKIP_TOP_FN_RES; + break; case 'c': wprintw(w, "enter mode 'd' or 'a' => "); c = wgetch(w); @@ -622,6 +628,12 @@ pmcstat_keypress_log(void) args.pa_topmode = PMCSTAT_TOP_ACCUM; wprintw(w, "switching to accumulation mode"); } + break; + case 'I': + if (args.pa_flags & FLAG_SHOW_OFFSET) + args.pa_flags &= ~FLAG_SHOW_OFFSET; + else + args.pa_flags |= FLAG_SHOW_OFFSET; break; case 'm': pmcstat_mergepmc = !pmcstat_mergepmc;