Merge branches 'pm-opp' and 'pm-tools'
Merge OPP (operating performance points) and tooling updates for 6.11-rc1: - Fix missing cleanup on error in _opp_attach_genpd() (Viresh Kumar). - Introduce an OF helper function to inform if required-opps is used and drop a redundant in-parameter to _set_opp_level() (Ulf Hansson). - Update pm-graph to v5.12 which includes fixes and major code revamp for python3.12 (Todd Brandt). - Address several assorted issues in the cpupower utility (Roman Storozhenko). * pm-opp: OPP: Introduce an OF helper function to inform if required-opps is used OPP: Drop a redundant in-parameter to _set_opp_level() OPP: Fix missing cleanup on error in _opp_attach_genpd() * pm-tools: cpupower: fix lib default installation path cpupower: Disable direct build of the 'bench' subproject cpupower: Change the var type of the 'monitor' subcommand display mode cpupower: Remove absent 'v' parameter from monitor man page cpupower: Improve cpupower build process description cpupower: Add 'help' target to the main Makefile cpupower: Replace a dead reference link with working ones pm-graph: v5.12, code revamp for python3.12 pm-graph: v5.12, fixes
This commit is contained in:
commit
a02bed4183
10 changed files with 814 additions and 578 deletions
|
@ -1102,8 +1102,7 @@ static int _set_required_opps(struct device *dev, struct opp_table *opp_table,
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int _set_opp_level(struct device *dev, struct opp_table *opp_table,
|
||||
struct dev_pm_opp *opp)
|
||||
static int _set_opp_level(struct device *dev, struct dev_pm_opp *opp)
|
||||
{
|
||||
unsigned int level = 0;
|
||||
int ret = 0;
|
||||
|
@ -1171,7 +1170,7 @@ static int _disable_opp_table(struct device *dev, struct opp_table *opp_table)
|
|||
if (opp_table->regulators)
|
||||
regulator_disable(opp_table->regulators[0]);
|
||||
|
||||
ret = _set_opp_level(dev, opp_table, NULL);
|
||||
ret = _set_opp_level(dev, NULL);
|
||||
if (ret)
|
||||
goto out;
|
||||
|
||||
|
@ -1220,7 +1219,7 @@ static int _set_opp(struct device *dev, struct opp_table *opp_table,
|
|||
return ret;
|
||||
}
|
||||
|
||||
ret = _set_opp_level(dev, opp_table, opp);
|
||||
ret = _set_opp_level(dev, opp);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
|
@ -1267,7 +1266,7 @@ static int _set_opp(struct device *dev, struct opp_table *opp_table,
|
|||
return ret;
|
||||
}
|
||||
|
||||
ret = _set_opp_level(dev, opp_table, opp);
|
||||
ret = _set_opp_level(dev, opp);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
|
@ -2443,8 +2442,10 @@ static int _opp_attach_genpd(struct opp_table *opp_table, struct device *dev,
|
|||
* Cross check it again and fix if required.
|
||||
*/
|
||||
gdev = dev_to_genpd_dev(virt_dev);
|
||||
if (IS_ERR(gdev))
|
||||
return PTR_ERR(gdev);
|
||||
if (IS_ERR(gdev)) {
|
||||
ret = PTR_ERR(gdev);
|
||||
goto err;
|
||||
}
|
||||
|
||||
genpd_table = _find_opp_table(gdev);
|
||||
if (!IS_ERR(genpd_table)) {
|
||||
|
|
|
@ -1443,6 +1443,38 @@ int of_get_required_opp_performance_state(struct device_node *np, int index)
|
|||
}
|
||||
EXPORT_SYMBOL_GPL(of_get_required_opp_performance_state);
|
||||
|
||||
/**
|
||||
* dev_pm_opp_of_has_required_opp - Find out if a required-opps exists.
|
||||
* @dev: The device to investigate.
|
||||
*
|
||||
* Returns true if the device's node has a "operating-points-v2" property and if
|
||||
* the corresponding node for the opp-table describes opp nodes that uses the
|
||||
* "required-opps" property.
|
||||
*
|
||||
* Return: True if a required-opps is present, else false.
|
||||
*/
|
||||
bool dev_pm_opp_of_has_required_opp(struct device *dev)
|
||||
{
|
||||
struct device_node *opp_np, *np;
|
||||
int count;
|
||||
|
||||
opp_np = _opp_of_get_opp_desc_node(dev->of_node, 0);
|
||||
if (!opp_np)
|
||||
return false;
|
||||
|
||||
np = of_get_next_available_child(opp_np, NULL);
|
||||
of_node_put(opp_np);
|
||||
if (!np) {
|
||||
dev_warn(dev, "Empty OPP table\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
count = of_count_phandle_with_args(np, "required-opps", NULL);
|
||||
of_node_put(np);
|
||||
|
||||
return count > 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* dev_pm_opp_get_of_node() - Gets the DT node corresponding to an opp
|
||||
* @opp: opp for which DT node has to be returned for
|
||||
|
|
|
@ -474,6 +474,7 @@ int dev_pm_opp_of_get_sharing_cpus(struct device *cpu_dev, struct cpumask *cpuma
|
|||
struct device_node *dev_pm_opp_of_get_opp_desc_node(struct device *dev);
|
||||
struct device_node *dev_pm_opp_get_of_node(struct dev_pm_opp *opp);
|
||||
int of_get_required_opp_performance_state(struct device_node *np, int index);
|
||||
bool dev_pm_opp_of_has_required_opp(struct device *dev);
|
||||
int dev_pm_opp_of_find_icc_paths(struct device *dev, struct opp_table *opp_table);
|
||||
int dev_pm_opp_of_register_em(struct device *dev, struct cpumask *cpus);
|
||||
int dev_pm_opp_calc_power(struct device *dev, unsigned long *uW,
|
||||
|
@ -552,6 +553,11 @@ static inline int of_get_required_opp_performance_state(struct device_node *np,
|
|||
return -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
static inline bool dev_pm_opp_of_has_required_opp(struct device *dev)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
static inline int dev_pm_opp_of_find_icc_paths(struct device *dev, struct opp_table *opp_table)
|
||||
{
|
||||
return -EOPNOTSUPP;
|
||||
|
|
|
@ -67,6 +67,7 @@ LANGUAGES = de fr it cs pt ka
|
|||
bindir ?= /usr/bin
|
||||
sbindir ?= /usr/sbin
|
||||
mandir ?= /usr/man
|
||||
libdir ?= /usr/lib
|
||||
includedir ?= /usr/include
|
||||
localedir ?= /usr/share/locale
|
||||
docdir ?= /usr/share/doc/packages/cpupower
|
||||
|
@ -94,15 +95,6 @@ RANLIB = $(CROSS)ranlib
|
|||
HOSTCC = gcc
|
||||
MKDIR = mkdir
|
||||
|
||||
# 64bit library detection
|
||||
include ../../scripts/Makefile.arch
|
||||
|
||||
ifeq ($(IS_64_BIT), 1)
|
||||
libdir ?= /usr/lib64
|
||||
else
|
||||
libdir ?= /usr/lib
|
||||
endif
|
||||
|
||||
# Now we set up the build system
|
||||
#
|
||||
|
||||
|
@ -332,4 +324,39 @@ uninstall:
|
|||
rm -f $(DESTDIR)${localedir}/$$HLANG/LC_MESSAGES/cpupower.mo; \
|
||||
done;
|
||||
|
||||
.PHONY: all utils libcpupower update-po create-gmo install-lib install-tools install-man install-gmo install uninstall clean
|
||||
help:
|
||||
@echo 'Building targets:'
|
||||
@echo ' all - Default target. Could be omitted. Put build artifacts'
|
||||
@echo ' to "O" cmdline option dir (default: current dir)'
|
||||
@echo ' install - Install previously built project files from the output'
|
||||
@echo ' dir defined by "O" cmdline option (default: current dir)'
|
||||
@echo ' to the install dir defined by "DESTDIR" cmdline or'
|
||||
@echo ' Makefile config block option (default: "")'
|
||||
@echo ' install-lib - Install previously built library binary from the output'
|
||||
@echo ' dir defined by "O" cmdline option (default: current dir)'
|
||||
@echo ' and library headers from "lib/" for userspace to the install'
|
||||
@echo ' dir defined by "DESTDIR" cmdline (default: "")'
|
||||
@echo ' install-tools - Install previously built "cpupower" util from the output'
|
||||
@echo ' dir defined by "O" cmdline option (default: current dir) and'
|
||||
@echo ' "cpupower-completion.sh" script from the src dir to the'
|
||||
@echo ' install dir defined by "DESTDIR" cmdline or Makefile'
|
||||
@echo ' config block option (default: "")'
|
||||
@echo ' install-man - Install man pages from the "man" src subdir to the'
|
||||
@echo ' install dir defined by "DESTDIR" cmdline or Makefile'
|
||||
@echo ' config block option (default: "")'
|
||||
@echo ' install-gmo - Install previously built language files from the output'
|
||||
@echo ' dir defined by "O" cmdline option (default: current dir)'
|
||||
@echo ' to the install dir defined by "DESTDIR" cmdline or Makefile'
|
||||
@echo ' config block option (default: "")'
|
||||
@echo ' install-bench - Install previously built "cpufreq-bench" util files from the'
|
||||
@echo ' output dir defined by "O" cmdline option (default: current dir)'
|
||||
@echo ' to the install dir defined by "DESTDIR" cmdline or Makefile'
|
||||
@echo ' config block option (default: "")'
|
||||
@echo ''
|
||||
@echo 'Cleaning targets:'
|
||||
@echo ' clean - Clean build artifacts from the dir defined by "O" cmdline'
|
||||
@echo ' option (default: current dir)'
|
||||
@echo ' uninstall - Remove previously installed files from the dir defined by "DESTDIR"'
|
||||
@echo ' cmdline or Makefile config block option (default: "")'
|
||||
|
||||
.PHONY: all utils libcpupower update-po create-gmo install-lib install-tools install-man install-gmo install uninstall clean help
|
||||
|
|
|
@ -22,16 +22,156 @@ interfaces [depending on configuration, see below].
|
|||
compilation and installation
|
||||
----------------------------
|
||||
|
||||
make
|
||||
su
|
||||
make install
|
||||
There are 2 output directories - one for the build output and another for
|
||||
the installation of the build results, that is the utility, library,
|
||||
man pages, etc...
|
||||
|
||||
should suffice on most systems. It builds libcpupower to put in
|
||||
/usr/lib; cpupower, cpufreq-bench_plot.sh to put in /usr/bin; and
|
||||
cpufreq-bench to put in /usr/sbin. If you want to set up the paths
|
||||
differently and/or want to configure the package to your specific
|
||||
needs, you need to open "Makefile" with an editor of your choice and
|
||||
edit the block marked CONFIGURATION.
|
||||
default directory
|
||||
-----------------
|
||||
|
||||
In the case of default directory, build and install process requires no
|
||||
additional parameters:
|
||||
|
||||
build
|
||||
-----
|
||||
|
||||
$ make
|
||||
|
||||
The output directory for the 'make' command is the current directory and
|
||||
its subdirs in the kernel tree:
|
||||
tools/power/cpupower
|
||||
|
||||
install
|
||||
-------
|
||||
|
||||
$ sudo make install
|
||||
|
||||
'make install' command puts targets to default system dirs:
|
||||
|
||||
-----------------------------------------------------------------------
|
||||
| Installing file | System dir |
|
||||
-----------------------------------------------------------------------
|
||||
| libcpupower | /usr/lib |
|
||||
-----------------------------------------------------------------------
|
||||
| cpupower | /usr/bin |
|
||||
-----------------------------------------------------------------------
|
||||
| cpufreq-bench_plot.sh | /usr/bin |
|
||||
-----------------------------------------------------------------------
|
||||
| man pages | /usr/man |
|
||||
-----------------------------------------------------------------------
|
||||
|
||||
To put it in other words it makes build results available system-wide,
|
||||
enabling any user to simply start using it without any additional steps
|
||||
|
||||
custom directory
|
||||
----------------
|
||||
|
||||
There are 2 make's command-line variables 'O' and 'DESTDIR' that setup
|
||||
appropriate dirs:
|
||||
'O' - build directory
|
||||
'DESTDIR' - installation directory. This variable could also be setup in
|
||||
the 'CONFIGURATION' block of the "Makefile"
|
||||
|
||||
build
|
||||
-----
|
||||
|
||||
$ make O=<your_custom_build_catalog>
|
||||
|
||||
Example:
|
||||
$ make O=/home/hedin/prj/cpupower/build
|
||||
|
||||
install
|
||||
-------
|
||||
|
||||
$ make O=<your_custom_build_catalog> DESTDIR=<your_custom_install_catalog>
|
||||
|
||||
Example:
|
||||
$ make O=/home/hedin/prj/cpupower/build DESTDIR=/home/hedin/prj/cpupower \
|
||||
> install
|
||||
|
||||
Notice that both variables 'O' and 'DESTDIR' have been provided. The reason
|
||||
is that the build results are saved in the custom output dir defined by 'O'
|
||||
variable. So, this dir is the source for the installation step. If only
|
||||
'DESTDIR' were provided then the 'install' target would assume that the
|
||||
build directory is the current one, build everything there and install
|
||||
from the current dir.
|
||||
|
||||
The files will be installed to the following dirs:
|
||||
|
||||
-----------------------------------------------------------------------
|
||||
| Installing file | System dir |
|
||||
-----------------------------------------------------------------------
|
||||
| libcpupower | ${DESTDIR}/usr/lib |
|
||||
-----------------------------------------------------------------------
|
||||
| cpupower | ${DESTDIR}/usr/bin |
|
||||
-----------------------------------------------------------------------
|
||||
| cpufreq-bench_plot.sh | ${DESTDIR}/usr/bin |
|
||||
-----------------------------------------------------------------------
|
||||
| man pages | ${DESTDIR}/usr/man |
|
||||
-----------------------------------------------------------------------
|
||||
|
||||
If you look at the table for the default 'make' output dirs you will
|
||||
notice that the only difference with the non-default case is the
|
||||
${DESTDIR} prefix. So, the structure of the output dirs remains the same
|
||||
regardles of the root output directory.
|
||||
|
||||
|
||||
clean and uninstall
|
||||
-------------------
|
||||
|
||||
'clean' target is intended for cleanup the build catalog from build results
|
||||
'uninstall' target is intended for removing installed files from the
|
||||
installation directory
|
||||
|
||||
default directory
|
||||
-----------------
|
||||
|
||||
This case is a straightforward one:
|
||||
$ make clean
|
||||
$ make uninstall
|
||||
|
||||
custom directory
|
||||
----------------
|
||||
|
||||
Use 'O' command line variable to remove previously built files from the
|
||||
build dir:
|
||||
$ make O=<your_custom_build_catalog> clean
|
||||
|
||||
Example:
|
||||
$ make O=/home/hedin/prj/cpupower/build clean
|
||||
|
||||
Use 'DESTDIR' command line variable to uninstall previously installed files
|
||||
from the given dir:
|
||||
$ make DESTDIR=<your_custom_install_catalog>
|
||||
|
||||
Example:
|
||||
make DESTDIR=/home/hedin/prj/cpupower uninstall
|
||||
|
||||
|
||||
running the tool
|
||||
----------------
|
||||
|
||||
default directory
|
||||
-----------------
|
||||
|
||||
$ sudo cpupower
|
||||
|
||||
custom directory
|
||||
----------------
|
||||
|
||||
When it comes to run the utility from the custom build catalog things
|
||||
become a little bit complicated as 'just run' approach doesn't work.
|
||||
Assuming that the current dir is '<your_custom_install_catalog>/usr',
|
||||
issuing the following command:
|
||||
|
||||
$ sudo ./bin/cpupower
|
||||
will produce the following error output:
|
||||
./bin/cpupower: error while loading shared libraries: libcpupower.so.1:
|
||||
cannot open shared object file: No such file or directory
|
||||
|
||||
The issue is that binary cannot find the 'libcpupower' library. So, we
|
||||
shall point to the lib dir:
|
||||
sudo LD_LIBRARY_PATH=lib64/ ./bin/cpupower
|
||||
|
||||
|
||||
THANKS
|
||||
|
|
|
@ -1,4 +1,9 @@
|
|||
# SPDX-License-Identifier: GPL-2.0
|
||||
ifeq ($(MAKELEVEL),0)
|
||||
$(error This Makefile is not intended to be run standalone, but only as a part \
|
||||
of the main one in the parent dir)
|
||||
endif
|
||||
|
||||
OUTPUT := ./
|
||||
ifeq ("$(origin O)", "command line")
|
||||
ifneq ($(O),)
|
||||
|
|
|
@ -81,11 +81,6 @@ Measure idle and frequency characteristics of an arbitrary command/workload.
|
|||
The executable \fBcommand\fP is forked and upon its exit, statistics gathered since it was
|
||||
forked are displayed.
|
||||
.RE
|
||||
.PP
|
||||
\-v
|
||||
.RS 4
|
||||
Increase verbosity if the binary was compiled with the DEBUG option set.
|
||||
.RE
|
||||
|
||||
.SH MONITOR DESCRIPTIONS
|
||||
.SS "Idle_Stats"
|
||||
|
@ -172,9 +167,11 @@ displayed.
|
|||
"BIOS and Kernel Developer’s Guide (BKDG) for AMD Family 14h Processors"
|
||||
https://support.amd.com/us/Processor_TechDocs/43170.pdf
|
||||
|
||||
"Intel® Turbo Boost Technology
|
||||
in Intel® Core™ Microarchitecture (Nehalem) Based Processors"
|
||||
http://download.intel.com/design/processor/applnots/320354.pdf
|
||||
"What Is Intel® Turbo Boost Technology?"
|
||||
https://www.intel.com/content/www/us/en/gaming/resources/turbo-boost.html
|
||||
|
||||
"Power Management - Technology Overview"
|
||||
https://cdrdv2.intel.com/v1/dl/getContent/637748
|
||||
|
||||
"Intel® 64 and IA-32 Architectures Software Developer's Manual
|
||||
Volume 3B: System Programming Guide"
|
||||
|
|
|
@ -35,7 +35,7 @@ static unsigned int avail_monitors;
|
|||
static char *progname;
|
||||
|
||||
enum operation_mode_e { list = 1, show, show_all };
|
||||
static int mode;
|
||||
static enum operation_mode_e mode;
|
||||
static int interval = 1;
|
||||
static char *show_monitors_param;
|
||||
static struct cpupower_topology cpu_top;
|
||||
|
|
|
@ -77,12 +77,12 @@ class SystemValues(aslib.SystemValues):
|
|||
fp.close()
|
||||
self.testdir = datetime.now().strftime('boot-%y%m%d-%H%M%S')
|
||||
def kernelVersion(self, msg):
|
||||
m = re.match('^[Ll]inux *[Vv]ersion *(?P<v>\S*) .*', msg)
|
||||
m = re.match(r'^[Ll]inux *[Vv]ersion *(?P<v>\S*) .*', msg)
|
||||
if m:
|
||||
return m.group('v')
|
||||
return 'unknown'
|
||||
def checkFtraceKernelVersion(self):
|
||||
m = re.match('^(?P<x>[0-9]*)\.(?P<y>[0-9]*)\.(?P<z>[0-9]*).*', self.kernel)
|
||||
m = re.match(r'^(?P<x>[0-9]*)\.(?P<y>[0-9]*)\.(?P<z>[0-9]*).*', self.kernel)
|
||||
if m:
|
||||
val = tuple(map(int, m.groups()))
|
||||
if val >= (4, 10, 0):
|
||||
|
@ -324,7 +324,7 @@ def parseKernelLog():
|
|||
idx = line.find('[')
|
||||
if idx > 1:
|
||||
line = line[idx:]
|
||||
m = re.match('[ \t]*(\[ *)(?P<ktime>[0-9\.]*)(\]) (?P<msg>.*)', line)
|
||||
m = re.match(r'[ \t]*(\[ *)(?P<ktime>[0-9\.]*)(\]) (?P<msg>.*)', line)
|
||||
if(not m):
|
||||
continue
|
||||
ktime = float(m.group('ktime'))
|
||||
|
@ -332,24 +332,24 @@ def parseKernelLog():
|
|||
break
|
||||
msg = m.group('msg')
|
||||
data.dmesgtext.append(line)
|
||||
if(ktime == 0.0 and re.match('^Linux version .*', msg)):
|
||||
if(ktime == 0.0 and re.match(r'^Linux version .*', msg)):
|
||||
if(not sysvals.stamp['kernel']):
|
||||
sysvals.stamp['kernel'] = sysvals.kernelVersion(msg)
|
||||
continue
|
||||
m = re.match('.* setting system clock to (?P<d>[0-9\-]*)[ A-Z](?P<t>[0-9:]*) UTC.*', msg)
|
||||
m = re.match(r'.* setting system clock to (?P<d>[0-9\-]*)[ A-Z](?P<t>[0-9:]*) UTC.*', msg)
|
||||
if(m):
|
||||
bt = datetime.strptime(m.group('d')+' '+m.group('t'), '%Y-%m-%d %H:%M:%S')
|
||||
bt = bt - timedelta(seconds=int(ktime))
|
||||
data.boottime = bt.strftime('%Y-%m-%d_%H:%M:%S')
|
||||
sysvals.stamp['time'] = bt.strftime('%B %d %Y, %I:%M:%S %p')
|
||||
continue
|
||||
m = re.match('^calling *(?P<f>.*)\+.* @ (?P<p>[0-9]*)', msg)
|
||||
m = re.match(r'^calling *(?P<f>.*)\+.* @ (?P<p>[0-9]*)', msg)
|
||||
if(m):
|
||||
func = m.group('f')
|
||||
pid = int(m.group('p'))
|
||||
devtemp[func] = (ktime, pid)
|
||||
continue
|
||||
m = re.match('^initcall *(?P<f>.*)\+.* returned (?P<r>.*) after (?P<t>.*) usecs', msg)
|
||||
m = re.match(r'^initcall *(?P<f>.*)\+.* returned (?P<r>.*) after (?P<t>.*) usecs', msg)
|
||||
if(m):
|
||||
data.valid = True
|
||||
data.end = ktime
|
||||
|
@ -359,7 +359,7 @@ def parseKernelLog():
|
|||
data.newAction(phase, f, pid, start, ktime, int(r), int(t))
|
||||
del devtemp[f]
|
||||
continue
|
||||
if(re.match('^Freeing unused kernel .*', msg)):
|
||||
if(re.match(r'^Freeing unused kernel .*', msg)):
|
||||
data.tUserMode = ktime
|
||||
data.dmesg['kernel']['end'] = ktime
|
||||
data.dmesg['user']['start'] = ktime
|
||||
|
|
File diff suppressed because it is too large
Load diff
Loading…
Reference in a new issue