2017-07-11 11:00:56

by Chunyan Zhang

[permalink] [raw]
Subject: [PATCH V2 00/10] add clock driver for Spreadtrum platforms

This is a rewrite of Spreadtrum's original clock driver[1] according to the
comments[2] from Stephen Boyd.

This series adds Spreadtrum clock support together with its binding
documentation and devicetree data.

Any comments would be greatly appreciated.

Thanks,
Chunyan

Changes from V1 (https://lkml.org/lkml/2017/6/17/356):
* Address Stephen's comments:
- Switch to use platform device driver instead of the DT probing mechanism.
- Move the common clock macro out from vendor directory, but need to remove those
overlap code from other vendors (such as sunxi-ng) once this gets merged.
- Add support to be built as a module.
- Add 'sprd_' prefix for all spin locks used in these drivers.
- Mark input parameter of sprd_x with const.
- Remove unreasonable dependencies to CONFIG_64BIT.
- Add readl() after writing the same register.
- Remove CLK_IS_BASIC which is no longer used.
- Remove unnecessary CLK_IGNORE_UNUSED when defining a clock.
- Change to expose all clock index.
- Use clk_ instead of ccu.
- Add Kconfig for sprd clocks.
- Move the fixed clocks out from the soc node.
- Switch to use 64-bit math in pll driver instead of 32-bit math.
* Revise binding documentation according to dt modification.
* Rename sc9860.c to sc9860-clk.c


[1] https://lwn.net/Articles/722739/
[2] https://www.spinics.net/lists/arm-kernel/msg582017.html


Chunyan Zhang (10):
drivers: move clock common macros out from vendor directories
dt-bindings: Add Spreadtrum clock binding documentation
clk: sprd: Add common infrastructure
clk: sprd: add gate clock support
clk: sprd: add mux clock support
clk: sprd: add divider clock support
clk: sprd: add composite clock support
clk: sprd: add adjustable pll support
clk: sprd: add clocks support for SC9860
arm64: dts: add clocks for SC9860

Documentation/devicetree/bindings/clock/sprd.txt | 36 +
arch/arm64/boot/dts/sprd/sc9860.dtsi | 22 +
arch/arm64/boot/dts/sprd/whale2.dtsi | 3 +-
drivers/clk/Kconfig | 1 +
drivers/clk/Makefile | 1 +
drivers/clk/clk_common.h | 60 +
drivers/clk/sprd/Kconfig | 14 +
drivers/clk/sprd/Makefile | 11 +
drivers/clk/sprd/common.c | 83 ++
drivers/clk/sprd/common.h | 56 +
drivers/clk/sprd/composite.c | 64 +
drivers/clk/sprd/composite.h | 47 +
drivers/clk/sprd/div.c | 98 ++
drivers/clk/sprd/div.h | 77 +
drivers/clk/sprd/gate.c | 104 ++
drivers/clk/sprd/gate.h | 58 +
drivers/clk/sprd/mux.c | 86 ++
drivers/clk/sprd/mux.h | 63 +
drivers/clk/sprd/pll.c | 236 +++
drivers/clk/sprd/pll.h | 133 ++
drivers/clk/sprd/sc9860-clk.c | 1726 ++++++++++++++++++++++
include/dt-bindings/clock/sprd,sc9860-clk.h | 375 +++++
22 files changed, 3352 insertions(+), 2 deletions(-)
create mode 100644 Documentation/devicetree/bindings/clock/sprd.txt
create mode 100644 drivers/clk/clk_common.h
create mode 100644 drivers/clk/sprd/Kconfig
create mode 100644 drivers/clk/sprd/Makefile
create mode 100644 drivers/clk/sprd/common.c
create mode 100644 drivers/clk/sprd/common.h
create mode 100644 drivers/clk/sprd/composite.c
create mode 100644 drivers/clk/sprd/composite.h
create mode 100644 drivers/clk/sprd/div.c
create mode 100644 drivers/clk/sprd/div.h
create mode 100644 drivers/clk/sprd/gate.c
create mode 100644 drivers/clk/sprd/gate.h
create mode 100644 drivers/clk/sprd/mux.c
create mode 100644 drivers/clk/sprd/mux.h
create mode 100644 drivers/clk/sprd/pll.c
create mode 100644 drivers/clk/sprd/pll.h
create mode 100644 drivers/clk/sprd/sc9860-clk.c
create mode 100644 include/dt-bindings/clock/sprd,sc9860-clk.h

--
2.7.4


2017-07-11 11:01:08

by Chunyan Zhang

[permalink] [raw]
Subject: [PATCH V2 02/10] dt-bindings: Add Spreadtrum clock binding documentation

Introduce a new binding with its documentation for Spreadtrum clock
sub-framework.

Signed-off-by: Chunyan Zhang <[email protected]>
---
Documentation/devicetree/bindings/clock/sprd.txt | 36 ++++++++++++++++++++++++
1 file changed, 36 insertions(+)
create mode 100644 Documentation/devicetree/bindings/clock/sprd.txt

diff --git a/Documentation/devicetree/bindings/clock/sprd.txt b/Documentation/devicetree/bindings/clock/sprd.txt
new file mode 100644
index 0000000..c6f3abf
--- /dev/null
+++ b/Documentation/devicetree/bindings/clock/sprd.txt
@@ -0,0 +1,36 @@
+Spreadtrum Clock Binding
+------------------------
+
+Required properties:
+- compatible: must contain the following compatible:
+ - "sprd,sc9860-clk" (only support SC9860 for the time being)
+
+- reg: Must contain the registers base address and length.
+ Clocks on most of Spreadtrum's SoCs were designed to locate in a few
+ different address areas, so there would be more than one items under
+ this property.
+
+- #clock-cells: must be 1
+
+Example:
+
+clk: clk {
+ compatible = "sprd,sc9860-clk";
+ #clock-cells = <1>;
+ reg = <0 0x20000000 0 0x400>,
+ <0 0x20210000 0 0x3000>,
+ <0 0x402b0000 0 0x4000>,
+ <0 0x402d0000 0 0x400>,
+ <0 0x402e0000 0 0x4000>,
+ <0 0x40400000 0 0x400>,
+ <0 0x40880000 0 0x400>,
+ <0 0x415e0000 0 0x400>,
+ <0 0x60200000 0 0x400>,
+ <0 0x61000000 0 0x400>,
+ <0 0x61100000 0 0x3000>,
+ <0 0x62000000 0 0x4000>,
+ <0 0x62100000 0 0x4000>,
+ <0 0x63000000 0 0x400>,
+ <0 0x63100000 0 0x3000>,
+ <0 0x70b00000 0 0x3000>;
+};
--
2.7.4

2017-07-11 11:01:03

by Chunyan Zhang

[permalink] [raw]
Subject: [PATCH V2 01/10] drivers: move clock common macros out from vendor directories

These macros are used by more than one SoC vendor platforms, avoid to
have many copies of these code, this patch moves them to the common
clock directory which every clock drivers can access to.

Signed-off-by: Chunyan Zhang <[email protected]>
---
drivers/clk/clk_common.h | 60 ++++++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 60 insertions(+)
create mode 100644 drivers/clk/clk_common.h

diff --git a/drivers/clk/clk_common.h b/drivers/clk/clk_common.h
new file mode 100644
index 0000000..21e93d2
--- /dev/null
+++ b/drivers/clk/clk_common.h
@@ -0,0 +1,60 @@
+/*
+ * drivers/clk/clk_common.h
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#ifndef _CLK_COMMON_H_
+#define _CLK_COMMON_H_
+
+#include <linux/clk-provider.h>
+
+#define CLK_HW_INIT(_name, _parent, _ops, _flags) \
+ (&(struct clk_init_data) { \
+ .flags = _flags, \
+ .name = _name, \
+ .parent_names = (const char *[]) { _parent }, \
+ .num_parents = 1, \
+ .ops = _ops, \
+ })
+
+#define CLK_HW_INIT_PARENTS(_name, _parents, _ops, _flags) \
+ (&(struct clk_init_data) { \
+ .flags = _flags, \
+ .name = _name, \
+ .parent_names = _parents, \
+ .num_parents = ARRAY_SIZE(_parents), \
+ .ops = _ops, \
+ })
+
+#define CLK_HW_INIT_NO_PARENT(_name, _ops, _flags) \
+ (&(struct clk_init_data) { \
+ .flags = _flags, \
+ .name = _name, \
+ .parent_names = NULL, \
+ .num_parents = 0, \
+ .ops = _ops, \
+ })
+
+#define CLK_FIXED_FACTOR(_struct, _name, _parent, \
+ _div, _mult, _flags) \
+ struct clk_fixed_factor _struct = { \
+ .div = _div, \
+ .mult = _mult, \
+ .hw.init = CLK_HW_INIT(_name, \
+ _parent, \
+ &clk_fixed_factor_ops, \
+ _flags), \
+ }
+
+#define CLK_FIXED_RATE(_struct, _name, _flags, \
+ _fixed_rate, _fixed_accuracy) \
+ struct clk_fixed_rate _struct = { \
+ .fixed_rate = _fixed_rate, \
+ .fixed_accuracy = _fixed_accuracy, \
+ .hw.init = CLK_HW_INIT_NO_PARENT(_name, \
+ &clk_fixed_rate_ops, \
+ _flags), \
+ }
+
+#endif /* _CLK_COMMON_H_ */
--
2.7.4

2017-07-11 11:01:26

by Chunyan Zhang

[permalink] [raw]
Subject: [PATCH V2 03/10] clk: sprd: Add common infrastructure

Added Spreadtrum's clock driver framework together with common
structures and interface functions.

Signed-off-by: Chunyan Zhang <[email protected]>
---
drivers/clk/Kconfig | 1 +
drivers/clk/Makefile | 1 +
drivers/clk/sprd/Kconfig | 4 +++
drivers/clk/sprd/Makefile | 3 ++
drivers/clk/sprd/common.c | 83 +++++++++++++++++++++++++++++++++++++++++++++++
drivers/clk/sprd/common.h | 56 ++++++++++++++++++++++++++++++++
6 files changed, 148 insertions(+)
create mode 100644 drivers/clk/sprd/Kconfig
create mode 100644 drivers/clk/sprd/Makefile
create mode 100644 drivers/clk/sprd/common.c
create mode 100644 drivers/clk/sprd/common.h

diff --git a/drivers/clk/Kconfig b/drivers/clk/Kconfig
index 36cfea3..baf1688 100644
--- a/drivers/clk/Kconfig
+++ b/drivers/clk/Kconfig
@@ -225,6 +225,7 @@ source "drivers/clk/mvebu/Kconfig"
source "drivers/clk/qcom/Kconfig"
source "drivers/clk/renesas/Kconfig"
source "drivers/clk/samsung/Kconfig"
+source "drivers/clk/sprd/Kconfig"
source "drivers/clk/sunxi-ng/Kconfig"
source "drivers/clk/tegra/Kconfig"
source "drivers/clk/ti/Kconfig"
diff --git a/drivers/clk/Makefile b/drivers/clk/Makefile
index c19983a..1d62721 100644
--- a/drivers/clk/Makefile
+++ b/drivers/clk/Makefile
@@ -81,6 +81,7 @@ obj-$(CONFIG_COMMON_CLK_SAMSUNG) += samsung/
obj-$(CONFIG_ARCH_SIRF) += sirf/
obj-$(CONFIG_ARCH_SOCFPGA) += socfpga/
obj-$(CONFIG_PLAT_SPEAR) += spear/
+obj-$(CONFIG_ARCH_SPRD) += sprd/
obj-$(CONFIG_ARCH_STI) += st/
obj-$(CONFIG_ARCH_SUNXI) += sunxi/
obj-$(CONFIG_ARCH_SUNXI) += sunxi-ng/
diff --git a/drivers/clk/sprd/Kconfig b/drivers/clk/sprd/Kconfig
new file mode 100644
index 0000000..67a3287
--- /dev/null
+++ b/drivers/clk/sprd/Kconfig
@@ -0,0 +1,4 @@
+config SPRD_COMMON_CLK
+ tristate "Clock support for Spreadtrum SoCs"
+ depends on ARCH_SPRD || COMPILE_TEST
+ default ARCH_SPRD
diff --git a/drivers/clk/sprd/Makefile b/drivers/clk/sprd/Makefile
new file mode 100644
index 0000000..74f4b80
--- /dev/null
+++ b/drivers/clk/sprd/Makefile
@@ -0,0 +1,3 @@
+obj-$(CONFIG_SPRD_COMMON_CLK) += clk-sprd.o
+
+clk-sprd-y += common.o
diff --git a/drivers/clk/sprd/common.c b/drivers/clk/sprd/common.c
new file mode 100644
index 0000000..5ff0473
--- /dev/null
+++ b/drivers/clk/sprd/common.c
@@ -0,0 +1,83 @@
+/*
+ * Spreadtrum clock infrastructure
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#include <linux/module.h>
+
+#include "common.h"
+
+static inline void __iomem *clk_find_base(const struct clk_addr_map *maps,
+ unsigned int num, unsigned int reg)
+{
+ int i;
+
+ for (i = 0; i < num; i++)
+ if ((reg & 0xffff0000) == maps[i].phy)
+ return maps[i].virt;
+
+ return 0;
+}
+
+int sprd_clk_probe(struct device_node *node, const struct clk_addr_map *maps,
+ unsigned int count, const struct sprd_clk_desc *desc)
+{
+ int i, ret = 0;
+ struct sprd_clk_common *cclk;
+ struct clk_hw *hw;
+
+ for (i = 0; i < desc->num_clk_clks; i++) {
+ cclk = desc->clk_clks[i];
+ if (!cclk)
+ continue;
+
+ cclk->base = clk_find_base(maps, count, cclk->reg);
+ if (!cclk->base) {
+ pr_err("%s: No mapped address found for clock(0x%x)\n",
+ __func__, cclk->reg);
+ return -EINVAL;
+ }
+ cclk->reg = cclk->reg & 0xffff;
+ }
+
+ for (i = 0; i < desc->hw_clks->num; i++) {
+
+ hw = desc->hw_clks->hws[i];
+
+ if (!hw)
+ continue;
+
+ ret = clk_hw_register(NULL, hw);
+ if (ret) {
+ pr_err("Couldn't register clock %d - %s\n",
+ i, hw->init->name);
+ goto err_clk_unreg;
+ }
+ }
+
+ ret = of_clk_add_hw_provider(node, of_clk_hw_onecell_get,
+ desc->hw_clks);
+ if (ret) {
+ pr_err("Failed to add clock provider.\n");
+ goto err_clk_unreg;
+ }
+
+ return 0;
+
+err_clk_unreg:
+ while (--i >= 0) {
+ hw = desc->hw_clks->hws[i];
+ if (!hw)
+ continue;
+
+ clk_hw_unregister(hw);
+ }
+
+ return ret;
+}
+EXPORT_SYMBOL_GPL(sprd_clk_probe);
+
+MODULE_LICENSE("GPL v2");
diff --git a/drivers/clk/sprd/common.h b/drivers/clk/sprd/common.h
new file mode 100644
index 0000000..c747a7d
--- /dev/null
+++ b/drivers/clk/sprd/common.h
@@ -0,0 +1,56 @@
+/*
+ * Spreadtrum clock infrastructure
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#ifndef _SPRD_CLK_COMMON_H_
+#define _SPRD_CLK_COMMON_H_
+
+#include <linux/clk-provider.h>
+
+#include "../clk_common.h"
+
+struct device_node;
+
+struct sprd_clk_common {
+ void __iomem *base;
+ u32 reg;
+ spinlock_t *lock;
+ struct clk_hw hw;
+};
+
+struct clk_addr_map {
+ phys_addr_t phy;
+ void __iomem *virt;
+};
+
+static inline u32 sprd_clk_readl(const struct sprd_clk_common *common)
+{
+ return readl(common->base + common->reg);
+}
+
+static inline void sprd_clk_writel(u32 val,
+ const struct sprd_clk_common *common)
+{
+ writel(val, common->base + common->reg);
+}
+
+static inline struct sprd_clk_common *
+ hw_to_sprd_clk_common(const struct clk_hw *hw)
+{
+ return container_of(hw, struct sprd_clk_common, hw);
+}
+
+struct sprd_clk_desc {
+ struct sprd_clk_common **clk_clks;
+ unsigned long num_clk_clks;
+ struct clk_hw_onecell_data *hw_clks;
+};
+
+int sprd_clk_probe(struct device_node *node, const struct clk_addr_map *maps,
+ unsigned int count, const struct sprd_clk_desc *desc);
+
+#endif /* _SPRD_CLK_COMMON_H_ */
--
2.7.4

2017-07-11 11:01:29

by Chunyan Zhang

[permalink] [raw]
Subject: [PATCH V2 05/10] clk: sprd: add mux clock support

This patch adds clock multiplexor support for Spreadtrum platforms,
the mux clocks also can be found in sprd composite clocks, so
provides two helpers that can be reused later on.

Original-by: Xiaolong Zhang <[email protected]>
Signed-off-by: Chunyan Zhang <[email protected]>
---
drivers/clk/sprd/Makefile | 1 +
drivers/clk/sprd/mux.c | 86 +++++++++++++++++++++++++++++++++++++++++++++++
drivers/clk/sprd/mux.h | 63 ++++++++++++++++++++++++++++++++++
3 files changed, 150 insertions(+)
create mode 100644 drivers/clk/sprd/mux.c
create mode 100644 drivers/clk/sprd/mux.h

diff --git a/drivers/clk/sprd/Makefile b/drivers/clk/sprd/Makefile
index 8cd5592..cee36b5 100644
--- a/drivers/clk/sprd/Makefile
+++ b/drivers/clk/sprd/Makefile
@@ -2,3 +2,4 @@ obj-$(CONFIG_SPRD_COMMON_CLK) += clk-sprd.o

clk-sprd-y += common.o
clk-sprd-y += gate.o
+clk-sprd-y += mux.o
diff --git a/drivers/clk/sprd/mux.c b/drivers/clk/sprd/mux.c
new file mode 100644
index 0000000..b5d8988
--- /dev/null
+++ b/drivers/clk/sprd/mux.c
@@ -0,0 +1,86 @@
+/*
+ * Spreadtrum multiplexer clock driver
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#include <linux/clk.h>
+#include <linux/clk-provider.h>
+
+#include "mux.h"
+
+DEFINE_SPINLOCK(sprd_mux_lock);
+EXPORT_SYMBOL_GPL(sprd_mux_lock);
+
+u8 sprd_mux_helper_get_parent(const struct sprd_clk_common *common,
+ const struct sprd_mux_internal *mux)
+{
+ u32 reg;
+ u8 parent;
+ int num_parents;
+ int i;
+
+ reg = sprd_clk_readl(common);
+ parent = reg >> mux->shift;
+ parent &= (1 << mux->width) - 1;
+
+ if (mux->table) {
+ num_parents = clk_hw_get_num_parents(&common->hw);
+
+ for (i = 0; i < num_parents; i++)
+ if (parent == mux->table[i] ||
+ (i < (num_parents - 1) && parent > mux->table[i] &&
+ parent < mux->table[i + 1]))
+ return i;
+ if (i == num_parents)
+ return i - 1;
+ }
+
+ return parent;
+}
+EXPORT_SYMBOL_GPL(sprd_mux_helper_get_parent);
+
+static u8 sprd_mux_get_parent(struct clk_hw *hw)
+{
+ struct sprd_mux *cm = hw_to_sprd_mux(hw);
+
+ return sprd_mux_helper_get_parent(&cm->common, &cm->mux);
+}
+
+int sprd_mux_helper_set_parent(const struct sprd_clk_common *common,
+ const struct sprd_mux_internal *mux,
+ u8 index)
+{
+ unsigned long flags = 0;
+ u32 reg;
+
+ if (mux->table)
+ index = mux->table[index];
+
+ spin_lock_irqsave(common->lock, flags);
+
+ reg = sprd_clk_readl(common);
+ reg &= ~GENMASK(mux->width + mux->shift - 1, mux->shift);
+ sprd_clk_writel(reg | (index << mux->shift), common);
+
+ spin_unlock_irqrestore(common->lock, flags);
+
+ return 0;
+}
+EXPORT_SYMBOL_GPL(sprd_mux_helper_set_parent);
+
+static int sprd_mux_set_parent(struct clk_hw *hw, u8 index)
+{
+ struct sprd_mux *cm = hw_to_sprd_mux(hw);
+
+ return sprd_mux_helper_set_parent(&cm->common, &cm->mux, index);
+}
+
+const struct clk_ops sprd_mux_ops = {
+ .get_parent = sprd_mux_get_parent,
+ .set_parent = sprd_mux_set_parent,
+ .determine_rate = __clk_mux_determine_rate,
+};
+EXPORT_SYMBOL_GPL(sprd_mux_ops);
diff --git a/drivers/clk/sprd/mux.h b/drivers/clk/sprd/mux.h
new file mode 100644
index 0000000..aa35514
--- /dev/null
+++ b/drivers/clk/sprd/mux.h
@@ -0,0 +1,63 @@
+/*
+ * Spreadtrum multiplexer clock driver
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#ifndef _SPRD_MUX_H_
+#define _SPRD_MUX_H_
+
+#include "common.h"
+
+struct sprd_mux_internal {
+ u8 shift;
+ u8 width;
+ const u8 *table;
+};
+
+struct sprd_mux {
+ struct sprd_mux_internal mux;
+ struct sprd_clk_common common;
+};
+
+#define _SPRD_MUX_CLK(_shift, _width, _table) \
+ { \
+ .shift = _shift, \
+ .width = _width, \
+ .table = _table, \
+ }
+
+#define SPRD_MUX_CLK(_struct, _name, _parents, _table, \
+ _reg, _shift, _width, \
+ _flags) \
+ struct sprd_mux _struct = { \
+ .mux = _SPRD_MUX_CLK(_shift, _width, _table), \
+ .common = { \
+ .reg = _reg, \
+ .lock = &sprd_mux_lock, \
+ .hw.init = CLK_HW_INIT_PARENTS(_name, \
+ _parents, \
+ &sprd_mux_ops,\
+ _flags), \
+ } \
+ }
+
+static inline struct sprd_mux *hw_to_sprd_mux(const struct clk_hw *hw)
+{
+ struct sprd_clk_common *common = hw_to_sprd_clk_common(hw);
+
+ return container_of(common, struct sprd_mux, common);
+}
+
+extern const struct clk_ops sprd_mux_ops;
+extern spinlock_t sprd_mux_lock;
+
+u8 sprd_mux_helper_get_parent(const struct sprd_clk_common *common,
+ const struct sprd_mux_internal *mux);
+int sprd_mux_helper_set_parent(const struct sprd_clk_common *common,
+ const struct sprd_mux_internal *mux,
+ u8 index);
+
+#endif /* _SPRD_MUX_H_ */
--
2.7.4

2017-07-11 11:01:46

by Chunyan Zhang

[permalink] [raw]
Subject: [PATCH V2 08/10] clk: sprd: add adjustable pll support

Introduced a common adjustable pll clock driver for Spreadtrum SoCs.

Original-by: Xiaolong Zhang <[email protected]>
Signed-off-by: Chunyan Zhang <[email protected]>
---
drivers/clk/sprd/Makefile | 1 +
drivers/clk/sprd/pll.c | 236 ++++++++++++++++++++++++++++++++++++++++++++++
drivers/clk/sprd/pll.h | 133 ++++++++++++++++++++++++++
3 files changed, 370 insertions(+)
create mode 100644 drivers/clk/sprd/pll.c
create mode 100644 drivers/clk/sprd/pll.h

diff --git a/drivers/clk/sprd/Makefile b/drivers/clk/sprd/Makefile
index 2262e76..d693969 100644
--- a/drivers/clk/sprd/Makefile
+++ b/drivers/clk/sprd/Makefile
@@ -5,3 +5,4 @@ clk-sprd-y += gate.o
clk-sprd-y += mux.o
clk-sprd-y += div.o
clk-sprd-y += composite.o
+clk-sprd-y += pll.o
diff --git a/drivers/clk/sprd/pll.c b/drivers/clk/sprd/pll.c
new file mode 100644
index 0000000..97935a2
--- /dev/null
+++ b/drivers/clk/sprd/pll.c
@@ -0,0 +1,236 @@
+/*
+ * Spreadtrum pll clock driver
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#include <linux/delay.h>
+#include <linux/err.h>
+#include <linux/slab.h>
+
+#include "pll.h"
+
+#define CLK_PLL_1M 1000000
+#define CLK_PLL_10M (CLK_PLL_1M * 10)
+
+#define pindex(pll, member) \
+ (pll->factors[member].shift / (8 * sizeof(pll->regs[0])))
+
+#define pshift(pll, member) \
+ (pll->factors[member].shift % (8 * sizeof(pll->regs[0])))
+
+#define pwidth(pll, member) \
+ pll->factors[member].width
+
+#define pmask(pll, member) \
+ ((pwidth(pll, member)) ? \
+ GENMASK(pwidth(pll, member) + pshift(pll, member) - 1, \
+ pshift(pll, member)) : 0)
+
+#define pinternal(pll, cfg, member) \
+ (cfg[pindex(pll, member)] & pmask(pll, member))
+
+#define pinternal_val(pll, cfg, member) \
+ (pinternal(pll, cfg, member) >> pshift(pll, member))
+
+static unsigned long pll_get_refin(const struct sprd_pll *pll)
+{
+ u32 shift, mask, index, refin_id = 3;
+ const unsigned long refin[4] = { 2, 4, 13, 26 };
+
+ if (pwidth(pll, PLL_REFIN)) {
+ index = pindex(pll, PLL_REFIN);
+ shift = pshift(pll, PLL_REFIN);
+ mask = pmask(pll, PLL_REFIN);
+ refin_id = (sprd_pll_readl(pll, index) & mask) >> shift;
+ if (refin_id > 3)
+ refin_id = 3;
+ }
+
+ return refin[refin_id];
+}
+
+static u32 pll_get_ibias(u64 rate, const u64 *table)
+{
+ u32 i, num = table[0];
+
+ for (i = 1; i < num + 1; i++)
+ if (rate <= table[i])
+ break;
+
+ return (i == num + 1) ? num : i;
+}
+
+static unsigned long _sprd_pll_recalc_rate(const struct sprd_pll *pll,
+ unsigned long parent_rate)
+{
+ u32 *cfg;
+ u32 i, mask, reg_num = pll->regs[0];
+ unsigned long rate, nint, kint = 0;
+ u64 refin;
+ u16 k1, k2;
+
+ cfg = kcalloc(reg_num, sizeof(*cfg), GFP_KERNEL);
+ if (!cfg)
+ return -ENOMEM;
+
+ for (i = 0; i < reg_num; i++)
+ cfg[i] = sprd_pll_readl(pll, i);
+
+ refin = pll_get_refin(pll);
+
+ if (pinternal(pll, cfg, PLL_PREDIV))
+ refin = refin * 2;
+
+ if (pwidth(pll, PLL_POSTDIV) &&
+ ((pll->fflag == 1 && pinternal(pll, cfg, PLL_POSTDIV)) ||
+ (!pll->fflag && !pinternal(pll, cfg, PLL_POSTDIV))))
+ refin = refin / 2;
+
+ if (!pinternal(pll, cfg, PLL_DIV_S)) {
+ rate = refin * pinternal_val(pll, cfg, PLL_N) * CLK_PLL_10M;
+ } else {
+ nint = pinternal_val(pll, cfg, PLL_NINT);
+ if (pinternal(pll, cfg, PLL_SDM_EN))
+ kint = pinternal_val(pll, cfg, PLL_KINT);
+
+ mask = pmask(pll, PLL_KINT);
+
+ k1 = pll->k1;
+ k2 = pll->k2;
+ rate = DIV_ROUND_CLOSEST_ULL(refin * kint * k1,
+ ((mask >> __ffs(mask)) + 1)) *
+ k2 + refin * nint * CLK_PLL_1M;
+ }
+
+ return rate;
+}
+
+#define SPRD_PLL_WRITE_CHECK(pll, i, mask, val) \
+ ((sprd_pll_readl(pll, i) & mask) == val) ? 0 : -EFAULT
+
+static int _sprd_pll_set_rate(const struct sprd_pll *pll,
+ unsigned long rate,
+ unsigned long parent_rate)
+{
+ struct reg_cfg *cfg;
+ int ret = 0;
+ u32 mask, shift, width, ibias_val, index;
+ u32 reg_num = pll->regs[0], i = 0;
+ unsigned long kint, nint;
+ u64 refin, fvco = rate;
+
+ cfg = kcalloc(reg_num, sizeof(*cfg), GFP_KERNEL);
+ if (!cfg)
+ return -ENOMEM;
+
+ refin = pll_get_refin(pll);
+
+ mask = pmask(pll, PLL_PREDIV);
+ index = pindex(pll, PLL_PREDIV);
+ width = pwidth(pll, PLL_PREDIV);
+ if (width && (sprd_pll_readl(pll, index) & mask))
+ refin = refin * 2;
+
+ mask = pmask(pll, PLL_POSTDIV);
+ index = pindex(pll, PLL_POSTDIV);
+ width = pwidth(pll, PLL_POSTDIV);
+ cfg[index].msk = mask;
+ if (width && ((pll->fflag == 1 && fvco <= pll->fvco) ||
+ (pll->fflag == 0 && fvco > pll->fvco)))
+ cfg[index].val |= mask;
+
+ if (width && fvco <= pll->fvco)
+ fvco = fvco * 2;
+
+ mask = pmask(pll, PLL_DIV_S);
+ index = pindex(pll, PLL_DIV_S);
+ cfg[index].val |= mask;
+ cfg[index].msk |= mask;
+
+ mask = pmask(pll, PLL_SDM_EN);
+ index = pindex(pll, PLL_SDM_EN);
+ cfg[index].val |= mask;
+ cfg[index].msk |= mask;
+
+ nint = fvco/(refin * CLK_PLL_1M);
+
+ mask = pmask(pll, PLL_NINT);
+ index = pindex(pll, PLL_NINT);
+ shift = pshift(pll, PLL_NINT);
+ cfg[index].val |= (nint << shift) & mask;
+ cfg[index].msk |= mask;
+
+ mask = pmask(pll, PLL_KINT);
+ index = pindex(pll, PLL_KINT);
+ width = pwidth(pll, PLL_KINT);
+ shift = pshift(pll, PLL_KINT);
+ kint = DIV_ROUND_CLOSEST_ULL(((fvco - refin * nint * CLK_PLL_1M) /
+ 10000) * ((mask >> shift) + 1),
+ refin * 100);
+ cfg[index].val |= (kint << shift) & mask;
+ cfg[index].msk |= mask;
+
+ ibias_val = pll_get_ibias(fvco, pll->itable);
+
+ mask = pmask(pll, PLL_IBIAS);
+ index = pindex(pll, PLL_IBIAS);
+ shift = pshift(pll, PLL_IBIAS);
+ cfg[index].val |= ibias_val << shift & mask;
+ cfg[index].msk |= mask;
+
+ for (i = 0; i < reg_num; i++) {
+ if (cfg[i].msk) {
+ sprd_pll_writel(pll, i, cfg[i].msk, cfg[i].val);
+ ret |= SPRD_PLL_WRITE_CHECK(pll, i, cfg[i].msk,
+ cfg[i].val);
+ }
+ }
+
+ if (!ret)
+ udelay(pll->udelay);
+
+ return ret;
+}
+
+static unsigned long sprd_pll_recalc_rate(struct clk_hw *hw,
+ unsigned long parent_rate)
+{
+ struct sprd_pll *pll = hw_to_sprd_pll(hw);
+
+ return _sprd_pll_recalc_rate(pll, parent_rate);
+}
+
+static int sprd_pll_set_rate(struct clk_hw *hw,
+ unsigned long rate,
+ unsigned long parent_rate)
+{
+ struct sprd_pll *pll = hw_to_sprd_pll(hw);
+
+ return _sprd_pll_set_rate(pll, rate, parent_rate);
+}
+
+static int sprd_pll_clk_prepare(struct clk_hw *hw)
+{
+ struct sprd_pll *pll = hw_to_sprd_pll(hw);
+
+ udelay(pll->udelay);
+
+ return 0;
+}
+
+static long sprd_pll_round_rate(struct clk_hw *hw, unsigned long rate,
+ unsigned long *prate)
+{
+ return rate;
+}
+
+const struct clk_ops sprd_pll_ops = {
+ .prepare = sprd_pll_clk_prepare,
+ .recalc_rate = sprd_pll_recalc_rate,
+ .round_rate = sprd_pll_round_rate,
+ .set_rate = sprd_pll_set_rate,
+};
+EXPORT_SYMBOL_GPL(sprd_pll_ops);
diff --git a/drivers/clk/sprd/pll.h b/drivers/clk/sprd/pll.h
new file mode 100644
index 0000000..af5b2da
--- /dev/null
+++ b/drivers/clk/sprd/pll.h
@@ -0,0 +1,133 @@
+/*
+ * Spreadtrum clock pll configurations
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#ifndef _SPRD_PLL_H_
+#define _SPRD_PLL_H_
+
+#include "common.h"
+
+struct reg_cfg {
+ u32 val;
+ u32 msk;
+};
+
+struct clk_bit_field {
+ u8 shift;
+ u8 width;
+};
+
+enum {
+ PLL_LOCK_DONE,
+ PLL_DIV_S,
+ PLL_MOD_EN,
+ PLL_SDM_EN,
+ PLL_REFIN,
+ PLL_IBIAS,
+ PLL_N,
+ PLL_NINT,
+ PLL_KINT,
+ PLL_PREDIV,
+ PLL_POSTDIV,
+
+ PLL_FACT_MAX
+};
+
+/*
+ * struct sprd_pll - definition of adjustable pll clock
+ *
+ * @reg: registers used to set the configuration of pll clock,
+ * reg[0] shows how many registers this pll clock uses.
+ * @itable: pll ibias table, itable[0] means how many items this
+ * table includes
+ * @udelay delay time after setting rate
+ * @factors used to calculate the pll clock rate
+ * @fvco: fvco threshold rate
+ * @fflag: fvco flag
+ */
+struct sprd_pll {
+ const u32 *regs;
+ const u64 *itable;
+ const struct clk_bit_field *factors;
+ u16 udelay;
+ u16 k1;
+ u16 k2;
+ u16 fflag;
+ u64 fvco;
+
+ struct sprd_clk_common common;
+};
+
+#define SPRD_PLL_WITH_ITABLE_K_FVCO(_struct, _name, _parent, _reg, \
+ _regs, _itable, _factors, _udelay, \
+ _k1, _k2, _fflag, _fvco) \
+ struct sprd_pll _struct = { \
+ .regs = _regs, \
+ .itable = _itable, \
+ .factors = _factors, \
+ .udelay = _udelay, \
+ .k1 = _k1, \
+ .k2 = _k2, \
+ .fflag = _fflag, \
+ .fvco = _fvco, \
+ .common = { \
+ .reg = _reg, \
+ .hw.init = CLK_HW_INIT(_name, \
+ _parent, \
+ &sprd_pll_ops, \
+ 0), \
+ }, \
+ }
+
+#define SPRD_PLL_WITH_ITABLE_K(_struct, _name, _parent, _reg, \
+ _regs, _itable, _factors, \
+ _udelay, _k1, _k2) \
+ SPRD_PLL_WITH_ITABLE_K_FVCO(_struct, _name, _parent, _reg, \
+ _regs, _itable, _factors, \
+ _udelay, _k1, _k2, 0, 0)
+
+#define SPRD_PLL_WITH_ITABLE_1K(_struct, _name, _parent, _reg, \
+ _regs, _itable, _factors, _udelay) \
+ SPRD_PLL_WITH_ITABLE_K_FVCO(_struct, _name, _parent, _reg, \
+ _regs, _itable, _factors, _udelay, \
+ 1000, 1000, 0, 0)
+
+static inline struct sprd_pll *hw_to_sprd_pll(struct clk_hw *hw)
+{
+ struct sprd_clk_common *common = hw_to_sprd_clk_common(hw);
+
+ return container_of(common, struct sprd_pll, common);
+}
+
+static inline u32 sprd_pll_readl(const struct sprd_pll *pll, u8 index)
+{
+ const struct sprd_clk_common *common = &pll->common;
+
+ if (WARN_ON(index >= pll->regs[0]))
+ return 0;
+
+ return readl(common->base + pll->regs[index + 1]);
+}
+
+static inline void sprd_pll_writel(const struct sprd_pll *pll, u8 index,
+ u32 msk, u32 val)
+{
+ const struct sprd_clk_common *common = &pll->common;
+ void __iomem *addr;
+ u32 reg;
+
+ if (WARN_ON(index >= pll->regs[0]))
+ return;
+
+ addr = common->base + pll->regs[index + 1];
+ reg = readl(addr);
+ writel((reg & ~msk) | val, addr);
+}
+
+extern const struct clk_ops sprd_pll_ops;
+
+#endif /* _SPRD_PLL_H_ */
--
2.7.4

2017-07-11 11:01:58

by Chunyan Zhang

[permalink] [raw]
Subject: [PATCH V2 09/10] clk: sprd: add clocks support for SC9860

This patch added the list of clocks for Spreadtrum's SC9860 SoC, together
with clock initialization code.

Original-by: Xiaolong Zhang <[email protected]>
Signed-off-by: Chunyan Zhang <[email protected]>
---
drivers/clk/sprd/Kconfig | 10 +
drivers/clk/sprd/Makefile | 3 +
drivers/clk/sprd/sc9860-clk.c | 1726 +++++++++++++++++++++++++++
include/dt-bindings/clock/sprd,sc9860-clk.h | 375 ++++++
4 files changed, 2114 insertions(+)
create mode 100644 drivers/clk/sprd/sc9860-clk.c
create mode 100644 include/dt-bindings/clock/sprd,sc9860-clk.h

diff --git a/drivers/clk/sprd/Kconfig b/drivers/clk/sprd/Kconfig
index 67a3287..8789247 100644
--- a/drivers/clk/sprd/Kconfig
+++ b/drivers/clk/sprd/Kconfig
@@ -2,3 +2,13 @@ config SPRD_COMMON_CLK
tristate "Clock support for Spreadtrum SoCs"
depends on ARCH_SPRD || COMPILE_TEST
default ARCH_SPRD
+
+if SPRD_COMMON_CLK
+
+# SoC Drivers
+
+config SPRD_SC9860_CLK
+ tristate "Support for the Spreadtrum SC9860 clocks"
+ depends on (ARM64 && ARCH_SPRD) || COMPILE_TEST
+ default ARM64 && ARCH_SPRD
+endif
diff --git a/drivers/clk/sprd/Makefile b/drivers/clk/sprd/Makefile
index d693969..b0d81e5 100644
--- a/drivers/clk/sprd/Makefile
+++ b/drivers/clk/sprd/Makefile
@@ -6,3 +6,6 @@ clk-sprd-y += mux.o
clk-sprd-y += div.o
clk-sprd-y += composite.o
clk-sprd-y += pll.o
+
+## SoC support
+obj-$(CONFIG_SPRD_SC9860_CLK) += sc9860-clk.o
diff --git a/drivers/clk/sprd/sc9860-clk.c b/drivers/clk/sprd/sc9860-clk.c
new file mode 100644
index 0000000..f70b941
--- /dev/null
+++ b/drivers/clk/sprd/sc9860-clk.c
@@ -0,0 +1,1726 @@
+/*
+ * Spreatrum SC9860 clock driver
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#include <linux/clk-provider.h>
+#include <linux/err.h>
+#include <linux/io.h>
+#include <linux/module.h>
+#include <linux/platform_device.h>
+#include <linux/slab.h>
+
+#include "common.h"
+#include "composite.h"
+#include "div.h"
+#include "gate.h"
+#include "mux.h"
+#include "pll.h"
+
+#include <dt-bindings/clock/sprd,sc9860-clk.h>
+
+static CLK_FIXED_RATE(ext_rco_100m, "ext-rco-100m", 0, 100000000, 0);
+static CLK_FIXED_RATE(ext_32k, "ext-32k", 0, 32768, 0);
+
+static CLK_FIXED_FACTOR(fac_4m, "fac-4m", "ext-26m",
+ 6, 1, 0);
+static CLK_FIXED_FACTOR(fac_2m, "fac-2m", "ext-26m",
+ 13, 1, 0);
+static CLK_FIXED_FACTOR(fac_1m, "fac-1m", "ext-26m",
+ 26, 1, 0);
+static CLK_FIXED_FACTOR(fac_250k, "fac-250k", "ext-26m",
+ 104, 1, 0);
+static CLK_FIXED_FACTOR(fac_rpll0_26m, "rpll0-26m", "ext-26m",
+ 1, 1, 0);
+static CLK_FIXED_FACTOR(fac_rpll1_26m, "rpll1-26m", "ext-26m",
+ 1, 1, 0);
+static CLK_FIXED_FACTOR(fac_rco_25m, "rco-25m", "ext-rc0-100m",
+ 4, 1, 0);
+static CLK_FIXED_FACTOR(fac_rco_4m, "rco-4m", "ext-rc0-100m",
+ 25, 1, 0);
+static CLK_FIXED_FACTOR(fac_rco_2m, "rco-2m", "ext-rc0-100m",
+ 50, 1, 0);
+static CLK_FIXED_FACTOR(fac_3k2, "fac-3k2", "ext-32k",
+ 10, 1, 0);
+static CLK_FIXED_FACTOR(fac_1k, "fac-1k", "ext-32k",
+ 32, 1, 0);
+
+static SPRD_GATE_CLK(rpll0_gate, "rpll0-gate", "ext-26m", 0x402b016c,
+ 0x1000, BIT(2), 0, 0);
+static SPRD_GATE_CLK(rpll1_gate, "rpll1-gate", "ext-26m", 0x402b016c,
+ 0x1000, BIT(18), 0, 0);
+static SPRD_GATE_CLK(mpll0_gate, "mpll0-gate", "ext-26m", 0x402b00b0,
+ 0x1000, BIT(2), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(mpll1_gate, "mpll1-gate", "ext-26m", 0x402b00b0,
+ 0x1000, BIT(18), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(dpll0_gate, "dpll0-gate", "ext-26m", 0x402b00b4,
+ 0x1000, BIT(2), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(dpll1_gate, "dpll1-gate", "ext-26m", 0x402b00b4,
+ 0x1000, BIT(18), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(gpll_gate, "gpll-gate", "ext-26m", 0x402b032c,
+ 0x1000, BIT(0), CLK_IGNORE_UNUSED,
+ CLK_GATE_SET_TO_DISABLE);
+static SPRD_GATE_CLK(cppll_gate, "cppll-gate", "ext-26m", 0x402b02b4,
+ 0x1000, BIT(2), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ltepll0_gate, "ltepll0-gate", "ext-26m", 0x402b00b8,
+ 0x1000, BIT(2), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ltepll1_gate, "ltepll1-gate", "ext-26m", 0x402b010c,
+ 0x1000, BIT(2), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(twpll_gate, "twpll-gate", "ext-26m", 0x402b00bc,
+ 0x1000, BIT(2), CLK_IGNORE_UNUSED, 0);
+
+/* GPLL/LPLL/DPLL/RPLL/CPLL */
+static const u64 const itable1[4] = {3, 780000000, 988000000, 1196000000};
+
+/* TWPLL/MPLL0/MPLL1 */
+static const u64 itable2[4] = {3, 1638000000, 2080000000, 2600000000UL};
+
+static const struct clk_bit_field const f_rpll[PLL_FACT_MAX] = {
+ { .shift = 0, .width = 1 }, /* lock_done */
+ { .shift = 3, .width = 1 }, /* div_s */
+ { .shift = 80, .width = 1 }, /* mod_en */
+ { .shift = 81, .width = 1 }, /* sdm_en */
+ { .shift = 0, .width = 0 }, /* refin */
+ { .shift = 14, .width = 2 }, /* ibias */
+ { .shift = 16, .width = 7 }, /* n */
+ { .shift = 4, .width = 7 }, /* nint */
+ { .shift = 32, .width = 23}, /* kint */
+ { .shift = 0, .width = 0 }, /* prediv */
+ { .shift = 0, .width = 0 }, /* postdiv */
+};
+static const u32 const regs_rpll0[4] = { 3, 0x44, 0x48, 0x4c };
+static SPRD_PLL_WITH_ITABLE_1K(rpll0_clk, "rpll0", "rpll0-gate", 0x40400044,
+ regs_rpll0, itable1, f_rpll, 200);
+
+static const u32 const regs_rpll1[4] = { 3, 0x50, 0x54, 0x58 };
+static SPRD_PLL_WITH_ITABLE_1K(rpll1_clk, "rpll1", "rpll1-gate", 0x40400050,
+ regs_rpll1, itable1, f_rpll, 200);
+
+static const struct clk_bit_field const f_mpll0[PLL_FACT_MAX] = {
+ { .shift = 20, .width = 1 }, /* lock_done */
+ { .shift = 19, .width = 1 }, /* div_s */
+ { .shift = 18, .width = 1 }, /* mod_en */
+ { .shift = 17, .width = 1 }, /* sdm_en */
+ { .shift = 0, .width = 0 }, /* refin */
+ { .shift = 11, .width = 2 }, /* ibias */
+ { .shift = 0, .width = 7 }, /* n */
+ { .shift = 57, .width = 7 }, /* nint */
+ { .shift = 32, .width = 23}, /* kint */
+ { .shift = 0, .width = 0 }, /* prediv */
+ { .shift = 56, .width = 1 }, /* postdiv */
+};
+static const u32 const regs_mpll0[3] = { 2, 0x24, 0x28 };
+static SPRD_PLL_WITH_ITABLE_K_FVCO(mpll0_clk, "mpll0", "mpll0-gate", 0x40400024,
+ regs_mpll0, itable2, f_mpll0, 200,
+ 1000, 1000, 1, 1300000000);
+
+static const struct clk_bit_field const f_mpll1[PLL_FACT_MAX] = {
+ { .shift = 20, .width = 1 }, /* lock_done */
+ { .shift = 19, .width = 1 }, /* div_s */
+ { .shift = 18, .width = 1 }, /* mod_en */
+ { .shift = 17, .width = 1 }, /* sdm_en */
+ { .shift = 0, .width = 0 }, /* refin */
+ { .shift = 11, .width = 2 }, /* ibias */
+ { .shift = 0, .width = 7 }, /* n */
+ { .shift = 57, .width = 7 }, /* nint */
+ { .shift = 32, .width = 23}, /* kint */
+ { .shift = 56, .width = 1 }, /* prediv */
+ { .shift = 0, .width = 0 }, /* postdiv */
+};
+static const u32 const regs_mpll1[3] = { 2, 0x2c, 0x30 };
+static SPRD_PLL_WITH_ITABLE_1K(mpll1_clk, "mpll1", "mpll1-gate", 0x4040002c,
+ regs_mpll1, itable2, f_mpll1, 200);
+
+static const struct clk_bit_field const f_dpll[PLL_FACT_MAX] = {
+ { .shift = 16, .width = 1 }, /* lock_done */
+ { .shift = 15, .width = 1 }, /* div_s */
+ { .shift = 14, .width = 1 }, /* mod_en */
+ { .shift = 13, .width = 1 }, /* sdm_en */
+ { .shift = 0, .width = 0 }, /* refin */
+ { .shift = 8, .width = 2 }, /* ibias */
+ { .shift = 0, .width = 7 }, /* n */
+ { .shift = 57, .width = 7 }, /* nint */
+ { .shift = 32, .width = 23}, /* kint */
+ { .shift = 0, .width = 0 }, /* prediv */
+ { .shift = 0, .width = 0 }, /* postdiv */
+};
+static const u32 const regs_dpll0[3] = { 2, 0x34, 0x38 };
+static SPRD_PLL_WITH_ITABLE_1K(dpll0_clk, "dpll0", "dpll0-gate", 0x40400034,
+ regs_dpll0, itable1, f_dpll, 200);
+
+static const u32 const regs_dpll1[3] = { 2, 0x3c, 0x40 };
+static SPRD_PLL_WITH_ITABLE_1K(dpll1_clk, "dpll1", "dpll1-gate", 0x4040003c,
+ regs_dpll1, itable1, f_dpll, 200);
+
+static const struct clk_bit_field const f_gpll[PLL_FACT_MAX] = {
+ { .shift = 18, .width = 1 }, /* lock_done */
+ { .shift = 15, .width = 1 }, /* div_s */
+ { .shift = 14, .width = 1 }, /* mod_en */
+ { .shift = 13, .width = 1 }, /* sdm_en */
+ { .shift = 0, .width = 0 }, /* refin */
+ { .shift = 8, .width = 2 }, /* ibias */
+ { .shift = 0, .width = 7 }, /* n */
+ { .shift = 57, .width = 7 }, /* nint */
+ { .shift = 32, .width = 23}, /* kint */
+ { .shift = 0, .width = 0 }, /* prediv */
+ { .shift = 17, .width = 1 }, /* postdiv */
+};
+static const u32 const regs_gpll[3] = { 2, 0x9c, 0xa0 };
+static SPRD_PLL_WITH_ITABLE_K_FVCO(gpll_clk, "gpll", "gpll-gate", 0x4040009c,
+ regs_gpll, itable1, f_gpll, 200,
+ 1000, 1000, 1, 600000000);
+
+static const struct clk_bit_field const f_cppll[PLL_FACT_MAX] = {
+ { .shift = 17, .width = 1 }, /* lock_done */
+ { .shift = 15, .width = 1 }, /* div_s */
+ { .shift = 14, .width = 1 }, /* mod_en */
+ { .shift = 13, .width = 1 }, /* sdm_en */
+ { .shift = 0, .width = 0 }, /* refin */
+ { .shift = 8, .width = 2 }, /* ibias */
+ { .shift = 0, .width = 7 }, /* n */
+ { .shift = 57, .width = 7 }, /* nint */
+ { .shift = 32, .width = 23}, /* kint */
+ { .shift = 0, .width = 0 }, /* prediv */
+ { .shift = 0, .width = 0 }, /* postdiv */
+};
+static const u32 const regs_cppll[3] = { 2, 0xc4, 0xc8 };
+static SPRD_PLL_WITH_ITABLE_1K(cppll_clk, "cppll", "cppll-gate", 0x404000c4,
+ regs_cppll, itable1, f_cppll, 200);
+
+static const struct clk_bit_field const f_ltepll[PLL_FACT_MAX] = {
+ { .shift = 31, .width = 1 }, /* lock_done */
+ { .shift = 27, .width = 1 }, /* div_s */
+ { .shift = 26, .width = 1 }, /* mod_en */
+ { .shift = 25, .width = 1 }, /* sdm_en */
+ { .shift = 0, .width = 0 }, /* refin */
+ { .shift = 20, .width = 2 }, /* ibias */
+ { .shift = 0, .width = 7 }, /* n */
+ { .shift = 57, .width = 7 }, /* nint */
+ { .shift = 32, .width = 23}, /* kint */
+ { .shift = 0, .width = 0 }, /* prediv */
+ { .shift = 0, .width = 0 }, /* postdiv */
+};
+static const u32 const regs_ltepll0[3] = { 2, 0x64, 0x68 };
+static SPRD_PLL_WITH_ITABLE_1K(ltepll0_clk, "ltepll0", "ltepll0-gate",
+ 0x40400064, regs_ltepll0, itable1,
+ f_ltepll, 200);
+static const u32 const regs_ltepll1[3] = { 2, 0x6c, 0x70 };
+static SPRD_PLL_WITH_ITABLE_1K(ltepll1_clk, "ltepll1", "ltepll1-gate",
+ 0x4040006c, regs_ltepll1, itable1,
+ f_ltepll, 200);
+
+static const struct clk_bit_field const f_twpll[PLL_FACT_MAX] = {
+ { .shift = 21, .width = 1 }, /* lock_done */
+ { .shift = 20, .width = 1 }, /* div_s */
+ { .shift = 19, .width = 1 }, /* mod_en */
+ { .shift = 18, .width = 1 }, /* sdm_en */
+ { .shift = 0, .width = 0 }, /* refin */
+ { .shift = 13, .width = 2 }, /* ibias */
+ { .shift = 0, .width = 7 }, /* n */
+ { .shift = 57, .width = 7 }, /* nint */
+ { .shift = 32, .width = 23}, /* kint */
+ { .shift = 0, .width = 0 }, /* prediv */
+ { .shift = 0, .width = 0 }, /* postdiv */
+};
+static const u32 const regs_twpll[3] = { 2, 0x5c, 0x60 };
+static SPRD_PLL_WITH_ITABLE_1K(twpll_clk, "twpll", "twpll-gate", 0x4040005c,
+ regs_twpll, itable2, f_twpll, 200);
+
+static CLK_FIXED_FACTOR(gpll_42m5, "gpll-42m5", "gpll", 20, 1, 0);
+static CLK_FIXED_FACTOR(twpll_768m, "twpll-768m", "twpll", 2, 1, 0);
+static CLK_FIXED_FACTOR(twpll_384m, "twpll-384m", "twpll", 4, 1, 0);
+static CLK_FIXED_FACTOR(twpll_192m, "twpll-192m", "twpll", 8, 1, 0);
+static CLK_FIXED_FACTOR(twpll_96m, "twpll-96m", "twpll", 16, 1, 0);
+static CLK_FIXED_FACTOR(twpll_48m, "twpll-48m", "twpll", 32, 1, 0);
+static CLK_FIXED_FACTOR(twpll_24m, "twpll-24m", "twpll", 64, 1, 0);
+static CLK_FIXED_FACTOR(twpll_12m, "twpll-12m", "twpll", 128, 1, 0);
+static CLK_FIXED_FACTOR(twpll_512m, "twpll-512m", "twpll", 3, 1, 0);
+static CLK_FIXED_FACTOR(twpll_256m, "twpll-256m", "twpll", 6, 1, 0);
+static CLK_FIXED_FACTOR(twpll_128m, "twpll-128m", "twpll", 12, 1, 0);
+static CLK_FIXED_FACTOR(twpll_64m, "twpll-64m", "twpll", 24, 1, 0);
+static CLK_FIXED_FACTOR(twpll_307m2, "twpll-307m2", "twpll", 5, 1, 0);
+static CLK_FIXED_FACTOR(twpll_153m6, "twpll-153m6", "twpll", 10, 1, 0);
+static CLK_FIXED_FACTOR(twpll_76m8, "twpll-76m8", "twpll", 20, 1, 0);
+static CLK_FIXED_FACTOR(twpll_51m2, "twpll-51m2", "twpll", 30, 1, 0);
+static CLK_FIXED_FACTOR(twpll_38m4, "twpll-38m4", "twpll", 40, 1, 0);
+static CLK_FIXED_FACTOR(twpll_19m2, "twpll-19m2", "twpll", 80, 1, 0);
+static CLK_FIXED_FACTOR(l0_614m4, "l0-614m4", "ltepll0", 2, 1, 0);
+static CLK_FIXED_FACTOR(l0_409m6, "l0-409m6", "ltepll0", 3, 1, 0);
+static CLK_FIXED_FACTOR(l0_38m, "l0-38m", "ltepll0", 32, 1, 0);
+static CLK_FIXED_FACTOR(l1_38m, "l1-38m", "ltepll1", 32, 1, 0);
+static CLK_FIXED_FACTOR(rpll0_192m, "rpll0-192m", "rpll0", 6, 1, 0);
+static CLK_FIXED_FACTOR(rpll0_96m, "rpll0-96m", "rpll0", 12, 1, 0);
+static CLK_FIXED_FACTOR(rpll0_48m, "rpll0-48m", "rpll0", 24, 1, 0);
+static CLK_FIXED_FACTOR(rpll1_468m, "rpll1-468m", "rpll1", 2, 1, 0);
+static CLK_FIXED_FACTOR(rpll1_192m, "rpll1-192m", "rpll1", 6, 1, 0);
+static CLK_FIXED_FACTOR(rpll1_96m, "rpll1-96m", "rpll1", 12, 1, 0);
+static CLK_FIXED_FACTOR(rpll1_64m, "rpll1-64m", "rpll1", 18, 1, 0);
+static CLK_FIXED_FACTOR(rpll1_48m, "rpll1-48m", "rpll1", 24, 1, 0);
+static CLK_FIXED_FACTOR(dpll0_50m, "dpll0-50m", "dpll0", 16, 1, 0);
+static CLK_FIXED_FACTOR(dpll1_50m, "dpll1-50m", "dpll1", 16, 1, 0);
+static CLK_FIXED_FACTOR(cppll_50m, "cppll-50m", "cppll", 18, 1, 0);
+static CLK_FIXED_FACTOR(m0_39m, "m0-39m", "mpll0", 32, 1, 0);
+static CLK_FIXED_FACTOR(m1_63m, "m1-63m", "mpll1", 32, 1, 0);
+
+static const char * const aon_apb_parents[] = { "rco-25m", "ext-26m",
+ "ext-rco-100m", "twpll-96m",
+ "twpll-128m",
+ "twpll-153m6" };
+static SPRD_COMP_CLK(aon_apb, "aon-apb", aon_apb_parents, 0x402d0230,
+ 0, 0, 3, 8, 2, 0);
+
+static const char * const aux_parents[] = { "ext-32k", "rpll0-26m",
+ "rpll1-26m", "ext-26m",
+ "cppll-50m", "rco-25m",
+ "dpll0-50m", "dpll1-50m",
+ "gpll-42m5", "twpll-48m",
+ "m0-39m", "m1-63m",
+ "l0-38m", "l1-38m" };
+
+static SPRD_COMP_CLK(aux0_clk, "aux0", aux_parents, 0x402d0238,
+ 0, 0, 5, 8, 4, 0);
+static SPRD_COMP_CLK(aux1_clk, "aux1", aux_parents, 0x402d023c,
+ 0, 0, 5, 8, 4, 0);
+static SPRD_COMP_CLK(aux2_clk, "aux2", aux_parents, 0x402d0240,
+ 0, 0, 5, 8, 4, 0);
+static SPRD_COMP_CLK(probe_clk, "probe", aux_parents, 0x402d0244,
+ 0, 0, 5, 8, 4, 0);
+
+static const char * const sp_ahb_parents[] = { "rco-4m", "ext-26m",
+ "ext-rco-100m", "twpll-96m",
+ "twpll-128m",
+ "twpll-153m6" };
+static SPRD_COMP_CLK(sp_ahb, "sp-ahb", sp_ahb_parents, 0x402d02d0,
+ 0, 0, 3, 8, 2, 0);
+
+static const char * const cci_parents[] = { "ext-26m", "twpll-384m",
+ "l0-614m4", "twpll-768m" };
+static SPRD_COMP_CLK(cci_clk, "cci", cci_parents, 0x402d0304,
+ 0, 0, 2, 8, 2, 0);
+static SPRD_COMP_CLK(gic_clk, "gic", cci_parents, 0x402d0304,
+ 0, 0, 2, 8, 2, 0);
+static SPRD_COMP_CLK(cssys_clk, "cssys", cci_parents, 0x402d0310,
+ 0, 0, 2, 8, 2, 0);
+
+static const char * const sdio_2x_parents[] = { "fac-1m", "ext-26m",
+ "twpll-307m2", "twpll-384m",
+ "l0-409m6" };
+static SPRD_COMP_CLK(sdio0_2x, "sdio0-2x", sdio_2x_parents, 0x402d0328,
+ 0, 0, 3, 8, 4, 0);
+static SPRD_COMP_CLK(sdio1_2x, "sdio1-2x", sdio_2x_parents, 0x402d0330,
+ 0, 0, 3, 8, 4, 0);
+static SPRD_COMP_CLK(sdio2_2x, "sdio2-2x", sdio_2x_parents, 0x402d0338,
+ 0, 0, 3, 8, 4, 0);
+static SPRD_COMP_CLK(emmc_2x, "emmc-2x", sdio_2x_parents, 0x402d0340,
+ 0, 0, 3, 8, 4, 0);
+
+static const char * const uart_parents[] = { "ext-26m", "twpll-48m",
+ "twpll-51m2", "twpll-96m" };
+static SPRD_COMP_CLK(uart0_clk, "uart0", uart_parents, 0x20000030,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(uart1_clk, "uart1", uart_parents, 0x20000034,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(uart2_clk, "uart2", uart_parents, 0x20000038,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(uart3_clk, "uart3", uart_parents, 0x2000003c,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(uart4_clk, "uart4", uart_parents, 0x20000040,
+ 0, 0, 2, 8, 3, 0);
+
+static const char * const i2c_parents[] = { "ext-26m", "twpll-48m",
+ "twpll-51m2", "twpll-153m6" };
+static SPRD_COMP_CLK(i2c0_clk, "i2c0", i2c_parents, 0x20000044,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(i2c1_clk, "i2c1", i2c_parents, 0x20000048,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(i2c2_clk, "i2c2", i2c_parents, 0x2000004c,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(i2c3_clk, "i2c3", i2c_parents, 0x20000050,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(i2c4_clk, "i2c4", i2c_parents, 0x20000054,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(i2c5_clk, "i2c5", i2c_parents, 0x20000058,
+ 0, 0, 2, 8, 3, 0);
+
+static const char * const spi_parents[] = { "ext-26m", "twpll-128m",
+ "twpll-153m6", "twpll-192m" };
+static SPRD_COMP_CLK(spi0_clk, "spi0", spi_parents, 0x2000005c,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(spi1_clk, "spi1", spi_parents, 0x20000060,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(spi2_clk, "spi2", spi_parents, 0x20000064,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(spi3_clk, "spi3", spi_parents, 0x20000068,
+ 0, 0, 2, 8, 3, 0);
+
+static const char * const iis_parents[] = { "ext-26m",
+ "twpll-128m",
+ "twpll-153m6" };
+static SPRD_COMP_CLK(iis0_clk, "iis0", iis_parents, 0x2000006c,
+ 0, 0, 2, 8, 6, 0);
+static SPRD_COMP_CLK(iis1_clk, "iis1", iis_parents, 0x20000070,
+ 0, 0, 2, 8, 6, 0);
+static SPRD_COMP_CLK(iis2_clk, "iis2", iis_parents, 0x20000074,
+ 0, 0, 2, 8, 6, 0);
+static SPRD_COMP_CLK(iis3_clk, "iis3", iis_parents, 0x20000078,
+ 0, 0, 2, 8, 6, 0);
+
+static const u8 mcu_table[] = { 0, 1, 2, 3, 4, 8 };
+static const char * const lit_mcu_parents[] = { "ext-26m", "twpll-512m",
+ "twpll-768m", "ltepll0",
+ "twpll", "mpll0" };
+static SPRD_COMP_CLK(lit_mcu, "lit-mcu", lit_mcu_parents, 0x40880020,
+ mcu_table, 0, 4, 4, 3, 0);
+
+static const char * const big_mcu_parents[] = { "ext-26m", "twpll-512m",
+ "twpll-768m", "ltepll0",
+ "twpll", "mpll1" };
+static SPRD_COMP_CLK(big_mcu, "big-mcu", big_mcu_parents, 0x40880024,
+ mcu_table, 0, 4, 4, 3, 0);
+
+static const char * const gpu_parents[] = { "twpll-512m",
+ "twpll-768m",
+ "gpll" };
+static SPRD_COMP_CLK(gpu_clk, "gpu", gpu_parents, 0x60200020,
+ 0, 0, 2, 8, 4, 0);
+
+static const char * const vsp_parents[] = { "twpll-76m8", "twpll-128m",
+ "twpll-256m", "twpll-307m2",
+ "twpll-384m" };
+static SPRD_COMP_CLK(vsp_clk, "vsp", vsp_parents, 0x61000024,
+ 0, 0, 3, 8, 2, 0);
+
+static const char * const dispc_parents[] = { "twpll-76m8", "twpll-128m",
+ "twpll-256m", "twpll-307m2" };
+static SPRD_COMP_CLK(vsp_enc, "vsp-enc", dispc_parents, 0x61000028,
+ 0, 0, 2, 8, 2, 0);
+static SPRD_COMP_CLK(dispc0_dpi, "dispc0-dpi", dispc_parents, 0x63000034,
+ 0, 0, 2, 8, 2, 0);
+static SPRD_COMP_CLK(dispc1_dpi, "dispc1-dpi", dispc_parents, 0x63000040,
+ 0, 0, 2, 8, 2, 0);
+
+static const char * const sensor_parents[] = { "ext-26m", "twpll-48m",
+ "twpll-76m8", "twpll-96m" };
+static SPRD_COMP_CLK(sensor0_clk, "sensor0", sensor_parents, 0x62000024,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(sensor1_clk, "sensor1", sensor_parents, 0x62000028,
+ 0, 0, 2, 8, 3, 0);
+static SPRD_COMP_CLK(sensor2_clk, "sensor2", sensor_parents, 0x6200002c,
+ 0, 0, 2, 8, 3, 0);
+
+static SPRD_DIV_CLK(sdio0_1x, "sdio0-1x", "sdio0-2x", 0x402d032c,
+ 8, 1, 0);
+static SPRD_DIV_CLK(sdio1_1x, "sdio1-1x", "sdio1-2x", 0x402d0334,
+ 8, 1, 0);
+static SPRD_DIV_CLK(sdio2_1x, "sdio2-1x", "sdio2-2x", 0x402d033c,
+ 8, 1, 0);
+static SPRD_DIV_CLK(emmc_1x, "emmc-1x", "emmc-2x", 0x402d0344,
+ 8, 1, 0);
+
+#define SC9860_MUX_FLAG \
+ (CLK_GET_RATE_NOCACHE | CLK_SET_RATE_NO_REPARENT)
+
+static const char * const adi_parents[] = { "rco-4m", "ext-26m",
+ "rco-25m", "twpll-38m4",
+ "twpll-51m2" };
+static SPRD_MUX_CLK(adi_clk, "adi", adi_parents, NULL, 0x402d0234,
+ 0, 3, SC9860_MUX_FLAG);
+
+static const char * const pwm_parents[] = { "ext-32k", "ext-26m",
+ "rco-4m", "rco-25m",
+ "twpll-48m" };
+static SPRD_MUX_CLK(pwm0_clk, "pwm0", pwm_parents, NULL, 0x402d0248,
+ 0, 3, SC9860_MUX_FLAG);
+static SPRD_MUX_CLK(pwm1_clk, "pwm1", pwm_parents, NULL, 0x402d024c,
+ 0, 3, SC9860_MUX_FLAG);
+static SPRD_MUX_CLK(pwm2_clk, "pwm2", pwm_parents, NULL, 0x402d0250,
+ 0, 3, SC9860_MUX_FLAG);
+static SPRD_MUX_CLK(pwm3_clk, "pwm3", pwm_parents, NULL, 0x402d0254,
+ 0, 3, SC9860_MUX_FLAG);
+
+static const char * const efuse_parents[] = { "rco-25m", "ext-26m" };
+static SPRD_MUX_CLK(efuse_clk, "efuse", efuse_parents, NULL, 0x402d0258,
+ 0, 1, SC9860_MUX_FLAG);
+
+static const char * const cm3_uart_parents[] = { "rco-4m", "ext-26m",
+ "rco-100m", "twpll-48m",
+ "twpll-51m2", "twpll-96m",
+ "twpll-128m" };
+static SPRD_MUX_CLK(cm3_uart0, "cm3-uart0", cm3_uart_parents, NULL, 0x402d025c,
+ 0, 3, SC9860_MUX_FLAG);
+static SPRD_MUX_CLK(cm3_uart1, "cm3-uart1", cm3_uart_parents, NULL, 0x402d0260,
+ 0, 3, SC9860_MUX_FLAG);
+
+static const char * const thm_parents[] = { "ext-32k", "fac-250k" };
+static SPRD_MUX_CLK(thm_clk, "thm", thm_parents, NULL, 0x402d0270,
+ 0, 1, SC9860_MUX_FLAG);
+
+static const char * const cm3_i2c_parents[] = { "rco-4m",
+ "ext-26m",
+ "rco-100m",
+ "twpll-48m",
+ "twpll-51m2",
+ "twpll-153m6" };
+static SPRD_MUX_CLK(cm3_i2c0, "cm3-i2c0", cm3_i2c_parents, NULL, 0x402d0274,
+ 0, 3, SC9860_MUX_FLAG);
+static SPRD_MUX_CLK(cm3_i2c1, "cm3-i2c1", cm3_i2c_parents, NULL, 0x402d0278,
+ 0, 3, SC9860_MUX_FLAG);
+static SPRD_MUX_CLK(aon_i2c, "aon-i2c", cm3_i2c_parents, NULL, 0x402d0280,
+ 0, 3, SC9860_MUX_FLAG);
+
+static const char * const cm4_spi_parents[] = { "ext-26m", "twpll-96m",
+ "rco-100m", "twpll-128m",
+ "twpll-153m6", "twpll-192m" };
+static SPRD_MUX_CLK(cm4_spi, "cm4-spi", cm4_spi_parents, NULL, 0x402d027c,
+ 0, 3, SC9860_MUX_FLAG);
+
+static SPRD_MUX_CLK(avs_clk, "avs", uart_parents, NULL, 0x402d0284,
+ 0, 2, SC9860_MUX_FLAG);
+
+static const char * const ca53_dap_parents[] = { "ext-26m", "rco-4m",
+ "rco-100m", "twpll-76m8",
+ "twpll-128m", "twpll-153m6" };
+static SPRD_MUX_CLK(ca53_dap, "ca53-dap", ca53_dap_parents, NULL, 0x402d0288,
+ 0, 3, SC9860_MUX_FLAG);
+
+static const char * const ca53_ts_parents[] = { "ext-32k", "ext-26m",
+ "clk-twpll-128m",
+ "clk-twpll-153m6" };
+static SPRD_MUX_CLK(ca53_ts, "ca53-ts", ca53_ts_parents, NULL, 0x402d0290,
+ 0, 2, SC9860_MUX_FLAG);
+
+static const char * const djtag_tck_parents[] = { "rco-4m", "ext-26m" };
+static SPRD_MUX_CLK(djtag_tck, "djtag-tck", djtag_tck_parents, NULL,
+ 0x402d02c8, 0, 1, SC9860_MUX_FLAG);
+
+static const char * const pmu_parents[] = { "ext-32k", "rco-4m", "clk-4m" };
+static SPRD_MUX_CLK(pmu_clk, "pmu", pmu_parents, NULL, 0x402d02e0,
+ 0, 2, SC9860_MUX_FLAG);
+
+static const char * const pmu_26m_parents[] = { "rco-25m", "ext-26m" };
+static SPRD_MUX_CLK(pmu_26m, "pmu-26m", pmu_26m_parents, NULL,
+ 0x402d02e4, 0, 1, SC9860_MUX_FLAG);
+
+static const char * const debounce_parents[] = { "ext-32k", "rco-4m",
+ "rco-25m", "ext-26m" };
+static SPRD_MUX_CLK(debounce_clk, "debounce", debounce_parents, NULL,
+ 0x402d02e8, 0, 2, SC9860_MUX_FLAG);
+
+static const char * const otg2_ref_parents[] = { "twpll-12m", "twpll-24m" };
+static SPRD_MUX_CLK(otg2_ref, "otg2-ref", otg2_ref_parents, NULL,
+ 0x402d02f4, 0, 1, SC9860_MUX_FLAG);
+
+static const char * const usb3_ref_parents[] = { "twpll-24m", "twpll-19m2",
+ "twpll-48m" };
+static SPRD_MUX_CLK(usb3_ref, "usb3-ref", usb3_ref_parents, NULL,
+ 0x402d02f8, 0, 2, SC9860_MUX_FLAG);
+
+static const char * const ap_axi_parents[] = { "ext-26m", "twpll-76m8",
+ "twpll-128m", "twpll-256m" };
+static SPRD_MUX_CLK(ap_axi, "ap-axi", ap_axi_parents, NULL,
+ 0x402d0324, 0, 2, SC9860_MUX_FLAG);
+
+static const char * const ap_apb_parents[] = { "ext-26m", "twpll-64m",
+ "twpll-96m", "twpll-128m" };
+static SPRD_MUX_CLK(ap_apb, "ap-apb", ap_apb_parents, NULL,
+ 0x20000020, 0, 1, SC9860_MUX_FLAG);
+
+static const char * const ahb_parents[] = { "ext-26m", "twpll-96m",
+ "twpll-128m", "twpll-153m6" };
+static SPRD_MUX_CLK(ahb_vsp, "ahb-vsp", ahb_parents, NULL,
+ 0x61000020, 0, 2, SC9860_MUX_FLAG);
+static SPRD_MUX_CLK(ahb_disp, "ahb-disp", ahb_parents, NULL,
+ 0x63000020, 0, 2, SC9860_MUX_FLAG);
+static SPRD_MUX_CLK(ahb_cam, "ahb-cam", ahb_parents, NULL,
+ 0x62000020, 0, 2, SC9860_MUX_FLAG);
+
+static SPRD_GATE_CLK(mipi_csi0_eb, "mipi-csi0-eb", "ahb-cam", 0x6200004c,
+ 0, BIT(16), 0, 0);
+static SPRD_GATE_CLK(mipi_csi1_eb, "mipi-csi1-eb", "ahb-cam", 0x62000050,
+ 0, BIT(16), 0, 0);
+static SPRD_GATE_CLK(usb3_eb, "usb3-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(2), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(usb3_suspend, "usb3-suspend", "ap-axi", 0x20210000,
+ 0x1000, BIT(3), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(usb3_ref_eb, "usb3-ref-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(4), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(dma_eb, "dma-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(5), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(sdio0_eb, "sdio0-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(7), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(sdio1_eb, "sdio1-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(8), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(sdio2_eb, "sdio2-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(9), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(emmc_eb, "emmc-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(10), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(rom_eb, "rom-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(12), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(busmon_eb, "busmon-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(13), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(cc63s_eb, "cc63s-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(22), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(cc63p_eb, "cc63p-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(23), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ce0_eb, "ce0-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(24), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ce1_eb, "ce1-eb", "ap-axi", 0x20210000,
+ 0x1000, BIT(25), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(avs_lit_eb, "avs-lit-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(0), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(avs_big_eb, "avs-big-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(1), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ap_intc5_eb, "ap-intc5-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(2), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(gpio_eb, "gpio-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(3), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(pwm0_eb, "pwm0-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(4), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(pwm1_eb, "pwm1-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(5), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(pwm2_eb, "pwm2-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(6), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(pwm3_eb, "pwm3-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(7), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(kpd_eb, "kpd-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(8), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(aon_sys_eb, "aon-sys-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(9), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ap_sys_eb, "ap-sys-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(10), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(aon_tmr_eb, "aon-tmr-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(11), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ap_tmr0_eb, "ap-tmr0-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(12), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(efuse_eb, "efuse-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(13), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(eic_eb, "eic-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(14), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(pub1_reg_eb, "pub1-reg-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(15), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(adi_eb, "adi-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(16), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ap_intc0_eb, "ap-intc0-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(17), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ap_intc1_eb, "ap-intc1-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(18), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ap_intc2_eb, "ap-intc2-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(19), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ap_intc3_eb, "ap-intc3-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(20), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ap_intc4_eb, "ap-intc4-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(21), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(splk_eb, "splk-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(22), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(mspi_eb, "mspi-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(23), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(pub0_reg_eb, "pub0-reg-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(24), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(pin_eb, "pin-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(25), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(aon_ckg_eb, "aon-ckg-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(26), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(gpu_eb, "gpu-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(27), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(apcpu_ts0_eb, "apcpu-ts0-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(28), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(apcpu_ts1_eb, "apcpu-ts1-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(29), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(dap_eb, "dap-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(30), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(i2c_eb, "i2c-eb", "aon-apb", 0x402e0000,
+ 0x1000, BIT(31), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(pmu_eb, "pmu-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(0), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(thm_eb, "thm-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(1), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(aux0_eb, "aux0-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(2), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(aux1_eb, "aux1-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(3), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(aux2_eb, "aux2-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(4), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(probe_eb, "probe-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(5), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(gpu0_avs_eb, "gpu0-avs-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(6), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(gpu1_avs_eb, "gpu1-avs-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(7), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(apcpu_wdg_eb, "apcpu-wdg-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(8), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ap_tmr1_eb, "ap-tmr1-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(9), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ap_tmr2_eb, "ap-tmr2-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(10), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(disp_emc_eb, "disp-emc-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(11), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(zip_emc_eb, "zip-emc-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(12), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(gsp_emc_eb, "gsp-emc-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(13), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(osc_aon_eb, "osc-aon-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(14), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(lvds_trx_eb, "lvds-trx-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(15), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(lvds_tcxo_eb, "lvds-tcxo-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(16), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(mdar_eb, "mdar-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(17), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(rtc4m0_cal_eb, "rtc4m0-cal-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(18), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(rct100m_cal_eb, "rct100m-cal-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(19), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(djtag_eb, "djtag-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(20), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(mbox_eb, "mbox-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(21), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(aon_dma_eb, "aon-dma-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(22), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(dbg_emc_eb, "dbg-emc-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(23), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(lvds_pll_div_en, "lvds-pll-div-en", "aon-apb", 0x402e0004,
+ 0x1000, BIT(24), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(def_eb, "def-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(25), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(aon_apb_rsv0, "aon-apb-rsv0", "aon-apb", 0x402e0004,
+ 0x1000, BIT(26), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(orp_jtag_eb, "orp-jtag-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(27), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(vsp_eb, "vsp-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(28), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(cam_eb, "cam-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(29), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(disp_eb, "disp-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(30), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(dbg_axi_if_eb, "dbg-axi-if-eb", "aon-apb", 0x402e0004,
+ 0x1000, BIT(31), CLK_IGNORE_UNUSED, 0);
+
+static SPRD_GATE_CLK(sdio0_2x_en, "sdio0-2x-en", "aon-apb", 0x402e013c,
+ 0x1000, BIT(2), 0, 0);
+static SPRD_GATE_CLK(sdio1_2x_en, "sdio1-2x-en", "aon-apb", 0x402e013c,
+ 0x1000, BIT(4), 0, 0);
+static SPRD_GATE_CLK(sdio2_2x_en, "sdio2-2x-en", "aon-apb", 0x402e013c,
+ 0x1000, BIT(6), 0, 0);
+static SPRD_GATE_CLK(emmc_2x_en, "emmc-2x-en", "aon-apb", 0x402e013c,
+ 0x1000, BIT(9), 0, 0);
+
+static SPRD_GATE_CLK(agcp_iis0_eb, "agcp-iis0-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(0), 0, 0);
+static SPRD_GATE_CLK(agcp_iis1_eb, "agcp-iis1-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(1), 0, 0);
+static SPRD_GATE_CLK(agcp_iis2_eb, "agcp-iis2-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(2), 0, 0);
+static SPRD_GATE_CLK(agcp_iis3_eb, "agcp-iis3-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(3), 0, 0);
+static SPRD_GATE_CLK(agcp_uart_eb, "agcp-uart-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(4), 0, 0);
+static SPRD_GATE_CLK(agcp_dmacp_eb, "agcp-dmacp-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(5), 0, 0);
+static SPRD_GATE_CLK(agcp_dmaap_eb, "agcp-dmaap-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(6), 0, 0);
+static SPRD_GATE_CLK(agcp_arc48k_eb, "agcp-arc48k-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(10), 0, 0);
+static SPRD_GATE_CLK(agcp_src44p1k_eb, "agcp-src44p1k-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(11), 0, 0);
+static SPRD_GATE_CLK(agcp_mcdt_eb, "agcp-mcdt-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(12), 0, 0);
+static SPRD_GATE_CLK(agcp_vbcifd_eb, "agcp-vbcifd-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(13), 0, 0);
+static SPRD_GATE_CLK(agcp_vbc_eb, "agcp-vbc-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(14), 0, 0);
+static SPRD_GATE_CLK(agcp_spinlock_eb, "agcp-spinlock-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(15), 0, 0);
+static SPRD_GATE_CLK(agcp_icu_eb, "agcp-icu-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(16), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(agcp_ap_ashb_eb, "agcp-ap-ashb-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(17), 0, 0);
+static SPRD_GATE_CLK(agcp_cp_ashb_eb, "agcp-cp-ashb-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(18), 0, 0);
+static SPRD_GATE_CLK(agcp_aud_eb, "agcp-aud-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(19), 0, 0);
+static SPRD_GATE_CLK(agcp_audif_eb, "agcp-audif-eb", "aon-apb",
+ 0x415e0000, 0x100, BIT(20), 0, 0);
+
+static SPRD_GATE_CLK(vsp_dec_eb, "vsp-dec-eb", "ahb_vsp", 0x61100000,
+ 0x1000, BIT(0), 0, 0);
+static SPRD_GATE_CLK(vsp_ckg_eb, "vsp-ckg-eb", "ahb_vsp", 0x61100000,
+ 0x1000, BIT(1), 0, 0);
+static SPRD_GATE_CLK(vsp_mmu_eb, "vsp-mmu-eb", "ahb_vsp", 0x61100000,
+ 0x1000, BIT(2), 0, 0);
+static SPRD_GATE_CLK(vsp_enc_eb, "vsp-enc-eb", "ahb_vsp", 0x61100000,
+ 0x1000, BIT(3), 0, 0);
+static SPRD_GATE_CLK(vpp_eb, "vpp-eb", "ahb_vsp", 0x61100000,
+ 0x1000, BIT(4), 0, 0);
+static SPRD_GATE_CLK(vsp_26m_eb, "vsp-26m-eb", "ahb_vsp", 0x61100000,
+ 0x1000, BIT(5), 0, 0);
+
+static SPRD_GATE_CLK(vsp_axi_gate, "vsp-axi-gate", "ahb_vsp", 0x61100008,
+ 0, BIT(0), 0, 0);
+static SPRD_GATE_CLK(vsp_enc_gate, "vsp-enc-gate", "ahb_vsp", 0x61100008,
+ 0, BIT(1), 0, 0);
+static SPRD_GATE_CLK(vpp_axi_gate, "vpp-axi-gate", "ahb_vsp", 0x61100008,
+ 0, BIT(2), 0, 0);
+static SPRD_GATE_CLK(vsp_bm_gate, "vsp-bm-gate", "ahb_vsp", 0x61100008,
+ 0, BIT(8), 0, 0);
+static SPRD_GATE_CLK(vsp_enc_bm_gate, "vsp-enc-bm-gate", "ahb_vsp", 0x61100008,
+ 0, BIT(9), 0, 0);
+static SPRD_GATE_CLK(vpp_bm_gate, "vpp-bm-gate", "ahb_vsp", 0x61100008,
+ 0, BIT(10), 0, 0);
+static SPRD_GATE_CLK(dcam0_eb, "dcam0-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(0), 0, 0);
+static SPRD_GATE_CLK(dcam1_eb, "dcam1-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(1), 0, 0);
+static SPRD_GATE_CLK(isp0_eb, "isp0-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(2), 0, 0);
+static SPRD_GATE_CLK(csi0_eb, "csi0-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(3), 0, 0);
+static SPRD_GATE_CLK(csi1_eb, "csi1-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(4), 0, 0);
+static SPRD_GATE_CLK(jpg0_eb, "jpg0-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(5), 0, 0);
+static SPRD_GATE_CLK(jpg1_eb, "jpg1-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(6), 0, 0);
+static SPRD_GATE_CLK(cam_ckg_eb, "cam-ckg-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(7), 0, 0);
+static SPRD_GATE_CLK(cam_mmu_eb, "cam-mmu-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(8), 0, 0);
+static SPRD_GATE_CLK(isp1_eb, "isp1-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(9), 0, 0);
+static SPRD_GATE_CLK(cpp_eb, "cpp-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(10), 0, 0);
+static SPRD_GATE_CLK(mmu_pf_eb, "mmu-pf-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(11), 0, 0);
+static SPRD_GATE_CLK(isp2_eb, "isp2-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(12), 0, 0);
+static SPRD_GATE_CLK(dcam2isp_if_eb, "dcam2isp-if-eb", "ahb_cam", 0x62100000,
+ 0x1000, BIT(13), 0, 0);
+static SPRD_GATE_CLK(isp2dcam_if_eb, "isp2dcam-if-eb", "ahb_cam", 0x62100000,
+ 0x1000, BIT(14), 0, 0);
+static SPRD_GATE_CLK(isp_lclk_eb, "isp-lclk-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(15), 0, 0);
+static SPRD_GATE_CLK(isp_iclk_eb, "isp-iclk-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(16), 0, 0);
+static SPRD_GATE_CLK(isp_mclk_eb, "isp-mclk-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(17), 0, 0);
+static SPRD_GATE_CLK(isp_pclk_eb, "isp-pclk-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(18), 0, 0);
+static SPRD_GATE_CLK(isp_isp2dcam_eb, "isp-isp2dcam-eb", "ahb_cam", 0x62100000,
+ 0x1000, BIT(19), 0, 0);
+static SPRD_GATE_CLK(dcam0_if_eb, "dcam0-if-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(20), 0, 0);
+static SPRD_GATE_CLK(clk26m_if_eb, "clk26m-if-eb", "ahb-cam", 0x62100000,
+ 0x1000, BIT(21), 0, 0);
+
+static SPRD_GATE_CLK(cphy0_gate, "cphy0-gate", "ahb-cam", 0x62100008,
+ 0, BIT(0), 0, 0);
+static SPRD_GATE_CLK(mipi_csi0_gate, "mipi-csi0-gate", "ahb_cam", 0x62100008,
+ 0, BIT(1), 0, 0);
+static SPRD_GATE_CLK(cphy1_gate, "cphy1-gate", "ahb-cam", 0x62100008,
+ 0, BIT(2), 0, 0);
+static SPRD_GATE_CLK(mipi_csi1, "mipi-csi1", "ahb-cam", 0x62100008,
+ 0, BIT(3), 0, 0);
+static SPRD_GATE_CLK(dcam0_axi_gate, "dcam0-axi-gate", "ahb_cam", 0x62100008,
+ 0, BIT(4), 0, 0);
+static SPRD_GATE_CLK(dcam1_axi_gate, "dcam1-axi-gate", "ahb_cam", 0x62100008,
+ 0, BIT(5), 0, 0);
+static SPRD_GATE_CLK(sensor0_gate, "sensor0-gate", "ahb-cam", 0x62100008,
+ 0, BIT(6), 0, 0);
+static SPRD_GATE_CLK(sensor1_gate, "sensor1-gate", "ahb-cam", 0x62100008,
+ 0, BIT(7), 0, 0);
+static SPRD_GATE_CLK(jpg0_axi_gate, "jpg0-axi-gate", "ahb_cam", 0x62100008,
+ 0, BIT(8), 0, 0);
+static SPRD_GATE_CLK(gpg1_axi_gate, "gpg1-axi-gate", "ahb_cam", 0x62100008,
+ 0, BIT(9), 0, 0);
+static SPRD_GATE_CLK(isp0_axi_gate, "isp0-axi-gate", "ahb_cam", 0x62100008,
+ 0, BIT(10), 0, 0);
+static SPRD_GATE_CLK(isp1_axi_gate, "isp1-axi-gate", "ahb_cam", 0x62100008,
+ 0, BIT(11), 0, 0);
+static SPRD_GATE_CLK(isp2_axi_gate, "isp2-axi-gate", "ahb_cam", 0x62100008,
+ 0, BIT(12), 0, 0);
+static SPRD_GATE_CLK(cpp_axi_gate, "cpp-axi-gate", "ahb-cam", 0x62100008,
+ 0, BIT(13), 0, 0);
+static SPRD_GATE_CLK(d0_if_axi_gate, "d0-if-axi-gate", "ahb_cam", 0x62100008,
+ 0, BIT(14), 0, 0);
+static SPRD_GATE_CLK(d2i_if_axi_gate, "d2i-if-axi-gate", "ahb_cam", 0x62100008,
+ 0, BIT(15), 0, 0);
+static SPRD_GATE_CLK(i2d_if_axi_gate, "i2d-if-axi-gate", "ahb_cam", 0x62100008,
+ 0, BIT(16), 0, 0);
+static SPRD_GATE_CLK(spare_axi_gate, "spare-axi-gate", "ahb_cam", 0x62100008,
+ 0, BIT(17), 0, 0);
+static SPRD_GATE_CLK(sensor2_gate, "sensor2-gate", "ahb-cam", 0x62100008,
+ 0, BIT(18), 0, 0);
+
+static SPRD_GATE_CLK(d0if_in_d_en, "d0if-in-d-en", "ahb-cam", 0x62100028,
+ 0x1000, BIT(0), 0, 0);
+static SPRD_GATE_CLK(d1if_in_d_en, "d1if-in-d-en", "ahb-cam", 0x62100028,
+ 0x1000, BIT(1), 0, 0);
+static SPRD_GATE_CLK(d0if_in_d2i_en, "d0if-in-d2i-en", "ahb_cam", 0x62100028,
+ 0x1000, BIT(2), 0, 0);
+static SPRD_GATE_CLK(d1if_in_d2i_en, "d1if-in-d2i-en", "ahb_cam", 0x62100028,
+ 0x1000, BIT(3), 0, 0);
+static SPRD_GATE_CLK(ia_in_d2i_en, "ia-in-d2i-en", "ahb-cam", 0x62100028,
+ 0x1000, BIT(4), 0, 0);
+static SPRD_GATE_CLK(ib_in_d2i_en, "ib-in-d2i-en", "ahb-cam", 0x62100028,
+ 0x1000, BIT(5), 0, 0);
+static SPRD_GATE_CLK(ic_in_d2i_en, "ic-in-d2i-en", "ahb-cam", 0x62100028,
+ 0x1000, BIT(6), 0, 0);
+static SPRD_GATE_CLK(ia_in_i_en, "ia-in-i-en", "ahb-cam", 0x62100028,
+ 0x1000, BIT(7), 0, 0);
+static SPRD_GATE_CLK(ib_in_i_en, "ib-in-i-en", "ahb-cam", 0x62100028,
+ 0x1000, BIT(8), 0, 0);
+static SPRD_GATE_CLK(ic_in_i_en, "ic-in-i-en", "ahb-cam", 0x62100028,
+ 0x1000, BIT(9), 0, 0);
+
+static SPRD_GATE_CLK(dispc0_eb, "dispc0-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(0), 0, 0);
+static SPRD_GATE_CLK(dispc1_eb, "dispc1-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(1), 0, 0);
+static SPRD_GATE_CLK(dispc_mmu_eb, "dispc-mmu-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(2), 0, 0);
+static SPRD_GATE_CLK(gsp0_eb, "gsp0-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(3), 0, 0);
+static SPRD_GATE_CLK(gsp1_eb, "gsp1-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(4), 0, 0);
+static SPRD_GATE_CLK(gsp0_mmu_eb, "gsp0-mmu-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(5), 0, 0);
+static SPRD_GATE_CLK(gsp1_mmu_eb, "gsp1-mmu-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(6), 0, 0);
+static SPRD_GATE_CLK(dsi0_eb, "dsi0-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(7), 0, 0);
+static SPRD_GATE_CLK(dsi1_eb, "dsi1-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(8), 0, 0);
+static SPRD_GATE_CLK(disp_ckg_eb, "disp-ckg-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(9), 0, 0);
+static SPRD_GATE_CLK(disp_gpu_eb, "disp-gpu-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(10), 0, 0);
+static SPRD_GATE_CLK(gpu_mtx_eb, "gpu-mtx-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(13), 0, 0);
+static SPRD_GATE_CLK(gsp_mtx_eb, "gsp-mtx-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(14), 0, 0);
+static SPRD_GATE_CLK(tmc_mtx_eb, "tmc-mtx-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(15), 0, 0);
+static SPRD_GATE_CLK(dispc_mtx_eb, "dispc-mtx-eb", "ahb-disp", 0x63100000,
+ 0x1000, BIT(16), 0, 0);
+
+static SPRD_GATE_CLK(dphy0_gate, "dphy0-gate", "ahb-disp", 0x63100008,
+ 0, BIT(0), 0, 0);
+static SPRD_GATE_CLK(dphy1_gate, "dphy1-gate", "ahb-disp", 0x63100008,
+ 0, BIT(1), 0, 0);
+static SPRD_GATE_CLK(gsp0_a_gate, "gsp0-a-gate", "ahb-disp", 0x63100008,
+ 0, BIT(2), 0, 0);
+static SPRD_GATE_CLK(gsp1_a_gate, "gsp1-a-gate", "ahb-disp", 0x63100008,
+ 0, BIT(3), 0, 0);
+static SPRD_GATE_CLK(gsp0_f_gate, "gsp0-f-gate", "ahb-disp", 0x63100008,
+ 0, BIT(4), 0, 0);
+static SPRD_GATE_CLK(gsp1_f_gate, "gsp1-f-gate", "ahb-disp", 0x63100008,
+ 0, BIT(5), 0, 0);
+static SPRD_GATE_CLK(d_mtx_f_gate, "d-mtx-f-gate", "ahb-disp", 0x63100008,
+ 0, BIT(6), 0, 0);
+static SPRD_GATE_CLK(d_mtx_a_gate, "d-mtx-a-gate", "ahb-disp", 0x63100008,
+ 0, BIT(7), 0, 0);
+static SPRD_GATE_CLK(d_noc_f_gate, "d-noc-f-gate", "ahb-disp", 0x63100008,
+ 0, BIT(8), 0, 0);
+static SPRD_GATE_CLK(d_noc_a_gate, "d-noc-a-gate", "ahb-disp", 0x63100008,
+ 0, BIT(9), 0, 0);
+static SPRD_GATE_CLK(gsp_mtx_f_gate, "gsp-mtx-f-gate", "ahb-disp", 0x63100008,
+ 0, BIT(10), 0, 0);
+static SPRD_GATE_CLK(gsp_mtx_a_gate, "gsp-mtx-a-gate", "ahb-disp", 0x63100008,
+ 0, BIT(11), 0, 0);
+static SPRD_GATE_CLK(gsp_noc_f_gate, "gsp-noc-f-gate", "ahb-disp", 0x63100008,
+ 0, BIT(12), 0, 0);
+static SPRD_GATE_CLK(gsp_noc_a_gate, "gsp-noc-a-gate", "ahb-disp", 0x63100008,
+ 0, BIT(13), 0, 0);
+static SPRD_GATE_CLK(dispm0idle_gate, "dispm0idle-gate", "ahb-disp", 0x63100008,
+ 0, BIT(14), 0, 0);
+static SPRD_GATE_CLK(gspm0idle_gate, "gspm0idle-gate", "ahb-disp", 0x63100008,
+ 0, BIT(15), 0, 0);
+static SPRD_GATE_CLK(sim0_eb, "sim0-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(0), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(iis0_eb, "iis0-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(1), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(iis1_eb, "iis1-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(2), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(iis2_eb, "iis2-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(3), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(iis3_eb, "iis3-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(4), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(spi0_eb, "spi0-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(5), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(spi1_eb, "spi1-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(6), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(spi2_eb, "spi2-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(7), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(i2c0_eb, "i2c0-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(8), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(i2c1_eb, "i2c1-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(9), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(i2c2_eb, "i2c2-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(10), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(i2c3_eb, "i2c3-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(11), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(i2c4_eb, "i2c4-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(12), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(i2c5_eb, "i2c5-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(13), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(uart0_eb, "uart0-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(14), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(uart1_eb, "uart1-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(15), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(uart2_eb, "uart2-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(16), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(uart3_eb, "uart3-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(17), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(uart4_eb, "uart4-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(18), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(ap_ckg_eb, "ap-ckg-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(19), CLK_IGNORE_UNUSED, 0);
+static SPRD_GATE_CLK(spi3_eb, "spi3-eb", "ap_apb", 0x70b00000,
+ 0x1000, BIT(20), CLK_IGNORE_UNUSED, 0);
+
+static struct sprd_clk_common *sc9860_clk_clks[] = {
+ &rpll0_gate.common,
+ &rpll1_gate.common,
+ &mpll0_gate.common,
+ &mpll1_gate.common,
+ &dpll0_gate.common,
+ &dpll1_gate.common,
+ &gpll_gate.common,
+ &cppll_gate.common,
+ &ltepll0_gate.common,
+ &ltepll1_gate.common,
+ &twpll_gate.common,
+ &rpll0_clk.common,
+ &rpll1_clk.common,
+ &mpll0_clk.common,
+ &mpll1_clk.common,
+ &dpll0_clk.common,
+ &dpll1_clk.common,
+ &gpll_clk.common,
+ &cppll_clk.common,
+ &ltepll0_clk.common,
+ &ltepll1_clk.common,
+ &twpll_clk.common,
+ &aon_apb.common,
+ &aux0_clk.common,
+ &aux1_clk.common,
+ &aux2_clk.common,
+ &probe_clk.common,
+ &sp_ahb.common,
+ &cci_clk.common,
+ &gic_clk.common,
+ &cssys_clk.common,
+ &sdio0_2x.common,
+ &sdio1_2x.common,
+ &sdio2_2x.common,
+ &emmc_2x.common,
+ &uart0_clk.common,
+ &uart1_clk.common,
+ &uart2_clk.common,
+ &uart3_clk.common,
+ &uart4_clk.common,
+ &i2c0_clk.common,
+ &i2c1_clk.common,
+ &i2c2_clk.common,
+ &i2c3_clk.common,
+ &i2c4_clk.common,
+ &i2c5_clk.common,
+ &spi0_clk.common,
+ &spi1_clk.common,
+ &spi2_clk.common,
+ &spi3_clk.common,
+ &iis0_clk.common,
+ &iis1_clk.common,
+ &iis2_clk.common,
+ &iis3_clk.common,
+ &lit_mcu.common,
+ &big_mcu.common,
+ &gpu_clk.common,
+ &vsp_clk.common,
+ &vsp_enc.common,
+ &dispc0_dpi.common,
+ &dispc1_dpi.common,
+ &sensor0_clk.common,
+ &sensor1_clk.common,
+ &sensor2_clk.common,
+ &sdio0_1x.common,
+ &sdio1_1x.common,
+ &sdio2_1x.common,
+ &emmc_1x.common,
+ &adi_clk.common,
+ &pwm0_clk.common,
+ &pwm1_clk.common,
+ &pwm2_clk.common,
+ &pwm3_clk.common,
+ &efuse_clk.common,
+ &cm3_uart0.common,
+ &cm3_uart1.common,
+ &thm_clk.common,
+ &cm3_i2c0.common,
+ &cm3_i2c1.common,
+ &cm4_spi.common,
+ &aon_i2c.common,
+ &avs_clk.common,
+ &ca53_dap.common,
+ &ca53_ts.common,
+ &djtag_tck.common,
+ &pmu_clk.common,
+ &pmu_26m.common,
+ &debounce_clk.common,
+ &otg2_ref.common,
+ &usb3_ref.common,
+ &ap_axi.common,
+ &ap_apb.common,
+ &ahb_vsp.common,
+ &ahb_disp.common,
+ &ahb_cam.common,
+ &mipi_csi0_eb.common,
+ &mipi_csi1_eb.common,
+ &usb3_eb.common,
+ &usb3_suspend.common,
+ &usb3_ref_eb.common,
+ &dma_eb.common,
+ &sdio0_eb.common,
+ &sdio1_eb.common,
+ &sdio2_eb.common,
+ &emmc_eb.common,
+ &rom_eb.common,
+ &busmon_eb.common,
+ &cc63s_eb.common,
+ &cc63p_eb.common,
+ &ce0_eb.common,
+ &ce1_eb.common,
+ &avs_lit_eb.common,
+ &avs_big_eb.common,
+ &ap_intc5_eb.common,
+ &gpio_eb.common,
+ &pwm0_eb.common,
+ &pwm1_eb.common,
+ &pwm2_eb.common,
+ &pwm3_eb.common,
+ &kpd_eb.common,
+ &aon_sys_eb.common,
+ &ap_sys_eb.common,
+ &aon_tmr_eb.common,
+ &ap_tmr0_eb.common,
+ &efuse_eb.common,
+ &eic_eb.common,
+ &pub1_reg_eb.common,
+ &adi_eb.common,
+ &ap_intc0_eb.common,
+ &ap_intc1_eb.common,
+ &ap_intc2_eb.common,
+ &ap_intc3_eb.common,
+ &ap_intc4_eb.common,
+ &splk_eb.common,
+ &mspi_eb.common,
+ &pub0_reg_eb.common,
+ &pin_eb.common,
+ &aon_ckg_eb.common,
+ &gpu_eb.common,
+ &apcpu_ts0_eb.common,
+ &apcpu_ts1_eb.common,
+ &dap_eb.common,
+ &i2c_eb.common,
+ &pmu_eb.common,
+ &thm_eb.common,
+ &aux0_eb.common,
+ &aux1_eb.common,
+ &aux2_eb.common,
+ &probe_eb.common,
+ &gpu0_avs_eb.common,
+ &gpu1_avs_eb.common,
+ &apcpu_wdg_eb.common,
+ &ap_tmr1_eb.common,
+ &ap_tmr2_eb.common,
+ &disp_emc_eb.common,
+ &zip_emc_eb.common,
+ &gsp_emc_eb.common,
+ &osc_aon_eb.common,
+ &lvds_trx_eb.common,
+ &lvds_tcxo_eb.common,
+ &mdar_eb.common,
+ &rtc4m0_cal_eb.common,
+ &rct100m_cal_eb.common,
+ &djtag_eb.common,
+ &mbox_eb.common,
+ &aon_dma_eb.common,
+ &dbg_emc_eb.common,
+ &lvds_pll_div_en.common,
+ &def_eb.common,
+ &aon_apb_rsv0.common,
+ &orp_jtag_eb.common,
+ &vsp_eb.common,
+ &cam_eb.common,
+ &disp_eb.common,
+ &dbg_axi_if_eb.common,
+ &sdio0_2x_en.common,
+ &sdio1_2x_en.common,
+ &sdio2_2x_en.common,
+ &emmc_2x_en.common,
+ &agcp_iis0_eb.common,
+ &agcp_iis1_eb.common,
+ &agcp_iis2_eb.common,
+ &agcp_iis3_eb.common,
+ &agcp_uart_eb.common,
+ &agcp_dmacp_eb.common,
+ &agcp_dmaap_eb.common,
+ &agcp_arc48k_eb.common,
+ &agcp_src44p1k_eb.common,
+ &agcp_mcdt_eb.common,
+ &agcp_vbcifd_eb.common,
+ &agcp_vbc_eb.common,
+ &agcp_spinlock_eb.common,
+ &agcp_icu_eb.common,
+ &agcp_ap_ashb_eb.common,
+ &agcp_cp_ashb_eb.common,
+ &agcp_aud_eb.common,
+ &agcp_audif_eb.common,
+ &vsp_dec_eb.common,
+ &vsp_ckg_eb.common,
+ &vsp_mmu_eb.common,
+ &vsp_enc_eb.common,
+ &vpp_eb.common,
+ &vsp_26m_eb.common,
+ &vsp_axi_gate.common,
+ &vsp_enc_gate.common,
+ &vpp_axi_gate.common,
+ &vsp_bm_gate.common,
+ &vsp_enc_bm_gate.common,
+ &vpp_bm_gate.common,
+ &dcam0_eb.common,
+ &dcam1_eb.common,
+ &isp0_eb.common,
+ &csi0_eb.common,
+ &csi1_eb.common,
+ &jpg0_eb.common,
+ &jpg1_eb.common,
+ &cam_ckg_eb.common,
+ &cam_mmu_eb.common,
+ &isp1_eb.common,
+ &cpp_eb.common,
+ &mmu_pf_eb.common,
+ &isp2_eb.common,
+ &dcam2isp_if_eb.common,
+ &isp2dcam_if_eb.common,
+ &isp_lclk_eb.common,
+ &isp_iclk_eb.common,
+ &isp_mclk_eb.common,
+ &isp_pclk_eb.common,
+ &isp_isp2dcam_eb.common,
+ &dcam0_if_eb.common,
+ &clk26m_if_eb.common,
+ &cphy0_gate.common,
+ &mipi_csi0_gate.common,
+ &cphy1_gate.common,
+ &mipi_csi1.common,
+ &dcam0_axi_gate.common,
+ &dcam1_axi_gate.common,
+ &sensor0_gate.common,
+ &sensor1_gate.common,
+ &jpg0_axi_gate.common,
+ &gpg1_axi_gate.common,
+ &isp0_axi_gate.common,
+ &isp1_axi_gate.common,
+ &isp2_axi_gate.common,
+ &cpp_axi_gate.common,
+ &d0_if_axi_gate.common,
+ &d2i_if_axi_gate.common,
+ &i2d_if_axi_gate.common,
+ &spare_axi_gate.common,
+ &sensor2_gate.common,
+ &d0if_in_d_en.common,
+ &d1if_in_d_en.common,
+ &d0if_in_d2i_en.common,
+ &d1if_in_d2i_en.common,
+ &ia_in_d2i_en.common,
+ &ib_in_d2i_en.common,
+ &ic_in_d2i_en.common,
+ &ia_in_i_en.common,
+ &ib_in_i_en.common,
+ &ic_in_i_en.common,
+ &dispc0_eb.common,
+ &dispc1_eb.common,
+ &dispc_mmu_eb.common,
+ &gsp0_eb.common,
+ &gsp1_eb.common,
+ &gsp0_mmu_eb.common,
+ &gsp1_mmu_eb.common,
+ &dsi0_eb.common,
+ &dsi1_eb.common,
+ &disp_ckg_eb.common,
+ &disp_gpu_eb.common,
+ &gpu_mtx_eb.common,
+ &gsp_mtx_eb.common,
+ &tmc_mtx_eb.common,
+ &dispc_mtx_eb.common,
+ &dphy0_gate.common,
+ &dphy1_gate.common,
+ &gsp0_a_gate.common,
+ &gsp1_a_gate.common,
+ &gsp0_f_gate.common,
+ &gsp1_f_gate.common,
+ &d_mtx_f_gate.common,
+ &d_mtx_a_gate.common,
+ &d_noc_f_gate.common,
+ &d_noc_a_gate.common,
+ &gsp_mtx_f_gate.common,
+ &gsp_mtx_a_gate.common,
+ &gsp_noc_f_gate.common,
+ &gsp_noc_a_gate.common,
+ &dispm0idle_gate.common,
+ &gspm0idle_gate.common,
+ &sim0_eb.common,
+ &iis0_eb.common,
+ &iis1_eb.common,
+ &iis2_eb.common,
+ &iis3_eb.common,
+ &spi0_eb.common,
+ &spi1_eb.common,
+ &spi2_eb.common,
+ &i2c0_eb.common,
+ &i2c1_eb.common,
+ &i2c2_eb.common,
+ &i2c3_eb.common,
+ &i2c4_eb.common,
+ &i2c5_eb.common,
+ &uart0_eb.common,
+ &uart1_eb.common,
+ &uart2_eb.common,
+ &uart3_eb.common,
+ &uart4_eb.common,
+ &ap_ckg_eb.common,
+ &spi3_eb.common,
+};
+
+static struct clk_hw_onecell_data sc9860_hw_clks = {
+ .hws = {
+ [CLK_EXT_RCO_100M] = &ext_rco_100m.hw,
+ [CLK_EXT_32K] = &ext_32k.hw,
+ [CLK_FAC_4M] = &fac_4m.hw,
+ [CLK_FAC_2M] = &fac_2m.hw,
+ [CLK_FAC_1M] = &fac_1m.hw,
+ [CLK_FAC_250K] = &fac_250k.hw,
+ [CLK_FAC_RPLL0_26M] = &fac_rpll0_26m.hw,
+ [CLK_FAC_RPLL1_26M] = &fac_rpll1_26m.hw,
+ [CLK_FAC_RCO25M] = &fac_rco_25m.hw,
+ [CLK_FAC_RCO4M] = &fac_rco_4m.hw,
+ [CLK_FAC_RCO2M] = &fac_rco_2m.hw,
+ [CLK_FAC_3K2] = &fac_3k2.hw,
+ [CLK_FAC_1K] = &fac_1k.hw,
+ [CLK_RPLL0_GATE] = &rpll0_gate.common.hw,
+ [CLK_RPLL1_GATE] = &rpll1_gate.common.hw,
+ [CLK_MPLL0_GATE] = &mpll0_gate.common.hw,
+ [CLK_MPLL1_GATE] = &mpll1_gate.common.hw,
+ [CLK_DPLL0_GATE] = &dpll0_gate.common.hw,
+ [CLK_DPLL1_GATE] = &dpll1_gate.common.hw,
+ [CLK_GPLL_GATE] = &gpll_gate.common.hw,
+ [CLK_CPPLL_GATE] = &cppll_gate.common.hw,
+ [CLK_LTEPLL0_GATE] = &ltepll0_gate.common.hw,
+ [CLK_LTEPLL1_GATE] = &ltepll1_gate.common.hw,
+ [CLK_TWPLL_GATE] = &twpll_gate.common.hw,
+ [CLK_RPLL0] = &rpll0_clk.common.hw,
+ [CLK_RPLL1] = &rpll1_clk.common.hw,
+ [CLK_MPLL0] = &mpll0_clk.common.hw,
+ [CLK_MPLL1] = &mpll1_clk.common.hw,
+ [CLK_DPLL0] = &dpll0_clk.common.hw,
+ [CLK_DPLL1] = &dpll1_clk.common.hw,
+ [CLK_GPLL] = &gpll_clk.common.hw,
+ [CLK_CPPLL] = &cppll_clk.common.hw,
+ [CLK_LTEPLL0] = &ltepll0_clk.common.hw,
+ [CLK_LTEPLL1] = &ltepll1_clk.common.hw,
+ [CLK_TWPLL] = &twpll_clk.common.hw,
+ [CLK_GPLL_42M5] = &gpll_42m5.hw,
+ [CLK_TWPLL_768M] = &twpll_768m.hw,
+ [CLK_TWPLL_384M] = &twpll_384m.hw,
+ [CLK_TWPLL_192M] = &twpll_192m.hw,
+ [CLK_TWPLL_96M] = &twpll_96m.hw,
+ [CLK_TWPLL_48M] = &twpll_48m.hw,
+ [CLK_TWPLL_24M] = &twpll_24m.hw,
+ [CLK_TWPLL_12M] = &twpll_12m.hw,
+ [CLK_TWPLL_512M] = &twpll_512m.hw,
+ [CLK_TWPLL_256M] = &twpll_256m.hw,
+ [CLK_TWPLL_128M] = &twpll_128m.hw,
+ [CLK_TWPLL_64M] = &twpll_64m.hw,
+ [CLK_TWPLL_307M2] = &twpll_307m2.hw,
+ [CLK_TWPLL_153M6] = &twpll_153m6.hw,
+ [CLK_TWPLL_76M8] = &twpll_76m8.hw,
+ [CLK_TWPLL_51M2] = &twpll_51m2.hw,
+ [CLK_TWPLL_38M4] = &twpll_38m4.hw,
+ [CLK_TWPLL_19M2] = &twpll_19m2.hw,
+ [CLK_L0_614M4] = &l0_614m4.hw,
+ [CLK_L0_409M6] = &l0_409m6.hw,
+ [CLK_L0_38M] = &l0_38m.hw,
+ [CLK_L1_38M] = &l1_38m.hw,
+ [CLK_RPLL0_192M] = &rpll0_192m.hw,
+ [CLK_RPLL0_96M] = &rpll0_96m.hw,
+ [CLK_RPLL0_48M] = &rpll0_48m.hw,
+ [CLK_RPLL1_468M] = &rpll1_468m.hw,
+ [CLK_RPLL1_192M] = &rpll1_192m.hw,
+ [CLK_RPLL1_96M] = &rpll1_96m.hw,
+ [CLK_RPLL1_64M] = &rpll1_64m.hw,
+ [CLK_RPLL1_48M] = &rpll1_48m.hw,
+ [CLK_DPLL0_50M] = &dpll0_50m.hw,
+ [CLK_DPLL1_50M] = &dpll1_50m.hw,
+ [CLK_CPPLL_50M] = &cppll_50m.hw,
+ [CLK_M0_39M] = &m0_39m.hw,
+ [CLK_M1_63M] = &m1_63m.hw,
+ [CLK_AON_APB] = &aon_apb.common.hw,
+ [CLK_AUX0] = &aux0_clk.common.hw,
+ [CLK_AUX1] = &aux1_clk.common.hw,
+ [CLK_AUX2] = &aux2_clk.common.hw,
+ [CLK_PROBE] = &probe_clk.common.hw,
+ [CLK_SP_AHB] = &sp_ahb.common.hw,
+ [CLK_CCI] = &cci_clk.common.hw,
+ [CLK_GIC] = &gic_clk.common.hw,
+ [CLK_CSSYS] = &cssys_clk.common.hw,
+ [CLK_SDIO0_2X] = &sdio0_2x.common.hw,
+ [CLK_SDIO1_2X] = &sdio1_2x.common.hw,
+ [CLK_SDIO2_2X] = &sdio2_2x.common.hw,
+ [CLK_EMMC_2X] = &emmc_2x.common.hw,
+ [CLK_UART0] = &uart0_clk.common.hw,
+ [CLK_UART1] = &uart1_clk.common.hw,
+ [CLK_UART2] = &uart2_clk.common.hw,
+ [CLK_UART3] = &uart3_clk.common.hw,
+ [CLK_UART4] = &uart4_clk.common.hw,
+ [CLK_I2C0] = &i2c0_clk.common.hw,
+ [CLK_I2C1] = &i2c1_clk.common.hw,
+ [CLK_I2C2] = &i2c2_clk.common.hw,
+ [CLK_I2C3] = &i2c3_clk.common.hw,
+ [CLK_I2C4] = &i2c4_clk.common.hw,
+ [CLK_I2C5] = &i2c5_clk.common.hw,
+ [CLK_SPI0] = &spi0_clk.common.hw,
+ [CLK_SPI1] = &spi1_clk.common.hw,
+ [CLK_SPI2] = &spi2_clk.common.hw,
+ [CLK_SPI3] = &spi3_clk.common.hw,
+ [CLK_IIS0] = &iis0_clk.common.hw,
+ [CLK_IIS1] = &iis1_clk.common.hw,
+ [CLK_IIS2] = &iis2_clk.common.hw,
+ [CLK_IIS3] = &iis3_clk.common.hw,
+ [CLK_LIT_MCU] = &lit_mcu.common.hw,
+ [CLK_BIG_MCU] = &big_mcu.common.hw,
+ [CLK_GPU] = &gpu_clk.common.hw,
+ [CLK_VSP] = &vsp_clk.common.hw,
+ [CLK_VSP_ENC] = &vsp_enc.common.hw,
+ [CLK_DISPC0_DPI] = &dispc0_dpi.common.hw,
+ [CLK_DISPC1_DPI] = &dispc1_dpi.common.hw,
+ [CLK_SENSOR0] = &sensor0_clk.common.hw,
+ [CLK_SENSOR1] = &sensor1_clk.common.hw,
+ [CLK_SENSOR2] = &sensor2_clk.common.hw,
+ [CLK_SDIO0_1X] = &sdio0_1x.common.hw,
+ [CLK_SDIO1_1X] = &sdio1_1x.common.hw,
+ [CLK_SDIO2_1X] = &sdio2_1x.common.hw,
+ [CLK_EMMC_1X] = &emmc_1x.common.hw,
+ [CLK_ADI] = &adi_clk.common.hw,
+ [CLK_PWM0] = &pwm0_clk.common.hw,
+ [CLK_PWM1] = &pwm1_clk.common.hw,
+ [CLK_PWM2] = &pwm2_clk.common.hw,
+ [CLK_PWM3] = &pwm3_clk.common.hw,
+ [CLK_EFUSE] = &efuse_clk.common.hw,
+ [CLK_CM3_UART0] = &cm3_uart0.common.hw,
+ [CLK_CM3_UART1] = &cm3_uart1.common.hw,
+ [CLK_THM] = &thm_clk.common.hw,
+ [CLK_CM3_I2C0] = &cm3_i2c0.common.hw,
+ [CLK_CM3_I2C1] = &cm3_i2c1.common.hw,
+ [CLK_CM4_SPI] = &cm4_spi.common.hw,
+ [CLK_AON_I2C] = &aon_i2c.common.hw,
+ [CLK_AVS] = &avs_clk.common.hw,
+ [CLK_CA53_DAP] = &ca53_dap.common.hw,
+ [CLK_CA53_TS] = &ca53_ts.common.hw,
+ [CLK_DJTAG_TCK] = &djtag_tck.common.hw,
+ [CLK_PMU] = &pmu_clk.common.hw,
+ [CLK_PMU_26M] = &pmu_26m.common.hw,
+ [CLK_DEBOUNCE] = &debounce_clk.common.hw,
+ [CLK_OTG2_REF] = &otg2_ref.common.hw,
+ [CLK_USB3_REF] = &usb3_ref.common.hw,
+ [CLK_AP_AXI] = &ap_axi.common.hw,
+ [CLK_AP_APB] = &ap_apb.common.hw,
+ [CLK_AHB_VSP] = &ahb_vsp.common.hw,
+ [CLK_AHB_DISP] = &ahb_disp.common.hw,
+ [CLK_AHB_CAM] = &ahb_cam.common.hw,
+ [CLK_MIPI_CSI0_EB] = &mipi_csi0_eb.common.hw,
+ [CLK_MIPI_CSI1_EB] = &mipi_csi1_eb.common.hw,
+ [CLK_USB3_EB] = &usb3_eb.common.hw,
+ [CLK_USB3_SUSPEND_EB] = &usb3_suspend.common.hw,
+ [CLK_USB3_REF_EB] = &usb3_ref_eb.common.hw,
+ [CLK_DMA_EB] = &dma_eb.common.hw,
+ [CLK_SDIO0_EB] = &sdio0_eb.common.hw,
+ [CLK_SDIO1_EB] = &sdio1_eb.common.hw,
+ [CLK_SDIO2_EB] = &sdio2_eb.common.hw,
+ [CLK_EMMC_EB] = &emmc_eb.common.hw,
+ [CLK_ROM_EB] = &rom_eb.common.hw,
+ [CLK_BUSMON_EB] = &busmon_eb.common.hw,
+ [CLK_CC63S_EB] = &cc63s_eb.common.hw,
+ [CLK_CC63P_EB] = &cc63p_eb.common.hw,
+ [CLK_CE0_EB] = &ce0_eb.common.hw,
+ [CLK_CE1_EB] = &ce1_eb.common.hw,
+ [CLK_AVS_LIT_EB] = &avs_lit_eb.common.hw,
+ [CLK_AVS_BIG_EB] = &avs_big_eb.common.hw,
+ [CLK_AP_INTC5_EB] = &ap_intc5_eb.common.hw,
+ [CLK_GPIO_EB] = &gpio_eb.common.hw,
+ [CLK_PWM0_EB] = &pwm0_eb.common.hw,
+ [CLK_PWM1_EB] = &pwm1_eb.common.hw,
+ [CLK_PWM2_EB] = &pwm2_eb.common.hw,
+ [CLK_PWM3_EB] = &pwm3_eb.common.hw,
+ [CLK_KPD_EB] = &kpd_eb.common.hw,
+ [CLK_AON_SYS_EB] = &aon_sys_eb.common.hw,
+ [CLK_AP_SYS_EB] = &ap_sys_eb.common.hw,
+ [CLK_AON_TMR_EB] = &aon_tmr_eb.common.hw,
+ [CLK_AP_TMR0_EB] = &ap_tmr0_eb.common.hw,
+ [CLK_EFUSE_EB] = &efuse_eb.common.hw,
+ [CLK_EIC_EB] = &eic_eb.common.hw,
+ [CLK_PUB1_REG_EB] = &pub1_reg_eb.common.hw,
+ [CLK_ADI_EB] = &adi_eb.common.hw,
+ [CLK_AP_INTC0_EB] = &ap_intc0_eb.common.hw,
+ [CLK_AP_INTC1_EB] = &ap_intc1_eb.common.hw,
+ [CLK_AP_INTC2_EB] = &ap_intc2_eb.common.hw,
+ [CLK_AP_INTC3_EB] = &ap_intc3_eb.common.hw,
+ [CLK_AP_INTC4_EB] = &ap_intc4_eb.common.hw,
+ [CLK_SPLK_EB] = &splk_eb.common.hw,
+ [CLK_MSPI_EB] = &mspi_eb.common.hw,
+ [CLK_PUB0_REG_EB] = &pub0_reg_eb.common.hw,
+ [CLK_PIN_EB] = &pin_eb.common.hw,
+ [CLK_AON_CKG_EB] = &aon_ckg_eb.common.hw,
+ [CLK_GPU_EB] = &gpu_eb.common.hw,
+ [CLK_APCPU_TS0_EB] = &apcpu_ts0_eb.common.hw,
+ [CLK_APCPU_TS1_EB] = &apcpu_ts1_eb.common.hw,
+ [CLK_DAP_EB] = &dap_eb.common.hw,
+ [CLK_I2C_EB] = &i2c_eb.common.hw,
+ [CLK_PMU_EB] = &pmu_eb.common.hw,
+ [CLK_THM_EB] = &thm_eb.common.hw,
+ [CLK_AUX0_EB] = &aux0_eb.common.hw,
+ [CLK_AUX1_EB] = &aux1_eb.common.hw,
+ [CLK_AUX2_EB] = &aux2_eb.common.hw,
+ [CLK_PROBE_EB] = &probe_eb.common.hw,
+ [CLK_GPU0_AVS_EB] = &gpu0_avs_eb.common.hw,
+ [CLK_GPU1_AVS_EB] = &gpu1_avs_eb.common.hw,
+ [CLK_APCPU_WDG_EB] = &apcpu_wdg_eb.common.hw,
+ [CLK_AP_TMR1_EB] = &ap_tmr1_eb.common.hw,
+ [CLK_AP_TMR2_EB] = &ap_tmr2_eb.common.hw,
+ [CLK_DISP_EMC_EB] = &disp_emc_eb.common.hw,
+ [CLK_ZIP_EMC_EB] = &zip_emc_eb.common.hw,
+ [CLK_GSP_EMC_EB] = &gsp_emc_eb.common.hw,
+ [CLK_OSC_AON_EB] = &osc_aon_eb.common.hw,
+ [CLK_LVDS_TRX_EB] = &lvds_trx_eb.common.hw,
+ [CLK_LVDS_TCXO_EB] = &lvds_tcxo_eb.common.hw,
+ [CLK_MDAR_EB] = &mdar_eb.common.hw,
+ [CLK_RTC4M0_CAL_EB] = &rtc4m0_cal_eb.common.hw,
+ [CLK_RCT100M_CAL_EB] = &rct100m_cal_eb.common.hw,
+ [CLK_DJTAG_EB] = &djtag_eb.common.hw,
+ [CLK_MBOX_EB] = &mbox_eb.common.hw,
+ [CLK_AON_DMA_EB] = &aon_dma_eb.common.hw,
+ [CLK_DBG_EMC_EB] = &dbg_emc_eb.common.hw,
+ [CLK_LVDS_PLL_DIV_EN] = &lvds_pll_div_en.common.hw,
+ [CLK_DEF_EB] = &def_eb.common.hw,
+ [CLK_AON_APB_RSV0] = &aon_apb_rsv0.common.hw,
+ [CLK_ORP_JTAG_EB] = &orp_jtag_eb.common.hw,
+ [CLK_VSP_EB] = &vsp_eb.common.hw,
+ [CLK_CAM_EB] = &cam_eb.common.hw,
+ [CLK_DISP_EB] = &disp_eb.common.hw,
+ [CLK_DBG_AXI_IF_EB] = &dbg_axi_if_eb.common.hw,
+ [CLK_SDIO0_2X_EN] = &sdio0_2x_en.common.hw,
+ [CLK_SDIO1_2X_EN] = &sdio1_2x_en.common.hw,
+ [CLK_SDIO2_2X_EN] = &sdio2_2x_en.common.hw,
+ [CLK_EMMC_2X_EN] = &emmc_2x_en.common.hw,
+ [CLK_AGCP_IIS0_EB] = &agcp_iis0_eb.common.hw,
+ [CLK_AGCP_IIS1_EB] = &agcp_iis1_eb.common.hw,
+ [CLK_AGCP_IIS2_EB] = &agcp_iis2_eb.common.hw,
+ [CLK_AGCP_IIS3_EB] = &agcp_iis3_eb.common.hw,
+ [CLK_AGCP_UART_EB] = &agcp_uart_eb.common.hw,
+ [CLK_AGCP_DMACP_EB] = &agcp_dmacp_eb.common.hw,
+ [CLK_AGCP_DMAAP_EB] = &agcp_dmaap_eb.common.hw,
+ [CLK_AGCP_ARC48K_EB] = &agcp_arc48k_eb.common.hw,
+ [CLK_AGCP_SRC44P1K_EB] = &agcp_src44p1k_eb.common.hw,
+ [CLK_AGCP_MCDT_EB] = &agcp_mcdt_eb.common.hw,
+ [CLK_AGCP_VBCIFD_EB] = &agcp_vbcifd_eb.common.hw,
+ [CLK_AGCP_VBC_EB] = &agcp_vbc_eb.common.hw,
+ [CLK_AGCP_SPINLOCK_EB] = &agcp_spinlock_eb.common.hw,
+ [CLK_AGCP_ICU_EB] = &agcp_icu_eb.common.hw,
+ [CLK_AGCP_AP_ASHB_EB] = &agcp_ap_ashb_eb.common.hw,
+ [CLK_AGCP_CP_ASHB_EB] = &agcp_cp_ashb_eb.common.hw,
+ [CLK_AGCP_AUD_EB] = &agcp_aud_eb.common.hw,
+ [CLK_AGCP_AUDIF_EB] = &agcp_audif_eb.common.hw,
+ [CLK_VSP_DEC_EB] = &vsp_dec_eb.common.hw,
+ [CLK_VSP_CKG_EB] = &vsp_ckg_eb.common.hw,
+ [CLK_VSP_MMU_EB] = &vsp_mmu_eb.common.hw,
+ [CLK_VSP_ENC_EB] = &vsp_enc_eb.common.hw,
+ [CLK_VPP_EB] = &vpp_eb.common.hw,
+ [CLK_VSP_26M_EB] = &vsp_26m_eb.common.hw,
+ [CLK_VSP_AXI_GATE] = &vsp_axi_gate.common.hw,
+ [CLK_VSP_ENC_GATE] = &vsp_enc_gate.common.hw,
+ [CLK_VPP_AXI_GATE] = &vpp_axi_gate.common.hw,
+ [CLK_VSP_BM_GATE] = &vsp_bm_gate.common.hw,
+ [CLK_VSP_ENC_BM_GATE] = &vsp_enc_bm_gate.common.hw,
+ [CLK_VPP_BM_GATE] = &vpp_bm_gate.common.hw,
+ [CLK_DCAM0_EB] = &dcam0_eb.common.hw,
+ [CLK_DCAM1_EB] = &dcam1_eb.common.hw,
+ [CLK_ISP0_EB] = &isp0_eb.common.hw,
+ [CLK_CSI0_EB] = &csi0_eb.common.hw,
+ [CLK_CSI1_EB] = &csi1_eb.common.hw,
+ [CLK_JPG0_EB] = &jpg0_eb.common.hw,
+ [CLK_JPG1_EB] = &jpg1_eb.common.hw,
+ [CLK_CAM_CKG_EB] = &cam_ckg_eb.common.hw,
+ [CLK_CAM_MMU_EB] = &cam_mmu_eb.common.hw,
+ [CLK_ISP1_EB] = &isp1_eb.common.hw,
+ [CLK_CPP_EB] = &cpp_eb.common.hw,
+ [CLK_MMU_PF_EB] = &mmu_pf_eb.common.hw,
+ [CLK_ISP2_EB] = &isp2_eb.common.hw,
+ [CLK_DCAM2ISP_IF_EB] = &dcam2isp_if_eb.common.hw,
+ [CLK_ISP2DCAM_IF_EB] = &isp2dcam_if_eb.common.hw,
+ [CLK_ISP_LCLK_EB] = &isp_lclk_eb.common.hw,
+ [CLK_ISP_ICLK_EB] = &isp_iclk_eb.common.hw,
+ [CLK_ISP_MCLK_EB] = &isp_mclk_eb.common.hw,
+ [CLK_ISP_PCLK_EB] = &isp_pclk_eb.common.hw,
+ [CLK_ISP_ISP2DCAM_EB] = &isp_isp2dcam_eb.common.hw,
+ [CLK_DCAM0_IF_EB] = &dcam0_if_eb.common.hw,
+ [CLK_CLK26M_IF_EB] = &clk26m_if_eb.common.hw,
+ [CLK_CPHY0_GATE] = &cphy0_gate.common.hw,
+ [CLK_MIPI_CSI0_GATE] = &mipi_csi0_gate.common.hw,
+ [CLK_CPHY1_GATE] = &cphy1_gate.common.hw,
+ [CLK_MIPI_CSI1] = &mipi_csi1.common.hw,
+ [CLK_DCAM0_AXI_GATE] = &dcam0_axi_gate.common.hw,
+ [CLK_DCAM1_AXI_GATE] = &dcam1_axi_gate.common.hw,
+ [CLK_SENSOR0_GATE] = &sensor0_gate.common.hw,
+ [CLK_SENSOR1_GATE] = &sensor1_gate.common.hw,
+ [CLK_JPG0_AXI_GATE] = &jpg0_axi_gate.common.hw,
+ [CLK_GPG1_AXI_GATE] = &gpg1_axi_gate.common.hw,
+ [CLK_ISP0_AXI_GATE] = &isp0_axi_gate.common.hw,
+ [CLK_ISP1_AXI_GATE] = &isp1_axi_gate.common.hw,
+ [CLK_ISP2_AXI_GATE] = &isp2_axi_gate.common.hw,
+ [CLK_CPP_AXI_GATE] = &cpp_axi_gate.common.hw,
+ [CLK_D0_IF_AXI_GATE] = &d0_if_axi_gate.common.hw,
+ [CLK_D2I_IF_AXI_GATE] = &d2i_if_axi_gate.common.hw,
+ [CLK_I2D_IF_AXI_GATE] = &i2d_if_axi_gate.common.hw,
+ [CLK_SPARE_AXI_GATE] = &spare_axi_gate.common.hw,
+ [CLK_SENSOR2_GATE] = &sensor2_gate.common.hw,
+ [CLK_D0IF_IN_D_EN] = &d0if_in_d_en.common.hw,
+ [CLK_D1IF_IN_D_EN] = &d1if_in_d_en.common.hw,
+ [CLK_D0IF_IN_D2I_EN] = &d0if_in_d2i_en.common.hw,
+ [CLK_D1IF_IN_D2I_EN] = &d1if_in_d2i_en.common.hw,
+ [CLK_IA_IN_D2I_EN] = &ia_in_d2i_en.common.hw,
+ [CLK_IB_IN_D2I_EN] = &ib_in_d2i_en.common.hw,
+ [CLK_IC_IN_D2I_EN] = &ic_in_d2i_en.common.hw,
+ [CLK_IA_IN_I_EN] = &ia_in_i_en.common.hw,
+ [CLK_IB_IN_I_EN] = &ib_in_i_en.common.hw,
+ [CLK_IC_IN_I_EN] = &ic_in_i_en.common.hw,
+ [CLK_DISPC0_EB] = &dispc0_eb.common.hw,
+ [CLK_DISPC1_EB] = &dispc1_eb.common.hw,
+ [CLK_DISPC_MMU_EB] = &dispc_mmu_eb.common.hw,
+ [CLK_GSP0_EB] = &gsp0_eb.common.hw,
+ [CLK_GSP1_EB] = &gsp1_eb.common.hw,
+ [CLK_GSP0_MMU_EB] = &gsp0_mmu_eb.common.hw,
+ [CLK_GSP1_MMU_EB] = &gsp1_mmu_eb.common.hw,
+ [CLK_DSI0_EB] = &dsi0_eb.common.hw,
+ [CLK_DSI1_EB] = &dsi1_eb.common.hw,
+ [CLK_DISP_CKG_EB] = &disp_ckg_eb.common.hw,
+ [CLK_DISP_GPU_EB] = &disp_gpu_eb.common.hw,
+ [CLK_GPU_MTX_EB] = &gpu_mtx_eb.common.hw,
+ [CLK_GSP_MTX_EB] = &gsp_mtx_eb.common.hw,
+ [CLK_TMC_MTX_EB] = &tmc_mtx_eb.common.hw,
+ [CLK_DISPC_MTX_EB] = &dispc_mtx_eb.common.hw,
+ [CLK_DPHY0_GATE] = &dphy0_gate.common.hw,
+ [CLK_DPHY1_GATE] = &dphy1_gate.common.hw,
+ [CLK_GSP0_A_GATE] = &gsp0_a_gate.common.hw,
+ [CLK_GSP1_A_GATE] = &gsp1_a_gate.common.hw,
+ [CLK_GSP0_F_GATE] = &gsp0_f_gate.common.hw,
+ [CLK_GSP1_F_GATE] = &gsp1_f_gate.common.hw,
+ [CLK_D_MTX_F_GATE] = &d_mtx_f_gate.common.hw,
+ [CLK_D_MTX_A_GATE] = &d_mtx_a_gate.common.hw,
+ [CLK_D_NOC_F_GATE] = &d_noc_f_gate.common.hw,
+ [CLK_D_NOC_A_GATE] = &d_noc_a_gate.common.hw,
+ [CLK_GSP_MTX_F_GATE] = &gsp_mtx_f_gate.common.hw,
+ [CLK_GSP_MTX_A_GATE] = &gsp_mtx_a_gate.common.hw,
+ [CLK_GSP_NOC_F_GATE] = &gsp_noc_f_gate.common.hw,
+ [CLK_GSP_NOC_A_GATE] = &gsp_noc_a_gate.common.hw,
+ [CLK_DISPM0IDLE_GATE] = &dispm0idle_gate.common.hw,
+ [CLK_GSPM0IDLE_GATE] = &gspm0idle_gate.common.hw,
+ [CLK_SIM0_EB] = &sim0_eb.common.hw,
+ [CLK_IIS0_EB] = &iis0_eb.common.hw,
+ [CLK_IIS1_EB] = &iis1_eb.common.hw,
+ [CLK_IIS2_EB] = &iis2_eb.common.hw,
+ [CLK_IIS3_EB] = &iis3_eb.common.hw,
+ [CLK_SPI0_EB] = &spi0_eb.common.hw,
+ [CLK_SPI1_EB] = &spi1_eb.common.hw,
+ [CLK_SPI2_EB] = &spi2_eb.common.hw,
+ [CLK_I2C0_EB] = &i2c0_eb.common.hw,
+ [CLK_I2C1_EB] = &i2c1_eb.common.hw,
+ [CLK_I2C2_EB] = &i2c2_eb.common.hw,
+ [CLK_I2C3_EB] = &i2c3_eb.common.hw,
+ [CLK_I2C4_EB] = &i2c4_eb.common.hw,
+ [CLK_I2C5_EB] = &i2c5_eb.common.hw,
+ [CLK_UART0_EB] = &uart0_eb.common.hw,
+ [CLK_UART1_EB] = &uart1_eb.common.hw,
+ [CLK_UART2_EB] = &uart2_eb.common.hw,
+ [CLK_UART3_EB] = &uart3_eb.common.hw,
+ [CLK_UART4_EB] = &uart4_eb.common.hw,
+ [CLK_AP_CKG_EB] = &ap_ckg_eb.common.hw,
+ [CLK_SPI3_EB] = &spi3_eb.common.hw,
+ },
+ .num = CLK_NUMBER_SC9860,
+};
+
+static const struct sprd_clk_desc sc9860_clk_desc = {
+ .clk_clks = sc9860_clk_clks,
+ .num_clk_clks = ARRAY_SIZE(sc9860_clk_clks),
+
+ .hw_clks = &sc9860_hw_clks,
+};
+
+static int sc9860_clk_probe(struct platform_device *pdev)
+{
+ void __iomem *base;
+ unsigned int i, count = pdev->num_resources;
+ int ret = 0;
+ struct resource *res;
+ struct clk_addr_map *sc9860_maps;
+
+ sc9860_maps = kcalloc(count, sizeof(*sc9860_maps), GFP_KERNEL);
+ if (!sc9860_maps)
+ return -ENOMEM;
+
+ for (i = 0; i < count; i++) {
+ res = platform_get_resource(pdev, IORESOURCE_MEM, i);
+ base = devm_ioremap_resource(&pdev->dev, res);
+ if (IS_ERR(base)) {
+ ret = PTR_ERR(base);
+ goto free_maps;
+ }
+
+ sc9860_maps[i].phy = res->start & 0xffff0000;
+ sc9860_maps[i].virt = base;
+ }
+
+ ret = sprd_clk_probe(pdev->dev.of_node, sc9860_maps,
+ count, &sc9860_clk_desc);
+ if (ret)
+ goto free_maps;
+
+ pr_info("SC9860: %u clocks have been registered now.\n",
+ CLK_NUMBER_SC9860);
+
+free_maps:
+ kfree(sc9860_maps);
+ return ret;
+}
+
+static const struct of_device_id sc9860_clk_ids[] = {
+ { .compatible = "sprd,sc9860-clk" },
+ { }
+};
+MODULE_DEVICE_TABLE(of, sc9860_clk_ids);
+
+static struct platform_driver sc9860_clk_driver = {
+ .probe = sc9860_clk_probe,
+ .driver = {
+ .name = "sc9860-clk",
+ .of_match_table = sc9860_clk_ids,
+ },
+};
+//builtin_platform_driver(sc9860_clk_driver);
+module_platform_driver(sc9860_clk_driver);
+
+MODULE_DESCRIPTION("Spreadtrum SC9860 Clock Driver");
+MODULE_LICENSE("GPL v2");
+MODULE_ALIAS("platform:sc9860-clk");
diff --git a/include/dt-bindings/clock/sprd,sc9860-clk.h b/include/dt-bindings/clock/sprd,sc9860-clk.h
new file mode 100644
index 0000000..79b2404
--- /dev/null
+++ b/include/dt-bindings/clock/sprd,sc9860-clk.h
@@ -0,0 +1,375 @@
+/*
+ * Spreadtrum SC9860 platform clocks
+ *
+ * Copyright (C) 2017, Spreadtrum Communications Inc.
+ *
+ * SPDX-License-Identifier: (GPL-2.0+ OR MIT)
+ */
+
+#ifndef _DT_BINDINGS_CLK_SC9860_H_
+#define _DT_BINDINGS_CLK_SC9860_H_
+
+#define CLK_EXT_RCO_100M 0
+#define CLK_EXT_32K 1
+#define CLK_FAC_4M 2
+#define CLK_FAC_2M 3
+#define CLK_FAC_1M 4
+#define CLK_FAC_250K 5
+#define CLK_FAC_RPLL0_26M 6
+#define CLK_FAC_RPLL1_26M 7
+#define CLK_FAC_RCO25M 8
+#define CLK_FAC_RCO4M 9
+#define CLK_FAC_RCO2M 10
+#define CLK_FAC_3K2 11
+#define CLK_FAC_1K 12
+#define CLK_RPLL0_GATE 13
+#define CLK_RPLL1_GATE 14
+#define CLK_MPLL0_GATE 15
+#define CLK_MPLL1_GATE 16
+#define CLK_DPLL0_GATE 17
+#define CLK_DPLL1_GATE 18
+#define CLK_GPLL_GATE 19
+#define CLK_CPPLL_GATE 20
+#define CLK_LTEPLL0_GATE 21
+#define CLK_LTEPLL1_GATE 22
+#define CLK_TWPLL_GATE 23
+#define CLK_RPLL0 24
+#define CLK_RPLL1 25
+#define CLK_MPLL0 26
+#define CLK_MPLL1 27
+#define CLK_DPLL0 28
+#define CLK_DPLL1 29
+#define CLK_GPLL 30
+#define CLK_CPPLL 31
+#define CLK_LTEPLL0 32
+#define CLK_LTEPLL1 33
+#define CLK_TWPLL 34
+#define CLK_GPLL_42M5 35
+#define CLK_TWPLL_768M 36
+#define CLK_TWPLL_384M 37
+#define CLK_TWPLL_192M 38
+#define CLK_TWPLL_96M 39
+#define CLK_TWPLL_48M 40
+#define CLK_TWPLL_24M 41
+#define CLK_TWPLL_12M 42
+#define CLK_TWPLL_512M 43
+#define CLK_TWPLL_256M 44
+#define CLK_TWPLL_128M 45
+#define CLK_TWPLL_64M 46
+#define CLK_TWPLL_307M2 47
+#define CLK_TWPLL_153M6 48
+#define CLK_TWPLL_76M8 49
+#define CLK_TWPLL_51M2 50
+#define CLK_TWPLL_38M4 51
+#define CLK_TWPLL_19M2 52
+#define CLK_L0_614M4 53
+#define CLK_L0_409M6 54
+#define CLK_L0_38M 55
+#define CLK_L1_38M 56
+#define CLK_RPLL0_192M 57
+#define CLK_RPLL0_96M 58
+#define CLK_RPLL0_48M 59
+#define CLK_RPLL1_468M 60
+#define CLK_RPLL1_192M 61
+#define CLK_RPLL1_96M 62
+#define CLK_RPLL1_64M 63
+#define CLK_RPLL1_48M 64
+#define CLK_DPLL0_50M 65
+#define CLK_DPLL1_50M 66
+#define CLK_CPPLL_50M 67
+#define CLK_M0_39M 68
+#define CLK_M1_63M 69
+#define CLK_AON_APB 70
+#define CLK_AUX0 71
+#define CLK_AUX1 72
+#define CLK_AUX2 73
+#define CLK_PROBE 74
+#define CLK_SP_AHB 75
+#define CLK_CCI 76
+#define CLK_GIC 77
+#define CLK_CSSYS 78
+#define CLK_SDIO0_2X 79
+#define CLK_SDIO1_2X 80
+#define CLK_SDIO2_2X 81
+#define CLK_EMMC_2X 82
+#define CLK_UART0 83
+#define CLK_UART1 84
+#define CLK_UART2 85
+#define CLK_UART3 86
+#define CLK_UART4 87
+#define CLK_I2C0 88
+#define CLK_I2C1 89
+#define CLK_I2C2 90
+#define CLK_I2C3 91
+#define CLK_I2C4 92
+#define CLK_I2C5 93
+#define CLK_SPI0 94
+#define CLK_SPI1 95
+#define CLK_SPI2 96
+#define CLK_SPI3 97
+#define CLK_IIS0 98
+#define CLK_IIS1 99
+#define CLK_IIS2 100
+#define CLK_IIS3 101
+#define CLK_LIT_MCU 102
+#define CLK_BIG_MCU 103
+#define CLK_GPU 104
+#define CLK_VSP 105
+#define CLK_VSP_ENC 106
+#define CLK_DISPC0_DPI 107
+#define CLK_DISPC1_DPI 108
+#define CLK_SENSOR0 109
+#define CLK_SENSOR1 110
+#define CLK_SENSOR2 111
+#define CLK_SDIO0_1X 112
+#define CLK_SDIO1_1X 113
+#define CLK_SDIO2_1X 114
+#define CLK_EMMC_1X 115
+#define CLK_ADI 116
+#define CLK_PWM0 117
+#define CLK_PWM1 118
+#define CLK_PWM2 119
+#define CLK_PWM3 120
+#define CLK_EFUSE 121
+#define CLK_CM3_UART0 122
+#define CLK_CM3_UART1 123
+#define CLK_THM 124
+#define CLK_CM3_I2C0 125
+#define CLK_CM3_I2C1 126
+#define CLK_CM4_SPI 127
+#define CLK_AON_I2C 128
+#define CLK_AVS 129
+#define CLK_CA53_DAP 130
+#define CLK_CA53_TS 131
+#define CLK_DJTAG_TCK 132
+#define CLK_PMU 133
+#define CLK_PMU_26M 134
+#define CLK_DEBOUNCE 135
+#define CLK_OTG2_REF 136
+#define CLK_USB3_REF 137
+#define CLK_AP_AXI 138
+#define CLK_AP_APB 139
+#define CLK_AHB_VSP 140
+#define CLK_AHB_DISP 141
+#define CLK_AHB_CAM 142
+#define CLK_MIPI_CSI0_EB 143
+#define CLK_MIPI_CSI1_EB 144
+#define CLK_USB3_EB 145
+#define CLK_USB3_SUSPEND_EB 146
+#define CLK_USB3_REF_EB 147
+#define CLK_DMA_EB 148
+#define CLK_SDIO0_EB 149
+#define CLK_SDIO1_EB 150
+#define CLK_SDIO2_EB 151
+#define CLK_EMMC_EB 152
+#define CLK_ROM_EB 153
+#define CLK_BUSMON_EB 154
+#define CLK_CC63S_EB 155
+#define CLK_CC63P_EB 156
+#define CLK_CE0_EB 157
+#define CLK_CE1_EB 158
+#define CLK_AVS_LIT_EB 159
+#define CLK_AVS_BIG_EB 160
+#define CLK_AP_INTC5_EB 161
+#define CLK_GPIO_EB 162
+#define CLK_PWM0_EB 163
+#define CLK_PWM1_EB 164
+#define CLK_PWM2_EB 165
+#define CLK_PWM3_EB 166
+#define CLK_KPD_EB 167
+#define CLK_AON_SYS_EB 168
+#define CLK_AP_SYS_EB 169
+#define CLK_AON_TMR_EB 170
+#define CLK_AP_TMR0_EB 171
+#define CLK_EFUSE_EB 172
+#define CLK_EIC_EB 173
+#define CLK_PUB1_REG_EB 174
+#define CLK_ADI_EB 175
+#define CLK_AP_INTC0_EB 176
+#define CLK_AP_INTC1_EB 177
+#define CLK_AP_INTC2_EB 178
+#define CLK_AP_INTC3_EB 179
+#define CLK_AP_INTC4_EB 180
+#define CLK_SPLK_EB 181
+#define CLK_MSPI_EB 182
+#define CLK_PUB0_REG_EB 183
+#define CLK_PIN_EB 184
+#define CLK_AON_CKG_EB 185
+#define CLK_GPU_EB 186
+#define CLK_APCPU_TS0_EB 187
+#define CLK_APCPU_TS1_EB 188
+#define CLK_DAP_EB 189
+#define CLK_I2C_EB 190
+#define CLK_PMU_EB 191
+#define CLK_THM_EB 192
+#define CLK_AUX0_EB 193
+#define CLK_AUX1_EB 194
+#define CLK_AUX2_EB 195
+#define CLK_PROBE_EB 196
+#define CLK_GPU0_AVS_EB 197
+#define CLK_GPU1_AVS_EB 198
+#define CLK_APCPU_WDG_EB 199
+#define CLK_AP_TMR1_EB 200
+#define CLK_AP_TMR2_EB 201
+#define CLK_DISP_EMC_EB 202
+#define CLK_ZIP_EMC_EB 203
+#define CLK_GSP_EMC_EB 204
+#define CLK_OSC_AON_EB 205
+#define CLK_LVDS_TRX_EB 206
+#define CLK_LVDS_TCXO_EB 207
+#define CLK_MDAR_EB 208
+#define CLK_RTC4M0_CAL_EB 209
+#define CLK_RCT100M_CAL_EB 210
+#define CLK_DJTAG_EB 211
+#define CLK_MBOX_EB 212
+#define CLK_AON_DMA_EB 213
+#define CLK_DBG_EMC_EB 214
+#define CLK_LVDS_PLL_DIV_EN 215
+#define CLK_DEF_EB 216
+#define CLK_AON_APB_RSV0 217
+#define CLK_ORP_JTAG_EB 218
+#define CLK_VSP_EB 219
+#define CLK_CAM_EB 220
+#define CLK_DISP_EB 221
+#define CLK_DBG_AXI_IF_EB 222
+#define CLK_SDIO0_2X_EN 223
+#define CLK_SDIO1_2X_EN 224
+#define CLK_SDIO2_2X_EN 225
+#define CLK_EMMC_2X_EN 226
+#define CLK_AGCP_IIS0_EB 227
+#define CLK_AGCP_IIS1_EB 228
+#define CLK_AGCP_IIS2_EB 229
+#define CLK_AGCP_IIS3_EB 230
+#define CLK_AGCP_UART_EB 231
+#define CLK_AGCP_DMACP_EB 232
+#define CLK_AGCP_DMAAP_EB 233
+#define CLK_AGCP_ARC48K_EB 234
+#define CLK_AGCP_SRC44P1K_EB 235
+#define CLK_AGCP_MCDT_EB 236
+#define CLK_AGCP_VBCIFD_EB 237
+#define CLK_AGCP_VBC_EB 238
+#define CLK_AGCP_SPINLOCK_EB 239
+#define CLK_AGCP_ICU_EB 240
+#define CLK_AGCP_AP_ASHB_EB 241
+#define CLK_AGCP_CP_ASHB_EB 242
+#define CLK_AGCP_AUD_EB 243
+#define CLK_AGCP_AUDIF_EB 244
+#define CLK_VSP_DEC_EB 245
+#define CLK_VSP_CKG_EB 246
+#define CLK_VSP_MMU_EB 247
+#define CLK_VSP_ENC_EB 248
+#define CLK_VPP_EB 249
+#define CLK_VSP_26M_EB 250
+#define CLK_VSP_AXI_GATE 251
+#define CLK_VSP_ENC_GATE 252
+#define CLK_VPP_AXI_GATE 253
+#define CLK_VSP_BM_GATE 254
+#define CLK_VSP_ENC_BM_GATE 255
+#define CLK_VPP_BM_GATE 256
+#define CLK_DCAM0_EB 257
+#define CLK_DCAM1_EB 258
+#define CLK_ISP0_EB 259
+#define CLK_CSI0_EB 260
+#define CLK_CSI1_EB 261
+#define CLK_JPG0_EB 262
+#define CLK_JPG1_EB 263
+#define CLK_CAM_CKG_EB 264
+#define CLK_CAM_MMU_EB 265
+#define CLK_ISP1_EB 266
+#define CLK_CPP_EB 267
+#define CLK_MMU_PF_EB 268
+#define CLK_ISP2_EB 269
+#define CLK_DCAM2ISP_IF_EB 270
+#define CLK_ISP2DCAM_IF_EB 271
+#define CLK_ISP_LCLK_EB 272
+#define CLK_ISP_ICLK_EB 273
+#define CLK_ISP_MCLK_EB 274
+#define CLK_ISP_PCLK_EB 275
+#define CLK_ISP_ISP2DCAM_EB 276
+#define CLK_DCAM0_IF_EB 277
+#define CLK_CLK26M_IF_EB 278
+#define CLK_CPHY0_GATE 279
+#define CLK_MIPI_CSI0_GATE 280
+#define CLK_CPHY1_GATE 281
+#define CLK_MIPI_CSI1 282
+#define CLK_DCAM0_AXI_GATE 283
+#define CLK_DCAM1_AXI_GATE 284
+#define CLK_SENSOR0_GATE 285
+#define CLK_SENSOR1_GATE 286
+#define CLK_JPG0_AXI_GATE 287
+#define CLK_GPG1_AXI_GATE 288
+#define CLK_ISP0_AXI_GATE 289
+#define CLK_ISP1_AXI_GATE 290
+#define CLK_ISP2_AXI_GATE 291
+#define CLK_CPP_AXI_GATE 292
+#define CLK_D0_IF_AXI_GATE 293
+#define CLK_D2I_IF_AXI_GATE 294
+#define CLK_I2D_IF_AXI_GATE 295
+#define CLK_SPARE_AXI_GATE 296
+#define CLK_SENSOR2_GATE 297
+#define CLK_D0IF_IN_D_EN 298
+#define CLK_D1IF_IN_D_EN 299
+#define CLK_D0IF_IN_D2I_EN 300
+#define CLK_D1IF_IN_D2I_EN 301
+#define CLK_IA_IN_D2I_EN 302
+#define CLK_IB_IN_D2I_EN 303
+#define CLK_IC_IN_D2I_EN 304
+#define CLK_IA_IN_I_EN 305
+#define CLK_IB_IN_I_EN 306
+#define CLK_IC_IN_I_EN 307
+#define CLK_DISPC0_EB 308
+#define CLK_DISPC1_EB 309
+#define CLK_DISPC_MMU_EB 310
+#define CLK_GSP0_EB 311
+#define CLK_GSP1_EB 312
+#define CLK_GSP0_MMU_EB 313
+#define CLK_GSP1_MMU_EB 314
+#define CLK_DSI0_EB 315
+#define CLK_DSI1_EB 316
+#define CLK_DISP_CKG_EB 317
+#define CLK_DISP_GPU_EB 318
+#define CLK_GPU_MTX_EB 319
+#define CLK_GSP_MTX_EB 320
+#define CLK_TMC_MTX_EB 321
+#define CLK_DISPC_MTX_EB 322
+#define CLK_DPHY0_GATE 323
+#define CLK_DPHY1_GATE 324
+#define CLK_GSP0_A_GATE 325
+#define CLK_GSP1_A_GATE 326
+#define CLK_GSP0_F_GATE 327
+#define CLK_GSP1_F_GATE 328
+#define CLK_D_MTX_F_GATE 329
+#define CLK_D_MTX_A_GATE 330
+#define CLK_D_NOC_F_GATE 331
+#define CLK_D_NOC_A_GATE 332
+#define CLK_GSP_MTX_F_GATE 333
+#define CLK_GSP_MTX_A_GATE 334
+#define CLK_GSP_NOC_F_GATE 335
+#define CLK_GSP_NOC_A_GATE 336
+#define CLK_DISPM0IDLE_GATE 337
+#define CLK_GSPM0IDLE_GATE 338
+#define CLK_SIM0_EB 339
+#define CLK_IIS0_EB 340
+#define CLK_IIS1_EB 341
+#define CLK_IIS2_EB 342
+#define CLK_IIS3_EB 343
+#define CLK_SPI0_EB 344
+#define CLK_SPI1_EB 345
+#define CLK_SPI2_EB 346
+#define CLK_I2C0_EB 347
+#define CLK_I2C1_EB 348
+#define CLK_I2C2_EB 349
+#define CLK_I2C3_EB 350
+#define CLK_I2C4_EB 351
+#define CLK_I2C5_EB 352
+#define CLK_UART0_EB 353
+#define CLK_UART1_EB 354
+#define CLK_UART2_EB 355
+#define CLK_UART3_EB 356
+#define CLK_UART4_EB 357
+#define CLK_AP_CKG_EB 358
+#define CLK_SPI3_EB 359
+
+#define CLK_NUMBER_SC9860 (CLK_SPI3_EB + 1)
+
+#endif /* _DT_BINDINGS_CLK_SC9860_H_ */
--
2.7.4

2017-07-11 11:01:50

by Chunyan Zhang

[permalink] [raw]
Subject: [PATCH V2 10/10] arm64: dts: add clocks for SC9860

Now we have clock driver, so add clock devicetree data for SC9860.

Signed-off-by: Chunyan Zhang <[email protected]>
---
arch/arm64/boot/dts/sprd/sc9860.dtsi | 22 ++++++++++++++++++++++
arch/arm64/boot/dts/sprd/whale2.dtsi | 3 +--
2 files changed, 23 insertions(+), 2 deletions(-)

diff --git a/arch/arm64/boot/dts/sprd/sc9860.dtsi b/arch/arm64/boot/dts/sprd/sc9860.dtsi
index 7b7d8ce..8d3f549 100644
--- a/arch/arm64/boot/dts/sprd/sc9860.dtsi
+++ b/arch/arm64/boot/dts/sprd/sc9860.dtsi
@@ -7,6 +7,7 @@
*/

#include <dt-bindings/interrupt-controller/arm-gic.h>
+#include <dt-bindings/clock/sprd,sc9860-clk.h>
#include "whale2.dtsi"

/ {
@@ -183,6 +184,27 @@
};

soc {
+ clk: clk {
+ compatible = "sprd,sc9860-clk";
+ #clock-cells = <1>;
+ reg = <0 0x20000000 0 0x400>,
+ <0 0x20210000 0 0x3000>,
+ <0 0x402b0000 0 0x4000>,
+ <0 0x402d0000 0 0x400>,
+ <0 0x402e0000 0 0x4000>,
+ <0 0x40400000 0 0x400>,
+ <0 0x40880000 0 0x400>,
+ <0 0x415e0000 0 0x400>,
+ <0 0x60200000 0 0x400>,
+ <0 0x61000000 0 0x400>,
+ <0 0x61100000 0 0x3000>,
+ <0 0x62000000 0 0x4000>,
+ <0 0x62100000 0 0x4000>,
+ <0 0x63000000 0 0x400>,
+ <0 0x63100000 0 0x3000>,
+ <0 0x70b00000 0 0x3000>;
+ };
+
funnel@10001000 { /* SoC Funnel */
compatible = "arm,coresight-funnel", "arm,primecell";
reg = <0 0x10001000 0 0x1000>;
diff --git a/arch/arm64/boot/dts/sprd/whale2.dtsi b/arch/arm64/boot/dts/sprd/whale2.dtsi
index 7c217c5..a4f376e 100644
--- a/arch/arm64/boot/dts/sprd/whale2.dtsi
+++ b/arch/arm64/boot/dts/sprd/whale2.dtsi
@@ -59,13 +59,12 @@
status = "disabled";
};
};
-
};

ext_26m: ext-26m {
compatible = "fixed-clock";
#clock-cells = <0>;
clock-frequency = <26000000>;
- clock-output-names = "ext_26m";
+ clock-output-names = "ext-26m";
};
};
--
2.7.4

2017-07-11 11:01:34

by Chunyan Zhang

[permalink] [raw]
Subject: [PATCH V2 06/10] clk: sprd: add divider clock support

This is a feature that can also be found in sprd composite clocks,
provide a bunch of helpers that can be reused later on.

Original-by: Xiaolong Zhang <[email protected]>
Signed-off-by: Chunyan Zhang <[email protected]>
---
drivers/clk/sprd/Makefile | 1 +
drivers/clk/sprd/div.c | 98 +++++++++++++++++++++++++++++++++++++++++++++++
drivers/clk/sprd/div.h | 77 +++++++++++++++++++++++++++++++++++++
3 files changed, 176 insertions(+)
create mode 100644 drivers/clk/sprd/div.c
create mode 100644 drivers/clk/sprd/div.h

diff --git a/drivers/clk/sprd/Makefile b/drivers/clk/sprd/Makefile
index cee36b5..80e6039 100644
--- a/drivers/clk/sprd/Makefile
+++ b/drivers/clk/sprd/Makefile
@@ -3,3 +3,4 @@ obj-$(CONFIG_SPRD_COMMON_CLK) += clk-sprd.o
clk-sprd-y += common.o
clk-sprd-y += gate.o
clk-sprd-y += mux.o
+clk-sprd-y += div.o
diff --git a/drivers/clk/sprd/div.c b/drivers/clk/sprd/div.c
new file mode 100644
index 0000000..8ba6642
--- /dev/null
+++ b/drivers/clk/sprd/div.c
@@ -0,0 +1,98 @@
+/*
+ * Spreadtrum divider clock driver
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#include <linux/clk-provider.h>
+
+#include "div.h"
+
+DEFINE_SPINLOCK(sprd_div_lock);
+EXPORT_SYMBOL_GPL(sprd_div_lock);
+
+long sprd_div_helper_round_rate(struct sprd_clk_common *common,
+ const struct sprd_div_internal *div,
+ unsigned long rate,
+ unsigned long *parent_rate)
+{
+ return divider_round_rate(&common->hw, rate, parent_rate,
+ NULL, div->width, 0);
+}
+EXPORT_SYMBOL_GPL(sprd_div_helper_round_rate);
+
+static long sprd_div_round_rate(struct clk_hw *hw, unsigned long rate,
+ unsigned long *parent_rate)
+{
+ struct sprd_div *cd = hw_to_sprd_div(hw);
+
+ return sprd_div_helper_round_rate(&cd->common, &cd->div,
+ rate, parent_rate);
+}
+
+unsigned long sprd_div_helper_recalc_rate(struct sprd_clk_common *common,
+ const struct sprd_div_internal *div,
+ unsigned long parent_rate)
+{
+ unsigned long val;
+ u32 reg;
+
+ reg = sprd_clk_readl(common);
+ val = reg >> div->shift;
+ val &= (1 << div->width) - 1;
+
+ return divider_recalc_rate(&common->hw, parent_rate, val, NULL, 0);
+}
+EXPORT_SYMBOL_GPL(sprd_div_helper_recalc_rate);
+
+static unsigned long sprd_div_recalc_rate(struct clk_hw *hw,
+ unsigned long parent_rate)
+{
+ struct sprd_div *cd = hw_to_sprd_div(hw);
+
+ return sprd_div_helper_recalc_rate(&cd->common, &cd->div, parent_rate);
+}
+
+int sprd_div_helper_set_rate(const struct sprd_clk_common *common,
+ const struct sprd_div_internal *div,
+ unsigned long rate,
+ unsigned long parent_rate)
+{
+ unsigned long flags;
+ unsigned long val;
+ u32 reg;
+
+ val = divider_get_val(rate, parent_rate, NULL,
+ div->width, 0);
+
+ spin_lock_irqsave(common->lock, flags);
+
+ reg = sprd_clk_readl(common);
+ reg &= ~GENMASK(div->width + div->shift - 1, div->shift);
+
+ sprd_clk_writel(reg | (val << div->shift), common);
+
+ spin_unlock_irqrestore(common->lock, flags);
+
+ return 0;
+
+}
+EXPORT_SYMBOL_GPL(sprd_div_helper_set_rate);
+
+static int sprd_div_set_rate(struct clk_hw *hw, unsigned long rate,
+ unsigned long parent_rate)
+{
+ struct sprd_div *cd = hw_to_sprd_div(hw);
+
+ return sprd_div_helper_set_rate(&cd->common, &cd->div,
+ rate, parent_rate);
+}
+
+const struct clk_ops sprd_div_ops = {
+ .recalc_rate = sprd_div_recalc_rate,
+ .round_rate = sprd_div_round_rate,
+ .set_rate = sprd_div_set_rate,
+};
+EXPORT_SYMBOL_GPL(sprd_div_ops);
diff --git a/drivers/clk/sprd/div.h b/drivers/clk/sprd/div.h
new file mode 100644
index 0000000..128348e
--- /dev/null
+++ b/drivers/clk/sprd/div.h
@@ -0,0 +1,77 @@
+/*
+ * Spreadtrum divider clock driver
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#ifndef _SPRD_DIV_H_
+#define _SPRD_DIV_H_
+
+#include "common.h"
+
+/**
+ * struct sprd_div_internal - Internal divider description
+ * @shift: Bit offset of the divider in its register
+ * @width: Width of the divider field in its register
+ *
+ * That structure represents a single divider, and is meant to be
+ * embedded in other structures representing the various clock
+ * classes.
+ */
+struct sprd_div_internal {
+ u8 shift;
+ u8 width;
+};
+
+#define _SPRD_DIV_CLK(_shift, _width) \
+ { \
+ .shift = _shift, \
+ .width = _width, \
+ }
+
+struct sprd_div {
+ struct sprd_div_internal div;
+ struct sprd_clk_common common;
+};
+
+#define SPRD_DIV_CLK(_struct, _name, _parent, _reg, \
+ _shift, _width, _flags) \
+ struct sprd_div _struct = { \
+ .div = _SPRD_DIV_CLK(_shift, _width), \
+ .common = { \
+ .reg = _reg, \
+ .lock = &sprd_div_lock, \
+ .hw.init = CLK_HW_INIT(_name, \
+ _parent, \
+ &sprd_div_ops, \
+ _flags), \
+ } \
+ }
+
+static inline struct sprd_div *hw_to_sprd_div(const struct clk_hw *hw)
+{
+ struct sprd_clk_common *common = hw_to_sprd_clk_common(hw);
+
+ return container_of(common, struct sprd_div, common);
+}
+
+long sprd_div_helper_round_rate(struct sprd_clk_common *common,
+ const struct sprd_div_internal *div,
+ unsigned long rate,
+ unsigned long *parent_rate);
+
+unsigned long sprd_div_helper_recalc_rate(struct sprd_clk_common *common,
+ const struct sprd_div_internal *div,
+ unsigned long parent_rate);
+
+int sprd_div_helper_set_rate(const struct sprd_clk_common *common,
+ const struct sprd_div_internal *div,
+ unsigned long rate,
+ unsigned long parent_rate);
+
+extern const struct clk_ops sprd_div_ops;
+extern spinlock_t sprd_div_lock;
+
+#endif /* _SPRD_DIV_H_ */
--
2.7.4

2017-07-11 11:02:29

by Chunyan Zhang

[permalink] [raw]
Subject: [PATCH V2 04/10] clk: sprd: add gate clock support

Some clocks on the Spreadtrum's SoCs are just simple gates. Add
support for those clocks.

Original-by: Xiaolong Zhang <[email protected]>
Signed-off-by: Chunyan Zhang <[email protected]>
---
drivers/clk/sprd/Makefile | 1 +
drivers/clk/sprd/gate.c | 104 ++++++++++++++++++++++++++++++++++++++++++++++
drivers/clk/sprd/gate.h | 58 ++++++++++++++++++++++++++
3 files changed, 163 insertions(+)
create mode 100644 drivers/clk/sprd/gate.c
create mode 100644 drivers/clk/sprd/gate.h

diff --git a/drivers/clk/sprd/Makefile b/drivers/clk/sprd/Makefile
index 74f4b80..8cd5592 100644
--- a/drivers/clk/sprd/Makefile
+++ b/drivers/clk/sprd/Makefile
@@ -1,3 +1,4 @@
obj-$(CONFIG_SPRD_COMMON_CLK) += clk-sprd.o

clk-sprd-y += common.o
+clk-sprd-y += gate.o
diff --git a/drivers/clk/sprd/gate.c b/drivers/clk/sprd/gate.c
new file mode 100644
index 0000000..aa56b2b
--- /dev/null
+++ b/drivers/clk/sprd/gate.c
@@ -0,0 +1,104 @@
+/*
+ * Spreadtrum gate clock driver
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#include <linux/clk-provider.h>
+
+#include "gate.h"
+
+DEFINE_SPINLOCK(sprd_gate_lock);
+EXPORT_SYMBOL_GPL(sprd_gate_lock);
+
+static void sprd_gate_endisable(const struct sprd_gate *sg, u32 en)
+{
+ const struct sprd_clk_common *common = &sg->common;
+ unsigned long flags = 0;
+ u32 reg;
+ int set = sg->flags & CLK_GATE_SET_TO_DISABLE ? 1 : 0;
+
+ set ^= en;
+
+ spin_lock_irqsave(common->lock, flags);
+
+ reg = sprd_clk_readl(common);
+
+ if (set)
+ reg |= sg->op_bit;
+ else
+ reg &= ~sg->op_bit;
+
+ sprd_clk_writel(reg, common);
+
+ spin_unlock_irqrestore(common->lock, flags);
+}
+
+static void clk_sc_gate_endisable(const struct sprd_gate *sg, u32 en)
+{
+ const struct sprd_clk_common *common = &sg->common;
+ unsigned long flags = 0;
+ int set = sg->flags & CLK_GATE_SET_TO_DISABLE ? 1 : 0;
+ u32 offset;
+
+ set ^= en;
+
+ /*
+ * Each set/clear gate clock has three registers:
+ * common->reg - base register
+ * common->reg + offset - set register
+ * common->reg + 2 * offset - clear register
+ */
+ offset = set ? sg->sc_offset : sg->sc_offset * 2;
+
+ spin_lock_irqsave(common->lock, flags);
+ sprd_clk_writel_offset(sg->op_bit, common, offset);
+ spin_unlock_irqrestore(common->lock, flags);
+}
+
+static void sprd_gate_disable(struct clk_hw *hw)
+{
+ struct sprd_gate *sg = hw_to_sprd_gate(hw);
+
+ if (sg->sc_offset)
+ clk_sc_gate_endisable(sg, 0);
+ else
+ sprd_gate_endisable(sg, 0);
+}
+
+static int sprd_gate_enable(struct clk_hw *hw)
+{
+ struct sprd_gate *sg = hw_to_sprd_gate(hw);
+
+ if (sg->sc_offset)
+ clk_sc_gate_endisable(sg, 1);
+ else
+ sprd_gate_endisable(sg, 1);
+
+ return 0;
+}
+
+static int sprd_gate_is_enabled(struct clk_hw *hw)
+{
+ struct sprd_gate *sg = hw_to_sprd_gate(hw);
+ struct sprd_clk_common *common = &sg->common;
+ u32 reg;
+
+ reg = sprd_clk_readl(common);
+
+ if (sg->flags & CLK_GATE_SET_TO_DISABLE)
+ reg ^= sg->op_bit;
+
+ reg &= sg->op_bit;
+
+ return reg ? 1 : 0;
+}
+
+const struct clk_ops sprd_gate_ops = {
+ .disable = sprd_gate_disable,
+ .enable = sprd_gate_enable,
+ .is_enabled = sprd_gate_is_enabled,
+};
+EXPORT_SYMBOL_GPL(sprd_gate_ops);
diff --git a/drivers/clk/sprd/gate.h b/drivers/clk/sprd/gate.h
new file mode 100644
index 0000000..7fb4e49
--- /dev/null
+++ b/drivers/clk/sprd/gate.h
@@ -0,0 +1,58 @@
+/*
+ * Spreadtrum gate clock driver
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#ifndef _SPRD_GATE_H_
+#define _SPRD_GATE_H_
+
+#include "common.h"
+
+struct sprd_gate {
+ u32 op_bit;
+ u16 flags;
+ u16 sc_offset;
+
+ struct sprd_clk_common common;
+};
+
+#define SPRD_GATE_CLK(_struct, _name, _parent, _reg, _sc_offset, \
+ _op_bit, _flags, _gate_flags) \
+ struct sprd_gate _struct = { \
+ .op_bit = _op_bit, \
+ .sc_offset = _sc_offset, \
+ .flags = _gate_flags, \
+ .common = { \
+ .reg = _reg, \
+ .lock = &sprd_gate_lock, \
+ .hw.init = CLK_HW_INIT(_name, \
+ _parent, \
+ &sprd_gate_ops, \
+ _flags), \
+ } \
+ }
+
+static inline struct sprd_gate *hw_to_sprd_gate(const struct clk_hw *hw)
+{
+ struct sprd_clk_common *common = hw_to_sprd_clk_common(hw);
+
+ return container_of(common, struct sprd_gate, common);
+}
+
+static inline void sprd_clk_writel_offset(u32 val,
+ const struct sprd_clk_common *common, u32 offset)
+{
+ writel(val, common->base + common->reg + offset);
+}
+
+void sprd_gate_helper_disable(struct sprd_clk_common *common, u32 gate);
+int sprd_gate_helper_enable(struct sprd_clk_common *common, u32 gate);
+int sprd_gate_helper_is_enabled(struct sprd_clk_common *common, u32 gate);
+
+extern const struct clk_ops sprd_gate_ops;
+extern spinlock_t sprd_gate_lock;
+
+#endif /* _SPRD_GATE_H_ */
--
2.7.4

2017-07-11 11:02:49

by Chunyan Zhang

[permalink] [raw]
Subject: [PATCH V2 07/10] clk: sprd: add composite clock support

This patch introduced composite driveri for Spreadtrum's SoCs. The
functions of this composite clock simply consist of divider and
mux clocks.

Original-by: Xiaolong Zhang <[email protected]>
Signed-off-by: Chunyan Zhang <[email protected]>
---
drivers/clk/sprd/Makefile | 1 +
drivers/clk/sprd/composite.c | 64 ++++++++++++++++++++++++++++++++++++++++++++
drivers/clk/sprd/composite.h | 47 ++++++++++++++++++++++++++++++++
3 files changed, 112 insertions(+)
create mode 100644 drivers/clk/sprd/composite.c
create mode 100644 drivers/clk/sprd/composite.h

diff --git a/drivers/clk/sprd/Makefile b/drivers/clk/sprd/Makefile
index 80e6039..2262e76 100644
--- a/drivers/clk/sprd/Makefile
+++ b/drivers/clk/sprd/Makefile
@@ -4,3 +4,4 @@ clk-sprd-y += common.o
clk-sprd-y += gate.o
clk-sprd-y += mux.o
clk-sprd-y += div.o
+clk-sprd-y += composite.o
diff --git a/drivers/clk/sprd/composite.c b/drivers/clk/sprd/composite.c
new file mode 100644
index 0000000..25b045d
--- /dev/null
+++ b/drivers/clk/sprd/composite.c
@@ -0,0 +1,64 @@
+/*
+ * Spreadtrum composite clock driver
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#include <linux/clk-provider.h>
+
+#include "composite.h"
+
+DEFINE_SPINLOCK(sprd_comp_lock);
+EXPORT_SYMBOL_GPL(sprd_comp_lock);
+
+static long sprd_comp_round_rate(struct clk_hw *hw, unsigned long rate,
+ unsigned long *parent_rate)
+{
+ struct sprd_comp *cc = hw_to_sprd_comp(hw);
+
+ return sprd_div_helper_round_rate(&cc->common, &cc->div,
+ rate, parent_rate);
+}
+
+static unsigned long sprd_comp_recalc_rate(struct clk_hw *hw,
+ unsigned long parent_rate)
+{
+ struct sprd_comp *cc = hw_to_sprd_comp(hw);
+
+ return sprd_div_helper_recalc_rate(&cc->common, &cc->div, parent_rate);
+}
+
+static int sprd_comp_set_rate(struct clk_hw *hw, unsigned long rate,
+ unsigned long parent_rate)
+{
+ struct sprd_comp *cc = hw_to_sprd_comp(hw);
+
+ return sprd_div_helper_set_rate(&cc->common, &cc->div,
+ rate, parent_rate);
+}
+
+static u8 sprd_comp_get_parent(struct clk_hw *hw)
+{
+ struct sprd_comp *cc = hw_to_sprd_comp(hw);
+
+ return sprd_mux_helper_get_parent(&cc->common, &cc->mux);
+}
+
+static int sprd_comp_set_parent(struct clk_hw *hw, u8 index)
+{
+ struct sprd_comp *cc = hw_to_sprd_comp(hw);
+
+ return sprd_mux_helper_set_parent(&cc->common, &cc->mux, index);
+}
+
+const struct clk_ops sprd_comp_ops = {
+ .get_parent = sprd_comp_get_parent,
+ .set_parent = sprd_comp_set_parent,
+
+ .round_rate = sprd_comp_round_rate,
+ .recalc_rate = sprd_comp_recalc_rate,
+ .set_rate = sprd_comp_set_rate,
+};
+EXPORT_SYMBOL_GPL(sprd_comp_ops);
diff --git a/drivers/clk/sprd/composite.h b/drivers/clk/sprd/composite.h
new file mode 100644
index 0000000..f5ca0c9
--- /dev/null
+++ b/drivers/clk/sprd/composite.h
@@ -0,0 +1,47 @@
+/*
+ * Spreadtrum composite clock driver
+ *
+ * Copyright (C) 2017 Spreadtrum, Inc.
+ *
+ * SPDX-License-Identifier: GPL-2.0
+ */
+
+#ifndef _SPRD_COMPOSITE_H_
+#define _SPRD_COMPOSITE_H_
+
+#include "common.h"
+#include "mux.h"
+#include "div.h"
+
+struct sprd_comp {
+ struct sprd_mux_internal mux;
+ struct sprd_div_internal div;
+ struct sprd_clk_common common;
+};
+
+#define SPRD_COMP_CLK(_struct, _name, _parent, _reg, _table, \
+ _mshift, _mwidth, _dshift, _dwidth, _flags) \
+ struct sprd_comp _struct = { \
+ .mux = _SPRD_MUX_CLK(_mshift, _mwidth, _table), \
+ .div = _SPRD_DIV_CLK(_dshift, _dwidth), \
+ .common = { \
+ .reg = _reg, \
+ .lock = &sprd_comp_lock, \
+ .hw.init = CLK_HW_INIT_PARENTS(_name, \
+ _parent, \
+ &sprd_comp_ops, \
+ _flags), \
+ } \
+ }
+
+static inline struct sprd_comp *hw_to_sprd_comp(const struct clk_hw *hw)
+{
+ struct sprd_clk_common *common = hw_to_sprd_clk_common(hw);
+
+ return container_of(common, struct sprd_comp, common);
+}
+
+extern const struct clk_ops sprd_comp_ops;
+extern spinlock_t sprd_comp_lock;
+
+#endif /* _SPRD_COMPOSITE_H_ */
--
2.7.4

2017-07-14 16:10:24

by Rob Herring (Arm)

[permalink] [raw]
Subject: Re: [PATCH V2 02/10] dt-bindings: Add Spreadtrum clock binding documentation

On Tue, Jul 11, 2017 at 06:56:19PM +0800, Chunyan Zhang wrote:
> Introduce a new binding with its documentation for Spreadtrum clock
> sub-framework.
>
> Signed-off-by: Chunyan Zhang <[email protected]>
> ---
> Documentation/devicetree/bindings/clock/sprd.txt | 36 ++++++++++++++++++++++++
> 1 file changed, 36 insertions(+)
> create mode 100644 Documentation/devicetree/bindings/clock/sprd.txt

Acked-by: Rob Herring <[email protected]>

2017-07-17 02:03:02

by Chunyan Zhang

[permalink] [raw]
Subject: Re: [PATCH V2 02/10] dt-bindings: Add Spreadtrum clock binding documentation

On 15 July 2017 at 00:10, Rob Herring <[email protected]> wrote:
> On Tue, Jul 11, 2017 at 06:56:19PM +0800, Chunyan Zhang wrote:
>> Introduce a new binding with its documentation for Spreadtrum clock
>> sub-framework.
>>
>> Signed-off-by: Chunyan Zhang <[email protected]>
>> ---
>> Documentation/devicetree/bindings/clock/sprd.txt | 36 ++++++++++++++++++++++++
>> 1 file changed, 36 insertions(+)
>> create mode 100644 Documentation/devicetree/bindings/clock/sprd.txt
>
> Acked-by: Rob Herring <[email protected]>

Thank you, Rob

Cheers,
Chunyan

2017-07-21 22:57:34

by Stephen Boyd

[permalink] [raw]
Subject: Re: [PATCH V2 02/10] dt-bindings: Add Spreadtrum clock binding documentation

On 07/11, Chunyan Zhang wrote:
> Introduce a new binding with its documentation for Spreadtrum clock
> sub-framework.
>
> Signed-off-by: Chunyan Zhang <[email protected]>
> ---
> Documentation/devicetree/bindings/clock/sprd.txt | 36 ++++++++++++++++++++++++
> 1 file changed, 36 insertions(+)
> create mode 100644 Documentation/devicetree/bindings/clock/sprd.txt
>
> diff --git a/Documentation/devicetree/bindings/clock/sprd.txt b/Documentation/devicetree/bindings/clock/sprd.txt
> new file mode 100644
> index 0000000..c6f3abf
> --- /dev/null
> +++ b/Documentation/devicetree/bindings/clock/sprd.txt
> @@ -0,0 +1,36 @@
> +Spreadtrum Clock Binding
> +------------------------
> +
> +Required properties:
> +- compatible: must contain the following compatible:
> + - "sprd,sc9860-clk" (only support SC9860 for the time being)
> +
> +- reg: Must contain the registers base address and length.
> + Clocks on most of Spreadtrum's SoCs were designed to locate in a few
> + different address areas, so there would be more than one items under
> + this property.
> +
> +- #clock-cells: must be 1
> +
> +Example:
> +
> +clk: clk {

clock-controller for the node name?

> + compatible = "sprd,sc9860-clk";
> + #clock-cells = <1>;
> + reg = <0 0x20000000 0 0x400>,
> + <0 0x20210000 0 0x3000>,
> + <0 0x402b0000 0 0x4000>,
> + <0 0x402d0000 0 0x400>,
> + <0 0x402e0000 0 0x4000>,
> + <0 0x40400000 0 0x400>,
> + <0 0x40880000 0 0x400>,
> + <0 0x415e0000 0 0x400>,
> + <0 0x60200000 0 0x400>,
> + <0 0x61000000 0 0x400>,
> + <0 0x61100000 0 0x3000>,
> + <0 0x62000000 0 0x4000>,
> + <0 0x62100000 0 0x4000>,
> + <0 0x63000000 0 0x400>,
> + <0 0x63100000 0 0x3000>,
> + <0 0x70b00000 0 0x3000>;

I'm still suspecting that we need multiple nodes, for each device
the clocks are embedded in. Mediatek SoCs have a similar design,
and they have many nodes. Does it happen to always be in some
fixed offset inside the different devices that use the clks?

--
Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum,
a Linux Foundation Collaborative Project

2017-07-25 10:27:08

by Chunyan Zhang

[permalink] [raw]
Subject: Re: [PATCH V2 02/10] dt-bindings: Add Spreadtrum clock binding documentation

Hi Stephen,

On 22 July 2017 at 06:57, Stephen Boyd <[email protected]> wrote:
> On 07/11, Chunyan Zhang wrote:
>> Introduce a new binding with its documentation for Spreadtrum clock
>> sub-framework.
>>
>> Signed-off-by: Chunyan Zhang <[email protected]>
>> ---
>> Documentation/devicetree/bindings/clock/sprd.txt | 36 ++++++++++++++++++++++++
>> 1 file changed, 36 insertions(+)
>> create mode 100644 Documentation/devicetree/bindings/clock/sprd.txt
>>
>> diff --git a/Documentation/devicetree/bindings/clock/sprd.txt b/Documentation/devicetree/bindings/clock/sprd.txt
>> new file mode 100644
>> index 0000000..c6f3abf
>> --- /dev/null
>> +++ b/Documentation/devicetree/bindings/clock/sprd.txt
>> @@ -0,0 +1,36 @@
>> +Spreadtrum Clock Binding
>> +------------------------
>> +
>> +Required properties:
>> +- compatible: must contain the following compatible:
>> + - "sprd,sc9860-clk" (only support SC9860 for the time being)
>> +
>> +- reg: Must contain the registers base address and length.
>> + Clocks on most of Spreadtrum's SoCs were designed to locate in a few
>> + different address areas, so there would be more than one items under
>> + this property.
>> +
>> +- #clock-cells: must be 1
>> +
>> +Example:
>> +
>> +clk: clk {
>
> clock-controller for the node name?

Ah, sorry I forgot to address this.

>
>> + compatible = "sprd,sc9860-clk";
>> + #clock-cells = <1>;
>> + reg = <0 0x20000000 0 0x400>,
>> + <0 0x20210000 0 0x3000>,
>> + <0 0x402b0000 0 0x4000>,
>> + <0 0x402d0000 0 0x400>,
>> + <0 0x402e0000 0 0x4000>,
>> + <0 0x40400000 0 0x400>,
>> + <0 0x40880000 0 0x400>,
>> + <0 0x415e0000 0 0x400>,
>> + <0 0x60200000 0 0x400>,
>> + <0 0x61000000 0 0x400>,
>> + <0 0x61100000 0 0x3000>,
>> + <0 0x62000000 0 0x4000>,
>> + <0 0x62100000 0 0x4000>,
>> + <0 0x63000000 0 0x400>,
>> + <0 0x63100000 0 0x3000>,
>> + <0 0x70b00000 0 0x3000>;
>
> I'm still suspecting that we need multiple nodes, for each device
> the clocks are embedded in. Mediatek SoCs have a similar design,
> and they have many nodes. Does it happen to always be in some
> fixed offset inside the different devices that use the clks?

Unfortunately clock design on SC9860 is not the case.

>From the device tree file [1] which we're using internally, we can see
there're 9 ranges of clocks are located on the same address area with
syscons, they respectively are:
<0 0x20210000 0 0x3000>,
<0 0x402b0000 0 0x4000>,
<0 0x402e0000 0 0x4000>,
<0 0x40400000 0 0x400>,
<0 0x415e0000 0 0x400>,
<0 0x61100000 0 0x3000>,
<0 0x62100000 0 0x4000>,
<0 0x63100000 0 0x3000>,
<0 0x70b00000 0 0x3000>;

others ranges (listed below) are only for clocks, neither same with
any devices nor syscons:

<0 0x20000000 0 0x400>, is for AP (application processor) clocks
<0 0x402d0000 0 0x400>, is for AON prediv clocks
<0 0x40880000 0 0x400>,
<0 0x60200000 0 0x400>, is for GPU clocks
<0 0x61000000 0 0x400>, is for VSP clocks
<0 0x62000000 0 0x4000>,is for camera clocks
<0 0x63000000 0 0x400>, is for display clocks

Let's see dcam as an example.
The dcam device is on 0x6220 0000 [2], while dcam clocks are on 0x6200
0000, and also some dcam clocks are on 0x6210 0000 which is the same
address area with a syscon called 'cam_ahb_controller' [3].

I can separate them into multiple nodes, and then there will be 16
clock nodes in dt, isn't it too much?

Which solution do you think is better for our case?


Thanks,
Chunyan


[1] https://github.com/sprdlinux/kernel/blob/sp9860g-1h10/arch/arm64/boot/dts/sprd/whale.dtsi#L29
[2] https://github.com/sprdlinux/kernel/blob/sp9860g-1h10/arch/arm64/boot/dts/sprd/sc9850s.dtsi#L372
[3] https://github.com/sprdlinux/kernel/blob/sp9860g-1h10/arch/arm64/boot/dts/sprd/whale.dtsi#L71

>
> --
> Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum,
> a Linux Foundation Collaborative Project