PM: EM: Change debugfs configuration to use runtime EM table data
[linux-2.6-block.git] / kernel / power / energy_model.c
index a631d7d52c402fbf11adbf320e15d00cc12e2587..548908e686ed86e943932d3707ff00d62ea6c8b4 100644 (file)
@@ -37,20 +37,65 @@ static bool _is_cpu_device(struct device *dev)
 #ifdef CONFIG_DEBUG_FS
 static struct dentry *rootdir;
 
-static void em_debug_create_ps(struct em_perf_state *ps, struct dentry *pd)
+struct em_dbg_info {
+       struct em_perf_domain *pd;
+       int ps_id;
+};
+
+#define DEFINE_EM_DBG_SHOW(name, fname)                                        \
+static int em_debug_##fname##_show(struct seq_file *s, void *unused)   \
+{                                                                      \
+       struct em_dbg_info *em_dbg = s->private;                        \
+       struct em_perf_state *table;                                    \
+       unsigned long val;                                              \
+                                                                       \
+       rcu_read_lock();                                                \
+       table = em_perf_state_from_pd(em_dbg->pd);                      \
+       val = table[em_dbg->ps_id].name;                                \
+       rcu_read_unlock();                                              \
+                                                                       \
+       seq_printf(s, "%lu\n", val);                                    \
+       return 0;                                                       \
+}                                                                      \
+DEFINE_SHOW_ATTRIBUTE(em_debug_##fname)
+
+DEFINE_EM_DBG_SHOW(frequency, frequency);
+DEFINE_EM_DBG_SHOW(power, power);
+DEFINE_EM_DBG_SHOW(cost, cost);
+DEFINE_EM_DBG_SHOW(performance, performance);
+DEFINE_EM_DBG_SHOW(flags, inefficiency);
+
+static void em_debug_create_ps(struct em_perf_domain *em_pd,
+                              struct em_dbg_info *em_dbg, int i,
+                              struct dentry *pd)
 {
+       struct em_perf_state *table;
+       unsigned long freq;
        struct dentry *d;
        char name[24];
 
-       snprintf(name, sizeof(name), "ps:%lu", ps->frequency);
+       em_dbg[i].pd = em_pd;
+       em_dbg[i].ps_id = i;
+
+       rcu_read_lock();
+       table = em_perf_state_from_pd(em_pd);
+       freq = table[i].frequency;
+       rcu_read_unlock();
+
+       snprintf(name, sizeof(name), "ps:%lu", freq);
 
        /* Create per-ps directory */
        d = debugfs_create_dir(name, pd);
-       debugfs_create_ulong("frequency", 0444, d, &ps->frequency);
-       debugfs_create_ulong("power", 0444, d, &ps->power);
-       debugfs_create_ulong("cost", 0444, d, &ps->cost);
-       debugfs_create_ulong("performance", 0444, d, &ps->performance);
-       debugfs_create_ulong("inefficient", 0444, d, &ps->flags);
+       debugfs_create_file("frequency", 0444, d, &em_dbg[i],
+                           &em_debug_frequency_fops);
+       debugfs_create_file("power", 0444, d, &em_dbg[i],
+                           &em_debug_power_fops);
+       debugfs_create_file("cost", 0444, d, &em_dbg[i],
+                           &em_debug_cost_fops);
+       debugfs_create_file("performance", 0444, d, &em_dbg[i],
+                           &em_debug_performance_fops);
+       debugfs_create_file("inefficient", 0444, d, &em_dbg[i],
+                           &em_debug_inefficiency_fops);
 }
 
 static int em_debug_cpus_show(struct seq_file *s, void *unused)
@@ -73,6 +118,7 @@ DEFINE_SHOW_ATTRIBUTE(em_debug_flags);
 
 static void em_debug_create_pd(struct device *dev)
 {
+       struct em_dbg_info *em_dbg;
        struct dentry *d;
        int i;
 
@@ -86,9 +132,14 @@ static void em_debug_create_pd(struct device *dev)
        debugfs_create_file("flags", 0444, d, dev->em_pd,
                            &em_debug_flags_fops);
 
+       em_dbg = devm_kcalloc(dev, dev->em_pd->nr_perf_states,
+                             sizeof(*em_dbg), GFP_KERNEL);
+       if (!em_dbg)
+               return;
+
        /* Create a sub-directory for each performance state */
        for (i = 0; i < dev->em_pd->nr_perf_states; i++)
-               em_debug_create_ps(&dev->em_pd->table[i], d);
+               em_debug_create_ps(dev->em_pd, em_dbg, i, d);
 
 }