Commit 12ba8571ab6b232f5facef6b1dd28c5ebc2b530a

Authored by Linus Torvalds

Merge tag 'clk-fixes-for-linus' of git://git.linaro.org/people/mike.turquette/linux

Pull clock driver fixes from Mike Turquette:
 "Small number of fixes for clock drivers and a single null pointer
  dereference fix in the framework core code.

  The driver fixes vary from fixing section mismatch warnings to
  preventing machines from hanging (and preventing developers from
  crying)"

* tag 'clk-fixes-for-linus' of git://git.linaro.org/people/mike.turquette/linux:
  clk: fix possible null pointer dereference
  Revert "clk: ppc-corenet: Fix Section mismatch warning"
  clk: rockchip: fix deadlock possibility in cpuclk
  clk: berlin: bg2q: remove non-exist "smemc" gate clock
  clk: at91: keep slow clk enabled to prevent system hang
  clk: rockchip: fix rk3288 cpuclk core dividers
  clk: rockchip: fix rk3066 pll lock bit location
  clk: rockchip: Fix clock gate for rk3188 hclk_emem_peri
  clk: rockchip: add CLK_IGNORE_UNUSED flag to fix rk3066/rk3188 USB Host

Showing 7 changed files Side-by-side Diff

drivers/clk/at91/clk-slow.c
... ... @@ -70,6 +70,7 @@
70 70  
71 71 #define to_clk_sam9x5_slow(hw) container_of(hw, struct clk_sam9x5_slow, hw)
72 72  
  73 +static struct clk *slow_clk;
73 74  
74 75 static int clk_slow_osc_prepare(struct clk_hw *hw)
75 76 {
... ... @@ -357,6 +358,8 @@
357 358 clk = clk_register(NULL, &slowck->hw);
358 359 if (IS_ERR(clk))
359 360 kfree(slowck);
  361 + else
  362 + slow_clk = clk;
360 363  
361 364 return clk;
362 365 }
... ... @@ -433,6 +436,8 @@
433 436 clk = clk_register(NULL, &slowck->hw);
434 437 if (IS_ERR(clk))
435 438 kfree(slowck);
  439 + else
  440 + slow_clk = clk;
436 441  
437 442 return clk;
438 443 }
... ... @@ -465,4 +470,26 @@
465 470  
466 471 of_clk_add_provider(np, of_clk_src_simple_get, clk);
467 472 }
  473 +
  474 +/*
  475 + * FIXME: All slow clk users are not properly claiming it (get + prepare +
  476 + * enable) before using it.
  477 + * If all users properly claiming this clock decide that they don't need it
  478 + * anymore (or are removed), it is disabled while faulty users are still
  479 + * requiring it, and the system hangs.
  480 + * Prevent this clock from being disabled until all users are properly
  481 + * requesting it.
  482 + * Once this is done we should remove this function and the slow_clk variable.
  483 + */
  484 +static int __init of_at91_clk_slow_retain(void)
  485 +{
  486 + if (!slow_clk)
  487 + return 0;
  488 +
  489 + __clk_get(slow_clk);
  490 + clk_prepare_enable(slow_clk);
  491 +
  492 + return 0;
  493 +}
  494 +arch_initcall(of_at91_clk_slow_retain);
drivers/clk/berlin/bg2q.c
... ... @@ -285,7 +285,6 @@
285 285 { "pbridge", "perif", 15, CLK_IGNORE_UNUSED },
286 286 { "sdio", "perif", 16, CLK_IGNORE_UNUSED },
287 287 { "nfc", "perif", 18 },
288   - { "smemc", "perif", 19 },
289 288 { "pcie", "perif", 22 },
290 289 };
291 290  
drivers/clk/clk-ppc-corenet.c
... ... @@ -291,7 +291,7 @@
291 291 {}
292 292 };
293 293  
294   -static struct platform_driver ppc_corenet_clk_driver __initdata = {
  294 +static struct platform_driver ppc_corenet_clk_driver = {
295 295 .driver = {
296 296 .name = "ppc_corenet_clock",
297 297 .of_match_table = ppc_clk_ids,
... ... @@ -1366,7 +1366,7 @@
1366 1366 new_rate = clk->ops->determine_rate(clk->hw, rate,
1367 1367 &best_parent_rate,
1368 1368 &parent_hw);
1369   - parent = parent_hw->clk;
  1369 + parent = parent_hw ? parent_hw->clk : NULL;
1370 1370 } else if (clk->ops->round_rate) {
1371 1371 new_rate = clk->ops->round_rate(clk->hw, rate,
1372 1372 &best_parent_rate);
drivers/clk/rockchip/clk-cpu.c
... ... @@ -124,10 +124,11 @@
124 124 {
125 125 const struct rockchip_cpuclk_reg_data *reg_data = cpuclk->reg_data;
126 126 unsigned long alt_prate, alt_div;
  127 + unsigned long flags;
127 128  
128 129 alt_prate = clk_get_rate(cpuclk->alt_parent);
129 130  
130   - spin_lock(cpuclk->lock);
  131 + spin_lock_irqsave(cpuclk->lock, flags);
131 132  
132 133 /*
133 134 * If the old parent clock speed is less than the clock speed
... ... @@ -164,7 +165,7 @@
164 165 cpuclk->reg_base + reg_data->core_reg);
165 166 }
166 167  
167   - spin_unlock(cpuclk->lock);
  168 + spin_unlock_irqrestore(cpuclk->lock, flags);
168 169 return 0;
169 170 }
170 171  
... ... @@ -173,6 +174,7 @@
173 174 {
174 175 const struct rockchip_cpuclk_reg_data *reg_data = cpuclk->reg_data;
175 176 const struct rockchip_cpuclk_rate_table *rate;
  177 + unsigned long flags;
176 178  
177 179 rate = rockchip_get_cpuclk_settings(cpuclk, ndata->new_rate);
178 180 if (!rate) {
... ... @@ -181,7 +183,7 @@
181 183 return -EINVAL;
182 184 }
183 185  
184   - spin_lock(cpuclk->lock);
  186 + spin_lock_irqsave(cpuclk->lock, flags);
185 187  
186 188 if (ndata->old_rate < ndata->new_rate)
187 189 rockchip_cpuclk_set_dividers(cpuclk, rate);
... ... @@ -201,7 +203,7 @@
201 203 if (ndata->old_rate > ndata->new_rate)
202 204 rockchip_cpuclk_set_dividers(cpuclk, rate);
203 205  
204   - spin_unlock(cpuclk->lock);
  206 + spin_unlock_irqrestore(cpuclk->lock, flags);
205 207 return 0;
206 208 }
207 209  
drivers/clk/rockchip/clk-rk3188.c
... ... @@ -210,6 +210,17 @@
210 210 PNAME(mux_mac_p) = { "gpll", "dpll" };
211 211 PNAME(mux_sclk_macref_p) = { "mac_src", "ext_rmii" };
212 212  
  213 +static struct rockchip_pll_clock rk3066_pll_clks[] __initdata = {
  214 + [apll] = PLL(pll_rk3066, PLL_APLL, "apll", mux_pll_p, 0, RK2928_PLL_CON(0),
  215 + RK2928_MODE_CON, 0, 5, 0, rk3188_pll_rates),
  216 + [dpll] = PLL(pll_rk3066, PLL_DPLL, "dpll", mux_pll_p, 0, RK2928_PLL_CON(4),
  217 + RK2928_MODE_CON, 4, 4, 0, NULL),
  218 + [cpll] = PLL(pll_rk3066, PLL_CPLL, "cpll", mux_pll_p, 0, RK2928_PLL_CON(8),
  219 + RK2928_MODE_CON, 8, 6, ROCKCHIP_PLL_SYNC_RATE, rk3188_pll_rates),
  220 + [gpll] = PLL(pll_rk3066, PLL_GPLL, "gpll", mux_pll_p, 0, RK2928_PLL_CON(12),
  221 + RK2928_MODE_CON, 12, 7, ROCKCHIP_PLL_SYNC_RATE, rk3188_pll_rates),
  222 +};
  223 +
213 224 static struct rockchip_pll_clock rk3188_pll_clks[] __initdata = {
214 225 [apll] = PLL(pll_rk3066, PLL_APLL, "apll", mux_pll_p, 0, RK2928_PLL_CON(0),
215 226 RK2928_MODE_CON, 0, 6, 0, rk3188_pll_rates),
216 227  
... ... @@ -427,11 +438,11 @@
427 438 /* hclk_peri gates */
428 439 GATE(0, "hclk_peri_axi_matrix", "hclk_peri", CLK_IGNORE_UNUSED, RK2928_CLKGATE_CON(4), 0, GFLAGS),
429 440 GATE(0, "hclk_peri_ahb_arbi", "hclk_peri", CLK_IGNORE_UNUSED, RK2928_CLKGATE_CON(4), 6, GFLAGS),
430   - GATE(0, "hclk_emem_peri", "hclk_peri", 0, RK2928_CLKGATE_CON(4), 7, GFLAGS),
  441 + GATE(0, "hclk_emem_peri", "hclk_peri", CLK_IGNORE_UNUSED, RK2928_CLKGATE_CON(4), 7, GFLAGS),
431 442 GATE(HCLK_EMAC, "hclk_emac", "hclk_peri", 0, RK2928_CLKGATE_CON(7), 0, GFLAGS),
432 443 GATE(HCLK_NANDC0, "hclk_nandc0", "hclk_peri", 0, RK2928_CLKGATE_CON(5), 9, GFLAGS),
433   - GATE(0, "hclk_usb_peri", "hclk_peri", 0, RK2928_CLKGATE_CON(4), 5, GFLAGS),
434   - GATE(HCLK_OTG0, "hclk_usbotg0", "hclk_peri", 0, RK2928_CLKGATE_CON(5), 13, GFLAGS),
  444 + GATE(0, "hclk_usb_peri", "hclk_peri", CLK_IGNORE_UNUSED, RK2928_CLKGATE_CON(4), 5, GFLAGS),
  445 + GATE(HCLK_OTG0, "hclk_usbotg0", "hclk_peri", CLK_IGNORE_UNUSED, RK2928_CLKGATE_CON(5), 13, GFLAGS),
435 446 GATE(HCLK_HSADC, "hclk_hsadc", "hclk_peri", 0, RK2928_CLKGATE_CON(7), 5, GFLAGS),
436 447 GATE(HCLK_PIDF, "hclk_pidfilter", "hclk_peri", 0, RK2928_CLKGATE_CON(7), 6, GFLAGS),
437 448 GATE(HCLK_SDMMC, "hclk_sdmmc", "hclk_peri", 0, RK2928_CLKGATE_CON(5), 10, GFLAGS),
... ... @@ -592,7 +603,8 @@
592 603 GATE(0, "hclk_cif1", "hclk_cpu", 0, RK2928_CLKGATE_CON(6), 6, GFLAGS),
593 604 GATE(0, "hclk_hdmi", "hclk_cpu", 0, RK2928_CLKGATE_CON(4), 14, GFLAGS),
594 605  
595   - GATE(HCLK_OTG1, "hclk_usbotg1", "hclk_peri", 0, RK2928_CLKGATE_CON(5), 14, GFLAGS),
  606 + GATE(HCLK_OTG1, "hclk_usbotg1", "hclk_peri", CLK_IGNORE_UNUSED,
  607 + RK2928_CLKGATE_CON(5), 14, GFLAGS),
596 608  
597 609 GATE(0, "aclk_cif1", "aclk_vio1", 0, RK2928_CLKGATE_CON(6), 7, GFLAGS),
598 610  
... ... @@ -680,7 +692,8 @@
680 692 GATE(0, "hclk_imem0", "hclk_cpu", 0, RK2928_CLKGATE_CON(4), 14, GFLAGS),
681 693 GATE(0, "hclk_imem1", "hclk_cpu", 0, RK2928_CLKGATE_CON(4), 15, GFLAGS),
682 694  
683   - GATE(HCLK_OTG1, "hclk_usbotg1", "hclk_peri", 0, RK2928_CLKGATE_CON(7), 3, GFLAGS),
  695 + GATE(HCLK_OTG1, "hclk_usbotg1", "hclk_peri", CLK_IGNORE_UNUSED,
  696 + RK2928_CLKGATE_CON(7), 3, GFLAGS),
684 697 GATE(HCLK_HSIC, "hclk_hsic", "hclk_peri", 0, RK2928_CLKGATE_CON(7), 4, GFLAGS),
685 698  
686 699 GATE(PCLK_TIMER3, "pclk_timer3", "pclk_cpu", 0, RK2928_CLKGATE_CON(7), 9, GFLAGS),
... ... @@ -735,8 +748,8 @@
735 748 static void __init rk3066a_clk_init(struct device_node *np)
736 749 {
737 750 rk3188_common_clk_init(np);
738   - rockchip_clk_register_plls(rk3188_pll_clks,
739   - ARRAY_SIZE(rk3188_pll_clks),
  751 + rockchip_clk_register_plls(rk3066_pll_clks,
  752 + ARRAY_SIZE(rk3066_pll_clks),
740 753 RK3066_GRF_SOC_STATUS);
741 754 rockchip_clk_register_branches(rk3066a_clk_branches,
742 755 ARRAY_SIZE(rk3066a_clk_branches));
drivers/clk/rockchip/clk-rk3288.c
... ... @@ -145,20 +145,20 @@
145 145 }
146 146  
147 147 static struct rockchip_cpuclk_rate_table rk3288_cpuclk_rates[] __initdata = {
148   - RK3288_CPUCLK_RATE(1800000000, 2, 4, 2, 4, 4),
149   - RK3288_CPUCLK_RATE(1704000000, 2, 4, 2, 4, 4),
150   - RK3288_CPUCLK_RATE(1608000000, 2, 4, 2, 4, 4),
151   - RK3288_CPUCLK_RATE(1512000000, 2, 4, 2, 4, 4),
152   - RK3288_CPUCLK_RATE(1416000000, 2, 4, 2, 4, 4),
153   - RK3288_CPUCLK_RATE(1200000000, 2, 4, 2, 4, 4),
154   - RK3288_CPUCLK_RATE(1008000000, 2, 4, 2, 4, 4),
155   - RK3288_CPUCLK_RATE( 816000000, 2, 4, 2, 4, 4),
156   - RK3288_CPUCLK_RATE( 696000000, 2, 4, 2, 4, 4),
157   - RK3288_CPUCLK_RATE( 600000000, 2, 4, 2, 4, 4),
158   - RK3288_CPUCLK_RATE( 408000000, 2, 4, 2, 4, 4),
159   - RK3288_CPUCLK_RATE( 312000000, 2, 4, 2, 4, 4),
160   - RK3288_CPUCLK_RATE( 216000000, 2, 4, 2, 4, 4),
161   - RK3288_CPUCLK_RATE( 126000000, 2, 4, 2, 4, 4),
  148 + RK3288_CPUCLK_RATE(1800000000, 1, 3, 1, 3, 3),
  149 + RK3288_CPUCLK_RATE(1704000000, 1, 3, 1, 3, 3),
  150 + RK3288_CPUCLK_RATE(1608000000, 1, 3, 1, 3, 3),
  151 + RK3288_CPUCLK_RATE(1512000000, 1, 3, 1, 3, 3),
  152 + RK3288_CPUCLK_RATE(1416000000, 1, 3, 1, 3, 3),
  153 + RK3288_CPUCLK_RATE(1200000000, 1, 3, 1, 3, 3),
  154 + RK3288_CPUCLK_RATE(1008000000, 1, 3, 1, 3, 3),
  155 + RK3288_CPUCLK_RATE( 816000000, 1, 3, 1, 3, 3),
  156 + RK3288_CPUCLK_RATE( 696000000, 1, 3, 1, 3, 3),
  157 + RK3288_CPUCLK_RATE( 600000000, 1, 3, 1, 3, 3),
  158 + RK3288_CPUCLK_RATE( 408000000, 1, 3, 1, 3, 3),
  159 + RK3288_CPUCLK_RATE( 312000000, 1, 3, 1, 3, 3),
  160 + RK3288_CPUCLK_RATE( 216000000, 1, 3, 1, 3, 3),
  161 + RK3288_CPUCLK_RATE( 126000000, 1, 3, 1, 3, 3),
162 162 };
163 163  
164 164 static const struct rockchip_cpuclk_reg_data rk3288_cpuclk_data = {