aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/clk/qcom
diff options
context:
space:
mode:
authorStephen Boyd <sboyd@codeaurora.org>2014-03-21 20:59:37 -0400
committerMike Turquette <mturquette@linaro.org>2014-04-30 14:51:51 -0400
commit49fc825f0cc221768c5711b8ec6a71bd49f2663e (patch)
tree4c358a9db39a28e9ba79d77a021a13a59637eefb /drivers/clk/qcom
parent63589e92c2d975cc63222e5bd4a9a1fa2a1187ac (diff)
clk: qcom: Consolidate common probe code
Most of the probe code is the same between all the different clock controllers. Consolidate the code into a common.c file. This makes changes to the common probe parts easier and reduces chances for bugs. Signed-off-by: Stephen Boyd <sboyd@codeaurora.org> Signed-off-by: Mike Turquette <mturquette@linaro.org>
Diffstat (limited to 'drivers/clk/qcom')
-rw-r--r--drivers/clk/qcom/Makefile1
-rw-r--r--drivers/clk/qcom/common.c99
-rw-r--r--drivers/clk/qcom/common.h34
-rw-r--r--drivers/clk/qcom/gcc-msm8660.c87
-rw-r--r--drivers/clk/qcom/gcc-msm8960.c77
-rw-r--r--drivers/clk/qcom/gcc-msm8974.c77
-rw-r--r--drivers/clk/qcom/mmcc-msm8960.c78
-rw-r--r--drivers/clk/qcom/mmcc-msm8974.c80
8 files changed, 196 insertions, 337 deletions
diff --git a/drivers/clk/qcom/Makefile b/drivers/clk/qcom/Makefile
index f60db2ef1aee..689e05bf4f95 100644
--- a/drivers/clk/qcom/Makefile
+++ b/drivers/clk/qcom/Makefile
@@ -1,5 +1,6 @@
1obj-$(CONFIG_COMMON_CLK_QCOM) += clk-qcom.o 1obj-$(CONFIG_COMMON_CLK_QCOM) += clk-qcom.o
2 2
3clk-qcom-y += common.o
3clk-qcom-y += clk-regmap.o 4clk-qcom-y += clk-regmap.o
4clk-qcom-y += clk-pll.o 5clk-qcom-y += clk-pll.o
5clk-qcom-y += clk-rcg.o 6clk-qcom-y += clk-rcg.o
diff --git a/drivers/clk/qcom/common.c b/drivers/clk/qcom/common.c
new file mode 100644
index 000000000000..86b45fba5f90
--- /dev/null
+++ b/drivers/clk/qcom/common.c
@@ -0,0 +1,99 @@
1/*
2 * Copyright (c) 2013-2014, The Linux Foundation. All rights reserved.
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13
14#include <linux/export.h>
15#include <linux/regmap.h>
16#include <linux/platform_device.h>
17#include <linux/clk-provider.h>
18#include <linux/reset-controller.h>
19
20#include "common.h"
21#include "clk-regmap.h"
22#include "reset.h"
23
24struct qcom_cc {
25 struct qcom_reset_controller reset;
26 struct clk_onecell_data data;
27 struct clk *clks[];
28};
29
30int qcom_cc_probe(struct platform_device *pdev, const struct qcom_cc_desc *desc)
31{
32 void __iomem *base;
33 struct resource *res;
34 int i, ret;
35 struct device *dev = &pdev->dev;
36 struct clk *clk;
37 struct clk_onecell_data *data;
38 struct clk **clks;
39 struct regmap *regmap;
40 struct qcom_reset_controller *reset;
41 struct qcom_cc *cc;
42 size_t num_clks = desc->num_clks;
43 struct clk_regmap **rclks = desc->clks;
44
45 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
46 base = devm_ioremap_resource(dev, res);
47 if (IS_ERR(base))
48 return PTR_ERR(base);
49
50 regmap = devm_regmap_init_mmio(dev, base, desc->config);
51 if (IS_ERR(regmap))
52 return PTR_ERR(regmap);
53
54 cc = devm_kzalloc(dev, sizeof(*cc) + sizeof(*clks) * num_clks,
55 GFP_KERNEL);
56 if (!cc)
57 return -ENOMEM;
58
59 clks = cc->clks;
60 data = &cc->data;
61 data->clks = clks;
62 data->clk_num = num_clks;
63
64 for (i = 0; i < num_clks; i++) {
65 if (!rclks[i])
66 continue;
67 clk = devm_clk_register_regmap(dev, rclks[i]);
68 if (IS_ERR(clk))
69 return PTR_ERR(clk);
70 clks[i] = clk;
71 }
72
73 ret = of_clk_add_provider(dev->of_node, of_clk_src_onecell_get, data);
74 if (ret)
75 return ret;
76
77 reset = &cc->reset;
78 reset->rcdev.of_node = dev->of_node;
79 reset->rcdev.ops = &qcom_reset_ops;
80 reset->rcdev.owner = dev->driver->owner;
81 reset->rcdev.nr_resets = desc->num_resets;
82 reset->regmap = regmap;
83 reset->reset_map = desc->resets;
84 platform_set_drvdata(pdev, &reset->rcdev);
85
86 ret = reset_controller_register(&reset->rcdev);
87 if (ret)
88 of_clk_del_provider(dev->of_node);
89
90 return ret;
91}
92EXPORT_SYMBOL_GPL(qcom_cc_probe);
93
94void qcom_cc_remove(struct platform_device *pdev)
95{
96 of_clk_del_provider(pdev->dev.of_node);
97 reset_controller_unregister(platform_get_drvdata(pdev));
98}
99EXPORT_SYMBOL_GPL(qcom_cc_remove);
diff --git a/drivers/clk/qcom/common.h b/drivers/clk/qcom/common.h
new file mode 100644
index 000000000000..2c3cfc860348
--- /dev/null
+++ b/drivers/clk/qcom/common.h
@@ -0,0 +1,34 @@
1/*
2 * Copyright (c) 2014, The Linux Foundation. All rights reserved.
3 *
4 * This software is licensed under the terms of the GNU General Public
5 * License version 2, as published by the Free Software Foundation, and
6 * may be copied, distributed, and modified under those terms.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 */
13#ifndef __QCOM_CLK_COMMON_H__
14#define __QCOM_CLK_COMMON_H__
15
16struct platform_device;
17struct regmap_config;
18struct clk_regmap;
19struct qcom_reset_map;
20
21struct qcom_cc_desc {
22 const struct regmap_config *config;
23 struct clk_regmap **clks;
24 size_t num_clks;
25 const struct qcom_reset_map *resets;
26 size_t num_resets;
27};
28
29extern int qcom_cc_probe(struct platform_device *pdev,
30 const struct qcom_cc_desc *desc);
31
32extern void qcom_cc_remove(struct platform_device *pdev);
33
34#endif
diff --git a/drivers/clk/qcom/gcc-msm8660.c b/drivers/clk/qcom/gcc-msm8660.c
index bc0b7f1fcfbe..44bc6fa64d78 100644
--- a/drivers/clk/qcom/gcc-msm8660.c
+++ b/drivers/clk/qcom/gcc-msm8660.c
@@ -25,6 +25,7 @@
25#include <dt-bindings/clock/qcom,gcc-msm8660.h> 25#include <dt-bindings/clock/qcom,gcc-msm8660.h>
26#include <dt-bindings/reset/qcom,gcc-msm8660.h> 26#include <dt-bindings/reset/qcom,gcc-msm8660.h>
27 27
28#include "common.h"
28#include "clk-regmap.h" 29#include "clk-regmap.h"
29#include "clk-pll.h" 30#include "clk-pll.h"
30#include "clk-rcg.h" 31#include "clk-rcg.h"
@@ -2701,94 +2702,28 @@ static const struct regmap_config gcc_msm8660_regmap_config = {
2701 .fast_io = true, 2702 .fast_io = true,
2702}; 2703};
2703 2704
2705static const struct qcom_cc_desc gcc_msm8660_desc = {
2706 .config = &gcc_msm8660_regmap_config,
2707 .clks = gcc_msm8660_clks,
2708 .num_clks = ARRAY_SIZE(gcc_msm8660_clks),
2709 .resets = gcc_msm8660_resets,
2710 .num_resets = ARRAY_SIZE(gcc_msm8660_resets),
2711};
2712
2704static const struct of_device_id gcc_msm8660_match_table[] = { 2713static const struct of_device_id gcc_msm8660_match_table[] = {
2705 { .compatible = "qcom,gcc-msm8660" }, 2714 { .compatible = "qcom,gcc-msm8660" },
2706 { } 2715 { }
2707}; 2716};
2708MODULE_DEVICE_TABLE(of, gcc_msm8660_match_table); 2717MODULE_DEVICE_TABLE(of, gcc_msm8660_match_table);
2709 2718
2710struct qcom_cc {
2711 struct qcom_reset_controller reset;
2712 struct clk_onecell_data data;
2713 struct clk *clks[];
2714};
2715
2716static int gcc_msm8660_probe(struct platform_device *pdev) 2719static int gcc_msm8660_probe(struct platform_device *pdev)
2717{ 2720{
2718 void __iomem *base; 2721 return qcom_cc_probe(pdev, &gcc_msm8660_desc);
2719 struct resource *res;
2720 int i, ret;
2721 struct device *dev = &pdev->dev;
2722 struct clk *clk;
2723 struct clk_onecell_data *data;
2724 struct clk **clks;
2725 struct regmap *regmap;
2726 size_t num_clks;
2727 struct qcom_reset_controller *reset;
2728 struct qcom_cc *cc;
2729
2730 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
2731 base = devm_ioremap_resource(dev, res);
2732 if (IS_ERR(base))
2733 return PTR_ERR(base);
2734
2735 regmap = devm_regmap_init_mmio(dev, base, &gcc_msm8660_regmap_config);
2736 if (IS_ERR(regmap))
2737 return PTR_ERR(regmap);
2738
2739 num_clks = ARRAY_SIZE(gcc_msm8660_clks);
2740 cc = devm_kzalloc(dev, sizeof(*cc) + sizeof(*clks) * num_clks,
2741 GFP_KERNEL);
2742 if (!cc)
2743 return -ENOMEM;
2744
2745 clks = cc->clks;
2746 data = &cc->data;
2747 data->clks = clks;
2748 data->clk_num = num_clks;
2749
2750 /* Temporary until RPM clocks supported */
2751 clk = clk_register_fixed_rate(dev, "cxo", NULL, CLK_IS_ROOT, 19200000);
2752 if (IS_ERR(clk))
2753 return PTR_ERR(clk);
2754
2755 clk = clk_register_fixed_rate(dev, "pxo", NULL, CLK_IS_ROOT, 27000000);
2756 if (IS_ERR(clk))
2757 return PTR_ERR(clk);
2758
2759 for (i = 0; i < num_clks; i++) {
2760 if (!gcc_msm8660_clks[i])
2761 continue;
2762 clk = devm_clk_register_regmap(dev, gcc_msm8660_clks[i]);
2763 if (IS_ERR(clk))
2764 return PTR_ERR(clk);
2765 clks[i] = clk;
2766 }
2767
2768 ret = of_clk_add_provider(dev->of_node, of_clk_src_onecell_get, data);
2769 if (ret)
2770 return ret;
2771
2772 reset = &cc->reset;
2773 reset->rcdev.of_node = dev->of_node;
2774 reset->rcdev.ops = &qcom_reset_ops,
2775 reset->rcdev.owner = THIS_MODULE,
2776 reset->rcdev.nr_resets = ARRAY_SIZE(gcc_msm8660_resets),
2777 reset->regmap = regmap;
2778 reset->reset_map = gcc_msm8660_resets,
2779 platform_set_drvdata(pdev, &reset->rcdev);
2780
2781 ret = reset_controller_register(&reset->rcdev);
2782 if (ret)
2783 of_clk_del_provider(dev->of_node);
2784
2785 return ret;
2786} 2722}
2787 2723
2788static int gcc_msm8660_remove(struct platform_device *pdev) 2724static int gcc_msm8660_remove(struct platform_device *pdev)
2789{ 2725{
2790 of_clk_del_provider(pdev->dev.of_node); 2726 qcom_cc_remove(pdev);
2791 reset_controller_unregister(platform_get_drvdata(pdev));
2792 return 0; 2727 return 0;
2793} 2728}
2794 2729
diff --git a/drivers/clk/qcom/gcc-msm8960.c b/drivers/clk/qcom/gcc-msm8960.c
index fd446ab2fd98..633b019891bb 100644
--- a/drivers/clk/qcom/gcc-msm8960.c
+++ b/drivers/clk/qcom/gcc-msm8960.c
@@ -25,6 +25,7 @@
25#include <dt-bindings/clock/qcom,gcc-msm8960.h> 25#include <dt-bindings/clock/qcom,gcc-msm8960.h>
26#include <dt-bindings/reset/qcom,gcc-msm8960.h> 26#include <dt-bindings/reset/qcom,gcc-msm8960.h>
27 27
28#include "common.h"
28#include "clk-regmap.h" 29#include "clk-regmap.h"
29#include "clk-pll.h" 30#include "clk-pll.h"
30#include "clk-rcg.h" 31#include "clk-rcg.h"
@@ -2875,51 +2876,24 @@ static const struct regmap_config gcc_msm8960_regmap_config = {
2875 .fast_io = true, 2876 .fast_io = true,
2876}; 2877};
2877 2878
2879static const struct qcom_cc_desc gcc_msm8960_desc = {
2880 .config = &gcc_msm8960_regmap_config,
2881 .clks = gcc_msm8960_clks,
2882 .num_clks = ARRAY_SIZE(gcc_msm8960_clks),
2883 .resets = gcc_msm8960_resets,
2884 .num_resets = ARRAY_SIZE(gcc_msm8960_resets),
2885};
2886
2878static const struct of_device_id gcc_msm8960_match_table[] = { 2887static const struct of_device_id gcc_msm8960_match_table[] = {
2879 { .compatible = "qcom,gcc-msm8960" }, 2888 { .compatible = "qcom,gcc-msm8960" },
2880 { } 2889 { }
2881}; 2890};
2882MODULE_DEVICE_TABLE(of, gcc_msm8960_match_table); 2891MODULE_DEVICE_TABLE(of, gcc_msm8960_match_table);
2883 2892
2884struct qcom_cc {
2885 struct qcom_reset_controller reset;
2886 struct clk_onecell_data data;
2887 struct clk *clks[];
2888};
2889
2890static int gcc_msm8960_probe(struct platform_device *pdev) 2893static int gcc_msm8960_probe(struct platform_device *pdev)
2891{ 2894{
2892 void __iomem *base;
2893 struct resource *res;
2894 int i, ret;
2895 struct device *dev = &pdev->dev;
2896 struct clk *clk; 2895 struct clk *clk;
2897 struct clk_onecell_data *data; 2896 struct device *dev = &pdev->dev;
2898 struct clk **clks;
2899 struct regmap *regmap;
2900 size_t num_clks;
2901 struct qcom_reset_controller *reset;
2902 struct qcom_cc *cc;
2903
2904 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
2905 base = devm_ioremap_resource(dev, res);
2906 if (IS_ERR(base))
2907 return PTR_ERR(base);
2908
2909 regmap = devm_regmap_init_mmio(dev, base, &gcc_msm8960_regmap_config);
2910 if (IS_ERR(regmap))
2911 return PTR_ERR(regmap);
2912
2913 num_clks = ARRAY_SIZE(gcc_msm8960_clks);
2914 cc = devm_kzalloc(dev, sizeof(*cc) + sizeof(*clks) * num_clks,
2915 GFP_KERNEL);
2916 if (!cc)
2917 return -ENOMEM;
2918
2919 clks = cc->clks;
2920 data = &cc->data;
2921 data->clks = clks;
2922 data->clk_num = num_clks;
2923 2897
2924 /* Temporary until RPM clocks supported */ 2898 /* Temporary until RPM clocks supported */
2925 clk = clk_register_fixed_rate(dev, "cxo", NULL, CLK_IS_ROOT, 19200000); 2899 clk = clk_register_fixed_rate(dev, "cxo", NULL, CLK_IS_ROOT, 19200000);
@@ -2930,39 +2904,12 @@ static int gcc_msm8960_probe(struct platform_device *pdev)
2930 if (IS_ERR(clk)) 2904 if (IS_ERR(clk))
2931 return PTR_ERR(clk); 2905 return PTR_ERR(clk);
2932 2906
2933 for (i = 0; i < num_clks; i++) { 2907 return qcom_cc_probe(pdev, &gcc_msm8960_desc);
2934 if (!gcc_msm8960_clks[i])
2935 continue;
2936 clk = devm_clk_register_regmap(dev, gcc_msm8960_clks[i]);
2937 if (IS_ERR(clk))
2938 return PTR_ERR(clk);
2939 clks[i] = clk;
2940 }
2941
2942 ret = of_clk_add_provider(dev->of_node, of_clk_src_onecell_get, data);
2943 if (ret)
2944 return ret;
2945
2946 reset = &cc->reset;
2947 reset->rcdev.of_node = dev->of_node;
2948 reset->rcdev.ops = &qcom_reset_ops,
2949 reset->rcdev.owner = THIS_MODULE,
2950 reset->rcdev.nr_resets = ARRAY_SIZE(gcc_msm8960_resets),
2951 reset->regmap = regmap;
2952 reset->reset_map = gcc_msm8960_resets,
2953 platform_set_drvdata(pdev, &reset->rcdev);
2954
2955 ret = reset_controller_register(&reset->rcdev);
2956 if (ret)
2957 of_clk_del_provider(dev->of_node);
2958
2959 return ret;
2960} 2908}
2961 2909
2962static int gcc_msm8960_remove(struct platform_device *pdev) 2910static int gcc_msm8960_remove(struct platform_device *pdev)
2963{ 2911{
2964 of_clk_del_provider(pdev->dev.of_node); 2912 qcom_cc_remove(pdev);
2965 reset_controller_unregister(platform_get_drvdata(pdev));
2966 return 0; 2913 return 0;
2967} 2914}
2968 2915
diff --git a/drivers/clk/qcom/gcc-msm8974.c b/drivers/clk/qcom/gcc-msm8974.c
index 51d457e2b959..0d1edc1e9b31 100644
--- a/drivers/clk/qcom/gcc-msm8974.c
+++ b/drivers/clk/qcom/gcc-msm8974.c
@@ -25,6 +25,7 @@
25#include <dt-bindings/clock/qcom,gcc-msm8974.h> 25#include <dt-bindings/clock/qcom,gcc-msm8974.h>
26#include <dt-bindings/reset/qcom,gcc-msm8974.h> 26#include <dt-bindings/reset/qcom,gcc-msm8974.h>
27 27
28#include "common.h"
28#include "clk-regmap.h" 29#include "clk-regmap.h"
29#include "clk-pll.h" 30#include "clk-pll.h"
30#include "clk-rcg.h" 31#include "clk-rcg.h"
@@ -2574,51 +2575,24 @@ static const struct regmap_config gcc_msm8974_regmap_config = {
2574 .fast_io = true, 2575 .fast_io = true,
2575}; 2576};
2576 2577
2578static const struct qcom_cc_desc gcc_msm8974_desc = {
2579 .config = &gcc_msm8974_regmap_config,
2580 .clks = gcc_msm8974_clocks,
2581 .num_clks = ARRAY_SIZE(gcc_msm8974_clocks),
2582 .resets = gcc_msm8974_resets,
2583 .num_resets = ARRAY_SIZE(gcc_msm8974_resets),
2584};
2585
2577static const struct of_device_id gcc_msm8974_match_table[] = { 2586static const struct of_device_id gcc_msm8974_match_table[] = {
2578 { .compatible = "qcom,gcc-msm8974" }, 2587 { .compatible = "qcom,gcc-msm8974" },
2579 { } 2588 { }
2580}; 2589};
2581MODULE_DEVICE_TABLE(of, gcc_msm8974_match_table); 2590MODULE_DEVICE_TABLE(of, gcc_msm8974_match_table);
2582 2591
2583struct qcom_cc {
2584 struct qcom_reset_controller reset;
2585 struct clk_onecell_data data;
2586 struct clk *clks[];
2587};
2588
2589static int gcc_msm8974_probe(struct platform_device *pdev) 2592static int gcc_msm8974_probe(struct platform_device *pdev)
2590{ 2593{
2591 void __iomem *base;
2592 struct resource *res;
2593 int i, ret;
2594 struct device *dev = &pdev->dev;
2595 struct clk *clk; 2594 struct clk *clk;
2596 struct clk_onecell_data *data; 2595 struct device *dev = &pdev->dev;
2597 struct clk **clks;
2598 struct regmap *regmap;
2599 size_t num_clks;
2600 struct qcom_reset_controller *reset;
2601 struct qcom_cc *cc;
2602
2603 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
2604 base = devm_ioremap_resource(dev, res);
2605 if (IS_ERR(base))
2606 return PTR_ERR(base);
2607
2608 regmap = devm_regmap_init_mmio(dev, base, &gcc_msm8974_regmap_config);
2609 if (IS_ERR(regmap))
2610 return PTR_ERR(regmap);
2611
2612 num_clks = ARRAY_SIZE(gcc_msm8974_clocks);
2613 cc = devm_kzalloc(dev, sizeof(*cc) + sizeof(*clks) * num_clks,
2614 GFP_KERNEL);
2615 if (!cc)
2616 return -ENOMEM;
2617
2618 clks = cc->clks;
2619 data = &cc->data;
2620 data->clks = clks;
2621 data->clk_num = num_clks;
2622 2596
2623 /* Temporary until RPM clocks supported */ 2597 /* Temporary until RPM clocks supported */
2624 clk = clk_register_fixed_rate(dev, "xo", NULL, CLK_IS_ROOT, 19200000); 2598 clk = clk_register_fixed_rate(dev, "xo", NULL, CLK_IS_ROOT, 19200000);
@@ -2631,39 +2605,12 @@ static int gcc_msm8974_probe(struct platform_device *pdev)
2631 if (IS_ERR(clk)) 2605 if (IS_ERR(clk))
2632 return PTR_ERR(clk); 2606 return PTR_ERR(clk);
2633 2607
2634 for (i = 0; i < num_clks; i++) { 2608 return qcom_cc_probe(pdev, &gcc_msm8974_desc);
2635 if (!gcc_msm8974_clocks[i])
2636 continue;
2637 clk = devm_clk_register_regmap(dev, gcc_msm8974_clocks[i]);
2638 if (IS_ERR(clk))
2639 return PTR_ERR(clk);
2640 clks[i] = clk;
2641 }
2642
2643 ret = of_clk_add_provider(dev->of_node, of_clk_src_onecell_get, data);
2644 if (ret)
2645 return ret;
2646
2647 reset = &cc->reset;
2648 reset->rcdev.of_node = dev->of_node;
2649 reset->rcdev.ops = &qcom_reset_ops,
2650 reset->rcdev.owner = THIS_MODULE,
2651 reset->rcdev.nr_resets = ARRAY_SIZE(gcc_msm8974_resets),
2652 reset->regmap = regmap;
2653 reset->reset_map = gcc_msm8974_resets,
2654 platform_set_drvdata(pdev, &reset->rcdev);
2655
2656 ret = reset_controller_register(&reset->rcdev);
2657 if (ret)
2658 of_clk_del_provider(dev->of_node);
2659
2660 return ret;
2661} 2609}
2662 2610
2663static int gcc_msm8974_remove(struct platform_device *pdev) 2611static int gcc_msm8974_remove(struct platform_device *pdev)
2664{ 2612{
2665 of_clk_del_provider(pdev->dev.of_node); 2613 qcom_cc_remove(pdev);
2666 reset_controller_unregister(platform_get_drvdata(pdev));
2667 return 0; 2614 return 0;
2668} 2615}
2669 2616
diff --git a/drivers/clk/qcom/mmcc-msm8960.c b/drivers/clk/qcom/mmcc-msm8960.c
index f9b59c7e48e9..12f3c0b64fcd 100644
--- a/drivers/clk/qcom/mmcc-msm8960.c
+++ b/drivers/clk/qcom/mmcc-msm8960.c
@@ -26,6 +26,7 @@
26#include <dt-bindings/clock/qcom,mmcc-msm8960.h> 26#include <dt-bindings/clock/qcom,mmcc-msm8960.h>
27#include <dt-bindings/reset/qcom,mmcc-msm8960.h> 27#include <dt-bindings/reset/qcom,mmcc-msm8960.h>
28 28
29#include "common.h"
29#include "clk-regmap.h" 30#include "clk-regmap.h"
30#include "clk-pll.h" 31#include "clk-pll.h"
31#include "clk-rcg.h" 32#include "clk-rcg.h"
@@ -2222,85 +2223,28 @@ static const struct regmap_config mmcc_msm8960_regmap_config = {
2222 .fast_io = true, 2223 .fast_io = true,
2223}; 2224};
2224 2225
2226static const struct qcom_cc_desc mmcc_msm8960_desc = {
2227 .config = &mmcc_msm8960_regmap_config,
2228 .clks = mmcc_msm8960_clks,
2229 .num_clks = ARRAY_SIZE(mmcc_msm8960_clks),
2230 .resets = mmcc_msm8960_resets,
2231 .num_resets = ARRAY_SIZE(mmcc_msm8960_resets),
2232};
2233
2225static const struct of_device_id mmcc_msm8960_match_table[] = { 2234static const struct of_device_id mmcc_msm8960_match_table[] = {
2226 { .compatible = "qcom,mmcc-msm8960" }, 2235 { .compatible = "qcom,mmcc-msm8960" },
2227 { } 2236 { }
2228}; 2237};
2229MODULE_DEVICE_TABLE(of, mmcc_msm8960_match_table); 2238MODULE_DEVICE_TABLE(of, mmcc_msm8960_match_table);
2230 2239
2231struct qcom_cc {
2232 struct qcom_reset_controller reset;
2233 struct clk_onecell_data data;
2234 struct clk *clks[];
2235};
2236
2237static int mmcc_msm8960_probe(struct platform_device *pdev) 2240static int mmcc_msm8960_probe(struct platform_device *pdev)
2238{ 2241{
2239 void __iomem *base; 2242 return qcom_cc_probe(pdev, &mmcc_msm8960_desc);
2240 struct resource *res;
2241 int i, ret;
2242 struct device *dev = &pdev->dev;
2243 struct clk *clk;
2244 struct clk_onecell_data *data;
2245 struct clk **clks;
2246 struct regmap *regmap;
2247 size_t num_clks;
2248 struct qcom_reset_controller *reset;
2249 struct qcom_cc *cc;
2250
2251 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
2252 base = devm_ioremap_resource(dev, res);
2253 if (IS_ERR(base))
2254 return PTR_ERR(base);
2255
2256 regmap = devm_regmap_init_mmio(dev, base, &mmcc_msm8960_regmap_config);
2257 if (IS_ERR(regmap))
2258 return PTR_ERR(regmap);
2259
2260 num_clks = ARRAY_SIZE(mmcc_msm8960_clks);
2261 cc = devm_kzalloc(dev, sizeof(*cc) + sizeof(*clks) * num_clks,
2262 GFP_KERNEL);
2263 if (!cc)
2264 return -ENOMEM;
2265
2266 clks = cc->clks;
2267 data = &cc->data;
2268 data->clks = clks;
2269 data->clk_num = num_clks;
2270
2271 for (i = 0; i < num_clks; i++) {
2272 if (!mmcc_msm8960_clks[i])
2273 continue;
2274 clk = devm_clk_register_regmap(dev, mmcc_msm8960_clks[i]);
2275 if (IS_ERR(clk))
2276 return PTR_ERR(clk);
2277 clks[i] = clk;
2278 }
2279
2280 ret = of_clk_add_provider(dev->of_node, of_clk_src_onecell_get, data);
2281 if (ret)
2282 return ret;
2283
2284 reset = &cc->reset;
2285 reset->rcdev.of_node = dev->of_node;
2286 reset->rcdev.ops = &qcom_reset_ops,
2287 reset->rcdev.owner = THIS_MODULE,
2288 reset->rcdev.nr_resets = ARRAY_SIZE(mmcc_msm8960_resets),
2289 reset->regmap = regmap;
2290 reset->reset_map = mmcc_msm8960_resets,
2291 platform_set_drvdata(pdev, &reset->rcdev);
2292
2293 ret = reset_controller_register(&reset->rcdev);
2294 if (ret)
2295 of_clk_del_provider(dev->of_node);
2296
2297 return ret;
2298} 2243}
2299 2244
2300static int mmcc_msm8960_remove(struct platform_device *pdev) 2245static int mmcc_msm8960_remove(struct platform_device *pdev)
2301{ 2246{
2302 of_clk_del_provider(pdev->dev.of_node); 2247 qcom_cc_remove(pdev);
2303 reset_controller_unregister(platform_get_drvdata(pdev));
2304 return 0; 2248 return 0;
2305} 2249}
2306 2250
diff --git a/drivers/clk/qcom/mmcc-msm8974.c b/drivers/clk/qcom/mmcc-msm8974.c
index c95774514b81..60b7c24a5cd6 100644
--- a/drivers/clk/qcom/mmcc-msm8974.c
+++ b/drivers/clk/qcom/mmcc-msm8974.c
@@ -25,6 +25,7 @@
25#include <dt-bindings/clock/qcom,mmcc-msm8974.h> 25#include <dt-bindings/clock/qcom,mmcc-msm8974.h>
26#include <dt-bindings/reset/qcom,mmcc-msm8974.h> 26#include <dt-bindings/reset/qcom,mmcc-msm8974.h>
27 27
28#include "common.h"
28#include "clk-regmap.h" 29#include "clk-regmap.h"
29#include "clk-pll.h" 30#include "clk-pll.h"
30#include "clk-rcg.h" 31#include "clk-rcg.h"
@@ -2524,88 +2525,39 @@ static const struct regmap_config mmcc_msm8974_regmap_config = {
2524 .fast_io = true, 2525 .fast_io = true,
2525}; 2526};
2526 2527
2528static const struct qcom_cc_desc mmcc_msm8974_desc = {
2529 .config = &mmcc_msm8974_regmap_config,
2530 .clks = mmcc_msm8974_clocks,
2531 .num_clks = ARRAY_SIZE(mmcc_msm8974_clocks),
2532 .resets = mmcc_msm8974_resets,
2533 .num_resets = ARRAY_SIZE(mmcc_msm8974_resets),
2534};
2535
2527static const struct of_device_id mmcc_msm8974_match_table[] = { 2536static const struct of_device_id mmcc_msm8974_match_table[] = {
2528 { .compatible = "qcom,mmcc-msm8974" }, 2537 { .compatible = "qcom,mmcc-msm8974" },
2529 { } 2538 { }
2530}; 2539};
2531MODULE_DEVICE_TABLE(of, mmcc_msm8974_match_table); 2540MODULE_DEVICE_TABLE(of, mmcc_msm8974_match_table);
2532 2541
2533struct qcom_cc {
2534 struct qcom_reset_controller reset;
2535 struct clk_onecell_data data;
2536 struct clk *clks[];
2537};
2538
2539static int mmcc_msm8974_probe(struct platform_device *pdev) 2542static int mmcc_msm8974_probe(struct platform_device *pdev)
2540{ 2543{
2541 void __iomem *base; 2544 int ret;
2542 struct resource *res;
2543 int i, ret;
2544 struct device *dev = &pdev->dev;
2545 struct clk *clk;
2546 struct clk_onecell_data *data;
2547 struct clk **clks;
2548 struct regmap *regmap; 2545 struct regmap *regmap;
2549 size_t num_clks;
2550 struct qcom_reset_controller *reset;
2551 struct qcom_cc *cc;
2552
2553 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
2554 base = devm_ioremap_resource(dev, res);
2555 if (IS_ERR(base))
2556 return PTR_ERR(base);
2557
2558 regmap = devm_regmap_init_mmio(dev, base, &mmcc_msm8974_regmap_config);
2559 if (IS_ERR(regmap))
2560 return PTR_ERR(regmap);
2561
2562 num_clks = ARRAY_SIZE(mmcc_msm8974_clocks);
2563 cc = devm_kzalloc(dev, sizeof(*cc) + sizeof(*clks) * num_clks,
2564 GFP_KERNEL);
2565 if (!cc)
2566 return -ENOMEM;
2567
2568 clks = cc->clks;
2569 data = &cc->data;
2570 data->clks = clks;
2571 data->clk_num = num_clks;
2572
2573 clk_pll_configure_sr_hpm_lp(&mmpll1, regmap, &mmpll1_config, true);
2574 clk_pll_configure_sr_hpm_lp(&mmpll3, regmap, &mmpll3_config, false);
2575 2546
2576 for (i = 0; i < num_clks; i++) { 2547 ret = qcom_cc_probe(pdev, &mmcc_msm8974_desc);
2577 if (!mmcc_msm8974_clocks[i])
2578 continue;
2579 clk = devm_clk_register_regmap(dev, mmcc_msm8974_clocks[i]);
2580 if (IS_ERR(clk))
2581 return PTR_ERR(clk);
2582 clks[i] = clk;
2583 }
2584
2585 ret = of_clk_add_provider(dev->of_node, of_clk_src_onecell_get, data);
2586 if (ret) 2548 if (ret)
2587 return ret; 2549 return ret;
2588 2550
2589 reset = &cc->reset; 2551 regmap = dev_get_regmap(&pdev->dev, NULL);
2590 reset->rcdev.of_node = dev->of_node; 2552 clk_pll_configure_sr_hpm_lp(&mmpll1, regmap, &mmpll1_config, true);
2591 reset->rcdev.ops = &qcom_reset_ops, 2553 clk_pll_configure_sr_hpm_lp(&mmpll3, regmap, &mmpll3_config, false);
2592 reset->rcdev.owner = THIS_MODULE,
2593 reset->rcdev.nr_resets = ARRAY_SIZE(mmcc_msm8974_resets),
2594 reset->regmap = regmap;
2595 reset->reset_map = mmcc_msm8974_resets,
2596 platform_set_drvdata(pdev, &reset->rcdev);
2597
2598 ret = reset_controller_register(&reset->rcdev);
2599 if (ret)
2600 of_clk_del_provider(dev->of_node);
2601 2554
2602 return ret; 2555 return 0;
2603} 2556}
2604 2557
2605static int mmcc_msm8974_remove(struct platform_device *pdev) 2558static int mmcc_msm8974_remove(struct platform_device *pdev)
2606{ 2559{
2607 of_clk_del_provider(pdev->dev.of_node); 2560 qcom_cc_remove(pdev);
2608 reset_controller_unregister(platform_get_drvdata(pdev));
2609 return 0; 2561 return 0;
2610} 2562}
2611 2563