ARM: tegra: clock: enable clk reset for non-peripheral clocks
Add a new 'reset' clk op. This can be provided for any clock, not just peripherals. Signed-off-by: Dima Zavin <dima@android.com> Acked-by: Olof Johansson <olof@lixom.net> Signed-off-by: Colin Cross <ccross@android.com>
This commit is contained in:
parent
375b19cd34
commit
2b84cb4faa
|
@ -86,6 +86,7 @@ struct clk_ops {
|
||||||
int (*set_parent)(struct clk *, struct clk *);
|
int (*set_parent)(struct clk *, struct clk *);
|
||||||
int (*set_rate)(struct clk *, unsigned long);
|
int (*set_rate)(struct clk *, unsigned long);
|
||||||
long (*round_rate)(struct clk *, unsigned long);
|
long (*round_rate)(struct clk *, unsigned long);
|
||||||
|
void (*reset)(struct clk *, bool);
|
||||||
};
|
};
|
||||||
|
|
||||||
enum clk_state {
|
enum clk_state {
|
||||||
|
|
|
@ -263,6 +263,18 @@ static struct clk_ops tegra_clk_m_ops = {
|
||||||
.disable = tegra2_clk_m_disable,
|
.disable = tegra2_clk_m_disable,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
void tegra2_periph_reset_assert(struct clk *c)
|
||||||
|
{
|
||||||
|
BUG_ON(!c->ops->reset);
|
||||||
|
c->ops->reset(c, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tegra2_periph_reset_deassert(struct clk *c)
|
||||||
|
{
|
||||||
|
BUG_ON(!c->ops->reset);
|
||||||
|
c->ops->reset(c, false);
|
||||||
|
}
|
||||||
|
|
||||||
/* super clock functions */
|
/* super clock functions */
|
||||||
/* "super clocks" on tegra have two-stage muxes and a clock skipping
|
/* "super clocks" on tegra have two-stage muxes and a clock skipping
|
||||||
* super divider. We will ignore the clock skipping divider, since we
|
* super divider. We will ignore the clock skipping divider, since we
|
||||||
|
@ -895,23 +907,17 @@ static void tegra2_periph_clk_disable(struct clk *c)
|
||||||
CLK_OUT_ENB_CLR + PERIPH_CLK_TO_ENB_SET_REG(c));
|
CLK_OUT_ENB_CLR + PERIPH_CLK_TO_ENB_SET_REG(c));
|
||||||
}
|
}
|
||||||
|
|
||||||
void tegra2_periph_reset_deassert(struct clk *c)
|
static void tegra2_periph_clk_reset(struct clk *c, bool assert)
|
||||||
{
|
{
|
||||||
pr_debug("%s on clock %s\n", __func__, c->name);
|
unsigned long base = assert ? RST_DEVICES_SET : RST_DEVICES_CLR;
|
||||||
|
|
||||||
|
pr_debug("%s %s on clock %s\n", __func__,
|
||||||
|
assert ? "assert" : "deassert", c->name);
|
||||||
if (!(c->flags & PERIPH_NO_RESET))
|
if (!(c->flags & PERIPH_NO_RESET))
|
||||||
clk_writel(PERIPH_CLK_TO_ENB_BIT(c),
|
clk_writel(PERIPH_CLK_TO_ENB_BIT(c),
|
||||||
RST_DEVICES_CLR + PERIPH_CLK_TO_ENB_SET_REG(c));
|
base + PERIPH_CLK_TO_ENB_SET_REG(c));
|
||||||
}
|
}
|
||||||
|
|
||||||
void tegra2_periph_reset_assert(struct clk *c)
|
|
||||||
{
|
|
||||||
pr_debug("%s on clock %s\n", __func__, c->name);
|
|
||||||
if (!(c->flags & PERIPH_NO_RESET))
|
|
||||||
clk_writel(PERIPH_CLK_TO_ENB_BIT(c),
|
|
||||||
RST_DEVICES_SET + PERIPH_CLK_TO_ENB_SET_REG(c));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static int tegra2_periph_clk_set_parent(struct clk *c, struct clk *p)
|
static int tegra2_periph_clk_set_parent(struct clk *c, struct clk *p)
|
||||||
{
|
{
|
||||||
u32 val;
|
u32 val;
|
||||||
|
@ -1002,6 +1008,7 @@ static struct clk_ops tegra_periph_clk_ops = {
|
||||||
.set_parent = &tegra2_periph_clk_set_parent,
|
.set_parent = &tegra2_periph_clk_set_parent,
|
||||||
.set_rate = &tegra2_periph_clk_set_rate,
|
.set_rate = &tegra2_periph_clk_set_rate,
|
||||||
.round_rate = &tegra2_periph_clk_round_rate,
|
.round_rate = &tegra2_periph_clk_round_rate,
|
||||||
|
.reset = &tegra2_periph_clk_reset,
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Clock doubler ops */
|
/* Clock doubler ops */
|
||||||
|
|
Loading…
Reference in New Issue