All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v2 0/5] clk: rockchip: fix handling of fractional dividers
@ 2015-12-22 21:27 ` Heiko Stuebner
  0 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:27 UTC (permalink / raw)
  To: mturquette, sboyd
  Cc: linux-clk, linux-arm-kernel, linux-rockchip, sjoerd.simons, wxt,
	Heiko Stuebner

Essentially unchanged from the first iteration from back in august, just
including additional patches depending on that and fixing fractional
dividers on the rk3036 and spdif parent settings.

In v1, Stephen seemed essentially ok with it but Mike put forward his wish
to use his planned approach for connected clocks for handling this.

While that in itself will be very interesting also for handling Rockchip's
armclk generically, we're now in the situation that everything related
to audio output relies on working fractional dividers to produce the
needed clock frequencies, making audio-output essentially non-working on
all Rockchip socs in mainline at the moment.

So I'm somewhat hoping for some sort of intermediate solution here :-)


changes in v2:
- rebase original 3 patches onto 4.4
- add the 2 new patches from other series, that need that change

Heiko Stuebner (3):
  clk: add flag for clocks that need to be enabled on rate changes
  clk: rockchip: handle mux dependency of fractional dividers
  clk: rockchip: include downstream muxes into fractional dividers

Sjoerd Simons (1):
  clk: rockchip: Allow the RK3288 SPDIF clocks to change their parent

Xing Zheng (1):
  clk: rockchip: rk3036: include downstream muxes into fractional
    dividers

 drivers/clk/clk.c                 |  18 +++++
 drivers/clk/rockchip/clk-rk3036.c |  34 +++++-----
 drivers/clk/rockchip/clk-rk3188.c |  80 +++++++++++-----------
 drivers/clk/rockchip/clk-rk3288.c |  70 +++++++++----------
 drivers/clk/rockchip/clk.c        | 137 ++++++++++++++++++++++++++++++++++----
 drivers/clk/rockchip/clk.h        |  19 ++++++
 include/linux/clk-provider.h      |   1 +
 7 files changed, 254 insertions(+), 105 deletions(-)

-- 
2.6.4

^ permalink raw reply	[flat|nested] 15+ messages in thread

* [PATCH v2 0/5] clk: rockchip: fix handling of fractional dividers
@ 2015-12-22 21:27 ` Heiko Stuebner
  0 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:27 UTC (permalink / raw)
  To: linux-arm-kernel

Essentially unchanged from the first iteration from back in august, just
including additional patches depending on that and fixing fractional
dividers on the rk3036 and spdif parent settings.

In v1, Stephen seemed essentially ok with it but Mike put forward his wish
to use his planned approach for connected clocks for handling this.

While that in itself will be very interesting also for handling Rockchip's
armclk generically, we're now in the situation that everything related
to audio output relies on working fractional dividers to produce the
needed clock frequencies, making audio-output essentially non-working on
all Rockchip socs in mainline at the moment.

So I'm somewhat hoping for some sort of intermediate solution here :-)


changes in v2:
- rebase original 3 patches onto 4.4
- add the 2 new patches from other series, that need that change

Heiko Stuebner (3):
  clk: add flag for clocks that need to be enabled on rate changes
  clk: rockchip: handle mux dependency of fractional dividers
  clk: rockchip: include downstream muxes into fractional dividers

Sjoerd Simons (1):
  clk: rockchip: Allow the RK3288 SPDIF clocks to change their parent

Xing Zheng (1):
  clk: rockchip: rk3036: include downstream muxes into fractional
    dividers

 drivers/clk/clk.c                 |  18 +++++
 drivers/clk/rockchip/clk-rk3036.c |  34 +++++-----
 drivers/clk/rockchip/clk-rk3188.c |  80 +++++++++++-----------
 drivers/clk/rockchip/clk-rk3288.c |  70 +++++++++----------
 drivers/clk/rockchip/clk.c        | 137 ++++++++++++++++++++++++++++++++++----
 drivers/clk/rockchip/clk.h        |  19 ++++++
 include/linux/clk-provider.h      |   1 +
 7 files changed, 254 insertions(+), 105 deletions(-)

-- 
2.6.4

^ permalink raw reply	[flat|nested] 15+ messages in thread

* [PATCH v2 1/5] clk: add flag for clocks that need to be enabled on rate changes
  2015-12-22 21:27 ` Heiko Stuebner
@ 2015-12-22 21:27   ` Heiko Stuebner
  -1 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:27 UTC (permalink / raw)
  To: mturquette, sboyd
  Cc: linux-clk, linux-arm-kernel, linux-rockchip, sjoerd.simons, wxt,
	Heiko Stuebner

Some clocks need to be enabled to accept rate changes. This patch adds a
new flag CLK_SET_RATE_UNGATE that lets clk_change_rate enable the clock
before trying to change the rate and disable it again afterwards.
This of course doesn't effect clocks that are already running at that
point, as their refcount will only temporarily increase.

Signed-off-by: Heiko Stuebner <heiko@sntech.de>
Tested-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
Reviewed-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
---
 drivers/clk/clk.c            | 18 ++++++++++++++++++
 include/linux/clk-provider.h |  1 +
 2 files changed, 19 insertions(+)

diff --git a/drivers/clk/clk.c b/drivers/clk/clk.c
index f13c3f4..bd64a94 100644
--- a/drivers/clk/clk.c
+++ b/drivers/clk/clk.c
@@ -1443,6 +1443,15 @@ static void clk_change_rate(struct clk_core *core)
 	else if (core->parent)
 		best_parent_rate = core->parent->rate;
 
+	if (core->flags & CLK_SET_RATE_UNGATE) {
+		unsigned long flags;
+
+		clk_core_prepare(core);
+		flags = clk_enable_lock();
+		clk_core_enable(core);
+		clk_enable_unlock(flags);
+	}
+
 	if (core->new_parent && core->new_parent != core->parent) {
 		old_parent = __clk_set_parent_before(core, core->new_parent);
 		trace_clk_set_parent(core, core->new_parent);
@@ -1469,6 +1478,15 @@ static void clk_change_rate(struct clk_core *core)
 
 	core->rate = clk_recalc(core, best_parent_rate);
 
+	if (core->flags & CLK_SET_RATE_UNGATE) {
+		unsigned long flags;
+
+		flags = clk_enable_lock();
+		clk_core_disable(core);
+		clk_enable_unlock(flags);
+		clk_core_unprepare(core);
+	}
+
 	if (core->notifier_count && old_rate != core->rate)
 		__clk_notify(core, POST_RATE_CHANGE, old_rate, core->rate);
 
diff --git a/include/linux/clk-provider.h b/include/linux/clk-provider.h
index c56988a..a971ce4 100644
--- a/include/linux/clk-provider.h
+++ b/include/linux/clk-provider.h
@@ -31,6 +31,7 @@
 #define CLK_SET_RATE_NO_REPARENT BIT(7) /* don't re-parent on rate change */
 #define CLK_GET_ACCURACY_NOCACHE BIT(8) /* do not use the cached clk accuracy */
 #define CLK_RECALC_NEW_RATES	BIT(9) /* recalc rates after notifications */
+#define CLK_SET_RATE_UNGATE	BIT(10) /* clock needs to run to set rate */
 
 struct clk;
 struct clk_hw;
-- 
2.6.4

^ permalink raw reply related	[flat|nested] 15+ messages in thread

* [PATCH v2 1/5] clk: add flag for clocks that need to be enabled on rate changes
@ 2015-12-22 21:27   ` Heiko Stuebner
  0 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:27 UTC (permalink / raw)
  To: linux-arm-kernel

Some clocks need to be enabled to accept rate changes. This patch adds a
new flag CLK_SET_RATE_UNGATE that lets clk_change_rate enable the clock
before trying to change the rate and disable it again afterwards.
This of course doesn't effect clocks that are already running at that
point, as their refcount will only temporarily increase.

Signed-off-by: Heiko Stuebner <heiko@sntech.de>
Tested-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
Reviewed-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
---
 drivers/clk/clk.c            | 18 ++++++++++++++++++
 include/linux/clk-provider.h |  1 +
 2 files changed, 19 insertions(+)

diff --git a/drivers/clk/clk.c b/drivers/clk/clk.c
index f13c3f4..bd64a94 100644
--- a/drivers/clk/clk.c
+++ b/drivers/clk/clk.c
@@ -1443,6 +1443,15 @@ static void clk_change_rate(struct clk_core *core)
 	else if (core->parent)
 		best_parent_rate = core->parent->rate;
 
+	if (core->flags & CLK_SET_RATE_UNGATE) {
+		unsigned long flags;
+
+		clk_core_prepare(core);
+		flags = clk_enable_lock();
+		clk_core_enable(core);
+		clk_enable_unlock(flags);
+	}
+
 	if (core->new_parent && core->new_parent != core->parent) {
 		old_parent = __clk_set_parent_before(core, core->new_parent);
 		trace_clk_set_parent(core, core->new_parent);
@@ -1469,6 +1478,15 @@ static void clk_change_rate(struct clk_core *core)
 
 	core->rate = clk_recalc(core, best_parent_rate);
 
+	if (core->flags & CLK_SET_RATE_UNGATE) {
+		unsigned long flags;
+
+		flags = clk_enable_lock();
+		clk_core_disable(core);
+		clk_enable_unlock(flags);
+		clk_core_unprepare(core);
+	}
+
 	if (core->notifier_count && old_rate != core->rate)
 		__clk_notify(core, POST_RATE_CHANGE, old_rate, core->rate);
 
diff --git a/include/linux/clk-provider.h b/include/linux/clk-provider.h
index c56988a..a971ce4 100644
--- a/include/linux/clk-provider.h
+++ b/include/linux/clk-provider.h
@@ -31,6 +31,7 @@
 #define CLK_SET_RATE_NO_REPARENT BIT(7) /* don't re-parent on rate change */
 #define CLK_GET_ACCURACY_NOCACHE BIT(8) /* do not use the cached clk accuracy */
 #define CLK_RECALC_NEW_RATES	BIT(9) /* recalc rates after notifications */
+#define CLK_SET_RATE_UNGATE	BIT(10) /* clock needs to run to set rate */
 
 struct clk;
 struct clk_hw;
-- 
2.6.4

^ permalink raw reply related	[flat|nested] 15+ messages in thread

* [PATCH v2 2/5] clk: rockchip: handle mux dependency of fractional dividers
  2015-12-22 21:27 ` Heiko Stuebner
@ 2015-12-22 21:27   ` Heiko Stuebner
  -1 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:27 UTC (permalink / raw)
  To: mturquette, sboyd
  Cc: linux-clk, linux-arm-kernel, linux-rockchip, sjoerd.simons, wxt,
	Heiko Stuebner

The fractional dividers of Rockchip SoCs contain an "auto-gating-feature"
that requires the downstream mux to actually point to the fractional
divider and the fractional divider gate to be enabled, for it to really
accept changes to the divider ratio.

The downstream muxes themselfs are not generic enough to include them
directly into the fractional divider, as they have varying sources of
parent clocks including not only clocks related to the fractional
dividers but other clocks as well.

To solve this, allow our clock branches to specify direct child clock-
branches in the new child property, let the fractional divider register
its downstream mux through this and add a clock notifier that temporarily
switches the mux setting when it notices rate changes to the fractional
divider.

Signed-off-by: Heiko Stuebner <heiko@sntech.de>
Tested-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
Reviewed-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
---
 drivers/clk/rockchip/clk.c | 137 ++++++++++++++++++++++++++++++++++++++++-----
 drivers/clk/rockchip/clk.h |  19 +++++++
 2 files changed, 142 insertions(+), 14 deletions(-)

diff --git a/drivers/clk/rockchip/clk.c b/drivers/clk/rockchip/clk.c
index 443d6f0..d9a0b5d 100644
--- a/drivers/clk/rockchip/clk.c
+++ b/drivers/clk/rockchip/clk.c
@@ -102,22 +102,82 @@ static struct clk *rockchip_clk_register_branch(const char *name,
 	return clk;
 }
 
+struct rockchip_clk_frac {
+	struct notifier_block			clk_nb;
+	struct clk_fractional_divider		div;
+	struct clk_gate				gate;
+
+	struct clk_mux				mux;
+	const struct clk_ops			*mux_ops;
+	int					mux_frac_idx;
+
+	bool					rate_change_remuxed;
+	int					rate_change_idx;
+};
+
+#define to_rockchip_clk_frac_nb(nb) \
+			container_of(nb, struct rockchip_clk_frac, clk_nb)
+
+static int rockchip_clk_frac_notifier_cb(struct notifier_block *nb,
+					 unsigned long event, void *data)
+{
+	struct clk_notifier_data *ndata = data;
+	struct rockchip_clk_frac *frac = to_rockchip_clk_frac_nb(nb);
+	struct clk_mux *frac_mux = &frac->mux;
+	int ret = 0;
+
+	pr_debug("%s: event %lu, old_rate %lu, new_rate: %lu\n",
+		 __func__, event, ndata->old_rate, ndata->new_rate);
+	if (event == PRE_RATE_CHANGE) {
+		frac->rate_change_idx = frac->mux_ops->get_parent(&frac_mux->hw);
+		if (frac->rate_change_idx != frac->mux_frac_idx) {
+			frac->mux_ops->set_parent(&frac_mux->hw, frac->mux_frac_idx);
+			frac->rate_change_remuxed = 1;
+		}
+	} else if (event == POST_RATE_CHANGE) {
+		/*
+		 * The POST_RATE_CHANGE notifier runs directly after the
+		 * divider clock is set in clk_change_rate, so we'll have
+		 * remuxed back to the original parent before clk_change_rate
+		 * reaches the mux itself.
+		 */
+		if (frac->rate_change_remuxed) {
+			frac->mux_ops->set_parent(&frac_mux->hw, frac->rate_change_idx);
+			frac->rate_change_remuxed = 0;
+		}
+	}
+
+	return notifier_from_errno(ret);
+}
+
 static struct clk *rockchip_clk_register_frac_branch(const char *name,
 		const char *const *parent_names, u8 num_parents,
 		void __iomem *base, int muxdiv_offset, u8 div_flags,
 		int gate_offset, u8 gate_shift, u8 gate_flags,
-		unsigned long flags, spinlock_t *lock)
+		unsigned long flags, struct rockchip_clk_branch *child,
+		spinlock_t *lock)
 {
+	struct rockchip_clk_frac *frac;
 	struct clk *clk;
 	struct clk_gate *gate = NULL;
 	struct clk_fractional_divider *div = NULL;
 	const struct clk_ops *div_ops = NULL, *gate_ops = NULL;
 
-	if (gate_offset >= 0) {
-		gate = kzalloc(sizeof(*gate), GFP_KERNEL);
-		if (!gate)
-			return ERR_PTR(-ENOMEM);
+	if (muxdiv_offset < 0)
+		return ERR_PTR(-EINVAL);
 
+	if (child && child->branch_type != branch_mux) {
+		pr_err("%s: fractional child clock for %s can only be a mux\n",
+		       __func__, name);
+		return ERR_PTR(-EINVAL);
+	}
+
+	frac = kzalloc(sizeof(*frac), GFP_KERNEL);
+	if (!frac)
+		return ERR_PTR(-ENOMEM);
+
+	if (gate_offset >= 0) {
+		gate = &frac->gate;
 		gate->flags = gate_flags;
 		gate->reg = base + gate_offset;
 		gate->bit_idx = gate_shift;
@@ -125,13 +185,7 @@ static struct clk *rockchip_clk_register_frac_branch(const char *name,
 		gate_ops = &clk_gate_ops;
 	}
 
-	if (muxdiv_offset < 0)
-		return ERR_PTR(-EINVAL);
-
-	div = kzalloc(sizeof(*div), GFP_KERNEL);
-	if (!div)
-		return ERR_PTR(-ENOMEM);
-
+	div = &frac->div;
 	div->flags = div_flags;
 	div->reg = base + muxdiv_offset;
 	div->mshift = 16;
@@ -147,7 +201,61 @@ static struct clk *rockchip_clk_register_frac_branch(const char *name,
 				     NULL, NULL,
 				     &div->hw, div_ops,
 				     gate ? &gate->hw : NULL, gate_ops,
-				     flags);
+				     flags | CLK_SET_RATE_UNGATE);
+	if (IS_ERR(clk)) {
+		kfree(frac);
+		return clk;
+	}
+
+	if (child) {
+		struct clk_mux *frac_mux = &frac->mux;
+		struct clk_init_data init;
+		struct clk *mux_clk;
+		int i, ret;
+
+		frac->mux_frac_idx = -1;
+		for (i = 0; i < child->num_parents; i++) {
+			if (!strcmp(name, child->parent_names[i])) {
+				pr_debug("%s: found fractional parent in mux at pos %d\n",
+					 __func__, i);
+				frac->mux_frac_idx = i;
+				break;
+			}
+		}
+
+		frac->mux_ops = &clk_mux_ops;
+		frac->clk_nb.notifier_call = rockchip_clk_frac_notifier_cb;
+
+		frac_mux->reg = base + child->muxdiv_offset;
+		frac_mux->shift = child->mux_shift;
+		frac_mux->mask = BIT(child->mux_width) - 1;
+		frac_mux->flags = child->mux_flags;
+		frac_mux->lock = lock;
+		frac_mux->hw.init = &init;
+
+		init.name = child->name;
+		init.flags = child->flags | CLK_SET_RATE_PARENT;
+		init.ops = frac->mux_ops;
+		init.parent_names = child->parent_names;
+		init.num_parents = child->num_parents;
+
+		mux_clk = clk_register(NULL, &frac_mux->hw);
+		if (IS_ERR(mux_clk))
+			return clk;
+
+		rockchip_clk_add_lookup(mux_clk, child->id);
+
+		/* notifier on the fraction divider to catch rate changes */
+		if (frac->mux_frac_idx >= 0) {
+			ret = clk_notifier_register(clk, &frac->clk_nb);
+			if (ret)
+				pr_err("%s: failed to register clock notifier for %s\n",
+						__func__, name);
+		} else {
+			pr_warn("%s: could not find %s as parent of %s, rate changes may not work\n",
+				__func__, name, child->name);
+		}
+	}
 
 	return clk;
 }
@@ -251,7 +359,8 @@ void __init rockchip_clk_register_branches(
 				list->parent_names, list->num_parents,
 				reg_base, list->muxdiv_offset, list->div_flags,
 				list->gate_offset, list->gate_shift,
-				list->gate_flags, flags, &clk_lock);
+				list->gate_flags, flags, list->child,
+				&clk_lock);
 			break;
 		case branch_gate:
 			flags |= CLK_SET_RATE_PARENT;
diff --git a/drivers/clk/rockchip/clk.h b/drivers/clk/rockchip/clk.h
index 809ef81..3f71ee5 100644
--- a/drivers/clk/rockchip/clk.h
+++ b/drivers/clk/rockchip/clk.h
@@ -274,6 +274,7 @@ struct rockchip_clk_branch {
 	int				gate_offset;
 	u8				gate_shift;
 	u8				gate_flags;
+	struct rockchip_clk_branch	*child;
 };
 
 #define COMPOSITE(_id, cname, pnames, f, mo, ms, mw, mf, ds, dw,\
@@ -408,6 +409,24 @@ struct rockchip_clk_branch {
 		.gate_flags	= gf,				\
 	}
 
+#define COMPOSITE_FRACMUX(_id, cname, pname, f, mo, df, go, gs, gf, ch) \
+	{							\
+		.id		= _id,				\
+		.branch_type	= branch_fraction_divider,	\
+		.name		= cname,			\
+		.parent_names	= (const char *[]){ pname },	\
+		.num_parents	= 1,				\
+		.flags		= f,				\
+		.muxdiv_offset	= mo,				\
+		.div_shift	= 16,				\
+		.div_width	= 16,				\
+		.div_flags	= df,				\
+		.gate_offset	= go,				\
+		.gate_shift	= gs,				\
+		.gate_flags	= gf,				\
+		.child		= &(struct rockchip_clk_branch)ch, \
+	}
+
 #define MUX(_id, cname, pnames, f, o, s, w, mf)			\
 	{							\
 		.id		= _id,				\
-- 
2.6.4

^ permalink raw reply related	[flat|nested] 15+ messages in thread

* [PATCH v2 2/5] clk: rockchip: handle mux dependency of fractional dividers
@ 2015-12-22 21:27   ` Heiko Stuebner
  0 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:27 UTC (permalink / raw)
  To: linux-arm-kernel

The fractional dividers of Rockchip SoCs contain an "auto-gating-feature"
that requires the downstream mux to actually point to the fractional
divider and the fractional divider gate to be enabled, for it to really
accept changes to the divider ratio.

The downstream muxes themselfs are not generic enough to include them
directly into the fractional divider, as they have varying sources of
parent clocks including not only clocks related to the fractional
dividers but other clocks as well.

To solve this, allow our clock branches to specify direct child clock-
branches in the new child property, let the fractional divider register
its downstream mux through this and add a clock notifier that temporarily
switches the mux setting when it notices rate changes to the fractional
divider.

Signed-off-by: Heiko Stuebner <heiko@sntech.de>
Tested-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
Reviewed-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
---
 drivers/clk/rockchip/clk.c | 137 ++++++++++++++++++++++++++++++++++++++++-----
 drivers/clk/rockchip/clk.h |  19 +++++++
 2 files changed, 142 insertions(+), 14 deletions(-)

diff --git a/drivers/clk/rockchip/clk.c b/drivers/clk/rockchip/clk.c
index 443d6f0..d9a0b5d 100644
--- a/drivers/clk/rockchip/clk.c
+++ b/drivers/clk/rockchip/clk.c
@@ -102,22 +102,82 @@ static struct clk *rockchip_clk_register_branch(const char *name,
 	return clk;
 }
 
+struct rockchip_clk_frac {
+	struct notifier_block			clk_nb;
+	struct clk_fractional_divider		div;
+	struct clk_gate				gate;
+
+	struct clk_mux				mux;
+	const struct clk_ops			*mux_ops;
+	int					mux_frac_idx;
+
+	bool					rate_change_remuxed;
+	int					rate_change_idx;
+};
+
+#define to_rockchip_clk_frac_nb(nb) \
+			container_of(nb, struct rockchip_clk_frac, clk_nb)
+
+static int rockchip_clk_frac_notifier_cb(struct notifier_block *nb,
+					 unsigned long event, void *data)
+{
+	struct clk_notifier_data *ndata = data;
+	struct rockchip_clk_frac *frac = to_rockchip_clk_frac_nb(nb);
+	struct clk_mux *frac_mux = &frac->mux;
+	int ret = 0;
+
+	pr_debug("%s: event %lu, old_rate %lu, new_rate: %lu\n",
+		 __func__, event, ndata->old_rate, ndata->new_rate);
+	if (event == PRE_RATE_CHANGE) {
+		frac->rate_change_idx = frac->mux_ops->get_parent(&frac_mux->hw);
+		if (frac->rate_change_idx != frac->mux_frac_idx) {
+			frac->mux_ops->set_parent(&frac_mux->hw, frac->mux_frac_idx);
+			frac->rate_change_remuxed = 1;
+		}
+	} else if (event == POST_RATE_CHANGE) {
+		/*
+		 * The POST_RATE_CHANGE notifier runs directly after the
+		 * divider clock is set in clk_change_rate, so we'll have
+		 * remuxed back to the original parent before clk_change_rate
+		 * reaches the mux itself.
+		 */
+		if (frac->rate_change_remuxed) {
+			frac->mux_ops->set_parent(&frac_mux->hw, frac->rate_change_idx);
+			frac->rate_change_remuxed = 0;
+		}
+	}
+
+	return notifier_from_errno(ret);
+}
+
 static struct clk *rockchip_clk_register_frac_branch(const char *name,
 		const char *const *parent_names, u8 num_parents,
 		void __iomem *base, int muxdiv_offset, u8 div_flags,
 		int gate_offset, u8 gate_shift, u8 gate_flags,
-		unsigned long flags, spinlock_t *lock)
+		unsigned long flags, struct rockchip_clk_branch *child,
+		spinlock_t *lock)
 {
+	struct rockchip_clk_frac *frac;
 	struct clk *clk;
 	struct clk_gate *gate = NULL;
 	struct clk_fractional_divider *div = NULL;
 	const struct clk_ops *div_ops = NULL, *gate_ops = NULL;
 
-	if (gate_offset >= 0) {
-		gate = kzalloc(sizeof(*gate), GFP_KERNEL);
-		if (!gate)
-			return ERR_PTR(-ENOMEM);
+	if (muxdiv_offset < 0)
+		return ERR_PTR(-EINVAL);
 
+	if (child && child->branch_type != branch_mux) {
+		pr_err("%s: fractional child clock for %s can only be a mux\n",
+		       __func__, name);
+		return ERR_PTR(-EINVAL);
+	}
+
+	frac = kzalloc(sizeof(*frac), GFP_KERNEL);
+	if (!frac)
+		return ERR_PTR(-ENOMEM);
+
+	if (gate_offset >= 0) {
+		gate = &frac->gate;
 		gate->flags = gate_flags;
 		gate->reg = base + gate_offset;
 		gate->bit_idx = gate_shift;
@@ -125,13 +185,7 @@ static struct clk *rockchip_clk_register_frac_branch(const char *name,
 		gate_ops = &clk_gate_ops;
 	}
 
-	if (muxdiv_offset < 0)
-		return ERR_PTR(-EINVAL);
-
-	div = kzalloc(sizeof(*div), GFP_KERNEL);
-	if (!div)
-		return ERR_PTR(-ENOMEM);
-
+	div = &frac->div;
 	div->flags = div_flags;
 	div->reg = base + muxdiv_offset;
 	div->mshift = 16;
@@ -147,7 +201,61 @@ static struct clk *rockchip_clk_register_frac_branch(const char *name,
 				     NULL, NULL,
 				     &div->hw, div_ops,
 				     gate ? &gate->hw : NULL, gate_ops,
-				     flags);
+				     flags | CLK_SET_RATE_UNGATE);
+	if (IS_ERR(clk)) {
+		kfree(frac);
+		return clk;
+	}
+
+	if (child) {
+		struct clk_mux *frac_mux = &frac->mux;
+		struct clk_init_data init;
+		struct clk *mux_clk;
+		int i, ret;
+
+		frac->mux_frac_idx = -1;
+		for (i = 0; i < child->num_parents; i++) {
+			if (!strcmp(name, child->parent_names[i])) {
+				pr_debug("%s: found fractional parent in mux at pos %d\n",
+					 __func__, i);
+				frac->mux_frac_idx = i;
+				break;
+			}
+		}
+
+		frac->mux_ops = &clk_mux_ops;
+		frac->clk_nb.notifier_call = rockchip_clk_frac_notifier_cb;
+
+		frac_mux->reg = base + child->muxdiv_offset;
+		frac_mux->shift = child->mux_shift;
+		frac_mux->mask = BIT(child->mux_width) - 1;
+		frac_mux->flags = child->mux_flags;
+		frac_mux->lock = lock;
+		frac_mux->hw.init = &init;
+
+		init.name = child->name;
+		init.flags = child->flags | CLK_SET_RATE_PARENT;
+		init.ops = frac->mux_ops;
+		init.parent_names = child->parent_names;
+		init.num_parents = child->num_parents;
+
+		mux_clk = clk_register(NULL, &frac_mux->hw);
+		if (IS_ERR(mux_clk))
+			return clk;
+
+		rockchip_clk_add_lookup(mux_clk, child->id);
+
+		/* notifier on the fraction divider to catch rate changes */
+		if (frac->mux_frac_idx >= 0) {
+			ret = clk_notifier_register(clk, &frac->clk_nb);
+			if (ret)
+				pr_err("%s: failed to register clock notifier for %s\n",
+						__func__, name);
+		} else {
+			pr_warn("%s: could not find %s as parent of %s, rate changes may not work\n",
+				__func__, name, child->name);
+		}
+	}
 
 	return clk;
 }
@@ -251,7 +359,8 @@ void __init rockchip_clk_register_branches(
 				list->parent_names, list->num_parents,
 				reg_base, list->muxdiv_offset, list->div_flags,
 				list->gate_offset, list->gate_shift,
-				list->gate_flags, flags, &clk_lock);
+				list->gate_flags, flags, list->child,
+				&clk_lock);
 			break;
 		case branch_gate:
 			flags |= CLK_SET_RATE_PARENT;
diff --git a/drivers/clk/rockchip/clk.h b/drivers/clk/rockchip/clk.h
index 809ef81..3f71ee5 100644
--- a/drivers/clk/rockchip/clk.h
+++ b/drivers/clk/rockchip/clk.h
@@ -274,6 +274,7 @@ struct rockchip_clk_branch {
 	int				gate_offset;
 	u8				gate_shift;
 	u8				gate_flags;
+	struct rockchip_clk_branch	*child;
 };
 
 #define COMPOSITE(_id, cname, pnames, f, mo, ms, mw, mf, ds, dw,\
@@ -408,6 +409,24 @@ struct rockchip_clk_branch {
 		.gate_flags	= gf,				\
 	}
 
+#define COMPOSITE_FRACMUX(_id, cname, pname, f, mo, df, go, gs, gf, ch) \
+	{							\
+		.id		= _id,				\
+		.branch_type	= branch_fraction_divider,	\
+		.name		= cname,			\
+		.parent_names	= (const char *[]){ pname },	\
+		.num_parents	= 1,				\
+		.flags		= f,				\
+		.muxdiv_offset	= mo,				\
+		.div_shift	= 16,				\
+		.div_width	= 16,				\
+		.div_flags	= df,				\
+		.gate_offset	= go,				\
+		.gate_shift	= gs,				\
+		.gate_flags	= gf,				\
+		.child		= &(struct rockchip_clk_branch)ch, \
+	}
+
 #define MUX(_id, cname, pnames, f, o, s, w, mf)			\
 	{							\
 		.id		= _id,				\
-- 
2.6.4

^ permalink raw reply related	[flat|nested] 15+ messages in thread

* [PATCH v2 3/5] clk: rockchip: include downstream muxes into fractional dividers
  2015-12-22 21:27 ` Heiko Stuebner
@ 2015-12-22 21:28   ` Heiko Stuebner
  -1 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:28 UTC (permalink / raw)
  To: mturquette, sboyd
  Cc: linux-clk, linux-arm-kernel, linux-rockchip, sjoerd.simons, wxt,
	Heiko Stuebner

Use the newly introduced possibility to combine the fractional dividers
with their downstream muxes for all fractional dividers on currently
supported Rockchip SoCs.

Signed-off-by: Heiko Stuebner <heiko@sntech.de>
Tested-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
Reviewed-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
---
 drivers/clk/rockchip/clk-rk3188.c | 80 +++++++++++++++++++--------------------
 drivers/clk/rockchip/clk-rk3288.c | 66 ++++++++++++++++----------------
 2 files changed, 74 insertions(+), 72 deletions(-)

diff --git a/drivers/clk/rockchip/clk-rk3188.c b/drivers/clk/rockchip/clk-rk3188.c
index c2c35d4..6398a91 100644
--- a/drivers/clk/rockchip/clk-rk3188.c
+++ b/drivers/clk/rockchip/clk-rk3188.c
@@ -335,11 +335,11 @@ static struct rockchip_clk_branch common_clk_branches[] __initdata = {
 	COMPOSITE(0, "hsadc_src", mux_pll_src_gpll_cpll_p, 0,
 			RK2928_CLKSEL_CON(22), 0, 1, MFLAGS, 8, 8, DFLAGS,
 			RK2928_CLKGATE_CON(2), 6, GFLAGS),
-	COMPOSITE_FRAC(0, "hsadc_frac", "hsadc_src", 0,
+	COMPOSITE_FRACMUX(0, "hsadc_frac", "hsadc_src", 0,
 			RK2928_CLKSEL_CON(23), 0,
-			RK2928_CLKGATE_CON(2), 7, GFLAGS),
-	MUX(0, "sclk_hsadc_out", mux_sclk_hsadc_p, 0,
-			RK2928_CLKSEL_CON(22), 4, 2, MFLAGS),
+			RK2928_CLKGATE_CON(2), 7, GFLAGS,
+		MUX(0, "sclk_hsadc_out", mux_sclk_hsadc_p, 0,
+				RK2928_CLKSEL_CON(22), 4, 2, MFLAGS)),
 	INVERTER(SCLK_HSADC, "sclk_hsadc", "sclk_hsadc_out",
 			RK2928_CLKSEL_CON(22), 7, IFLAGS),
 
@@ -350,11 +350,11 @@ static struct rockchip_clk_branch common_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "spdif_pre", "i2s_src", 0,
 			RK2928_CLKSEL_CON(5), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 13, GFLAGS),
-	COMPOSITE_FRAC(0, "spdif_frac", "spdif_pre", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "spdif_frac", "spdif_pll", CLK_SET_RATE_PARENT,
 			RK2928_CLKSEL_CON(9), 0,
-			RK2928_CLKGATE_CON(0), 14, GFLAGS),
-	MUX(SCLK_SPDIF, "sclk_spdif", mux_sclk_spdif_p, CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(5), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(0), 14, GFLAGS,
+		MUX(SCLK_SPDIF, "sclk_spdif", mux_sclk_spdif_p, CLK_SET_RATE_PARENT,
+				RK2928_CLKSEL_CON(5), 8, 2, MFLAGS)),
 
 	/*
 	 * Clock-Architecture Diagram 4
@@ -385,35 +385,35 @@ static struct rockchip_clk_branch common_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "uart0_pre", "uart_src", 0,
 			RK2928_CLKSEL_CON(13), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(1), 8, GFLAGS),
-	COMPOSITE_FRAC(0, "uart0_frac", "uart0_pre", 0,
+	COMPOSITE_FRACMUX(0, "uart0_frac", "uart0_pre", 0,
 			RK2928_CLKSEL_CON(17), 0,
-			RK2928_CLKGATE_CON(1), 9, GFLAGS),
-	MUX(SCLK_UART0, "sclk_uart0", mux_sclk_uart0_p, 0,
-			RK2928_CLKSEL_CON(13), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(1), 9, GFLAGS,
+		MUX(SCLK_UART0, "sclk_uart0", mux_sclk_uart0_p, 0,
+				RK2928_CLKSEL_CON(13), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart1_pre", "uart_src", 0,
 			RK2928_CLKSEL_CON(14), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(1), 10, GFLAGS),
-	COMPOSITE_FRAC(0, "uart1_frac", "uart1_pre", 0,
+	COMPOSITE_FRACMUX(0, "uart1_frac", "uart1_pre", 0,
 			RK2928_CLKSEL_CON(18), 0,
-			RK2928_CLKGATE_CON(1), 11, GFLAGS),
-	MUX(SCLK_UART1, "sclk_uart1", mux_sclk_uart1_p, 0,
-			RK2928_CLKSEL_CON(14), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(1), 11, GFLAGS,
+		MUX(SCLK_UART1, "sclk_uart1", mux_sclk_uart1_p, 0,
+				RK2928_CLKSEL_CON(14), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart2_pre", "uart_src", 0,
 			RK2928_CLKSEL_CON(15), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(1), 12, GFLAGS),
-	COMPOSITE_FRAC(0, "uart2_frac", "uart2_pre", 0,
+	COMPOSITE_FRACMUX(0, "uart2_frac", "uart2_pre", 0,
 			RK2928_CLKSEL_CON(19), 0,
-			RK2928_CLKGATE_CON(1), 13, GFLAGS),
-	MUX(SCLK_UART2, "sclk_uart2", mux_sclk_uart2_p, 0,
-			RK2928_CLKSEL_CON(15), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(1), 13, GFLAGS,
+		MUX(SCLK_UART2, "sclk_uart2", mux_sclk_uart2_p, 0,
+				RK2928_CLKSEL_CON(15), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart3_pre", "uart_src", 0,
 			RK2928_CLKSEL_CON(16), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(1), 14, GFLAGS),
-	COMPOSITE_FRAC(0, "uart3_frac", "uart3_pre", 0,
+	COMPOSITE_FRACMUX(0, "uart3_frac", "uart3_pre", 0,
 			RK2928_CLKSEL_CON(20), 0,
-			RK2928_CLKGATE_CON(1), 15, GFLAGS),
-	MUX(SCLK_UART3, "sclk_uart3", mux_sclk_uart3_p, 0,
-			RK2928_CLKSEL_CON(16), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(1), 15, GFLAGS,
+		MUX(SCLK_UART3, "sclk_uart3", mux_sclk_uart3_p, 0,
+				RK2928_CLKSEL_CON(16), 8, 2, MFLAGS)),
 
 	GATE(SCLK_JTAG, "jtag", "ext_jtag", 0, RK2928_CLKGATE_CON(1), 3, GFLAGS),
 
@@ -584,27 +584,27 @@ static struct rockchip_clk_branch rk3066a_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "i2s0_pre", "i2s_src", 0,
 			RK2928_CLKSEL_CON(2), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 7, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s0_frac", "i2s0_pre", 0,
+	COMPOSITE_FRACMUX(0, "i2s0_frac", "i2s0_pre", 0,
 			RK2928_CLKSEL_CON(6), 0,
-			RK2928_CLKGATE_CON(0), 8, GFLAGS),
-	MUX(SCLK_I2S0, "sclk_i2s0", mux_sclk_i2s0_p, 0,
-			RK2928_CLKSEL_CON(2), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(0), 8, GFLAGS,
+		MUX(SCLK_I2S0, "sclk_i2s0", mux_sclk_i2s0_p, 0,
+				RK2928_CLKSEL_CON(2), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "i2s1_pre", "i2s_src", 0,
 			RK2928_CLKSEL_CON(3), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 9, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s1_frac", "i2s1_pre", 0,
+	COMPOSITE_FRACMUX(0, "i2s1_frac", "i2s1_pre", 0,
 			RK2928_CLKSEL_CON(7), 0,
-			RK2928_CLKGATE_CON(0), 10, GFLAGS),
-	MUX(SCLK_I2S1, "sclk_i2s1", mux_sclk_i2s1_p, 0,
-			RK2928_CLKSEL_CON(3), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(0), 10, GFLAGS,
+		MUX(SCLK_I2S1, "sclk_i2s1", mux_sclk_i2s1_p, 0,
+				RK2928_CLKSEL_CON(3), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "i2s2_pre", "i2s_src", 0,
 			RK2928_CLKSEL_CON(4), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 11, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s2_frac", "i2s2_pre", 0,
+	COMPOSITE_FRACMUX(0, "i2s2_frac", "i2s2_pre", 0,
 			RK2928_CLKSEL_CON(8), 0,
-			RK2928_CLKGATE_CON(0), 12, GFLAGS),
-	MUX(SCLK_I2S2, "sclk_i2s2", mux_sclk_i2s2_p, 0,
-			RK2928_CLKSEL_CON(4), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(0), 12, GFLAGS,
+		MUX(SCLK_I2S2, "sclk_i2s2", mux_sclk_i2s2_p, 0,
+				RK2928_CLKSEL_CON(4), 8, 2, MFLAGS)),
 
 	GATE(HCLK_I2S1, "hclk_i2s1", "hclk_cpu", 0, RK2928_CLKGATE_CON(7), 3, GFLAGS),
 	GATE(HCLK_I2S2, "hclk_i2s2", "hclk_cpu", 0, RK2928_CLKGATE_CON(7), 4, GFLAGS),
@@ -691,11 +691,11 @@ static struct rockchip_clk_branch rk3188_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "i2s0_pre", "i2s_src", 0,
 			RK2928_CLKSEL_CON(3), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 9, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s0_frac", "i2s0_pre", 0,
+	COMPOSITE_FRACMUX(0, "i2s0_frac", "i2s0_pre", 0,
 			RK2928_CLKSEL_CON(7), 0,
-			RK2928_CLKGATE_CON(0), 10, GFLAGS),
-	MUX(SCLK_I2S0, "sclk_i2s0", mux_sclk_i2s0_p, 0,
-			RK2928_CLKSEL_CON(3), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(0), 10, GFLAGS,
+		MUX(SCLK_I2S0, "sclk_i2s0", mux_sclk_i2s0_p, 0,
+				RK2928_CLKSEL_CON(3), 8, 2, MFLAGS)),
 
 	GATE(0, "hclk_imem0", "hclk_cpu", 0, RK2928_CLKGATE_CON(4), 14, GFLAGS),
 	GATE(0, "hclk_imem1", "hclk_cpu", 0, RK2928_CLKGATE_CON(4), 15, GFLAGS),
diff --git a/drivers/clk/rockchip/clk-rk3288.c b/drivers/clk/rockchip/clk-rk3288.c
index 11b40fb..e0bb0f0 100644
--- a/drivers/clk/rockchip/clk-rk3288.c
+++ b/drivers/clk/rockchip/clk-rk3288.c
@@ -304,11 +304,11 @@ static struct rockchip_clk_branch rk3288_clk_branches[] __initdata = {
 	COMPOSITE(0, "i2s_src", mux_pll_src_cpll_gpll_p, 0,
 			RK3288_CLKSEL_CON(4), 15, 1, MFLAGS, 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(4), 1, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s_frac", "i2s_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "i2s_frac", "i2s_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(8), 0,
-			RK3288_CLKGATE_CON(4), 2, GFLAGS),
-	MUX(0, "i2s_pre", mux_i2s_pre_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(4), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(4), 2, GFLAGS,
+		MUX(0, "i2s_pre", mux_i2s_pre_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(4), 8, 2, MFLAGS)),
 	COMPOSITE_NODIV(SCLK_I2S0_OUT, "i2s0_clkout", mux_i2s_clkout_p, 0,
 			RK3288_CLKSEL_CON(4), 12, 1, MFLAGS,
 			RK3288_CLKGATE_CON(4), 0, GFLAGS),
@@ -320,20 +320,22 @@ static struct rockchip_clk_branch rk3288_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "spdif_pre", "spdif_src", 0,
 			RK3288_CLKSEL_CON(5), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(4), 4, GFLAGS),
-	COMPOSITE_FRAC(0, "spdif_frac", "spdif_src", 0,
+	COMPOSITE_FRACMUX(0, "spdif_frac", "spdif_src", 0,
 			RK3288_CLKSEL_CON(9), 0,
-			RK3288_CLKGATE_CON(4), 5, GFLAGS),
-	COMPOSITE_NODIV(SCLK_SPDIF, "sclk_spdif", mux_spdif_p, 0,
-			RK3288_CLKSEL_CON(5), 8, 2, MFLAGS,
+			RK3288_CLKGATE_CON(4), 5, GFLAGS,
+		MUX(0, "spdif_mux", mux_spdif_p, 0,
+				RK3288_CLKSEL_CON(5), 8, 2, MFLAGS)),
+	GATE(SCLK_SPDIF, "sclk_spdif", "spdif_mux", 0,
 			RK3288_CLKGATE_CON(4), 6, GFLAGS),
 	COMPOSITE_NOMUX(0, "spdif_8ch_pre", "spdif_src", 0,
 			RK3288_CLKSEL_CON(40), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(4), 7, GFLAGS),
-	COMPOSITE_FRAC(0, "spdif_8ch_frac", "spdif_8ch_pre", 0,
+	COMPOSITE_FRACMUX(0, "spdif_8ch_frac", "spdif_8ch_pre", 0,
 			RK3288_CLKSEL_CON(41), 0,
-			RK3288_CLKGATE_CON(4), 8, GFLAGS),
-	COMPOSITE_NODIV(SCLK_SPDIF8CH, "sclk_spdif_8ch", mux_spdif_8ch_p, 0,
-			RK3288_CLKSEL_CON(40), 8, 2, MFLAGS,
+			RK3288_CLKGATE_CON(4), 8, GFLAGS,
+		MUX(0, "spdif_8ch_mux", mux_spdif_8ch_p, 0,
+				RK3288_CLKSEL_CON(40), 8, 2, MFLAGS)),
+	GATE(SCLK_SPDIF8CH, "sclk_spdif_8ch", "spdif_8ch_mux", 0,
 			RK3288_CLKGATE_CON(4), 9, GFLAGS),
 
 	GATE(0, "sclk_acc_efuse", "xin24m", 0,
@@ -536,45 +538,45 @@ static struct rockchip_clk_branch rk3288_clk_branches[] __initdata = {
 	COMPOSITE(0, "uart0_src", mux_pll_src_cpll_gll_usb_npll_p, 0,
 			RK3288_CLKSEL_CON(13), 13, 2, MFLAGS, 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(1), 8, GFLAGS),
-	COMPOSITE_FRAC(0, "uart0_frac", "uart0_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart0_frac", "uart0_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(17), 0,
-			RK3288_CLKGATE_CON(1), 9, GFLAGS),
-	MUX(SCLK_UART0, "sclk_uart0", mux_uart0_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(13), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(1), 9, GFLAGS,
+		MUX(SCLK_UART0, "sclk_uart0", mux_uart0_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(13), 8, 2, MFLAGS)),
 	MUX(0, "uart_src", mux_pll_src_cpll_gpll_p, 0,
 			RK3288_CLKSEL_CON(13), 15, 1, MFLAGS),
 	COMPOSITE_NOMUX(0, "uart1_src", "uart_src", 0,
 			RK3288_CLKSEL_CON(14), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(1), 10, GFLAGS),
-	COMPOSITE_FRAC(0, "uart1_frac", "uart1_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart1_frac", "uart1_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(18), 0,
-			RK3288_CLKGATE_CON(1), 11, GFLAGS),
-	MUX(SCLK_UART1, "sclk_uart1", mux_uart1_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(14), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(1), 11, GFLAGS,
+		MUX(SCLK_UART1, "sclk_uart1", mux_uart1_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(14), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart2_src", "uart_src", 0,
 			RK3288_CLKSEL_CON(15), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(1), 12, GFLAGS),
-	COMPOSITE_FRAC(0, "uart2_frac", "uart2_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart2_frac", "uart2_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(19), 0,
-			RK3288_CLKGATE_CON(1), 13, GFLAGS),
-	MUX(SCLK_UART2, "sclk_uart2", mux_uart2_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(15), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(1), 13, GFLAGS,
+		MUX(SCLK_UART2, "sclk_uart2", mux_uart2_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(15), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart3_src", "uart_src", 0,
 			RK3288_CLKSEL_CON(16), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(1), 14, GFLAGS),
-	COMPOSITE_FRAC(0, "uart3_frac", "uart3_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart3_frac", "uart3_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(20), 0,
-			RK3288_CLKGATE_CON(1), 15, GFLAGS),
-	MUX(SCLK_UART3, "sclk_uart3", mux_uart3_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(16), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(1), 15, GFLAGS,
+		MUX(SCLK_UART3, "sclk_uart3", mux_uart3_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(16), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart4_src", "uart_src", 0,
 			RK3288_CLKSEL_CON(3), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(2), 12, GFLAGS),
-	COMPOSITE_FRAC(0, "uart4_frac", "uart4_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart4_frac", "uart4_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(7), 0,
-			RK3288_CLKGATE_CON(2), 13, GFLAGS),
-	MUX(SCLK_UART4, "sclk_uart4", mux_uart4_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(3), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(2), 13, GFLAGS,
+		MUX(SCLK_UART4, "sclk_uart4", mux_uart4_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(3), 8, 2, MFLAGS)),
 
 	COMPOSITE(0, "mac_pll_src", mux_pll_src_npll_cpll_gpll_p, 0,
 			RK3288_CLKSEL_CON(21), 0, 2, MFLAGS, 8, 5, DFLAGS,
-- 
2.6.4

^ permalink raw reply related	[flat|nested] 15+ messages in thread

* [PATCH v2 3/5] clk: rockchip: include downstream muxes into fractional dividers
@ 2015-12-22 21:28   ` Heiko Stuebner
  0 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:28 UTC (permalink / raw)
  To: linux-arm-kernel

Use the newly introduced possibility to combine the fractional dividers
with their downstream muxes for all fractional dividers on currently
supported Rockchip SoCs.

Signed-off-by: Heiko Stuebner <heiko@sntech.de>
Tested-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
Reviewed-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
---
 drivers/clk/rockchip/clk-rk3188.c | 80 +++++++++++++++++++--------------------
 drivers/clk/rockchip/clk-rk3288.c | 66 ++++++++++++++++----------------
 2 files changed, 74 insertions(+), 72 deletions(-)

diff --git a/drivers/clk/rockchip/clk-rk3188.c b/drivers/clk/rockchip/clk-rk3188.c
index c2c35d4..6398a91 100644
--- a/drivers/clk/rockchip/clk-rk3188.c
+++ b/drivers/clk/rockchip/clk-rk3188.c
@@ -335,11 +335,11 @@ static struct rockchip_clk_branch common_clk_branches[] __initdata = {
 	COMPOSITE(0, "hsadc_src", mux_pll_src_gpll_cpll_p, 0,
 			RK2928_CLKSEL_CON(22), 0, 1, MFLAGS, 8, 8, DFLAGS,
 			RK2928_CLKGATE_CON(2), 6, GFLAGS),
-	COMPOSITE_FRAC(0, "hsadc_frac", "hsadc_src", 0,
+	COMPOSITE_FRACMUX(0, "hsadc_frac", "hsadc_src", 0,
 			RK2928_CLKSEL_CON(23), 0,
-			RK2928_CLKGATE_CON(2), 7, GFLAGS),
-	MUX(0, "sclk_hsadc_out", mux_sclk_hsadc_p, 0,
-			RK2928_CLKSEL_CON(22), 4, 2, MFLAGS),
+			RK2928_CLKGATE_CON(2), 7, GFLAGS,
+		MUX(0, "sclk_hsadc_out", mux_sclk_hsadc_p, 0,
+				RK2928_CLKSEL_CON(22), 4, 2, MFLAGS)),
 	INVERTER(SCLK_HSADC, "sclk_hsadc", "sclk_hsadc_out",
 			RK2928_CLKSEL_CON(22), 7, IFLAGS),
 
@@ -350,11 +350,11 @@ static struct rockchip_clk_branch common_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "spdif_pre", "i2s_src", 0,
 			RK2928_CLKSEL_CON(5), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 13, GFLAGS),
-	COMPOSITE_FRAC(0, "spdif_frac", "spdif_pre", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "spdif_frac", "spdif_pll", CLK_SET_RATE_PARENT,
 			RK2928_CLKSEL_CON(9), 0,
-			RK2928_CLKGATE_CON(0), 14, GFLAGS),
-	MUX(SCLK_SPDIF, "sclk_spdif", mux_sclk_spdif_p, CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(5), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(0), 14, GFLAGS,
+		MUX(SCLK_SPDIF, "sclk_spdif", mux_sclk_spdif_p, CLK_SET_RATE_PARENT,
+				RK2928_CLKSEL_CON(5), 8, 2, MFLAGS)),
 
 	/*
 	 * Clock-Architecture Diagram 4
@@ -385,35 +385,35 @@ static struct rockchip_clk_branch common_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "uart0_pre", "uart_src", 0,
 			RK2928_CLKSEL_CON(13), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(1), 8, GFLAGS),
-	COMPOSITE_FRAC(0, "uart0_frac", "uart0_pre", 0,
+	COMPOSITE_FRACMUX(0, "uart0_frac", "uart0_pre", 0,
 			RK2928_CLKSEL_CON(17), 0,
-			RK2928_CLKGATE_CON(1), 9, GFLAGS),
-	MUX(SCLK_UART0, "sclk_uart0", mux_sclk_uart0_p, 0,
-			RK2928_CLKSEL_CON(13), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(1), 9, GFLAGS,
+		MUX(SCLK_UART0, "sclk_uart0", mux_sclk_uart0_p, 0,
+				RK2928_CLKSEL_CON(13), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart1_pre", "uart_src", 0,
 			RK2928_CLKSEL_CON(14), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(1), 10, GFLAGS),
-	COMPOSITE_FRAC(0, "uart1_frac", "uart1_pre", 0,
+	COMPOSITE_FRACMUX(0, "uart1_frac", "uart1_pre", 0,
 			RK2928_CLKSEL_CON(18), 0,
-			RK2928_CLKGATE_CON(1), 11, GFLAGS),
-	MUX(SCLK_UART1, "sclk_uart1", mux_sclk_uart1_p, 0,
-			RK2928_CLKSEL_CON(14), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(1), 11, GFLAGS,
+		MUX(SCLK_UART1, "sclk_uart1", mux_sclk_uart1_p, 0,
+				RK2928_CLKSEL_CON(14), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart2_pre", "uart_src", 0,
 			RK2928_CLKSEL_CON(15), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(1), 12, GFLAGS),
-	COMPOSITE_FRAC(0, "uart2_frac", "uart2_pre", 0,
+	COMPOSITE_FRACMUX(0, "uart2_frac", "uart2_pre", 0,
 			RK2928_CLKSEL_CON(19), 0,
-			RK2928_CLKGATE_CON(1), 13, GFLAGS),
-	MUX(SCLK_UART2, "sclk_uart2", mux_sclk_uart2_p, 0,
-			RK2928_CLKSEL_CON(15), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(1), 13, GFLAGS,
+		MUX(SCLK_UART2, "sclk_uart2", mux_sclk_uart2_p, 0,
+				RK2928_CLKSEL_CON(15), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart3_pre", "uart_src", 0,
 			RK2928_CLKSEL_CON(16), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(1), 14, GFLAGS),
-	COMPOSITE_FRAC(0, "uart3_frac", "uart3_pre", 0,
+	COMPOSITE_FRACMUX(0, "uart3_frac", "uart3_pre", 0,
 			RK2928_CLKSEL_CON(20), 0,
-			RK2928_CLKGATE_CON(1), 15, GFLAGS),
-	MUX(SCLK_UART3, "sclk_uart3", mux_sclk_uart3_p, 0,
-			RK2928_CLKSEL_CON(16), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(1), 15, GFLAGS,
+		MUX(SCLK_UART3, "sclk_uart3", mux_sclk_uart3_p, 0,
+				RK2928_CLKSEL_CON(16), 8, 2, MFLAGS)),
 
 	GATE(SCLK_JTAG, "jtag", "ext_jtag", 0, RK2928_CLKGATE_CON(1), 3, GFLAGS),
 
@@ -584,27 +584,27 @@ static struct rockchip_clk_branch rk3066a_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "i2s0_pre", "i2s_src", 0,
 			RK2928_CLKSEL_CON(2), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 7, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s0_frac", "i2s0_pre", 0,
+	COMPOSITE_FRACMUX(0, "i2s0_frac", "i2s0_pre", 0,
 			RK2928_CLKSEL_CON(6), 0,
-			RK2928_CLKGATE_CON(0), 8, GFLAGS),
-	MUX(SCLK_I2S0, "sclk_i2s0", mux_sclk_i2s0_p, 0,
-			RK2928_CLKSEL_CON(2), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(0), 8, GFLAGS,
+		MUX(SCLK_I2S0, "sclk_i2s0", mux_sclk_i2s0_p, 0,
+				RK2928_CLKSEL_CON(2), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "i2s1_pre", "i2s_src", 0,
 			RK2928_CLKSEL_CON(3), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 9, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s1_frac", "i2s1_pre", 0,
+	COMPOSITE_FRACMUX(0, "i2s1_frac", "i2s1_pre", 0,
 			RK2928_CLKSEL_CON(7), 0,
-			RK2928_CLKGATE_CON(0), 10, GFLAGS),
-	MUX(SCLK_I2S1, "sclk_i2s1", mux_sclk_i2s1_p, 0,
-			RK2928_CLKSEL_CON(3), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(0), 10, GFLAGS,
+		MUX(SCLK_I2S1, "sclk_i2s1", mux_sclk_i2s1_p, 0,
+				RK2928_CLKSEL_CON(3), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "i2s2_pre", "i2s_src", 0,
 			RK2928_CLKSEL_CON(4), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 11, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s2_frac", "i2s2_pre", 0,
+	COMPOSITE_FRACMUX(0, "i2s2_frac", "i2s2_pre", 0,
 			RK2928_CLKSEL_CON(8), 0,
-			RK2928_CLKGATE_CON(0), 12, GFLAGS),
-	MUX(SCLK_I2S2, "sclk_i2s2", mux_sclk_i2s2_p, 0,
-			RK2928_CLKSEL_CON(4), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(0), 12, GFLAGS,
+		MUX(SCLK_I2S2, "sclk_i2s2", mux_sclk_i2s2_p, 0,
+				RK2928_CLKSEL_CON(4), 8, 2, MFLAGS)),
 
 	GATE(HCLK_I2S1, "hclk_i2s1", "hclk_cpu", 0, RK2928_CLKGATE_CON(7), 3, GFLAGS),
 	GATE(HCLK_I2S2, "hclk_i2s2", "hclk_cpu", 0, RK2928_CLKGATE_CON(7), 4, GFLAGS),
@@ -691,11 +691,11 @@ static struct rockchip_clk_branch rk3188_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "i2s0_pre", "i2s_src", 0,
 			RK2928_CLKSEL_CON(3), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 9, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s0_frac", "i2s0_pre", 0,
+	COMPOSITE_FRACMUX(0, "i2s0_frac", "i2s0_pre", 0,
 			RK2928_CLKSEL_CON(7), 0,
-			RK2928_CLKGATE_CON(0), 10, GFLAGS),
-	MUX(SCLK_I2S0, "sclk_i2s0", mux_sclk_i2s0_p, 0,
-			RK2928_CLKSEL_CON(3), 8, 2, MFLAGS),
+			RK2928_CLKGATE_CON(0), 10, GFLAGS,
+		MUX(SCLK_I2S0, "sclk_i2s0", mux_sclk_i2s0_p, 0,
+				RK2928_CLKSEL_CON(3), 8, 2, MFLAGS)),
 
 	GATE(0, "hclk_imem0", "hclk_cpu", 0, RK2928_CLKGATE_CON(4), 14, GFLAGS),
 	GATE(0, "hclk_imem1", "hclk_cpu", 0, RK2928_CLKGATE_CON(4), 15, GFLAGS),
diff --git a/drivers/clk/rockchip/clk-rk3288.c b/drivers/clk/rockchip/clk-rk3288.c
index 11b40fb..e0bb0f0 100644
--- a/drivers/clk/rockchip/clk-rk3288.c
+++ b/drivers/clk/rockchip/clk-rk3288.c
@@ -304,11 +304,11 @@ static struct rockchip_clk_branch rk3288_clk_branches[] __initdata = {
 	COMPOSITE(0, "i2s_src", mux_pll_src_cpll_gpll_p, 0,
 			RK3288_CLKSEL_CON(4), 15, 1, MFLAGS, 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(4), 1, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s_frac", "i2s_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "i2s_frac", "i2s_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(8), 0,
-			RK3288_CLKGATE_CON(4), 2, GFLAGS),
-	MUX(0, "i2s_pre", mux_i2s_pre_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(4), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(4), 2, GFLAGS,
+		MUX(0, "i2s_pre", mux_i2s_pre_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(4), 8, 2, MFLAGS)),
 	COMPOSITE_NODIV(SCLK_I2S0_OUT, "i2s0_clkout", mux_i2s_clkout_p, 0,
 			RK3288_CLKSEL_CON(4), 12, 1, MFLAGS,
 			RK3288_CLKGATE_CON(4), 0, GFLAGS),
@@ -320,20 +320,22 @@ static struct rockchip_clk_branch rk3288_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "spdif_pre", "spdif_src", 0,
 			RK3288_CLKSEL_CON(5), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(4), 4, GFLAGS),
-	COMPOSITE_FRAC(0, "spdif_frac", "spdif_src", 0,
+	COMPOSITE_FRACMUX(0, "spdif_frac", "spdif_src", 0,
 			RK3288_CLKSEL_CON(9), 0,
-			RK3288_CLKGATE_CON(4), 5, GFLAGS),
-	COMPOSITE_NODIV(SCLK_SPDIF, "sclk_spdif", mux_spdif_p, 0,
-			RK3288_CLKSEL_CON(5), 8, 2, MFLAGS,
+			RK3288_CLKGATE_CON(4), 5, GFLAGS,
+		MUX(0, "spdif_mux", mux_spdif_p, 0,
+				RK3288_CLKSEL_CON(5), 8, 2, MFLAGS)),
+	GATE(SCLK_SPDIF, "sclk_spdif", "spdif_mux", 0,
 			RK3288_CLKGATE_CON(4), 6, GFLAGS),
 	COMPOSITE_NOMUX(0, "spdif_8ch_pre", "spdif_src", 0,
 			RK3288_CLKSEL_CON(40), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(4), 7, GFLAGS),
-	COMPOSITE_FRAC(0, "spdif_8ch_frac", "spdif_8ch_pre", 0,
+	COMPOSITE_FRACMUX(0, "spdif_8ch_frac", "spdif_8ch_pre", 0,
 			RK3288_CLKSEL_CON(41), 0,
-			RK3288_CLKGATE_CON(4), 8, GFLAGS),
-	COMPOSITE_NODIV(SCLK_SPDIF8CH, "sclk_spdif_8ch", mux_spdif_8ch_p, 0,
-			RK3288_CLKSEL_CON(40), 8, 2, MFLAGS,
+			RK3288_CLKGATE_CON(4), 8, GFLAGS,
+		MUX(0, "spdif_8ch_mux", mux_spdif_8ch_p, 0,
+				RK3288_CLKSEL_CON(40), 8, 2, MFLAGS)),
+	GATE(SCLK_SPDIF8CH, "sclk_spdif_8ch", "spdif_8ch_mux", 0,
 			RK3288_CLKGATE_CON(4), 9, GFLAGS),
 
 	GATE(0, "sclk_acc_efuse", "xin24m", 0,
@@ -536,45 +538,45 @@ static struct rockchip_clk_branch rk3288_clk_branches[] __initdata = {
 	COMPOSITE(0, "uart0_src", mux_pll_src_cpll_gll_usb_npll_p, 0,
 			RK3288_CLKSEL_CON(13), 13, 2, MFLAGS, 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(1), 8, GFLAGS),
-	COMPOSITE_FRAC(0, "uart0_frac", "uart0_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart0_frac", "uart0_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(17), 0,
-			RK3288_CLKGATE_CON(1), 9, GFLAGS),
-	MUX(SCLK_UART0, "sclk_uart0", mux_uart0_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(13), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(1), 9, GFLAGS,
+		MUX(SCLK_UART0, "sclk_uart0", mux_uart0_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(13), 8, 2, MFLAGS)),
 	MUX(0, "uart_src", mux_pll_src_cpll_gpll_p, 0,
 			RK3288_CLKSEL_CON(13), 15, 1, MFLAGS),
 	COMPOSITE_NOMUX(0, "uart1_src", "uart_src", 0,
 			RK3288_CLKSEL_CON(14), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(1), 10, GFLAGS),
-	COMPOSITE_FRAC(0, "uart1_frac", "uart1_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart1_frac", "uart1_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(18), 0,
-			RK3288_CLKGATE_CON(1), 11, GFLAGS),
-	MUX(SCLK_UART1, "sclk_uart1", mux_uart1_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(14), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(1), 11, GFLAGS,
+		MUX(SCLK_UART1, "sclk_uart1", mux_uart1_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(14), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart2_src", "uart_src", 0,
 			RK3288_CLKSEL_CON(15), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(1), 12, GFLAGS),
-	COMPOSITE_FRAC(0, "uart2_frac", "uart2_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart2_frac", "uart2_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(19), 0,
-			RK3288_CLKGATE_CON(1), 13, GFLAGS),
-	MUX(SCLK_UART2, "sclk_uart2", mux_uart2_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(15), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(1), 13, GFLAGS,
+		MUX(SCLK_UART2, "sclk_uart2", mux_uart2_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(15), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart3_src", "uart_src", 0,
 			RK3288_CLKSEL_CON(16), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(1), 14, GFLAGS),
-	COMPOSITE_FRAC(0, "uart3_frac", "uart3_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart3_frac", "uart3_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(20), 0,
-			RK3288_CLKGATE_CON(1), 15, GFLAGS),
-	MUX(SCLK_UART3, "sclk_uart3", mux_uart3_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(16), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(1), 15, GFLAGS,
+		MUX(SCLK_UART3, "sclk_uart3", mux_uart3_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(16), 8, 2, MFLAGS)),
 	COMPOSITE_NOMUX(0, "uart4_src", "uart_src", 0,
 			RK3288_CLKSEL_CON(3), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(2), 12, GFLAGS),
-	COMPOSITE_FRAC(0, "uart4_frac", "uart4_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart4_frac", "uart4_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(7), 0,
-			RK3288_CLKGATE_CON(2), 13, GFLAGS),
-	MUX(SCLK_UART4, "sclk_uart4", mux_uart4_p, CLK_SET_RATE_PARENT,
-			RK3288_CLKSEL_CON(3), 8, 2, MFLAGS),
+			RK3288_CLKGATE_CON(2), 13, GFLAGS,
+		MUX(SCLK_UART4, "sclk_uart4", mux_uart4_p, CLK_SET_RATE_PARENT,
+				RK3288_CLKSEL_CON(3), 8, 2, MFLAGS)),
 
 	COMPOSITE(0, "mac_pll_src", mux_pll_src_npll_cpll_gpll_p, 0,
 			RK3288_CLKSEL_CON(21), 0, 2, MFLAGS, 8, 5, DFLAGS,
-- 
2.6.4

^ permalink raw reply related	[flat|nested] 15+ messages in thread

* [PATCH v2 4/5] clk: rockchip: rk3036: include downstream muxes into fractional dividers
  2015-12-22 21:27 ` Heiko Stuebner
@ 2015-12-22 21:28   ` Heiko Stuebner
  -1 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:28 UTC (permalink / raw)
  To: mturquette, sboyd
  Cc: linux-clk, linux-arm-kernel, linux-rockchip, sjoerd.simons, wxt,
	Xing Zheng, Heiko Stuebner

From: Xing Zheng <zhengxing@rock-chips.com>

Use the newly introduced possibility to combine the fractional dividers
with their downstream muxes for all fractional dividers on currently
supported RK3036 SoCs.

Signed-off-by: Xing Zheng <zhengxing@rock-chips.com>
Signed-off-by: Caesar Wang <wxt@rock-chips.com>
Signed-off-by: Heiko Stuebner <heiko@sntech.de>
---
 drivers/clk/rockchip/clk-rk3036.c | 34 +++++++++++++++++-----------------
 1 file changed, 17 insertions(+), 17 deletions(-)

diff --git a/drivers/clk/rockchip/clk-rk3036.c b/drivers/clk/rockchip/clk-rk3036.c
index 7333b053..fb35263 100644
--- a/drivers/clk/rockchip/clk-rk3036.c
+++ b/drivers/clk/rockchip/clk-rk3036.c
@@ -227,21 +227,21 @@ static struct rockchip_clk_branch rk3036_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "uart2_src", "uart_pll_clk", 0,
 			RK2928_CLKSEL_CON(13), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(1), 8, GFLAGS),
-	COMPOSITE_FRAC(0, "uart0_frac", "uart0_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart0_frac", "uart0_src", CLK_SET_RATE_PARENT,
 			RK2928_CLKSEL_CON(17), 0,
-			RK2928_CLKGATE_CON(1), 9, GFLAGS),
-	COMPOSITE_FRAC(0, "uart1_frac", "uart1_src", CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(18), 0,
-			RK2928_CLKGATE_CON(1), 11, GFLAGS),
-	COMPOSITE_FRAC(0, "uart2_frac", "uart2_src", CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(19), 0,
-			RK2928_CLKGATE_CON(1), 13, GFLAGS),
+			RK2928_CLKGATE_CON(1), 9, GFLAGS,
 	MUX(SCLK_UART0, "sclk_uart0", mux_uart0_p, CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(13), 8, 2, MFLAGS),
+			RK2928_CLKSEL_CON(13), 8, 2, MFLAGS)),
+	COMPOSITE_FRACMUX(0, "uart1_frac", "uart1_src", CLK_SET_RATE_PARENT,
+			RK2928_CLKSEL_CON(18), 0,
+			RK2928_CLKGATE_CON(1), 11, GFLAGS,
 	MUX(SCLK_UART1, "sclk_uart1", mux_uart1_p, CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(14), 8, 2, MFLAGS),
+			RK2928_CLKSEL_CON(14), 8, 2, MFLAGS)),
+	COMPOSITE_FRACMUX(0, "uart2_frac", "uart2_src", CLK_SET_RATE_PARENT,
+			RK2928_CLKSEL_CON(19), 0,
+			RK2928_CLKGATE_CON(1), 13, GFLAGS,
 	MUX(SCLK_UART2, "sclk_uart2", mux_uart2_p, CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(15), 8, 2, MFLAGS),
+			RK2928_CLKSEL_CON(15), 8, 2, MFLAGS)),
 
 	COMPOSITE(0, "aclk_vcodec", mux_pll_src_3plls_p, 0,
 			RK2928_CLKSEL_CON(32), 14, 2, MFLAGS, 8, 5, DFLAGS,
@@ -289,11 +289,11 @@ static struct rockchip_clk_branch rk3036_clk_branches[] __initdata = {
 	COMPOSITE(0, "i2s_src", mux_pll_src_3plls_p, 0,
 			RK2928_CLKSEL_CON(3), 14, 2, MFLAGS, 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 9, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s_frac", "i2s_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "i2s_frac", "i2s_src", CLK_SET_RATE_PARENT,
 			RK2928_CLKSEL_CON(7), 0,
-			RK2928_CLKGATE_CON(0), 10, GFLAGS),
+			RK2928_CLKGATE_CON(0), 10, GFLAGS,
 	MUX(0, "i2s_pre", mux_i2s_pre_p, CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(3), 8, 2, MFLAGS),
+			RK2928_CLKSEL_CON(3), 8, 2, MFLAGS)),
 	COMPOSITE_NODIV(SCLK_I2S_OUT, "i2s_clkout", mux_i2s_clkout_p, 0,
 			RK2928_CLKSEL_CON(3), 12, 1, MFLAGS,
 			RK2928_CLKGATE_CON(0), 13, GFLAGS),
@@ -303,11 +303,11 @@ static struct rockchip_clk_branch rk3036_clk_branches[] __initdata = {
 	COMPOSITE(0, "spdif_src", mux_pll_src_3plls_p, 0,
 			RK2928_CLKSEL_CON(5), 10, 2, MFLAGS, 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(2), 10, GFLAGS),
-	COMPOSITE_FRAC(0, "spdif_frac", "spdif_src", 0,
+	COMPOSITE_FRACMUX(0, "spdif_frac", "spdif_src", 0,
 			RK2928_CLKSEL_CON(9), 0,
-			RK2928_CLKGATE_CON(2), 12, GFLAGS),
+			RK2928_CLKGATE_CON(2), 12, GFLAGS,
 	MUX(SCLK_SPDIF, "sclk_spdif", mux_spdif_p, 0,
-			RK2928_CLKSEL_CON(5), 8, 2, MFLAGS),
+			RK2928_CLKSEL_CON(5), 8, 2, MFLAGS)),
 
 	GATE(SCLK_OTGPHY0, "sclk_otgphy0", "xin12m", CLK_IGNORE_UNUSED,
 			RK2928_CLKGATE_CON(1), 5, GFLAGS),
-- 
2.6.4

^ permalink raw reply related	[flat|nested] 15+ messages in thread

* [PATCH v2 4/5] clk: rockchip: rk3036: include downstream muxes into fractional dividers
@ 2015-12-22 21:28   ` Heiko Stuebner
  0 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:28 UTC (permalink / raw)
  To: linux-arm-kernel

From: Xing Zheng <zhengxing@rock-chips.com>

Use the newly introduced possibility to combine the fractional dividers
with their downstream muxes for all fractional dividers on currently
supported RK3036 SoCs.

Signed-off-by: Xing Zheng <zhengxing@rock-chips.com>
Signed-off-by: Caesar Wang <wxt@rock-chips.com>
Signed-off-by: Heiko Stuebner <heiko@sntech.de>
---
 drivers/clk/rockchip/clk-rk3036.c | 34 +++++++++++++++++-----------------
 1 file changed, 17 insertions(+), 17 deletions(-)

diff --git a/drivers/clk/rockchip/clk-rk3036.c b/drivers/clk/rockchip/clk-rk3036.c
index 7333b053..fb35263 100644
--- a/drivers/clk/rockchip/clk-rk3036.c
+++ b/drivers/clk/rockchip/clk-rk3036.c
@@ -227,21 +227,21 @@ static struct rockchip_clk_branch rk3036_clk_branches[] __initdata = {
 	COMPOSITE_NOMUX(0, "uart2_src", "uart_pll_clk", 0,
 			RK2928_CLKSEL_CON(13), 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(1), 8, GFLAGS),
-	COMPOSITE_FRAC(0, "uart0_frac", "uart0_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "uart0_frac", "uart0_src", CLK_SET_RATE_PARENT,
 			RK2928_CLKSEL_CON(17), 0,
-			RK2928_CLKGATE_CON(1), 9, GFLAGS),
-	COMPOSITE_FRAC(0, "uart1_frac", "uart1_src", CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(18), 0,
-			RK2928_CLKGATE_CON(1), 11, GFLAGS),
-	COMPOSITE_FRAC(0, "uart2_frac", "uart2_src", CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(19), 0,
-			RK2928_CLKGATE_CON(1), 13, GFLAGS),
+			RK2928_CLKGATE_CON(1), 9, GFLAGS,
 	MUX(SCLK_UART0, "sclk_uart0", mux_uart0_p, CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(13), 8, 2, MFLAGS),
+			RK2928_CLKSEL_CON(13), 8, 2, MFLAGS)),
+	COMPOSITE_FRACMUX(0, "uart1_frac", "uart1_src", CLK_SET_RATE_PARENT,
+			RK2928_CLKSEL_CON(18), 0,
+			RK2928_CLKGATE_CON(1), 11, GFLAGS,
 	MUX(SCLK_UART1, "sclk_uart1", mux_uart1_p, CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(14), 8, 2, MFLAGS),
+			RK2928_CLKSEL_CON(14), 8, 2, MFLAGS)),
+	COMPOSITE_FRACMUX(0, "uart2_frac", "uart2_src", CLK_SET_RATE_PARENT,
+			RK2928_CLKSEL_CON(19), 0,
+			RK2928_CLKGATE_CON(1), 13, GFLAGS,
 	MUX(SCLK_UART2, "sclk_uart2", mux_uart2_p, CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(15), 8, 2, MFLAGS),
+			RK2928_CLKSEL_CON(15), 8, 2, MFLAGS)),
 
 	COMPOSITE(0, "aclk_vcodec", mux_pll_src_3plls_p, 0,
 			RK2928_CLKSEL_CON(32), 14, 2, MFLAGS, 8, 5, DFLAGS,
@@ -289,11 +289,11 @@ static struct rockchip_clk_branch rk3036_clk_branches[] __initdata = {
 	COMPOSITE(0, "i2s_src", mux_pll_src_3plls_p, 0,
 			RK2928_CLKSEL_CON(3), 14, 2, MFLAGS, 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(0), 9, GFLAGS),
-	COMPOSITE_FRAC(0, "i2s_frac", "i2s_src", CLK_SET_RATE_PARENT,
+	COMPOSITE_FRACMUX(0, "i2s_frac", "i2s_src", CLK_SET_RATE_PARENT,
 			RK2928_CLKSEL_CON(7), 0,
-			RK2928_CLKGATE_CON(0), 10, GFLAGS),
+			RK2928_CLKGATE_CON(0), 10, GFLAGS,
 	MUX(0, "i2s_pre", mux_i2s_pre_p, CLK_SET_RATE_PARENT,
-			RK2928_CLKSEL_CON(3), 8, 2, MFLAGS),
+			RK2928_CLKSEL_CON(3), 8, 2, MFLAGS)),
 	COMPOSITE_NODIV(SCLK_I2S_OUT, "i2s_clkout", mux_i2s_clkout_p, 0,
 			RK2928_CLKSEL_CON(3), 12, 1, MFLAGS,
 			RK2928_CLKGATE_CON(0), 13, GFLAGS),
@@ -303,11 +303,11 @@ static struct rockchip_clk_branch rk3036_clk_branches[] __initdata = {
 	COMPOSITE(0, "spdif_src", mux_pll_src_3plls_p, 0,
 			RK2928_CLKSEL_CON(5), 10, 2, MFLAGS, 0, 7, DFLAGS,
 			RK2928_CLKGATE_CON(2), 10, GFLAGS),
-	COMPOSITE_FRAC(0, "spdif_frac", "spdif_src", 0,
+	COMPOSITE_FRACMUX(0, "spdif_frac", "spdif_src", 0,
 			RK2928_CLKSEL_CON(9), 0,
-			RK2928_CLKGATE_CON(2), 12, GFLAGS),
+			RK2928_CLKGATE_CON(2), 12, GFLAGS,
 	MUX(SCLK_SPDIF, "sclk_spdif", mux_spdif_p, 0,
-			RK2928_CLKSEL_CON(5), 8, 2, MFLAGS),
+			RK2928_CLKSEL_CON(5), 8, 2, MFLAGS)),
 
 	GATE(SCLK_OTGPHY0, "sclk_otgphy0", "xin12m", CLK_IGNORE_UNUSED,
 			RK2928_CLKGATE_CON(1), 5, GFLAGS),
-- 
2.6.4

^ permalink raw reply related	[flat|nested] 15+ messages in thread

* [PATCH v2 5/5] clk: rockchip: Allow the RK3288 SPDIF clocks to change their parent
  2015-12-22 21:27 ` Heiko Stuebner
@ 2015-12-22 21:28   ` Heiko Stuebner
  -1 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:28 UTC (permalink / raw)
  To: mturquette, sboyd
  Cc: linux-clk, linux-arm-kernel, linux-rockchip, sjoerd.simons, wxt,
	Heiko Stuebner

From: Sjoerd Simons <sjoerd.simons@collabora.co.uk>

The clock branches leading to sclk_spdif and sclk_spdif_8ch on RK3288
SoCs only feed those clocks, allow those clocks to change their parents
all the way up the hierarchy.

Signed-off-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
Signed-off-by: Heiko Stuebner <heiko@sntech.de>
---
 drivers/clk/rockchip/clk-rk3288.c | 16 ++++++++--------
 1 file changed, 8 insertions(+), 8 deletions(-)

diff --git a/drivers/clk/rockchip/clk-rk3288.c b/drivers/clk/rockchip/clk-rk3288.c
index e0bb0f0..80065e6 100644
--- a/drivers/clk/rockchip/clk-rk3288.c
+++ b/drivers/clk/rockchip/clk-rk3288.c
@@ -317,25 +317,25 @@ static struct rockchip_clk_branch rk3288_clk_branches[] __initdata = {
 
 	MUX(0, "spdif_src", mux_pll_src_cpll_gpll_p, 0,
 			RK3288_CLKSEL_CON(5), 15, 1, MFLAGS),
-	COMPOSITE_NOMUX(0, "spdif_pre", "spdif_src", 0,
+	COMPOSITE_NOMUX(0, "spdif_pre", "spdif_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(5), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(4), 4, GFLAGS),
-	COMPOSITE_FRACMUX(0, "spdif_frac", "spdif_src", 0,
+	COMPOSITE_FRACMUX(0, "spdif_frac", "spdif_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(9), 0,
 			RK3288_CLKGATE_CON(4), 5, GFLAGS,
-		MUX(0, "spdif_mux", mux_spdif_p, 0,
+		MUX(0, "spdif_mux", mux_spdif_p, CLK_SET_RATE_PARENT,
 				RK3288_CLKSEL_CON(5), 8, 2, MFLAGS)),
-	GATE(SCLK_SPDIF, "sclk_spdif", "spdif_mux", 0,
+	GATE(SCLK_SPDIF, "sclk_spdif", "spdif_mux", CLK_SET_RATE_PARENT,
 			RK3288_CLKGATE_CON(4), 6, GFLAGS),
-	COMPOSITE_NOMUX(0, "spdif_8ch_pre", "spdif_src", 0,
+	COMPOSITE_NOMUX(0, "spdif_8ch_pre", "spdif_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(40), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(4), 7, GFLAGS),
-	COMPOSITE_FRACMUX(0, "spdif_8ch_frac", "spdif_8ch_pre", 0,
+	COMPOSITE_FRACMUX(0, "spdif_8ch_frac", "spdif_8ch_pre", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(41), 0,
 			RK3288_CLKGATE_CON(4), 8, GFLAGS,
-		MUX(0, "spdif_8ch_mux", mux_spdif_8ch_p, 0,
+		MUX(0, "spdif_8ch_mux", mux_spdif_8ch_p, CLK_SET_RATE_PARENT,
 				RK3288_CLKSEL_CON(40), 8, 2, MFLAGS)),
-	GATE(SCLK_SPDIF8CH, "sclk_spdif_8ch", "spdif_8ch_mux", 0,
+	GATE(SCLK_SPDIF8CH, "sclk_spdif_8ch", "spdif_8ch_mux", CLK_SET_RATE_PARENT,
 			RK3288_CLKGATE_CON(4), 9, GFLAGS),
 
 	GATE(0, "sclk_acc_efuse", "xin24m", 0,
-- 
2.6.4

^ permalink raw reply related	[flat|nested] 15+ messages in thread

* [PATCH v2 5/5] clk: rockchip: Allow the RK3288 SPDIF clocks to change their parent
@ 2015-12-22 21:28   ` Heiko Stuebner
  0 siblings, 0 replies; 15+ messages in thread
From: Heiko Stuebner @ 2015-12-22 21:28 UTC (permalink / raw)
  To: linux-arm-kernel

From: Sjoerd Simons <sjoerd.simons@collabora.co.uk>

The clock branches leading to sclk_spdif and sclk_spdif_8ch on RK3288
SoCs only feed those clocks, allow those clocks to change their parents
all the way up the hierarchy.

Signed-off-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk>
Signed-off-by: Heiko Stuebner <heiko@sntech.de>
---
 drivers/clk/rockchip/clk-rk3288.c | 16 ++++++++--------
 1 file changed, 8 insertions(+), 8 deletions(-)

diff --git a/drivers/clk/rockchip/clk-rk3288.c b/drivers/clk/rockchip/clk-rk3288.c
index e0bb0f0..80065e6 100644
--- a/drivers/clk/rockchip/clk-rk3288.c
+++ b/drivers/clk/rockchip/clk-rk3288.c
@@ -317,25 +317,25 @@ static struct rockchip_clk_branch rk3288_clk_branches[] __initdata = {
 
 	MUX(0, "spdif_src", mux_pll_src_cpll_gpll_p, 0,
 			RK3288_CLKSEL_CON(5), 15, 1, MFLAGS),
-	COMPOSITE_NOMUX(0, "spdif_pre", "spdif_src", 0,
+	COMPOSITE_NOMUX(0, "spdif_pre", "spdif_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(5), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(4), 4, GFLAGS),
-	COMPOSITE_FRACMUX(0, "spdif_frac", "spdif_src", 0,
+	COMPOSITE_FRACMUX(0, "spdif_frac", "spdif_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(9), 0,
 			RK3288_CLKGATE_CON(4), 5, GFLAGS,
-		MUX(0, "spdif_mux", mux_spdif_p, 0,
+		MUX(0, "spdif_mux", mux_spdif_p, CLK_SET_RATE_PARENT,
 				RK3288_CLKSEL_CON(5), 8, 2, MFLAGS)),
-	GATE(SCLK_SPDIF, "sclk_spdif", "spdif_mux", 0,
+	GATE(SCLK_SPDIF, "sclk_spdif", "spdif_mux", CLK_SET_RATE_PARENT,
 			RK3288_CLKGATE_CON(4), 6, GFLAGS),
-	COMPOSITE_NOMUX(0, "spdif_8ch_pre", "spdif_src", 0,
+	COMPOSITE_NOMUX(0, "spdif_8ch_pre", "spdif_src", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(40), 0, 7, DFLAGS,
 			RK3288_CLKGATE_CON(4), 7, GFLAGS),
-	COMPOSITE_FRACMUX(0, "spdif_8ch_frac", "spdif_8ch_pre", 0,
+	COMPOSITE_FRACMUX(0, "spdif_8ch_frac", "spdif_8ch_pre", CLK_SET_RATE_PARENT,
 			RK3288_CLKSEL_CON(41), 0,
 			RK3288_CLKGATE_CON(4), 8, GFLAGS,
-		MUX(0, "spdif_8ch_mux", mux_spdif_8ch_p, 0,
+		MUX(0, "spdif_8ch_mux", mux_spdif_8ch_p, CLK_SET_RATE_PARENT,
 				RK3288_CLKSEL_CON(40), 8, 2, MFLAGS)),
-	GATE(SCLK_SPDIF8CH, "sclk_spdif_8ch", "spdif_8ch_mux", 0,
+	GATE(SCLK_SPDIF8CH, "sclk_spdif_8ch", "spdif_8ch_mux", CLK_SET_RATE_PARENT,
 			RK3288_CLKGATE_CON(4), 9, GFLAGS),
 
 	GATE(0, "sclk_acc_efuse", "xin24m", 0,
-- 
2.6.4

^ permalink raw reply related	[flat|nested] 15+ messages in thread

* Re: [PATCH v2 0/5] clk: rockchip: fix handling of fractional dividers
@ 2015-12-24  0:11   ` Michael Turquette
  0 siblings, 0 replies; 15+ messages in thread
From: Michael Turquette @ 2015-12-24  0:11 UTC (permalink / raw)
  To: Heiko Stuebner
  Cc: sboyd, linux-clk, linux-arm-kernel, linux-rockchip, sjoerd.simons, wxt

On 12/22, Heiko Stuebner wrote:
> Essentially unchanged from the first iteration from back in august, just
> including additional patches depending on that and fixing fractional
> dividers on the rk3036 and spdif parent settings.
> 
> In v1, Stephen seemed essentially ok with it but Mike put forward his wish
> to use his planned approach for connected clocks for handling this.
> 
> While that in itself will be very interesting also for handling Rockchip's
> armclk generically, we're now in the situation that everything related
> to audio output relies on working fractional dividers to produce the
> needed clock frequencies, making audio-output essentially non-working on
> all Rockchip socs in mainline at the moment.
> 
> So I'm somewhat hoping for some sort of intermediate solution here :-)

Intermediate solution applied.

Regards,
Mike

> 
> 
> changes in v2:
> - rebase original 3 patches onto 4.4
> - add the 2 new patches from other series, that need that change
> 
> Heiko Stuebner (3):
>   clk: add flag for clocks that need to be enabled on rate changes
>   clk: rockchip: handle mux dependency of fractional dividers
>   clk: rockchip: include downstream muxes into fractional dividers
> 
> Sjoerd Simons (1):
>   clk: rockchip: Allow the RK3288 SPDIF clocks to change their parent
> 
> Xing Zheng (1):
>   clk: rockchip: rk3036: include downstream muxes into fractional
>     dividers
> 
>  drivers/clk/clk.c                 |  18 +++++
>  drivers/clk/rockchip/clk-rk3036.c |  34 +++++-----
>  drivers/clk/rockchip/clk-rk3188.c |  80 +++++++++++-----------
>  drivers/clk/rockchip/clk-rk3288.c |  70 +++++++++----------
>  drivers/clk/rockchip/clk.c        | 137 ++++++++++++++++++++++++++++++++++----
>  drivers/clk/rockchip/clk.h        |  19 ++++++
>  include/linux/clk-provider.h      |   1 +
>  7 files changed, 254 insertions(+), 105 deletions(-)
> 
> -- 
> 2.6.4
> 

^ permalink raw reply	[flat|nested] 15+ messages in thread

* Re: [PATCH v2 0/5] clk: rockchip: fix handling of fractional dividers
@ 2015-12-24  0:11   ` Michael Turquette
  0 siblings, 0 replies; 15+ messages in thread
From: Michael Turquette @ 2015-12-24  0:11 UTC (permalink / raw)
  To: Heiko Stuebner
  Cc: sboyd-sgV2jX0FEOL9JmXXK+q4OQ,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	sjoerd.simons-ZGY8ohtN/8pPYcu2f3hruQ,
	linux-clk-u79uwXL29TY76Z2rM5mHXA,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	wxt-TNX95d0MmH7DzftRWevZcw

On 12/22, Heiko Stuebner wrote:
> Essentially unchanged from the first iteration from back in august, just
> including additional patches depending on that and fixing fractional
> dividers on the rk3036 and spdif parent settings.
> 
> In v1, Stephen seemed essentially ok with it but Mike put forward his wish
> to use his planned approach for connected clocks for handling this.
> 
> While that in itself will be very interesting also for handling Rockchip's
> armclk generically, we're now in the situation that everything related
> to audio output relies on working fractional dividers to produce the
> needed clock frequencies, making audio-output essentially non-working on
> all Rockchip socs in mainline at the moment.
> 
> So I'm somewhat hoping for some sort of intermediate solution here :-)

Intermediate solution applied.

Regards,
Mike

> 
> 
> changes in v2:
> - rebase original 3 patches onto 4.4
> - add the 2 new patches from other series, that need that change
> 
> Heiko Stuebner (3):
>   clk: add flag for clocks that need to be enabled on rate changes
>   clk: rockchip: handle mux dependency of fractional dividers
>   clk: rockchip: include downstream muxes into fractional dividers
> 
> Sjoerd Simons (1):
>   clk: rockchip: Allow the RK3288 SPDIF clocks to change their parent
> 
> Xing Zheng (1):
>   clk: rockchip: rk3036: include downstream muxes into fractional
>     dividers
> 
>  drivers/clk/clk.c                 |  18 +++++
>  drivers/clk/rockchip/clk-rk3036.c |  34 +++++-----
>  drivers/clk/rockchip/clk-rk3188.c |  80 +++++++++++-----------
>  drivers/clk/rockchip/clk-rk3288.c |  70 +++++++++----------
>  drivers/clk/rockchip/clk.c        | 137 ++++++++++++++++++++++++++++++++++----
>  drivers/clk/rockchip/clk.h        |  19 ++++++
>  include/linux/clk-provider.h      |   1 +
>  7 files changed, 254 insertions(+), 105 deletions(-)
> 
> -- 
> 2.6.4
> 

^ permalink raw reply	[flat|nested] 15+ messages in thread

* [PATCH v2 0/5] clk: rockchip: fix handling of fractional dividers
@ 2015-12-24  0:11   ` Michael Turquette
  0 siblings, 0 replies; 15+ messages in thread
From: Michael Turquette @ 2015-12-24  0:11 UTC (permalink / raw)
  To: linux-arm-kernel

On 12/22, Heiko Stuebner wrote:
> Essentially unchanged from the first iteration from back in august, just
> including additional patches depending on that and fixing fractional
> dividers on the rk3036 and spdif parent settings.
> 
> In v1, Stephen seemed essentially ok with it but Mike put forward his wish
> to use his planned approach for connected clocks for handling this.
> 
> While that in itself will be very interesting also for handling Rockchip's
> armclk generically, we're now in the situation that everything related
> to audio output relies on working fractional dividers to produce the
> needed clock frequencies, making audio-output essentially non-working on
> all Rockchip socs in mainline at the moment.
> 
> So I'm somewhat hoping for some sort of intermediate solution here :-)

Intermediate solution applied.

Regards,
Mike

> 
> 
> changes in v2:
> - rebase original 3 patches onto 4.4
> - add the 2 new patches from other series, that need that change
> 
> Heiko Stuebner (3):
>   clk: add flag for clocks that need to be enabled on rate changes
>   clk: rockchip: handle mux dependency of fractional dividers
>   clk: rockchip: include downstream muxes into fractional dividers
> 
> Sjoerd Simons (1):
>   clk: rockchip: Allow the RK3288 SPDIF clocks to change their parent
> 
> Xing Zheng (1):
>   clk: rockchip: rk3036: include downstream muxes into fractional
>     dividers
> 
>  drivers/clk/clk.c                 |  18 +++++
>  drivers/clk/rockchip/clk-rk3036.c |  34 +++++-----
>  drivers/clk/rockchip/clk-rk3188.c |  80 +++++++++++-----------
>  drivers/clk/rockchip/clk-rk3288.c |  70 +++++++++----------
>  drivers/clk/rockchip/clk.c        | 137 ++++++++++++++++++++++++++++++++++----
>  drivers/clk/rockchip/clk.h        |  19 ++++++
>  include/linux/clk-provider.h      |   1 +
>  7 files changed, 254 insertions(+), 105 deletions(-)
> 
> -- 
> 2.6.4
> 

^ permalink raw reply	[flat|nested] 15+ messages in thread

end of thread, other threads:[~2015-12-24  0:11 UTC | newest]

Thread overview: 15+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-12-22 21:27 [PATCH v2 0/5] clk: rockchip: fix handling of fractional dividers Heiko Stuebner
2015-12-22 21:27 ` Heiko Stuebner
2015-12-22 21:27 ` [PATCH v2 1/5] clk: add flag for clocks that need to be enabled on rate changes Heiko Stuebner
2015-12-22 21:27   ` Heiko Stuebner
2015-12-22 21:27 ` [PATCH v2 2/5] clk: rockchip: handle mux dependency of fractional dividers Heiko Stuebner
2015-12-22 21:27   ` Heiko Stuebner
2015-12-22 21:28 ` [PATCH v2 3/5] clk: rockchip: include downstream muxes into " Heiko Stuebner
2015-12-22 21:28   ` Heiko Stuebner
2015-12-22 21:28 ` [PATCH v2 4/5] clk: rockchip: rk3036: " Heiko Stuebner
2015-12-22 21:28   ` Heiko Stuebner
2015-12-22 21:28 ` [PATCH v2 5/5] clk: rockchip: Allow the RK3288 SPDIF clocks to change their parent Heiko Stuebner
2015-12-22 21:28   ` Heiko Stuebner
2015-12-24  0:11 ` [PATCH v2 0/5] clk: rockchip: fix handling of fractional dividers Michael Turquette
2015-12-24  0:11   ` Michael Turquette
2015-12-24  0:11   ` Michael Turquette

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.