]> git.karo-electronics.de Git - karo-tx-linux.git/commitdiff
ENGR00329450 ARM: imx: set CLK_SET_RATE_GATE for gate and divider clocks
authorShawn Guo <shawn.guo@freescale.com>
Mon, 1 Sep 2014 02:52:56 +0000 (10:52 +0800)
committerNitin Garg <nitin.garg@freescale.com>
Fri, 16 Jan 2015 03:17:33 +0000 (21:17 -0600)
A recent QSPI boot failure (5% possibility) on i.MX6SX reminds us that
the peripheral clocks are still missing the check, rate cannot be
changed when the clock is enabled due to the glitchy multiplexers.

Commit a63839445ad3 (ENGR00325423: ARM: imx: pllv3 can only be
configured when it's powered off) adds the check for PLL clocks but
misses the peripheral clocks.  The patch uses the help from clock
framework to check the condition with flag CLK_SET_RATE_GATE.

We adds flag CLK_SET_RATE_GATE for i.MX gate and divider clocks on
which the client drivers usually make clk_set_rate() call, so that the
call will fail when clock is still on instead of standing the risk of
running into glitch issue.

shawn.guo: cherry-pick commit 6487168bc783 from imx_3.10.y

Signed-off-by: Shawn Guo <shawn.guo@freescale.com>
arch/arm/mach-imx/clk.h

index c7cb8c98014d9bceeef92aa8b2e701c1cb18c293..2e5e1e80a25bb9d978af312056acbd6d7be3809e 100644 (file)
@@ -40,16 +40,18 @@ struct clk *imx_clk_gate_exclusive(const char *name, const char *parent,
 static inline struct clk *imx_clk_gate2(const char *name, const char *parent,
                void __iomem *reg, u8 shift)
 {
-       return clk_register_gate2(NULL, name, parent, CLK_SET_RATE_PARENT, reg,
-                       shift, 0, &imx_ccm_lock, NULL);
+       return clk_register_gate2(NULL, name, parent,
+                       CLK_SET_RATE_PARENT | CLK_SET_RATE_GATE,
+                       reg, shift, 0, &imx_ccm_lock, NULL);
 }
 
 static inline struct clk *imx_clk_gate2_shared(const char *name,
                const char *parent, void __iomem *reg, u8 shift,
                unsigned int *share_count)
 {
-       return clk_register_gate2(NULL, name, parent, CLK_SET_RATE_PARENT, reg,
-                       shift, 0, &imx_ccm_lock, share_count);
+       return clk_register_gate2(NULL, name, parent,
+                       CLK_SET_RATE_PARENT | CLK_SET_RATE_GATE,
+                       reg, shift, 0, &imx_ccm_lock, share_count);
 }
 
 struct clk *imx_clk_pfd(const char *name, const char *parent_name,
@@ -79,7 +81,8 @@ static inline struct clk *imx_clk_fixed(const char *name, int rate)
 static inline struct clk *imx_clk_divider(const char *name, const char *parent,
                void __iomem *reg, u8 shift, u8 width)
 {
-       return clk_register_divider(NULL, name, parent, CLK_SET_RATE_PARENT,
+       return clk_register_divider(NULL, name, parent,
+                       CLK_SET_RATE_PARENT | CLK_SET_RATE_GATE,
                        reg, shift, width, 0, &imx_ccm_lock);
 }