public inbox for linux-omap@vger.kernel.org
 help / color / mirror / Atom feed
From: Paul Walmsley <paul@pwsan.com>
To: linux-omap-open-source@linux.omap.com
Subject: [PATCH 07/27] omap2 clock: init clksel clock parents to hardware reality at clock init
Date: Mon, 27 Aug 2007 02:39:03 -0600	[thread overview]
Message-ID: <20070827084122.756992676@pwsan.com> (raw)
In-Reply-To: 20070827083856.549249288@pwsan.com

[-- Attachment #1: add_init_clksel_parent.patch --]
[-- Type: text/plain, Size: 10795 bytes --]

Source-selectable clksel clocks have a 'default parent' assigned to them
at compile-time.  This default parent may or may not match the reality 
that is configured in the hardware registers by the bootloader.  Clock tree
recalculations could be erratic if the struct clk parent field contents
don't match the hardware registers.

Resolve this by creating omap2_init_clksel_parent() to read the hardware
registers and update the struct clk parent field as appropriate for clksel
clocks.  Add an '.init' field to each source-selectable clk structure so
that the parent is fixed up when the clock is initially registered.  (We
don't do this for clksel clocks that are only rate-selectable, since they
only have one possible parent clock.)

Signed-off-by: Paul Walmsley <paul@pwsan.com>

---
 arch/arm/mach-omap2/clock.c |   59 ++++++++++++++++++++++++++++++++++++++++----
 arch/arm/mach-omap2/clock.h |   22 ++++++++++++++++
 2 files changed, 76 insertions(+), 5 deletions(-)

Index: linux-omap/arch/arm/mach-omap2/clock.c
===================================================================
--- linux-omap.orig/arch/arm/mach-omap2/clock.c	2007-08-27 00:37:39.000000000 -0600
+++ linux-omap/arch/arm/mach-omap2/clock.c	2007-08-27 00:37:46.000000000 -0600
@@ -93,6 +93,55 @@
  * Omap2 specific clock functions
  *-------------------------------------------------------------------------*/
 
+static inline u8 mask_to_shift(u32 mask)
+{
+	return ffs(mask) - 1;
+}
+
+/**
+ * omap2_init_clksel_parent - set a clksel clk's parent field from the hardware
+ * @clk: OMAP clock struct ptr to use
+ *
+ * Given a pointer to a source-selectable struct clk, read the hardware
+ * register and determine what its parent is currently set to.  Update the
+ * clk->parent field with the appropriate clk ptr.
+ */
+static void omap2_init_clksel_parent(struct clk *clk)
+{
+	const struct clksel *clks;
+	const struct clksel_rate *clkr;
+	u32 r, found = 0;
+
+	if (!clk->clksel)
+		return;
+
+	/* XXX Should be __raw_readl for non-CM 3430 clocks ? */
+	r = cm_read_reg(clk->clksel_reg) & clk->clksel_mask;
+	r >>= mask_to_shift(clk->clksel_mask);
+
+	for (clks = clk->clksel; clks->parent && !found; clks++) {
+		for (clkr = clks->rates; clkr->div && !found; clkr++) {
+			if ((clkr->flags & cpu_mask) && (clkr->val == r)) {
+				if (clk->parent != clks->parent) {
+					pr_debug("clock: inited %s parent "
+						 "to %s (was %s)\n",
+						 clk->name, clks->parent->name,
+						 ((clk->parent->name) ?
+						  clk->parent->name : "NULL"));
+					clk->parent = clks->parent;
+				};
+				found = 1;
+			}
+		}
+	}
+
+	if (!found)
+		printk(KERN_ERR "clock: init parent: could not find "
+		       "regval %0x for clock %s\n", r,  clk->name);
+
+	return;
+}
+
 /* Recalculate SYST_CLK */
 static void omap2_sys_clk_recalc(struct clk * clk)
 {
@@ -1193,6 +1242,11 @@
 	struct clk ** clkp;
 	u32 clkrate;
 
+	if (cpu_is_omap242x())
+		cpu_mask = RATE_IN_242X;
+	else if (cpu_is_omap2430())
+		cpu_mask = RATE_IN_243X;
+
 	clk_init(&omap2_clk_functions);
 	omap2_get_crystal_rate(&osc_ck, &sys_ck);
 
@@ -1210,11 +1264,6 @@
 		}
 	}
 
-	if (cpu_is_omap242x())
-		cpu_mask = RATE_IN_242X;
-	else if (cpu_is_omap2430())
-		cpu_mask = RATE_IN_243X;
-
 	/* Check the MPU rate set by bootloader */
 	clkrate = omap2_get_dpll_rate(&dpll_ck);
 	for (prcm = rate_table; prcm->mpu_speed; prcm++) {
Index: linux-omap/arch/arm/mach-omap2/clock.h
===================================================================
--- linux-omap.orig/arch/arm/mach-omap2/clock.h	2007-08-27 00:37:43.000000000 -0600
+++ linux-omap/arch/arm/mach-omap2/clock.h	2007-08-27 00:37:46.000000000 -0600
@@ -29,6 +29,7 @@
 static long omap2_round_to_table_rate(struct clk * clk, unsigned long rate);
 static void omap2_clk_disable(struct clk *clk);
 static void omap2_sys_clk_recalc(struct clk * clk);
+static void omap2_init_clksel_parent(struct clk *clk);
 static u32 omap2_clksel_to_divisor(u32 div_sel, u32 field_val);
 static u32 omap2_clksel_get_divisor(struct clk *clk);
 static void omap2_dpll_recalc(struct clk *clk);
@@ -690,6 +691,7 @@
 				RATE_FIXED | CM_PLL_SEL1 | RATE_PROPAGATES |
 				PARENT_CONTROLS_CLOCK,
 	.src_offset	= OMAP24XX_54M_SOURCE_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(PLL_MOD, CM_CLKSEL1),
 	.clksel_mask	= OMAP24XX_54M_SOURCE,
 	.clksel		= func_54m_clksel,
@@ -729,6 +731,7 @@
 	.flags		= CLOCK_IN_OMAP242X | CLOCK_IN_OMAP243X |
 				RATE_FIXED | RATE_PROPAGATES |
 				PARENT_CONTROLS_CLOCK,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(PLL_MOD, CM_CLKSEL1),
 	.clksel_mask	= OMAP2430_96M_SOURCE,
 	.clksel		= func_96m_clksel,
@@ -761,6 +764,7 @@
 				RATE_FIXED | CM_PLL_SEL1 | RATE_PROPAGATES |
 				PARENT_CONTROLS_CLOCK,
 	.src_offset	= OMAP24XX_48M_SOURCE_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(PLL_MOD, CM_CLKSEL1),
 	.clksel_mask	= OMAP24XX_48M_SOURCE,
 	.clksel		= func_48m_clksel,
@@ -830,6 +834,7 @@
 	.src_offset	= OMAP24XX_CLKOUT_SOURCE_SHIFT,
 	.enable_reg	= OMAP24XX_PRCM_CLKOUT_CTRL,
 	.enable_bit	= OMAP24XX_CLKOUT_EN_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP24XX_PRCM_CLKOUT_CTRL,
 	.clksel_mask	= OMAP24XX_CLKOUT_SOURCE_MASK,
 	.clksel		= common_clkout_src_clksel,
@@ -872,6 +877,7 @@
 				RATE_PROPAGATES,
 	.enable_reg	= OMAP24XX_PRCM_CLKOUT_CTRL,
 	.enable_bit	= OMAP2420_CLKOUT2_EN_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP24XX_PRCM_CLKOUT_CTRL,
 	.clksel_mask	= OMAP2420_CLKOUT2_SOURCE_MASK,
 	.clksel		= common_clkout_src_clksel,
@@ -937,6 +943,7 @@
 				ALWAYS_ENABLED | CM_MPU_SEL1 | DELAYED_APP |
 				CONFIG_PARTICIPANT | RATE_PROPAGATES,
 	.rate_offset	= OMAP24XX_CLKSEL_MPU_SHIFT,	/* bits 0-4 */
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(MPU_MOD, CM_CLKSEL),
 	.clksel_mask	= OMAP24XX_CLKSEL_MPU_MASK,
 	.clksel		= mpu_clksel,
@@ -1431,6 +1438,7 @@
 	.enable_bit	= OMAP24XX_EN_DSS1_SHIFT,
 	.rate_offset	= OMAP24XX_CLKSEL_DSS1_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_DSS1_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL1),
 	.clksel_mask	= OMAP24XX_CLKSEL_DSS1_MASK,
 	.clksel		= dss1_fck_clksel,
@@ -1462,6 +1470,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_DSS2_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_DSS2_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL1),
 	.clksel_mask	= OMAP24XX_CLKSEL_DSS2_MASK,
 	.clksel		= dss2_fck_clksel,
@@ -1522,6 +1531,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(WKUP_MOD, OMAP24XX_CM_FCLKEN),	/* Bit0 */
 	.enable_bit	= OMAP24XX_EN_GPT1_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT1_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT1_MASK,
 	.clksel		= gpt_clksel,
@@ -1545,6 +1555,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_GPT2_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT2_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT2_MASK,
 	.clksel		= gpt_clksel,
@@ -1568,6 +1579,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_GPT3_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT3_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT3_MASK,
 	.clksel		= gpt_clksel,
@@ -1591,6 +1603,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_GPT4_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT4_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT4_MASK,
 	.clksel		= gpt_clksel,
@@ -1614,6 +1627,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_GPT5_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT5_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT5_MASK,
 	.clksel		= gpt_clksel,
@@ -1637,6 +1651,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_GPT6_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT6_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT6_MASK,
 	.clksel		= gpt_clksel,
@@ -1660,6 +1675,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_GPT7_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT7_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT7_MASK,
 	.clksel		= gpt_clksel,
@@ -1683,6 +1699,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_GPT8_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT8_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT8_MASK,
 	.clksel		= gpt_clksel,
@@ -1706,6 +1723,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_GPT9_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT9_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT9_MASK,
 	.clksel		= gpt_clksel,
@@ -1729,6 +1747,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_GPT10_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT10_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT10_MASK,
 	.clksel		= gpt_clksel,
@@ -1752,6 +1771,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_GPT11_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT11_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT11_MASK,
 	.clksel		= gpt_clksel,
@@ -1775,6 +1795,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP24XX_EN_GPT12_SHIFT,
 	.src_offset	= OMAP24XX_CLKSEL_GPT12_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL2),
 	.clksel_mask	= OMAP24XX_CLKSEL_GPT12_MASK,
 	.clksel		= gpt_clksel,
@@ -2308,6 +2329,7 @@
 	.enable_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_FCLKEN1),
 	.enable_bit	= OMAP2420_EN_VLYNQ_SHIFT,
 	.src_offset	= OMAP2420_CLKSEL_VLYNQ_SHIFT,
+	.init		= &omap2_init_clksel_parent,
 	.clksel_reg	= OMAP_CM_REGADDR(CORE_MOD, CM_CLKSEL1),
 	.clksel_mask	= OMAP2420_CLKSEL_VLYNQ_MASK,
 	.clksel		= vlynq_fck_clksel,

-- 

  parent reply	other threads:[~2007-08-27  8:39 UTC|newest]

Thread overview: 29+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2007-08-27  8:38 [PATCH 00/27] omap2 clock: resend: framework generalization, cleanup Paul Walmsley
2007-08-27  8:38 ` [PATCH 01/27] omap2 clock: dsp_ick parent is dsp_fck, not core_ck Paul Walmsley
2007-08-27  8:38 ` [PATCH 02/27] omap2 clock: generalize initial clock rate setup: recalculate_root_clocks() Paul Walmsley
2007-08-27  8:38 ` [PATCH 03/27] omap2 clock: mark onchip_clksas __initdata Paul Walmsley
2007-08-27  8:39 ` [PATCH 04/27] omap2 clock: remove superfluous omap2_propagate_rate() Paul Walmsley
2007-08-27  8:39 ` [PATCH 05/27] omap2 clock: rename, add comment to omap2_mpu_recalc() Paul Walmsley
2007-08-27  8:39 ` [PATCH 06/27] omap2 clock: add clksel and clksel_rate data Paul Walmsley
2007-08-27  8:39 ` Paul Walmsley [this message]
2007-08-27  8:39 ` [PATCH 08/27] omap2 clock: convert omap2_clksel_to_divisor and omap2_divisor_to_clksel to use new clksel struct Paul Walmsley
2007-08-27  8:39 ` [PATCH 09/27] omap2 clock: convert omap2_clksel_round_rate " Paul Walmsley
2007-08-27  8:39 ` [PATCH 10/27] omap2 clock: convert omap2_get_clksel " Paul Walmsley
2007-08-27  8:39 ` [PATCH 11/27] omap2 clock: convert omap2_clksel_get_src_field() " Paul Walmsley
2007-08-27  8:39 ` [PATCH 12/27] omap2 clock: stop using clk->src_offset in omap2_clk_set_rate() Paul Walmsley
2007-08-27  8:39 ` [PATCH 13/27] omap2 clock: stop using clk->src_offset in omap2_clk_set_parent() Paul Walmsley
2007-08-27  8:39 ` [PATCH 14/27] omap2 clock: clean out old code from omap2_clksel_recalc() Paul Walmsley
2007-08-27  8:39 ` [PATCH 15/27] omap2 clock: convert remaining clksel clocks to use omap2_clksel_recalc Paul Walmsley
2007-08-27  8:39 ` [PATCH 16/27] omap2 clock: remove all {src, rate}_offset fields from struct clk Paul Walmsley
2007-08-27  8:39 ` [PATCH 17/27] omap2 clock: use the struct clk round_rate field for clksel rate rounding code Paul Walmsley
2007-08-27  8:39 ` [PATCH 18/27] omap2 clock: separate clksel set_rate code into its own function Paul Walmsley
2007-08-27  8:39 ` [PATCH 19/27] omap2 clock: drop RATE_CKCTL from all OMAP2 clocks Paul Walmsley
2007-08-27  8:39 ` [PATCH 20/27] omap2 clock: remove *_SEL* clock flags Paul Walmsley
2007-08-27  8:39 ` [PATCH 21/27] omap2 clock: call clock-specific enable/disable functions if present Paul Walmsley
2007-08-27  8:39 ` [PATCH 22/27] omap2 clock: use custom osc_ck enable/disable routines Paul Walmsley
2007-08-27  8:39 ` [PATCH 23/27] omap2 clock: use standard clk->enable/disable for APLLs Paul Walmsley
2007-08-27  8:39 ` [PATCH 24/27] omap2 clock: replace omap2_get_crystal_rate() with clock-specific recalc code Paul Walmsley
2007-08-27  8:39 ` [PATCH 25/27] omap2 clock: Standardize DPLL rate recalculation with struct dpll_data Paul Walmsley
2007-08-27  8:39 ` [PATCH 26/27] omap2 clock: generalize clock enable upon framework initialization Paul Walmsley
2007-08-27  8:39 ` [PATCH 27/27] omap2 clock: add three missing clocks: gpmc_fck, sdma_{i, f}ck Paul Walmsley
2007-08-31 18:24 ` [PATCH 00/27] omap2 clock: resend: framework generalization, cleanup Tony Lindgren

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20070827084122.756992676@pwsan.com \
    --to=paul@pwsan.com \
    --cc=linux-omap-open-source@linux.omap.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox