A set of clk driver fixes that resolve issues for various SoCs. Most of

these are incorrect clk data, like bad parent descriptions. When the clk
 tree is improperly described things don't work, like USB and UFS
 controllers, because clk frequencies are wonky. Here are the extra
 details:
 
  - Fix the parent of UFS reference clks on Qualcomm SC8280XP so that UFS
    works properly.
  - Fix the clk ID for USB on AT91 RM9200 so the USB driver continues to
    probe.
  - Stop using of_device_get_match_data() on the wrong device for a
    Samsung Exynos driver so it gets the proper clk data.
  - Fix ExynosAutov9 binding.
  - Fix the parent of the div4 clk on Exynos7885.
  - Stop calling runtime PM APIs from the Qualcomm GDSC driver directly
    as it leads to a lockdep splat and is just plain wrong because it
    violates runtime PM semantics by calling runtime PM APIs when the
    device has been runtime PM disabled.
 -----BEGIN PGP SIGNATURE-----
 
 iQJFBAABCAAvFiEE9L57QeeUxqYDyoaDrQKIl8bklSUFAmOH34YRHHNib3lkQGtl
 cm5lbC5vcmcACgkQrQKIl8bklSWa1w/7BNQeGBZaSZR4AM44xvIHqOn0DJnsKDws
 4cPf2tUMSSlfjaSceuF84dM78JSJlxN2QtMKqxooI5H/AwcKA7ZhmKgqHmytPGb8
 yHALXy0nL3+ojuzXB46wn+EN6B7odeAK99dcEsUEytDHDgxUck0WvHmFjUJFwu/r
 2BbQVqGw8EYWz7fngbbovoCGmddLgoHam0dLq5lkiSe7b9NXx+zWilcoEbbXHGah
 HNOkjoeKV1Mub7XlWM86DYp3XH7hn9/gb+ztETVG2OZnPl3vLTI9+CaTyGfVx/29
 0ZwaPOxdzBaOLw+We64BY7ikgqNN274TBt1U6EtL+SBKVlqPd173EcxcNtb93pac
 2OAopef2/DximX6gLQYX8XeAaRJ4HQM1JKH6qdUV2vzlruT+S13/FT8tPsORzFRY
 xGxX98vhVHg6r6BWg0IdLl5F/9QAz2NyPkfxK24wDcnTNVcInmBRYBC2IsaNuXq8
 agOjfxST+V+Lxc8w5lT1zGZIEnvrXcIsW4YT1piacZQsZeUYGPn+7imkBZR+4/mC
 0ggLmTd27u0mzN8ecjLR8mu1D+acoXm+8qAk4CPIRjq3uns03nAgB0yt0aFZV5Z1
 zE+vuNnjlFlTxH+h5vDhmM7QWCLhs9CMRHL41aEDV60ADRC6rkbJodIczpPqlxg4
 c1HkSKuZLaA=
 =EmWU
 -----END PGP SIGNATURE-----

Merge tag 'clk-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/clk/linux

Pull clk fixes from Stephen Boyd:
 "A set of clk driver fixes that resolve issues for various SoCs.

  Most of these are incorrect clk data, like bad parent descriptions.
  When the clk tree is improperly described things don't work, like USB
  and UFS controllers, because clk frequencies are wonky. Here are the
  extra details:

   - Fix the parent of UFS reference clks on Qualcomm SC8280XP so that
     UFS works properly

   - Fix the clk ID for USB on AT91 RM9200 so the USB driver continues
     to probe

   - Stop using of_device_get_match_data() on the wrong device for a
     Samsung Exynos driver so it gets the proper clk data

   - Fix ExynosAutov9 binding

   - Fix the parent of the div4 clk on Exynos7885

   - Stop calling runtime PM APIs from the Qualcomm GDSC driver directly
     as it leads to a lockdep splat and is just plain wrong because it
     violates runtime PM semantics by calling runtime PM APIs when the
     device has been runtime PM disabled"

* tag 'clk-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/clk/linux:
  clk: qcom: gcc-sc8280xp: add cxo as parent for three ufs ref clks
  ARM: at91: rm9200: fix usb device clock id
  clk: samsung: Revert "clk: samsung: exynos-clkout: Use of_device_get_match_data()"
  dt-bindings: clock: exynosautov9: fix reference to CMU_FSYS1
  clk: qcom: gdsc: Remove direct runtime PM calls
  clk: samsung: exynos7885: Correct "div4" clock parents
This commit is contained in:
Linus Torvalds 2022-11-30 15:46:46 -08:00
commit 063c0e773a
8 changed files with 21 additions and 64 deletions

View File

@ -148,7 +148,7 @@ allOf:
items:
- const: oscclk
- const: dout_clkcmu_fsys1_bus
- const: dout_clkcmu_fsys1_mmc_card
- const: gout_clkcmu_fsys1_mmc_card
- const: dout_clkcmu_fsys1_usbdrd
- if:

View File

@ -666,7 +666,7 @@
compatible = "atmel,at91rm9200-udc";
reg = <0xfffb0000 0x4000>;
interrupts = <11 IRQ_TYPE_LEVEL_HIGH 2>;
clocks = <&pmc PMC_TYPE_PERIPHERAL 11>, <&pmc PMC_TYPE_SYSTEM 2>;
clocks = <&pmc PMC_TYPE_PERIPHERAL 11>, <&pmc PMC_TYPE_SYSTEM 1>;
clock-names = "pclk", "hclk";
status = "disabled";
};

View File

@ -40,7 +40,7 @@ static const struct clk_pll_characteristics rm9200_pll_characteristics = {
};
static const struct sck at91rm9200_systemck[] = {
{ .n = "udpck", .p = "usbck", .id = 2 },
{ .n = "udpck", .p = "usbck", .id = 1 },
{ .n = "uhpck", .p = "usbck", .id = 4 },
{ .n = "pck0", .p = "prog0", .id = 8 },
{ .n = "pck1", .p = "prog1", .id = 9 },

View File

@ -5364,6 +5364,8 @@ static struct clk_branch gcc_ufs_1_card_clkref_clk = {
.enable_mask = BIT(0),
.hw.init = &(const struct clk_init_data) {
.name = "gcc_ufs_1_card_clkref_clk",
.parent_data = &gcc_parent_data_tcxo,
.num_parents = 1,
.ops = &clk_branch2_ops,
},
},
@ -5432,6 +5434,8 @@ static struct clk_branch gcc_ufs_card_clkref_clk = {
.enable_mask = BIT(0),
.hw.init = &(const struct clk_init_data) {
.name = "gcc_ufs_card_clkref_clk",
.parent_data = &gcc_parent_data_tcxo,
.num_parents = 1,
.ops = &clk_branch2_ops,
},
},
@ -5848,6 +5852,8 @@ static struct clk_branch gcc_ufs_ref_clkref_clk = {
.enable_mask = BIT(0),
.hw.init = &(const struct clk_init_data) {
.name = "gcc_ufs_ref_clkref_clk",
.parent_data = &gcc_parent_data_tcxo,
.num_parents = 1,
.ops = &clk_branch2_ops,
},
},

View File

@ -11,7 +11,6 @@
#include <linux/kernel.h>
#include <linux/ktime.h>
#include <linux/pm_domain.h>
#include <linux/pm_runtime.h>
#include <linux/regmap.h>
#include <linux/regulator/consumer.h>
#include <linux/reset-controller.h>
@ -56,22 +55,6 @@ enum gdsc_status {
GDSC_ON
};
static int gdsc_pm_runtime_get(struct gdsc *sc)
{
if (!sc->dev)
return 0;
return pm_runtime_resume_and_get(sc->dev);
}
static int gdsc_pm_runtime_put(struct gdsc *sc)
{
if (!sc->dev)
return 0;
return pm_runtime_put_sync(sc->dev);
}
/* Returns 1 if GDSC status is status, 0 if not, and < 0 on error */
static int gdsc_check_status(struct gdsc *sc, enum gdsc_status status)
{
@ -271,8 +254,9 @@ static void gdsc_retain_ff_on(struct gdsc *sc)
regmap_update_bits(sc->regmap, sc->gdscr, mask, mask);
}
static int _gdsc_enable(struct gdsc *sc)
static int gdsc_enable(struct generic_pm_domain *domain)
{
struct gdsc *sc = domain_to_gdsc(domain);
int ret;
if (sc->pwrsts == PWRSTS_ON)
@ -328,22 +312,11 @@ static int _gdsc_enable(struct gdsc *sc)
return 0;
}
static int gdsc_enable(struct generic_pm_domain *domain)
static int gdsc_disable(struct generic_pm_domain *domain)
{
struct gdsc *sc = domain_to_gdsc(domain);
int ret;
ret = gdsc_pm_runtime_get(sc);
if (ret)
return ret;
return _gdsc_enable(sc);
}
static int _gdsc_disable(struct gdsc *sc)
{
int ret;
if (sc->pwrsts == PWRSTS_ON)
return gdsc_assert_reset(sc);
@ -388,18 +361,6 @@ static int _gdsc_disable(struct gdsc *sc)
return 0;
}
static int gdsc_disable(struct generic_pm_domain *domain)
{
struct gdsc *sc = domain_to_gdsc(domain);
int ret;
ret = _gdsc_disable(sc);
gdsc_pm_runtime_put(sc);
return ret;
}
static int gdsc_init(struct gdsc *sc)
{
u32 mask, val;
@ -447,11 +408,6 @@ static int gdsc_init(struct gdsc *sc)
return ret;
}
/* ...and the power-domain */
ret = gdsc_pm_runtime_get(sc);
if (ret)
goto err_disable_supply;
/*
* Votable GDSCs can be ON due to Vote from other masters.
* If a Votable GDSC is ON, make sure we have a Vote.
@ -459,14 +415,14 @@ static int gdsc_init(struct gdsc *sc)
if (sc->flags & VOTABLE) {
ret = gdsc_update_collapse_bit(sc, false);
if (ret)
goto err_put_rpm;
goto err_disable_supply;
}
/* Turn on HW trigger mode if supported */
if (sc->flags & HW_CTRL) {
ret = gdsc_hwctrl(sc, true);
if (ret < 0)
goto err_put_rpm;
goto err_disable_supply;
}
/*
@ -496,13 +452,10 @@ static int gdsc_init(struct gdsc *sc)
ret = pm_genpd_init(&sc->pd, NULL, !on);
if (ret)
goto err_put_rpm;
goto err_disable_supply;
return 0;
err_put_rpm:
if (on)
gdsc_pm_runtime_put(sc);
err_disable_supply:
if (on && sc->rsupply)
regulator_disable(sc->rsupply);
@ -541,8 +494,6 @@ int gdsc_register(struct gdsc_desc *desc,
for (i = 0; i < num; i++) {
if (!scs[i])
continue;
if (pm_runtime_enabled(dev))
scs[i]->dev = dev;
scs[i]->regmap = regmap;
scs[i]->rcdev = rcdev;
ret = gdsc_init(scs[i]);

View File

@ -30,7 +30,6 @@ struct reset_controller_dev;
* @resets: ids of resets associated with this gdsc
* @reset_count: number of @resets
* @rcdev: reset controller
* @dev: the device holding the GDSC, used for pm_runtime calls
*/
struct gdsc {
struct generic_pm_domain pd;
@ -74,7 +73,6 @@ struct gdsc {
const char *supply;
struct regulator *rsupply;
struct device *dev;
};
struct gdsc_desc {

View File

@ -81,17 +81,19 @@ MODULE_DEVICE_TABLE(of, exynos_clkout_ids);
static int exynos_clkout_match_parent_dev(struct device *dev, u32 *mux_mask)
{
const struct exynos_clkout_variant *variant;
const struct of_device_id *match;
if (!dev->parent) {
dev_err(dev, "not instantiated from MFD\n");
return -EINVAL;
}
variant = of_device_get_match_data(dev->parent);
if (!variant) {
match = of_match_device(exynos_clkout_ids, dev->parent);
if (!match) {
dev_err(dev, "cannot match parent device\n");
return -EINVAL;
}
variant = match->data;
*mux_mask = variant->mux_mask;

View File

@ -231,7 +231,7 @@ static const struct samsung_div_clock top_div_clks[] __initconst = {
CLK_CON_DIV_PLL_SHARED0_DIV2, 0, 1),
DIV(CLK_DOUT_SHARED0_DIV3, "dout_shared0_div3", "fout_shared0_pll",
CLK_CON_DIV_PLL_SHARED0_DIV3, 0, 2),
DIV(CLK_DOUT_SHARED0_DIV4, "dout_shared0_div4", "fout_shared0_pll",
DIV(CLK_DOUT_SHARED0_DIV4, "dout_shared0_div4", "dout_shared0_div2",
CLK_CON_DIV_PLL_SHARED0_DIV4, 0, 1),
DIV(CLK_DOUT_SHARED0_DIV5, "dout_shared0_div5", "fout_shared0_pll",
CLK_CON_DIV_PLL_SHARED0_DIV5, 0, 3),
@ -239,7 +239,7 @@ static const struct samsung_div_clock top_div_clks[] __initconst = {
CLK_CON_DIV_PLL_SHARED1_DIV2, 0, 1),
DIV(CLK_DOUT_SHARED1_DIV3, "dout_shared1_div3", "fout_shared1_pll",
CLK_CON_DIV_PLL_SHARED1_DIV3, 0, 2),
DIV(CLK_DOUT_SHARED1_DIV4, "dout_shared1_div4", "fout_shared1_pll",
DIV(CLK_DOUT_SHARED1_DIV4, "dout_shared1_div4", "dout_shared1_div2",
CLK_CON_DIV_PLL_SHARED1_DIV4, 0, 1),
/* CORE */