diff options
56 files changed, 2110 insertions, 423 deletions
diff --git a/arch/arm/mach-omap1/devices.c b/arch/arm/mach-omap1/devices.c index 0cc54dd553e..726c02c9c0c 100644 --- a/arch/arm/mach-omap1/devices.c +++ b/arch/arm/mach-omap1/devices.c @@ -357,6 +357,33 @@ static inline void omap_init_uwire(void) {} #endif +#define OMAP1_RNG_BASE 0xfffe5000 + +static struct resource omap1_rng_resources[] = { + { + .start = OMAP1_RNG_BASE, + .end = OMAP1_RNG_BASE + 0x4f, + .flags = IORESOURCE_MEM, + }, +}; + +static struct platform_device omap1_rng_device = { + .name = "omap_rng", + .id = -1, + .num_resources = ARRAY_SIZE(omap1_rng_resources), + .resource = omap1_rng_resources, +}; + +static void omap1_init_rng(void) +{ + if (!cpu_is_omap16xx()) + return; + + (void) platform_device_register(&omap1_rng_device); +} + +/*-------------------------------------------------------------------------*/ + /* * This gets called after board-specific INIT_MACHINE, and initializes most * on-chip peripherals accessible on this board (except for few like USB): @@ -395,6 +422,7 @@ static int __init omap1_init_devices(void) omap_init_spi100k(); omap_init_sti(); omap_init_uwire(); + omap1_init_rng(); return 0; } diff --git a/arch/arm/mach-omap1/timer.c b/arch/arm/mach-omap1/timer.c index aa81593db1a..cdeb9d3ef64 100644 --- a/arch/arm/mach-omap1/timer.c +++ b/arch/arm/mach-omap1/timer.c @@ -141,7 +141,7 @@ static int __init omap1_dm_timer_init(void) pdata->set_timer_src = omap1_dm_timer_set_src; pdata->timer_capability = OMAP_TIMER_ALWON | - OMAP_TIMER_NEEDS_RESET; + OMAP_TIMER_NEEDS_RESET | OMAP_TIMER_HAS_DSP_IRQ; ret = platform_device_add_data(pdev, pdata, sizeof(*pdata)); if (ret) { diff --git a/arch/arm/mach-omap2/Makefile b/arch/arm/mach-omap2/Makefile index 845202358dd..b807deb0f52 100644 --- a/arch/arm/mach-omap2/Makefile +++ b/arch/arm/mach-omap2/Makefile @@ -179,6 +179,7 @@ obj-$(CONFIG_ARCH_OMAP4) += omap_hwmod_44xx_data.o # EMU peripherals obj-$(CONFIG_OMAP3_EMU) += emu.o +obj-$(CONFIG_HW_PERF_EVENTS) += pmu.o # L3 interconnect obj-$(CONFIG_ARCH_OMAP3) += omap_l3_smx.o diff --git a/arch/arm/mach-omap2/board-apollon.c b/arch/arm/mach-omap2/board-apollon.c index 3e2d76f05af..cea3abace81 100644 --- a/arch/arm/mach-omap2/board-apollon.c +++ b/arch/arm/mach-omap2/board-apollon.c @@ -202,7 +202,7 @@ static inline void __init apollon_init_smc91x(void) return; } - clk_enable(gpmc_fck); + clk_prepare_enable(gpmc_fck); rate = clk_get_rate(gpmc_fck); eth_cs = APOLLON_ETH_CS; @@ -246,7 +246,7 @@ static inline void __init apollon_init_smc91x(void) gpmc_cs_free(APOLLON_ETH_CS); } out: - clk_disable(gpmc_fck); + clk_disable_unprepare(gpmc_fck); clk_put(gpmc_fck); } diff --git a/arch/arm/mach-omap2/board-h4.c b/arch/arm/mach-omap2/board-h4.c index f6c48dd764f..8d04bf851af 100644 --- a/arch/arm/mach-omap2/board-h4.c +++ b/arch/arm/mach-omap2/board-h4.c @@ -265,9 +265,9 @@ static inline void __init h4_init_debug(void) return; } - clk_enable(gpmc_fck); + clk_prepare_enable(gpmc_fck); rate = clk_get_rate(gpmc_fck); - clk_disable(gpmc_fck); + clk_disable_unprepare(gpmc_fck); clk_put(gpmc_fck); if (is_gpmc_muxed()) @@ -311,7 +311,7 @@ static inline void __init h4_init_debug(void) gpmc_cs_free(eth_cs); out: - clk_disable(gpmc_fck); + clk_disable_unprepare(gpmc_fck); clk_put(gpmc_fck); } diff --git a/arch/arm/mach-omap2/board-omap4panda.c b/arch/arm/mach-omap2/board-omap4panda.c index 8ebb16c5182..556e777b9c4 100644 --- a/arch/arm/mach-omap2/board-omap4panda.c +++ b/arch/arm/mach-omap2/board-omap4panda.c @@ -171,7 +171,7 @@ static void __init omap4_ehci_init(void) return; } clk_set_rate(phy_ref_clk, 19200000); - clk_enable(phy_ref_clk); + clk_prepare_enable(phy_ref_clk); /* disable the power to the usb hub prior to init and reset phy+hub */ ret = gpio_request_array(panda_ehci_gpios, diff --git a/arch/arm/mach-omap2/clkt2xxx_apll.c b/arch/arm/mach-omap2/clkt2xxx_apll.c index b19a1f7234a..c2d15212d64 100644 --- a/arch/arm/mach-omap2/clkt2xxx_apll.c +++ b/arch/arm/mach-omap2/clkt2xxx_apll.c @@ -59,7 +59,7 @@ static int omap2_clk_apll_enable(struct clk *clk, u32 status_mask) omap2_cm_write_mod_reg(cval, PLL_MOD, CM_CLKEN); omap2_cm_wait_idlest(cm_idlest_pll, status_mask, - OMAP24XX_CM_IDLEST_VAL, clk->name); + OMAP24XX_CM_IDLEST_VAL, __clk_get_name(clk)); /* * REVISIT: Should we return an error code if omap2_wait_clock_ready() diff --git a/arch/arm/mach-omap2/clkt2xxx_virt_prcm_set.c b/arch/arm/mach-omap2/clkt2xxx_virt_prcm_set.c index cabcfdba524..3524f0e7b6d 100644 --- a/arch/arm/mach-omap2/clkt2xxx_virt_prcm_set.c +++ b/arch/arm/mach-omap2/clkt2xxx_virt_prcm_set.c @@ -68,14 +68,15 @@ unsigned long omap2_table_mpu_recalc(struct clk *clk) long omap2_round_to_table_rate(struct clk *clk, unsigned long rate) { const struct prcm_config *ptr; - long highest_rate; + long highest_rate, sys_clk_rate; highest_rate = -EINVAL; + sys_clk_rate = __clk_get_rate(sclk); for (ptr = rate_table; ptr->mpu_speed; ptr++) { if (!(ptr->flags & cpu_mask)) continue; - if (ptr->xtal_speed != sclk->rate) + if (ptr->xtal_speed != sys_clk_rate) continue; highest_rate = ptr->mpu_speed; @@ -94,12 +95,15 @@ int omap2_select_table_rate(struct clk *clk, unsigned long rate) const struct prcm_config *prcm; unsigned long found_speed = 0; unsigned long flags; + long sys_clk_rate; + + sys_clk_rate = __clk_get_rate(sclk); for (prcm = rate_table; prcm->mpu_speed; prcm++) { if (!(prcm->flags & cpu_mask)) continue; - if (prcm->xtal_speed != sclk->rate) + if (prcm->xtal_speed != sys_clk_rate) continue; if (prcm->mpu_speed <= rate) { diff --git a/arch/arm/mach-omap2/clkt34xx_dpll3m2.c b/arch/arm/mach-omap2/clkt34xx_dpll3m2.c index 298887b5bf6..7c6da2f731d 100644 --- a/arch/arm/mach-omap2/clkt34xx_dpll3m2.c +++ b/arch/arm/mach-omap2/clkt34xx_dpll3m2.c @@ -56,6 +56,7 @@ int omap3_core_dpll_m2_set_rate(struct clk *clk, unsigned long rate) struct omap_sdrc_params *sdrc_cs0; struct omap_sdrc_params *sdrc_cs1; int ret; + unsigned long clkrate; if (!clk || !rate) return -EINVAL; @@ -64,11 +65,12 @@ int omap3_core_dpll_m2_set_rate(struct clk *clk, unsigned long rate) if (validrate != rate) return -EINVAL; - sdrcrate = sdrc_ick_p->rate; - if (rate > clk->rate) - sdrcrate <<= ((rate / clk->rate) >> 1); + sdrcrate = __clk_get_rate(sdrc_ick_p); + clkrate = __clk_get_rate(clk); + if (rate > clkrate) + sdrcrate <<= ((rate / clkrate) >> 1); else - sdrcrate >>= ((clk->rate / rate) >> 1); + sdrcrate >>= ((clkrate / rate) >> 1); ret = omap2_sdrc_get_params(sdrcrate, &sdrc_cs0, &sdrc_cs1); if (ret) @@ -82,7 +84,7 @@ int omap3_core_dpll_m2_set_rate(struct clk *clk, unsigned long rate) /* * XXX This only needs to be done when the CPU frequency changes */ - _mpurate = arm_fck_p->rate / CYCLES_PER_MHZ; + _mpurate = __clk_get_rate(arm_fck_p) / CYCLES_PER_MHZ; c = (_mpurate << SDRC_MPURATE_SCALE) >> SDRC_MPURATE_BASE_SHIFT; c += 1; /* for safety */ c *= SDRC_MPURATE_LOOPS; @@ -90,8 +92,8 @@ int omap3_core_dpll_m2_set_rate(struct clk *clk, unsigned long rate) if (c == 0) c = 1; - pr_debug("clock: changing CORE DPLL rate from %lu to %lu\n", clk->rate, - validrate); + pr_debug("clock: changing CORE DPLL rate from %lu to %lu\n", + clkrate, validrate); pr_debug("clock: SDRC CS0 timing params used: RFR %08x CTRLA %08x CTRLB %08x MR %08x\n", sdrc_cs0->rfr_ctrl, sdrc_cs0->actim_ctrla, sdrc_cs0->actim_ctrlb, sdrc_cs0->mr); @@ -102,14 +104,14 @@ int omap3_core_dpll_m2_set_rate(struct clk *clk, unsigned long rate) if (sdrc_cs1) omap3_configure_core_dpll( - new_div, unlock_dll, c, rate > clk->rate, + new_div, unlock_dll, c, rate > clkrate, sdrc_cs0->rfr_ctrl, sdrc_cs0->actim_ctrla, sdrc_cs0->actim_ctrlb, sdrc_cs0->mr, sdrc_cs1->rfr_ctrl, sdrc_cs1->actim_ctrla, sdrc_cs1->actim_ctrlb, sdrc_cs1->mr); else omap3_configure_core_dpll( - new_div, unlock_dll, c, rate > clk->rate, + new_div, unlock_dll, c, rate > clkrate, sdrc_cs0->rfr_ctrl, sdrc_cs0->actim_ctrla, sdrc_cs0->actim_ctrlb, sdrc_cs0->mr, 0, 0, 0, 0); diff --git a/arch/arm/mach-omap2/clkt_clksel.c b/arch/arm/mach-omap2/clkt_clksel.c index 19a980956d4..eaed3900a83 100644 --- a/arch/arm/mach-omap2/clkt_clksel.c +++ b/arch/arm/mach-omap2/clkt_clksel.c @@ -72,7 +72,7 @@ static const struct clksel *_get_clksel_by_parent(struct clk *clk, if (!clks->parent) { /* This indicates a data problem */ WARN(1, "clock: %s: could not find parent clock %s in clksel array\n", - clk->name, src_clk->name); + __clk_get_name(clk), __clk_get_name(src_clk)); return NULL; } @@ -127,7 +127,8 @@ static u8 _get_div_and_fieldval(struct clk *src_clk, struct clk *clk, if (max_div == 0) { /* This indicates an error in the clksel data */ WARN(1, "clock: %s: could not find divisor for parent %s\n", - clk->name, src_clk->parent->name); + __clk_get_name(clk), + __clk_get_name(__clk_get_parent(src_clk))); return 0; } @@ -176,8 +177,10 @@ static u32 _clksel_to_divisor(struct clk *clk, u32 field_val) { const struct clksel *clks; const struct clksel_rate *clkr; + struct clk *parent; - clks = _get_clksel_by_parent(clk, clk->parent); + parent = __clk_get_parent(clk); + clks = _get_clksel_by_parent(clk, parent); if (!clks) return 0; @@ -191,8 +194,8 @@ static u32 _clksel_to_divisor(struct clk *clk, u32 field_val) if (!clkr->div) { /* This indicates a data error */ - WARN(1, "clock: %s: could not find fieldval %d parent %s\n", - clk->name, field_val, clk->parent->name); + WARN(1, "clock: %s: could not find fieldval %d for parent %s\n", + __clk_get_name(clk), field_val, __clk_get_name(parent)); return 0; } @@ -213,11 +216,13 @@ static u32 _divisor_to_clksel(struct clk *clk, u32 div) { const struct clksel *clks; const struct clksel_rate *clkr; + struct clk *parent; /* should never happen */ WARN_ON(div == 0); - clks = _get_clksel_by_parent(clk, clk->parent); + parent = __clk_get_parent(clk); + clks = _get_clksel_by_parent(clk, parent); if (!clks) return ~0; @@ -230,8 +235,8 @@ static u32 _divisor_to_clksel(struct clk *clk, u32 div) } if (!clkr->div) { - pr_err("clock: %s: could not find divisor %d parent %s\n", - clk->name, div, clk->parent->name); + pr_err("clock: %s: could not find divisor %d for parent %s\n", + __clk_get_name(clk), div, __clk_get_name(parent)); return ~0; } @@ -281,16 +286,23 @@ u32 omap2_clksel_round_rate_div(struct clk *clk, unsigned long target_rate, const struct clksel *clks; const struct clksel_rate *clkr; u32 last_div = 0; + struct clk *parent; + unsigned long parent_rate; + const char *clk_name; + + parent = __clk_get_parent(clk); + parent_rate = __clk_get_rate(parent); + clk_name = __clk_get_name(clk); if (!clk->clksel || !clk->clksel_mask) return ~0; pr_debug("clock: clksel_round_rate_div: %s target_rate %ld\n", - clk->name, target_rate); + clk_name, target_rate); *new_div = 1; - clks = _get_clksel_by_parent(clk, clk->parent); + clks = _get_clksel_by_parent(clk, parent); if (!clks) return ~0; @@ -300,29 +312,29 @@ u32 omap2_clksel_round_rate_div(struct clk *clk, unsigned long target_rate, /* Sanity check */ if (clkr->div <= last_div) - pr_err("clock: %s: clksel_rate table not sorted", - clk->name); + pr_err("clock: %s: clksel_rate table not sorted\n", + clk_name); last_div = clkr->div; - test_rate = clk->parent->rate / clkr->div; + test_rate = parent_rate / clkr->div; if (test_rate <= target_rate) break; /* found it */ } if (!clkr->div) { - pr_err("clock: %s: could not find divisor for target rate %ld parent %s\n", - clk->name, target_rate, clk->parent->name); + pr_err("clock: %s: could not find divisor for target rate %ld for parent %s\n", + clk_name, target_rate, __clk_get_name(parent)); return ~0; } *new_div = clkr->div; pr_debug("clock: new_div = %d, new_rate = %ld\n", *new_div, - (clk->parent->rate / clkr->div)); + (parent_rate / clkr->div)); - return clk->parent->rate / clkr->div; + return parent_rate / clkr->div; } /* @@ -344,10 +356,15 @@ void omap2_init_clksel_parent(struct clk *clk) const struct clksel *clks; const struct clksel_rate *clkr; u32 r, found = 0; + struct clk *parent; + const char *clk_name; if (!clk->clksel || !clk->clksel_mask) return; + parent = __clk_get_parent(clk); + clk_name = __clk_get_name(clk); + r = __raw_readl(clk->clksel_reg) & clk->clksel_mask; r >>= __ffs(clk->clksel_mask); @@ -357,11 +374,13 @@ void omap2_init_clksel_parent(struct clk *clk) continue; if (clkr->val == r) { - if (clk->parent != clks->parent) { + if (parent != clks->parent) { pr_debug("clock: %s: inited parent to %s (was %s)\n", - clk->name, clks->parent->name, - ((clk->parent) ? - clk->parent->name : "NULL")); + clk_name, + __clk_get_name(clks->parent), + ((parent) ? + __clk_get_name(parent) : + "NULL")); clk_reparent(clk, clks->parent); }; found = 1; @@ -371,7 +390,7 @@ void omap2_init_clksel_parent(struct clk *clk) /* This indicates a data error */ WARN(!found, "clock: %s: init parent: could not find regval %0x\n", - clk->name, r); + clk_name, r); return; } @@ -389,15 +408,17 @@ unsigned long omap2_clksel_recalc(struct clk *clk) { unsigned long rate; u32 div = 0; + struct clk *parent; div = _read_divisor(clk); if (div == 0) - return clk->rate; + return __clk_get_rate(clk); - rate = clk->parent->rate / div; + parent = __clk_get_parent(clk); + rate = __clk_get_rate(parent) / div; - pr_debug("clock: %s: recalc'd rate is %ld (div %d)\n", clk->name, - rate, div); + pr_debug("clock: %s: recalc'd rate is %ld (div %d)\n", + __clk_get_name(clk), rate, div); return rate; } @@ -452,9 +473,10 @@ int omap2_clksel_set_rate(struct clk *clk, unsigned long rate) _write_clksel_reg(clk, field_val); - clk->rate = clk->parent->rate / new_div; + clk->rate = __clk_get_rate(__clk_get_parent(clk)) / new_div; - pr_debug("clock: %s: set rate to %ld\n", clk->name, clk->rate); + pr_debug("clock: %s: set rate to %ld\n", __clk_get_name(clk), + __clk_get_rate(clk)); return 0; } @@ -496,13 +518,15 @@ int omap2_clksel_set_parent(struct clk *clk, struct clk *new_parent) clk_reparent(clk, new_parent); /* CLKSEL clocks follow their parents' rates, divided by a divisor */ - clk->rate = new_parent->rate; + clk->rate = __clk_get_rate(new_parent); if (parent_div > 0) - clk->rate /= parent_div; + __clk_get_rate(clk) /= parent_div; pr_debug("clock: %s: set parent to %s (new rate %ld)\n", - clk->name, clk->parent->name, clk->rate); + __clk_get_name(clk), + __clk_get_name(__clk_get_parent(clk)), + __clk_get_rate(clk)); return 0; } diff --git a/arch/arm/mach-omap2/clkt_dpll.c b/arch/arm/mach-omap2/clkt_dpll.c index 83b658bf385..80411142f48 100644 --- a/arch/arm/mach-omap2/clkt_dpll.c +++ b/arch/arm/mach-omap2/clkt_dpll.c @@ -87,7 +87,7 @@ static int _dpll_test_fint(struct clk *clk, u8 n) dd = clk->dpll_data; /* DPLL divider must result in a valid jitter correction val */ - fint = clk->parent->rate / n; + fint = __clk_get_rate(__clk_get_parent(clk)) / n; if (cpu_is_omap24xx()) { /* Should not be called for OMAP2, so warn if it is called */ @@ -252,16 +252,16 @@ u32 omap2_get_dpll_rate(struct clk *clk) if (cpu_is_omap24xx()) { if (v == OMAP2XXX_EN_DPLL_LPBYPASS || v == OMAP2XXX_EN_DPLL_FRBYPASS) - return dd->clk_bypass->rate; + return __clk_get_rate(dd->clk_bypass); } else if (cpu_is_omap34xx()) { if (v == OMAP3XXX_EN_DPLL_LPBYPASS || v == OMAP3XXX_EN_DPLL_FRBYPASS) - return dd->clk_bypass->rate; + return __clk_get_rate(dd->clk_bypass); } else if (soc_is_am33xx() || cpu_is_omap44xx()) { if (v == OMAP4XXX_EN_DPLL_LPBYPASS || v == OMAP4XXX_EN_DPLL_FRBYPASS || v == OMAP4XXX_EN_DPLL_MNBYPASS) - return dd->clk_bypass->rate; + return __clk_get_rate(dd->clk_bypass); } v = __raw_readl(dd->mult_div1_reg); @@ -270,7 +270,7 @@ u32 omap2_get_dpll_rate(struct clk *clk) dpll_div = v & dd->div1_mask; dpll_div >>= __ffs(dd->div1_mask); - dpll_clk = (long long)dd->clk_ref->rate * dpll_mult; + dpll_clk = (long long) __clk_get_rate(dd->clk_ref) * dpll_mult; do_div(dpll_clk, dpll_div + 1); return dpll_clk; @@ -296,16 +296,20 @@ long omap2_dpll_round_rate(struct clk *clk, unsigned long target_rate) unsigned long scaled_rt_rp; unsigned long new_rate = 0; struct dpll_data *dd; + unsigned long ref_rate; + const char *clk_name; if (!clk || !clk->dpll_data) return ~0; dd = clk->dpll_data; + ref_rate = __clk_get_rate(dd->clk_ref); + clk_name = __clk_get_name(clk); pr_debug("clock: %s: starting DPLL round_rate, target rate %ld\n", - clk->name, target_rate); + clk_name, target_rate); - scaled_rt_rp = target_rate / (dd->clk_ref->rate / DPLL_SCALE_FACTOR); + scaled_rt_rp = target_rate / (ref_rate / DPLL_SCALE_FACTOR); scaled_max_m = dd->max_multiplier * DPLL_SCALE_FACTOR; dd->last_rounded_rate = 0; @@ -332,14 +336,14 @@ long omap2_dpll_round_rate(struct clk *clk, unsigned long target_rate) break; r = _dpll_test_mult(&m, n, &new_rate, target_rate, - dd->clk_ref->rate); + ref_rate); /* m can't be set low enough for this n - try with a larger n */ if (r == DPLL_MULT_UNDERFLOW) continue; pr_debug("clock: %s: m = %d: n = %d: new_rate = %ld\n", - clk->name, m, n, new_rate); + clk_name, m, n, new_rate); if (target_rate == new_rate) { dd->last_rounded_m = m; @@ -350,8 +354,8 @@ long omap2_dpll_round_rate(struct clk *clk, unsigned long target_rate) } if (target_rate != new_rate) { - pr_debug("clock: %s: cannot round to rate %ld\n", clk->name, - target_rate); + pr_debug("clock: %s: cannot round to rate %ld\n", + clk_name, target_rate); return ~0; } diff --git a/arch/arm/mach-omap2/clock.c b/arch/arm/mach-omap2/clock.c index e97f98ffe8b..961ac8f7e13 100644 --- a/arch/arm/mach-omap2/clock.c +++ b/arch/arm/mach-omap2/clock.c @@ -78,7 +78,7 @@ static void _omap2_module_wait_ready(struct clk *clk) clk->ops->find_idlest(clk, &idlest_reg, &idlest_bit, &idlest_val); omap2_cm_wait_idlest(idlest_reg, (1 << idlest_bit), idlest_val, - clk->name); + __clk_get_name(clk)); } /* Public functions */ @@ -94,18 +94,21 @@ static void _omap2_module_wait_ready(struct clk *clk) void omap2_init_clk_clkdm(struct clk *clk) { struct clockdomain *clkdm; + const char *clk_name; |