aboutsummaryrefslogtreecommitdiff
path: root/drivers
diff options
context:
space:
mode:
authorViresh Kumar <viresh.kumar@linaro.org>2012-12-21 12:25:22 +0530
committerJon Medhurst <tixy@linaro.org>2013-04-29 09:43:52 +0100
commit81ac613e2140039350f4224cba73c3935e6ea509 (patch)
tree7c11b3ab91ec7a26ded9f2a065a6aa8a66e9d74e /drivers
parented0ed40aa2c88dd8eef102bc4a466a8a7ca6f346 (diff)
cpufreq: arm_big_little: Remove all platform drivers dependencies
Currently, we need to add entry for any new platform using this driver in compatible list of arm_big_little.c driver. Which is not good. Lets make this driver independent of slave drivers. Now, slave drivers would be calling register routine of arm_big_little.c driver and would pass ops as parameter. Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/cpufreq/arm_big_little.c63
-rw-r--r--drivers/cpufreq/arm_big_little.h11
-rw-r--r--drivers/cpufreq/vexpress_big_little.c21
3 files changed, 49 insertions, 46 deletions
diff --git a/drivers/cpufreq/arm_big_little.c b/drivers/cpufreq/arm_big_little.c
index 5edaba26034..8455ac77153 100644
--- a/drivers/cpufreq/arm_big_little.c
+++ b/drivers/cpufreq/arm_big_little.c
@@ -23,7 +23,6 @@
#include <linux/cpufreq.h>
#include <linux/cpumask.h>
#include <linux/export.h>
-#include <linux/module.h>
#include <linux/of_platform.h>
#include <linux/slab.h>
#include <linux/types.h>
@@ -242,49 +241,47 @@ static struct cpufreq_driver bl_cpufreq_driver = {
.attr = bl_cpufreq_attr,
};
-/* All platforms using this driver must have their entry here */
-static struct of_device_id bl_of_match[] = {
- {
- .compatible = "arm,vexpress,v2p-ca15,tc2",
- .data = vexpress_bl_get_ops
- },
- {},
-};
-
-static int __init bl_cpufreq_modinit(void)
+int bl_cpufreq_register(struct cpufreq_arm_bl_ops *ops)
{
- int i, size = ARRAY_SIZE(bl_of_match);
- struct cpufreq_arm_bl_ops *(*bl_get_ops)(void) = NULL;
-
- for (i = 0; i < size; i++) {
- if (of_machine_is_compatible(bl_of_match[i].compatible)) {
- bl_get_ops = bl_of_match[i].data;
- break;
- }
+ int ret;
+
+ if (arm_bl_ops) {
+ pr_debug("%s: Already registered: %s, exiting\n", __func__,
+ arm_bl_ops->name);
+ return -EBUSY;
}
- if (!bl_get_ops) {
- pr_err("No platform matched, exiting\n");
+ if (!ops || !strlen(ops->name) || !ops->get_freq_tbl) {
+ pr_err("%s: Invalid arm_bl_ops, exiting\n", __func__);
return -ENODEV;
}
- arm_bl_ops = bl_get_ops();
- if (!arm_bl_ops || !arm_bl_ops->get_freq_tbl) {
- pr_err("Invalid ops returned by platform: %s\n",
- bl_of_match[i].compatible);
- return -EINVAL;
+ arm_bl_ops = ops;
+
+ ret = cpufreq_register_driver(&bl_cpufreq_driver);
+ if (ret) {
+ pr_info("%s: Failed registering platform driver: %s, err: %d\n",
+ __func__, ops->name, ret);
+ arm_bl_ops = NULL;
+ } else {
+ pr_info("%s: Registered platform driver: %s\n", __func__,
+ ops->name);
}
- return cpufreq_register_driver(&bl_cpufreq_driver);
+ return ret;
}
-module_init(bl_cpufreq_modinit);
+EXPORT_SYMBOL_GPL(bl_cpufreq_register);
-static void __exit bl_cpufreq_modexit(void)
+void bl_cpufreq_unregister(struct cpufreq_arm_bl_ops *ops)
{
+ if (arm_bl_ops != ops) {
+ pr_info("%s: Registered with: %s, can't unregister, exiting\n",
+ __func__, arm_bl_ops->name);
+ }
+
cpufreq_unregister_driver(&bl_cpufreq_driver);
+ pr_info("%s: Un-registered platform driver: %s\n", __func__,
+ arm_bl_ops->name);
arm_bl_ops = NULL;
}
-module_exit(bl_cpufreq_modexit);
-
-MODULE_DESCRIPTION("ARM big LITTLE platforms cpufreq driver");
-MODULE_LICENSE("GPL");
+EXPORT_SYMBOL_GPL(bl_cpufreq_unregister);
diff --git a/drivers/cpufreq/arm_big_little.h b/drivers/cpufreq/arm_big_little.h
index 050aef9c076..5b50fc72abc 100644
--- a/drivers/cpufreq/arm_big_little.h
+++ b/drivers/cpufreq/arm_big_little.h
@@ -23,6 +23,7 @@
#include <linux/types.h>
struct cpufreq_arm_bl_ops {
+ char name[CPUFREQ_NAME_LEN];
struct cpufreq_frequency_table *(*get_freq_tbl)(u32 cluster, int *count);
void (*put_freq_tbl)(u32 cluster);
};
@@ -31,13 +32,7 @@ struct cpufreq_frequency_table *
arm_bl_copy_table_from_array(unsigned int *table, int count);
void arm_bl_free_freq_table(u32 cluster);
-#if defined(CONFIG_ARM_VEXPRESS_BL_CPUFREQ) || defined(CONFIG_ARM_VEXPRESS_BL_CPUFREQ_MODULE)
-struct cpufreq_arm_bl_ops *vexpress_bl_get_ops(void);
-#else
-static struct cpufreq_arm_bl_ops *vexpress_bl_get_ops(void)
-{
- return NULL;
-}
-#endif
+int bl_cpufreq_register(struct cpufreq_arm_bl_ops *ops);
+void bl_cpufreq_unregister(struct cpufreq_arm_bl_ops *ops);
#endif /* CPUFREQ_ARM_BIG_LITTLE_H */
diff --git a/drivers/cpufreq/vexpress_big_little.c b/drivers/cpufreq/vexpress_big_little.c
index 1b44ae2ad36..81080b1f437 100644
--- a/drivers/cpufreq/vexpress_big_little.c
+++ b/drivers/cpufreq/vexpress_big_little.c
@@ -24,6 +24,7 @@
#include <linux/cpufreq.h>
#include <linux/export.h>
+#include <linux/module.h>
#include <linux/types.h>
#include <linux/vexpress.h>
#include "arm_big_little.h"
@@ -47,17 +48,27 @@ static void vexpress_put_freq_tbl(u32 cluster)
}
static struct cpufreq_arm_bl_ops vexpress_bl_ops = {
+ .name = "vexpress-bl",
.get_freq_tbl = vexpress_get_freq_tbl,
.put_freq_tbl = vexpress_put_freq_tbl,
};
-struct cpufreq_arm_bl_ops *vexpress_bl_get_ops(void)
+static int vexpress_bl_init(void)
{
if (!vexpress_spc_check_loaded()) {
- pr_info("No SPC found\n");
- return NULL;
+ pr_info("%s: No SPC found\n", __func__);
+ return -ENOENT;
}
- return &vexpress_bl_ops;
+ return bl_cpufreq_register(&vexpress_bl_ops);
}
-EXPORT_SYMBOL_GPL(vexpress_bl_get_ops);
+module_init(vexpress_bl_init);
+
+static void vexpress_bl_exit(void)
+{
+ return bl_cpufreq_unregister(&vexpress_bl_ops);
+}
+module_exit(vexpress_bl_exit);
+
+MODULE_DESCRIPTION("ARM Vexpress big LITTLE cpufreq driver");
+MODULE_LICENSE("GPL");