From b5e982a2e60980757d8c462f405cb036e722bf7a Mon Sep 17 00:00:00 2001 From: Finley Xiao Date: Tue, 25 Jul 2017 15:49:17 +0800 Subject: [PATCH] PM / OPP: add a summary tree in debugfs On rk3399-evb-rev3 the opp_summary would for example look something like: device rate(Hz) target(uV) min(uV) max(uV) ------------------------------------------------------------------- platform-dmc 200000000 825000 825000 825000 300000000 850000 850000 850000 400000000 850000 850000 850000 528000000 900000 900000 900000 600000000 900000 900000 900000 800000000 900000 900000 900000 platform-ff9a0000.gpu 200000000 800000 800000 800000 297000000 800000 800000 800000 400000000 825000 825000 825000 500000000 875000 875000 875000 600000000 925000 925000 925000 800000000 1100000 1100000 1100000 cpu4 408000000 800000 800000 800000 600000000 800000 800000 800000 816000000 800000 800000 800000 1008000000 850000 850000 850000 1200000000 875000 875000 875000 1416000000 975000 975000 975000 1608000000 1025000 1025000 1025000 1800000000 1125000 1125000 1125000 cpu0 408000000 800000 800000 800000 600000000 800000 800000 800000 816000000 800000 800000 800000 1008000000 850000 850000 850000 1200000000 925000 925000 925000 1416000000 1050000 1050000 1050000 Change-Id: I0d33bb84fd36d79df3c1630d98c84f1f6bc42728 Signed-off-by: Finley Xiao --- drivers/base/power/opp/core.c | 60 +++++++++++++++++++++++++++++++++++ 1 file changed, 60 insertions(+) diff --git a/drivers/base/power/opp/core.c b/drivers/base/power/opp/core.c index 9d7bec3bbbcf..1cc0d9ab358d 100644 --- a/drivers/base/power/opp/core.c +++ b/drivers/base/power/opp/core.c @@ -2156,3 +2156,63 @@ int dev_pm_opp_of_add_table(struct device *dev) } EXPORT_SYMBOL_GPL(dev_pm_opp_of_add_table); #endif + +#ifdef CONFIG_DEBUG_FS +#include + +static int opp_summary_show(struct seq_file *s, void *data) +{ + struct list_head *lists = (struct list_head *)s->private; + struct opp_table *opp_table; + struct dev_pm_opp *opp; + + mutex_lock(&opp_table_lock); + + seq_puts(s, " device rate(Hz) target(uV) min(uV) max(uV)\n"); + seq_puts(s, "-------------------------------------------------------------------\n"); + + list_for_each_entry_rcu(opp_table, lists, node) { + seq_printf(s, " %s\n", opp_table->dentry_name); + list_for_each_entry(opp, &opp_table->opp_list, node) { + seq_printf(s, "%31lu %12lu %11lu %11lu\n", + opp->rate, + opp->u_volt, + opp->u_volt_min, + opp->u_volt_max); + } + } + + mutex_unlock(&opp_table_lock); + + return 0; +} + +static int opp_summary_open(struct inode *inode, struct file *file) +{ + return single_open(file, opp_summary_show, inode->i_private); +} + +static const struct file_operations opp_summary_fops = { + .open = opp_summary_open, + .read = seq_read, + .llseek = seq_lseek, + .release = single_release, +}; + +static int __init opp_debug_init(void) +{ + struct dentry *parent, *d; + + parent = debugfs_lookup("opp", NULL); + if (!parent) + return -ENOMEM; + + d = debugfs_create_file("opp_summary", 0444, parent, &opp_tables, + &opp_summary_fops); + if (!d) + return -ENOMEM; + + return 0; +} +late_initcall(opp_debug_init); +#endif -- 2.34.1