From 4559d65f2a00d57f7fa21339370bb93d89a69c46 Mon Sep 17 00:00:00 2001 From: Karel Zak Date: Mon, 24 May 2021 12:24:33 +0200 Subject: lscpu: add SCALMHZ% and "CPU scaling MHz:" $ lscpu ... Model name: Intel(R) Core(TM) i7-4790K CPU @ 4.00GHz CPU family: 6 Model: 60 Thread(s) per core: 2 Core(s) per socket: 4 Socket(s): 1 Stepping: 3 CPU(s) scaling MHz: 61% CPU max MHz: 4400.0000 CPU min MHz: 800.0000 ... $ lscpu -e=CPU,MAXMHZ,MINMHZ,MHZ,SCALMHZ% CPU MAXMHZ MINMHZ MHZ SCALMHZ% 0 4400.0000 800.0000 2800.000 64% 1 4400.0000 800.0000 4000.146 91% 2 4400.0000 800.0000 2800.000 64% 3 4400.0000 800.0000 2800.000 64% 4 4400.0000 800.0000 2800.000 64% 5 4400.0000 800.0000 4400.000 100% 6 4400.0000 800.0000 800.000 18% 7 4400.0000 800.0000 2800.000 64% iAddresses: https://issues.redhat.com/browse/RHEL-12783 Upstream: http://github.com/util-linux/util-linux/commit/9b9e4f5d06be55f4b9e1a52b448055933df92c6b Addresses: https://github.com/karelzak/util-linux/issues/1314 Signed-off-by: Karel Zak --- Documentation/TODO | 1 + sys-utils/lscpu-cputype.c | 6 ++++++ sys-utils/lscpu-topology.c | 21 +++++++++++++++++++++ sys-utils/lscpu.c | 9 +++++++++ sys-utils/lscpu.h | 4 +++- 5 files changed, 40 insertions(+), 1 deletion(-) diff --git a/Documentation/TODO b/Documentation/TODO index 33ffa189d..e382e4b97 100644 --- a/Documentation/TODO +++ b/Documentation/TODO @@ -53,6 +53,7 @@ cal lscpu ----- + - add --freq output to visualise CPU use, see https://github.com/karelzak/util-linux/issues/1314 - read cpuid and uname information from file if --sysroot is specified, then we can prepare regression tests completely independent on hw and architecture. diff --git a/sys-utils/lscpu-cputype.c b/sys-utils/lscpu-cputype.c index 7b5b109c9..dd0c86084 100644 --- a/sys-utils/lscpu-cputype.c +++ b/sys-utils/lscpu-cputype.c @@ -530,6 +530,12 @@ int lscpu_read_cpuinfo(struct lscpu_cxt *cxt) pr->curr_type->static_mhz = xstrdup(value); if (pattern->id == PAT_BOGOMIPS_CPU && pr->curr_type && !pr->curr_type->bogomips) pr->curr_type->bogomips = xstrdup(value); + if (pattern->id == PAT_MHZ && pr->curr_cpu && value) { + errno = 0; + pr->curr_cpu->mhz_cur_freq = strtof(value, NULL); + if (errno) + pr->curr_cpu->mhz_cur_freq = 0; + } break; case CPUINFO_LINE_CPUTYPE: if (pr->curr_type && is_different_cputype(pr->curr_type, pattern->offset, value)) { diff --git a/sys-utils/lscpu-topology.c b/sys-utils/lscpu-topology.c index f4e8181b7..bba727643 100644 --- a/sys-utils/lscpu-topology.c +++ b/sys-utils/lscpu-topology.c @@ -588,6 +588,27 @@ float lsblk_cputype_get_minmhz(struct lscpu_cxt *cxt, struct lscpu_cputype *ct) return res; } +/* returns scaling (use) of CPUs freq. in percent */ +float lsblk_cputype_get_scalmhz(struct lscpu_cxt *cxt, struct lscpu_cputype *ct) +{ + size_t i; + float fmax = 0, fcur = 0; + + for (i = 0; i < cxt->npossibles; i++) { + struct lscpu_cpu *cpu = cxt->cpus[i]; + + if (!cpu || cpu->type != ct || !is_cpu_present(cxt, cpu)) + continue; + if (cpu->mhz_max_freq <= 0.0 || cpu->mhz_cur_freq <= 0.0) + continue; + fmax += cpu->mhz_max_freq; + fcur += cpu->mhz_cur_freq; + } + if (fcur <= 0.0) + return 0.0; + return fcur / fmax * 100; +} + int lscpu_read_topology(struct lscpu_cxt *cxt) { size_t i; diff --git a/sys-utils/lscpu.c b/sys-utils/lscpu.c index 8829098aa..47dd9d72f 100644 --- a/sys-utils/lscpu.c +++ b/sys-utils/lscpu.c @@ -105,6 +105,7 @@ enum { COL_CPU_CONFIGURED, COL_CPU_ONLINE, COL_CPU_MHZ, + COL_CPU_SCALMHZ, COL_CPU_MAXMHZ, COL_CPU_MINMHZ, }; @@ -150,6 +151,7 @@ static struct lscpu_coldesc coldescs_cpu[] = [COL_CPU_CONFIGURED] = { "CONFIGURED", N_("shows if the hypervisor has allocated the CPU") }, [COL_CPU_ONLINE] = { "ONLINE", N_("shows if Linux currently makes use of the CPU"), SCOLS_FL_RIGHT }, [COL_CPU_MHZ] = { "MHZ", N_("shows the currently MHz of the CPU"), SCOLS_FL_RIGHT }, + [COL_CPU_SCALMHZ] = { "SCALMHZ%", N_("shows scaling percentage of the CPU frequency"), SCOLS_FL_RIGHT }, [COL_CPU_MAXMHZ] = { "MAXMHZ", N_("shows the maximum MHz of the CPU"), SCOLS_FL_RIGHT }, [COL_CPU_MINMHZ] = { "MINMHZ", N_("shows the minimum MHz of the CPU"), SCOLS_FL_RIGHT } }; @@ -425,6 +427,10 @@ static char *get_cell_data( if (cpu->mhz) xstrncpy(buf, cpu->mhz, bufsz); break; + case COL_CPU_SCALMHZ: + if (cpu->mhz_cur_freq && cpu->mhz_max_freq) + snprintf(buf, bufsz, "%.0f%%", cpu->mhz_cur_freq / cpu->mhz_max_freq * 100); + break; case COL_CPU_MAXMHZ: if (cpu->mhz_max_freq) snprintf(buf, bufsz, "%.4f", cpu->mhz_max_freq); @@ -890,6 +896,9 @@ print_summary_cputype(struct lscpu_cxt *cxt, add_summary_s(tb, sec, _("CPU static MHz:"), ct->static_mhz); if (ct->has_freq) { + float scal = lsblk_cputype_get_scalmhz(cxt, ct); + if (scal > 0.0) + add_summary_x(tb, sec, _("CPU(s) scaling MHz:"), "%.0f%%", scal); add_summary_x(tb, sec, _("CPU max MHz:"), "%.4f", lsblk_cputype_get_maxmhz(cxt, ct)); add_summary_x(tb, sec, _("CPU min MHz:"), "%.4f", lsblk_cputype_get_minmhz(cxt, ct)); } diff --git a/sys-utils/lscpu.h b/sys-utils/lscpu.h index e52c77c22..62f532581 100644 --- a/sys-utils/lscpu.h +++ b/sys-utils/lscpu.h @@ -127,11 +127,12 @@ struct lscpu_cpu { int logical_id; char *bogomips; /* per-CPU bogomips */ - char *mhz; /* max freq from cpuinfo */ + char *mhz; /* freq from cpuinfo */ char *dynamic_mhz; /* from cpuinf for s390 */ char *static_mhz; /* from cpuinf for s390 */ float mhz_max_freq; /* realtime freq from /sys/.../cpuinfo_max_freq */ float mhz_min_freq; /* realtime freq from /sys/.../cpuinfo_min_freq */ + float mhz_cur_freq; int coreid; int socketid; @@ -280,6 +281,7 @@ void lscpu_cputype_free_topology(struct lscpu_cputype *ct); float lsblk_cputype_get_maxmhz(struct lscpu_cxt *cxt, struct lscpu_cputype *ct); float lsblk_cputype_get_minmhz(struct lscpu_cxt *cxt, struct lscpu_cputype *ct); +float lsblk_cputype_get_scalmhz(struct lscpu_cxt *cxt, struct lscpu_cputype *ct); struct lscpu_arch *lscpu_read_architecture(struct lscpu_cxt *cxt); void lscpu_free_architecture(struct lscpu_arch *ar); -- 2.43.0